Description
Hi, this is my first Github post so please bear with me. I'm using Plotly v2.7.0 in Python 3.6.5.
I am trying to display text around certain 3D points and position the text based on the points' positions. Basically, I want the text to always display on the outside to improve readability. To see the expected behavior in 2D, check out out the first screenshot below or the corresponding HTML doc in the zip folder.
There are two bugs (I believe, anyway) that I've found:
- An array of
textposition
strings has no effect on the placement of the text. See the second screenshot. - Setting
textposition
for individual traces will work only for certain alignment strings. See the third screenshot.
Here is the working code to do this in 2d.
import plotly as py
import plotly.graph_objs as go
import numpy as np
# Create the data points.
n = 25
angles = np.linspace(0, 2 * np.pi, n)
xpts = np.array(n * [0])
ypts = np.cos(angles) / 2
zpts = np.sin(angles)
# Set the text for every 5th marker, the rest are blank.
texts = [""] * n
texts[::5] = ["Hello There"] * len(texts[::5])
# Set text alignment based on position of marker.
align_flags = ["middle right" if pt > 0 else "middle left" for pt in ypts]
# Create the 2D version. This works as expected.
dots2d = go.Scatter(x=ypts, y=zpts, text=texts,
mode="markers+text", textposition=align_flags)
# Make the figure.
fig = go.Figure(data=[dots_combined])
py.offline.plot(fig, filename="Figures/bug_report.html")
This produces the figure below. This is what we're after, with the text displayed on the outside of the circle.
Now, we will try to do the same in 3D. This is bug number 1 is the list above.
# Create the 3D version. The textposition argument has no effect.
dots3d = go.Scatter3d(x=xpts, y=ypts, z=zpts, text=texts,
mode="markers+text", textposition=align_flags)
# Make the figure.
fig = go.Figure(data=[dots3d])
py.offline.plot(fig, filename="Figures/bug_report.html")
The strings are all top center
instead of middle left
or middle right
:
Now, an ugly way to make the plot is to create each dot as an individual trace. This almost works. This is bug number 2.
# Create individual traces for every point. The textposition argument only works for left-aligned.
dots_individual = []
for ind in range(n):
dots_individual.append(
go.Scatter3d(x=[xpts[ind]], y=[ypts[ind]], z=[zpts[ind]], text=[texts[ind]],
mode="markers+text", textposition=align_flags[ind],
marker=dict(size=10, color="black"),
showlegend=False,
)
)
# Make the figure.
fig = go.Figure(data=dots_individual)
py.offline.plot(fig, filename="Figures/bug_report.html")
This produces the behavior below. The left-aligned text looks perfect, while the right-aligned text overlaps with the marker. Note: changing to textposition=[align_flags[ind]]
produces the same behavior as bug number 1.
Please let me know if I should include anything more, or if I've made any terrible Github transgressions! The Python file and figures are attached in the zip folder.
bug_report.zip