12

I'd like to draw attention to particular instances of self-similarity in Sierpinski's triangle in LaTeX. Moreover, I would like to do so in a way that is customisable; that is, so that I can focus on different triangles.

I would be happy with something like this:

enter image description here,

where I can change the red sub-triangle if necessary.

Something like this would be ideal though:

enter image description here,

with the same ease of changing the red sub-triangle.


EDIT: If I may I'd like to ask even more of your ability. I'd like to do something like this too:

enter image description here,

where the red and the blue triangles could be changed (by a novice like me).


Here's the code for the picture I've been painting on. It's not mine! See some of the first comments below.

\documentclass[tikz]{standalone}
\usetikzlibrary{shapes.geometric}
\begin{document}
\begin{tikzpicture}[
main tri/.style={isosceles triangle,fill,isosceles triangle apex angle=60,
                 rotate=90,inner sep=0,outer sep=0},
filler tri/.style={isosceles triangle,fill=white,rotate=-90,isosceles triangle apex angle=60,
                 inner sep=0,outer sep=0}]
\node[minimum height=2cm,main tri] (a) {};
%==================
\node[minimum height=1cm,filler tri] (b) at (a.center){};
%==================
\node[minimum height=0.5cm,filler tri,anchor=right corner] (c1) at (b.left side){};
\node[minimum height=0.5cm,filler tri,anchor=left corner] (c2) at (b.right side){};
\node[minimum height=0.5cm,filler tri,anchor=apex] (c3) at (b.west){};
% ===================
\foreach \x in {1,2,3}{
\node[minimum height=0.25cm,filler tri,anchor=right corner] (d1\x) at (c\x.left side){};
\node[minimum height=0.25cm,filler tri,anchor=left corner] (d2\x) at (c\x.right side){};
\node[minimum height=0.25cm,filler tri,anchor=apex] (d3\x) at (c\x.west){};
}
% ===================
\foreach \x in {1,2,3}{
    \foreach \y in {1,2,3}{
    \node[minimum height=0.125cm,filler tri,anchor=right corner] (e1\x\y) at (d\x\y.left side){};
    \node[minimum height=0.125cm,filler tri,anchor=left corner] (e2\x\y) at (d\x\y.right side){};
    \node[minimum height=0.125cm,filler tri,anchor=apex] (e3\x\y) at (d\x\y.west){};
    }
}

\end{tikzpicture}
\end{document}

I'm afraid I don't know where to begin.

Shaun
  • 293

1 Answers1

12

With both pdflatex or lualatex :

Edit One can divide the number of iteration in each loop by 2.

enter image description here

\documentclass[margin=3pt]{standalone}
\usepackage{tikz,xparse}
\usetikzlibrary{calc}

\usepackage{ifluatex}

\ifluatex
    \usepackage{fontspec,luacode}
    \directlua{dofile("Sierpinski.lua")}
    \newcommand{\Sierpinski}[1]{%
        \directlua{Sierpinski(#1)}
    }
\else
    \newcommand{\Sierpinski}[1]{%
    \foreach \l in {1,...,#1} {%
        \pgfmathsetmacro{\Tr}{5/(2^(\l))}

        \pgfmathparse{2^\l - 1}
        \ifnum\l=1
            \fill [white] ($(60:\Tr)+(0,0)$) -- ++(0:\Tr) -- ++(-120:\Tr) -- cycle;")
        \else
        \foreach \i in {1,3,...,\pgfmathresult} {%
            \pgfmathparse{2^\l - \i - 1}
            \foreach \j in {0,...,\pgfmathresult} {%
            \fill [white] ($(60:\i*\Tr)+(\j*\Tr,0)$) -- ++(0:\Tr) -- ++(-120:\Tr) -- cycle;")
            }
        }
        \fi
    }
    }   
\fi




\NewDocumentCommand{\Triangle}{%
    O{S}    % node prefix
    m   % color
    m   % level
    mm  % coordinates
    }{%
    \pgfmathsetmacro{\Tr}{5/2^#3}
    \fill[#2] ($(60:#4*\Tr)+(#5*\Tr,0)$) coordinate (#10)
        -- ++(0:\Tr) coordinate (#11)
        -- ++(120:\Tr) coordinate (#12)
        -- cycle;")
}

\begin{document}

\begin{tikzpicture}

\Triangle{black}{0}{0}{0}
\Triangle[R]{green}{1}{0}{1}
\Triangle[B]{blue}{2}{2}{0}

\Sierpinski{5}

\draw[-stealth,red] (R0) to [out=100, in=-20] (B0) ;
\draw[-stealth,red] (R1) to [out=100, in=-20] (B1) ;
\draw[-stealth,red] (R2) to [out=100, in=-20] (B2) ;

\end{tikzpicture}
\end{document}

And Sierpinski.lua file :

tp = tex.print



function Sierpinski (level)

local s = 5     -- size

--tp("\\fill [black] (0,0) -- ++(0:"..s..") -- ++(120:"..s..") -- cycle;")

for l = 1,level
do
    s = s / 2
    for i = 1,2^l - 1,2
    do
        for j = 0,2^l - i -1,2
        do
            tp("\\fill [white] ($(60:"..i*s..")+("..j*s..",0)$) -- ++(0:"..s..") -- ++(-120:"..s..") -- cycle;")
        end
    end
end

end
Tarass
  • 16,912