Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

PGF backend: Fix vertical positioning of multi-line text #3003

Closed
wants to merge 1 commit into from

Conversation

adamreeve
Copy link

This addresses issue #3000. The horizontal aligment is maintained, but for multi-line text the vertical alignment is applied manually in a similar way to the SVG backend.

@adamreeve
Copy link
Author

Thanks, I don't think the label appearing outside the figure is specific to the pgf backend with this patch though, I get the same thing with other backends. You can use figure.tight_layout() to make sure everything fits in nicely.

@tacaswell tacaswell added this to the v1.4.0 milestone Apr 27, 2014
@tacaswell
Copy link
Member

@pwuertz Can you review this?

@tacaswell
Copy link
Member

@adamreeve Can you add an entry to CHANGELOG?

Because text is drawn line-by-line, the anchor point of the text object
being drawn is not applicable to all lines.
When multi-line text is detected, apply the vertical alignment to the
anchor manually using the requested x and y positions.
This is based on the code in RendererSVG._draw_text_as_text.
@adamreeve
Copy link
Author

Hi @tacaswell, I added the CHANGELOG entry and rebased to avoid a merge.

@pwuertz
Copy link
Contributor

pwuertz commented Apr 28, 2014

Code looks very good to me, although I think it is the function calling the backend's draw_text() method that needs to be fixed. The problem originates from the fact that the mtext instances given to the backend are completely wrong. At some point matplotlib splits up lines, calculates the vertical positions and calls draw_text multiple times, where it should provide individual, correct mtext instances for all lines.

@pwuertz pwuertz closed this Apr 28, 2014
@pwuertz pwuertz reopened this Apr 28, 2014
@adamreeve
Copy link
Author

Yeah, I had a quick look and Text._get_layout in lib/matplotlib/text.py is where the text is split into multiple lines. These lines are then used by Text.draw which calls the renderer for each line and passes the Text object in as the mtext parameter.

An alternative approach could be to let the renderer say that it can handle multi-line text, then let it split the lines up itself and position them using the mtext info or just draw all the text with something like a parbox as you mentioned in #3000.

@pwuertz
Copy link
Contributor

pwuertz commented Apr 28, 2014

Here is the quick fix that omits mtext in cases where it isn't valid (#3017).

@adamreeve Thats right, it is probably much cleaner to move the _get_layout code to the base backend since it depends on the renderer anyway and allow backend subclasses to handle multiple lines for themselves if necessary, like using parbox for latex. Unfortunately I don't think it is possible to do that reliably in latex for the reasons I mentioned in #3000.

@adamreeve
Copy link
Author

Ok thanks, I'll close this PR then. Right, that makes sense, so providing correct mtext instances for the separate lines would be the most useful for the PGF backend.

@adamreeve adamreeve closed this Apr 28, 2014
@pwuertz
Copy link
Contributor

pwuertz commented Apr 28, 2014

Thanks for your work and thoughts on this.

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.

None yet

4 participants