has2k1 / plotnine

A Grammar of Graphics for Python
https://plotnine.org
MIT License
3.99k stars 213 forks source link

Inconsistent ordering between legend and `geom_boxplot` when using `coord_flip` #815

Closed floringogianu closed 1 week ago

floringogianu commented 3 months ago

When flipping the coordinates of a boxplot the series are ordered from bottom to top in the figure and from top to bottom in the legend. When not flipping the axes the figure looks as expected.

df = pd.DataFrame({
    "y": np.random.randn(3, 2, 3).flatten(),
    "W": ["a", "b", "c"] * 3 * 2,
    "G": ["g1", "g2"] * 3 * 3
})

(
    p9.ggplot(df)
    + p9.geom_boxplot(p9.aes(x="factor(G)", y="y", color="W"))
    + p9.coord_flip()
)

image

has2k1 commented 2 months ago

The ordering of groups in the plot is from low coordinate value to high coordinate value, while that of the vertical legend is from top to bottom. coord_flip maintains this ordering in the plot and it also does not modify the legend.

It would look better in this case if it did modify the legend, but that would be unnecessary for some other geoms like geom_point. I don't think there is a way to do this well without too much complexity e.g. the positioning would depend on the coordinates.

The solution is to reverse the colour breaks.

import plotnine as p9
import numpy as np
import pandas as pd

df = pd.DataFrame({
    "y": np.random.randn(3, 2, 3).flatten(),
    "W": ["a", "b", "c"] * 3 * 2,
    "G": ["g1", "g2"] * 3 * 3,
})

(
    p9.ggplot(df)
    + p9.geom_boxplot(p9.aes(x="G", y="y", color="W"))
    + p9.coord_flip()
    + p9.scale_color_discrete(breaks=reversed)
)

coord-flip-reverse-legend