Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Appearance settings

Commit 2f4a3e3

Browse filesBrowse files
authored
Merge pull request #17257 from tacaswell/backport_eps_work
Backport eps work
2 parents 687531d + 746c691 commit 2f4a3e3
Copy full SHA for 2f4a3e3

File tree

Expand file treeCollapse file tree

7 files changed

+122
-97
lines changed
Filter options
Expand file treeCollapse file tree

7 files changed

+122
-97
lines changed

‎lib/matplotlib/backends/backend_ps.py

Copy file name to clipboardExpand all lines: lib/matplotlib/backends/backend_ps.py
+13-12Lines changed: 13 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -543,8 +543,7 @@ def draw_tex(self, gc, x, y, s, prop, angle, ismath='TeX!', mtext=None):
543543
r'\psfrag{%s}[Bl][Bl][1][%f]{\fontsize{%f}{%f}%s}' % (
544544
thetext, angle, fontsize, fontsize*1.25, tex))
545545
else:
546-
# Stick to the bottom alignment, but this may give incorrect
547-
# baseline some times.
546+
# Stick to the bottom alignment.
548547
pos = _nums_to_str(x-corr, y-bl)
549548
self.psfrag.append(
550549
r'\psfrag{%s}[bl][bl][1][%f]{\fontsize{%f}{%f}%s}' % (
@@ -1234,19 +1233,21 @@ def convert_psfrags(tmpfile, psfrags, font_preamble, custom_preamble,
12341233
"""
12351234
with mpl.rc_context({
12361235
"text.latex.preamble":
1237-
rcParams["text.latex.preamble"] +
1238-
r"\usepackage{psfrag,color}"
1239-
r"\usepackage[dvips]{graphicx}"
1240-
r"\PassOptionsToPackage{dvips}{geometry}"}):
1236+
mpl.rcParams["text.latex.preamble"] +
1237+
r"\usepackage{psfrag,color}""\n"
1238+
r"\usepackage[dvips]{graphicx}""\n"
1239+
r"\geometry{papersize={%(width)sin,%(height)sin},"
1240+
r"body={%(width)sin,%(height)sin},margin=0in}"
1241+
% {"width": paper_width, "height": paper_height}
1242+
}):
12411243
dvifile = TexManager().make_dvi(
1242-
r"\newgeometry{papersize={%(width)sin,%(height)sin},"
1243-
r"body={%(width)sin,%(height)sin}, margin={0in,0in}}""\n"
1244-
r"\begin{figure}"
1245-
r"\centering\leavevmode%(psfrags)s"
1246-
r"\includegraphics*[angle=%(angle)s]{%(epsfile)s}"
1244+
"\n"
1245+
r"\begin{figure}""\n"
1246+
r" \centering\leavevmode""\n"
1247+
r" %(psfrags)s""\n"
1248+
r" \includegraphics*[angle=%(angle)s]{%(epsfile)s}""\n"
12471249
r"\end{figure}"
12481250
% {
1249-
"width": paper_width, "height": paper_height,
12501251
"psfrags": "\n".join(psfrags),
12511252
"angle": 90 if orientation == 'landscape' else 0,
12521253
"epsfile": pathlib.Path(tmpfile).resolve().as_posix(),

‎lib/matplotlib/dviread.py

Copy file name to clipboardExpand all lines: lib/matplotlib/dviread.py
+21Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -269,6 +269,12 @@ def _output(self):
269269
maxx = max(maxx, x + w)
270270
maxy = max(maxy, y + e)
271271
maxy_pure = max(maxy_pure, y)
272+
if self._baseline_v is not None:
273+
maxy_pure = self._baseline_v # This should normally be the case.
274+
self._baseline_v = None
275+
276+
if not self.text and not self.boxes: # Avoid infs/nans from inf+/-inf.
277+
return Page(text=[], boxes=[], width=0, height=0, descent=0)
272278

273279
if self.dpi is None:
274280
# special case for ease of debugging: output raw dvi coordinates
@@ -296,9 +302,24 @@ def _read(self):
296302
Read one page from the file. Return True if successful,
297303
False if there were no more pages.
298304
"""
305+
# Pages appear to start with the sequence
306+
# bop (begin of page)
307+
# xxx comment
308+
# down
309+
# push
310+
# down, down
311+
# push
312+
# down (possibly multiple)
313+
# push <= here, v is the baseline position.
314+
# etc.
315+
# (dviasm is useful to explore this structure.)
316+
self._baseline_v = None
299317
while True:
300318
byte = self.file.read(1)[0]
301319
self._dtable[byte](self, byte)
320+
if (self._baseline_v is None
321+
and len(getattr(self, "stack", [])) == 3):
322+
self._baseline_v = self.v
302323
if byte == 140: # end of page
303324
return True
304325
if self.state is _dvistate.post_post: # end of file
Binary file not shown.
Loading

‎lib/matplotlib/tests/test_usetex.py

Copy file name to clipboard
+38-12Lines changed: 38 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,4 @@
1+
import numpy as np
12
import pytest
23
import platform
34

@@ -7,31 +8,56 @@
78
from matplotlib.ticker import EngFormatter
89

910

10-
@pytest.fixture(autouse=True) # All tests in this module use usetex.
11-
def usetex():
12-
if not mpl.checkdep_usetex(True):
13-
pytest.skip('Missing TeX of Ghostscript or dvipng')
14-
mpl.rcParams['text.usetex'] = True
11+
if not mpl.checkdep_usetex(True):
12+
pytestmark = pytest.mark.skip('Missing TeX of Ghostscript or dvipng')
1513

1614

17-
@image_comparison(baseline_images=['test_usetex'],
18-
extensions=['pdf', 'png'],
19-
tol={'aarch64': 2.868}.get(platform.machine(), 0.3))
15+
@image_comparison(
16+
baseline_images=['test_usetex'],
17+
extensions=['pdf', 'png'],
18+
style="mpl20")
2019
def test_usetex():
20+
mpl.rcParams['text.usetex'] = True
2121
fig = plt.figure()
2222
ax = fig.add_subplot(111)
23-
ax.text(0.1, 0.2,
23+
kwargs = {"verticalalignment": "baseline", "size": 24,
24+
"bbox": dict(pad=0, edgecolor="k", facecolor="none")}
25+
ax.text(0.2, 0.7,
2426
# the \LaTeX macro exercises character sizing and placement,
2527
# \left[ ... \right\} draw some variable-height characters,
2628
# \sqrt and \frac draw horizontal rules, \mathrm changes the font
2729
r'\LaTeX\ $\left[\int\limits_e^{2e}'
2830
r'\sqrt\frac{\log^3 x}{x}\,\mathrm{d}x \right\}$',
29-
fontsize=24)
30-
ax.set_xticks([])
31-
ax.set_yticks([])
31+
**kwargs)
32+
ax.text(0.2, 0.3, "lg", **kwargs)
33+
ax.text(0.4, 0.3, r"$\frac{1}{2}\pi$", **kwargs)
34+
ax.text(0.6, 0.3, "$p^{3^A}$", **kwargs)
35+
ax.text(0.8, 0.3, "$p_{3_2}$", **kwargs)
36+
for x in {t.get_position()[0] for t in ax.texts}:
37+
ax.axvline(x)
38+
for y in {t.get_position()[1] for t in ax.texts}:
39+
ax.axhline(y)
40+
ax.set_axis_off()
41+
42+
43+
@check_figures_equal()
44+
def test_empty(fig_test, fig_ref):
45+
mpl.rcParams['text.usetex'] = True
46+
fig_test.text(.5, .5, "% a comment")
3247

3348

3449
@check_figures_equal()
3550
def test_unicode_minus(fig_test, fig_ref):
51+
mpl.rcParams['text.usetex'] = True
3652
fig_test.text(.5, .5, "$-$")
3753
fig_ref.text(.5, .5, "\N{MINUS SIGN}")
54+
55+
56+
def test_mathdefault():
57+
plt.rcParams["axes.formatter.use_mathtext"] = True
58+
fig = plt.figure()
59+
fig.add_subplot().set_xlim(-1, 1)
60+
# Check that \mathdefault commands generated by tickers don't cause
61+
# problems when later switching usetex on.
62+
mpl.rcParams['text.usetex'] = True
63+
fig.canvas.draw()

‎lib/matplotlib/texmanager.py

Copy file name to clipboardExpand all lines: lib/matplotlib/texmanager.py
+37-29Lines changed: 37 additions & 29 deletions
Original file line numberDiff line numberDiff line change
@@ -192,6 +192,25 @@ def get_custom_preamble(self):
192192
"""Return a string containing user additions to the tex preamble."""
193193
return rcParams['text.latex.preamble']
194194

195+
def _get_preamble(self):
196+
unicode_preamble = "\n".join([
197+
r"\usepackage[utf8]{inputenc}",
198+
r"\DeclareUnicodeCharacter{2212}{\ensuremath{-}}",
199+
]) if rcParams["text.latex.unicode"] else ""
200+
return "\n".join([
201+
r"\documentclass{article}",
202+
# Pass-through \mathdefault, which is used in non-usetex mode to
203+
# use the default text font but was historically suppressed in
204+
# usetex mode.
205+
r"\newcommand{\mathdefault}[1]{#1}",
206+
self._font_preamble,
207+
unicode_preamble,
208+
# Needs to come early so that the custom preamble can change the
209+
# geometry, e.g. in convert_psfrags.
210+
r"\usepackage[papersize=72in,body=70in,margin=1in]{geometry}",
211+
self.get_custom_preamble(),
212+
])
213+
195214
def make_tex(self, tex, fontsize):
196215
"""
197216
Generate a tex file to render the tex string at a specific font size.
@@ -200,29 +219,22 @@ def make_tex(self, tex, fontsize):
200219
"""
201220
basefile = self.get_basefile(tex, fontsize)
202221
texfile = '%s.tex' % basefile
203-
custom_preamble = self.get_custom_preamble()
204222
fontcmd = {'sans-serif': r'{\sffamily %s}',
205223
'monospace': r'{\ttfamily %s}'}.get(self.font_family,
206224
r'{\rmfamily %s}')
207225
tex = fontcmd % tex
208226

209-
unicode_preamble = "\n".join([
210-
r"\usepackage[utf8]{inputenc}",
211-
r"\DeclareUnicodeCharacter{2212}{\ensuremath{-}}",
212-
]) if rcParams["text.latex.unicode"] else ""
213-
214227
s = r"""
215-
\documentclass{article}
216228
%s
217-
%s
218-
%s
219-
\usepackage[papersize={72in,72in},body={70in,70in},margin={1in,1in}]{geometry}
220229
\pagestyle{empty}
221230
\begin{document}
222-
\fontsize{%f}{%f}%s
231+
%% The empty hbox ensures that a page is printed even for empty inputs, except
232+
%% when using psfrag which gets confused by it.
233+
\fontsize{%f}{%f}%%
234+
\ifdefined\psfrag\else\hbox{}\fi%%
235+
%s
223236
\end{document}
224-
""" % (self._font_preamble, unicode_preamble, custom_preamble,
225-
fontsize, fontsize * 1.25, tex)
237+
""" % (self._get_preamble(), fontsize, fontsize * 1.25, tex)
226238
with open(texfile, 'wb') as fh:
227239
if rcParams['text.latex.unicode']:
228240
fh.write(s.encode('utf8'))
@@ -250,27 +262,17 @@ def make_tex_preview(self, tex, fontsize):
250262
"""
251263
basefile = self.get_basefile(tex, fontsize)
252264
texfile = '%s.tex' % basefile
253-
custom_preamble = self.get_custom_preamble()
254265
fontcmd = {'sans-serif': r'{\sffamily %s}',
255266
'monospace': r'{\ttfamily %s}'}.get(self.font_family,
256267
r'{\rmfamily %s}')
257268
tex = fontcmd % tex
258269

259-
unicode_preamble = "\n".join([
260-
r"\usepackage[utf8]{inputenc}",
261-
r"\DeclareUnicodeCharacter{2212}{\ensuremath{-}}",
262-
]) if rcParams["text.latex.unicode"] else ""
263-
264270
# newbox, setbox, immediate, etc. are used to find the box
265271
# extent of the rendered text.
266272

267273
s = r"""
268-
\documentclass{article}
269-
%s
270-
%s
271274
%s
272275
\usepackage[active,showbox,tightpage]{preview}
273-
\usepackage[papersize={72in,72in},body={70in,70in},margin={1in,1in}]{geometry}
274276
275277
%% we override the default showbox as it is treated as an error and makes
276278
%% the exit status not zero
@@ -282,8 +284,7 @@ def make_tex_preview(self, tex, fontsize):
282284
{\fontsize{%f}{%f}%s}
283285
\end{preview}
284286
\end{document}
285-
""" % (self._font_preamble, unicode_preamble, custom_preamble,
286-
fontsize, fontsize * 1.25, tex)
287+
""" % (self._get_preamble(), fontsize, fontsize * 1.25, tex)
287288
with open(texfile, 'wb') as fh:
288289
if rcParams['text.latex.unicode']:
289290
fh.write(s.encode('utf8'))
@@ -391,9 +392,16 @@ def make_png(self, tex, fontsize, dpi):
391392
# see get_rgba for a discussion of the background
392393
if not os.path.exists(pngfile):
393394
dvifile = self.make_dvi(tex, fontsize)
394-
self._run_checked_subprocess(
395-
["dvipng", "-bg", "Transparent", "-D", str(dpi),
396-
"-T", "tight", "-o", pngfile, dvifile], tex)
395+
cmd = ["dvipng", "-bg", "Transparent", "-D", str(dpi),
396+
"-T", "tight", "-o", pngfile, dvifile]
397+
# When testing, disable FreeType rendering for reproducibility; but
398+
# dvipng 1.16 has a bug (fixed in f3ff241) that breaks --freetype0
399+
# mode, so for it we keep FreeType enabled; the image will be
400+
# slightly off.
401+
if (getattr(mpl, "_called_from_pytest", False)
402+
and mpl._get_executable_info("dvipng").version != "1.16"):
403+
cmd.insert(1, "--freetype0")
404+
self._run_checked_subprocess(cmd, tex)
397405
return pngfile
398406

399407
def get_grey(self, tex, fontsize=None, dpi=None):
@@ -446,7 +454,7 @@ def get_text_width_height_descent(self, tex, fontsize, renderer=None):
446454
return width, height + depth, depth
447455

448456
else:
449-
# use dviread. It sometimes returns a wrong descent.
457+
# use dviread.
450458
dvifile = self.make_dvi(tex, fontsize)
451459
with dviread.Dvi(dvifile, 72 * dpi_fraction) as dvi:
452460
page, = dvi

0 commit comments

Comments
0 (0)
Morty Proxy This is a proxified and sanitized view of the page, visit original site.