Prerequisites: Basic LaTeX knowledge
Time to complete: 40-45 minutes
Difficulty: Intermediate to Advanced
What you’ll learn: TikZ syntax, libraries, drawing techniques, and practical examples
Time to complete: 40-45 minutes
Difficulty: Intermediate to Advanced
What you’ll learn: TikZ syntax, libraries, drawing techniques, and practical examples
Introduction to TikZ
What is TikZ?
TikZ (TikZ ist kein Zeichenprogramm - TikZ is not a drawing program) is a powerful package for creating graphics programmatically in LaTeX. It provides:Precise Control
Exact positioning and measurements
Consistency
Matching document fonts and styles
Programmable
Loops, variables, and calculations
Integration
Seamless LaTeX integration
Basic Setup
Copy
\documentclass{article}
\usepackage{tikz}
% Load common libraries
\usetikzlibrary{
arrows.meta, % Arrow styles
positioning, % Relative positioning
shapes.geometric, % Additional shapes
calc, % Coordinate calculations
patterns, % Fill patterns
decorations.pathmorphing, % Path decorations
backgrounds, % Background layers
fit, % Fitting nodes
chains, % Chain positioning
shadows % Drop shadows
}
\begin{document}
% Inline TikZ
\begin{tikzpicture}
\draw (0,0) -- (2,1);
\end{tikzpicture}
% Centered figure
\begin{figure}[htbp]
\centering
\begin{tikzpicture}
% Drawing commands here
\end{tikzpicture}
\caption{TikZ diagram}
\end{figure}
\end{document}
Basic Drawing
Coordinates and Paths
Copy
\begin{tikzpicture}[scale=1.5]
% Cartesian coordinates
\draw[->] (-0.5,0) -- (4,0) node[right] {$x$};
\draw[->] (0,-0.5) -- (0,3) node[above] {$y$};
% Points
\fill (1,1) circle (2pt) node[below] {$(1,1)$};
\fill (3,2) circle (2pt) node[right] {$(3,2)$};
% Path with multiple segments
\draw[thick, blue] (0,0) -- (1,1) -- (2,0.5) -- (3,2);
% Curved path
\draw[thick, red] (0,2) .. controls (1,3) and (2,1) .. (3,2.5);
% Closed path
\draw[thick, green, fill=green!20]
(0.5,0.5) -- (1.5,0.5) -- (1,1.5) -- cycle;
% Polar coordinates
\draw[purple] (0,0) -- (45:2) node[midway, above] {$(45:2)$};
% Relative coordinates
\draw[orange, thick] (2,1) -- ++(1,0.5) -- ++(0.5,-0.5);
\end{tikzpicture}
Nodes and Labels
Copy
\begin{tikzpicture}[
every node/.style={font=\sffamily},
main node/.style={circle, draw, minimum size=1cm}
]
% Basic nodes
\node (A) at (0,0) {Simple text};
\node[draw] (B) at (3,0) {Boxed text};
\node[circle, draw] (C) at (6,0) {Circle};
% Styled nodes
\node[main node, fill=blue!20] (D) at (0,2) {D};
\node[rectangle, draw, rounded corners, fill=red!20] (E) at (3,2) {Rect};
\node[ellipse, draw, fill=green!20] (F) at (6,2) {Ellipse};
% Node connections
\draw[->] (A) -- (B);
\draw[->] (B) -- (C);
\draw[<->, thick] (D) -- (E);
\draw[->, dashed] (E) -- (F);
% Labels on edges
\draw[->] (D) -- (A) node[midway, left] {edge};
\draw[->] (F) -- (C) node[near start, right] {label};
\end{tikzpicture}
Flowcharts and Diagrams
Basic Flowcharts
Copy
\begin{tikzpicture}[
node distance=2cm,
startstop/.style={rectangle, rounded corners, draw, fill=red!30, minimum width=3cm, minimum height=1cm},
process/.style={rectangle, draw, fill=blue!30, minimum width=3cm, minimum height=1cm},
decision/.style={diamond, draw, fill=green!30, minimum width=3cm, minimum height=1cm, aspect=2},
io/.style={trapezium, trapezium left angle=70, trapezium right angle=110, draw, fill=yellow!30, minimum width=3cm, minimum height=1cm},
arrow/.style={thick, ->, >=stealth}
]
% Nodes
\node[startstop] (start) {Start};
\node[io, below=of start] (input) {Input data};
\node[process, below=of input] (process1) {Process data};
\node[decision, below=of process1] (decision) {Valid?};
\node[process, below=of decision] (process2) {Generate output};
\node[startstop, below=of process2] (stop) {End};
% Alternative path
\node[process, right=3cm of decision] (error) {Handle error};
% Connections
\draw[arrow] (start) -- (input);
\draw[arrow] (input) -- (process1);
\draw[arrow] (process1) -- (decision);
\draw[arrow] (decision) -- node[left] {Yes} (process2);
\draw[arrow] (decision) -- node[above] {No} (error);
\draw[arrow] (error) |- (input);
\draw[arrow] (process2) -- (stop);
\end{tikzpicture}
State Diagrams
Copy
\begin{tikzpicture}[
>=stealth,
node distance=3cm,
state/.style={circle, draw, minimum size=1.5cm, font=\small},
initial/.style={state, fill=green!30},
final/.style={state, double, fill=red!30},
transition/.style={->, thick}
]
% States
\node[initial] (idle) {Idle};
\node[state, right=of idle] (loading) {Loading};
\node[state, right=of loading] (active) {Active};
\node[state, below=of active] (error) {Error};
\node[final, below=of idle] (terminated) {Done};
% Transitions
\draw[transition] (idle) -- node[above] {start} (loading);
\draw[transition] (loading) -- node[above] {success} (active);
\draw[transition] (loading) -- node[right] {fail} (error);
\draw[transition] (active) -- node[right] {complete} (terminated);
\draw[transition] (error) -- node[below] {retry} (loading);
\draw[transition] (error) -- node[left] {abort} (terminated);
\draw[transition, bend left=30] (active) to node[above] {reset} (idle);
% Self loop
\draw[transition] (active) to[loop above] node {update} (active);
\end{tikzpicture}
Graphs and Trees
Graph Structures
Copy
\begin{tikzpicture}[
node distance=2cm,
vertex/.style={circle, draw, fill=blue!20, minimum size=8mm},
edge/.style={thick}
]
% Vertices
\node[vertex] (A) {A};
\node[vertex, right=of A] (B) {B};
\node[vertex, below right=of A] (C) {C};
\node[vertex, below left=of A] (D) {D};
\node[vertex, below=of C] (E) {E};
% Edges
\draw[edge] (A) -- (B);
\draw[edge] (A) -- (C);
\draw[edge] (A) -- (D);
\draw[edge] (B) -- (C);
\draw[edge] (C) -- (D);
\draw[edge] (C) -- (E);
\draw[edge] (D) -- (E);
% Edge labels
\draw[edge] (B) -- node[above right] {5} (E);
\end{tikzpicture}
Tree Structures
Copy
\begin{tikzpicture}[
level distance=1.5cm,
level 1/.style={sibling distance=4cm},
level 2/.style={sibling distance=2cm},
level 3/.style={sibling distance=1cm},
treenode/.style={circle, draw, fill=green!30, minimum size=8mm},
edge from parent/.style={draw, ->, >=stealth}
]
% Binary tree
\node[treenode] {8}
child {
node[treenode] {3}
child {
node[treenode] {1}
}
child {
node[treenode] {6}
child {
node[treenode] {4}
}
child {
node[treenode] {7}
}
}
}
child {
node[treenode] {10}
child[missing] {}
child {
node[treenode] {14}
child {
node[treenode] {13}
}
child[missing] {}
}
};
\end{tikzpicture}
Scientific Diagrams
Mathematical Diagrams
Copy
\begin{tikzpicture}[scale=1.5]
% Axes
\draw[->] (-0.5,0) -- (4,0) node[right] {$x$};
\draw[->] (0,-0.5) -- (0,3) node[above] {$y$};
% Grid
\draw[gray, very thin] (0,0) grid (3.5,2.5);
% Function plots
\draw[blue, thick, domain=0:3.5, samples=100]
plot (\x, {0.5*\x*\x - \x + 1});
\draw[red, thick, domain=0:3.5, samples=100]
plot (\x, {sin(\x r) + 1});
\draw[green, thick, domain=0.1:3.5, samples=100]
plot (\x, {ln(\x) + 1});
% Labels
\node[blue] at (3,2.2) {$f(x) = \frac{1}{2}x^2 - x + 1$};
\node[red] at (2,0.3) {$g(x) = \sin(x) + 1$};
\node[green] at (3.2,1.3) {$h(x) = \ln(x) + 1$};
% Points of interest
\fill[blue] (2,1) circle (2pt) node[above right] {$(2,1)$};
\end{tikzpicture}
Physics Diagrams
Copy
\begin{tikzpicture}[
force/.style={->, thick, blue},
mass/.style={rectangle, draw, fill=gray!30, minimum width=1.5cm, minimum height=1.5cm}
]
% Free body diagram
\node[mass] (m) {$m$};
% Forces
\draw[force] (m.north) -- ++(0,2) node[above] {$N$};
\draw[force] (m.south) -- ++(0,-2) node[below] {$mg$};
\draw[force] (m.east) -- ++(1.5,0) node[right] {$F$};
\draw[force] (m.west) -- ++(-1,0) node[left] {$f$};
% Surface
\draw[thick] (-3,-0.75) -- (3,-0.75);
\foreach \x in {-3,-2.5,...,3} {
\draw (\x,-0.75) -- (\x-0.25,-1);
}
% Angle for inclined plane
\begin{scope}[xshift=6cm]
\draw[thick] (0,0) -- (4,0) -- (4,2) -- cycle;
\node[mass, rotate=26.57] at (2.5,1.25) {$m$};
\draw[force] (2.5,1.25) -- ++(0,-2) node[below] {$mg$};
\draw[force, rotate=26.57] (2.5,1.25) -- ++(0,1.5) node[above] {$N$};
\node at (0.5,0.15) {$\theta$};
\end{scope}
\end{tikzpicture}
Advanced Techniques
Loops and Automation
Copy
\begin{tikzpicture}
% Grid of nodes using foreach
\foreach \x in {0,1,2,3,4} {
\foreach \y in {0,1,2,3} {
\node[circle, draw, fill=blue!\x0!green!\y0]
at (\x,\y) {\tiny \x,\y};
}
}
% Radial pattern
\begin{scope}[xshift=7cm, yshift=2cm]
\foreach \angle in {0,30,...,330} {
\draw[thick, color=red!\angle!blue]
(0,0) -- (\angle:2);
\fill[color=red!\angle!blue]
(\angle:2) circle (2pt);
}
\end{scope}
% Connected graph
\begin{scope}[yshift=-5cm]
\foreach \i in {1,...,6} {
\node[circle, draw, fill=orange!30]
(n\i) at ({360/6 * (\i-1)}:2) {\i};
}
\foreach \i in {1,...,6} {
\foreach \j in {\i,...,6} {
\draw[gray] (n\i) -- (n\j);
}
}
\end{scope}
\end{tikzpicture}
Styles and Scopes
Copy
\begin{tikzpicture}[
% Define custom styles
my node/.style={
circle,
draw=#1,
fill=#1!20,
minimum size=1cm,
font=\bfseries
},
my edge/.style={
thick,
->,
>=stealth,
#1
},
important/.style={
my node=red,
drop shadow
},
normal/.style={
my node=blue
}
]
% Use custom styles
\node[important] (A) at (0,0) {A};
\node[normal] (B) at (3,0) {B};
\node[normal] (C) at (3,3) {C};
\node[important] (D) at (0,3) {D};
% Styled edges
\draw[my edge={red, dashed}] (A) -- (B);
\draw[my edge={blue}] (B) -- (C);
\draw[my edge={green, bend left}] (C) -- (D);
\draw[my edge={orange, bend right}] (D) -- (A);
% Scope with different settings
\begin{scope}[xshift=6cm, scale=0.8, opacity=0.7]
\node[my node=purple] (E) at (0,0) {E};
\node[my node=cyan] (F) at (2,2) {F};
\draw[my edge={thick}] (E) -- (F);
\end{scope}
\end{tikzpicture}
Decorations and Patterns
Copy
\begin{tikzpicture}[
decoration={
snake,
amplitude=.5mm,
segment length=3mm
}
]
% Different decorations
\draw[decorate, thick] (0,0) -- (3,0) node[right] {snake};
\draw[
decoration={coil, segment length=4mm},
decorate, thick
] (0,1) -- (3,1) node[right] {coil};
\draw[
decoration={zigzag, segment length=4mm},
decorate, thick
] (0,2) -- (3,2) node[right] {zigzag};
\draw[
decoration={random steps, segment length=3mm},
decorate, thick
] (0,3) -- (3,3) node[right] {random};
% Text along path
\draw[
decoration={
text along path,
text={This text follows the curve!}
},
decorate
] (5,0) .. controls (6,2) and (7,2) .. (8,0);
% Arrow decorations
\draw[
thick,
decoration={
markings,
mark=at position 0.25 with {\arrow{>}},
mark=at position 0.5 with {\arrow{>}},
mark=at position 0.75 with {\arrow{>}}
},
postaction={decorate}
] (5,3) circle (1);
\end{tikzpicture}
Best Practices
Optimization Tips
TikZ best practices:
- Use styles - Define reusable styles for consistency
- Name nodes - Makes connections easier
- Use calculations - Let TikZ compute positions
- Layer wisely - Background, main, foreground
- Externalize - Compile complex diagrams separately
- Comment code - Especially for complex diagrams
- Use libraries - Don’t reinvent the wheel
- Test incrementally - Build diagrams step by step
Common Pitfalls
Avoid these TikZ mistakes:
- Hardcoded positions - Use relative positioning
- Repeated code - Use loops and styles
- Complex paths - Break into smaller parts
- Missing libraries - Load required libraries
- Scale issues - Test at final size
- Memory problems - Externalize large diagrams
- Forgotten semicolons - Every command needs one
Complete Examples
Network Diagram
Copy
\documentclass{article}
\usepackage{tikz}
\usetikzlibrary{positioning, shapes.geometric, shadows, backgrounds}
\begin{document}
\begin{tikzpicture}[
node distance=2cm,
server/.style={
rectangle, draw, fill=blue!20,
minimum width=2cm, minimum height=1.5cm,
drop shadow, font=\small
},
client/.style={
rectangle, draw, fill=green!20,
minimum width=1.5cm, minimum height=1cm,
drop shadow, font=\small
},
database/.style={
cylinder, draw, fill=orange!20,
minimum width=2cm, minimum height=1.5cm,
shape border rotate=90,
drop shadow, font=\small
},
cloud/.style={
cloud, draw, fill=gray!20,
minimum width=3cm, minimum height=2cm,
drop shadow, font=\small
},
connection/.style={thick, ->, >=stealth},
label/.style={font=\footnotesize, fill=white, inner sep=2pt}
]
% Core components
\node[cloud] (internet) {Internet};
\node[server, below=3cm of internet] (loadbalancer) {Load Balancer};
% Web servers
\node[server, below left=2cm and 1cm of loadbalancer] (web1) {Web Server 1};
\node[server, below right=2cm and 1cm of loadbalancer] (web2) {Web Server 2};
% Application servers
\node[server, below=of web1] (app1) {App Server 1};
\node[server, below=of web2] (app2) {App Server 2};
% Databases
\node[database, below right=2cm and 0cm of app1] (db1) {Primary DB};
\node[database, right=1cm of db1] (db2) {Replica DB};
% Clients
\node[client, left=3cm of internet] (client1) {Client 1};
\node[client, above left=1cm and 2cm of internet] (client2) {Client 2};
\node[client, above right=1cm and 2cm of internet] (client3) {Client 3};
% Connections
\draw[connection] (client1) -- (internet);
\draw[connection] (client2) -- (internet);
\draw[connection] (client3) -- (internet);
\draw[connection, <->] (internet) -- node[label] {HTTPS} (loadbalancer);
\draw[connection] (loadbalancer) -- (web1);
\draw[connection] (loadbalancer) -- (web2);
\draw[connection] (web1) -- (app1);
\draw[connection] (web2) -- (app2);
\draw[connection] (app1) -- (db1);
\draw[connection] (app2) -- (db1);
\draw[connection, <->] (db1) -- node[label] {Sync} (db2);
% Background regions
\begin{pgfonlayer}{background}
\fill[yellow!20, rounded corners]
([shift={(-0.5,0.5)}]loadbalancer.north west)
rectangle
([shift={(0.5,-0.5)}]db2.south east);
\node[above] at (loadbalancer.north) {Data Center};
\end{pgfonlayer}
\end{tikzpicture}
\end{document}
Data Flow Diagram
Copy
\documentclass{article}
\usepackage{tikz}
\usetikzlibrary{arrows.meta, positioning, shapes, decorations.pathmorphing}
\begin{document}
\begin{tikzpicture}[
>=latex,
node distance=2.5cm,
process/.style={
rectangle, draw, fill=blue!30,
minimum width=3cm, minimum height=1cm,
rounded corners, font=\small\sffamily
},
data/.style={
trapezium, draw, fill=green!30,
trapezium left angle=70,
trapezium right angle=110,
minimum width=2.5cm, minimum height=0.8cm,
font=\small\sffamily
},
storage/.style={
rectangle, draw, fill=orange!30,
minimum width=2.5cm, minimum height=0.8cm,
path picture={
\draw ([xshift=0.1cm]path picture bounding box.north west)
-- ([xshift=-0.1cm]path picture bounding box.north east);
},
font=\small\sffamily
},
flow/.style={thick, ->, >=stealth},
label/.style={font=\footnotesize, above, sloped}
]
% Input layer
\node[data] (input) {Raw Data};
% Processing pipeline
\node[process, below=of input] (validate) {Validate};
\node[process, below=of validate] (transform) {Transform};
\node[process, below=of transform] (analyze) {Analyze};
% Storage
\node[storage, right=3cm of validate] (raw) {Raw Storage};
\node[storage, right=3cm of transform] (processed) {Processed DB};
\node[storage, right=3cm of analyze] (results) {Results Cache};
% Output
\node[data, below=of analyze] (output) {Reports};
\node[process, right=of output] (visualize) {Visualize};
\node[data, right=of visualize] (dashboard) {Dashboard};
% Main flow
\draw[flow] (input) -- node[label] {Stream} (validate);
\draw[flow] (validate) -- node[label] {Valid} (transform);
\draw[flow] (transform) -- node[label] {Clean} (analyze);
\draw[flow] (analyze) -- node[label] {Insights} (output);
% Storage connections
\draw[flow, dashed] (validate) -- node[label] {Archive} (raw);
\draw[flow, dashed] (transform) -- node[label] {Store} (processed);
\draw[flow, dashed] (analyze) -- node[label] {Cache} (results);
% Visualization flow
\draw[flow] (output) -- (visualize);
\draw[flow] (visualize) -- (dashboard);
\draw[flow, bend right] (results) to node[label, below] {Query} (visualize);
% Error handling
\node[process, left=2cm of transform, fill=red!30] (error) {Error Handler};
\draw[flow, red, bend right] (validate) to node[label, below] {Invalid} (error);
\draw[flow, red, bend right] (transform) to node[label, below] {Failed} (error);
\draw[flow, red] (error) |- (input);
% Decorations
\node[above=0.5cm of input, font=\large\bfseries] {Data Processing Pipeline};
% Legend
\begin{scope}[xshift=8cm, yshift=-3cm]
\node[process, minimum width=2cm] (l1) at (0,0) {Process};
\node[data, minimum width=2cm] (l2) at (0,-1) {Data};
\node[storage, minimum width=2cm] (l3) at (0,-2) {Storage};
\draw[flow] (3,0) -- node[above] {Flow} (4.5,0);
\draw[flow, dashed] (3,-1) -- node[above] {Store} (4.5,-1);
\node[above=0.3cm of l1, font=\bfseries] {Legend};
\end{scope}
\end{tikzpicture}
\end{document}
Next Steps
Explore more LaTeX visualization:PGFPlots
Advanced plotting and charts
Circuit Diagrams
Electronic circuit drawings
Chemical Structures
Molecular diagrams
3D Graphics
Three-dimensional drawings
Pro tip: Start simple and build complexity gradually. Use the TikZ manual (texdoc tikz) as your reference - it’s comprehensive with excellent examples. Consider externalizing complex diagrams to speed up compilation of your main document.