I am very new to TikZ and I have trouble making a diagram similar to the one here:
My problems are specifically making MUX
to get to inputs which would be on 1/3 and 2/3 of the width. Taking sigma signal outside of the border while still being above and to the right from the X
block. Making all the lines bend with 90% to get to the final nodes. Adding the dX
labels next to the operators.
My current code is:
\documentclass{article}
\usepackage{tikz}
\usetikzlibrary{positioning,intersections,shapes.geometric,fit,arrows,decorations.shapes,decorations.markings}
\begin{document}
\tikzstyle{register} = [rectangle, draw, text centered]
\tikzstyle{multiplexor} = [rectangle, draw, text centered, minimum width = 4em, minimum height = 2em]
\tikzstyle{operation} = [circle, draw, text centered, minimum size=3em]
\tikzstyle{port} = [pin edge={to->,thin,black}]
\begin{tikzpicture}[node distance = 5em, auto]
\node (mux) [multiplexor] {MUX};
\node (delay) [register, on grid, below of = mux] {Delay};
\node (add_one) [operation, right of = mux] {$+1$};
\node (mult) [operation, on grid, below right of = add_one] {$\times$};
\node (exp) [operation, below of = mult] {$\exp$};
\node (xmin) [port, above of = mux, xshift=-1em] {$x_{min}$};
\node (sigma) [port, above of = border, above right of = mult] {$sigma$};
\node (addr) [port, below of = border, below of = delay] {$address$};
\node (data) [port, below of = border, below of = mult] {$data$};
\node (border) [draw, dashed,inner sep=3pt,fit = (xmin) (exp)] {};
\draw [->] (sigma) |- (mult);
\draw [->] (xmin) -> ([xshift=-2em] mux);
\draw [->] (add_one) -> (mux);
\draw [->] (mux) -> (delay);
\draw [->] (mux) |- (add_one);
\draw [->] (add_one) |- (mult);
\draw [->] (delay) -> (addr);
\draw [->] (mult) -> (exp);
\draw [->] (exp) -> (data);
\end{tikzpicture}
\end{document}
which outputs:
Any help would be appreciated.
Best Answer
For these kinds of drawings I'd first inspect which is the most convenient way to locate nodes: you positioned manually the nodes, but in this case I think the
matrix
library and consequently to position the nodes in a matrix fashion is really convenient.But let's start first with the styles:
The first four are more or less yours styles (some differences are: changed a bit the dimensions, used the same base for
multiplexor
andregister
and convert\tikzstyle
into\tikzset
as per Should \tikzset or \tikzstyle be used to define TikZ styles?). The fifth style, instead, concerns the matrix aspect: remember to load the library with\usetikzlibrary{matrix}
.The matrix is the following:
Consider that with the option
matrix of nodes
each element has automatically a name in the form:matrix name - row number - column number
. Each element, then inherits its own style with the syntax|[style]|
and it is possible to omit each time\node{---};
again thanks to the optionmatrix of nodes
.Now, to locate the labels
dx
, wherex
isa,m,e
, it is possible to exploitlabels
: in this case they are positioned with an angle of 10 degrees out of the node; if you want them exactly on the right, use the keyright
.The label position phase goes like:
To reduce the labels' font size, in the option of the tikzpicture there's a way to set it in
\scriptsize
.Until now, the diagram looks more or less like:
Before starting to connect the elements, I'd go to box the matrix: since its aspect has already been set within the style
matrix aspect
, the box can be introduced there without changing the picture's code.The new options are:
draw
: obvious;loosely dashed
: to customize the border aspect;inner xsep=2em,inner ysep=10ex
: to customize in a different way the horizontal and vertical distance of the matrix border from its content;solid
otherwise the internal elements of the matrix will inherit the dashed option.The result is:
Let's pass now to depict the connections. They require the
calc
library, so load it.I'd start with
x_min
:This is saying that the starting point is the position of the element 1-1 of the matrix placed at 1/3 (from left to right -> north west to north east) going up for 1 cm from there. The text is written through the "label syntax" such that no sort of customization on the font size should be done since it has already been done before with
every label/.style={font=\scriptsize}
.Instead, to connect the
multiplexer
with the element on his right, the following style is needed:while the actual connection is:
To get exactly the point, 2/3 from left to right, I just inverted the anchors of the multiplexer in the previous connection.
Now it looks:
Proceeding a bit faster, to locate the
x
and then connect this midway point to the+1
node, one could do:Notice the (y) is the other midway point; with:
it is possible to connect it to
\times
node and to set also the connection from\times
toexp
and fromexp
to the bottom adding the labeldata
. Notice the syntax:This says that the final point is computed as the intersection of the element and the south east anchor of the matrix; after that, it is shifted down by 1cm.
Another important thing to be highlighted is that both "middle" points are defined through
node[coordinate,...,]
: this is becausecoordinates
do not introduce additional space (for a more detailed explanation see TikZ: difference between \node and \coordinate?).Replicating this concept to:
allows to have both
data
andaddress
on the same level.Finally, we missed just
sigma
:This is similar to what did before, but we need some horizontal space, the
0.5
to have exactly the connection desired.BTW: just realize that we need some more horizontal space between the matrix content and border, so the
inner xsep=2em
should becomeinner xsep=3em
.The complete code for reference: