summaryrefslogtreecommitdiff
path: root/macros/latex/contrib/wargame/source/hex/shape.dtx
diff options
context:
space:
mode:
Diffstat (limited to 'macros/latex/contrib/wargame/source/hex/shape.dtx')
-rw-r--r--macros/latex/contrib/wargame/source/hex/shape.dtx368
1 files changed, 368 insertions, 0 deletions
diff --git a/macros/latex/contrib/wargame/source/hex/shape.dtx b/macros/latex/contrib/wargame/source/hex/shape.dtx
new file mode 100644
index 0000000000..0d31da837f
--- /dev/null
+++ b/macros/latex/contrib/wargame/source/hex/shape.dtx
@@ -0,0 +1,368 @@
+% \iffalse
+% --------------------------------------------------------------------
+%<*hex>
+% \fi
+%
+% \subsubsection{Hexes}
+% \label{sec:impl:hex:hex}
+%
+% In this part, we make macros etc. for the hexes.
+%
+% A hex shape. We make a node of this shape if we are to give a name
+% to the hex added. We add a bunch of anchors to it so we may easily
+% refer to it. This is also where we actual fill stuff into the hex,
+% such as terrain and so on.
+%
+% \begin{macrocode}
+\hex@dbg{5}{Base vertex: \hex@xx,\hex@yy}
+\hex@dbg{5}{Base edges: \hex@e@xx,\hex@e@yy}
+\pgfdeclareshape{hex/hex}{%
+ \saveddimen\radius{\pgf@x=\hex@radius}
+ \savedanchor{\east}{ \pgfqpoint{ \hex@radius}{0cm}}
+ \savedanchor{\west}{ \pgfqpoint{-\hex@radius}{0cm}}
+ \savedanchor{\northeast}{ \pgfqpoint{ \hex@dx}{ \hex@dy}}
+ \savedanchor{\northwest}{ \pgfqpoint{-\hex@dx}{ \hex@dy}}
+ \savedanchor{\southwest}{ \pgfqpoint{-\hex@dx}{-\hex@dy}}
+ \savedanchor{\southeast}{ \pgfqpoint{ \hex@dx}{-\hex@dy}}
+ \savedanchor{\northedge}{ \pgfqpoint{ 0cm}{ \hex@dy}}
+ \savedanchor{\southedge}{ \pgfqpoint{ 0cm}{-\hex@dy}}
+ \savedanchor{\northeastedge}{\pgfqpoint{ \hex@e@dx}{ \hex@e@dy}}
+ \savedanchor{\northwestedge}{\pgfqpoint{-\hex@e@dx}{ \hex@e@dy}}
+ \savedanchor{\southwestedge}{\pgfqpoint{-\hex@e@dx}{-\hex@e@dy}}
+ \savedanchor{\southeastedge}{\pgfqpoint{ \hex@e@dx}{-\hex@e@dy}}
+ \savedmacro\init{%
+ \def\hexpath{%
+ \pgfpathmoveto{\east}%
+ \pgfpathlineto{\northeast}%
+ \pgfpathlineto{\northwest}%
+ \pgfpathlineto{\west}%
+ \pgfpathlineto{\southwest}%
+ \pgfpathlineto{\southeast}%
+ \pgfpathclose}
+ }
+% \end{macrocode}
+%
+% These are the actual user callable anchors. We make anchors for
+% each vertex and mid points on each edge.
+%
+% \begin{macrocode}
+%%
+ \anchor{center}{ \pgfpointorigin}
+ \anchor{east}{ \east}
+ \anchor{west}{ \west}
+ \anchor{north east}{ \northeast}
+ \anchor{north west}{ \northwest}
+ \anchor{south west}{ \southwest}
+ \anchor{south east}{ \southeast}
+ \anchor{north edge}{ \northedge}
+ \anchor{south edge}{ \southedge}
+ \anchor{north east edge}{\northeastedge}
+ \anchor{north west edge}{\northwestedge}
+ \anchor{south west edge}{\southwestedge}
+ \anchor{south east edge}{\southeastedge}
+% \end{macrocode}
+%
+% Next we make some short hand aliases for each of these anchors.
+%
+% \begin{macrocode}
+ \anchor{E}{ \east}
+ \anchor{W}{ \west}
+ \anchor{NE}{ \northeast}
+ \anchor{NW}{ \northwest}
+ \anchor{SW}{ \southwest}
+ \anchor{SE}{ \southeast}
+ \anchor{N edge}{ \northedge}
+ \anchor{S edge}{ \southedge}
+ \anchor{NE edge}{\northeastedge}
+ \anchor{NW edge}{\northwestedge}
+ \anchor{SW edge}{\southwestedge}
+ \anchor{SE edge}{\southeastedge}
+% \end{macrocode}
+%
+% The next part is commented out because its not obvious we'll use
+% these.
+%
+% \begin{macrocode}
+ %%
+ \savedanchor{\chitnorth}{ \pgfqpoint{ 0cm}{ 0.6cm}}
+ \savedanchor{\chitsouth}{ \pgfqpoint{ 0cm}{ -0.6cm}}
+ \savedanchor{\chiteast}{ \pgfqpoint{ 0.6cm}{ 0cm}}
+ \savedanchor{\chitwest}{ \pgfqpoint{-0.6cm}{ 0cm}}
+ \savedanchor{\chitnortheast}{\pgfqpoint{ 0.6cm}{ 0.6cm}}
+ \savedanchor{\chitnorthwest}{\pgfqpoint{-0.6cm}{ 0.6cm}}
+ \savedanchor{\chitsouthwest}{\pgfqpoint{-0.6cm}{-0.6cm}}
+ \savedanchor{\chitsoutheast}{\pgfqpoint{ 0.6cm}{-0.6cm}}
+ %
+ \anchor{chit north}{\chitnorth}
+ \anchor{chit south}{\chitsouth}
+ \anchor{chit east}{\chiteast}
+ \anchor{chit west}{\chitwest}
+ \anchor{chit north east}{\chitnortheast}
+ \anchor{chit north west}{\chitnorthwest}
+ \anchor{chit south west}{\chitsouthwest}
+ \anchor{chit south east}{\chitsoutheast}
+ %
+ \anchor{chit N}{\chitnorth}
+ \anchor{chit S}{\chitsouth}
+ \anchor{chit E}{\chiteast}
+ \anchor{chit W}{\chitwest}
+ \anchor{chit NE}{\chitnortheast}
+ \anchor{chit NW}{\chitnorthwest}
+ \anchor{chit SW}{\chitsouthwest}
+ \anchor{chit SE}{\chitsoutheast}
+ %
+% \end{macrocode}
+%
+% The background path. This path may be drawn when the node is
+% drawn. However, we will do most of the work in the
+% \cs{behindbackgroundpath} which gets drawn \emph{after} this path.
+%
+% \begin{macrocode}
+ \backgroundpath{\init\hexpath}
+% \end{macrocode}
+%
+% The \emph{behind} background path, where we do most of the work.
+%
+% \begin{macrocode}
+ \behindforegroundpath{%
+ \hex@dbg{2}{Hex behind foreground path:
+ ^^JTerrain: `\meaning\hex@terrain'
+ ^^JRidges: `\meaning\hex@ridges'
+ ^^JTown: `\meaning\hex@town'
+ ^^JExtra clipped: `\meaning\hex@extra@clip'
+ ^^JLabel: `\meaning\hex@label'
+ ^^JExtra: `\meaning\hex@extra'
+ ^^JLast node name:`\meaning\tikzlastnode'
+ ^^JHex row: `\meaning\hex@row'
+ ^^JHex col: `\meaning\hex@col'
+ }%
+ \init%
+% \end{macrocode}
+%
+% We start a scope and clip to the hex path first.
+%
+% \begin{macrocode}
+ \scope%
+ \hexpath%
+ \pgfusepath{clip}%
+% \end{macrocode}
+%
+% Anything inside this scope is clipped to the hex path. The next
+% step is to see if we have a specified terrain for the hex.
+%
+% \begin{macrocode}
+ \@ifundefined{hex@terrain}{\let\hex@terrain\empty}{}%
+ \ifx\hex@terrain\empty\else\hex@do@terrain\fi%
+% \end{macrocode}
+%
+% This concludes the processing of the terrain of the hex. Next, we
+% must see if the user specified ridges.
+%
+% \begin{macrocode}
+ \@ifundefined{hex@ridges}{\let\hex@ridges\empty}{}%
+ \ifx\hex@ridges\empty\else\hex@do@ridges\fi%
+% \end{macrocode}
+%
+% This concludes the processing of the ridges of the hex. Next, we
+% should process any extra (clipped) stuff specified. The user may
+% pass options to each \spec{pic}ture by preceding it with
+% \oarg{options}.
+%
+% \begin{macrocode}
+ \@ifundefined{hex@extra@clip}{\let\hex@extra@clip\empty}{}
+ \ifx\hex@extra@clip\empty\else%
+ \hex@dbg{5}{Extra clipped: `\meaning\hex@extra'}
+ \pgfpointorigin\wg@tmpa=\pgf@x\wg@tmpb=\pgf@y%
+ \wg@pic@all{\hex@extra@clip}{}{\the\wg@tmpa,\the\wg@tmpb}{}%
+ \fi%
+% \end{macrocode}
+%
+% This concludes the extra stuff put in the hex. Next, we should
+% place the label is specified. Note, we may know the hex row and
+% column at this point, stored in \cs{hex@row} and \cs{hex@column},
+% respectively. We may want to name the generated node from these if
+% the user specified that option (perhaps use \cs{pgfnoderename} or
+% similar).
+%
+% \begin{macrocode}
+ \@ifundefined{hex@label}{\let\hex@label\empty}{}
+ \ifx\hex@label\empty\else\hex@do@label\fi%
+ \endscope%
+% \end{macrocode}
+%
+% This concludes the label processing, and stuff that should be
+% clipped to the hex shape. If the user specified a town, we can now
+% make that.
+%
+% \begin{macrocode}
+ \@ifundefined{hex@town}{\let\hex@town\empty}{}
+ \@ifundefined{hex@c@pic}{\let\hex@c@pic\empty}{}
+ \ifx\hex@town\empty\else\hex@do@town\fi%
+% \end{macrocode}
+%
+% We can now add extra (non-clipped) stuff. We assume that extra
+% stuff is \spec{pic}tures. The user may pass options to each
+% \spec{pic}ture by preceding it with \oarg{options}.
+%
+% \begin{macrocode}
+ \@ifundefined{hex@extra}{\let\hex@extra\empty}{}
+ \ifx\hex@extra\empty\else%
+ \hex@dbg{5}{Extra: `\meaning\hex@extra'}
+ \pgfpointorigin\wg@tmpa=\pgf@x\wg@tmpb=\pgf@y%
+ \wg@pic@all{\hex@extra}{}{\the\wg@tmpa,\the\wg@tmpb}{}%
+ \fi%
+ }
+}
+% \end{macrocode}
+%
+% \begin{HexKey*}{
+% /hex/terrain,
+% /hex/town,
+% /hex/label,
+% /hex/ridges,
+% /hex/extra,
+% /hex/extra clipped}
+%
+% Next, we set up the name space for hex keys. This is the top level
+% name space for hexes. Sub keys \spec{terrain}, \spec{ridges},
+% \spec{town}, \spec{extra}, \spec{label}, and \spec{extra clipped},
+% store their arguments in macros and we expand these later on. This
+% allows us to scope some of the keys given to those specific parts.
+%
+% Define keys for hexagon options. These are
+%
+% \begin{tabular}{|l|p{.7\linewidth}|}
+% \hline
+% \rowcolor{headbg}
+% {\color{headfg}\textbf{Name}}
+% & {\color{headfg}\textbf{Description}}\\
+% \hline
+% \spec{terrain} & Terrain\\
+% \spec{label} & Label on hex\\
+% \spec{town} & Town in hex. Optionally with a name\\
+% \spec{ridges} & Ridge markings on hex\\
+% \spec{extra} & More \\
+% \spec{extra clipped} & More clipped to hex\\
+% \hline
+% \end{tabular}
+%
+% \begin{macrocode}
+\tikzset{%
+ /hex/.search also={/tikz},%
+ /hex/.cd,%
+ terrain/.store in=\hex@terrain,%
+ ridges/.store in=\hex@ridges,%
+ town/.store in=\hex@town,%
+ extra/.store in=\hex@extra,%
+ label/.store in=\hex@label,%
+ extra clipped/.store in=\hex@extra@clip%
+}
+% \end{macrocode}
+% \end{HexKey*}
+%
+% \begin{TikzKey}{hex}
+% The next key is the real work horse of the show. Specifying the
+% \spec{hex} key to a node effectively creates a hex for us. Now,
+% there are some things we cannot do outright in the node shape
+% code. For example, we cannot set the name of the node created
+% from the shape code. Therefore, the use of \cs{hex} is often the
+% right choice.
+%
+% \begin{macrocode}
+\tikzset{%
+ hex/hex/.style={
+ transform shape,
+ anchor=center,
+ draw=pgfstrokecolor,
+ fill=none,
+ thick,
+ solid},
+ hex/.code={%
+ \hex@dbg{1}{=== Hex with options: `#1'}%
+ \pgfkeys{/tikz/transform shape,/tikz/shape=hex/hex}
+ \pgfkeys{/hex/.cd,/tikz/hex/hex,/tikz/every hex/.try,#1}}}
+% \end{macrocode}
+% \end{TikzKey}
+%
+% The first thing is to set the default graphics options. The key
+% \spec{every hex} can be set to hex options to be used for all hexes.
+% For example, if one want to label all hexes with an auto-generated
+% label, one can do
+%
+% \begin{Syntax}
+% \cs{tikzset}\{every hex/.style=\{label=\{auto=numbered\}\}\}
+% \end{Syntax}
+%
+% This, coupled with the \spec{hex/label is name} option allows us to
+% set up the board with really minimal effort. We can then use the
+% board coordinates when placing units, and other things.
+%
+%
+% Now we have set up these tools we can go on and define the user
+% facing macro.
+%
+% \begin{Macro}{\hex,\hex@,\hex@@}
+%
+% This will add a hex to the output graphics. Note, the macro
+% need not be followed by a semi-colon (\spec{;}).
+%
+% First argument is optional options.
+%
+% \begin{macrocode}
+\def\hex{%
+ \@ifnextchar[{\hex@}{\hex@[]}%]
+}
+% \end{macrocode}
+%
+% Second optional argument is the coordinates. These should be given
+% in the hex coordinate system.
+%
+% \begin{macrocode}
+\def\hex@[#1]{%
+ \@ifnextchar({\hex@@{#1}}{%
+ \hex@@{#1}(c=0,r=0)}%)
+}
+% \end{macrocode}
+%
+% Third argument is the name to be used.
+%
+% \begin{macrocode}
+\def\hex@@#1(#2){%
+ \@ifnextchar({\hex@@@{#1}{#2}}{\hex@@@{#1}{#2}()}%)
+}
+% \end{macrocode}
+%
+% Now for the real work-horse. First thing is to reset keys and parse
+% them out from the arguments.
+%
+% \begin{macrocode}
+% Third argument is name
+\def\hex@@@#1#2(#3){%
+ \node[hex={#1}] (tmp) at (hex cs:#2) {};%
+ \hex@dbg{8}{=== Label text: `\meaning\hex@l@text'}
+ \ifx|#3|\relax%
+ \@ifundefined{hex@l@text}{%
+ \hex@dbg{8}{=== Label text of hex (#2) not defined}%
+ \let\hex@l@text\empty%
+ }{}
+ \ifhex@label@is@name%
+ \hex@dbg{5}{=== Use label text of hex (#2) as name}%
+ \ifx\hex@l@text\@empty%
+ \hex@dbg{8}{=== Argh! Label text is empty! `\meaning\hex@l@text'}
+ \else%
+ \hex@dbg{3}{=== Renaming hex to label text `\hex@l@text'}
+ \pgfnoderename{\hex@l@text}{tmp}%
+ \fi%
+ \fi%
+ \else%
+ \hex@dbg{3}{=== Renaming hex to user defined name `#3'}%
+ \pgfnoderename{#3}{tmp}%
+ \fi%
+ \@ifnextchar;{\@gobble}{}%
+}
+% \end{macrocode}
+% \end{Macro}
+% \iffalse
+%</hex>
+% --------------------------------------------------------------------
+% \fi