How to Draw a Tree of Grids Using TikZ-PGF

graphsgridstikz-pgftikz-trees

I need to draw a game tree that is similar to the image below. Is there any way to do this using the Tikz package so that the grids can simply be added as nodes?

Tree of grids

Best Answer

TikZ doesn't have a node shape of this form. But since it is just a rectangle with some added lines, it is relatively straightforward to define (once knowing how to define shapes).

\documentclass{article}
\usepackage{tikz}
\usetikzlibrary{positioning}

\makeatletter
\pgfkeys{/pgf/grid lines/.initial=2}

\pgfdeclareshape{grid}{
    % inherit most things from the rectangle shape
    \inheritsavedanchors[from=rectangle]
    \inheritanchorborder[from=rectangle]
    \inheritanchor[from=rectangle]{center}
    \inheritanchor[from=rectangle]{north}
    \inheritanchor[from=rectangle]{south}
    \inheritanchor[from=rectangle]{west}
    \inheritanchor[from=rectangle]{east}
    \inheritanchor[from=rectangle]{south east}
    \inheritanchor[from=rectangle]{south west}
    \inheritanchor[from=rectangle]{north east}
    \inheritanchor[from=rectangle]{north west}
    \inheritbackgroundpath[from=rectangle]

    \savedmacro\lines{%
        \pgfmathtruncatemacro\lines{\pgfkeysvalueof{/pgf/grid lines}}%
    }

    % draw the grid
    \beforebackgroundpath{
        % store lower right in xa/ya and upper right in xb/yb
        \southwest \pgf@xa=\pgf@x \pgf@ya=\pgf@y
        \northeast \pgf@xb=\pgf@x \pgf@yb=\pgf@y

        % compute distance between the lines
        \pgfmathparse{(\the\pgf@xb-\the\pgf@xa)/(\lines + 1)}
        \pgf@xc=\pgfmathresult pt
        \pgfmathparse{(\the\pgf@yb-\the\pgf@ya)/(\lines + 1)}
        \pgf@yc=\pgfmathresult pt

        % draw grid
        \c@pgf@counta=0
        \c@pgf@countb\lines\relax
        \pgf@xb=\pgf@xa
        \advance\pgf@xb\pgf@xc\relax
        \pgfmathloop
            \ifnum\c@pgf@counta<\c@pgf@countb
                \pgfpathmoveto{\pgfpoint{\pgf@xb}{\pgf@ya}}
                \pgfpathlineto{\pgfpoint{\pgf@xb}{\pgf@yb}}
                \advance\c@pgf@counta 1\relax
                \advance\pgf@xb\pgf@xc\relax
        \repeatpgfmathloop
        % set \pgf@xb to the right side
        \c@pgf@counta=0
        \pgf@yb=\pgf@ya
        \advance\pgf@yb\pgf@yc\relax
        \pgfmathloop
            \ifnum\c@pgf@counta<\c@pgf@countb
                \pgfpathmoveto{\pgfpoint{\pgf@xa}{\pgf@yb}}
                \pgfpathlineto{\pgfpoint{\pgf@xb}{\pgf@yb}}
                \advance\c@pgf@counta 1\relax
                \advance\pgf@yb\pgf@yc\relax
        \repeatpgfmathloop
        \pgfusepath{stroke}
    }

    % add anchors for vertices (intersections of grid lines)
    % and center points (centers of the small rectangles).
    %
    % vertex anchors are simply called 'x y' with '0 0' being the lower left
    % vertex.
    % center anchors are called 'center x y' with 'center 1 1' being the center
    % of the lower left rectangle
    \pgfutil@g@addto@macro\pgf@sh@s@grid{%
        \c@pgf@counta\lines
        \advance\c@pgf@counta 1\relax
        \pgfmathloop\ifnum\c@pgf@counta>-1
            {% group to allow nesting of loops
                \c@pgf@countb\lines
                \advance\c@pgf@countb 1\relax
                \pgfmathloop\ifnum\c@pgf@countb>-1
                    \pgfutil@ifundefined{pgf@anchor@grid@\the\c@pgf@counta\space\the\c@pgf@countb}{%
                        % need to use xdef, so that \c@pgf@counta/b are expanded
                        % vertices
                        \expandafter\xdef\csname pgf@anchor@grid@\the\c@pgf@counta\space\the\c@pgf@countb\endcsname{%
                            \noexpand\southwest \noexpand\pgf@xa=\noexpand\pgf@x \noexpand\pgf@ya=\noexpand\pgf@y
                            \noexpand\northeast \noexpand\pgf@xb=\noexpand\pgf@x \noexpand\pgf@yb=\noexpand\pgf@y
                            \noexpand\pgfmathparse{(\noexpand\the\noexpand\pgf@xb-\noexpand\the\noexpand\pgf@xa)/(\noexpand\lines + 1)*\the\c@pgf@counta}
                            \noexpand\pgf@x=\noexpand\pgf@xa\noexpand\relax
                            \noexpand\advance\noexpand\pgf@x\noexpand\pgfmathresult pt\noexpand\relax
                            \noexpand\pgfmathparse{(\noexpand\the\noexpand\pgf@yb-\noexpand\the\noexpand\pgf@ya)/(\noexpand\lines + 1)*\the\c@pgf@countb}
                            \noexpand\pgf@y=\noexpand\pgf@ya\noexpand\relax
                            \noexpand\advance\noexpand\pgf@y\noexpand\pgfmathresult pt\noexpand\relax
                        }
                        % centers
                        \expandafter\xdef\csname pgf@anchor@grid@center\space\the\c@pgf@counta\space\the\c@pgf@countb\endcsname{%
                            \noexpand\southwest \noexpand\pgf@xa=\noexpand\pgf@x \noexpand\pgf@ya=\noexpand\pgf@y
                            \noexpand\northeast \noexpand\pgf@xb=\noexpand\pgf@x \noexpand\pgf@yb=\noexpand\pgf@y
                            \noexpand\pgfmathparse{(\noexpand\the\noexpand\pgf@xb-\noexpand\the\noexpand\pgf@xa)/(2*(\noexpand\lines + 1))*(2*\the\c@pgf@counta-1)}
                            \noexpand\pgf@x=\noexpand\pgf@xa\noexpand\relax
                            \noexpand\advance\noexpand\pgf@x\noexpand\pgfmathresult pt\noexpand\relax
                            \noexpand\pgfmathparse{(\noexpand\the\noexpand\pgf@yb-\noexpand\the\noexpand\pgf@ya)/(2*(\noexpand\lines + 1))*(2*\the\c@pgf@countb-1)}
                            \noexpand\pgf@y=\noexpand\pgf@ya\noexpand\relax
                            \noexpand\advance\noexpand\pgf@y\noexpand\pgfmathresult pt\noexpand\relax
                        }
                    }{\c@pgf@countb0\relax}
                    \advance\c@pgf@countb-1\relax
                \repeatpgfmathloop
            }
            \advance\c@pgf@counta-1\relax
        \repeatpgfmathloop
    }
}
\makeatother

\begin{document}
\begin{tikzpicture}[
        mygrid/.style={
            draw,
            grid,
            grid lines=2,
            minimum width=2cm,
            minimum height=2cm}
        ]
    \node [mygrid,fill=red] (A) at (0,0) {};
    \node [mygrid,below=0.66cm of A] (B) {};
    \node [mygrid,right=0.66cm of B] (C) {};
    \draw[thick] (A) -- (B);
    \draw[thick] (A.south) -- (C.north);
    \node at (A.0 0) {(0,0)};
    \node at (A.1 3) {(1,3)};
    \node at (A.2 2) {(2,2)};
    \node at (A.3 3) {(3,3)};
    \node at (B.1 1) {(1,1)};
    \node at (B.center 1 3) {(1,3)};
    \node at (B.center 2 2) {(2,2)};
    \node at (B.center 3 3) {(3,3)};
    \fill[blue] (C.1 1) rectangle (C.2 2);
\end{tikzpicture}
\end{document}

The above code defines a node shape named grid that is basically a rectangle with a grid. It also defines a grid lines key (with default value 2) to set the number of grid lines inside the rectangle.

result of code above

Update: I added some useful anchors.

Related Question