The VS Code plot navigator and Makie

I want to clarify something that confused me when using CairoMakie and GLMakie in Visual Studio Code. I couldn’t find an explanation in the Makie documentation, so I’ll make a topic here to help anyone else who runs into this.

When using Makie.jl in VS Code, the choice of backend affects whether the plot appears in VS Code’s plot navigator or in a separate window. I’ll cover each one separately.

Using GLMakie

When making a figure in GLMakie, the figure is displayed in a separate window and not in the plot navigator. (This is fine. I’m not complaining. Actually, I like this feature.) As you add code to the figure, the window will update itself, a very nice feature. Here is an example:

f = Figure();
sc = display(f);

##

Evaluating the code until this point will generate a blank window. Continuing,

ax = Axis(f[1, 1], title = "Figure 1", xlabel = "x", ylabel = "y")
x = range(-10, stop=10, length = 20)
y = x.^2
scatter!(ax, x, y, label = "Data")
##

Now a parabola will be added to the figure. A second plot can be added:

ax2 = Axis(f[1, 2], tite = "Figure 2", xlabel = "x", ylabel = "y")
for i in 1:4
    lines!(ax2, cumsum(randn(100)), label = "%i")
end

##

You can change the theme, but you have to re-plot everything afterward:

set_theme!(theme_dark())

When I was watching the JuliaCon2021 Makie talk, I was wondering why there were ## in the code. These tell the editor to evaluate until that point (typing Shift + Enter). Convenient.

Using CairoMakie

With CairoMakie, plots appear in the plot navigator and not in a separate window. Also, you cannot successively add to the figure. Each time you evaluate, a new figure is generated. So if you just evaluate

f = Figure();
sc = display(f);

a blank figure is generated. If you then evaluate

ax = Axis(f[1, 1], title = "Figure 1", xlabel = "x", ylabel = "y")
x = range(-10, stop=10, length = 20)
y = x.^2
scatter!(ax, x, y, label = "Data")
current_figure()

a new figure with the parabola is generated. Note that you have to use either f or current_figure() to show the figure, which should be placed at the end of your code. With CairoMakie, you generate the entire figure at once whereas you can generate the figure piecemeal with GLMakie.

Concluding thoughts

Personally, sometimes I like to see the figure generated as I go in a separate window when I’m doing some kind of analysis. In these cases, I need to check if my analysis is working correctly and I don’t want one hundred useless plots in the plot navigator (e.g. I’m plotting best fit curves and want to plot the data, the guess, and the best fit). Other times, I like the plot navigator because I can browse several versions of a figure. Of course, CairoMakie generates publication-quality plots and should be used for final production and GLMakie emphasizes performance.

I think I got all of that right, but if I missed something or there are more details to add, please add to the discussion. I only just started learning Julia a month ago and welcome feedback on best practices and whatnot.

Versions:
Julia 1.6.2
CairoMakie 0.6.5
GLMakie 0.4.6
Julia VS Code plugin 1.4.0
VS Code 1.60.0

Here's the full code for my example
using CairoMakie
using GLMakie

##

GLMakie.activate!()
# CairoMakie.activate!()

f = Figure(resolution = (800, 600));
sc = display(f);
##

ax = Axis(f[1, 1], title = "Figure 1", xlabel = "x", ylabel = "y")
x = range(-10, stop=10, length = 20)
y = x.^2
scatter!(ax, x, y, label = "Data")

##

ax2 = Axis(f[1, 2], tite = "Figure 2", xlabel = "x", ylabel = "y")
for i in 1:4
    lines!(ax2, cumsum(randn(100)), label = "%i")
end

# current_figure()

##

set_theme!(theme_light())
8 Likes

Note that if you run Makie.inline!(true), GLMakie plots also appear in the navigator. The difference is whether GLMakie routes into its own display system or the normal stack, which has the plot pane if you’re in VSCode and haven’t disabled it.

6 Likes

Thank you for that clarification.

1 Like

Is there any way to make CairoMakie ‘replace’ a previous plot, if I’m updating a figure? Due to my workflow, a lot of half-finished plots tend to accumulate in the plot navigator, sometimes a couple of hundred, most of them no longer useful.

Even just a way to programmatically delete certain plots, instead of having to push a button would be useful.

That would have to be a VSCode feature, because CairoMakie just hands off its plot data to VSCode. Maybe that would be a good feature request, then one could activate like a “current plot” object that would replace previous ones while active

1 Like

That’s tricky, but I suspect the main issue here is that using a ; to suppress displaying results didn’t work in VSCode for the longest time (it’s fixed now though).

But there is a button that lets me delete plots in a targeted manner. Do you think there is some way to ‘push’ it programmatically?

Not currently, no. We could add a function to VSCodeServer or a special MIME type that would delete the last or all plots, but I’m not convinced that’d be a good idea.The right solution would probably be to let the plotting framework supply a figure id, so that the frontend can make sure to only display a figure once and replace the content on the next display call.

2 Likes

I’ve been looking for this quiet a while now too.

Looking at my 12015th plot (live convergence statistics) I thought I’d just +1 this :slight_smile:

So: Any of pfitzseb’s suggestions would be awesome.

1 Like

https://github.com/julia-vscode/julia-vscode/pull/2940

Thank you for this explanation! I tried this in vscode, but unfortunately I’m not able to get any output at all. Plot windows are generated in REPL, but I can’t get even a blank window in VS Code. Any ideas?

If you copy the code at the bottom of my post (the “full code”) then it should work. This is pretty old now, but I just tested it and it still works for the latest versions of Julia and Makie (there is one typo in ax2. I wrote tite but it should be title). Copy the full example, paste into a Julia file in VS Code and evaluate by either pressing the “play” button or pressing alt+Enter (evaluate until the next ##) or shift+Enter (evaluate one line).

A common misstep among beginners is forgetting to activate the Julia environment for the project you are working on. Usually this is as easy as typing ]activate . in the REPL in VS Code to activate the environment for the current folder. Also check out the Getting Started tutorial for VS Code.

Minor note:
You can delete the semicolons ; – they are not necessary.

Interesting, it still doesn’t work but I do get a blank window now. It just closes by itself after 15 or so seconds. I’ll go check out the Getting Started tutorial, and thank you for the reply!

That sounds like something weird is going on. You could try quitting the Julia session and restarting everything. Also, make sure everything is up to date. Julia version 1.8.5 is the latest now and you can update your packages by typing: ]up