
Я хочу добавить label
к узлу, но "внутри" узла. Что-то вроде этого:
В руководстве, похоже, указано, что это возможно, хотя конкретный ключ не назван.
... Точка привязки для узла метки ... определяется таким образом, что узел метки будет «отвернут» от границы основного узла. Выбранная точка привязки зависит от положения выбранной точки границы и ее положения относительно центра основного узла, а также от того, установлена ли опция трансформации формы.В целом выбор должен быть таким, какой вы ожидаете, но в сложных ситуациях вам, возможно, придется устанавливать якорь самостоятельно.(выделено мной)
Но когда я пробую такой пример:
\documentclass{standalone}
\usepackage{tikz}
\begin{document}
\tikz \node [circle,draw,label={[red,anchor=north]above:X}] {my circle};
\end{document}
Я не вижу никаких изменений в положении узла метки. Он по-прежнему «снаружи».
Есть идеи?
решение1
Проблема здесь в том, что TikZ применяет некоторую автоматизацию (а именно макрос \tikz@auto@anchor
), которая перезапишет ваш набор anchor
.
Мы можем либо перехватить .code
ключ, который применяется последним в узле, который используется внутри для метки (да, даже после наших собственных настроек red, anchor=north
) и который вызывает \tikz@auto@anchor
:
\tikzset{label anchor/.style={tikz@label@post/.append style={anchor=#1}}}
или позволим макросу, который выполняет вычисления, немного расслабиться (дополнительный ключ не нужен):
\tikzset{anchor/.append code=\let\tikz@auto@anchor\relax}
Если новый и улучшенный anchor
ключ теперь будет использоваться более глобально (например, \tikz[anchor=<dir>]
), это также повлияет на узлы (и в настоящее время есть способ вернуть его).
Я также предоставляю ключ inside
(вы даже можете использовать его дважды, чтобы обратить эффект).
Код
\documentclass[tikz]{standalone}
\usepackage{etoolbox}
\makeatletter
\tikzset{anchor/.append code=\let\tikz@auto@anchor\relax}
\tikzset{inside/.code=\preto\tikz@auto@anchor{\pgf@x-\pgf@x\pgf@y-\pgf@y}}
\makeatother
\begin{document}
\tikz\node [anchor=west, circle,draw,label={[red, anchor=north]above:X}] {my circle};
\tikz\node [anchor=west, circle,draw,label={[red, inside]below:X}] {my circle};
\end{document}
Выход
решение2
Вот еще один подход, эксплуатирующий эту append after command
опцию. Суть в том, что, ссылаясь на якорь, \tikzlastnode.center
можно добавлять, относительно этой позиции, ярлыки.
Новый стиль, способный выполнить эту задачу my label
:
\tikzset{my label/.style args={#1:#2}{
append after command={
(\tikzlastnode.center) node [#1] {#2}
}
}
}
А мве:
\documentclass[tikz,png,border=10pt]{standalone}
\usepackage{tikz}
\tikzset{my label/.style args={#1:#2}{
append after command={
(\tikzlastnode.center) node [#1] {#2}
}
}
}
\begin{document}
\tikz \node [circle,draw,my label={red,above=0.15cm:X}] {my circle};
\tikz \node [circle,draw,my label={red,below=0.15cm:X}] {my circle};
\end{document}
что дает в качестве результатов:
Стиль принимает в качестве первого аргумента любой параметр TikZ, поэтому легко настраивать цвета и положение: действительно, лучше немного отрегулировать смещение, чтобы не перекрывать текст.
Если же вы знаете, что метку всегда следует размещать под «северной границей», то лучшим решением будет изменить стиль my label
на:
\tikzset{my label/.style args={#1:#2}{
append after command={
(\tikzlastnode.north) node [#1] {#2}
}
}
}
Таким образом, просто установив:
\tikz\node [circle,draw,my label={red,below:X}] {my circle};
позволяет достичь цели.
А мве:
\documentclass[tikz,png,border=10pt]{standalone}
\usepackage{tikz}
\tikzset{my label/.style args={#1:#2}{
append after command={
(\tikzlastnode.north) node [#1] {#2}
}
}
}
\begin{document}
\begin{tikzpicture}
\node [circle,draw,my label={red,below:X}] {my circle};
\node [circle,draw,my label={red,below=0.15cm:X},xshift=2cm] {my circle};
\end{tikzpicture}
\end{document}
Результат:
Пересмотр
Предыдущий метод страдает, как сказано в комментариях, если нужно ввести более одной метки. Но это вполне осуществимо, если вместо введения узлов мы вводим координаты с метками.
Код:
\documentclass[tikz,png,border=10pt]{standalone}
\usepackage{tikz}
\tikzset{my label/.style args={[#1]#2:#3}{
append after command={
(\tikzlastnode.center) coordinate[label={[label distance=0.1cm,#1]#2:#3}]
}
},
}
\begin{document}
\begin{tikzpicture}
\node [circle,
draw,
my label={[red]above:X},
my label={[green!70!blue]below:Y},
my label={[blue,yshift=0.3cm]above:Z}] {my circle};
\node [circle,
draw,
my label={[blue,yshift=-0.15cm]below:X},
my label={[green!70!blue]70:Z},
my label={[orange!80!red]130:Y},
xshift=2cm] {my circle};
\end{tikzpicture}
\end{document}
Результат:
Примечание: использование label distance
в определении параметра позволяет не допустить перекрытия текста метки, когда просто говорится:
\tikz\node [circle,draw,my label={[red]below:X}] {my circle};
решение3
Вы также можете сместить метку:
\documentclass{standalone}
\usepackage{tikz}
\begin{document}
\tikz \node [circle,draw,label={[red,yshift=-0.5cm]above:X}] {my circle};
\tikz \node [circle,draw,label={[red,label distance=-0.5cm]above:X}] {my circle};
\end{document}