# How to implement interactive plots in IJulia

**URL:** <https://discourse.julialang.org/t/how-to-implement-interactive-plots-in-ijulia/9284>\
**Category:** Visualization\
**Tags:** question, plotting, interactivity\
**Created:** [February 23, 2018, 6:39pm UTC](https://discourse.julialang.org/t/how-to-implement-interactive-plots-in-ijulia/9284 "2018-02-23T18:39:25Z")\
**Posts on this page:** 12\
**Page:** 1

<div class="post-metadata">

**Author:** ![mbaz](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/mbaz/32/17295_2.png) [@mbaz](https://discourse.julialang.org/u/mbaz)\
**Post date:** [February 23, 2018, 6:39pm UTC](https://discourse.julialang.org/t/how-to-implement-interactive-plots-in-ijulia/9284/1 "2018-02-23T18:39:25Z")

</div>

I am trying to get interactive plots with Gaston in IJulia notebooks. I am almost there, but there is one final piece of the puzzle that I can’t quite figure out. I have this code in a notebook:

```julia
using Gaston, Reactive, Interact
t = 0:0.01:1
@manipulate for phi=0:0.1:6.28
    plot(cos.(2π*t+phi))
end

```

This gets me a slider and an initial plot. When I move the slider, though, what I get is a bunch of slightly different plots in a very long stack; in other words, each new plot is not being displayed on top of the previous one, but below it.

What do I need to do to get this to work? I looked at Gadfly’s code, but I can’t find what they’re doing differently from me.

In Gaston, I add a method to `show`:

```julia
function Base.show(io::IO, ::MIME"image/svg+xml", x::Figure)
    write(io,x.svgdata)
end

```

and I display the image at the end of every `plot` command with:

```julia
display(fig)

```

where `Figure` is Gaston’s figure type, `fig` is the current figure, and `fig.svgdata` contains the actual SVG code that I send to the notebook.

(Let me know if you need to see the whole code: I’m working on a private branch right now, and the code on github produces PNG files instead of SVG code).

Thanks!

---

<div class="post-metadata">

**Author:** ![jheinen](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/jheinen/32/2787_2.png) [@jheinen](https://discourse.julialang.org/u/jheinen)\
**Post date:** [February 23, 2018, 7:01pm UTC](https://discourse.julialang.org/t/how-to-implement-interactive-plots-in-ijulia/9284/2 "2018-02-23T19:01:14Z")

</div>

You might try GR:

```julia
using GR, Interact
t = 0:0.01:1
@manipulate for phi=0:0.1:6.28
    plot(cos.(2π*t+phi))
end

```

It should work out of the box and you don’t have the Gnuplot overhead - moreover the display should be much faster …

---

<div class="post-metadata">

**Author:** ![mbaz](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/mbaz/32/17295_2.png) [@mbaz](https://discourse.julialang.org/u/mbaz)\
**Post date:** [February 23, 2018, 7:03pm UTC](https://discourse.julialang.org/t/how-to-implement-interactive-plots-in-ijulia/9284/3 "2018-02-23T19:03:06Z")

</div>

I wasn’t very clear, sorry: I’m the maintainer of Gaston, and I’m trying to get it to work as an experiment. I want to learn how to do it, and I’m also curious about how fast it actually is.

---

<div class="post-metadata">

**Author:** ![MA\_Laforge](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/ma_laforge/32/385_2.png) [@MA\_Laforge](https://discourse.julialang.org/u/MA_Laforge)\
**Post date:** [February 24, 2018, 3:20am UTC](https://discourse.julialang.org/t/how-to-implement-interactive-plots-in-ijulia/9284/4 "2018-02-24T03:20:55Z")

</div>

Hi @mbaz,

The problem is that the code you wrote above is actually trying to render the plot itself. That’s not what you are supposed to do in order to use interact properly.

Instead, the `@manipulate` macro is supposed to return a plot _ **object** _ (in your case, a `Gaston.Figure` object, I suppose). What happens then is that `Interact` will trigger a `show()` of the returned object each time the value of `phi` changes.

I can kind of get your code to work using the latest tagged version of `Gaston` by doing the following:

```julia
using Gaston, Reactive, Interact
t = 0:0.01:1
@manipulate for phi=0:0.1:6.28
    id=plot(cos.(2π*t+phi))
    p=Gaston.Figure(id)
    return p
end

```

Unfortunately, this code still uses the `plot()` function (because I don’t know how to update the plotted values in `Gaston` without using the `plot()` function… So you end up with an incorrectly generated plot at the top, followed by the properly rendered interactive plot at the bottom of the `IJulia` output.

Hope this helps!

---

<div class="post-metadata">

**Author:** ![mbaz](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/mbaz/32/17295_2.png) [@mbaz](https://discourse.julialang.org/u/mbaz)\
**Post date:** [February 24, 2018, 4:33pm UTC](https://discourse.julialang.org/t/how-to-implement-interactive-plots-in-ijulia/9284/5 "2018-02-24T16:33:34Z")

</div>

That is very useful information and probably the piece I was missing. Thank you!

---

<div class="post-metadata">

**Author:** ![mbaz](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/mbaz/32/17295_2.png) [@mbaz](https://discourse.julialang.org/u/mbaz)\
**Post date:** [February 28, 2018, 2:14am UTC](https://discourse.julialang.org/t/how-to-implement-interactive-plots-in-ijulia/9284/6 "2018-02-28T02:14:27Z")

</div>

I’d appreciate a bit of advice; I’ve made progress but not found a complete solution.

I’ve modified my code so that `plot` returns a value of type Gaston.Figure. I also have a function `llplot` that renders the figure using gnuplot. I want to handle two cases:

- Case 1 is REPL use: gnuplot renders the figure to the screen.
- Case 2 is Jupyter use: gnuplot returns the figure in SVG format, which I want to pass to the notebook.

Case 1 is easy to handle:

```julia
function Base.show(io::IO, x::Figure)
    println("show 1") # debugging
    llplot(x)
end

```

Note that there is no MIME string here. I don’t think MIME makes sense here; at least I can’t imagine how to define a meaningful MIME string for this case.

Attempting to address Case 2, I have this function:

```julia
function Base.show(io::IO, ::MIME"image/svg+xml", x::Figure)
    println("show 2") # debugging
    llplot(x)
    write(io,x.svg)
end

```

In this case, `llplot` writes the SVG image to `x.svg`.

I’m pretty sure this is incorrect, because when I plot in IJulia, I get a correct plot but I also see

```julia
show 1
show 2

```

meaning that the plot is getting rendered twice. How is the correct way to code this? Does `display` play a role here?

---

<div class="post-metadata">

**Author:** ![MA\_Laforge](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/ma_laforge/32/385_2.png) [@MA\_Laforge](https://discourse.julialang.org/u/MA_Laforge)\
**Post date:** [March 2, 2018, 3:47am UTC](https://discourse.julialang.org/t/how-to-implement-interactive-plots-in-ijulia/9284/7 "2018-03-02T03:47:10Z")

</div>

### Short Answer

You are not supposed to define `Base.show(::IO, ::Figure)` to do what you are trying to do. I am not even certain you are ever supposed to define `show()` without including `::MIME` as the second argument.

### How to do this properly

Consider this dummy `Figure` structure as an illustration:

```julia-auto
struct Figure
end

```

We then define the show function as you did previously for SVG:

```julia-auto
function Base.show(io::IO, ::MIME"image/svg+xml", x::Figure)
    println(io, "show 2") # debugging
    println("show 2 -runs")
end

```

Then, you can specialize `display()` to depend on IJulia/REPL:

```julia-auto
function Base.display(d::IJulia.InlineDisplay, x::Figure)
    println("display fig from IJulia")
end
function Base.display(d::Base.REPL.REPLDisplay, x::Figure)
    println(d.repl.t.out_stream, "display fig from REPL")
end

```

### Simple test

```julia-auto
d=Base.Multimedia.displays[2] #usually top-most display in IJulia
f=Figure() #Some plot

println("\n\nrun show(f):")
show(f)

println("\n\nrun show(STDOUT, MIME, f):")
show(STDOUT, MIME"image/svg+xml"(), f)

println("\n\nrun display(f):")
display(f) #Use topmost display on Base.Multimedia.displays[] "stack"

println("\n\nrun display(d, f):")
display(d,f) #Explicitly display on display "d"

; #semicolon: Don't "show" "result" from last line

```

### More advanced usage of display

I personally prefer being more explicit with `display()`. Instead of specializing on `InlineDisplay` or `REPLDisplay`, I would expect my user to push a `GnuPlotDisplay` (defined in your module).

This gives the user a choice to use the GnuPlot window when working with IJulia as well…

```julia-auto
struct GnuPlotDisplay <: Base.Display
end

function Base.display(d::GnuPlotDisplay, x::Figure)
    println("display fig with GnuPlot")
end

```

Here is a small example on how to use `GnuPlotDisplay` to control plotting in a more explicit fashion:

```julia-auto
pushdisplay(GnuPlotDisplay()) #Could add GnuPlotDisplay @ top of stack (as "most rich display")
@show Base.Multimedia.displays

display(f) #Implicitly use topmost display on Base.Multimedia.displays "stack"

popdisplay() #Remove GnuPlotDisplay from top of stack
@show Base.Multimedia.displays

display(GnuPlotDisplay(), f) #Explicitly call for displaying with GnuPlot
;

```

---

<div class="post-metadata">

**Author:** ![mbaz](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/mbaz/32/17295_2.png) [@mbaz](https://discourse.julialang.org/u/mbaz)\
**Post date:** [March 2, 2018, 3:05pm UTC](https://discourse.julialang.org/t/how-to-implement-interactive-plots-in-ijulia/9284/8 "2018-03-02T15:05:03Z")

</div>

Thanks a lot for the detailed explanation; it will be very useful. There’s a lot for me to learn here.

If you don’t mind my asking, how did you figure all this out? I’ve read the docs on multimedia I/O but I’m unable to extrapolate from that to what you just explained.

---

<div class="post-metadata">

**Author:** ![MA\_Laforge](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/ma_laforge/32/385_2.png) [@MA\_Laforge](https://discourse.julialang.org/u/MA_Laforge)\
**Post date:** [March 3, 2018, 12:04am UTC](https://discourse.julialang.org/t/how-to-implement-interactive-plots-in-ijulia/9284/9 "2018-03-03T00:04:30Z")

</div>

> @mbaz: If you don’t mind my asking, how did you figure all this out? […]

Good question. I don’t remember exactly. I think that in the 2015-16 timeframe, there was a more philosophical section on multimedia I/O than what there is now. What I see right now seems more mechanical than what I remember… more like a simple API description. I am not certain anymore, though.

I do know I had to follow the code a bit using the `@edit` macro. For example, running:

```julia
@edit show("hello")

```

shows me where the 1-parameter wrapper function for show is defined:

```julia
show(x) = show(STDOUT::IO, x)

```

---

<div class="post-metadata">

**Author:** ![MA\_Laforge](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/ma_laforge/32/385_2.png) [@MA\_Laforge](https://discourse.julialang.org/u/MA_Laforge)\
**Post date:** [March 3, 2018, 3:10am UTC](https://discourse.julialang.org/t/how-to-implement-interactive-plots-in-ijulia/9284/10 "2018-03-03T03:10:54Z")

</div>

### Errata

It appears I was wrong when I mentionned you were probably “not supposed to define `Base.show(::IO, ::Figure)` […]”.

Upon reading the “Types|Custom pretty-printing” section of the manual, it appears you _ **are** _ encouraged to define the 2-argument version of `show()`. In fact, the manual provides the example:

```julia-auto
julia> Base.show(io::IO, z::Polar) = print(io, z.r, " * exp(", z.Θ, "im)")

```

… but I highly suggest you to output a “textual” version of your Figure object if you do so (ex: `Figure: GnuPlot "TITLE HERE"; 4 subplots; ...`). This would allow users to quickly “inspect” what’s in a plot object without actually having to render anything.

### So why did you get those odd results?

I am not really sure why, in IJulia, you get both `show()` functions to run (both “show 1” & “show 2” get written to your output).

I did a few more tests that reveal something interesting:

```julia-auto
struct Figure
end

function Base.show(io::IO, x::Figure)
    println(io, "show 1")
        @show typeof(io)
    println("show 1 -runs")
end

function Base.show(io::IO, ::MIME"image/svg+xml", x::Figure)
    println(io, "show 2")
        @show typeof(io)
    println("show 2 -runs")
end

```

I then simply create a new `Figure`, and leave it to be output in IJulia:

```julia-auto
f = Figure()
f #Have IJulia "write" f to its output

```

The output is quite intriguing:

```julia-auto
typeof(io) = IOContext{Base.AbstractIOBuffer{Array{UInt8,1}}}
show 1 -runs
typeof(io) = IOContext{Base.AbstractIOBuffer{Array{UInt8,1}}}
show 2 -runs

```

I am not sure why both versions of `show()` run… I am also not sure what this `IOContext{AbstractIOBuffer}` is exactly…

I actually expected that “returning” `f` at the end of an IJulia block would trigger the appropriate `display()` method. I certainly do not expect it to trigger 2 consecutive `show()` methods.

If you “run” `f` by itself in the Julia REPL, it does exactly what I expect: it triggers the appropriate `display()` method.

### Conclusion

I really don’t understand what’s going on in the IJulia session. I don’t know if this is the intended behaviour, and I am not sure who to ask.

---

<div class="post-metadata">

**Author:** ![mbaz](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/mbaz/32/17295_2.png) [@mbaz](https://discourse.julialang.org/u/mbaz)\
**Post date:** [March 7, 2018, 12:09am UTC](https://discourse.julialang.org/t/how-to-implement-interactive-plots-in-ijulia/9284/11 "2018-03-07T00:09:30Z")

</div>

I got it to work, and in the end the code was quite simple. I wanted to have a `plot` command that returns a `Figure` object that renders like this:

- If inside Jupyter, display figure as SVG.
- elseif `terminal=="null"`, don’t display anything.
- elseif `terminal=="dumb"`, display the figure as text on the REPL
- elseif `terminal` is something else, have gnuplot render the figure using X11.

To plot inside Jupyter I define

```julia
function Base.show(io::IO, ::MIME"image/svg+xml", x::Figure)
    llplot()
    write(io,x.svg)
end

```

The key insight is that IJulia will call this function because it is the “richer” display for a `Figure`. To plot on the REPL I have

```julia
function Base.show(io::IO, ::MIME"text/plain", x::Figure)
    llplot()
    term = gaston_config.terminal
    if term == "null"
        return nothing
    elseif term == "dumb"
        print(x.text)
    else
        return nothing
    end
end

```

In the REPL, this function will be called instead of the first one, because the REPL does not support SVG.

I’m still not sure how to support the “textual” version of the `Figure` object. It’d be nice to support that, but I think many users expect `plot` to render the figure without further output. Maybe I can have an `inspect(x::Figure)` command for that.

I’m not yet certain but I think the IJulia behavior is a bug. I can certainly reproduce the behavior where it calls `show` twice. I’ll play with it a bit more and maybe open an issue. **EDIT:** [This is expected behavior](https://github.com/JuliaLang/IJulia.jl/issues/574).

Thank you for all your help and for setting me on the right track.

---

<div class="post-metadata">

**Author:** ![hasanOryx](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/hasanoryx/32/5373_2.png) [@hasanOryx](https://discourse.julialang.org/u/hasanOryx)\
**Post date:** [September 10, 2019, 6:04pm UTC](https://discourse.julialang.org/t/how-to-implement-interactive-plots-in-ijulia/9284/12 "2019-09-10T18:04:07Z")

</div>

> [@jheinen](#):
>
> @manipulat

What is `@manipulater`
