访问tikz坐标的逻辑值

访问tikz坐标的逻辑值

在 TikZ 中,可以使用库let的语法calc或使用 PGF 命令访问节点的坐标值\pgfpointanchor。但是,这些值是点的尺寸/长度,而不是所用坐标系的值。例如,我喜欢用它们的逻辑坐标值标记图中的某些点和节点,例如在标准中tikzpicture,即x=1cm,y=1cm实际上,处的点应该用而不是用(1,2)标记。节点不是手动定位的,而是使用 TikZ 的各种相对定位技术,所以我自己不知道坐标。这是关于具有正交 X 轴和 Y 轴的普通二维 XY 坐标系。(1,2)(28.4527pt,56.9055pt)

我目前的做法是获取单位向量的长度(以点为单位),然后用坐标长度除以它,以计算所用坐标系的相应值。这种方法行得通,但当然会导致舍入误差,例如 1.9998 而不是 2。然后我使用函数\numsiunitx数字舍入为合适的位数。

我的问题:有没有更好的tikz坐标来实现这一
目标x=1pt,y=1pt

在这里,我的概念验证解决方案目前非常僵化,因为它仅适用于节点。

\documentclass[png]{standalone}
\usepackage{tikz}
\usetikzlibrary{intersections}
\usepackage[round-mode=places]{siunitx}

\makeatletter
\newcommand\xcoord[2][center]{{%
    \pgfpointxy{1}{1}%
    \@tempdima=\pgf@x
    \pgfpointanchor{#2}{#1}%
    \@tempdimb=\pgf@x
    \pgfmathparse{\@tempdimb/\@tempdima}%
    \num{\pgfmathresult}%
}}
\newcommand\ycoord[2][center]{{%
    \pgfpointxy{1}{1}%
    \@tempdima=\pgf@y
    \pgfpointanchor{#2}{#1}%
    \@tempdimb=\pgf@y
    \pgfmathparse{\@tempdimb/\@tempdima}%
    \num{\pgfmathresult}%
}}
\makeatother

\begin{document}
\begin{tikzpicture}
    \draw [help lines] (0,0) grid [step=1] (2,4);
    \draw [name path=A] (0,0) -- (2,4);
    \draw [name path=B] (2,0) -- (0,4);
    \draw [name intersections={of=A and B}]
        (intersection-1)
        node [right] {(\xcoord{intersection-1},\ycoord{intersection-1})}
        circle (2pt);
\end{tikzpicture}
\end{document}

结果

答案1

PGF的\pgfmathprintnumber宏使您可以打印和格式,包括四舍五入到十进制数字\pgfmathprintnumber[precision=2]{\pgfmathresult}

单位向量存储在\pgf@xx(x 单位向量的 x 分量)和\pgf@yy(y 单位向量的 y 分量)中。因此,您的函数可以缩短为

\makeatletter
\newcommand\xcoord[2][center]{{%
    \pgfpointanchor{#2}{#1}%
    \pgfmathparse{\pgf@x/\pgf@xx}%
    \pgfmathprintnumber{\pgfmathresult}%
}}
\newcommand\ycoord[2][center]{{%
    \pgfpointanchor{#2}{#1}%
    \pgfmathparse{\pgf@y/\pgf@yy}%
    \pgfmathprintnumber{\pgfmathresult}%
}}
\makeatother

答案2

这是从节点或锚点中提取坐标值的另一种方法。

\makeatletter
\def\extractcoord#1#2#3{
  \path let \p1=(#3) in \pgfextra{
    \pgfmathsetmacro#1{\x{1}/\pgf@xx}
    \pgfmathsetmacro#2{\y{1}/\pgf@yy}
    \xdef#1{#1} \xdef#2{#2}
  };
}
\makeatother

例子:

在此处输入图片描述

\documentclass{article}
\usepackage{tikz}
\usetikzlibrary{calc}
\makeatletter
\def\extractcoord#1#2#3{
  \path let \p1=(#3) in \pgfextra{
    \pgfmathsetmacro#1{\x{1}/\pgf@xx}
    \pgfmathsetmacro#2{\y{1}/\pgf@yy}
    \xdef#1{#1} \xdef#2{#2}
  };
}
\makeatother
\pagestyle{empty}
\begin{document}
\begin{tikzpicture}
  \draw[help lines] (0,0) grid (3,4);
  \begin{scope}[shift={(1,1)}]
    \coordinate (A) at (0,0);
    \coordinate (B) at (2,3) ;
    \coordinate (C) at ($(A)!.5!(B)$);
    \fill[red] (A) circle(2pt);
    \fill[red] (B) circle(2pt);
    \fill[blue] (C) circle(2pt);
    \extractcoord\x\y{C}
  \end{scope}
  \extractcoord\xb\yb{C}
\end{tikzpicture}

Inner scope: $(\x,\y)$\par
Global scope: $(\xb,\yb)$\par
Inner scope (fixed precision):
$(\pgfmathprintnumber[precision=2]{\x},\pgfmathprintnumber[precision=2]{\y})$\par
\end{document}

答案3

将尺寸划分为1cm标量将使您以厘米为单位的数字值与Tikz的\let坐标构造(需要加载Tikz的calc库),可以简化您的示例,如下所示。

\documentclass{standalone}
\usepackage{tikz}
\usetikzlibrary{calc,intersections}

\begin{document}

\begin{tikzpicture}
    \draw [help lines] (0,0) grid [step=1] (2,4);
    \draw [name path=A] (0,0) -- (2,4);
    \draw [name path=B] (2,0) -- (0,4);
    \draw [name intersections={of=A and B}]
        let
           \p1=(intersection-1),
           \n1={scalar(\x1/1cm)},
           \n2={scalar(\y1/1cm)}
        in
        (\p1)
        node [right] {(\n1,\n2)}
        circle (2pt);
\end{tikzpicture}

\end{document}

获取坐标分量的数值


上述代码没有明确格式化打印的数字。这是一个带格式的版本。

以下命令将(包的)\scalar可以处理的数学表达式作为强制参数,并去除其维度(如果有),返回纯数值。然后,它使用(包的) 格式化该值,并将其选项设置为的可选参数。\pgfmathparsepgfmath\pgfmathprintnumberpgf\scalar

\newcommand{\scalar}[2][]{%
   \pgfmathscalar{#2}%
   \pgfmathprintnumber[#1]{\pgfmathresult}%
}

例如,以下命令的名称\logv是“逻辑值”的缩写,即出现在您的帖子标题中的表达式,接受维度,并以厘米(Tikz的默认单元)返回其数值,以返回2个小数点位置。

\newcommand{\logv}[1]{\scalar[precision=2,fixed zerofill]{#1/1cm}}

使用这些工具,并记住tikz包会自动加载pgfpgfmath包,上面的答案可以重写如下。

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

\newcommand{\scalar}[2][]{%
   \pgfmathscalar{#2}%
   \pgfmathprintnumber[#1]{\pgfmathresult}%
}
\newcommand{\logv}[1]{\scalar[precision=2,fixed zerofill]{#1/1cm}}

\begin{document}
\begin{tikzpicture}
    \draw [help lines] (0,0) grid [step=1] (2,4);
    \draw [name path=A] (0,0) -- (2,4);
    \draw [name path=B] (2,0) -- (0,4);
    \draw [name intersections={of=A and B}]
       let \p1=(intersection-1) in
       (\p1)
       node [right] {(\logv{\x1},\logv{\y1})}
        circle (2pt);
\end{tikzpicture}
\end{document}

在原始答案中添加数字格式

相关内容