Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add option to close an Axis3's outline box #2349

Open
fatteneder opened this issue Oct 20, 2022 · 5 comments · May be fixed by #4305
Open

Add option to close an Axis3's outline box #2349

fatteneder opened this issue Oct 20, 2022 · 5 comments · May be fixed by #4305
Labels
Axis3 related to Axis3 enhancement Feature requests and enhancements good first issue This should come with some instructions! Makie Backend independent issues (Makie core)

Comments

@fatteneder
Copy link
Contributor

As requested on Discord, implement the ax.BoxStyle = 'full'; option from MATLAB here: https://www.mathworks.com/help/matlab/ref/box.html

I think that might be a good first issue. Could somebody please add a tag?

@asinghvi17 asinghvi17 added good first issue This should come with some instructions! Makie Backend independent issues (Makie core) labels Feb 6, 2023
@ffreyer ffreyer added enhancement Feature requests and enhancements Axis3 related to Axis3 labels Aug 23, 2024
@lukashappe
Copy link

lukashappe commented Aug 27, 2024

Description

I started working on this. So far I can close the outlinebox after adding fields for the color of Spine 4 to the Axis3-type and modifying add_gridlines_and_frames! to optinaly use either 6 or 8 Points to make the Framelines. I controll this by setting and the field fullbox I also added to the Axis3-type.
Now first this seems to work and close the outlinebox. But when I put data inside the box the new spines are obviously still shown behind the data.

Question

Can someone give me a hint how tho achieve that the front spines are shown above the contents of the box?

Changes in the code

#in types.jl
@Block Axis3 <: AbstractAxis begin
...
"Controls if the 4. Spines are created to close the outline box"
fullbox = false
"The color of x spine 4"
xspinecolor_4 = :black
"The color of y spine 4"
yspinecolor_4 = :black
"The color of z spine 4"
zspinecolor_4 = :black
"The x spine width"
...


#in axis3d.jl
function add_gridlines_and_frames!(topscene, scene, ax, dim::Int, limits, ticknode, miv, min1, min2, xreversed, yreversed, zreversed)
...
 framepoints = lift(limits, scene.camera.projectionview, scene.viewport, min1, min2, xreversed, yreversed, zreversed
            ) do lims, _, pxa, mi1, mi2, xrev, yrev, zrev
        o = pxa.origin

        rev1 = (xrev, yrev, zrev)[d1]
        rev2 = (xrev, yrev, zrev)[d2]

        mi1 = mi1 ⊻ rev1
        mi2 = mi2 ⊻ rev2

        f(mi) = mi ? minimum : maximum
        p1 = dpoint(minimum(lims)[dim], f(!mi1)(lims)[d1], f(mi2)(lims)[d2])
        p2 = dpoint(maximum(lims)[dim], f(!mi1)(lims)[d1], f(mi2)(lims)[d2])
        p3 = dpoint(minimum(lims)[dim], f(mi1)(lims)[d1], f(mi2)(lims)[d2])
        p4 = dpoint(maximum(lims)[dim], f(mi1)(lims)[d1], f(mi2)(lims)[d2])
        p5 = dpoint(minimum(lims)[dim], f(mi1)(lims)[d1], f(!mi2)(lims)[d2])
        p6 = dpoint(maximum(lims)[dim], f(mi1)(lims)[d1], f(!mi2)(lims)[d2])
        p7 = dpoint(minimum(lims)[dim], f(!mi1)(lims)[d1], f(!mi2)(lims)[d2])
        p8 = dpoint(maximum(lims)[dim], f(!mi1)(lims)[d1], f(!mi2)(lims)[d2])

        # we are going to transform the 3d frame points into 2d of the topscene
        # because otherwise the frame lines can
        # be cut when they lie directly on the scene boundary
        if ax.fullbox[] == true
            to_topscene_z_2d.([p1, p2, p3, p4, p5, p6, p7, p8], Ref(scene))
        else 
            to_topscene_z_2d.([p1, p2, p3, p4, p5, p6], Ref(scene))
        end    
    end
    colors = Observable{Any}()
    if ax.fullbox[] == true
        map!(vcat, colors, attr(:spinecolor_1), attr(:spinecolor_2), attr(:spinecolor_3), attr(:spinecolor_4))
    else
        map!(vcat, colors, attr(:spinecolor_1), attr(:spinecolor_2), attr(:spinecolor_3))
    end
    framelines = linesegments!(topscene, framepoints, color = colors, linewidth = attr(:spinewidth),
    # transparency = true,
visible = attr(:spinesvisible), inspectable = false)
...

@ffreyer
Copy link
Collaborator

ffreyer commented Aug 27, 2024

Oh there is also already a pr for this, but it seems to have stalled. #2742

The lines end up behind because of

function to_topscene_z_2d(p3d, scene)
o = scene.viewport[].origin
p2d = Point2f(o + Makie.project(scene, p3d))
# -10000 is an arbitrary weird constant that in preliminary testing didn't seem
# to clip into plot objects anymore
Point3f(p2d..., -10000)
end

That projects the 3D coordinates into screen space and then sets their depth values to the lowest possible value, i.e. as far behind as possible. Continuing this infrastructure would require you to figure out which lines are in front and set them (start and end point) to +10000 z.

@lukashappe
Copy link

lukashappe commented Aug 27, 2024

Thanks for that fast answer!
I tried to set the value in the function you mentioned to +10000. If i understand you right this should result in all the lines beeing displayed in front.

function to_topscene_z_2d(p3d, scene)
    o = scene.viewport[].origin
    p2d = Point2f(o + Makie.project(scene, p3d))
    # -10000 is an arbitrary weird constant that in preliminary testing didn't seem
    # to clip into plot objects anymore
    Point3f(p2d..., 10000)
end

But this is not the case. Actually I didn't notice any changes in my plots.

@lukashappe
Copy link

Thanks for that fast answer! I tried to set the value in the function you mentioned to +10000. If i understand you right this should result in all the lines beeing displayed in front.

function to_topscene_z_2d(p3d, scene)
    o = scene.viewport[].origin
    p2d = Point2f(o + Makie.project(scene, p3d))
    # -10000 is an arbitrary weird constant that in preliminary testing didn't seem
    # to clip into plot objects anymore
    Point3f(p2d..., 10000)
end

But this is not the case. Actually I didn't notice any changes in my plots.

Oh, I just found out that this is backend dependent.
It does what you predicted when I use GLMakie. (Was using CairoMakie before)
Any suggestions what to do next?

@ffreyer
Copy link
Collaborator

ffreyer commented Aug 31, 2024

Ah yes, this wouldn't be expected to work in CairoMakie.

I guess add an Attribute to Axis3 to control whether the full frame is drawn or not?

@lukashappe lukashappe linked a pull request Sep 3, 2024 that will close this issue
1 task
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Axis3 related to Axis3 enhancement Feature requests and enhancements good first issue This should come with some instructions! Makie Backend independent issues (Makie core)
Projects
Status: No status
Development

Successfully merging a pull request may close this issue.

4 participants