Skip to content

Instantly share code, notes, and snippets.

@jkrumbiegel
Created March 12, 2022 13:25
Show Gist options
  • Save jkrumbiegel/cfcadb19785e13edb5f22b59e1ddac1c to your computer and use it in GitHub Desktop.
Save jkrumbiegel/cfcadb19785e13edb5f22b59e1ddac1c to your computer and use it in GitHub Desktop.
sankey makie
function sankey!(target, x1, x2, bend, start_min, start_max, stop_min, stop_max, color_start, color_stop)
bezier(t, p1, p2, p3, p4) = (1 - t)^3 * p1 + 3(1 - t)^2 * t * p2 + 3 * (1 - t) * t^2 * p3 + t^3 * p4
b(t, start, stop) = begin
p_start = Point2f(x1, start)
p_stop = Point2f(x2, stop)
c1 = Point2f(x1 + bend * (x2-x1), start)
c2 = Point2f(x2 - bend * (x2-x1), stop)
bezier(t, p_start, c1, c2, p_stop)
end
points_min = [b(t, start_min, stop_min) for t in range(0, 1, length = 100)]
points_max = [b(t, start_max, stop_max) for t in range(0, 1, length = 100)]
band!(target, points_min, points_max, color = 1:100, colormap = Makie.Colors.alphacolor.(Makie.to_color.([color_start, color_stop]), 0.5))
end
using Random
function invsortperm(x; kwargs...)
s = sortperm(x; kwargs...)
v = zeros(Int, length(s))
for (i, ss) in enumerate(s)
v[ss] = i
end
v
end
let
vals = map(repeat(1:4, inner = 4), repeat(1:4, 4)) do start, stop
(v = rand(), start, stop)
end
start_edges = cumsum([0; [v.v for v in vals]])
invs = invsortperm(vals, by = (x -> (x.stop, x.start)))
srted = sort(vals, by = (x -> (x.stop, x.start)))
stop_edges = cumsum([0; [v.v for v in srted]])
f = Figure()
tickpos_left = map(1:4) do i
start = (i-1)*4+1
stop = i*4+1
0.5 * (start_edges[stop] + start_edges[start]) + 0.3 * i
end
tickpos_right = map(1:4) do i
start = (i-1)*4+1
stop = i*4+1
0.5 * (stop_edges[stop] + stop_edges[start]) + 0.3 * i
end
ax = Axis(f[1, 1], yticks = (tickpos_left, "Starting label " .* string.(1:4)))
ax2 = Axis(f[1, 1], yticks = (tickpos_right, "Ending label " .* string.(1:4)),
yaxisposition = :right)
linkaxes!(ax, ax2)
hidedecorations!(ax2)
hidespines!(ax2)
ax2.yticklabelsvisible = true
hidexdecorations!(ax)
hideydecorations!(ax, ticklabels = false)
hidespines!(ax)
for (i, val) in enumerate(vals)
smin = start_edges[i] + 0.3 * fld1(i, 4)
smax = start_edges[i+1] + 0.3 * fld1(i, 4)
emin = stop_edges[invs[i]] + 0.3 * fld1(invs[i], 4)
emax = stop_edges[invs[i]+1] + 0.3 * fld1(invs[i], 4)
sankey!(ax, 0, 1, 0.4, smin, smax, emin, emax,
Makie.wong_colors()[val.start],
Makie.wong_colors()[val.stop],
)
end
for i in 1:4
start = (i-1)*4+1
stop = i*4+1
barplot!(ax, [0], [start_edges[stop]] .+ 0.3 * i,
fillto = start_edges[start] + 0.3 * i,
width = 0.02, color = Makie.wong_colors()[i])
barplot!(ax, [1], [stop_edges[stop]] .+ 0.3 * i,
fillto = stop_edges[start] + 0.3 * i,
width = 0.02, color = Makie.wong_colors()[i])
end
tightlimits!(ax)
Label(f[1, 1, Top()], "How it started", halign = :left, padding = (0, 0, 5, 0))
Label(f[1, 1, Top()], "How it's going", halign = :right, padding = (0, 0, 5, 0))
f
end
@jkrumbiegel
Copy link
Author

grafik

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment