Animation of a GraphPlots in an Array

Hi all,

I have a big simulation loop resulting in a graphplot for each timestep. I store each of those plots in an array. Ultimately, I’d like to animate over all entries in this array. The minimal working example looks somehow like this:

using GraphPlot

gplotvec = Array{Any}(nothing, 100)

for i in 1:100
    g = graphfamous("karate")
    gplotvec[i] = gplot(g)
return gplotvec
end

I tried different things like initializing an animation object and storing each element of the array in a frame of the animation object - doesn’t work. The problem could be that the array elements are of type context rather than type plot(?).

Any help is highly appreciated :blush:

Hi. I can’t help you with GraphPlot, sorry. But I can show you how I make animated graphs using Karnak.jl.

dots

Using your setup of creating a vector of graphs, each of the 20 frames shows one of the graphs and NetworkLayout.jl’s stress algorithm coping well enough, most of the time.

code for gif
using Graphs
using Karnak

nG = 20

gplotvec = Graph[]
for i in 1:nG
    push!(gplotvec, grid([i, i + 1]))
end

cols = Luxor.Colors.JULIA_LOGO_COLORS

function frame(scene, framenumber)
    background("black")
    sethue("grey30")
    drawgraph(gplotvec[framenumber], 
        vertexfillcolors = (v) -> cols[mod1(v, end)],
        vertexshapesizes = 6,
        layout=spring)
    sethue("white")
    text(string(framenumber), boxtopleft() * 0.9)
end

movie = Movie(800, 500, "dots")
animate(movie, [Scene(movie, frame, 1:nG)], 
    framerate=3,
    creategif=true,
    pathname="/tmp/dots.gif")

There’s plenty of documentation, and feel free to open an issue on github if it’s not enough.

Alternatively, you can investigate GraphMakie.jl, which I’d guess ties into Makie’s animation system.

3 Likes

Thanks very much, @cormullion for your reply! Somehow I found a workaround using compose.jl (already used in graphplot.jl).

anim = Animation()

for i in 1:500
	cur_timestep = round(timestep * i, digits = 2)
	output = compose(gplotvec[i],
		(context(), rectangle(), fill("grey")))
	j = length(anim.frames) + 1
	tmpfilename = joinpath(anim.dir, @sprintf("%06d.png", j))
	Compose.draw(PNG(tmpfilename), output)
	push!(anim.frames, tmpfilename)
end

gif(anim, "anim_test.gif", fps = 20)
1 Like