3

I am trying to sort components of a stacked bar chart individually for better readability (either in the DataFrame itself) or once the chart is graphed and I cannot figure out if there is a good way to do this.

For example, I have this dictionary of players & the time spent against their opponents -

so_oppo_dict = {
  'Player 1': {'Opponent 1': 2.15, 'Opponent 2': 3.5333, 'Opponent 3': 3.1}, 
  'Player 2': {'Opponent 1': 2.2167, 'Opponent 2': 1.8667, 'Opponent 3': 2.3333}, 
  'Player 3': {'Opponent 1': 1.5333, 'Opponent 2': 4.3833, 'Opponent 3': 4.15}
}

I then graph it using the following code to turn it into a stacked bar chart -

fig, ax = plt.subplots()
ax = plt.subplot(111)
so_oppo_df.T.plot(kind="barh", stacked=True, ax=ax)
fig.tight_layout()
fig.savefig('opponents-stacked.png')

My resulting graph looks like this and each component of the stacked bar graph is sorted in the same order. What I would like to do is rearrange the the componets of the bars to sort by highest to lowest (so the green and orange bars would come before the blue bars) - is this possible to do?

enter image description here

mattdonders
  • 1,328
  • 1
  • 19
  • 42

1 Answers1

0

Based on this phenomenal answer I was able to produce exactly what was needed. Here is the code snippet that I finalized below & the resulting image (with a much larger dictionary).

x = so_oppo_df.index
indexes = np.argsort(so_oppo_df.values).T
widths = np.sort(so_oppo_df.values).T
order = -1
lefts = widths[::order].cumsum(axis=0)
lefts = np.insert(lefts, 0, np.zeros(len(lefts[0])), axis=0)

mpp_colors = dict(zip(so_oppo_df.columns, plt.cm.get_cmap("tab20c").colors))

for k, (idxs, vals) in enumerate(list(zip(indexes, widths))[::order]):
    mps = np.take(np.array(so_oppo_df.columns), idxs)
    ax1.barh(x, width=vals, left=lefts[k], color=[mpp_colors[m] for m in mps])

ax1.legend((np.take(np.array(so_oppo_df.columns), np.argsort(so_oppo_df.values)[0]))[::-1], bbox_to_anchor=(1.05, 1), loc='upper left', ncol=1)
ax1.title.set_text(f"Team Opposition - 5v5 Sorted TOI")

Horizontal Bar Chart (Sorted by Individual Values)

mattdonders
  • 1,328
  • 1
  • 19
  • 42