Open nbsmokee opened 3 years ago
pgfplotsx has the same problem with the size
parameter., it somewhat ignores it. Setting a size
changes the saved image, but the result is not the one chosen and appears to depend on the data to be plotted.
GR defaults to 600x400 px, while PGFPlotsX default to 914x539 px, using the following MWE
using Plots, LaTeXStrings
data = rand(10)
plot(data)
savefig("size_gr.png")
pgfplotsx()
plot(data)
savefig("size_pgfplotsx.png")
The result is difficult to replicate, because with random data each run can end (or not) in a different final image size for PGFPlotsX.
The aspect ratio of the actual plot (everything but the legend) seems similar enough though, doing
using Plots, LaTeXStrings
data = rand(10)
plot(data)
savefig("size_gr.png")
pgfplotsx()
plot(data, legend=false)
savefig("size_pgfplotsx.png")
I get 600x400 px (600/400 = 1.5) for GR, as it should, and 860x546 px (860/546 = 1.575) for PGFPlotsX. So, in the ballpark.
The fact that kind of tries to respect the aspect ratio can be seen again doing
using Plots, LaTeXStrings
pgfplotsx()
for i in 1:30
plot(rand(10), size=(600,600))
savefig("size_pgfplotsx_" * string(i) * ".png")
end
I get 30 images with varying sizes: 914x849 px (x2), 914x841 px (x1), 914x839 px (x26), 923x839 px (x1), but all close to 1:1, if it weren’t for the legend. A different run would give different results, obviously. Clearly is taking the input size, the data and then choosing the final size, but as far as I know it is not documented which algorithm is used, as to reversed it and control effectively the final size.
In practice this is "solved" by trying different inputs until you get one output you like/can use. What is especially annoying is the preference for odd values making impossible to use a series of images for a video with VideoIO.jl (in the example above not a single one got an even x even value).
This is maybe tangentially related to #2303, where GR produces results off by one pixel.
From julia> versioninfo()
Julia Version 1.5.3
Commit 788b2c77c1 (2020-11-09 13:37 UTC)
Platform Info:
OS: Windows (x86_64-w64-mingw32)
CPU: Intel(R) Core(TM) i5-6200U CPU @ 2.30GHz
WORD_SIZE: 64
LIBM: libopenlibm
LLVM: libLLVM-9.0.1 (ORCJIT, skylake)
From (@v1.5) pkg> status
[b964fa9f] LaTeXStrings v1.2.0
[8314cec4] PGFPlotsX v1.2.10
[91a5bcdd] Plots v1.9.1
[f3b207a7] StatsPlots v0.14.17
I had this problem too. For Plotly, this works for me as a workaround.
using Plots
import Plotly
plotlyjs()
y = randn(20, 4)
plt = plot(y, size=(300,400), show=true)
width, height = plt.attr[:size]
Plots.prepare_output(plt)
Plotly.savefig(Plots.plotlybase_syncplot(plt), "test.png", width=width, height=height)
I'm trying to use PlotlyJS in Pluto, but I cannot save files using the desired resolution. I've tried the above method but it doesn't work. I'm forced to use the GR backend to save files, but it lacks the nice interactive features plotlyjs has.
For reference, a similar workaround for PlotlyJS in Pluto is
import PlotlyJS
width, height = plt.attr[:size]
Plots.prepare_output(plt)
PlotlyJS.savefig(Plots.plotlyjs_syncplot(plt), "plot.pdf", width=width, height=height)
This problem definitely occurs using the Plotly backend in Plots.jl . Unfortunately the savefig exported in Plots.jl does NOT have width and height arguments. I haven't yet tried @ranocha solution.
This is an important issue for automating and creating plots for documents. I hope that the Plots.jl crew can remedy this. Interestingly, if you save the figure directly from within the vscode Julia plots pane, the svg file will have the correct sizing.
This is still a problem for my setup, but I can also not use the work proposed by @ranocha because plotlybase_syncplot
is not available:
Julia Version 1.9.2
Plotly v0.4.1 PlotlyBase v0.8.19 PlotlyJS v0.18.13 PlotlyKaleido v2.2.2 Plots v1.39.0
using Plots
import Plotly
plotlyjs()
function save_pdf(p, filename)
width, height = p.attr[:size]
Plots.prepare_output(p)
Plotly.savefig(Plots.plotlybase_syncplot(p), filename, width=width, height=height)
end
p = plot(...)
save_pdf(p, filename)
Results in
ERROR: UndefVarError: `plotlybase_syncplot` not defined
Any suggestion or alternative work around would be greatly appreciated.
It's now called plotlyjs_syncplot
I think this has not been reported before. I found that, when using the PlotlyJS backend, the
size
anddpi
kwargs seem to be ingored and thus don't produce the expected results.Details
size
, with the following MWE the plot shows up correctly in the plot pane (I use vscode, if that's important), but when I callsavefig
, the created image will always have a resolution of 700 * 500, as if thesize
keyword was not there. This is particularly annoying since obviously I need the plots to have a certain non-standard aspect ratio.y = randn(20, 4) plot(y, size=(300,400), show=true) savefig("test.png")
Backends
This bug occurs on ( insert
x
below )Versions
Plots.jl version: v1.9.1 Backend version (
]st -m
): PlotlyJS v0.14.0 Output ofversioninfo()
: