# Penrose tiling in TikZ

How can I auto-generate a Penrose tiling by TikZ? Here's my code for Mathematica:

GG = (Sqrt[5]+1)/2;
standardthin = {1/2+Sqrt[GG^2-(1/2)^2] I , 0, 1};
standardthick = {GG/2+Sqrt[1-(GG/2)^2] I, 0, GG};
sectthin[n_, t_] :=
If[n > 0,
Join[sectthin[n-2, {t[[2]], t[[3]], (GG*t[[3]]+t[[1]])/(GG+1)}],
sectthick[n-1, {(GG*t[[3]]+t[[1]])/(GG+1), t[[1]], t[[2]]}]],
{thin @@ N[t]}];
sectthick[n_, t_] :=
If[n > 0,
Join[sectthick[n-2, {(GG*t[[2]]+t[[3]])/(GoldenRatio+1),t[[1]],t[[2]]}],
sectthin[n-1, {t[[3]], (GG*t[[2]]+t[[3]])/(GG+1), t[[1]]}]],
{thick @@ N[t]}];
addtothick[n_, t_, d_] :=
If[d == 0, {},
Join[{frame @@ t},
If[EvenQ[d],
Join[addtothick[n+2, {t[[2]], t[[3]], ((GG+1)*t[[1]]-GG*t[[3]])},d/2],
sectthin[n+1, {((GG+1)*t[[1]]-GG*t[[3]]), t[[1]], t[[2]]}]],
Join[addtothin[n+1, {t[[2]], t[[3]], ((GG+1)*t[[1]]-t[[2]])/GG}, (d-1)/2],
sectthin[n-1, {t[[3]], ((GG+1)*t[[1]]-t[[2]])/GG, t[[1]]}]]]]];

addtothin[n_, t_, d_] :=
If[d == 0, {},
Join[{frame @@ t},
If[EvenQ[d],
Join[addtothin[n+2, {((GG+1)*t[[3]]-GG*t[[2]]), t[[1]], t[[2]]}, d/2],
sectthick[n+1, {t[[3]], ((GG+1)*t[[3]]-GG*t[[2]]), t[[1]]}]],
Join[addtothick[n+1, {t[[3]], ((GG+1)*t[[2]]-t[[1]])/GG, t[[1]]}, (d -1)/2],
sectthick[n-1, {t[[2]], t[[3]], ((GG+1)*t[[2]]-t[[1]])/GG}]]]]];

triangle[a_, b_, c_] := Graphics[Line[{Re[#], Im[#]} & /@ {a, b, c, a}]];
thin := triangle;
thick := triangle;

frame[a_, b_, c_] := Graphics[{Thickness[0.005], Line[{Re[#], Im[#]} & /@ {a, b, c, a}]}]

Show[addtothin[0, standardthin, 200], AspectRatio -> Automatic]


which creates something like

-
Can you provide the atoms that you want to use in the generation? – percusse Jun 27 '12 at 16:11
Short answer: by implementing the construction algorithm. ;-) -- While this is an interesting topic (I'd like to see a real answer myself) I think you can improve your question by elaborating a bit. For example: What are your efforts so far? Which penrose tiling (P1, P2 or P3) do you want? – Fritz Jun 27 '12 at 16:12
PSTricks can do that ... – Herbert Jun 27 '12 at 16:21
@Fritz: I have a code I wrote in Mathematica, which does P2 :p Does it help posting the code here? – Yuji Jun 27 '12 at 16:48
@Herbert Can you please undelete your answer to my recent question? I like the code; it leaves something mathematical to think about. – kan Jun 27 '12 at 17:16

Third edit: a faster and more customizable variation!

Features of this version:

• builds Penrose tilings with Robinson's triangles (semikites and semidarts) or kite and dart.
• uses TikZ styles to specify filling and drawing.
• uses TikZ styles to design shapes of each pieces.
• provides TikZ styles to use Penrose tilings as pattern.

My (long) code is divided in several parts.

Here's the longest part (preamble, some default styles and the macros to build and to draw/fill tilings by recursion):

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

% phi = golden ratio = (1+sqrt(5))/2
% invphi = 1/phi
% n: number of decompositions left to do
% ver: starting vertex
% angle: direction of first edge
% len: lenght of first edge
% rot: sense of rotation (0 => anticlockwise, 1 => clockwise)

\pgfmathsetmacro{\invphi}{2/(1+sqrt(5))}

% default styles
\tikzset{
% borders style
penrose line/.style={draw=black,line join=round},
% semikites and semidarts styles
penrose clockwise semikite/.style={penrose line},
penrose anticlockwise semikite/.style={penrose line},
penrose clockwise semidart/.style={penrose line},
penrose anticlockwise semidart/.style={penrose line},
% kites and darts styles
penrose kite/.style={penrose line},
penrose dart/.style={penrose line},
% the three paths (and the three corresponding reverse paths)
penrose common/.style={},
penrose path 1/.style={penrose common},
penrose path 2/.style={penrose common},
penrose path 3/.style={penrose common},
penrose rev path 1/.style={penrose common},
penrose rev path 2/.style={penrose common},
penrose rev path 3/.style={penrose common},
}

\newcommand\penrosedrawclockwisesemikite[3]{% ver, angle, len
% semikite (clockwise)
\path (#1) +(#2:#3) coordinate (#1-b) +(#2-36:#3) coordinate (#1-c);
\path[penrose anticlockwise semikite] (#1)
to[penrose path 1] (#1-b)
to[penrose path 2] (#1-c)
to[penrose path 3] (#1);
}

\newcommand\penrosedrawanticlockwisesemikite[3]{% ver, angle, len
% semikite (anticlockwise)
\path (#1) +(#2:#3) coordinate (#1-b) +(#2+36:#3) coordinate (#1-c);
\path[penrose clockwise semikite] (#1)
to[penrose path 1] (#1-b)
to[penrose path 2] (#1-c)
to[penrose path 3] (#1);
}

\newcommand\penrosesemikite[5]{% n, ver, angle, len, rot
\ifnum#1=0 % draw or recursive decomposition ?
\ifnum#5=1 % anticlockwise or clockwise ?
\penrosedrawclockwisesemikite{#2}{#3}{#4}
\else
\penrosedrawanticlockwisesemikite{#2}{#3}{#4}
\fi
\else
{
% decomposition (semikite => 2 semikites and 1 semidart)
\edef\dep{#1}
\edef\ver{#2}
\edef\angle{#3}
\edef\len{#4}
\edef\rot{#5}
\pgfmathtruncatemacro{\n}{\dep-1}
\edef\namex{\ver\n}
\pgfmathsetlengthmacro{\newlen}{\len*\invphi}
\ifnum#5=1 % anticlockwise or clockwise ?
\path (\ver) ++(\angle-36:\len) coordinate (\namex);
\pgfmathtruncatemacro{\newanglea}{mod(\angle+108,360)}
\penrosesemikite{\n}{\namex}{\newanglea}{\newlen}{1}
\penrosesemikite{\n}{\namex}{\newanglea}{\newlen}{0}
\penrosesemidart{\n}{\ver}{\angle}{\newlen}{1}
\else
\path (\ver) ++(\angle+36:\len) coordinate (\namex);
\pgfmathtruncatemacro{\newanglea}{mod(\angle-108,360)}
\penrosesemikite{\n}{\namex}{\newanglea}{\newlen}{0}
\penrosesemikite{\n}{\namex}{\newanglea}{\newlen}{1}
\penrosesemidart{\n}{\ver}{\angle}{\newlen}{0}
\fi
}
\fi
}

\newcommand\penrosedrawkite[3]{% ver, angle, len
% kite (current clockwise semikite + opposite anticlockwise semikite)
\path (#1)
+(#2+36:#3) coordinate (#1-b)
+(#2:#3)    coordinate (#1-c)
+(#2-36:#3) coordinate (#1-d);
\path[penrose kite] (#1)
to[penrose path 1] (#1-b)
to[penrose rev path 2] (#1-c)
to[penrose path 2] (#1-d)
to[penrose rev path 1] (#1);
}

\newcommand\penrosekite[5]{% n, ver, angle, len, rot
\ifnum#1=0 % draw or recursive decomposition ?
\ifnum#5=1 % draw kite if current semikite is clockwise
\penrosedrawkite{#2}{#3}{#4}
\fi
\else
{
% decomposition (semikite => 2 semikites and 1 semidart)
\edef\dep{#1}
\edef\ver{#2}
\edef\angle{#3}
\edef\len{#4}
\edef\rot{#5}
\pgfmathtruncatemacro{\n}{\dep-1}
\edef\namex{\ver\n}
\pgfmathsetlengthmacro{\newlen}{\len*\invphi}
\ifnum#5=1 % anticlockwise or clockwise ?
\path (\ver) ++(\angle-36:\len) coordinate (\namex);
\pgfmathtruncatemacro{\newanglea}{mod(\angle+108,360)}
\penrosekite{\n}{\namex}{\newanglea}{\newlen}{1}
\penrosekite{\n}{\namex}{\newanglea}{\newlen}{0}
\penrosedart{\n}{\ver}{\angle}{\newlen}{1}
\else
\path (\ver) ++(\angle+36:\len) coordinate (\namex);
\pgfmathtruncatemacro{\newanglea}{mod(\angle-108,360)}
\penrosekite{\n}{\namex}{\newanglea}{\newlen}{0}
\penrosekite{\n}{\namex}{\newanglea}{\newlen}{1}
\penrosedart{\n}{\ver}{\angle}{\newlen}{0}
\fi
}
\fi
}

\newcommand\penrosedrawclockwisesemidart[3]{
% semidart (clockwise)
\path (#1)
+(#2:#3)            coordinate (#1-b)
+(#2-36:#3*\invphi) coordinate (#1-c);
\path[penrose anticlockwise semidart] (#1)
to[penrose path 3] (#1-b)
to[penrose path 2] (#1-c)
to[penrose path 1] (#1);
}

\newcommand\penrosedrawanticlockwisesemidart[3]{
% semidart (anticlockwise)
\path (#1)
+(#2:#3)            coordinate (#1-b)
+(#2+36:#3*\invphi) coordinate (#1-c);
\path[penrose clockwise semidart] (#1)
to[penrose path 3] (#1-b)
to[penrose path 2] (#1-c)
to[penrose path 1] (#1);
}

\newcommand\penrosesemidart[5]{% n, ver, angle, len, rot
\ifnum#1=0 % draw or recursive decomposition ?
\ifnum#5=1 % anticlockwise or clockwise ?
\penrosedrawclockwisesemidart{#2}{#3}{#4}
\else
\penrosedrawanticlockwisesemidart{#2}{#3}{#4}
\fi
\else
{
% decomposition (semidart => 1 semikite and 1 semidart)
\edef\dep{#1}
\edef\ver{#2}
\edef\angle{#3}
\edef\len{#4}
\edef\rot{#5}
\pgfmathtruncatemacro{\n}{\dep-1}
\edef\namex{\ver\n}
\pgfmathsetlengthmacro{\newlen}{\len*\invphi}
\path (\ver) ++(\angle:\len) coordinate (\namex);
\ifnum#5=1 % anticlockwise or clockwise
\pgfmathsetmacro{\newanglea}{mod(\angle-144,360)}
\pgfmathsetmacro{\newangleb}{mod(\angle-36,360)}
\penrosesemidart{\n}{\namex}{\newanglea}{\newlen}{1}
\penrosesemikite{\n}{\ver}{\newangleb}{\newlen}{0}
\else
\pgfmathtruncatemacro{\newanglea}{mod(\angle+144,360)}
\pgfmathtruncatemacro{\newangleb}{mod(\angle+36,360)}
\penrosesemidart{\n}{\namex}{\newanglea}{\newlen}{0}
\penrosesemikite{\n}{\ver}{\newangleb}{\newlen}{1}
\fi
}
\fi
}

\newcommand\penrosedrawdart[3]{
% dart (current clockwise semidart + opposite anticlockwise semidart)
\path (#1)
+(#2:#3)            coordinate (#1-b)
+(#2-36:#3*\invphi) coordinate (#1-c)
+(#2-72:#3)         coordinate (#1-d);
\path[penrose dart] (#1)
to[penrose path 3] (#1-b)
to[penrose path 2] (#1-c)
to[penrose rev path 2] (#1-d)
to[penrose rev path 3] (#1);
}

\newcommand\penrosedart[5]{% n, ver, angle, len, rot
\ifnum#1=0 % draw or recursive decomposition ?
\ifnum#5=1 % draw dart if current semidart is clockwise
\penrosedrawdart{#2}{#3}{#4}
\fi
\else
{
% decomposition (semidart => 1 semikite and 1 semidart)
\edef\dep{#1}
\edef\ver{#2}
\edef\angle{#3}
\edef\len{#4}
\edef\rot{#5}
\pgfmathtruncatemacro{\n}{\dep-1}
\edef\namex{\ver\n}
\pgfmathsetlengthmacro{\newlen}{\len*\invphi}
\path (\ver) ++(\angle:\len) coordinate (\namex);
\ifnum#5=1 % anticlockwise or clockwise
\pgfmathsetmacro{\newanglea}{mod(\angle-144,360)}
\pgfmathsetmacro{\newangleb}{mod(\angle-36,360)}
\penrosedart{\n}{\namex}{\newanglea}{\newlen}{1}
\penrosekite{\n}{\ver}{\newangleb}{\newlen}{0}
\else
\pgfmathtruncatemacro{\newanglea}{mod(\angle+144,360)}
\pgfmathtruncatemacro{\newangleb}{mod(\angle+36,360)}
\penrosedart{\n}{\namex}{\newanglea}{\newlen}{0}
\penrosekite{\n}{\ver}{\newangleb}{\newlen}{1}
\fi
}
\fi
}


The second part provides four styles to use Penrose tilings as fill pattern of arbitrary path:

\newcommand\setveclength[5]{%
%\typeout{-#1-#2-#3-#4-}%
\pgfpointanchor{#2}{#3}
\pgfgetlastxy{\penrosexa}{\penroseya}
\pgfpointanchor{#4}{#5}
\pgfgetlastxy{\penrosexb}{\penroseyb}
\pgfmathparse{veclen(\penrosexb-\penrosexa,\penroseyb-\penroseya)}
\edef#1{\pgfmathresult}
}

\tikzset{
semipenrose sym fill/.style={
path picture={
\setveclength{\mylen}%
{path picture bounding box}{center}%
{path picture bounding box}{north west}
\pgfmathsetmacro{\len}{1.17*\mylen}
\begin{scope}[shift={(path picture bounding box.center)}]
\foreach \level in {0,...,4}{
\begin{scope}[rotate=\level*72+9]
\coordinate (a) at (0,0);
\penrosesemikite{#1}{a}{0}{\len pt}{0}
\penrosesemikite{#1}{a}{0}{\len pt}{1}
\end{scope}
}
\end{scope}
}
},
semipenrose fill/.style={
path picture={
\setveclength{\mylen}%
{path picture bounding box}{center}%
{path picture bounding box}{west}
\pgfmathsetmacro{\len}{1.33*\mylen}
\begin{scope}[shift={(path picture bounding box.center)},rotate=9]
\coordinate (a) at (-\len pt,0);
\path (a) +(36:2*\len pt) coordinate (b);
\path (a) +(-36:2*\len pt) coordinate (c);
\penrosesemidart{#1}{b}{36-180}{2*\len pt}{1}
\penrosesemikite{#1}{a}{0}{2*\len pt}{0}
\penrosesemikite{#1}{a}{0}{2*\len pt}{1}
\penrosesemidart{#1}{c}{180-36}{2*\len pt}{0}
\end{scope}
}
},
penrose sym fill/.style={
path picture={
\setveclength{\mylen}%
{path picture bounding box}{center}%
{path picture bounding box}{north west}
\pgfmathsetmacro{\len}{1.23*\mylen}
\begin{scope}[shift={(path picture bounding box.center)}]
\foreach \level in {0,...,4}{
\begin{scope}[rotate=\level*72+9]
\coordinate (a) at (0,0);
\penrosekite{#1}{a}{18}{\len pt}{0}
\penrosekite{#1}{a}{18}{\len pt}{1}
\end{scope}
}
\end{scope}
}
},
penrose fill/.style={
path picture={
\setveclength{\mylen}%
{path picture bounding box}{center}%
{path picture bounding box}{west}
\pgfmathsetmacro{\len}{2.38*\mylen}
\begin{scope}[shift={(path picture bounding box.center)},rotate=9]
\coordinate (a) at (-\len pt,0);
\path (a) +(36:2*\len pt) coordinate (b);
\path (a) +(-36:2*\len pt) coordinate (c);
\penrosedart{#1}{b}{36-180}{2*\len pt}{1}
\penrosekite{#1}{a}{0}{2*\len pt}{0}
\penrosekite{#1}{a}{0}{2*\len pt}{1}
\penrosedart{#1}{c}{180-36}{2*\len pt}{0}
\end{scope}
}
},
}


...then some examples.

First example (with default values):

\usetikzlibrary{shapes.arrows}
\pgfmathsetlengthmacro{\len}{4cm}
\pgfmathtruncatemacro{\recurs}{5}
\begin{document}
\begin{tikzpicture}
\tikzset{
gray arrow/.style={
fill=gray,minimum height=.5cm,rotate=-90,
single arrow,single arrow head extend=1mm,
},
}
% explanations of building process
\begin{scope}
\path (-4cm,0)   coordinate (a)
+(.75cm,-1.25cm) coordinate (arr)
++(0,-2.5cm)     coordinate (b);
\penrosesemikite{0}{a}{0}{1.5cm}{0}
\penrosesemikite{1}{b}{0}{1.5cm}{0}
\node[gray arrow] at (arr){};

\path (-2cm,0)   coordinate (a)
+(.75cm,-1.25cm) coordinate (arr)
++(0,-2.5cm)     coordinate (b);
\penrosesemikite{0}{a}{0}{1.5cm}{1}
\penrosesemikite{1}{b}{0}{1.5cm}{1}
\node[gray arrow] at (arr){};

\path (0cm,0)    coordinate (a)
+(.75cm,-1.25cm) coordinate (arr)
++(0,-2.5cm)     coordinate (b);
\penrosesemidart{0}{a}{0}{1.5cm}{0}
\penrosesemidart{1}{b}{0}{1.5cm}{0}
\node[gray arrow] at (arr){};

\path (2cm,0)    coordinate (a)
+(.75cm,-1.25cm) coordinate (arr)
++(0,-2.5cm)     coordinate (b);
\penrosesemidart{0}{a}{0}{1.5cm}{1}
\penrosesemidart{1}{b}{0}{1.5cm}{1}
\node[gray arrow] at (arr){};
\end{scope}
% example of semidarts and semikites
\begin{scope}[yshift=-2*\len]
\foreach \level in {0,...,4}{
\begin{scope}[rotate=\level*72]
\coordinate (a) at (0,0);
\penrosesemikite{\recurs}{a}{0}{\len}{0}
\penrosesemikite{\recurs}{a}{0}{\len}{1}
\end{scope}
}
\end{scope}
% explanations of building process
\begin{scope}[yshift=-3.3*\len]
\path (-3cm,0)   coordinate (a)
+(.75cm,-1.25cm) coordinate (arr)
++(0,-2.5cm)     coordinate (b);
\penrosesemikite{0}{a}{0}{1.5cm}{1}
\penrosesemikite{0}{a}{0}{1.5cm}{0}
\penrosekite{0}{b}{0}{1.5cm}{1}
\penrosekite{0}{b}{0}{1.5cm}{0}
\node[gray arrow] at (arr){};

\path (1cm,0)    coordinate (a)
+(.75cm,-1.25cm) coordinate (arr)
++(0,-2.5cm)     coordinate (b);
\penrosesemidart{0}{a}{36}{1.5cm}{1}
\penrosesemidart{0}{a}{-36}{1.5cm}{0}
\penrosedart{0}{b}{36}{1.5cm}{1}
\penrosedart{0}{b}{-36}{1.5cm}{0}
\node[gray arrow] at (arr){};
\end{scope}
% example of darts and kites
\begin{scope}[yshift=-5.2*\len]
\foreach \level in {0,...,4}{
\begin{scope}[rotate=\level*72]
\coordinate (a) at (0,0);
\penrosekite{\recurs}{a}{0}{\len}{0}
\penrosekite{\recurs}{a}{0}{\len}{1}
\end{scope}
}
\end{scope}
\end{tikzpicture}
\end{document}


The same example by appending the following lines :

  \tikzset{
% style for borders
line/.style={draw=white,rounded corners=0pt},
% styles for semikites and semidarts
penrose clockwise semikite/.style={fill=orange,line},
penrose anticlockwise semikite/.style={fill=orange!50!black,line},
penrose clockwise semidart/.style={fill=cyan!80,line},
penrose anticlockwise semidart/.style={fill=cyan!50,line},
% styles for kites and darts
penrose kite/.style={fill=red!75!black,line},
penrose dart/.style={fill=olive!75!white,line},
}


Third example with shape variations (by appending the following lines):

  % set the three paths (and the three reverse paths)
\pgfmathtruncatemacro{\defang}{36}
\tikzset{
common/.style={relative,looseness=1},
penrose path 1/.style={out=\defang,in=180-\defang,common},
penrose path 2/.style={out=\defang,in=180-\defang,common},
penrose path 3/.style={out=-\defang,in=180+\defang,common},
penrose rev path 1/.style={out=-\defang,in=180+\defang,common},
penrose rev path 2/.style={out=-\defang,in=180+\defang,common},
penrose rev path 3/.style={out=\defang,in=180-\defang,common},
}


Last example: using Penrose tiling as pattern.

\begin{document}
\begin{tikzpicture}
% some colors
\tikzset{
penrose line/.style={draw=white,line join=round,
line width=.1pt,rounded corners=2pt},
penrose kite/.style={left color=blue,right color=cyan,penrose line},
penrose dart/.style={left color=yellow,right color=red,penrose line},
}
\begin{scope}
% four styles exists: 'penrose fill', 'penrose sym fill',
% 'semipenrose fill' and 'semipenrose sym fill'.
% (argument is depth of recursion)
\path[penrose fill=7,rounded corners=0mm]
(0,.2) -- (4,0) -- (3,3) -- (2,2) -- (1,2) -- cycle;
\end{scope}
\end{tikzpicture}
\end{document}


-
Is that really a penrose tiling? Interesing nonetheless. – Fritz Jun 29 '12 at 6:30
@Fritz Each of the ten triangles are a Penrose tiling. If you are in doubt, follow the first link I gave. – Paul Gaborit Jun 29 '12 at 6:35
Great addition!! Do you think that it can be transformed into a custom fill pattern as in this one : tex.stackexchange.com/questions/54358/… ? Then Herbert's answer is truly replicated. By the way here is an interesting lecture from Peter Lu if you want to kill time: Harvard Colloquium Lecture – percusse Jun 30 '12 at 18:24
@percusse: Good question! A fill pattern (as defined by TikZ/pgf) is periodic. Penrose tiling is non-periodic. How to transform a non-periodic tiling into a periodic pattern ? – Paul Gaborit Jun 30 '12 at 19:37
Fantastic. I hope this finds its way to the official version! – percusse Jul 16 '12 at 23:35

run with pdflatex -shell-escape or pdflatex -enable-write18 (for Windows)

\documentclass{article}
\usepackage[pdf]{pstricks}
\begin{document}

\begin{pspicture}(10,8)
\pspolygon[fillstyle=penrose](0,4)(5,8)(10,4)
\pspolygon[fillstyle=penrose,psscale=0.2](0,0)(5,4)(10,0)
\end{pspicture}

\begin{pspicture}(10,8)
\pspolygon[fillstyle=penroseA,hatchcolor=white](0,4)(5,8)(10,4)
\pspolygon[fillstyle=penroseA,psscale=0.5,
kitecolor=yellow,dartcolor=cyan,hatchcolor=blue](0,0)(5,4)(10,0)
\end{pspicture}
\end{document}


for the fillstyle=penroseA it needs the current pstricks.tex and pstricks.pro from http://texnik.dante.de/

-
What pstricks documentation should I read to learn more? – Paul Gaborit Jun 30 '12 at 21:45
May be a bug with \pspolygon[fillstyle=penrose,psscale=0.2](0,0)(0,15)(15,15)(15,0)? – Paul Gaborit Jun 30 '12 at 21:54
you need the pstricks.tex and pstricks.pro from texnik.dante.de The example code can be found in texnik.dante.de/doc/generic/pstricks/pst-news12.pdf With the fillstyle penrose an extremely fast algoithm is used the reason why it can be a problem with small scaling values because the predefined area then can be smaller than the clipping area. However, I'll improve the code. It doesn't happened with the fill style penroseA which uses an other algorithm. – Herbert Jul 2 '12 at 9:11

This is my first attempt with TikZ. I try to make this : Penrose_tiling(P1). I agree with Herbert that the better method is to use a recursion but for the moment, I don't know how to begin a recursion in this case. So here I try only to reproduce the drawing that you can see in the link.

version 7

Remarks :

1) Now with the same methods, it's easy to get the complete figure given in the link.

2) Now it's interesting to find another way ...

3) I changed some names for options like penta instead of hexa. I added the green stars surrounded by five pentagons. I added the code for the little part at the end of my answer.

Some explanations. First I draw a pentagone (s) then I draw inside (s) five pentagons. I used \l=0.382 cm because I have not had the courage to make an effort to calculate the ratio between the lengths of pentagons ( but it's not a real great problem).

\documentclass{scrartcl}
\usepackage[dvipsnames]{xcolor}
\usepackage{tikz}
\usetikzlibrary{shapes}

\begin{document}
\def\l{0.382cm}

\begin{tikzpicture} [scale=2,
transform shape,
penta/.style= {shape                 =  regular polygon,
regular polygon sides = 5,
minimum size          = #1,
inner sep             = 0,
outer sep             = 0,
anchor                = south,
fill                  = lightgray}]
\node[penta=1cm,fill=yellow] (s) {};
\foreach \i in {1,...,5} {\node[draw,penta=\l,anchor=corner \i]  at (s.corner \i) {};}
\node[penta=\l,anchor=center,fill=MidnightBlue,rotate=36]  at (s.center) {};

\begin{scope}[rotate=108,sub penta/.style= {draw,penta=\l,anchor=corner \j}]
\foreach \i in {1,...,5}{%
\node[penta=1cm,fill=yellow,anchor=corner \i] (s\i) at (s.corner \i){};
\foreach \j in {1,...,5}{%
\pgfmathtruncatemacro\k{mod(\i,5)+1}
\ifnum\j=\i \tikzset{sub penta/.append style={fill=red}}         \fi
\ifnum\j=\k \tikzset{sub penta/.append style={fill=red}}         \fi
\node[sub penta] (s\i\j) at (s\i.corner \j){};
}
\node[penta=\l,anchor=center,fill=MidnightBlue,rotate=36]  at (s\i.center) {};
\pgfmathtruncatemacro\ii{mod(\i+1,5)+1}
\pgfmathtruncatemacro\iii{mod(\i+3,5)+1}
\node[penta=\l,anchor=corner \ii,fill=red,rotate=36,draw] (ss\i)  at (s\i.corner \iii) {};
}
\foreach \i in {1,...,5}{%
\pgfmathtruncatemacro\ii{mod(\i,5)+1}
\pgfmathtruncatemacro\j{mod(\i+1,5)+1}
\pgfmathtruncatemacro\k{mod(\i+2,5)+1}
\pgfmathtruncatemacro\h{mod(\i+2,5)+1}
\pgfmathtruncatemacro\l{mod(\i+3,5)+1}
\fill[MidnightBlue!40,draw=black] (s.corner \i)
-- (s\i\i.corner \l)
-- (s\i\i.corner \k)
-- (ss\i.corner \ii)
-- (ss\i.corner \i)
-- (s\ii\j.corner \l)
-- (s\ii\j.corner \h)
-- cycle;
}
\foreach \i in {1,...,5}{%
\pgfmathtruncatemacro\j{mod(\i+2,5)+1}
\node[penta=1cm,fill=yellow,anchor=corner \i,rotate=-36] (t\i) at (s\i\j.corner \j) {t};
\node[penta=1cm,fill=yellow,anchor=corner \i,rotate=108] (u\i) at (s\i\j.corner \j) {};
\foreach \k in {1,...,5} {%
\node[draw,penta=\l,anchor=corner \k,rotate=-36,fill=red] (t\i\k)  at (t\i.corner \k) {};}
\foreach \k in {1,...,5} {%
\node[draw,penta=\l,anchor=corner \k,rotate=108,fill=red]
(u\i\k) at  (u\i.corner \k) {};}
\node[penta=\l,anchor=center,fill=MidnightBlue]  at (t\i.center) {};
\node[penta=\l,anchor=center,fill=MidnightBlue]  at (u\i.center) {};
}
\foreach \i in {1,...,5} {%
\pgfmathtruncatemacro\j{mod(\i+3,5)+1}
\node[sub penta,fill=lightgray,anchor=center,rotate=36]  at (t\i\j){};
\node[sub penta,fill=lightgray,anchor=center,rotate=36]  at (u\j\i){};
}

\foreach \i in {1,...,5} {%
\pgfmathtruncatemacro\j{mod(\i+2,5)+1}
\pgfmathtruncatemacro\k{mod(\i+3,5)+1}
\pgfmathtruncatemacro\h{mod(\i+1,5)+1}
\pgfmathtruncatemacro\l{mod(\i,5)+1}
\fill[green] (ss\i.corner \h)  -- (t\l\h.corner \k) --
(u\i\j.corner \i) -- (ss\i.corner \k)  --
(u\i\j.corner \j) -- cycle;
}
\end{scope}
\foreach \j in {1,...,5}{%
\pgfmathtruncatemacro\k{mod(\j+1,5)+1}
\begin{scope}[rotate=108]
\node[penta=1cm,fill=yellow,anchor=corner \k] (xs\j) at (u\j.corner \k) {};
\foreach \i in {1,...,5} {\node[draw,penta=\l,anchor=corner \i]  at
(xs\j.corner \i) {};}
\node[penta=\l,anchor=center,fill=MidnightBlue,rotate=36]  at (xs\j.center) {};
\end{scope}
}
\foreach \i in {1,...,5}{%
\pgfmathtruncatemacro\j{mod(\i,5)+1}
\pgfmathtruncatemacro\k{mod(\i+1,5)+1} \pgfmathtruncatemacro\h{mod(\i+2,5)+1}
\begin{scope}[sub penta/.style= {draw,penta=\l},rotate=36+(\i-1)*72]
\node[sub penta,red,anchor=corner 4,draw=black] (p1) at (t\j\i.corner \j) {};
\node[sub penta,red,anchor=corner 3,draw=black] (p2) at (p1.corner 5) {};
\node[sub penta,red,anchor=corner 4,draw=black] (p3) at (p2.corner 1) {};
\node[sub penta,red,anchor=corner 5,draw=black] (p4) at (p3.corner 2) {};
\node[sub penta,red,anchor=corner 1,draw=black] (p5) at (p4.corner 3) {};
\fill[green] (p1.corner 5) -- (p3.corner 2) -- (p5.corner 4) -- (p2.corner 1) --
(p4.corner 3) -- cycle;
\fill[MidnightBlue!40,draw=black] (p1.corner 3) -- (p1.corner 4) --
(t\j\i.corner \k)  --
(t\j\j.corner \i)  --
(t\j\j.corner \j) --
(u\j\j.corner \k)  -- (u\j\j.corner \h) -- cycle;
\end{scope}}
\end{tikzpicture}

\end{document}


Green star surrounded by five pentagons

   \begin{tikzpicture} [scale=2,
transform shape,
penta/.style= {shape                 =  regular polygon,
regular polygon sides = 5,
minimum size          = #1,
inner sep             = 0,
outer sep             = 0,
anchor                = south,
fill                  = lightgray}]
\begin{scope}[sub penta/.style= {draw,penta=\l}]
\node[sub penta,red,anchor=corner 4,draw=black] (p1)  {};
\node[sub penta,red,anchor=corner 3,draw=black] (p2) at (p1.corner 5) {};
\node[sub penta,red,anchor=corner 4,draw=black] (p3) at (p2.corner 1) {};
\node[sub penta,red,anchor=corner 5,draw=black] (p4) at (p3.corner 2) {};
\node[sub penta,red,anchor=corner 1,draw=black] (p5) at (p4.corner 3) {};
\fill[green] (p1.corner 5) -- (p3.corner 2) -- (p5.corner 4) --
(p2.corner 1) -- (p4.corner 3) -- cycle;
\end{scope}

\end{tikzpicture}


With

  \def\r{2.31}
\draw[shift=(s.center),clip] (-54:\r) -- (18:\r) -- (90:\r) -- (162:\r) -- (234:\r) -- cycle;


we get :

-
without a recursion you don't get the correct Penrose tiling – Herbert Jun 28 '12 at 12:19
I agree that a recursion is the better way but I think that it's possible to reproduce Penrose_Tiling_(P1).svg en.wikipedia.org/wiki/File%3aPenrose_Tiling_%28P1%29.svg . The only difficulty is to add the colors. Is it possible to make this drawing with pstricks ? – Alain Matthes Jun 28 '12 at 12:41

Altermundus' lovely green star, like much of his code, can do with a simple loop.

\documentclass{scrartcl}
\usepackage[dvipsnames]{xcolor}
\usepackage{tikz}
\usetikzlibrary{shapes}
\def\ydo#1,#2,#3,#4;{%
\ifx\ydo#1\else
\noexpand\node[sub penta,red,anchor=corner #1,draw=black]%
(p#2)\if0#3\else at(p#3.corner #4)\fi{};
\expandafter\ydo
\fi
}
\begin{document}
\def\alterl{0.382cm}
\begin{tikzpicture}[
scale=2,transform shape,
penta/.style={%
shape=regular polygon,regular polygon sides=5,minimum size=#1,
inner sep=0pt,outer sep=0pt,anchor=south,fill=lightgray
}
]
\begin{scope}[sub penta/.style={draw,penta=\alterl}]
\pgfextra{%
\edef\x{\ydo 4,1,0,0;3,2,1,5;4,3,2,1;5,4,3,2;1,5,4,3;\ydo,,,;}\x
}%
\fill[green](p1.corner 5)--(p3.corner 2)--(p5.corner 4)
--(p2.corner 1)--(p4.corner 3)--cycle;
\end{scope}
\end{tikzpicture}
\end{document}


-