Style sheet macros and variables
Style sheets can get very big. Two ways to save space are described here.
Macros are predefined pieces of the style sheet which can be referenced by name. You define macros in the <defs> section like this:
<defs> <macro id='minor-road-label'> <scale max='40000'> <label case='assume-title' color='dimgrey' font-size='75%,5pt,12pt' glow='white' glowWidth='7%,0.5pt' priority='-2' wrapLines='0'/> </scale> </macro> <macro id='standard-tunnel'> <scale max='75000'> <tunnel dashArray='1.5,1.5' fade='0.3'/> </scale> </macro> </defs>
and refer to them like this:
<condition exp='@feature_type="service road"'> <line border='dimgrey+white' borderWidth='8%,0.35pt,1pt' fill='white' width='5m@6000_10m@40000,0.3pt'/> <macro ref='minor-road-label'/> <macro color='lightgrey' ref='one-way-arrow'/> <macro ref='standard-bridge'/> <macro ref='grey-tunnel'/> </condition>
Macros can contain any valid XML, as long as it is balanced, which means each opening tag must have a matching closing tag, or end in />.
You can provide parameters for a macro using ordinary attributes. In the body of the macro, you put the parameter name between ~ signs. For example, if you need to provide a color for minor road labels, you could do it like this:
<defs> <macro id='minor-road-label'> <label font-size='75%,8pt' glow='white' color='~labelcolor~' case='assume-title' maxScale='20000'/> </macro> </defs>
Then in the layer, you give a value for the parameter when calling the macro:
<macro ref='minor-road-label' labelcolor='black'/>
Style sheet variables are values which can be set by CartoType at run-time. You can use simple arithmetic expressions to test these values and use the result to decide which part of a style sheet is used.
You can select any part of a style sheet (that is, any balanced XML) using
<if exp="integer expression"> ... </if>
If the expression's value is non-zero the section is used, otherwise it is ignored. The operators 'and', 'or', 'lt', 'le', 'eq' or '==', 'ge', 'gt', '+', '-' (unary and binary), '!', '*' and '/' are supported, and also bracketed sub-expressions using ( ... ). Operator precedence follows C++. (The operators &&, ||, <, <=, >= and > are also legal but cannot easily be used because of conflicts with XML syntax.) The variable 'scale' is built-in. Other variables can be set using CartoType::CMap::SetStyleSheetVariable.
For example, imagine that certain road types are to be conditionally highlighted.
The application code would contain this C++ statement:
cur_map->SetStyleSheetVariable("highlight",1); // variable names are case-sensitive
and the style sheet would contain this section:
<condition test='@feature_type="primary road"'> <line fill='khaki'/> <if exp="highlight and scale le 25000"> <highlight fill='red' width='70%,1' opacity='50%' distance='40%'/> <highlight fill='green' width='70%,1' opacity='50%' distance='-40%'/> <highlight fill='blue' width='30%,1' distance='100%' dashArray='1,1'/> </if> </condition>
The XML elements in bold above use the expression "highlighting and scale le 25000" to turn on highlighting only if the variable highlight is non-zero and the scale denominator is less than or equal to 25,000.