offsetgroup with horizontally stacked/relative bar traces
It appears the feature to allow offsetgroup to work with stacked/relative bar traces (https://github.com/plotly/plotly.js/pull/7009) does not work with horizontally oriented bar traces. Taking the example from the documentation
https://plotly.com/python/bar-charts/#grouped-stacked-bar-chart
if I reverse the x and y axis and set orientation to 'h', the traces are not separated by the different offset groups:
import plotly.graph_objects as go
data = [
go.Bar(
y=['Q1', 'Q2', 'Q3', 'Q4'],
x=[150, 200, 250, 300],
name='New York',
offsetgroup="USA",
orientation='h'
),
go.Bar(
y=['Q1', 'Q2', 'Q3', 'Q4'],
x=[180, 220, 270, 320],
name='Boston',
offsetgroup="USA",
orientation='h'
),
go.Bar(
y=['Q1', 'Q2', 'Q3', 'Q4'],
x=[130, 170, 210, 260],
name='Montreal',
offsetgroup="Canada",
orientation='h'
),
go.Bar(
y=['Q1', 'Q2', 'Q3', 'Q4'],
x=[160, 210, 260, 310],
name='Toronto',
offsetgroup="Canada",
orientation='h'
)
]
layout = go.Layout(
title={
'text': 'Quarterly Sales by City, Grouped by Country'
},
yaxis={
'title': {
'text': 'Quarter'
}
},
xaxis={
'title': {
'text': 'Sales'
}
},
barmode='stack'
)
fig = go.Figure(data=data, layout=layout)
fig.show()
Using plotly 6.0.0.
Thanks for the report @neutralino - I'll see if we can find someone to work on this in the next cycle. If not, we can prioritize a pull request if you or someone else is able to put one together. Thanks - @gvwilson
Interestingly, this seems to only be the case for plotly.py, in plotly.js it works fine:
https://codepen.io/toffi-fee/pen/ByBgbyX
nice catch @my-tien - I'll see if we can find someone to dig into it in the next cycle.
@gvwilson I am quite curious why there is a difference in behaviour, so I'm also digging into it a bit.
@neutralino Just to make sure: Where did you try this code? Because the corresponding renderer extension in VSCode isn't yet upgraded to plotly.js 3.0.0 see here. But that means that neither rotation should display correctly in VSCode. But if you avoid the VSCode renderer by e.g. picking another renderer or saving the image to png, it looks correct for me:
# try another renderer
fig.show("browser")
# save to png
with open("mytest.png", "wb") as f:
f.write(pio.to_image(fig))
Ah I see, thanks @my-tien! Yes, I was trying it from both VSCode and PyCharm's notebook integration. Using the browser as the renderer works for me as well.
I have the same issue, but in the Jupyter environment. I tried plotly 6.0.0 and following Jupyter setup:
jupyter --version
IPython : 8.28.0
ipykernel : 6.29.5
ipywidgets : 8.1.5
jupyter_client : 8.6.3
jupyter_core : 5.7.2
jupyter_server : 2.14.2
jupyterlab : 4.2.5
nbclient : 0.10.0
nbconvert : 7.16.4
nbformat : 5.10.4
notebook : 7.2.2
qtconsole : not installed
traitlets : 5.14.3
When I used code from the docs https://plotly.com/python/bar-charts/#grouped-stacked-bar-chart, I got bar charts without grouping by offsetgroup.
Hi @pendyurinandrey the issue isn't with the plotly.py version but with the plotly.js dependency that the vscode-notebook-renderer uses. It is still at 2.35.2. The new feature was introduced in plotly.js 3.0.0 and plotly.py uses plotly.js under the hood for rendering: https://github.com/microsoft/vscode-notebook-renderers/blob/0ef2be324acaf56a505db81701da6bea4e727ebd/package.json#L168
Related problem - the scatter plot cannot use the offset group of the bar plot when bar plot is horizontal. The Grouped Bar and Scatter Chart example when modified as below to use horizontal layout doesn't work anymore. This doesn't work even using browser renderer.
import plotly.graph_objects as go
from plotly import data
df = data.tips()[data.tips()["day"] == "Sun"]
mean_values_df = df.groupby(by=["sex", "smoker"], as_index=False).mean(
numeric_only=True
)
smoker_mean = mean_values_df[mean_values_df.smoker == "Yes"].sort_values(
by="tip", ascending=False
)
non_smoker_mean = mean_values_df[mean_values_df.smoker == "No"].sort_values(
by="tip", ascending=False
)
smoker = df[df.smoker == "Yes"].sort_values(by="tip", ascending=False)
non_smoker = df[df.smoker == "No"].sort_values(by="tip", ascending=False)
fig = go.Figure(
layout=dict(
yaxis=dict(categoryorder="category descending"),
xaxis=dict(range=[0, 7]),
scattermode="group",
legend=dict(groupclick="toggleitem"),
)
)
fig.add_trace(
go.Bar(
y=smoker_mean.sex,
x=smoker_mean.tip,
name="Average",
marker_color="IndianRed",
offsetgroup="smoker",
legendgroup="smoker",
legendgrouptitle_text="Smoker",
orientation="h"
)
)
fig.add_trace(
go.Scatter(
y=smoker.sex,
x=smoker.tip,
mode="markers",
name="Individual tips",
marker=dict(color="LightSlateGrey", size=5),
offsetgroup="smoker",
legendgroup="smoker",
)
)
fig.add_trace(
go.Bar(
y=non_smoker_mean.sex,
x=non_smoker_mean.tip,
name="Average",
marker_color="LightSalmon",
offsetgroup="non-smoker",
legendgroup="non-smoker",
legendgrouptitle_text="Non-Smoker",
orientation="h"
)
)
fig.add_trace(
go.Scatter(
y=non_smoker.sex,
x=non_smoker.tip,
mode="markers",
name="Individual tips",
marker=dict(color="LightSteelBlue", size=5),
offsetgroup="non-smoker",
legendgroup="non-smoker",
)
)
fig.show()