Skip to content

Implement PdfPages for backend pgf#10548

Merged
anntzer merged 26 commits into
matplotlib:masterfrom
maxnoe:pgf_pdf_pages
Feb 28, 2018
Merged

Implement PdfPages for backend pgf#10548
anntzer merged 26 commits into
matplotlib:masterfrom
maxnoe:pgf_pdf_pages

Conversation

@maxnoe

@maxnoe maxnoe commented Feb 20, 2018

Copy link
Copy Markdown
Contributor

PR Summary

This adds a PdfPages class for backend_pgf analogous to the one in backend_pdf to be able to use the pgf backend with multi page pdfs.

Looking forward to reviews

PR Checklist

  • Has Pytest style unit tests
  • Code is PEP 8 compliant
  • New features are documented, with examples if plot related
  • Documentation is sphinx and numpydoc compliant
  • Added an entry to doc/users/next_whats_new/ if major new feature (follow instructions in README.rst there)
  • Documented in doc/api/api_changes.rst if API changed in a backward-incompatible way

Comment thread lib/matplotlib/backends/backend_pgf.py Outdated
for `'Creator'`, `'Producer'` and `'CreationDate'`. They
can be removed by setting them to `None`.
"""
self.outputfile = filename

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

all these attributes should be private unless you explicitly have a reason to make some public.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

sure

@anntzer

anntzer commented Feb 20, 2018

Copy link
Copy Markdown
Contributor

Would be nice to see how hard it is to implement a single MultiPage context for all relevant backends by adding the right methods to the RendererFoo classes. See e.g. https://github.com/anntzer/mplcairo/blob/master/lib/mplcairo/multipage.py as well.

But that may be too hard and a separate PR like this can work too.

@jkseppan

Copy link
Copy Markdown
Member

Yes, a generic multipage interface would be nice, but I wouldn't make it a requirement for this PR. Similarly, I wouldn't worry about implementing pdf metadata in the first version, just note in the documentation that it's not yet supported. The LaTeX hyperref package is probably the way to go for implementing that.

@jkseppan

Copy link
Copy Markdown
Member

We have tests that check that the output matches a baseline image. I think they currently exist only for the agg, pdf and svg backends, and I wouldn't really call them unit tests since they produce a complete output file and check the output. See https://github.com/matplotlib/matplotlib/tree/master/lib/matplotlib/testing for the infrastructure for the comparison tests. You could extend the pdf conversion to support multipage files, but that might get somewhat tricky.

Comment thread lib/matplotlib/backends/backend_pgf.py Outdated
'_file',
)

def __init__(self, filename, keep_empty=True, metadata=None):

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

probably arguments after filename can be made keyword only

"""
self._outputfile = filename
self._n_figures = 0
self.keep_empty = keep_empty

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

would make private too

Comment thread lib/matplotlib/backends/backend_pgf.py Outdated
Finalize this object, running LaTeX in a temporary directory
and moving the final pdf file to `filename`.
"""
self._file.write(r'\end{document}'.encode('utf-8') + b'\n')

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

just use a single literal bytestring

@maxnoe

maxnoe commented Feb 21, 2018

Copy link
Copy Markdown
Contributor Author

I implemented your comments and setting metadata using hyperref

@maxnoe maxnoe changed the title WIP: Implement PdfPages for backend pgf Implement PdfPages for backend pgf Feb 21, 2018
@maxnoe

maxnoe commented Feb 21, 2018

Copy link
Copy Markdown
Contributor Author

The Tests fail because the file I created in doc/users/next_whats_new is nowhere included. Where should it be included or what should I change?

@jkseppan

Copy link
Copy Markdown
Member

Add something like this: 2124ac8

@maxnoe

maxnoe commented Feb 21, 2018

Copy link
Copy Markdown
Contributor Author

Now the test fails because the lualatex version on travis is ancient. Any idea what to do about that? Edit the requires_lualatex decorator so it also checks for a version?

@jkseppan

Copy link
Copy Markdown
Member

Installing a newer TeX Live on Travis is a possibility but it sounds like it would really slow down the build. Does Appveyor have a sufficiently new luatex? If so, I think we could just check the version and skip the test if it is too old.

@maxnoe

maxnoe commented Feb 23, 2018

Copy link
Copy Markdown
Contributor Author

The failing Test Looks unrelated. Any idea what happened there? @jkseppan

@jkseppan

Copy link
Copy Markdown
Member

Yes, the failure looks unrelated. I restarted the test to see if it happens again.

@maxnoe

maxnoe commented Feb 23, 2018

Copy link
Copy Markdown
Contributor Author

@jkseppan Ok thanks. The tests are passing now.

Comment thread lib/matplotlib/backends/backend_pgf.py Outdated
return parse_lualatex_version(output.decode())


def parse_lualatex_version(output):

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

that probably doesn't need to be public

Comment thread lib/matplotlib/backends/backend_pgf.py Outdated
warnings.warn('error getting fonts from fc-list', UserWarning)


luatex_version_re = re.compile(

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

that definitely doesn't need to be public

Comment thread lib/matplotlib/backends/backend_pgf.py Outdated
return texsystem if texsystem in texsystem_options else "xelatex"


def get_lualatex_version():

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Note to other devs: would be nice to get #9571/#9639 merged first and integrate this version checking into that framework.

In the meantime, this function could(?) stay private.

@jkseppan

Copy link
Copy Markdown
Member

@maxnoe Just in case it's not obvious: I think what @anntzer means by public vs private is that the indicated functions and variables could be named starting with an underscore (_luatex_version_re, etc) so that users of Matplotlib don't come to depend on them directly.

@maxnoe

maxnoe commented Feb 24, 2018

Copy link
Copy Markdown
Contributor Author

@anntzer I made all the version functions/attributes private

@maxnoe

maxnoe commented Feb 27, 2018

Copy link
Copy Markdown
Contributor Author

@anntzer @jkseppan I resolved the conflicts

@maxnoe

maxnoe commented Feb 27, 2018

Copy link
Copy Markdown
Contributor Author

@anntzer @jkseppan The tests are passing again

latex_header = r"""\PassOptionsToPackage{{
{metadata}
}}{{hyperref}}
\RequirePackage{{hyperref}}

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

any reason why it's not a standard "usepackage[...]{hyperref}"? (perhaps, I dunno)

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Because People might use hyperref in their rc params latex header and like this it avoids the "hyperref loaded with incompatible options" error

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

so that's equivalent to "if hyperref is already loaded by the preamble, then merge these options with those passed in the preamble"? (again, just asking)

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yes, and the user specified options take precedence.

Comment thread lib/matplotlib/backends/backend_pgf.py Outdated
if self._n_figures == 0:
self._write_header(*figure.get_size_inches())
else:
if get_texcommand() == 'lualatex':

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

if get_texcommand == lualated and get_lualatex_version > ...?

Comment thread lib/matplotlib/backends/backend_pgf.py Outdated
np = r'\newpage\pdfpagewidth={}in\pdfpageheight={}in%'
self._file.write(np.format(
*figure.get_size_inches()
).encode('utf-8') + b'\n'

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

just include the newline in the format-string above?
here it may make sense to just use a bytes literal and %-interpolation

needs_pdflatex = pytest.mark.skipif(not check_for('pdflatex'),
reason='pdflatex + pgf is required')
needs_lualatex = pytest.mark.skipif(not check_for('lualatex'),
reason='lualatex + pgf is required')

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

indent

Comment thread tutorials/text/pgf.py
.. _pgf-rcfonts:


Multi-Page PDF Files

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

add entries to doc/api/howto_faq (which mentions the old pdfpages) and examples/misc/multipage_pdf?

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

done

@anntzer anntzer merged commit a2db882 into matplotlib:master Feb 28, 2018
@anntzer

anntzer commented Feb 28, 2018

Copy link
Copy Markdown
Contributor

Thanks for the PR!

@anntzer

anntzer commented Feb 28, 2018

Copy link
Copy Markdown
Contributor

@meeseeksdev backport to v3.0

@anntzer anntzer added this to the v3.0 milestone Feb 28, 2018
@maxnoe maxnoe deleted the pgf_pdf_pages branch February 28, 2018 09:11
@lumberbot-app

lumberbot-app Bot commented Feb 28, 2018

Copy link
Copy Markdown

Something went wrong ... Please have a look at my logs.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants