Reputation: 298
I have a scatter plot with two or more different data sets. For each data set I also added a hline of their means. I would like to link the hline to the legend of the corresponding dataset so that if I deselect a dataset in the legend, the hline disappears as well.
Is this possible in plotly?
import pandas as pd
import plotly.graph_objects as go
df = pd.DataFrame({'x': [0, 1, 2],
'y1': [5, 4, 7],
'y2': [2, 3, 1]})
fig = go.Figure()
fig.add_trace(go.Scatter(
x=df['x'],
y=df['y1'],
mode='markers',
name='y1'
))
fig.add_trace(go.Scatter(
x=df['x'],
y=df['y2'],
mode='markers',
name='y2'
))
fig.add_hline(y=df['y1'].mean())
fig.add_hline(y=df['y2'].mean())
fig.show()
Upvotes: 1
Views: 2339
Reputation: 1483
A workaround is that: For each horizontal/vertical line, draw a Scatter line with the same color and visible="legendonly"
.
It's worth noting that lines with visible="legendonly"
show in the legend with half alpha. So for correspondence, you'd better use alpha 0.5 to draw the horizontal/vertical lines and use alpha 1.0 to draw the invisible lines.
import pandas as pd
import plotly.graph_objects as go
import plotly.express as px
COLORS = px.colors.qualitative.Plotly
def hex_to_rgba(h, alpha):
"""
converts color value in hex format to rgba format with alpha transparency
"""
return tuple([int(h.lstrip("#")[i : i + 2], 16) for i in (0, 2, 4)] + [alpha])
df = pd.DataFrame({"x": [0, 1, 2], "y1": [5, 4, 7], "y2": [2, 3, 1]})
fig = go.Figure()
fig.add_trace(go.Scatter(x=df["x"], y=df["y1"], mode="markers", name="y1"))
fig.add_trace(go.Scatter(x=df["x"], y=df["y2"], mode="markers", name="y2"))
fig.add_hline(
y=df["y1"].mean(),
line={
"color": "rgba" + str(hex_to_rgba(h=COLORS[0], alpha=0.5)),
},
)
fig.add_trace(
go.Scatter(
x=df["x"],
y=df["y2"],
mode="lines",
visible="legendonly",
name="y1 mean",
line={
"color": COLORS[0],
},
)
)
fig.add_hline(
y=df["y2"].mean(),
line={
"color": "rgba" + str(hex_to_rgba(h=COLORS[1], alpha=0.5)),
},
)
fig.add_trace(
go.Scatter(
x=df["x"],
y=df["y2"],
mode="lines",
visible="legendonly",
name="y2 mean",
line={
"color": COLORS[1],
},
)
)
fig.show()
Upvotes: 0
Reputation: 35205
First, it must be graphically supported to be reflected in the legend. So we draw a line using the line mode of the scatter plot. Then, set up a legend group to group the scatter and line graphs. Once this is done, you can show or hide the legend by clicking on it.
The second image is an example of the y2 legend clicked to hide it.
import pandas as pd
import plotly.graph_objects as go
df = pd.DataFrame({'x': [0, 1, 2],
'y1': [5, 4, 7],
'y2': [2, 3, 1]})
fig = go.Figure()
fig.add_trace(go.Scatter(
x=df['x'],
y=df['y1'],
mode='markers',
name='y1',
legendgroup='1'
))
fig.add_trace(go.Scatter(
x=df['x'],
y=df['y2'],
mode='markers',
name='y2',
legendgroup='2'
))
fig.add_trace(
go.Scatter(
mode='lines',
x=df['x'],
y=[df['y1'].mean()]*len(df),
line_color='blue',
legendgroup='1'
)
)
fig.add_trace(
go.Scatter(
mode='lines',
x=df['x'],
y=[df['y2'].mean()]*len(df),
line_color='red',
legendgroup='2'
)
)
fig.show()
Upvotes: 1