diff --git a/src/examples.jl b/src/examples.jl index a00a61d9..9cf91a05 100644 --- a/src/examples.jl +++ b/src/examples.jl @@ -2,503 +2,857 @@ Holds all data needed for a documentation example... header, description, and plotting expression (Expr) """ mutable struct PlotExample - header::AbstractString - desc::AbstractString - exprs::Vector{Expr} + header::AbstractString + desc::AbstractString + exprs::Vector{Expr} end # the _examples we'll run for each const _examples = PlotExample[ + PlotExample( + "Lines", + "A simple line plot of the columns.", + [:( + begin + plot(Plots.fakedata(50, 5), w = 3) + end + )], + ), + PlotExample( + "Functions, adding data, and animations", + """ + Plot multiple functions. You can also put the function first, or use the form `plot(f, + xmin, xmax)` where f is a Function or AbstractVector{Function}.\n\nGet series data: + `x, y = plt[i]`. Set series data: `plt[i] = (x,y)`. Add to the series with + `push!`/`append!`.\n\nEasily build animations. (`convert` or `ffmpeg` must be available + to generate the animation.) Use command `gif(anim, filename, fps=15)` to save the + animation. + """, + [:( + begin + p = plot([sin, cos], zeros(0), leg = false) + anim = Animation() + for x in range(0, stop = 10π, length = 100) + push!(p, x, Float64[sin(x), cos(x)]) + frame(anim) + end + end + )], + ), + PlotExample( + "Parametric plots", + "Plot function pair (x(u), y(u)).", + [ + :( + begin + plot( + sin, + x -> sin(2x), + 0, + 2π, + line = 4, + leg = false, + fill = (0, :orange), + ) + end + ), + ], + ), + PlotExample( + "Colors", + """ + Access predefined palettes (or build your own with the `colorscheme` method). + Line/marker colors are auto-generated from the plot's palette, unless overridden. Set + the `z` argument to turn on series gradients. + """, + [ + :( + begin + y = rand(100) + plot( + 0:10:100, + rand(11, 4), + lab = "lines", + w = 3, + palette = :grays, + fill = 0, + α = 0.6, + ) + scatter!( + y, + zcolor = abs.(y .- 0.5), + m = (:heat, 0.8, Plots.stroke(1, :green)), + ms = 10 * abs.(y .- 0.5) .+ 4, + lab = "grad", + ) + end + ), + ], + ), + PlotExample( + "Global", + """ + Change the guides/background/limits/ticks. Convenience args `xaxis` and `yaxis` allow + you to pass a tuple or value which will be mapped to the relevant args automatically. + The `xaxis` below will be replaced with `xlabel` and `xlims` args automatically during + the preprocessing step. You can also use shorthand functions: `title!`, `xaxis!`, + `yaxis!`, `xlabel!`, `ylabel!`, `xlims!`, `ylims!`, `xticks!`, `yticks!` + """, + [ + :( + begin + using Statistics + y = rand(20, 3) + plot( + y, + xaxis = ("XLABEL", (-5, 30), 0:2:20, :flip), + background_color = RGB(0.2, 0.2, 0.2), + leg = false, + ) + hline!( + mean(y, dims = 1) + rand(1, 3), + line = (4, :dash, 0.6, [:lightgreen :green :darkgreen]), + ) + vline!([5, 10]) + title!("TITLE") + yaxis!("YLABEL", :log10) + end + ), + ], + ), -PlotExample("Lines", - "A simple line plot of the columns.", - [:(begin - plot(Plots.fakedata(50,5), w=3) - end)] -), + # PlotExample("Two-axis", + # "Use the `axis` arguments.", + # [ + # :(plot(Vector[randn(100), randn(100)*100], axis = [:l :r], ylabel="LEFT", yrightlabel="RIGHT", xlabel="X", title="TITLE")) + # ]), -PlotExample("Functions, adding data, and animations", -""" -Plot multiple functions. You can also put the function first, or use the form `plot(f, -xmin, xmax)` where f is a Function or AbstractVector{Function}.\n\nGet series data: -`x, y = plt[i]`. Set series data: `plt[i] = (x,y)`. Add to the series with -`push!`/`append!`.\n\nEasily build animations. (`convert` or `ffmpeg` must be available -to generate the animation.) Use command `gif(anim, filename, fps=15)` to save the -animation. -""", - [:(begin - p = plot([sin,cos], zeros(0), leg=false) - anim = Animation() - for x in range(0, stop=10π, length=100) - push!(p, x, Float64[sin(x), cos(x)]) - frame(anim) + PlotExample( + "Images", + "Plot an image. y-axis is set to flipped", + [ + :( + begin + import FileIO + path = + download("http://juliaplots.org/PlotReferenceImages.jl/Plots/pyplot/0.7.0/ref1.png") + img = FileIO.load(path) + plot(img) + end + ), + ], + ), + PlotExample( + "Arguments", + """ + Plot multiple series with different numbers of points. Mix arguments that apply to all + series (marker/markersize) with arguments unique to each series (colors). Special + arguments `line`, `marker`, and `fill` will automatically figure out what arguments to + set (for example, we are setting the `linestyle`, `linewidth`, and `color` arguments with + `line`.) Note that we pass a matrix of colors, and this applies the colors to each + series. + """, + [ + :( + begin + ys = Vector[rand(10), rand(20)] + plot( + ys, + color = [:black :orange], + line = (:dot, 4), + marker = ([:hex :d], 12, 0.8, Plots.stroke(3, :gray)), + ) + end + ), + ], + ), + PlotExample( + "Build plot in pieces", + "Start with a base plot...", + [:( + begin + plot(rand(100) / 3, reg = true, fill = (0, :green)) + end + )], + ), + PlotExample( + "", + "and add to it later.", + [:( + begin + scatter!(rand(100), markersize = 6, c = :orange) + end + )], + ), + PlotExample( + "Histogram2D", + "", + [:( + begin + histogram2d(randn(10000), randn(10000), nbins = 20) + end + )], + ), + PlotExample( + "Line types", + "", + [ + :( + begin + linetypes = [:path :steppre :steppost :sticks :scatter] + n = length(linetypes) + x = Vector[sort(rand(20)) for i = 1:n] + y = rand(20, n) + plot( + x, + y, + line = (linetypes, 3), + lab = map(string, linetypes), + ms = 15, + ) + end + ), + ], + ), + PlotExample( + "Line styles", + "", + [ + :( + begin + styles = filter( + s -> s in Plots.supported_styles(), + [:solid, :dash, :dot, :dashdot, :dashdotdot], + ) + styles = reshape(styles, 1, length(styles)) # Julia 0.6 unfortunately gives an error when transposing symbol vectors + n = length(styles) + y = cumsum(randn(20, n), dims = 1) + plot( + y, + line = (5, styles), + label = map(string, styles), + legendtitle = "linestyle", + ) + end + ), + ], + ), + PlotExample( + "Marker types", + "", + [ + :( + begin + markers = filter( + m -> m in Plots.supported_markers(), + Plots._shape_keys, + ) + markers = reshape(markers, 1, length(markers)) + n = length(markers) + x = range(0, stop = 10, length = n + 2)[2:(end - 1)] + y = repeat(reshape(reverse(x), 1, :), n, 1) + scatter( + x, + y, + m = (8, :auto), + lab = map(string, markers), + bg = :linen, + xlim = (0, 10), + ylim = (0, 10), + ) + end + ), + ], + ), + PlotExample( + "Bar", + "`x` is the midpoint of the bar. (todo: allow passing of edges instead of midpoints)", + [:( + begin + bar(randn(99)) + end + )], + ), + PlotExample( + "Histogram", + "", + [ + :( + begin + histogram( + randn(1000), + bins = :scott, + weights = repeat(1:5, outer = 200), + ) + end + ), + ], + ), + PlotExample( + "Subplots", + """ + Use the `layout` keyword, and optionally the convenient `@layout` macro to generate + arbitrarily complex subplot layouts. + """, + [ + :( + begin + l = @layout([a{0.1h}; b [c; d e]]) + plot( + randn(100, 5), + layout = l, + t = [:line :histogram :scatter :steppre :bar], + leg = false, + ticks = nothing, + border = :none, + ) + end + ), + ], + ), + PlotExample( + "Adding to subplots", + """ + Note here the automatic grid layout, as well as the order in which new series are added + to the plots. + """, + [ + :( + begin + plot( + Plots.fakedata(100, 10), + layout = 4, + palette = [:grays :blues :heat :lightrainbow], + bg_inside = [:orange :pink :darkblue :black], + ) + end + ), + ], + ), + PlotExample("", "", [:( + begin + using Random + Random.seed!(111) + plot!(Plots.fakedata(100, 10)) end - end)] -), + )]), + PlotExample( + "Open/High/Low/Close", + """ + Create an OHLC chart. Pass in a list of (open,high,low,close) tuples as your `y` + argument. This uses recipes to first convert the tuples to OHLC objects, and + subsequently create a :path series with the appropriate line segments. + """, + [ + :( + begin + n = 20 + hgt = rand(n) .+ 1 + bot = randn(n) + openpct = rand(n) + closepct = rand(n) + y = OHLC[ + ( + openpct[i] * hgt[i] + bot[i], + bot[i] + hgt[i], + bot[i], + closepct[i] * hgt[i] + bot[i], + ) + for i = 1:n + ] + ohlc(y) + end + ), + ], + ), + PlotExample( + "Annotations", + """ + The `annotations` keyword is used for text annotations in data-coordinates. Pass in a + tuple (x,y,text) or a vector of annotations. `annotate!(ann)` is shorthand for `plot!(; + annotation=ann)`. Series annotations are used for annotating individual data points. + They require only the annotation... x/y values are computed. A `PlotText` object can be + build with the method `text(string, attr...)`, which wraps font and color attributes. + """, + [ + :( + begin + y = rand(10) + plot( + y, + annotations = (3, y[3], Plots.text("this is #3", :left)), + leg = false, + ) + annotate!([ + (5, y[5], Plots.text("this is #5", 16, :red, :center)), + ( + 10, + y[10], + Plots.text("this is #10", :right, 20, "courier"), + ), + ]) + scatter!( + range(2, stop = 8, length = 6), + rand(6), + marker = (50, 0.2, :orange), + series_annotations = [ + "series", + "annotations", + "map", + "to", + "series", + Plots.text("data", :green), + ], + ) + end + ), + ], + ), + PlotExample( + "Custom Markers", + """A `Plots.Shape` is a light wrapper around vertices of a polygon. For supported + backends, pass arbitrary polygons as the marker shapes. Note: The center is (0,0) and + the size is expected to be rougly the area of the unit circle. + """, + [ + :( + begin + verts = [ + (-1.0, 1.0), + (-1.28, 0.6), + (-0.2, -1.4), + (0.2, -1.4), + (1.28, 0.6), + (1.0, 1.0), + (-1.0, 1.0), + (-0.2, -0.6), + (0.0, -0.2), + (-0.4, 0.6), + (1.28, 0.6), + (0.2, -1.4), + (-0.2, -1.4), + (0.6, 0.2), + (-0.2, 0.2), + (0.0, -0.2), + (0.2, 0.2), + (-0.2, -0.6), + ] + x = 0.1:0.2:0.9 + y = 0.7 * rand(5) .+ 0.15 + plot( + x, + y, + line = (3, :dash, :lightblue), + marker = (Shape(verts), 30, RGBA(0, 0, 0, 0.2)), + bg = :pink, + fg = :darkblue, + xlim = (0, 1), + ylim = (0, 1), + leg = false, + ) + end + ), + ], + ), + PlotExample( + "Contours", + """ + Any value for fill works here. We first build a filled contour from a function, then an + unfilled contour from a matrix. + """, + [:( + begin + x = 1:0.5:20 + y = 1:0.5:10 + f(x, y) = (3x + y^2) * abs(sin(x) + cos(y)) + X = repeat(reshape(x, 1, :), length(y), 1) + Y = repeat(y, 1, length(x)) + Z = map(f, X, Y) + p1 = contour(x, y, f, fill = true) + p2 = contour(x, y, Z) + plot(p1, p2) + end + )], + ), + PlotExample( + "Pie", + "", + [:( + begin + x = ["Nerds", "Hackers", "Scientists"] + y = [0.4, 0.35, 0.25] + pie(x, y, title = "The Julia Community", l = 0.5) + end + )], + ), + PlotExample( + "3D", + "", + [ + :( + begin + n = 100 + ts = range(0, stop = 8π, length = n) + x = ts .* map(cos, ts) + y = 0.1ts .* map(sin, ts) + z = 1:n + plot( + x, + y, + z, + zcolor = reverse(z), + m = (10, 0.8, :blues, Plots.stroke(0)), + leg = false, + cbar = true, + w = 5, + ) + plot!(zeros(n), zeros(n), 1:n, w = 10) + end + ), + ], + ), + PlotExample( + "DataFrames", + "Plot using DataFrame column symbols.", + [ + :(using StatsPlots), # can't be inside begin block because @df gets expanded first + :( + begin + import RDatasets + iris = RDatasets.dataset("datasets", "iris") + @df iris scatter( + :SepalLength, + :SepalWidth, + group = :Species, + title = "My awesome plot", + xlabel = "Length", + ylabel = "Width", + marker = (0.5, [:cross :hex :star7], 12), + bg = RGB(0.2, 0.2, 0.2), + ) + end + ), + ], + ), + PlotExample( + "Groups and Subplots", + "", + [ + :( + begin + group = rand(map(i -> "group $i", 1:4), 100) + plot( + rand(100), + layout = @layout([a b; c]), + group = group, + linetype = [:bar :scatter :steppre], + linecolor = :match, + ) + end + ), + ], + ), + PlotExample( + "Polar Plots", + "", + [:( + begin + Θ = range(0, stop = 1.5π, length = 100) + r = abs.(0.1 * randn(100) + sin.(3Θ)) + plot(Θ, r, proj = :polar, m = 2) + end + )], + ), + PlotExample( + "Heatmap, categorical axes, and aspect_ratio", + "", + [:( + begin + xs = [string("x", i) for i = 1:10] + ys = [string("y", i) for i = 1:4] + z = float((1:4) * reshape(1:10, 1, :)) + heatmap(xs, ys, z, aspect_ratio = 1) + end + )], + ), + PlotExample( + "Layouts, margins, label rotation, title location", + "", + [ + :( + begin + using Plots.PlotMeasures # for Measures, e.g. mm and px + plot( + rand(100, 6), + layout = @layout([a b; c]), + title = ["A" "B" "C"], + title_location = :left, + left_margin = [20mm 0mm], + bottom_margin = 10px, + xrotation = 60, + ) + end + ), + ], + ), + PlotExample( + "Boxplot and Violin series recipes", + "", + [ + :(using StatsPlots), # can't be inside begin block because @df gets expanded first + :( + begin + import RDatasets + singers = RDatasets.dataset("lattice", "singer") + @df singers violin( + :VoicePart, + :Height, + line = 0, + fill = (0.2, :blue), + ) + @df singers boxplot!( + :VoicePart, + :Height, + line = (2, :black), + fill = (0.3, :orange), + ) + end + ), + ], + ), + PlotExample( + "Animation with subplots", + "The `layout` macro can be used to create an animation with subplots.", + [ + :( + begin + l = @layout([[a; b] c]) + p = plot( + plot([sin, cos], 1, leg = false), + scatter([atan, cos], 1, leg = false), + plot(log, 1, xlims = (1, 10π), ylims = (0, 5), leg = false), + layout = l, + ) -PlotExample("Parametric plots", - "Plot function pair (x(u), y(u)).", - [:(begin - plot(sin, x->sin(2x), 0, 2π, line=4, leg=false, fill=(0,:orange)) - end)] -), - -PlotExample("Colors", -""" -Access predefined palettes (or build your own with the `colorscheme` method). -Line/marker colors are auto-generated from the plot's palette, unless overridden. Set -the `z` argument to turn on series gradients. -""", - [:(begin -y = rand(100) -plot(0:10:100,rand(11,4),lab="lines",w=3,palette=:grays,fill=0, α=0.6) -scatter!(y, zcolor=abs.(y.-0.5), m=(:heat,0.8,Plots.stroke(1,:green)), ms=10*abs.(y.-0.5).+4, - lab="grad") - end)] -), - -PlotExample("Global", -""" -Change the guides/background/limits/ticks. Convenience args `xaxis` and `yaxis` allow -you to pass a tuple or value which will be mapped to the relevant args automatically. -The `xaxis` below will be replaced with `xlabel` and `xlims` args automatically during -the preprocessing step. You can also use shorthand functions: `title!`, `xaxis!`, -`yaxis!`, `xlabel!`, `ylabel!`, `xlims!`, `ylims!`, `xticks!`, `yticks!` -""", - [:(begin -using Statistics -y = rand(20,3) -plot(y, xaxis=("XLABEL",(-5,30),0:2:20,:flip), background_color = RGB(0.2,0.2,0.2), - leg=false) -hline!(mean(y, dims = 1)+rand(1,3), line=(4,:dash,0.6,[:lightgreen :green :darkgreen])) -vline!([5,10]) -title!("TITLE") -yaxis!("YLABEL", :log10) - end)] -), - -# PlotExample("Two-axis", -# "Use the `axis` arguments.", -# [ -# :(plot(Vector[randn(100), randn(100)*100], axis = [:l :r], ylabel="LEFT", yrightlabel="RIGHT", xlabel="X", title="TITLE")) -# ]), - -PlotExample("Images", - "Plot an image. y-axis is set to flipped", - [:(begin - import FileIO - path = download("http://juliaplots.org/PlotReferenceImages.jl/Plots/pyplot/0.7.0/ref1.png") - img = FileIO.load(path) - plot(img) - end)] -), - -PlotExample("Arguments", -""" -Plot multiple series with different numbers of points. Mix arguments that apply to all -series (marker/markersize) with arguments unique to each series (colors). Special -arguments `line`, `marker`, and `fill` will automatically figure out what arguments to -set (for example, we are setting the `linestyle`, `linewidth`, and `color` arguments with -`line`.) Note that we pass a matrix of colors, and this applies the colors to each -series. -""", - [:(begin - ys = Vector[rand(10), rand(20)] - plot(ys, color=[:black :orange], line=(:dot,4), marker=([:hex :d],12,0.8,Plots.stroke(3,:gray))) - end)] -), - -PlotExample("Build plot in pieces", - "Start with a base plot...", - [:(begin - plot(rand(100)/3, reg=true, fill=(0,:green)) - end)] -), - -PlotExample("", - "and add to it later.", - [:(begin - scatter!(rand(100), markersize=6, c=:orange) - end)] -), - -PlotExample("Histogram2D", - "", - [:(begin - histogram2d(randn(10000), randn(10000), nbins=20) - end)] -), - -PlotExample("Line types", - "", - [:(begin - linetypes = [:path :steppre :steppost :sticks :scatter] - n = length(linetypes) - x = Vector[sort(rand(20)) for i in 1:n] - y = rand(20,n) - plot(x, y, line=(linetypes,3), lab=map(string,linetypes), ms=15) - end)] -), - -PlotExample("Line styles", - "", - [:(begin -styles = filter(s -> s in Plots.supported_styles(), - [:solid, :dash, :dot, :dashdot, :dashdotdot]) -styles = reshape(styles, 1, length(styles)) # Julia 0.6 unfortunately gives an error when transposing symbol vectors -n = length(styles) -y = cumsum(randn(20,n), dims = 1) -plot(y, line = (5, styles), label = map(string,styles), legendtitle = "linestyle") - end)] -), - -PlotExample("Marker types", - "", - [:(begin - markers = filter(m -> m in Plots.supported_markers(), Plots._shape_keys) - markers = reshape(markers, 1, length(markers)) - n = length(markers) - x = range(0, stop=10, length=n+2)[2:end-1] - y = repeat(reshape(reverse(x),1,:), n, 1) - scatter(x, y, m=(8,:auto), lab=map(string,markers), bg=:linen, xlim=(0,10), ylim=(0,10)) - end)] -), - -PlotExample("Bar", - "`x` is the midpoint of the bar. (todo: allow passing of edges instead of midpoints)", - [:(begin - bar(randn(99)) - end)] -), - -PlotExample("Histogram", - "", - [:(begin - histogram(randn(1000), bins = :scott, weights = repeat(1:5, outer = 200)) - end)] -), - -PlotExample("Subplots", -""" -Use the `layout` keyword, and optionally the convenient `@layout` macro to generate -arbitrarily complex subplot layouts. -""", - [:(begin -l = @layout([a{0.1h}; b [c;d e]]) -plot(randn(100,5), layout=l, t=[:line :histogram :scatter :steppre :bar], leg=false, - ticks=nothing, border=:none) - end)] -), - -PlotExample("Adding to subplots", -""" -Note here the automatic grid layout, as well as the order in which new series are added -to the plots. -""", - [:(begin -plot(Plots.fakedata(100,10), layout=4, palette=[:grays :blues :heat :lightrainbow], - bg_inside=[:orange :pink :darkblue :black]) - end)] -), - -PlotExample("", - "", - [:(begin - using Random - Random.seed!(111) - plot!(Plots.fakedata(100,10)) - end)] -), - -PlotExample("Open/High/Low/Close", -""" -Create an OHLC chart. Pass in a list of (open,high,low,close) tuples as your `y` -argument. This uses recipes to first convert the tuples to OHLC objects, and -subsequently create a :path series with the appropriate line segments. -""", - [:(begin -n=20 -hgt=rand(n).+1 -bot=randn(n) -openpct=rand(n) -closepct=rand(n) -y = OHLC[(openpct[i]*hgt[i]+bot[i], bot[i]+hgt[i], bot[i], - closepct[i]*hgt[i]+bot[i]) for i in 1:n] -ohlc(y) - end)] -), - -PlotExample("Annotations", -""" -The `annotations` keyword is used for text annotations in data-coordinates. Pass in a -tuple (x,y,text) or a vector of annotations. `annotate!(ann)` is shorthand for `plot!(; -annotation=ann)`. Series annotations are used for annotating individual data points. -They require only the annotation... x/y values are computed. A `PlotText` object can be -build with the method `text(string, attr...)`, which wraps font and color attributes. -""", - [:(begin -y = rand(10) -plot(y, annotations = (3,y[3], Plots.text("this is #3",:left)), leg=false) -annotate!([(5, y[5], Plots.text("this is #5",16,:red,:center)), - (10, y[10], Plots.text("this is #10",:right,20,"courier"))]) -scatter!(range(2, stop=8, length=6), rand(6), marker=(50,0.2,:orange), - series_annotations = ["series","annotations","map","to","series", - Plots.text("data",:green)]) - end)] -), - -PlotExample("Custom Markers", -"""A `Plots.Shape` is a light wrapper around vertices of a polygon. For supported -backends, pass arbitrary polygons as the marker shapes. Note: The center is (0,0) and -the size is expected to be rougly the area of the unit circle. -""", - [:(begin -verts = [(-1.0,1.0),(-1.28,0.6),(-0.2,-1.4),(0.2,-1.4),(1.28,0.6),(1.0,1.0), - (-1.0,1.0),(-0.2,-0.6),(0.0,-0.2),(-0.4,0.6),(1.28,0.6),(0.2,-1.4), - (-0.2,-1.4),(0.6,0.2),(-0.2,0.2),(0.0,-0.2),(0.2,0.2),(-0.2,-0.6)] -x = 0.1:0.2:0.9 -y = 0.7rand(5).+0.15 -plot(x, y, line = (3,:dash,:lightblue), marker = (Shape(verts),30,RGBA(0,0,0,0.2)), - bg=:pink, fg=:darkblue, xlim = (0,1), ylim=(0,1), leg=false) - end)] -), - -PlotExample("Contours", -""" -Any value for fill works here. We first build a filled contour from a function, then an -unfilled contour from a matrix. -""", - [:(begin - x = 1:0.5:20 - y = 1:0.5:10 - f(x,y) = (3x+y^2)*abs(sin(x)+cos(y)) - X = repeat(reshape(x,1,:), length(y), 1) - Y = repeat(y, 1, length(x)) - Z = map(f, X, Y) - p1 = contour(x, y, f, fill=true) - p2 = contour(x, y, Z) - plot(p1, p2) - end)] -), - -PlotExample("Pie", - "", - [:(begin - x = ["Nerds", "Hackers", "Scientists"] - y = [0.4, 0.35, 0.25] - pie(x, y, title="The Julia Community", l=0.5) - end)] -), - -PlotExample("3D", - "", - [:(begin - n = 100 - ts = range(0, stop=8π, length=n) - x = ts .* map(cos,ts) - y = 0.1ts .* map(sin,ts) - z = 1:n - plot(x, y, z, zcolor=reverse(z), m=(10,0.8,:blues,Plots.stroke(0)), leg=false, cbar=true, w=5) - plot!(zeros(n),zeros(n),1:n, w=10) - end)] -), - -PlotExample("DataFrames", - "Plot using DataFrame column symbols.", - [:(using StatsPlots), # can't be inside begin block because @df gets expanded first - :(begin - import RDatasets - iris = RDatasets.dataset("datasets", "iris") - @df iris scatter(:SepalLength, :SepalWidth, group=:Species, - title = "My awesome plot", xlabel = "Length", ylabel = "Width", - marker = (0.5, [:cross :hex :star7], 12), bg=RGB(.2,.2,.2)) - end)] -), - -PlotExample("Groups and Subplots", - "", - [:(begin - group = rand(map(i->"group $i",1:4),100) - plot(rand(100), layout=@layout([a b;c]), group=group, - linetype=[:bar :scatter :steppre], linecolor = :match) - end)] -), - -PlotExample("Polar Plots", - "", - [:(begin - Θ = range(0, stop=1.5π, length=100) - r = abs.(0.1randn(100)+sin.(3Θ)) - plot(Θ, r, proj=:polar, m=2) - end)] -), - -PlotExample("Heatmap, categorical axes, and aspect_ratio", - "", - [:(begin - xs = [string("x",i) for i=1:10] - ys = [string("y",i) for i=1:4] - z = float((1:4)*reshape(1:10,1,:)) - heatmap(xs, ys, z, aspect_ratio=1) - end)] -), - -PlotExample("Layouts, margins, label rotation, title location", - "", - [:(begin - using Plots.PlotMeasures # for Measures, e.g. mm and px - plot(rand(100,6),layout=@layout([a b; c]),title=["A" "B" "C"], - title_location=:left, left_margin=[20mm 0mm], - bottom_margin=10px, xrotation=60) - end)] -), - -PlotExample("Boxplot and Violin series recipes", - "", - [:(using StatsPlots), # can't be inside begin block because @df gets expanded first - :(begin - import RDatasets - singers = RDatasets.dataset("lattice", "singer") - @df singers violin(:VoicePart, :Height, line = 0, fill = (0.2, :blue)) - @df singers boxplot!(:VoicePart, :Height, line = (2,:black), fill = (0.3, :orange)) - end)] -), - -PlotExample("Animation with subplots", - "The `layout` macro can be used to create an animation with subplots.", - [:(begin - l = @layout([[a; b] c]) - p = plot(plot([sin,cos],1,leg=false), - scatter([atan,cos],1,leg=false), - plot(log,1,xlims=(1,10π),ylims=(0,5),leg=false),layout=l) - - anim = Animation() - for x = range(1, stop=10π, length=100) - plot(push!(p,x,Float64[sin(x),cos(x),atan(x),cos(x),log(x)])) - frame(anim) - end - end)] -), - -PlotExample("Spy", -""" -For a matrix `mat` with unique nonzeros `spy(mat)` returns a colorless plot. If `mat` has -various different nonzero values, a colorbar is added. The colorbar can be disabled with -`legend = nothing`. -""", - [:(begin - using SparseArrays - a = spdiagm(0 => ones(50), 1 => ones(49), -1 => ones(49), 10 => ones(40), -10 => ones(40)) - b = spdiagm(0 => 1:50, 1 => 1:49, -1 => 1:49, 10 => 1:40, -10 => 1:40) - plot(spy(a), spy(b), title = ["Unique nonzeros" "Different nonzeros"]) - end)] -), - -PlotExample("Magic grid argument", -""" -The grid lines can be modified individually for each axis with the magic `grid` argument. -""", - [:(begin - x = rand(10) - p1 = plot(x, title = "Default looks") - p2 = plot(x, grid = (:y, :olivedrab, :dot, 1, 0.9), title = "Modified y grid") - p3 = plot(deepcopy(p2), title = "Add x grid") - xgrid!(p3, :on, :cadetblue, 2, :dashdot, 0.4) - plot(p1, p2, p3, layout = (1, 3), label = "", fillrange = 0, fillalpha = 0.3) - end)] -), - -PlotExample("Framestyle", -""" -The style of the frame/axes of a (sub)plot can be changed with the `framestyle` -attribute. The default framestyle is `:axes`. -""", - [:(begin - scatter(fill(randn(10), 6), fill(randn(10), 6), - framestyle = [:box :semi :origin :zerolines :grid :none], - title = [":box" ":semi" ":origin" ":zerolines" ":grid" ":none"], - color = permutedims(1:6), layout = 6, label = "", markerstrokewidth = 0, - ticks = -2:2) - end)] -), - -PlotExample("Lines and markers with varying colors", -""" -You can use the `line_z` and `marker_z` properties to associate a color with -each line segment or marker in the plot. -""", - [:(begin - t = range(0, stop=1, length=100) - θ = 6π .* t - x = t .* cos.(θ) - y = t .* sin.(θ) - p1 = plot(x, y, line_z=t, linewidth=3, legend=false) - p2 = scatter(x, y, marker_z=+, color=:bluesreds, legend=false) - plot(p1, p2) - end)] -), - -PlotExample("Portfolio Composition maps", -""" -see: http://stackoverflow.com/a/37732384/5075246 -""", - [:(begin - using Random - Random.seed!(111) - tickers = ["IBM", "Google", "Apple", "Intel"] - N = 10 - D = length(tickers) - weights = rand(N,D) - weights ./= sum(weights, dims = 2) - returns = sort!((1:N) + D*randn(N)) - - portfoliocomposition(weights, returns, labels = permutedims(tickers)) - end)] -), - -PlotExample("Ribbons", - """ - Ribbons can be added to lines via the `ribbon` keyword; - you can pass a tuple of arrays (upper and lower bounds), - a single Array (for symmetric ribbons), a Function, or a number. - """, - [:(begin - plot( - plot(0:10; ribbon = (LinRange(0, 2, 10), LinRange(0, 1, 10))), - plot(0:10; ribbon = 0:0.5:5), - plot(0:10; ribbon = sqrt), - plot(0:10; ribbon = 1), - ) - end)] -), - -PlotExample("Histogram2D (complex values)", - "", - [:(begin - n = 10_000 - x = exp.(0.1randn(n) .+ randn(n).*(im)) - histogram2d(x, nbins=(20,40), show_empty_bins=true, - normed=true, aspect_ratio=1) - end)] -), - -PlotExample("Unconnected lines using `missing` or `NaN`", -""" -Missing values and non-finite values, including `NaN`, are not plotted. -Instead, lines are separated into segments at these values. -""", - [:(begin - x,y = [1,2,2,1,1], [1,2,1,2,1] - plot( - plot([rand(5); NaN; rand(5); NaN; rand(5)]), - plot([1,missing,2,3], marker=true), - plot([x; NaN; x.+2], [y; NaN; y.+1], arrow=2), - plot([1, 2+3im, Inf, 4im, 3, -Inf*im, 0, 3+3im], marker=true), - legend=false - ) - end)] -), + anim = Animation() + for x in range(1, stop = 10π, length = 100) + plot(push!( + p, + x, + Float64[sin(x), cos(x), atan(x), cos(x), log(x)], + )) + frame(anim) + end + end + ), + ], + ), + PlotExample( + "Spy", + """ + For a matrix `mat` with unique nonzeros `spy(mat)` returns a colorless plot. If `mat` has + various different nonzero values, a colorbar is added. The colorbar can be disabled with + `legend = nothing`. + """, + [ + :( + begin + using SparseArrays + a = spdiagm( + 0 => ones(50), + 1 => ones(49), + -1 => ones(49), + 10 => ones(40), + -10 => ones(40), + ) + b = spdiagm( + 0 => 1:50, + 1 => 1:49, + -1 => 1:49, + 10 => 1:40, + -10 => 1:40, + ) + plot( + spy(a), + spy(b), + title = ["Unique nonzeros" "Different nonzeros"], + ) + end + ), + ], + ), + PlotExample( + "Magic grid argument", + """ + The grid lines can be modified individually for each axis with the magic `grid` argument. + """, + [ + :( + begin + x = rand(10) + p1 = plot(x, title = "Default looks") + p2 = plot( + x, + grid = (:y, :olivedrab, :dot, 1, 0.9), + title = "Modified y grid", + ) + p3 = plot(deepcopy(p2), title = "Add x grid") + xgrid!(p3, :on, :cadetblue, 2, :dashdot, 0.4) + plot( + p1, + p2, + p3, + layout = (1, 3), + label = "", + fillrange = 0, + fillalpha = 0.3, + ) + end + ), + ], + ), + PlotExample( + "Framestyle", + """ + The style of the frame/axes of a (sub)plot can be changed with the `framestyle` + attribute. The default framestyle is `:axes`. + """, + [ + :( + begin + scatter( + fill(randn(10), 6), + fill(randn(10), 6), + framestyle = [:box :semi :origin :zerolines :grid :none], + title = [":box" ":semi" ":origin" ":zerolines" ":grid" ":none"], + color = permutedims(1:6), + layout = 6, + label = "", + markerstrokewidth = 0, + ticks = -2:2, + ) + end + ), + ], + ), + PlotExample( + "Lines and markers with varying colors", + """ + You can use the `line_z` and `marker_z` properties to associate a color with + each line segment or marker in the plot. + """, + [ + :( + begin + t = range(0, stop = 1, length = 100) + θ = 6π .* t + x = t .* cos.(θ) + y = t .* sin.(θ) + p1 = plot(x, y, line_z = t, linewidth = 3, legend = false) + p2 = scatter( + x, + y, + marker_z = +, + color = :bluesreds, + legend = false, + ) + plot(p1, p2) + end + ), + ], + ), + PlotExample( + "Portfolio Composition maps", + """ + see: http://stackoverflow.com/a/37732384/5075246 + """, + [ + :( + begin + using Random + Random.seed!(111) + tickers = ["IBM", "Google", "Apple", "Intel"] + N = 10 + D = length(tickers) + weights = rand(N, D) + weights ./= sum(weights, dims = 2) + returns = sort!((1:N) + D * randn(N)) + portfoliocomposition( + weights, + returns, + labels = permutedims(tickers), + ) + end + ), + ], + ), + PlotExample( + "Ribbons", + """ + Ribbons can be added to lines via the `ribbon` keyword; + you can pass a tuple of arrays (upper and lower bounds), + a single Array (for symmetric ribbons), a Function, or a number. + """, + [ + :( + begin + plot( + plot( + 0:10; + ribbon = (LinRange(0, 2, 10), LinRange(0, 1, 10)), + ), + plot(0:10; ribbon = 0:0.5:5), + plot(0:10; ribbon = sqrt), + plot(0:10; ribbon = 1), + ) + end + ), + ], + ), + PlotExample( + "Histogram2D (complex values)", + "", + [ + :( + begin + n = 10_000 + x = exp.(0.1 * randn(n) .+ randn(n) .* (im)) + histogram2d( + x, + nbins = (20, 40), + show_empty_bins = true, + normed = true, + aspect_ratio = 1, + ) + end + ), + ], + ), + PlotExample( + "Unconnected lines using `missing` or `NaN`", + """ + Missing values and non-finite values, including `NaN`, are not plotted. + Instead, lines are separated into segments at these values. + """, + [ + :( + begin + x, y = [1, 2, 2, 1, 1], [1, 2, 1, 2, 1] + plot( + plot([rand(5); NaN; rand(5); NaN; rand(5)]), + plot([1, missing, 2, 3], marker = true), + plot([x; NaN; x .+ 2], [y; NaN; y .+ 1], arrow = 2), + plot( + [1, 2 + 3im, Inf, 4im, 3, -Inf * im, 0, 3 + 3im], + marker = true, + ), + legend = false, + ) + end + ), + ], + ), ] # Some constants for PlotDocs and PlotReferenceImages @@ -517,21 +871,21 @@ _backend_skips = Dict( # make and display one plot function test_examples(pkgname::Symbol, idx::Int; debug = false, disp = true) - Plots._debugMode.on = debug - @info("Testing plot: $pkgname:$idx:$(_examples[idx].header)") - backend(pkgname) - backend() + Plots._debugMode.on = debug + @info("Testing plot: $pkgname:$idx:$(_examples[idx].header)") + backend(pkgname) + backend() - # prevent leaking variables (esp. functions) directly into Plots namespace - m = Module(:PlotExampleModule) - Base.eval(m, :(using Plots)) - map(exprs -> Base.eval(m, exprs), _examples[idx].exprs) + # prevent leaking variables (esp. functions) directly into Plots namespace + m = Module(:PlotExampleModule) + Base.eval(m, :(using Plots)) + map(exprs -> Base.eval(m, exprs), _examples[idx].exprs) - plt = current() - if disp - gui(plt) - end - plt + plt = current() + if disp + gui(plt) + end + plt end # generate all plots and create a dict mapping idx --> plt @@ -542,23 +896,29 @@ test_examples(pkgname[, idx]; debug = false, disp = true, sleep = nothing, Run the `idx` test example for a given backend, or all examples if `idx` is not specified. """ -function test_examples(pkgname::Symbol; debug = false, disp = true, sleep = nothing, - skip = [], only = nothing) - Plots._debugMode.on = debug - plts = Dict() - for i in eachindex(_examples) - only !== nothing && !(i in only) && continue - i in skip && continue - try - plt = test_examples(pkgname, i, debug=debug, disp=disp) - plts[i] = plt - catch ex - # TODO: put error info into markdown? - @warn("Example $pkgname:$i:$(_examples[i].header) failed with: $ex") +function test_examples( + pkgname::Symbol; + debug = false, + disp = true, + sleep = nothing, + skip = [], + only = nothing, +) + Plots._debugMode.on = debug + plts = Dict() + for i in eachindex(_examples) + only !== nothing && !(i in only) && continue + i in skip && continue + try + plt = test_examples(pkgname, i, debug = debug, disp = disp) + plts[i] = plt + catch ex + # TODO: put error info into markdown? + @warn("Example $pkgname:$i:$(_examples[i].header) failed with: $ex") + end + if sleep !== nothing + Base.sleep(sleep) + end end - if sleep !== nothing - Base.sleep(sleep) - end - end - plts + plts end