Matplotlib had a nice feature, markevery=n
, that, for a bivariate data set, allowed you to only plot every n-th point. This was quite useful if you had an abundance of data and wanted to reduce the graphical intensity of a figure. Is there any natural analog in Plots.jl
? Could there be?
you should be able to use view(x, 1:n:length(x))
!
I’d say that is preferable to adding a keyword to plot
That works if you are just plotting a vector.
But if you are using a recipe that generates the plots for you, and you are plotting some complicated struct, it might be difficult create such a view perhaps?
I guess that is true. I can’t really think of a concrete example but that’s not to say it won’t occur in the wild.
Let’s say you are plotting some struct that represents a bunch of solutions to some ODE with a recipe. Maybe you have a ton of timesteps but for the plot you don’t want the plots to be so dense.
Here, you just want to tell Plots.jl, please spread the points out a bit, without having to mess with the struct itself.
So that would be part of the recipe then, right? My point is, I think the most basic plotting construct should just accept views and not do this via kw_args - however, how you downsample in recipes will be much more domain specific and possibly will need kw_args
I think so too. It would be easy to implement a thin
kwarg in a recipe. You’d lose the applicability across Plots but have complete flexibility in terms of how to interpret it in the context of your recipe.
A disadvantage of the view
approach is that it’d apply to the line and the symbol. In matplotlib, markevery shows the line in full resolution. Using view
, you have to plot!
each series twice, once for the line and once for the symbols, and that makes it harder to make nice legends.
Thanks for explaining the marker-line dichotomy, that makes the mechanism make more sense. Oh and primary = false
is your friend wrt the legend.
Hi all, sorry for restarting this old thread. I had the same issue and worked out a solution in case people are reading this. Actually, for my sake, markevery wouldn’t have been exactly what I was after since it doesn’t account for changes in y.
using Plots, StatsFuns
pyplot()
function fixmarkerspacing(x, y, maxspace, rangex, rangey)
newx = [x[1]]
newy = [y[1]]
sumnorm = 0
for i ∈ 2:length(x)
sumnorm += sqrt(((x[i] - x[i-1])/rangex)^2 + ((y[i] - y[i-1])/rangey)^2)
if sumnorm > maxspace
push!(newx,x[i])
push!(newy,y[i])
sumnorm = sumnorm - maxspace
if sumnorm > maxspace # In case a jump in y was very large
sumnorm = 0
end
end
end
return newx, newy
end
x = -10:0.05:10
y = logistic.(x)
newx, newy = fixmarkerspacing(x, y, 0.2, 20, 1)
plot([], [], markershape = :square, label = "foo", linecolor = :blue, markercolor = :red)
plot!(x, y, linecolor = :blue, label = "")
plot!(newx, newy, line = false, markershape = :square, label = "", markercolor = :red)
With the result: