有没有办法使用 groupplots 对饼图进行分组?我想要类似这样的效果:
以下是 MWE:
\documentclass[times]{article}
\usepackage{pgfplots, pgfplotstable}
\usepackage{tikz}
\usepgfplotslibrary{groupplots}
\begin{document}
\newcommand{\legend}[2][]{
\begin{scope}[#1]
\path
\foreach \n/\s in {#2}
{
++(0,-10pt) node[\s,legend box] {} +(5pt,0) node[legend label] {\n}
}
;
\end{scope}
}
\tikzstyle{chart}=[
legend label/.style={font={\scriptsize},anchor=west,align=left},
legend box/.style={rectangle, draw, minimum size=5pt},
axis/.style={black,semithick,->},
axis label/.style={anchor=east,font={\tiny}},
]
\tikzstyle{pie chart}=[
chart,
slice/.style={line cap=round, line join=round, very thick,draw=white},
pie title/.style={font={\bf}},
slice type/.style 2 args={
##1/.style={fill=##2},
values of ##1/.style={}
}
]
\pgfdeclarelayer{background}
\pgfdeclarelayer{foreground}
\pgfsetlayers{background,main,foreground}
\newcommand{\pie}[3][]{
\begin{scope}[#1]
\pgfmathsetmacro{\curA}{90}
\pgfmathsetmacro{\r}{1}
\def\c{(0,0)}
\node[pie title] at (90:1.3) {#2};
\foreach \v/\s in{#3}{
\pgfmathsetmacro{\deltaA}{\v/100*360}
\pgfmathsetmacro{\nextA}{\curA + \deltaA}
\pgfmathsetmacro{\midA}{(\curA+\nextA)/2}
\path[slice,\s] \c
-- +(\curA:\r)
arc (\curA:\nextA:\r)
-- cycle;
\pgfmathsetmacro{\d}{max((\deltaA * -(.4/50) + 1) , .5)}
\begin{pgfonlayer}{foreground}
\path \c -- node[pos=\d,pie values,values of \s]{$\v\%$} +(\midA:\r);
\end{pgfonlayer}
\global\let\curA\nextA
}
\end{scope}
}
\begin{figure}
\begin{tikzpicture}
[
pie chart,
slice type={inlined}{lightgray},
slice type={noninlined}{darkgray},
pie values/.style={font={\tiny}},
scale=1
]
\pie{\footnotesize{benchmark}}{41/inlined,13/noninlined}
\legend[shift={(-1cm,-1cm)}]{{Inlined}/inlined, {Not inlined}/noninlined}
\end{tikzpicture}
\end{figure}
\end{document}
答案1
要放置饼图,您可以使用\subcaptionbox
(来自subcaption
包);可以借助新命令 来缩短饼图包含的代码;使用a 中的\putpie
两个s ,您可以将图例放置在所需的位置:minipage
\makebox
\documentclass{article}
\usepackage{pgfplots, pgfplotstable}
\usepackage{subcaption}
\usepgfplotslibrary{groupplots}
\pgfplotsset{compat=newest}
\newcommand{\legend}[2][]{
\begin{scope}[#1]
\path
\foreach \n/\s in {#2}
{
++(0,-10pt) node[\s,legend box] {} +(5pt,0) node[legend label] {\n}
}
;
\end{scope}
}
\tikzset{
chart/.style={
legend label/.style={font={\scriptsize},anchor=west,align=left},
legend box/.style={rectangle, draw, minimum size=5pt},
axis/.style={black,semithick,->},
axis label/.style={anchor=east,font={\tiny}},
},
pie chart/.style={
chart,
slice/.style={line cap=round, line join=round, very thick,draw=white},
pie title/.style={font={\bfseries}},
slice type/.style 2 args={
##1/.style={fill=##2},
values of ##1/.style={}
}
}
}
\pgfdeclarelayer{background}
\pgfdeclarelayer{foreground}
\pgfsetlayers{background,main,foreground}
\newcommand{\pie}[3][]{
\begin{scope}[#1]
\pgfmathsetmacro{\curA}{90}
\pgfmathsetmacro{\r}{1}
\def\c{(0,0)}
\node[pie title] at (90:1.3) {#2};
\foreach \v/\s in{#3}{
\pgfmathsetmacro{\deltaA}{\v/100*360}
\pgfmathsetmacro{\nextA}{\curA + \deltaA}
\pgfmathsetmacro{\midA}{(\curA+\nextA)/2}
\path[slice,\s] \c
-- +(\curA:\r)
arc (\curA:\nextA:\r)
-- cycle;
\pgfmathsetmacro{\d}{max((\deltaA * -(.4/50) + 1) , .5)}
\begin{pgfonlayer}{foreground}
\path \c -- node[pos=\d,pie values,values of \s]{$\v\%$} +(\midA:\r);
\end{pgfonlayer}
\global\let\curA\nextA
}
\end{scope}
}
\newcommand\putpie[1]{%
\subcaptionbox{}{%
\begin{tikzpicture}
#1
\end{tikzpicture}}%
}
\begin{document}
\begin{figure}
\tikzset{every picture/.style={
pie chart,
slice type={inlined}{lightgray},
slice type={noninlined}{darkgray},
pie values/.style={font={\tiny}},
scale=1
}
}
\pgfplotsset{legend style={
anchor=north,
legend columns=2,
cells={anchor=west},
font=\footnotesize,
rounded corners=2pt,
},
}
\captionsetup[subfigure]{labelformat=empty}% to suppress the labels from captions
\makebox[\linewidth][l]{%
\begin{minipage}{\linewidth}
\centering
\putpie{\pie{{\footnotesize benchmark}}{41/inlined,13/noninlined}}\hfill
\putpie{\pie{{\footnotesize benchmark}}{41/inlined,13/noninlined}}\hfill
\putpie{\pie{{\footnotesize benchmark}}{41/inlined,13/noninlined}}\hfill
\putpie{\pie{{\footnotesize benchmark}}{41/inlined,13/noninlined}}\hfill
\putpie{\pie{{\footnotesize benchmark}}{41/inlined,13/noninlined}}\\
\putpie{\pie{{\footnotesize benchmark}}{41/inlined,13/noninlined}}\hfill
\putpie{\pie{{\footnotesize benchmark}}{41/inlined,13/noninlined}}\hfill
\putpie{\pie{{\footnotesize benchmark}}{41/inlined,13/noninlined}}\hfill
\putpie{\pie{{\footnotesize benchmark}}{41/inlined,13/noninlined}}\hfill
\putpie{\pie{{\footnotesize benchmark}}{41/inlined,13/noninlined}}\\
\putpie{\pie{{\footnotesize benchmark}}{41/inlined,13/noninlined}}\hfill
\putpie{\pie{{\footnotesize benchmark}}{41/inlined,13/noninlined}}\hfill
\putpie{\pie{{\footnotesize benchmark}}{41/inlined,13/noninlined}}\hfill
\putpie{\pie{{\footnotesize benchmark}}{41/inlined,13/noninlined}}\hfill
\putpie{\pie{{\footnotesize benchmark}}{41/inlined,13/noninlined}}
\end{minipage}\quad
\begin{minipage}{3cm}
\raggedleft
\begin{tikzpicture}[remember picture]
\legend{{Inlined}/inlined, {Not inlined}/noninlined}
\end{tikzpicture}%
\end{minipage}}
\end{figure}
\end{document}
为了更好地控制各种图表的垂直对齐,最好使用环境subfigure
;此外,现在图表的标题已委托给\putpie
使用\caption
,可以使用一行\putpie
带有空内容的命令来为每一列生成标题:
\documentclass{article}
\usepackage{pgfplots, pgfplotstable}
\usepackage{subcaption}
\usepgfplotslibrary{groupplots}
\pgfplotsset{compat=newest}
\newcommand{\legend}[2][]{
\begin{scope}[#1]
\path
\foreach \n/\s in {#2}
{
++(0,-10pt) node[\s,legend box] {} +(5pt,0) node[legend label] {\n}
}
;
\end{scope}
}
\tikzset{
chart/.style={
legend label/.style={font={\scriptsize},anchor=west,align=left},
legend box/.style={rectangle, draw, minimum size=5pt},
axis/.style={black,semithick,->},
axis label/.style={anchor=east,font={\tiny}},
},
pie chart/.style={
chart,
slice/.style={line cap=round, line join=round, very thick,draw=white},
pie title/.style={font={\bfseries}},
slice type/.style 2 args={
##1/.style={fill=##2},
values of ##1/.style={}
}
}
}
\pgfdeclarelayer{background}
\pgfdeclarelayer{foreground}
\pgfsetlayers{background,main,foreground}
\newcommand{\pie}[3][]{
\begin{scope}[#1]
\pgfmathsetmacro{\curA}{90}
\pgfmathsetmacro{\r}{1}
\def\c{(0,0)}
\foreach \v/\s in{#3}{
\pgfmathsetmacro{\deltaA}{\v/100*360}
\pgfmathsetmacro{\nextA}{\curA + \deltaA}
\pgfmathsetmacro{\midA}{(\curA+\nextA)/2}
\path[slice,\s] \c
-- +(\curA:\r)
arc (\curA:\nextA:\r)
-- cycle;
\pgfmathsetmacro{\d}{max((\deltaA * -(.4/50) + 1) , .5)}
\begin{pgfonlayer}{foreground}
\path \c -- node[pos=\d,pie values,values of \s]{$\v\%$} +(\midA:\r);
\end{pgfonlayer}
\global\let\curA\nextA
}
\end{scope}
}
\newlength\PieWd
\setlength\PieWd{2.2cm}
\newcommand\putpie[2]{%
\begin{subfigure}[t]{\PieWd}
\centering
\caption{#2}
\begin{tikzpicture}
#1
\end{tikzpicture}%
\end{subfigure}%
}
\begin{document}
\begin{figure}
\tikzset{every picture/.style={
pie chart,
slice type={inlined}{lightgray},
slice type={noninlined}{darkgray},
pie values/.style={font={\tiny}},
scale=1
}
}
\pgfplotsset{legend style={
anchor=north,
legend columns=2,
cells={anchor=west},
font=\footnotesize,
rounded corners=2pt,
},
}
\captionsetup[subfigure]{labelformat=empty,textfont=bf}% to suppress the labels from captions and place the name in bold-face
\makebox[\linewidth][l]{%
\begin{minipage}{\linewidth}
\centering
\putpie{}{Column1}\hfill
\putpie{}{Column2}\hfill
\putpie{}{Column3}\hfill
\putpie{}{Column4}\hfill
\putpie{}{Column5}\\
\putpie{\pie{}{41/inlined,13/noninlined}}{benchmark}\hfill
\putpie{\pie{}{12/inlined,78/noninlined}}{some}\hfill
\putpie{\pie{}{9/inlined,35/noninlined}}{other}\hfill
\putpie{\pie{}{71/inlined,8/noninlined}}{title}\hfill
\putpie{\pie{}{47/inlined,14/noninlined}}{benchmark}\\[2ex]
\putpie{\pie{}{34/inlined,34/noninlined}}{perhaps}\hfill
\putpie{\pie{}{4/inlined,65/noninlined}}{different}\hfill
\putpie{\pie{}{23/inlined,32/noninlined}}{words}\hfill
\putpie{\pie{}{17/inlined,13/noninlined}}{benchmark}\hfill
\putpie{\pie{}{34/inlined,13/noninlined}}{benchmark}\\[2ex]
\putpie{\pie{}{50/inlined,50/noninlined}}{title2}\hfill
\putpie{\pie{}{21/inlined,12/noninlined}}{benchmark}\hfill
\putpie{\pie{}{34/inlined,43/noninlined}}{and}\hfill
\putpie{\pie{}{43/inlined,11/noninlined}}{other}\hfill
\putpie{\pie{}{66/inlined,22/noninlined}}{word}
\end{minipage}\quad
\begin{minipage}{3cm}
\raggedleft
\begin{tikzpicture}[remember picture]
\legend{{Inlined}/inlined, {Not inlined}/noninlined}
\end{tikzpicture}%
\end{minipage}}
\end{figure}
\end{document}
顺便说一句,我从弃用改为\tikzstyle
;\tikzset
此外,\footnotesize
不是带有参数的命令,而是字体开关,因此必须用作{\footnotesize text}
(括号是为了保持局部效果,并且\par
必须在离开长段落文本组之前添加。)