Compare commits

..
46 Commits
Author SHA1 Message Date
Daniel SchwabenederandGitHub 16b8d01b88 Merge pull request #2427 from daschw/ratio
use equal aspect ratio by default for images
2020-03-01 08:52:41 +01:00
Daniel Schwabeneder 8d7b07eab3 bump version 2020-03-01 01:57:22 +01:00
Daniel Schwabeneder 599d6a2ec8 add commented code to update refernce images 2020-03-01 01:56:46 +01:00
Daniel Schwabeneder 345f5654a3 use equal aspect ratio by default for images 2020-03-01 01:37:34 +01:00
Daniel SchwabenederandGitHub 77e04c45db Merge pull request #2426 from daschw/gr-scatter
Fix shape markers for GR
2020-02-29 21:38:49 +01:00
Daniel Schwabeneder ad4d7214e4 increase test accuracy 2020-02-29 21:00:51 +01:00
Daniel Schwabeneder 4051d016b9 Fix Shape markers for GR 2020-02-29 20:44:56 +01:00
Daniel SchwabenederandGitHub 8610a82a88 Merge pull request #2421 from daschw/release
bump version
2020-02-28 09:29:44 +01:00
Daniel Schwabeneder 4832d870dd bump version 2020-02-28 09:27:35 +01:00
Daniel SchwabenederandGitHub ace915fbfb Merge pull request #2420 from JuliaPlots/compathelper/new_version/2020-02-27-15-06-02-666-763792840
CompatHelper: bump compat for "GR" to "0.47"
2020-02-28 09:23:52 +01:00
Josef HeinenandGitHub c6593423f5 Update Project.toml 2020-02-28 09:09:54 +01:00
github-actions[bot] f69daa8cfe CompatHelper: bump compat for "GR" to "0.47" 2020-02-27 15:06:03 +00:00
Daniel SchwabenederandGitHub 71246620aa Merge pull request #2414 from daschw/release
bump version
2020-02-25 10:09:49 +01:00
Daniel Schwabeneder 6e3181375c bump version 2020-02-25 10:08:45 +01:00
Daniel SchwabenederandGitHub e7b1dc0cac Merge pull request #2413 from daschw/hdf5
AKWs in HDF5 backend
2020-02-25 09:58:05 +01:00
Daniel Schwabeneder d78bb56316 AKWs in HDF5 backend 2020-02-25 09:40:05 +01:00
Daniel SchwabenederandGitHub 648c5ac587 Merge pull request #2409 from daschw/readme
fix travis and appveyor links in readme
2020-02-24 10:23:00 +01:00
Daniel Schwabeneder df7d28dc99 fix travis and appveyor links in readme 2020-02-24 10:21:23 +01:00
Daniel SchwabenederandGitHub 4d28a49c70 Merge pull request #2408 from JuliaPlots/compathelper/new_version/2020-02-24-02-05-25-661-4174007980
CompatHelper: bump compat for "FFMPEG" to "0.3"
2020-02-24 10:15:37 +01:00
github-actions[bot] ef3e7af329 CompatHelper: bump compat for "FFMPEG" to "0.3" 2020-02-24 02:05:26 +00:00
YuvalandGitHub 3221b80aeb Merge pull request #2402 from yha/gr-scientific-ticks
Fix GR scientific notation for explicit ticks
2020-02-17 16:58:04 +02:00
Daniel SchwabenederandGitHub 13fc936e1f Merge pull request #2403 from daschw/animate
Fix animations for `import Plots`
2020-02-16 11:01:10 +01:00
Daniel Schwabeneder 4e5b1aa6e5 add missing Plots. 2020-02-16 09:55:57 +01:00
Daniel Schwabeneder cb577f0ef3 fix animate for import Plots 2020-02-16 09:52:55 +01:00
yha b23dd39e06 Fix GR scientific notation for explicit ticks 2020-02-13 18:14:15 +02:00
Daniel SchwabenederandGitHub 7498b3c769 Merge pull request #2398 from daschw/docs
prepare for docs rewrite
2020-02-13 11:32:01 +01:00
Daniel SchwabenederandGitHub 0c0a2c215c Merge pull request #2396 from GaaH/add-txt-extension
save unicodeplots with .txt extension
2020-02-12 09:12:42 +01:00
Daniel Schwabeneder b682bc8e96 prepare for docs rewrite 2020-02-12 07:28:30 +01:00
Gaëtan Caillaut 205345a8d3 save unicodeplots with .txt extension 2020-02-11 18:36:26 +01:00
Daniel SchwabenederandGitHub faff9cebe4 Merge pull request #2393 from daschw/pkgeval
add PkgEval badge to readme
2020-02-11 15:35:26 +01:00
Daniel Schwabeneder bcd1bc1009 add PkgEval badge to readme 2020-02-11 14:39:21 +01:00
Daniel SchwabenederandGitHub f2ca493a14 Merge pull request #2390 from daschw/release
tag minor release
2020-02-10 16:14:59 +01:00
Daniel Schwabeneder 54301fa97a up version 2020-02-10 16:13:19 +01:00
Daniel SchwabenederandGitHub 20a290792f Merge pull request #2388 from daschw/akw
Some fixes for KW -> Attr transition
2020-02-09 09:26:00 +01:00
Daniel Schwabeneder 31f5490517 fix typo 2020-02-08 23:57:48 +01:00
Daniel Schwabeneder 8554e632bd more reset_kw!s 2020-02-08 23:49:50 +01:00
Daniel Schwabeneder 70d0d786e2 fix fg_color 2020-02-08 23:48:35 +01:00
Daniel Schwabeneder 5af5ec7313 more AKWs 2020-02-08 23:29:09 +01:00
Daniel SchwabenederandGitHub 7fab2f1c6b Merge pull request #2387 from JuliaTagBot/master
Install TagBot as a GitHub Action
2020-02-08 20:07:01 +01:00
Daniel SchwabenederandGitHub 461ef20225 Merge pull request #2385 from daschw/hover
fix plotly hover in test image 6
2020-02-08 16:16:00 +01:00
Daniel SchwabenederandGitHub 4357fde5ea Merge pull request #2386 from daschw/attr
Missing methods for Attr
2020-02-08 16:15:43 +01:00
Daniel Schwabeneder f93977b1a4 implement get! and delete! for Attr 2020-02-08 15:52:32 +01:00
Julia TagBot 2e77d0df98 Install TagBot as a GitHub Action 2020-02-08 20:31:27 +07:00
Daniel Schwabeneder fc40b0e0ac fix plotly hover in test image 6 2020-02-07 23:12:34 +01:00
Daniel SchwabenederandGitHub 85aca2aa67 Merge pull request #2384 from daschw/testing
update julia version in travis and appveyor configs
2020-02-07 22:53:19 +01:00
Daniel Schwabeneder 961d6be9f9 julia version in travis and appveyor configs 2020-02-07 18:08:08 +01:00
24 changed files with 209 additions and 160 deletions
+11
View File
@@ -0,0 +1,11 @@
name: TagBot
on:
schedule:
- cron: 0 * * * *
jobs:
TagBot:
runs-on: ubuntu-latest
steps:
- uses: JuliaRegistries/TagBot@v1
with:
token: ${{ secrets.GITHUB_TOKEN }}
+1 -1
View File
@@ -5,7 +5,7 @@ os:
# - osx
julia:
- 1
- 1.2
- 1.3
- nightly
matrix:
+3 -3
View File
@@ -1,7 +1,7 @@
name = "Plots"
uuid = "91a5bcdd-55d7-5caf-9e0b-520d859cae80"
author = ["Tom Breloff (@tbreloff)"]
version = "0.29.0"
version = "0.29.4"
[deps]
Base64 = "2a0f44e3-6c83-55bd-87e4-b1978d98bd5f"
@@ -32,9 +32,9 @@ UUIDs = "cf7118a7-6976-5b1a-9a39-7adc72f591a4"
[compat]
Contour = "0.5"
FFMPEG = "0.2"
FFMPEG = "0.2, 0.3"
FixedPointNumbers = "0.6, 0.7, 0.8"
GR = "0.46"
GR = "0.46, 0.47"
GeometryTypes = "0.7"
JSON = "0.21"
Measures = "0.3"
+20 -8
View File
@@ -1,13 +1,25 @@
# Plots
[![Build Status](https://travis-ci.org/JuliaPlots/Plots.jl.svg?branch=master)](https://travis-ci.org/JuliaPlots/Plots.jl)
[![Build status](https://ci.appveyor.com/api/projects/status/github/juliaplots/plots.jl?branch=master&svg=true)](https://ci.appveyor.com/project/mkborregaard/plots-jl)
[![Join the chat at https://gitter.im/tbreloff/Plots.jl](https://badges.gitter.im/tbreloff/Plots.jl.svg)](https://gitter.im/tbreloff/Plots.jl?utm_source=badge&utm_medium=badge&utm_campaign=pr-badge&utm_content=badge)
<a href="http://docs.juliaplots.org/latest/" target="_blank"><img src="https://img.shields.io/badge/docs-latest-blue.svg" alt="Latest documentation"></a>
<!-- [![Plots](http://pkg.julialang.org/badges/Plots_0.3.svg)](http://pkg.julialang.org/?pkg=Plots&ver=0.3) -->
<!-- [![Plots](http://pkg.julialang.org/badges/Plots_0.4.svg)](http://pkg.julialang.org/?pkg=Plots&ver=0.4) -->
<!-- [![Coverage Status](https://coveralls.io/repos/tbreloff/Plots.jl/badge.svg?branch=master)](https://coveralls.io/r/tbreloff/Plots.jl?branch=master) -->
<!-- [![codecov.io](http://codecov.io/github/tbreloff/Plots.jl/coverage.svg?branch=master)](http://codecov.io/github/tbreloff/Plots.jl?branch=master) -->
[travis-img]: https://img.shields.io/travis/JuliaPlots/Plots.jl?logo=travis
[travis-url]: https://travis-ci.org/JuliaPlots/Plots.jl
[appveyor-img]: https://ci.appveyor.com/api/projects/status/github/juliaplots/plots.jl?branch=master&svg=true
[appveyor-url]: https://ci.appveyor.com/project/mkborregaard/plots-jl
[pkgeval-img]: https://juliaci.github.io/NanosoldierReports/pkgeval_badges/P/Plots.svg
[pkgeval-url]: https://juliaci.github.io/NanosoldierReports/pkgeval_badges/report.html
[gitter-img]: https://badges.gitter.im/tbreloff/Plots.jl.svg
[gitter-url]: https://gitter.im/tbreloff/Plots.jl?utm_source=badge&utm_medium=badge&utm_campaign=pr-badge&utm_content=badge
[docs-img]: https://img.shields.io/badge/docs-stable-blue.svg
[docs-url]: http://docs.juliaplots.org/latest/
[![][travis-img]][travis-url]
[![][appveyor-img]][appveyor-url]
[![][pkgeval-img]][pkgeval-url]
[![][gitter-img]][gitter-url]
[![][docs-img]][docs-url]
#### Created by Tom Breloff (@tbreloff)
+1 -1
View File
@@ -2,7 +2,7 @@ environment:
matrix:
# - julia_version: 0.7
- julia_version: 1
- julia_version: 1.2
- julia_version: 1.3
- julia_version: nightly
platform:
+3 -3
View File
@@ -163,16 +163,16 @@ function _animate(forloop::Expr, args...; callgif = false)
error("Unsupported animate filter: $args")
end
push!(block.args, :(if $filterexpr; frame($animsym); end))
push!(block.args, :(if $filterexpr; Plots.frame($animsym); end))
push!(block.args, :(global $countersym += 1))
# add a final call to `gif(anim)`?
retval = callgif ? :(gif($animsym)) : animsym
retval = callgif ? :(Plots.gif($animsym)) : animsym
# full expression:
esc(quote
$freqassert # if filtering, check frequency is an Integer > 0
$animsym = Animation() # init animation object
$animsym = Plots.Animation() # init animation object
global $countersym = 1 # init iteration counter
$forloop # for loop, saving a frame after each iteration
$retval # return the animation object, or the gif
+14 -16
View File
@@ -345,7 +345,7 @@ const _subplot_defaults = KW(
:legendtitlefontcolor => :match,
:annotations => [], # annotation tuples... list of (x,y,annotation)
:projection => :none, # can also be :polar or :3d
:aspect_ratio => :none, # choose from :none or :equal
:aspect_ratio => :auto, # choose from :none or :equal
:margin => 1mm,
:left_margin => :match,
:top_margin => :match,
@@ -906,7 +906,7 @@ _replace_markershape(shape::Symbol) = get(_markerAliases, shape, shape)
_replace_markershape(shapes::AVec) = map(_replace_markershape, shapes)
_replace_markershape(shape) = shape
function _add_markershape(plotattributes::KW)
function _add_markershape(plotattributes::AKW)
# add the markershape if it needs to be added... hack to allow "m=10" to add a shape,
# and still allow overriding in _apply_recipe
ms = pop!(plotattributes, :markershape_to_add, :none)
@@ -1145,13 +1145,13 @@ end
filter_data(v::AVec, idxfilter::AVec{Int}) = v[idxfilter]
filter_data(v, idxfilter) = v
function filter_data!(plotattributes::KW, idxfilter)
function filter_data!(plotattributes::AKW, idxfilter)
for s in (:x, :y, :z)
plotattributes[s] = filter_data(get(plotattributes, s, nothing), idxfilter)
end
end
function _filter_input_data!(plotattributes::KW)
function _filter_input_data!(plotattributes::AKW)
idxfilter = pop!(plotattributes, :idxfilter, nothing)
if idxfilter !== nothing
filter_data!(plotattributes, idxfilter)
@@ -1200,7 +1200,7 @@ function warnOnUnsupported(pkg::AbstractBackend, plotattributes)
end
end
function warnOnUnsupported_scales(pkg::AbstractBackend, plotattributes::KW)
function warnOnUnsupported_scales(pkg::AbstractBackend, plotattributes::AKW)
for k in (:xscale, :yscale, :zscale, :scale)
if haskey(plotattributes, k)
v = plotattributes[k]
@@ -1267,7 +1267,7 @@ end
# # if the value is `:match` then we take whatever match_color is.
# # this is mainly used for cascading defaults for foreground and background colors
# function color_or_match!(plotattributes::KW, k::Symbol, match_color)
# function color_or_match!(plotattributes::AKW, k::Symbol, match_color)
# v = plotattributes[k]
# plotattributes[k] = if v == :match
# match_color
@@ -1379,18 +1379,18 @@ Base.get(series::Series, k::Symbol, v) = get(series.plotattributes, k, v)
# -----------------------------------------------------------------------------
function fg_color(plotattributes::Attr)
fg = plotattributes[:foreground_color]
function fg_color(plotattributes::AKW)
fg = get(plotattributes, :foreground_color, :auto)
if fg == :auto
bg = plot_color(plotattributes[:background_color])
bg = plot_color(get(plotattributes, :background_color, :white))
fg = isdark(bg) ? colorant"white" : colorant"black"
else
plot_color(fg)
end
end
function fg_color_sp(plotattributes::Attr)
fgsp = plotattributes[:foreground_color_subplot]
function fg_color_sp(plotattributes::AKW)
fgsp = get(plotattributes, :foreground_color_subplot, :match)
if fg == :match
fg_color(plotattributes)
else
@@ -1402,11 +1402,9 @@ end
# update attr from an input dictionary
function _update_plot_args(plt::Plot, plotattributes_in::AKW)
# TODO do merged kws need to be removed from plotattributes_in?
merge!(plt.attr, plotattributes_in)
# for (k,v) in _plot_defaults
# slice_arg!(plotattributes_in, plt.attr, k, v, 1, true)
# end
for (k,v) in _plot_defaults
slice_arg!(plotattributes_in, plt.attr, k, 1, true)
end
# handle colors
plotattributes= plt.attr
+1 -1
View File
@@ -32,7 +32,7 @@ function get_axis(sp::Subplot, letter::Symbol)
end::Axis
end
function process_axis_arg!(plotattributes::KW, arg, letter = "")
function process_axis_arg!(plotattributes::AKW, arg, letter = "")
T = typeof(arg)
arg = get(_scaleAliases, arg, arg)
+47 -69
View File
@@ -232,9 +232,7 @@ function gr_polaraxes(rmin::Real, rmax::Real, sp::Subplot)
sinf = sind.(a)
cosf = cosd.(a)
rtick_values, rtick_labels = get_ticks(sp, yaxis)
if yaxis[:formatter] in (:scientific, :auto) && yaxis[:ticks] in (:auto, :native)
rtick_labels = convert_sci_unicode.(rtick_labels)
end
rtick_labels = gr_tick_label.((yaxis,), rtick_labels)
#draw angular grid
if xaxis[:grid]
@@ -307,15 +305,27 @@ end
# ---------------------------------------------------------
# draw ONE Shape
function gr_draw_marker(xi, yi, msize, shape::Shape)
function gr_draw_marker(series, xi, yi, clims, i, msize, shape::Shape)
sx, sy = coords(shape)
# convert to ndc coords (percentages of window)
GR.selntran(0)
w, h = gr_plot_size
f = msize / (w + h)
xi, yi = GR.wctondc(xi, yi)
GR.fillarea(xi .+ sx .* f,
yi .+ sy .* f)
xs = xi .+ sx .* f
ys = yi .+ sy .* f
# draw the interior
mc = get_markercolor(series, clims, i)
gr_set_fill(mc)
gr_set_transparency(mc, get_markeralpha(series, i))
GR.fillarea(xs, ys)
# draw the shapes
msc = get_markerstrokecolor(series, i)
gr_set_line(get_markerstrokewidth(series, i), :solid, msc)
gr_set_transparency(msc, get_markerstrokealpha(series, i))
GR.polyline(xs, ys)
GR.selntran(1)
end
@@ -325,7 +335,11 @@ function nominal_size()
end
# draw ONE symbol marker
function gr_draw_marker(xi, yi, msize::Number, shape::Symbol)
function gr_draw_marker(series, xi, yi, clims, i, msize::Number, shape::Symbol)
GR.setborderwidth(series[:markerstrokewidth]);
gr_set_bordercolor(get_markerstrokecolor(series, i));
gr_set_markercolor(get_markercolor(series, clims, i));
gr_set_transparency(get_markeralpha(series, i))
GR.setmarkertype(gr_markertype[shape])
GR.setmarkersize(0.3msize / nominal_size())
GR.polymarker([xi], [yi])
@@ -343,13 +357,7 @@ function gr_draw_markers(series::Series, x, y, clims, msize = series[:markersize
for i=eachindex(x)
msi = _cycle(msize, i)
shape = _cycle(shapes, i)
i
GR.setborderwidth(series[:markerstrokewidth]);
gr_set_bordercolor(get_markerstrokecolor(series, i));
gr_set_markercolor(get_markercolor(series, clims, i));
gr_set_transparency(get_markeralpha(series, i))
gr_draw_marker(x[i], y[i], msi, shape)
gr_draw_marker(series, x[i], y[i], clims, i, msi, shape)
end
end
end
@@ -770,6 +778,19 @@ function gr_get_ticks_size(ticks, rot)
return w, h
end
gr_tick_label(axis,label) = (axis[:formatter] in (:scientific, :auto)) ?
gr_convert_sci_tick_label(label) :
label
function gr_convert_sci_tick_label(label)
caret_split = split(label,'^')
if length(caret_split) == 2
base, exponent = caret_split
label = "$base^{$exponent}"
end
convert_sci_unicode(label)
end
function gr_axis_height(sp, axis)
ticks = get_ticks(sp, axis)
gr_set_font(tickfont(axis))
@@ -960,7 +981,7 @@ function gr_display(sp::Subplot{GRBackend}, w, h, viewport_canvas)
data_lims = gr_xy_axislims(sp)
xy_lims = data_lims
ratio = sp[:aspect_ratio]
ratio = get_aspect_ratio(sp)
if ratio != :none
if ratio == :equal
ratio = 1
@@ -1223,18 +1244,9 @@ function gr_display(sp::Subplot{GRBackend}, w, h, viewport_canvas)
end
for (cv, dv) in zip(xticks...)
xi, yi = gr_w3tondc(cv, yt, zt)
if xaxis[:ticks] in (:auto, :native)
if xaxis[:formatter] in (:scientific, :auto)
# ensure correct dispatch in gr_text for automatic log ticks
if xaxis[:scale] in _logScales
dv = string(dv, "\\ ")
end
dv = convert_sci_unicode(dv)
end
end
xi += (yaxis[:mirror] ? 1 : -1) * 1e-2 * (xaxis[:tick_direction] == :out ? 1.5 : 1.0)
yi += (xaxis[:mirror] ? 1 : -1) * 5e-3 * (xaxis[:tick_direction] == :out ? 1.5 : 1.0)
gr_text(xi, yi, string(dv))
gr_text(xi, yi, gr_tick_label(xaxis, dv))
end
end
@@ -1262,16 +1274,9 @@ function gr_display(sp::Subplot{GRBackend}, w, h, viewport_canvas)
end
for (cv, dv) in zip(yticks...)
xi, yi = gr_w3tondc(xt, cv, zt)
if yaxis[:ticks] in (:auto, :native)
if xaxis[:formatter] in (:scientific, :auto)
# ensure correct dispatch in gr_text for automatic log ticks
if yaxis[:scale] in _logScales
dv = string(dv, "\\ ")
end
dv = convert_sci_unicode(dv)
end
end
gr_text(xi + (yaxis[:mirror] ? -1 : 1) * 1e-2 * (yaxis[:tick_direction] == :out ? 1.5 : 1.0), yi + (yaxis[:mirror] ? 1 : -1) * 5e-3 * (yaxis[:tick_direction] == :out ? 1.5 : 1.0), string(dv))
gr_text(xi + (yaxis[:mirror] ? -1 : 1) * 1e-2 * (yaxis[:tick_direction] == :out ? 1.5 : 1.0),
yi + (yaxis[:mirror] ? 1 : -1) * 5e-3 * (yaxis[:tick_direction] == :out ? 1.5 : 1.0),
gr_tick_label(yaxis, dv))
end
end
@@ -1299,16 +1304,8 @@ function gr_display(sp::Subplot{GRBackend}, w, h, viewport_canvas)
end
for (cv, dv) in zip(zticks...)
xi, yi = gr_w3tondc(xt, yt, cv)
if zaxis[:ticks] in (:auto, :native)
if zaxis[:formatter] in (:scientific, :auto)
# ensure correct dispatch in gr_text for automatic log ticks
if zaxis[:scale] in _logScales
dv = string(dv, "\\ ")
end
dv = convert_sci_unicode(dv)
end
end
gr_text(xi + (zaxis[:mirror] ? 1 : -1) * 1e-2 * (zaxis[:tick_direction] == :out ? 1.5 : 1.0), yi, string(dv))
gr_text(xi + (zaxis[:mirror] ? 1 : -1) * 1e-2 * (zaxis[:tick_direction] == :out ? 1.5 : 1.0),
yi, gr_tick_label(zaxis, dv))
end
end
#
@@ -1405,19 +1402,9 @@ function gr_display(sp::Subplot{GRBackend}, w, h, viewport_canvas)
# x labels
flip, mirror = gr_set_xticks_font(sp)
for (cv, dv) in zip(xticks...)
# use xor ($) to get the right y coords
xi, yi = GR.wctondc(cv, sp[:framestyle] == :origin ? 0 : xor(flip, mirror) ? ymax : ymin)
# @show cv dv ymin xi yi flip mirror (flip $ mirror)
if xaxis[:ticks] in (:auto, :native)
# ensure correct dispatch in gr_text for automatic log ticks
if xaxis[:formatter] in (:scientific, :auto)
if xaxis[:scale] in _logScales
dv = string(dv, "\\ ")
end
dv = convert_sci_unicode(dv)
end
end
gr_text(xi, yi + (mirror ? 1 : -1) * 5e-3 * (xaxis[:tick_direction] == :out ? 1.5 : 1.0), string(dv))
gr_text(xi, yi + (mirror ? 1 : -1) * 5e-3 * (xaxis[:tick_direction] == :out ? 1.5 : 1.0),
gr_tick_label(xaxis, dv))
end
end
@@ -1425,19 +1412,10 @@ function gr_display(sp::Subplot{GRBackend}, w, h, viewport_canvas)
# y labels
flip, mirror = gr_set_yticks_font(sp)
for (cv, dv) in zip(yticks...)
# use xor ($) to get the right y coords
xi, yi = GR.wctondc(sp[:framestyle] == :origin ? 0 : xor(flip, mirror) ? xmax : xmin, cv)
# @show cv dv xmin xi yi
if yaxis[:ticks] in (:auto, :native)
# ensure correct dispatch in gr_text for automatic log ticks
if yaxis[:formatter] in (:scientific, :auto)
if yaxis[:scale] in _logScales
dv = string(dv, "\\ ")
end
dv = convert_sci_unicode(dv)
end
end
gr_text(xi + (mirror ? 1 : -1) * 1e-2 * (yaxis[:tick_direction] == :out ? 1.5 : 1.0), yi, string(dv))
gr_text(xi + (mirror ? 1 : -1) * 1e-2 * (yaxis[:tick_direction] == :out ? 1.5 : 1.0),
yi,
gr_tick_label(yaxis, dv))
end
end
+4 -4
View File
@@ -109,7 +109,7 @@ _hdf5_datapath(subpath::String) = "$_hdf5_dataroot/$subpath"
_hdf5_map_str2telem(k::String) = HDF5PLOT_MAP_STR2TELEM[k]
_hdf5_map_str2telem(v::Vector) = HDF5PLOT_MAP_STR2TELEM[v[1]]
function _hdf5_merge!(dest::Dict, src::Dict)
function _hdf5_merge!(dest, src)
for (k, v) in src
if isa(v, Axis)
_hdf5_merge!(dest[k].plotattributes, v.plotattributes)
@@ -295,7 +295,7 @@ function _hdf5plot_gwrite(grp, k::String, v::Tuple)
end
#NOTE: _hdf5plot_overwritetype overwrites "Array" type with "Tuple".
end
function _hdf5plot_gwrite(grp, k::String, plotattributes::Dict)
function _hdf5plot_gwrite(grp, k::String, plotattributes::AKW)
# @warn("Cannot write dict: $k=$plotattributes")
end
function _hdf5plot_gwrite(grp, k::String, v::AbstractRange)
@@ -376,7 +376,7 @@ function _hdf5plot_gwrite(grp, k::String, v::Subplot)
_hdf5plot_writetype(grp, Subplot)
return
end
function _hdf5plot_write(grp, plotattributes::Dict)
function _hdf5plot_write(grp, plotattributes::AKW)
for (k, v) in plotattributes
kstr = string(k)
_hdf5plot_gwrite(grp, kstr, v)
@@ -567,7 +567,7 @@ function _hdf5plot_read(grp, k::String)
end
#Read in values in group to populate plotattributes:
function _hdf5plot_read(grp, plotattributes::Dict)
function _hdf5plot_read(grp, plotattributes::AKW)
gnames = names(grp)
for k in gnames
try
+7 -7
View File
@@ -470,7 +470,7 @@ function _update_plot_object(plt::Plot{PGFPlotsBackend})
push!(style, string("title style = {font = ", pgf_font(sp[:titlefontsize], pgf_thickness_scaling(sp)), ", color = ", cstr, ", draw opacity = ", α, ", rotate = ", sp[:titlefontrotation], "}"))
end
if sp[:aspect_ratio] in (1, :equal)
if get_aspect_ratio(sp) in (1, :equal)
kw[:axisEqual] = "true"
end
@@ -482,12 +482,12 @@ function _update_plot_object(plt::Plot{PGFPlotsBackend})
fg_alpha = alpha(plot_color(sp[:foreground_color_legend]))
push!(style, string(
"legend style = {",
pgf_linestyle(pgf_thickness_scaling(sp), sp[:foreground_color_legend], fg_alpha, "solid", ), ",",
"fill = $cstr,",
"fill opacity = $bg_alpha,",
"text opacity = $(alpha(plot_color(sp[:legendfontcolor]))),",
"font = ", pgf_font(sp[:legendfontsize], pgf_thickness_scaling(sp)),
"legend style = {",
pgf_linestyle(pgf_thickness_scaling(sp), sp[:foreground_color_legend], fg_alpha, "solid", ), ",",
"fill = $cstr,",
"fill opacity = $bg_alpha,",
"text opacity = $(alpha(plot_color(sp[:legendfontcolor]))),",
"font = ", pgf_font(sp[:legendfontsize], pgf_thickness_scaling(sp)),
"}",
))
+2 -2
View File
@@ -108,7 +108,7 @@ function shrink_by(lo, sz, ratio)
end
function plotly_apply_aspect_ratio(sp::Subplot, plotarea, pcts)
aspect_ratio = sp[:aspect_ratio]
aspect_ratio = get_aspect_ratio(sp)
if aspect_ratio != :none
if aspect_ratio == :equal
aspect_ratio = 1.0
@@ -780,7 +780,7 @@ end
function plotly_hover!(plotattributes_out::KW, hover)
# hover text
if all(in([:none, false]), hover)
if hover === nothing || all(in([:none, false]), hover)
plotattributes_out[:hoverinfo] = "none"
elseif any(!isnothing, hover)
plotattributes_out[:hoverinfo] = "text"
+1 -1
View File
@@ -1155,7 +1155,7 @@ function _before_layout_calcs(plt::Plot{PyPlotBackend})
end
# aspect ratio
aratio = sp[:aspect_ratio]
aratio = get_aspect_ratio(sp)
if aratio != :none
ax."set_aspect"(isa(aratio, Symbol) ? string(aratio) : aratio, anchor = "C")
end
+3 -2
View File
@@ -433,7 +433,7 @@ each line segment or marker in the plot.
x = t .* cos.(θ)
y = t .* sin.(θ)
p1 = plot(x, y, line_z=t, linewidth=3, legend=false)
p2 = scatter(x, y, marker_z=(x,y)->x+y, color=:bluesreds, legend=false)
p2 = scatter(x, y, marker_z=+, color=:bluesreds, legend=false)
plot(p1, p2)
end)]
),
@@ -507,7 +507,8 @@ _backend_skips = Dict(
:gr => [25, 30],
:pyplot => [25, 30],
:plotlyjs => [2, 21, 24, 25, 30, 31],
:pgfplots => [2, 5, 6, 10, 16, 20, 22, 23, 25, 28, 30],
:plotly => [2, 21, 24, 25, 30, 31],
:pgfplots => [2, 5, 6, 10, 16, 20, 22, 23, 25, 28, 30, 31, 34, 37, 38, 39],
)
+2 -2
View File
@@ -616,7 +616,7 @@ end
# ----------------------------------------------------------------------
# @layout macro
function add_layout_pct!(kw::KW, v::Expr, idx::Integer, nidx::Integer)
function add_layout_pct!(kw::AKW, v::Expr, idx::Integer, nidx::Integer)
# dump(v)
# something like {0.2w}?
if v.head == :call && v.args[1] == :*
@@ -637,7 +637,7 @@ function add_layout_pct!(kw::KW, v::Expr, idx::Integer, nidx::Integer)
error("Couldn't match layout curly (idx=$idx): $v")
end
function add_layout_pct!(kw::KW, v::Number, idx::Integer)
function add_layout_pct!(kw::AKW, v::Number, idx::Integer)
# kw[idx == 1 ? :w : :h] = v*pct
idx == 1 && (kw[:w] = v*pct)
(idx == 2 || nidx == 1) && (kw[:h] = v*pct)
+8
View File
@@ -60,6 +60,13 @@ function html(plt::Plot, fn::AbstractString)
end
html(fn::AbstractString) = html(current(), fn)
function txt(plt::Plot, fn::AbstractString)
fn = addExtension(fn, "txt")
io = open(fn, "w")
show(io, MIME("text/plain"), plt)
close(io)
end
txt(fn::AbstractString) = txt(current(), fn)
# ----------------------------------------------------------------
@@ -73,6 +80,7 @@ const _savemap = Dict(
"tex" => tex,
"html" => html,
"tikz" => tex,
"txt" => txt,
)
function getExtension(fn::AbstractString)
+12 -12
View File
@@ -3,14 +3,14 @@
# ------------------------------------------------------------------
# preprocessing
function series_idx(kw_list::AVec{KW}, kw::KW)
function series_idx(kw_list::AVec{KW}, kw::AKW)
Int(kw[:series_plotindex]) - Int(kw_list[1][:series_plotindex]) + 1
end
function _expand_seriestype_array(plotattributes::KW, args)
function _expand_seriestype_array(plotattributes::AKW, args)
sts = get(plotattributes, :seriestype, :path)
if typeof(sts) <: AbstractArray
delete!(plotattributes, :seriestype)
reset_kw!(plotattributes, :seriestype)
rd = Vector{RecipeData}(undef, size(sts, 1))
for r in axes(sts, 1)
dc = copy(plotattributes)
@@ -23,7 +23,7 @@ function _expand_seriestype_array(plotattributes::KW, args)
end
end
function _preprocess_args(plotattributes::KW, args, still_to_process::Vector{RecipeData})
function _preprocess_args(plotattributes::AKW, args, still_to_process::Vector{RecipeData})
# the grouping mechanism is a recipe on a GroupBy object
# we simply add the GroupBy object to the front of the args list to allow
# the recipe to be applied
@@ -46,7 +46,7 @@ function _preprocess_args(plotattributes::KW, args, still_to_process::Vector{Rec
_axis_defaults_byletter[:y],
_axis_defaults_byletter[:z])
if haskey(defdict, k)
delete!(plotattributes, k)
reset_kw!(plotattributes, k)
end
end
end
@@ -59,7 +59,7 @@ end
# user recipes
function _process_userrecipes(plt::Plot, plotattributes::KW, args)
function _process_userrecipes(plt::Plot, plotattributes::AKW, args)
still_to_process = RecipeData[]
args = _preprocess_args(plotattributes, args, still_to_process)
@@ -110,7 +110,7 @@ function _process_userrecipe(plt::Plot, kw_list::Vector{KW}, recipedata::RecipeD
return
end
function _preprocess_userrecipe(kw::KW)
function _preprocess_userrecipe(kw::AKW)
_add_markershape(kw)
# if there was a grouping, filter the data here
@@ -134,7 +134,7 @@ function _preprocess_userrecipe(kw::KW)
return
end
function _add_errorbar_kw(kw_list::Vector{KW}, kw::KW)
function _add_errorbar_kw(kw_list::Vector{KW}, kw::AKW)
# handle error bars by creating new recipedata data... these will have
# the same recipedata index as the recipedata they are copied from
for esym in (:xerror, :yerror)
@@ -149,7 +149,7 @@ function _add_errorbar_kw(kw_list::Vector{KW}, kw::KW)
end
end
function _add_smooth_kw(kw_list::Vector{KW}, kw::KW)
function _add_smooth_kw(kw_list::Vector{KW}, kw::AKW)
# handle smoothing by adding a new series
if get(kw, :smooth, false)
x, y = kw[:x], kw[:y]
@@ -174,7 +174,7 @@ end
# to generate a list of RecipeData objects (data + attributes).
# If we applied a "plot recipe" without error, then add the returned datalist's KWs,
# otherwise we just add the original KW.
function _process_plotrecipe(plt::Plot, kw::KW, kw_list::Vector{KW}, still_to_process::Vector{KW})
function _process_plotrecipe(plt::Plot, kw::AKW, kw_list::Vector{KW}, still_to_process::Vector{KW})
if !isa(get(kw, :seriestype, nothing), Symbol)
# seriestype was never set, or it's not a Symbol, so it can't be a plot recipe
push!(kw_list, kw)
@@ -205,7 +205,7 @@ end
# ------------------------------------------------------------------
# setup plot and subplot
function _plot_setup(plt::Plot, plotattributes::KW, kw_list::Vector{KW})
function _plot_setup(plt::Plot, plotattributes::AKW, kw_list::Vector{KW})
# merge in anything meant for the Plot
for kw in kw_list, (k,v) in kw
haskey(_plot_defaults, k) && (plotattributes[k] = pop!(kw, k))
@@ -254,7 +254,7 @@ function _plot_setup(plt::Plot, plotattributes::KW, kw_list::Vector{KW})
plt[:inset_subplots] = nothing
end
function _subplot_setup(plt::Plot, plotattributes::KW, kw_list::Vector{KW})
function _subplot_setup(plt::Plot, plotattributes::AKW, kw_list::Vector{KW})
# we'll keep a map of subplot to an attribute override dict.
# Subplot/Axis attributes set by a user/series recipe apply only to the
# Subplot object which they belong to.
+1 -1
View File
@@ -163,7 +163,7 @@ end
# this is the core plotting function. recursively apply recipes to build
# a list of series KW dicts.
# note: at entry, we only have those preprocessed args which were passed in... no default values yet
function _plot!(plt::Plot, plotattributes::KW, args::Tuple)
function _plot!(plt::Plot, plotattributes::AKW, args::Tuple)
plotattributes[:plot_object] = plt
if !isempty(args) && !isdefined(Main, :StatsPlots) &&
+7 -7
View File
@@ -47,7 +47,7 @@ end
num_series(x::AMat) = size(x,2)
num_series(x) = 1
RecipesBase.apply_recipe(plotattributes::KW, ::Type{T}, plt::AbstractPlot) where {T} = throw(MethodError(T, "Unmatched plot recipe: $T"))
RecipesBase.apply_recipe(plotattributes::AKW, ::Type{T}, plt::AbstractPlot) where {T} = throw(MethodError(T, "Unmatched plot recipe: $T"))
# ---------------------------------------------------------------------------
@@ -813,7 +813,7 @@ end
# ---------------------------------------------------------------------------
# Error Bars
function error_style!(plotattributes::KW)
function error_style!(plotattributes::AKW)
plotattributes[:seriestype] = :path
plotattributes[:linecolor] = plotattributes[:markerstrokecolor]
plotattributes[:linewidth] = plotattributes[:markerstrokewidth]
@@ -874,8 +874,8 @@ end
# ---------------------------------------------------------------------------
# quiver
# function apply_series_recipe(plotattributes::KW, ::Type{Val{:quiver}})
function quiver_using_arrows(plotattributes::KW)
# function apply_series_recipe(plotattributes::AKW, ::Type{Val{:quiver}})
function quiver_using_arrows(plotattributes::AKW)
plotattributes[:label] = ""
plotattributes[:seriestype] = :path
if !isa(plotattributes[:arrow], Arrow)
@@ -913,8 +913,8 @@ function quiver_using_arrows(plotattributes::KW)
# KW[plotattributes]
end
# function apply_series_recipe(plotattributes::KW, ::Type{Val{:quiver}})
function quiver_using_hack(plotattributes::KW)
# function apply_series_recipe(plotattributes::AKW, ::Type{Val{:quiver}})
function quiver_using_hack(plotattributes::AKW)
plotattributes[:label] = ""
plotattributes[:seriestype] = :shape
@@ -959,7 +959,7 @@ function quiver_using_hack(plotattributes::KW)
# KW[plotattributes]
end
# function apply_series_recipe(plotattributes::KW, ::Type{Val{:quiver}})
# function apply_series_recipe(plotattributes::AKW, ::Type{Val{:quiver}})
@recipe function f(::Type{Val{:quiver}}, x, y, z)
if :arrow in supported_attrs()
quiver_using_arrows(plotattributes)
+2 -1
View File
@@ -267,7 +267,7 @@ end
# # --------------------------------------------------------------------
# helper function to ensure relevant attributes are wrapped by Surface
function wrap_surfaces(plotattributes::KW)
function wrap_surfaces(plotattributes::AKW)
if haskey(plotattributes, :fill_z)
v = plotattributes[:fill_z]
if !isa(v, Surface)
@@ -347,6 +347,7 @@ end
seriestype := :heatmap
yflip --> true
cbar --> false
aspect_ratio --> :equal
z, plotattributes[:fillcolor] = replace_image_with_heatmap(mat)
SliceIt, m, n, Surface(z)
end
+1 -1
View File
@@ -8,7 +8,7 @@ function theme(s::Symbol; kw...)
_theme(s, defaults; kw...)
end
function _theme(s::Symbol, defaults::KW; kw...)
function _theme(s::Symbol, defaults::AKW; kw...)
# Reset to defaults to overwrite active theme
reset_defaults()
+12
View File
@@ -30,6 +30,18 @@ Base.getindex(attr::Attr, k) = haskey(attr.explicit,k) ?
attr.explicit[k] : attr.defaults[k]
Base.haskey(attr::Attr, k) = haskey(attr.explicit,k) || haskey(attr.defaults,k)
Base.get(attr::Attr, k, default) = haskey(attr, k) ? attr[k] : default
function Base.get!(attr::Attr, k, default)
v = if haskey(attr, k)
attr[k]
else
attr.defaults[k] = default
end
return v
end
function Base.delete!(attr::Attr, k)
haskey(attr.explicit, k) && delete!(attr.explicit, k)
haskey(attr.defaults, k) && delete!(attr.defaults, k)
end
Base.length(attr::Attr) = length(union(keys(attr.explicit), keys(attr.defaults)))
function Base.iterate(attr::Attr)
exp_keys = keys(attr.explicit)
+21 -17
View File
@@ -116,24 +116,11 @@ end
function replace_image_with_heatmap(z::Array{T}) where T<:Colorant
n, m = size(z)
# idx = 0
colors = ColorGradient(vec(z))
newz = reshape(range(0, stop=1, length=n*m), n, m)
newz, colors
# newz = zeros(n, m)
# for i=1:n, j=1:m
# push!(colors, T(z[i,j]...))
# newz[i,j] = idx / (n*m-1)
# idx += 1
# end
# newz, ColorGradient(colors)
end
function imageHack(plotattributes::KW)
is_seriestype_supported(:heatmap) || error("Neither :image or :heatmap are supported!")
plotattributes[:seriestype] = :heatmap
plotattributes[:z], plotattributes[:fillcolor] = replace_image_with_heatmap(plotattributes[:z].surf)
end
# ---------------------------------------------------------------
"Build line segments for plotting"
@@ -499,7 +486,7 @@ function make_fillrange_side(y, rib)
end
# turn a ribbon into a fillrange
function make_fillrange_from_ribbon(kw::KW)
function make_fillrange_from_ribbon(kw::AKW)
y, rib = kw[:y], kw[:ribbon]
rib = wraptuple(rib)
rib1, rib2 = -first(rib), last(rib)
@@ -693,6 +680,10 @@ function get_markerstrokealpha(series, i::Int = 1)
_cycle(series[:markerstrokealpha], i)
end
function get_markerstrokewidth(series, i::Int = 1)
_cycle(series[:markerstrokewidth], i)
end
function has_attribute_segments(series::Series)
# we want to check if a series needs to be split into segments just because
# of its attributes
@@ -706,6 +697,19 @@ function has_attribute_segments(series::Series)
return any((typeof(series[attr]) <: AbstractVector && length(series[attr]) > 1) for attr in [:seriescolor, :seriesalpha, :linecolor, :linealpha, :linewidth, :linestyle, :fillcolor, :fillalpha, :markercolor, :markeralpha, :markerstrokecolor, :markerstrokealpha]) || any(typeof(series[attr]) <: AbstractArray for attr in (:line_z, :fill_z, :marker_z))
end
function get_aspect_ratio(sp)
aspect_ratio = sp[:aspect_ratio]
if aspect_ratio == :auto
aspect_ratio = :none
for series in series_list(sp)
if series[:seriestype] == :image
aspect_ratio = :equal
end
end
end
return aspect_ratio
end
# ---------------------------------------------------------------
makekw(; kw...) = KW(kw)
@@ -842,8 +846,8 @@ function dumpdict(io::IO, plotattributes::AKW, prefix = "", alwaysshow = false)
end
println(io)
end
DD(io::IO, plotattributes::KW, prefix = "") = dumpdict(io, plotattributes, prefix, true)
DD(plotattributes::KW, prefix = "") = DD(stdout, plotattributes, prefix)
DD(io::IO, plotattributes::AKW, prefix = "") = dumpdict(io, plotattributes, prefix, true)
DD(plotattributes::AKW, prefix = "") = DD(stdout, plotattributes, prefix)
function dumpcallstack()
error() # well... you wanted the stacktrace, didn't you?!?
@@ -1158,7 +1162,7 @@ function convert_sci_unicode(label::AbstractString)
for key in keys(unicode_dict)
label = replace(label, key => unicode_dict[key])
end
if occursin("10^{", label)
if occursin("×10^{", label)
label = string(label, "}")
end
label
+25 -1
View File
@@ -42,7 +42,31 @@ include("imgcomp.jl")
Random.seed!(1234)
default(show=false, reuse=true)
is_ci() = get(ENV, "CI", "false") == "true"
img_tol = is_ci() ? 10e-2 : 10e-2
img_tol = is_ci() ? 1e-2 : 1e-3
## Uncomment the following lines to update reference images for different backends
#=
@testset "GR" begin
image_comparison_facts(:gr, tol=img_tol, skip = Plots._backend_skips[:gr])
end
plotly()
@testset "Plotly" begin
image_comparison_facts(:plotly, tol=img_tol, skip = Plots._backend_skips[:plotlyjs])
end
pyplot()
@testset "PyPlot" begin
image_comparison_facts(:pyplot, tol=img_tol, skip = Plots._backend_skips[:pyplot])
end
pgfplots()
@testset "PGFPlots" begin
image_comparison_facts(:pgfplots, tol=img_tol, skip = Plots._backend_skips[:pgfplots])
end
=#
##
@testset "Backends" begin