我想根据输入文件在轴上绘制一组矩形。我的.tex
文件应该是这样的
\documentclass{article}
\usepackage{tikz,pgf}
\usetikzlibrary{plotmarks}
\usepackage{pgfplots, pgfplotstable}
\usetikzlibrary{fit,calc}
\begin{document}
\begin{tikzpicture}
\begin{axis}[
width=8cm,
height=8cm,
scale only axis,
xmin=-1, xmax=20,
ymin=-1, ymax=20,
xlabel={i},
ylabel={j},
title={Hi}]
\pgfplotstableread{data.dat}\table;
for each row in table
if (\gg=0)
{
\draw [black, fill=blue, thick] (axis cs:\x,\y) rectangle (axis cs:\xx,\yy);
\end{axis}
else if (\gg=1)
\draw [black, fill=red, thick] (axis cs:\x,\y) rectangle (axis cs:\xx,\yy);
\end{axis}
else if (\gg=2)
\draw [black, fill=red, thick] (axis cs:\x,\y) rectangle (axis cs:\xx,\yy);
\end{axis}
\end{tikzpicture}
\end{document}
我的输入文件如下所示
%% data.dat
x y xx yy gg
0 0 5 4 0
0 4 5 9 1
0 9 5 13 0
0 13 5 16 1
5 0 9 5 2
我怎样才能画出它们?
答案1
以下解决方案确实使用datatool
代替pgfplotstable
(我找不到在 a 中循环数据的引用pgfplotstable
)并且基于先前的答案我的。
我将所有TAB
字符替换为对,
LaTeXTAB
不太友好的字符,并且,
是默认分隔符。
该解决方案使用etoolbox
的工具将所有\draw
命令连接在一个宏中\mydraws
。
使用了两个宏:
\appto<macro>{<code>}
和\eappto<macro>{<code>}
。
第一个只是附加<code>
到宏,而<macro>
后者将<code>
首先扩展。
我们不想\draw
被扩展,因为 Ti钾Z 应该单独处理它;但我们希望\c
、\x
、\y
和\xx
扩展\yy
,因为它们保存实际值。如果我们不扩展这些宏,它们将首先\mydraws
在内部使用时被扩展\tikzpicture
,但现在它们都具有最后一行的值,我们只会得到一个框(但绘制了五次)……
代码
\documentclass{article}
\usepackage{tikz}
\usepackage{pgfplots}
\usepackage{datatool}
\usepackage{etoolbox}
\begin{filecontents}{data.dat}
x,y,xx,yy,gg
0,0,5,4,0
0,4,5,9,1
0,9,5,13,0
0,13,5,16,1
5,0,9,5,2
\end{filecontents}
\DTLloaddb[
headers={x,y,xx,yy,gg},
keys={x,y,xx,yy,gg}
]{data}{data.dat}
\begin{document}
\def\mydraws{}% \def is a TeX primitive, one could have said \newcommand*\mydraws{}, too.
\DTLforeach*{data}{\x=x,\y=y,\xx=xx,\yy=yy,\gg=gg}{
% \PackageWarning{}{x=\x, y=\y, xx=\xx, yy=\yy, gg=\gg} % DEBUG
\def\c{blue}
\ifnum\gg=0\relax
\def\c{blue}
\else\ifnum\gg=1\relax
\def\c{red}
\else
\def\c{red}
\fi\fi
\appto\mydraws{\draw}% \draw will not be expanded
\eappto\mydraws{ [black, fill=\c, thick] (axis cs:\x,\y) rectangle (axis cs:\xx,\yy);}% \c, \x, \y, \xx and \yy will be expanded to their actual value.
}
\begin{tikzpicture}
\begin{axis}[
width=8cm,
height=8cm,
scale only axis,
xmin=-1, xmax=20,
ymin=-1, ymax=20,
xlabel={i},
ylabel={j},
title={Hi}]
\mydraws
\end{axis}
\end{tikzpicture}
\end{document}
输出
答案2
另外还有一个pgfplotstable
从现有列中创建自定义列的解决方案。
\documentclass{article}
\usepackage{pgfplots,pgfplotstable,filecontents}
\pgfplotsset{compat=1.7}
\begin{filecontents*}{data.dat}
x y xx yy gg
0 0 5 4 0
0 4 5 9 1
0 9 5 13 0
0 13 5 16 1
5 0 9 5 2
\end{filecontents*}
\begin{document}
\pgfplotstableread{data.dat}\mytable
\pgfplotstablecreatecol[
create col/assign/.code={%
\getthisrow{x}\pointaa
\getthisrow{y}\pointab
\getthisrow{xx}\pointba
\getthisrow{yy}\pointbb
\getthisrow{gg}\mycolor
\pgfmathparse{\mycolor<2?(\mycolor<1?"blue":"red"):"green"}
\edef\temp{%
\noexpand\draw[black,fill=\pgfmathresult]
(axis cs:\pointaa,\pointab) rectangle (axis cs:\pointba,\pointbb);}
\pgfkeyslet{/pgfplots/table/create col/next content}\temp
}
]{drawer}{\mytable}
\begin{tikzpicture}
\begin{axis}[
width=8cm,
height=8cm,
scale only axis,
xmin=-1, xmax=20,
ymin=-1, ymax=20,
xlabel={i},
ylabel={j},
title={Hi},
]
\pgfplotstableforeachcolumnelement{drawer}\of\mytable\as\cell{\cell}
\end{axis}
\end{tikzpicture}
\end{document}