Skip to content

[Feature-Request] Add xshift/yshift to legend #3151

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

Closed
Braintelligence opened this issue Oct 25, 2018 · 14 comments
Closed

[Feature-Request] Add xshift/yshift to legend #3151

Braintelligence opened this issue Oct 25, 2018 · 14 comments
Labels
feature something new

Comments

@Braintelligence
Copy link

Hello everyone!
I'd wish for the legend to have xshift and yshift attributes, so I could position it more easily where I want it to be.

Currently I solved most of my positioning problems by using xshift/yshift with annotations and shapes but for some elements (for example "hacked" x axis titles via annotations) that are above where I want the legend to be I have huge problems of positioning for responsive layouts. (Especially with differing heights of the plot div when altering it for narrow displays.)

I can't tell how much work it would mean to implement this for the legend, but since other objects do have these attributes I hope it wouldn't create too much work. It would have an immense impact on how I could layout responsively, though, and would fix a myriad of problems that I have with layouting.

@alexcjohnson
Copy link
Collaborator

Makes sense, probably a fairly easy add. Feel like making a PR?? 😁

@alexcjohnson alexcjohnson added the feature something new label Oct 25, 2018
@Braintelligence
Copy link
Author

@alexcjohnson If cargo-culting away at the commit which added annotation xshift/yshift will do, I might take a shot in about 3-4 weeks. But I bet my code wouldn't be up to snuff regarding best practices :D

@etpinard
Copy link
Contributor

So legend.xshift and legend.yshift would be in pixels?

@Braintelligence
Copy link
Author

@etpinard correct

@Braintelligence
Copy link
Author

@alexcjohnson Would I have to create tests as well?

@alexcjohnson
Copy link
Collaborator

Would I have to create tests as well?

Someone would 😏 Most likely just an image test or two would suffice, and we can help, particularly if you can provide a figure JSON ({data, layout}) that shows the use of these shifts to suit your own use case.

@Braintelligence
Copy link
Author

Braintelligence commented Oct 26, 2018

As we're at it anyway: Would it be too hard to also include something like legend.rows where you can force the legend to distribute given legend items on so many rows?

Use-case: You set filtered legends invisible when downloading the PNG and if you have a lot of legend items in orientation = 'h' they will break into several rows. Now if you filter enough legend items it will reduce to one row but keep the positioning and thus a margin is created that messes up your layout because you don't want such a big margin to the following annotation elements.

An alternative way would be to somehow access something like legend.height that is a read-only attribute which you can access while layouting (is there something like a layout-hook?) or after layouting and relayout the positioning of everything that relies on the height/margin of the legend.
If you can force a number of rows you can emulate the legend height by knowing the font size and finding a magic number that you can multiply with legend rows combined with the legend margin itself.

EDIT: I currently have a legend with an approximate height of 160px due to a lot of <br> and a lot of legend items and not a huge amount of width. Filtering out enough traces, so that only one row of legend items remains, creates a huge margin 🙈. Knowing the legend height on draw would relieve me of this problem 😿.

@Braintelligence
Copy link
Author

Braintelligence commented Oct 29, 2018

So basically I found a workaround for my use-case by checking out fullDataLayout on a new plot. I created an invisible plot off the visible area and draw my stuff on there; I take the legend._height and only then draw the image that shall be downloaded.

I'm not in need of this feature anymore, so you may close it if you want or keep it for someone to work on 😸.

EDIT: Being able to predict the top margin of the legend (EDIT2: By positioning through yshift instead of adjusting the legend.y) is still somewhat desirable... Also drawing a plot just for the sake of getting the legend height is really demanding for the client. Will try to take a shot at xshift/yshift for legend in a few weeks; maybe one of you guys has an idea for an efficient way of calculating the legend height?
@alexcjohnson Any hints on how we could expose a Plotly function that calculates a legend height for a given plot width and data? Could you pinpoint me to the exact scope of code that calculates the legend dimensions? 😿

@brian428
Copy link

I think this would also address #1594, at least partially. It'll still probably require manually increasing the margin and then applying the shift to the legend, but at least it would provide some options for dealing with legend/axis overlaps.

@Braintelligence
Copy link
Author

Braintelligence commented Jan 22, 2019

Just a quick question/addition: Is it possible to xshift/yshift shapes? And if not: could we also add this? 😹

EDIT: To give a use-case: I want to display a horizontal line (shape line with width: 1 and y0=y1 and x0: 0 and x1: 0.9 with xref: "paper") and have an annotation at the end of it (x: 0.9 y: y0 and align: "left"). With fixed plot sizes that's not a problem but when you are able to achieve responsiveness you have vastly different results when using paper as ref due to variable plot width.
If I could use xshift, I could just offset the line shape by the same amount of pixels that I'd offset the annotation from the right end of the plot (shape x1: 1 with xshift: -20 and same with the annotation).

I guess I'll have to try and use x as xref instead now :D.

EDIT2: Actually xref: "x" doesn't help... the bars in my plot have varying width to which the annotation text size isn't adapting resulting in almost the same problem 😹

@Braintelligence
Copy link
Author

Hello everyone, is there any progress on this? 😸

@Braintelligence
Copy link
Author

Braintelligence commented Jul 9, 2019

I don't know if it was a shift in versions but legend._height returns wrong heights for me in some cases which results in broken code functionality for me now 😢 . It basically says that the legend has less height than is actually displayed.

This seems to be another problem with usage of <br> tags as far as I can tell. If I remove all <br> tags from trace names I can't reproduce it anymore.

EDIT: Nevermind, I had a bug in my margin calculation. Fixed it ^^.

@jackparmer
Copy link
Contributor

This issue has been tagged with NEEDS SPON$OR

A community PR for this feature would certainly be welcome, but our experience is deeper features like this are difficult to complete without the Plotly maintainers leading the effort.

Sponsorship range: $5k-$10k

What Sponsorship includes:

  • Completion of this feature to the Sponsor's satisfaction, in a manner coherent with the rest of the Plotly.js library and API
  • Tests for this feature
  • Long-term support (continued support of this feature in the latest version of Plotly.js)
  • Documentation at plotly.com/javascript
  • Possibility of integrating this feature with Plotly Graphing Libraries (Python, R, F#, Julia, MATLAB, etc)
  • Possibility of integrating this feature with Dash
  • Feature announcement on community.plotly.com with shout out to Sponsor (or can remain anonymous)
  • Gratification of advancing the world's most downloaded, interactive scientific graphing libraries (>50M downloads across supported languages)

Please include the link to this issue when contacting us to discuss.

@gvwilson
Copy link
Contributor

Hi - this issue has been sitting for a while, so as part of our effort to tidy up our public repositories I'm going to close it. If it's still a concern, we'd be grateful if you could open a new issue (with a short reproducible example if appropriate) so that we can add it to our stack. Cheers - @gvwilson

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
feature something new
Projects
None yet
Development

No branches or pull requests

6 participants