在数学中

在数学中

我应该指出,我已经熟悉 TikZ,并且正在寻找技术答案,好像 TikZ 还不够技术性。

这个问题归结为以下问题,这些东西之间有什么区别:

  • \def\pointA{\pgfpoint{0cm}{0cm}}
  • \coordinate (A) at (current page.north east);
  • \coordinate (A) at (1,1);
  • (current page.north east)
  • \node [anchor=east] {}<-- 一个锚点?:-p(仅展示术语重叠)
  • \pgfpointanchor<-- 但这一定是一个锚点,或者是一个点?:-p

我认为我的理解还不够,而且这干扰了我下面的尝试。

在数学中

A观点定义为:

点是平面上的一个精确位置或地点。重要的是要理解点不是一个事物,而是一个地方。

A协调定义为:

坐标是定义点位置的一组有序的数字。

锚点是:

在此处输入图片描述

我想用实际例子来澄清这一点。

让我们定义一个坐标:

\coordinate (rightmid) at ($ (current page.north east) + (0,-18cm) $); % use tikz calc library

有很多隐式坐标(应该称之为坐标、点、锚点还是别的什么?)比如:

  • (当前页面.西北)
  • (当前页面.北)
  • (当前页面.东北)
  • (当前页面.东)
  • (当前页面.东南)
  • (当前页面.南)
  • (当前页面.西南)
  • (当前页面.中心)

假设我想计算两件事物之间的垂直距离(我故意选择“事物”这个词)并将此变量存储在当前范围之外以供使用。

例如,这两个事物是 (当前页面.东北) 和 (右中)

为了进行算术运算,我知道以下选项(是全部吗?):

  1. 我可以用来\pgfmathparse评估算术

  2. 我可以使用\path let \p1=语法。

使用选项 1,我可以将 设置\pgfxa\pgfya\pgfx进行\pgfy计算并使用 获得结果\pgfmathresult

然后我可以定义一个唯一的长度(全局),例如\setlength{\mylength}{2cm}。然后我可以使用\mylength来检索它。这将不允许我将所有内容都写入一个独立的宏中,因为\setlength只能定义一次。另一种方法是使用\global\let\mylength{2cm},在我看来,这更适合这项工作(如果我错了,请纠正我。这对值+单位/维度有影响吗)?

综合起来

这是一个实验无法编译根据以下几个答案:

\documentclass{article}
\usepackage{fontspec}
\usepackage{tikz}
\usetikzlibrary{calc}

% A4 Paper
\pdfpagewidth=210mm \pdfpageheight=297mm % for PDF output
\paperwidth=210mm \paperheight=297mm     % for TikZ

\newcommand{\getdistance}[3]{
\makeatletter
% Syntax: <length variable/macro> <coordinate1> <coordinate2>
  \pgfpointdiff{\pgfpointanchor{#2}{center}} % https://tex.stackexchange.com/a/39325/13552
               {\pgfpointanchor{#3}{center}} % https://tex.stackexchange.com/a/39325/13552
  \pgf@xa=\pgf@x
  \pgf@ya=\pgf@y
  \pgfmathparse{veclen(\pgf@xa,\pgf@ya)} 
  \global\let#1\pgfmathresult % <-- I want the pgfmathresult to be a dimension like 510 pt
\makeatother
}

\begin{document}

\begin{tikzpicture}[overlay]
\coordinate (rightmidtest) at ($ (current page.north east) + (0,-10cm) $); % use tikz calc library
\coordinate (rightmid) at ($ (current page.north east) + (0,-18cm) $); % use tikz calc library
\end{tikzpicture}

\getdistance{\globalresult}{rightmidtest}{rightmid}
\getdistance{\globalresult}{current page.north east}{rightmid}
\getdistance % <-- Should expand to last distance measured
\end{document}

更新代码 2016-02-25在职的

经过对 percusse 的回答的分析和新的理解后,我想到了一些其他的东西。

记住:

  • (current page)是隐含的
  • 锚点 .center 在 TikZ 中是隐式的,但在 PGF 中不是\pgfpointanchor{<ref>}{<anchor e.g. center>}

我使用xparse宏的语法,因为它更容易阅读。

\documentclass{article}
\usepackage{fontspec}
\usepackage{tikz}
\usetikzlibrary{calc}
\usepackage{xparse}

\makeatletter
\NewDocumentCommand{\getdistance}{ m m O{center} m O{center} }{%
    %Syntax: {\<macro>} {<ref1>} [<anchor>] {<ref2>} [<anchor>]
    \pgfpointdiff{\pgfpointanchor{#2}{#3}}% https://tex.stackexchange.com/a/39325/13552
                 {\pgfpointanchor{#4}{#5}}% https://tex.stackexchange.com/a/39325/13552
    \pgf@xa=\pgf@x
    \pgf@ya=\pgf@y
    \pgfmathparse{veclen(\pgf@xa,\pgf@ya)} % result as number (floating point)
    %\pgfmathveclen{\pgf@xa}{\pgf@ya} % alternate syntax to pgfmathparse: result as number (floating point)
    %\global\let#1\pgfmathresult pt % does not recognize pt.
    \global\edef#1{\pgfmathresult\ pt}
    %\pgfmathprintnumber{\pgfmathresult}%
  }    
\makeatother    

 \begin{document}
 
\begin{tikzpicture}[remember picture,overlay]
    % (current page) is implicit
    % .center is implicit in TikZ but not in PGF \pgfpointanchor{<ref>}{<anchor e.g. center>}
    \coordinate (referral1) at ($ (current page.north east) + (0,-18cm) $); % use tikz calc library
    \node [minimum height=2cm] (referral2) {};
\end{tikzpicture}
    
\begin{tikzpicture}[remember picture,overlay]
  \getdistance{\globalresultA}{current page}{referral1}
  \getdistance{\globalresultB}{current page}[north east]{referral1}
  \getdistance{\globalresultC}{current page}[north east]{referral2}[north]
  \getdistance{\globalresultD}{current page}[north east]{referral2}[south]
\end{tikzpicture}

\globalresultA

\globalresultB

\globalresultC

\globalresultD
\end{document}

答案1

我认为混淆的原因是 TikZ 使用的是引用而不是对象。当a提到某个节点名称时。它通常假设用户可能指的是它的中心坐标。或者在两个东西之间绘制东西的情况下,如果其中一个是节点,那么它会神奇地计算出其边界上的点,这样用户就不会注意到。

但所有这些都是在内部完成的。与节点无关。节点有一个可以引用的名称和预定义的节点可理解的位置。

这些都不存储。它们只是检查是否存在或只是执行。换句话说,如果你写shape=duck,那么它不会检查所有可能的形状名称,它只是进行这种存在性检查(我对实际的宏使用了无意义的名称)

\pgfutil@ifdefined\pgf@Shape@#1@...{<if it exists use>}{<if not err>}

锚点也是一样的,如果你说,它会通过一些等等来anchor=heel询问这个名字。\pgf@sh@#1@anchor@#2

那么这些是从哪里来的呢?它们是通过形状声明来定义的,\savedanchor等等\anchor

所以它们就在那里,精心排列,这样当你引用它们时,从文本框的宽度高度到形状路径的所有内容都是痛苦的手工编码。这就是为什么定义新形状是一项非常繁琐的工作。当你引用它们时,它们的排列方式是将锚点位置(全局!)写入长度寄存器内\pgf@<x,y>

长话短说,当您引用节点锚点时,实际上有一个相当复杂的过程才能从中获取坐标。

此外,坐标\pgf@<x,y>和坐标类型节点之间是有区别的\coordinate

最后,当您引用一个节点时,TikZ 会尝试通过假设您指的是它的中心锚点来帮助您,这样您就可以节省一些击键,但有时您需要进行更精细的操作,例如距离测量。

您不能使用引用名称。您需要实际坐标(再次强调不是\coordinates)。正如 Mark Wibrow 所评论的那样,您必须以某种方式理解上下文,而这可以通过\pgf@process回答以下问题来实现:它是文字坐标吗(1,1)?它是节点名称吗?它是节点锚点吗?等等。然后,您可以使用生成的\pgf@<x,y>寄存器。

然后,您就可以对它们做任何您想做的事情。您的示例let语法也很好地简化了这一点,但它仍然在做您所描述的事情。实际上,您的问题基本上是为什么 TikZ 存在于 PGF 之上。它是一个设计精良的前端,具有非常冗长但功能强大的 PGF 语法。

答案2

\def\pointA{\pgfpoint{0cm}{0cm}}

仅当您熟悉 PGF(Ti 的基础)时才使用此功能Z)。无论如何,TeX 中做什么并不重要\pgfpoint;这个命令从来都不是单独存在的。通常它是语法的一部分,例如

\coordinate (A) at (current page.north east);

给点命名。实际的 x 和 y 坐标是什么并不重要。我们知道它(A)在哪里,这就是我们需要知道的一切。

\coordinate (A) at (1,1);

与上一个类似。通常我们命名点是为了 (A) 减少代码长度/复杂性和 (B) 提高可读性。例如

(current page.north east)

带括号时,它会发出搬去动作。这很像你拿着笔,将手移到下一个想要画的地方。例如

此代码使 TiZ 将笔移动到画布周围并声明节点/坐标。

\node [anchor=east] {}

将节点放置在钢笔当前位置的“附近”。我说的“附近”是指您给出的锚应与钢笔的位置一致。这很像您在船上可以将锚抛到您想要的地方,然后锚会固定住船。


实践部分

  • 你需要\makeatletter
  • 您可能想要\pgfmathsetlength而不是\pgfmathsetmacros\pgfmathparse
    • 但请记住,所有尺寸必须在使用前声明。
  • 使用节点时要小心(current page)。通常你需要[overlay]
  • 您需要处于tikzpicture环境内部才能检索您在tikzpicture环境中制作的任何内容。
    • 如果您不是在同一个环境中工作tikzpicture,您需要[remember picture]

\documentclass{article}
\usepackage{tikz}
\usetikzlibrary{calc}

\makeatletter
\newcommand{\getdistance}[3]{
% Syntax: <length variable/macro> <coordinate1> <coordinate2>
  \pgfpointdiff{\pgfpointanchor{#2}{center}} % http://tex.stackexchange.com/a/39325/13552
               {\pgfpointanchor{#3}{center}} % http://tex.stackexchange.com/a/39325/13552
  \pgf@xa=\pgf@x
  \pgf@ya=\pgf@y
  \pgfmathparse{veclen(\pgf@xa,\pgf@ya)} 
  \global\let#1\pgfmathresult % <-- I want the pgfmathresult to be a dimension like 510 pt
}

\begin{document}

\begin{tikzpicture}[remember picture,overlay]
\coordinate (rightmidtest) at ($ (current page.north east) + (0,-10cm) $); % use tikz calc library
\coordinate (rightmid) at ($ (current page.north east) + (0,-18cm) $); % use tikz calc library
\end{tikzpicture}

\tikz[remember picture,overlay]{
    \getdistance{\globalresulta}{rightmidtest}{rightmid}
    \getdistance{\globalresultb}{current page}{rightmid}
}

\globalresulta

\globalresultb

\end{document}

答案3

  1. \def\pointA{\pgfpoint{0cm}{0cm}}

    这基本上与\coordinate (A) at (0,0);

  2. \coordinate (A) at (current page.north east);

    这里您只是将页面的右上角命名为A。从位置已经命名的角度来看,这毫无意义,但不必输入所有内容而只需输入 会很有帮助A

  3. \coordinate (A) at (1,1);

    TikZ 中的坐标基本上是具有coordinate形状的节点,它们不需要标题,而且,特别重要的是,它们没有sep。所以这是一个要点。尽管如此,写\node[coordinate] (a) at (0,0) {};等于\coordinate (a) at (0,0);

    也可以看看TikZ:\node 和 \coordinate 之间的区别?

  4. (current page.north east)

    这表示当前“页面”的右上角。通常,这是一张 A4 纸,但可以是任意尺寸。在这种情况下,页面不一定是通常的纸张,但可以是任何指定区域。

  5. \node [anchor=east] {}<-- 一个锚?

    不,这不是锚点。这是一个节点,其定位是通过在坐标处放置设计的锚点来确定的。因此将放置具有与坐标重合的锚点\node [anchor=east] at (4,0) {};的节点。east(4,0)

答案4

我不知道如何编辑我的旧答案。我只会写一个新的。

Z 有很多方法可以指定点

  • 给出数字坐标。
    例如(1,2)(3mm,4in,5pt)(6:7)(axis cs:x=8)

  • 给出预定义的节点名称和锚点名称。
    例如(current page.south east)(current bounding box.north west)

  • 给出预定义的节点名称。
    例如(current page)。这相当于(current page.center)

  • 给出预定义的coordinate
    例如\coordinate(X)at(1,2);\path(X);。Acoordinate实际上是一个节点,其中锚点“消失”:(X)(X.center)(X.south)(X.34)均给出相同的结果。

他们的 PGF 对应物是

  • \pgfpointxy\pgfpointxyz\pgfpointpolar, 等等
  • \pgfpointanchor{#1}{#2}
  • \pgfpointanchor{#1}{center}
  • \pgfpointanchor{#1}{center}

现在你看到,在 的定义中\getdistance,只能填写一个节点名称,并且锚点center是强制选择的。因此

\getdistance{\globalresultb}{current page.north east}{rightmid}

无法编译,因为current page.north east不再是节点。但是

\coordinate (A) at (current page.north east);
\getdistance{\globalresultb}{A}{rightmid}

确实编译,因为(A)是节点的名称。

哪种输入可以处理取决于你\getdistance。例如在 TiZ,\tikz@parse@node可以处理(X)(Y.Z)。但不能(1,2)。更一般地\tikz@@scan@@no@calculator,和可以处理(X)(Y.Z)(1,2)。更一般地,\tikz@@@scan@@absolute可以处理($ (current page.north east) + (0,-10cm) $)。您需要选择一个。

相关内容