1

I am trying to plot a set of data as stacked x bars, using pgfplots.

My current problem is that since some of the segments are rather short, I don't know how to move only some of them in such way that they won't overlap.

Does anyone have a hint on how to solve the problem?

Hereafter I provide a MWE:

\documentclass{standalone}

\usepackage{pgfplots}
\usepackage{pgfplotstable}
\usepackage{filecontents}

\begin{filecontents*}{example.csv}
    Name,PEMFC,SOFC,PV,ElHeater,HeatPump,Boiler
    Power,0.244461026,0.554685519,0.200853455,0,0,0
    Heat,0.020609747,0.118257196,0,0.019495035,0.78497376,0.056664262
    Fuel,0,0.906053389,0,0,0,0.093946611
\end{filecontents*}

\pgfplotstableread\[col sep=comma\]{example.csv}\datatable
\makeatletter
\pgfplotsset{
    compat = 1.9,
    /pgfplots/flexible yticklabels from table/.code n args={3}{%
        \pgfplotstableread\[#3\]{#1}\coordinate@table
        \pgfplotstablegetcolumn{#2}\of{\coordinate@table}\to\pgfplots@yticklabels
        \let\pgfplots@yticklabel=\pgfplots@user@ticklabel@list@y
    }
}
\makeatother

\pgfplotsset{
    x axis style/.style={
        xticklabel style=#1,
        xlabel style=#1,
        x axis line style=#1,
        xtick style=#1
    }
}

\begin{document}
    \begin{tikzpicture}
    % Part of the figure plotting the size bars
    \begin{axis}\[
    xbar stacked, xmin=0, xmax=1,
    % bar width=0.6cm,
    width=15cm, height=5cm,
    xlabel={Energy Share},
    flexible yticklabels from table={example.csv}{Name}{col sep=comma},
    yticklabel style={text height=1.5ex}, % To make sure the text labels are nicely aligned
    ytick=data,
    nodes near coords,
    nodes near coords align={horizontal},
    nodes near coords style={xshift=-14pt, yshift=15pt, /pgf/number format/.cd, precision=2, fixed},
    xtick pos=bottom,ytick pos=left,
    legend style={
        area legend,
        at={(0.5,-0.5)},
        anchor=north,
        legend columns=3}
    \]
    \addplot table\[y expr=\coordindex,x=PEMFC\]{\datatable};
    \addplot table\[y expr=\coordindex,x=SOFC\]{\datatable};
    \addplot table\[y expr=\coordindex,x=PV\]{\datatable};
    \addplot table\[y expr=\coordindex,x=HeatPump\]{\datatable};
    \addplot table\[y expr=\coordindex,x=Boiler\]{\datatable};
    \addplot table\[y expr=\coordindex,x=ElHeater\]{\datatable};


    \legend{PEMFC, SOFC, Heat pump, Boiler, PV, El. heater} 
    \end{axis}



    \end{tikzpicture}
\end{document}

How it looks like right now

1 Answers1

2

Very similar to Stefan Pinnow's nice answer except that here the anchors also get adjusted depending on the position.

\documentclass{standalone}

\usepackage{pgfplots}
\usepackage{pgfplotstable}
\usepackage{filecontents}

\begin{filecontents*}{example.csv}
    Name,PEMFC,SOFC,PV,ElHeater,HeatPump,Boiler
    Power,0.244461026,0.554685519,0.200853455,0,0,0
    Heat,0.020609747,0.118257196,0,0.019495035,0.78497376,0.056664262
    Fuel,0,0.906053389,0,0,0,0.093946611
\end{filecontents*}

\pgfplotstableread[col sep=comma]{example.csv}\datatable
\makeatletter
\pgfplotsset{
    compat = 1.16, %<-changed
    /pgfplots/flexible yticklabels from table/.code n args={3}{%
        \pgfplotstableread[#3]{#1}\coordinate@table
        \pgfplotstablegetcolumn{#2}\of{\coordinate@table}\to\pgfplots@yticklabels
        \let\pgfplots@yticklabel=\pgfplots@user@ticklabel@list@y
    }
}
\makeatother

\pgfplotsset{
    x axis style/.style={
        xticklabel style=#1,
        xlabel style=#1,
        x axis line style=#1,
        xtick style=#1
    }
}

\begin{document}
    \begin{tikzpicture}
    % Part of the figure plotting the size bars
    \begin{axis}[
    xbar stacked, xmin=0, xmax=1,
    % bar width=0.6cm,
    width=15cm, height=5cm,
    xlabel={Energy Share},
    flexible yticklabels from table={example.csv}{Name}{col sep=comma},
    yticklabel style={text height=1.5ex}, % To make sure the text labels are nicely aligned
    ytick=data,
    visualization depends on={
                ifthenelse(meta>0.05,7pt,14pt) \as \myshift
            },
    visualization depends on={
                -135+90*x \as \myanchor
    },          
    nodes near coords,
    nodes near coords align={horizontal},
    nodes near coords style={%xshift=-14pt, yshift=15pt, 
    anchor=\myanchor,yshift=\myshift,
    /pgf/number format/.cd, precision=2, fixed},
    xtick pos=bottom,ytick pos=left,
    legend style={
        area legend,
        at={(0.5,-0.5)},
        anchor=north,
        legend columns=3}
    ]
    \addplot table[y expr=\coordindex,x=PEMFC]{\datatable};
    \addplot table[y expr=\coordindex,x=SOFC]{\datatable};
    \addplot table[y expr=\coordindex,x=PV]{\datatable};
    \addplot table[y expr=\coordindex,x=HeatPump]{\datatable};
    \addplot table[y expr=\coordindex,x=Boiler]{\datatable};
    \addplot table[y expr=\coordindex,x=ElHeater]{\datatable};


    \legend{PEMFC, SOFC, Heat pump, Boiler, PV, El. heater} 
    \end{axis}



    \end{tikzpicture}
\end{document}

enter image description here

  • Nice! Both this and the answer from Stefan Pinnow definitely do the trick!

    Thanks for the help, I had not seen the post that Stefan redirected me to. My bad!

    – Francesco Baldi Aug 02 '18 at 06:14
  • @FrancescoBaldi If the answer solved your problem, would you mind accepting it? One can accept answers by clicking on the check mark left of it. –  Aug 02 '18 at 11:54