2

I am currently trying to position some text in the center of a square drawn in a tikzpicture, like so:

example image

However, I am having a bit of trouble.

Take the following example:

\documentclass{article}
\usepackage[utf8]{inputenc}
\usepackage{graphicx}
\usepackage{tikzpagenodes}
\usepackage{tikz}
\usepackage{calc}
\usepackage{layouts}

\begin{document}

\begin{tikzpicture}[overlay, remember picture, x=1cm, y=1cm]
    \newcommand{\boxWidth}{5cm};
    \newcommand{\boxHeight}{3cm};
    \newcommand{\boxPosX}{5cm};
    \newcommand{\boxPosY}{-5cm};

    \newcommand{\someText}{Hello World};
    \newcommand{\textPosX}{\boxPosX + (\printinunitsof{cm}\widthof{\someText}/2)};
    \newcommand{\textPosY}{\boxPosY + \boxHeight / 2};

    \draw [line width=0.05cm, rounded corners=.3cm, color=red] (\boxPosX,\boxPosY) rectangle ++(\boxWidth, \boxHeight);

    \node at (\textPosX, \textPosY) {\someText};
\end{tikzpicture}

\end{document}

The problem arrises when I try using the width of the text: \widthof{\someText}/2 (from the calc package). (Reference Post)

According to the same reference post, \widthof returns a length in points, which is incompatible with centimeters. Therefore, I tried converting to centimeters by using the method described here: \printinunitsof{cm}\widthof{\someText}.

However, this still yields an "Illegal unit of measure (pt inserted)."

What am I doing wrong and how can I correctly convert my units from points to centimeters?

3
  • can you provide a sketch of your desired result. is behind this tikzpicturesomething which require so complicated code?
    – Zarko
    Commented Oct 9, 2018 at 19:35
  • 1
    You cannot do computations with \newcommand, use \pgfmathsetmacro instead, e.g. \pgfmathsetmacro{\textPosX}{\boxPosX + width("\someText")*1pt/2cm};. But this is absolutely unnecessary here, as far as I can see.
    – user121799
    Commented Oct 9, 2018 at 19:35
  • @Zarko I added a picture to help convey what I want.
    – Code Doggo
    Commented Oct 9, 2018 at 19:42

3 Answers 3

4

From your code I sort of sense what you might want:

\documentclass{article}
\usepackage[utf8]{inputenc}
\usepackage{tikzpagenodes}
\usepackage{calc}
\usepackage{layouts}

\begin{document}

\begin{tikzpicture}[overlay, remember picture, x=1cm, y=1cm]
    \newcommand{\boxWidth}{5cm};
    \newcommand{\boxHeight}{3cm};
    \newcommand{\boxPosX}{5cm};
    \newcommand{\boxPosY}{-5cm};

    \newcommand{\someText}{Hello World};
    \node[draw,line width=0.05cm, rounded corners=.3cm, color=red,
    minimum width=\boxWidth,minimum height=\boxHeight,text=black] at 
    ({\boxPosX},{\boxPosY}) {\someText};
\end{tikzpicture}

\end{document}

enter image description here

Instead of \newcommand use \pgfmathsetmacro to do computations, e.g. \pgfmathsetmacro{\textPosX}{\boxPosX + width("\someText")*1pt/2cm};. However, I think that all the complicated computations are unnecessary here. To put a text in the center of a box, it suffices to say \node[draw]{text}. And then you can do all sorts of spirifankerln like adding a minimum width, rounded corners etc.

7
  • Why can I do that addition in my new command for \textPosY, but I cannot do more complex computation? Why does \newcommand allows some computation?
    – Code Doggo
    Commented Oct 9, 2018 at 19:45
  • And I need something complex like this, because I will have several rectangles of the same size, each of which will have a unique string in them. The node method contours around the text only and adding redundant spaces is messy in my opinion.
    – Code Doggo
    Commented Oct 9, 2018 at 19:47
  • @DanHoynoski \newcommand by itself does not allow for computations. You're loading the calc package (which is not to be confused with the TikZ library of the same name), which allows you to do computations, but I guess once you load TikZ, this is sort of obsolete. And no, you can put pretty much anything inside a node of tikzpicture, graphics, equations... (just not tikzpictures, at least you shouldn't). There are tons of libraries which allow you to arrage rectangles of the same size, e.g. matrix or chains.
    – user121799
    Commented Oct 9, 2018 at 19:49
  • 1
    @DanHoynoski No, calc does not do any magic of that kind. It is TikZ which starts to parse these things and then sees "Oh, here is some x+y, let's add them." You can always check such things by saying e.g. \typeout{\boxPosX} and the you will see whether this is the string x+y or the sum.
    – user121799
    Commented Oct 9, 2018 at 20:06
  • 1
    @DanHoynoski Yes, width("xyz") is TikZ language. So I do not need to load the calc package. And if there are complications, you're usually better off if you use the tools of one package, rather than mixing them, in which case it is harder to debug.
    – user121799
    Commented Oct 9, 2018 at 20:11
5

If the text is to be placed in the centre of the rectangle, simply place it with a node midway down the path.

\draw [line width=0.05cm, rounded corners=.3cm, color=red] 
(\boxPosX,\boxPosY) rectangle ++(\boxWidth, \boxHeight)node[midway,text=black]{\someText};

rectangle

\documentclass{article}
\usepackage[utf8]{inputenc}
\usepackage{graphicx}
\usepackage{tikzpagenodes}
\usepackage{tikz}
\usepackage{calc}
\usepackage{layouts}

\begin{document}

\begin{tikzpicture}[overlay, remember picture, x=1cm, y=1cm]
    \newcommand{\boxWidth}{5cm};
    \newcommand{\boxHeight}{3cm};
    \newcommand{\boxPosX}{5cm};
    \newcommand{\boxPosY}{-5cm};

    \newcommand{\someText}{Hello World};
   %\newcommand{\textPosX}{\boxPosX + (\printinunitsof{cm}\widthof{\someText}/2)};
   %\newcommand{\textPosY}{\boxPosY + \boxHeight / 2};

\draw [line width=0.05cm, rounded corners=.3cm, color=red] 
(\boxPosX,\boxPosY) rectangle ++(\boxWidth, \boxHeight)node[midway,text=black]{\someText};

\end{tikzpicture}

\end{document}
2
  • I appreciate your answer! I did not think about adding another node like this! If I could accept two answers, I would!
    – Code Doggo
    Commented Oct 9, 2018 at 20:04
  • 1
    @DanHoynoski The notion of a path with Tikz is a notion that is not immediately obvious. Especially since according to the pages of the manual, it does not have exactly the same meaning.
    – AndréC
    Commented Oct 9, 2018 at 20:14
3

Just another way. If you have some already drawn rectangles (not nodes), you can use a fit node which encompasses rectangle corners and add a label in its center:

\documentclass{article}
\usepackage[utf8]{inputenc}
\usepackage{graphicx}
\usepackage{tikzpagenodes}
\usepackage{tikz}
\usepackage{calc}
\usepackage{layouts}
\usetikzlibrary{fit}
\begin{document}

\begin{tikzpicture}[overlay, remember picture, x=1cm, y=1cm]
    \newcommand{\boxWidth}{5cm};
    \newcommand{\boxHeight}{3cm};
    \newcommand{\boxPosX}{5cm};
    \newcommand{\boxPosY}{-5cm};

    \newcommand{\someText}{Hello World};
%    \newcommand{\textPosX}{\boxPosX + (\printinunitsof{cm}\widthof{\someText}/2)};
%    \newcommand{\textPosY}{\boxPosY + \boxHeight / 2};

    \draw [line width=0.05cm, rounded corners=.3cm, color=red] (\boxPosX,\boxPosY) rectangle ++(\boxWidth, \boxHeight);

    \node[fit={(\boxPosX,\boxPosY) (\boxPosX+\boxWidth,\boxPosY+\boxHeight)},  label=center:\someText] {};

    \draw [line width=0.05cm, rounded corners=.3cm, color=green] (-2,-5) coordinate (1) rectangle ++(5,2) coordinate (2);

    \node[fit={(1) (2)},  label=center:\someText] {};

\end{tikzpicture}

\end{document}

enter image description here

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .