Я хотел бы создать tikzpicture (на самом деле анимированную), которая считывала бы числа из текстового файла и использовала бы их либо как координаты или узлы, либо для дальнейших вычислений. Кажется, пакет datatool подойдет, но я могу заставить его работать, только если передам аргументы напрямую, как в MWE:
\documentclass{standalone}
\usepackage{filecontents}
\usepackage{tikz}
\usetikzlibrary{calc}
\usepackage{datatool}
\usepackage{animate}
\begin{filecontents*}{test.csv}
f wzb em
380 5 3
400 1 2
405 2 5
410 43 5656
415 4 94
420 4 6
\end{filecontents*}
\DTLsetseparator{ }
\DTLloaddb{widmo}{test.csv}
\begin{document}
\begin{animateinline}[label=graph_switch,controls=step]{1}
\multiframe{5}{iFrame=400+5}{
\begin{tikzpicture}
\useasboundingbox[draw] (-3,-2) rectangle (5,6);
\pgfmathparse{1000/\iFrame}
\edef\dlugosc{\pgfmathresult}
\DTLassignfirstmatch{widmo}{f}{405}{\wzb=wzb,\em=em}
%\DTLassignfirstmatch{widmo}{f}{\dlugosc}{\wzb=wzb,\em=em}
%\DTLassignfirstmatch{widmo}{f}{\iFrame}{\wzb=wzb,\em=em}
\draw[->] (0,0) -- (\wzb, \em) --(\dlugosc:1) node[left] {\dlugosc};
\node at (2,0) {em=\em, wzb=\wzb};
\end{tikzpicture}
}
\end{animateinline}
\end{document}
Две закомментированные строки не работают так, как я бы хотел. Есть ли простой способ исправить это или другой пакет, который позволит мне просматривать текстовый файл, выбирать значение из определенной строки и использовать его как переменную? Буду признателен за любые предложения по этому поводу.
решение1
В общем, когда вы сталкиваетесь с вызовом макроса, например
\DTLassignfirstmatch{widmo}{f}{\iFrame}{\wzb=wzb,\em=em}
в котором макрос, по-видимому, требует фактических данных, а не \iFrame
ссылки на данные, вам необходимо расширить команду, содержащую данные, в данном случае \iFrame
.
Если вам повезет, \iFrame
будет содержать фактические токены данных, и для их получения потребуется только одно расширение. Если вам не повезет, макрос \iFrame
вообще не будет расширяемым, и в этом случае то, что я описываю, не решит вашу проблему. Где-то между этими крайностями \iFrame
может потребоваться конечное число расширений для получения желаемых токенов данных (я не буду описывать, как это сделать здесь, но есть способы сделать это).
К счастью, в нашем случае \iFrame
содержит фактические токены данных, поэтому требуется только одно расширение. Типичный метод достижения этого следующий
\def\tmp{\DTLassignfirstmatch{widmo}{f}}
\expandafter\tmp\expandafter{\iFrame}{\wzb=wzb,\em=em}
Здесь мы сохраняем сбалансированное по фигурным скобкам выражение, ведущее к \iFrame
временному макросу \tmp
. Затем можно использовать \expandafter
для расширения\iFrame
дорасширяется \tmp
. Таким образом, к моменту \DTLassignfirstmatch
выполнения вхождение \iFrame
уже было расширено до фактических токенов данных, которые требуются от \DTL...
макроса.
решение2
В документации datatool
об этом сказано ясно:
\DTLassignfirstmatch{⟨db name⟩}{⟨col key⟩}{⟨value⟩}{⟨assign list⟩}
Это похоже на ,
\DTLassign
за исключением того, что применяется к первой строке в указанной базе данных, где столбец, идентифицированный меткой,⟨col key⟩
имеет указанное значение.Обратите внимание, что в матче не производится расширение.Значение должно точно совпадать.
(Страница 98, выделено мной.)
С другой стороны, сразу после этого описания вы найдете
\xDTLassignfirstmatch{⟨db name⟩}{⟨col key⟩}{⟨value⟩}{⟨assign list⟩}
Это похоже на
\DTLassignfirstmatch
, но выполняет одноуровневое расширение⟨value⟩
.
Итак, вы хотите использовать
\xDTLassignfirstmatch{widmo}{f}{\iFrame}{\wzb=wzb,\em=em}
Но если я попробую, то получу сообщение «слишком большой размер».
В любом случае, если я проверю это с помощью
\def\iFrame{405}
\xDTLassignfirstmatch{widmo}{f}{\iFrame}{\wzb=wzb,\em=em}
\verb|\wzb| = \wzb
\verb|\em| = \em
я получил