1

Is it possible to put data labels (values) in pandas/matplotlib stacked area charts?

In stacked bar plots, I use the below

for label in yrplot.patches:
    yrplot.annotate(label.get_height(), (label.get_x()+label.get_width()/2.,label.get_y()+label.get_height()/2.),
                 ha='center', va='center', xytext=(0, 1), 
                 textcoords='offset points')

Below is how I am plotting the stacked area chart

%matplotlib inline
import matplotlib.pyplot as plt
import seaborn as sns

yrplot = yrly_perc_df.plot(x='year', y=prod, kind='area', stacked=True, figsize=(15,10), color = areacolors)

yrplot.set_ylabel('share')
yrplot.legend(loc='center left', bbox_to_anchor=(1.0,0.5))

Snippet of the stacked area chart for percentage share plotted using above code

Any leads would be much appreciated. To state my want, it is something similar to this image but in a stacked area chart (data labels along the plot, similar to the first code in the question).

samkart
  • 6,007
  • 2
  • 14
  • 29
  • What is your desired output? – Sheldore Aug 05 '18 at 17:16
  • I want the yearly percentage values on the chart, like in bar charts' annotate. Is it possible in area charts? – samkart Aug 05 '18 at 17:19
  • 1
    Does this serve your needs? https://stackoverflow.com/questions/31573869/label-areas-in-python-matplotlib-stackplot – Sheldore Aug 05 '18 at 17:21
  • @Bazingaa No, this is not what I actually want. My want is something similar to [this](https://drive.google.com/file/d/1ejMG1DCvEsBOIyMdXvcwV_3hukqbbynQ/view?usp=sharing) but in a stacked area chart. – samkart Aug 05 '18 at 17:28
  • 1
    Link not working. Also you should try to post in the first place what you want so as to have more chances of getting an answer. – Sheldore Aug 05 '18 at 17:29
  • The title of you question should not say 'area plot' then. What you want is a bar plot. – Sheldore Aug 05 '18 at 17:31
  • @Bazingaa I want something similar to that. but in a stacked area chart, not a bar chart. I can do that in a stacked bar chart, but need help to do the same in a stacked area chart – samkart Aug 05 '18 at 17:32
  • 1
    @samkart you should really include your desired result in your question. I'm not opening your google documents! Also: Minimum working example? – Dux Aug 05 '18 at 17:46
  • Doesn't that make the questions long to read. Also, my want is to get the yearly data labels (%age values) for each 'prod' on the chart. The one I tried to do is there in my question. That's how I started my question. – samkart Aug 05 '18 at 17:49

1 Answers1

3

The annotations can be manually added to the stacked area chart, using the cumulative sum of the values to compute the y positions of the labels. Also, I suggest not to draw the annotation if the height of the stack is very small.

rs = np.random.RandomState(12)
values = np.abs(rs.randn(12, 4).cumsum(axis=0))
dates = pd.date_range("1 1 2016", periods=12, freq="M")
data = pd.DataFrame(values, dates, columns=["A", "B", "C", "D"])
ax = data.plot(kind='area', stacked=True)
ax.set_ylabel('value')
ax.legend(loc='center left', bbox_to_anchor=(1.0,0.5))

for x1 in data.index:
    # Y positions are given by the cumulative sum of the values, plus half of the height of the specific stack
    yCenteredS = data.loc[x1].cumsum()
    yCenteredS = [0.0] + yCenteredS.tolist()
    yCenteredS = [y + (yCenteredS[i+1] - y)/2. for i, y in enumerate(yCenteredS[:-1])]
    # Draw the values as annotations
    labels = pd.DataFrame(data={'y':yCenteredS, 'value':data.loc[x1].tolist()})
    # Don't draw the annotation if the stack is too small
    labels = labels[labels['value'] > 0.5]

    for _, y, value in labels.itertuples():
        ax.annotate('{:.2f}'.format(value), xy=(x1, y), ha='center', va='center',
                    bbox=dict(fc='white', ec='none', alpha=0.2, pad=1),
                    fontweight='heavy', fontsize='small')

enter image description here

fokkerplanck
  • 966
  • 6
  • 6