Plotting with user input

It can also be fun to do something like this with a small GLMakie GUI. Here’s a mockup where the “fit” is just a line from first to last point of random data, but you get the gist. Afterwards you have your acceptance results in the accepted Observable and can process that further.

using GLMakie


struct Fit
    y::Vector{Float64}
end

n = 100
fits = [Fit(cumsum(randn(n))) for _ in 1:n]
accepted = Observable(zeros(Bool, length(fits)))

f = Figure()
ax = Axis(f[1, 1])

i = Observable(1)


lines!(ax, @lift(fits[$i].y))

pseudofit_points = lift(i) do i
    f = fits[i]
    len = length(f.y)
    [Point2(1, f.y[1]), Point2(len, f.y[end])]
end

lines!(ax, pseudofit_points, color = @lift($accepted[$i] ? :lightgreen : :red), linestyle = :dash, linewidth = 3)

subgl = GridLayout(f[2, 1], tellwidth = false)

prevbutton = Button(subgl[1, 1], label = "Prev")
on(prevbutton.clicks) do _
    i[] = mod1(i[] - 1, n)
    reset_limits!(ax)
end

Label(subgl[1, 2], @lift("Fit $($i)"))

nextbutton = Button(subgl[1, 3], label = "Next")
on(nextbutton.clicks) do _
    i[] = mod1(i[] + 1, n)
    reset_limits!(ax)
end

togglebutton = Button(subgl[1, 4], label = @lift($accepted[$i] ? "Reject" : "Accept"))
on(togglebutton.clicks) do _
    accepted.val[i[]] =! accepted.val[i[]]
    notify(accepted)
end

f
7 Likes