这个问题有点出乎意料。我希望使用以下形式的数据生成自定义图形:
源类型 | 目标类型 | 时间 |
---|---|---|
南非 | 结核病 | 1.52 |
南卡罗来纳州 | 热电偶 | 11.18 |
巴拿马 | 助教 | 21.31 |
标准差 | 助教 | 12.63 |
南卡罗来纳州 | 道明 | 7.92 |
- 前两列各包含四个标签,可以是字符串或整数。
- 最后一列是数字。
- 该文件可能包含几百行。
我希望生成类似以下的图形(例如根据上表近似):
该图S-A
显示T-B
迅速地:1.52 分钟。所有条形的高度T-X
是列中的最大值time
。弧线的交点S-A
位于T-B
1.52 分钟处。
这在 Latex 或其他软件包/平台中可行吗?理想情况下,我还可以设计图形样式。最重要的是,更改框和弧的颜色。如果其他图形模板传达相同的信息,我愿意接受它们没有相互作用。
我做了大量研究,发现繁荣,但似乎找不到适合这种用例的东西。
答案1
起点可以是以下内容,甚至可能进一步实现自动化:
\documentclass[border=10mm]{standalone}
\usepackage{tikz}
\usetikzlibrary{matrix, positioning}
\usepackage{etoolbox}
\newlength\targetmaxheight
\setlength{\targetmaxheight}{3cm}
\newcounter{targetmaxvalue}
\setcounter{targetmaxvalue}{25}
\newlength\targetxsep
\newlength\targetysep
\setlength{\targetxsep}{1.5cm}
\setlength{\targetysep}{-.25cm}
\begin{document}
\begin{tikzpicture}[
source/.style={
matrix of nodes,
nodes={
draw
}
},
target/.style={
draw,
minimum width=1cm,
minimum height=\targetmaxheight,
}
]
\let\mymatrixcontent\empty
\foreach \s in {S-A,S-B,S-C,S-D}{%
\xappto\mymatrixcontent{ \s \\ }
}%
\node[source] at (0,0) (s) {
\mymatrixcontent
};
\node[target, above left=\targetysep and \targetxsep of s] (t-1) { T-A };
\node[target, above right=\targetysep and \targetxsep of s] (t-2) { T-B };
\node[target, below right=\targetysep and \targetxsep of s] (t-3) { T-C };
\node[target, below left=\targetysep and \targetxsep of s] (t-4) { T-D };
\draw (s-2-1) to[in=0, out=180] ([yshift={\targetmaxheight*(21.31/\value{targetmaxvalue})}]t-1.south east);
\draw (s-1-1) to[in=180, out=0] ([yshift={\targetmaxheight*(1.52/\value{targetmaxvalue})}]t-2.south west);
\draw (s-3-1) to[in=180, out=0] ([yshift={\targetmaxheight*(11.18/\value{targetmaxvalue})}]t-3.south west);
\draw (s-4-1) to[in=0, out=180] ([yshift={\targetmaxheight*(12.63/\value{targetmaxvalue})}]t-1.south east);
\draw (s-3-1) to[in=0, out=180] ([yshift={\targetmaxheight*(7.92/\value{targetmaxvalue})}]t-4.south east);
\end{tikzpicture}
\end{document}
通过更多的自动化(可能不是最优雅的方式):
\documentclass[border=10mm]{standalone}
\usepackage{tikz}
\usetikzlibrary{matrix, positioning}
\usepackage{etoolbox}
\newlength\targetmaxheight
\setlength{\targetmaxheight}{3cm}
\newcounter{targetmaxvalue}
\setcounter{targetmaxvalue}{25}
\newlength\targetxsep
\newlength\targetysep
\setlength{\targetxsep}{1.5cm}
\setlength{\targetysep}{-.25cm}
\begin{document}
\begin{tikzpicture}[
node distance={
\targetysep and \targetxsep
},
source/.style={
matrix of nodes,
nodes={
draw
}
},
target/.style={
draw,
minimum width=1cm,
minimum height=\targetmaxheight,
},
connect/.code args={(#1) to (#2) at #3}{
\path (#1);
\pgfgetlastxy{\tempsx}{\tempsy}
\path (#2);
\pgfgetlastxy{\temptx}{\tempty}
\draw (#1) to[
in={\ifdim\tempsx<\temptx 180\else 0\fi},
out={\ifdim\tempsx<\temptx 0\else 180\fi}
] ([yshift={\targetmaxheight*(#3/\value{targetmaxvalue})}]#2.south \ifdim\tempsx<\temptx west\else east\fi);
}
]
\let\mymatrixcontent\empty
\foreach \s in {S-A,S-B,S-C,S-D}{%
\xappto\mymatrixcontent{ \s \\ }
}%
\node[source] at (0,0) (s) {
\mymatrixcontent
};
\node[target, above left=of s] (t-1) { T-A };
\node[target, above right=of s] (t-2) { T-B };
\node[target, below right=of s] (t-3) { T-C };
\node[target, below left=of s] (t-4) { T-D };
\path[connect={(s-2-1) to (t-1) at 21.31}];
\path[connect={(s-1-1) to (t-2) at 1.52}];
\path[connect={(s-3-1) to (t-3) at 11.18}];
\path[connect={(s-4-1) to (t-1) at 12.63}];
\path[connect={(s-3-1) to (t-4) at 7.92}];
\end{tikzpicture}
\end{document}
结果看起来与上面相同。