OpenTTD-patches/docs/newgrf-additions-nml.html
2023-02-19 20:22:40 +00:00

708 lines
34 KiB
HTML

<!DOCTYPE html>
<html>
<head>
<meta http-equiv="Content-Type" content="text/html; charset=UTF-8" />
<title>JGR's Patchpack - Additions to NewGRF Specifications (NML)</title>
<style type="text/css">
td li { white-space: nowrap; text-align: left; }
th { white-space: nowrap; text-align: center; }
td, th { border: 1px solid #CCCCCC; padding: 0px 5px; }
table { border-collapse: collapse; empty-cells: show; }
span.code { font-family: "Courier New", Courier, mono; color: darkgreen; }
pre.code { font-family: "Courier New", Courier, mono; color: blue; background-color: #f8f9fa; border: 1px solid #eaecf0; padding: 1em; }
dt { font-weight: bold; }
</style>
</head>
<body>
<h2>Additions to NewGRF Specifications in JGR's Patchpack in NML</h2>
<p>This document describes non-standard additions to the <a href="https://newgrf-specs.tt-wiki.net/wiki/NML:Main">Official OpenTTD NML Specifications</a> which are present in this patchpack and the associated <a href="https://github.com/JGRennison/nml">NML fork</a>.
<p>These additions MAY also be present in other patchpacks. They MAY be removed or moved in future, if necessary.</p>
<p>Not all standard NewGRF features are supported by NML, consequently not all non-standard additions to the specifications are supported by this patchpack's associated NML fork, or are listed in this document.<br />
See the associated <a href="newgrf-additions.html">non-NML document</a> for more details.</p>
<p>All of the non-standard features listed below will automatically emit suitable feature tests, conditionals, etc. such that NewGRFs which use these features will work correctly
on OpenTTD versions which do not support these features, including standard trunk OpenTTD and older/other patchpack versions.</p>
<p>All of the non-standard variables listed below will return 0 on OpenTTD versions which do not support these features/variables, including standard trunk OpenTTD and older/other patchpack versions.</p>
<h3>Features with separate pages</h3>
<ul>
<li><a href="newgrf-roadstops-nml.html">Road stops (FEAT_ROADSTOPS)</a></li>
<li><a href="newgrf-newlandscape-nml.html">New landscape (FEAT_NEWLANDSCAPE)</a></li>
</ul>
<h3 id="sections">Sections</h3>
<ul>
<li><a href="#builtin-functions">Builtin functions</a></li>
<li><a href="#railtype-properties">Railtype properties</a></li>
<li><a href="#railtype-variables">Railtype variables</a></li>
<li><a href="#roadtype-properties">Roadtype properties</a></li>
<li><a href="#tramtype-properties">Tramtype properties</a></li>
<li><a href="#object-ids">Object IDs</a></li>
<li><a href="#object-properties">Object properties</a></li>
<li><a href="#object-variables">Object variables</a></li>
<li><a href="#global-variable-properties">Global variables properties</a></li>
<li><a href="#replace-new-sprites">Replace new sprites</a></li>
<li><a href="#signal-graphics">Signal graphics using switches</a></li>
</ul>
<br />
<h3 id="builtin-functions"><a href="https://newgrf-specs.tt-wiki.net/wiki/NML:Builtin_functions">Builtin functions</a></h3>
<p>
<h4>extended_feature_test(feature_name[, min_version[, max_version]])</h4>
This returns true if the given extended feature is present and has a version within the specified minimum and maximum (inclusive).<br />
This function should only be used after the grf{} block.<br />
In most cases it is not necessary to use this function, as extended properties (listed below) which are not supported are simply skipped/ignored.
</p>
<h3 id="railtype-properties"><a href="https://newgrf-specs.tt-wiki.net/wiki/NML:Railtypes#Railtype_properties">Railtype properties</a></h3>
<table>
<tr><th>Property</th><th>Value range</th><th>Comment</th></tr>
<tr><td>enable_programmable_pre_signals</td><td>0 or 1</td>
<td>
Enable programmable pre-signal graphics in <a href="https://newgrf-specs.tt-wiki.net/wiki/NML:Railtypes#signals">railtype signals</a>.<br />
Programmable pre-signals have a signal type (<span class="code">getbits(extra_callback_info2, 16, 8)</span>) of 6.
</td>
</tr>
<tr><td>enable_no_entry_signals</td><td>0 or 1</td>
<td>
Enable no-entry signal graphics in <a href="https://newgrf-specs.tt-wiki.net/wiki/NML:Railtypes#signals">railtype signals</a>.<br />
No-entry signals have a signal type (<span class="code">getbits(extra_callback_info2, 16, 8)</span>) of 7.<br />
No-entry signals always have a signal state of red.
</td>
</tr>
<tr><td>enable_restricted_signals</td><td>0 or 1</td>
<td>
Enable restricted signal flag in <a href="https://newgrf-specs.tt-wiki.net/wiki/NML:Railtypes#signals">railtype signals</a>.<br />
When enabled, bit 24 of variable <span class="code">extra_callback_info2</span> is set if the signal is restricted (has a routing restriction program attached).<br />
When enabled, the "Show restricted electric signals using default graphics" client setting and signal post recolouring is not applied.<br />
This flag must only be set if a different sprite is returned when bit 24 of <span class="code">extra_callback_info2</span> is set.
</td>
</tr>
<tr><td>enable_signal_recolour</td><td>0 or 1</td>
<td>
Enable recolouring of graphics in <a href="https://newgrf-specs.tt-wiki.net/wiki/NML:Railtypes#signals">railtype signals</a>.<br />
When enabled, in addition to returning a sprite, register 0x100 may be set to the following using STORE_TEMP:
<table>
<tr><th>Bits</th><th>Meaning</th></tr>
<tr><td>0 - 23</td><td>Recolour sprite to use. Set to 0 for no recolouring.</td></tr>
<tr><td>24 - 31</td><td>Reserved, set to zero.</td></tr>
</table>
<br />
If recolouring is not optional, the feature name: <span class="code">action0_railtype_recolour</span> should be checked using the
<span class="code">extended_feature_test</span> function
and if necessary a suitable fallback used or error message shown.<br />
If the OpenTTD version does not support this property/feature, then the property would ordinarily be ignored/skipped and no recolouring would be done.
</td>
</tr>
<tr><td>extra_aspects</td><td>0 - 6</td>
<td>
The value is the number of additional signal aspects to use (e.g. 4-aspect signalling should use a value of 2).<br />
When set, the lowest byte of <span class="code">extra_callback_info2</span> (signal state) may have the given number of additional values starting from 02:
<table>
<tr><th>Value</th><th>Meaning</th></tr>
<tr><td>00</td><td>Red signal</td></tr>
<tr><td>01</td><td>Green signal</td></tr>
<tr><td>02</td><td>1st extra aspect (e.g. yellow)</td></tr>
<tr><td>03</td><td>2nd extra aspect (e.g. double yellow)</td></tr>
<tr><td>...</td><td>Further extra aspects...</td></tr>
</table>
<br />
The provided value is currently clamped to be within the range 0 - 6 (inclusive).<br />
N.B. Realistic braking must be enabled for additional signal aspects to be used
</td>
</tr>
<tr><td>disable_realistic_braking</td><td>0 or 1</td>
<td>
When this property is set realistic braking is disabled for trains of this railtype even when realistic braking is otherwise in effect.
</td>
</tr>
</table>
<h3 id="railtype-variables"><a href="https://newgrf-specs.tt-wiki.net/wiki/NML:Railtypes#Railtype_variables">Railtype variables</a></h3>
<p>Variables in the table below which are not supported by the version of OpenTTD being used return a value of 0.</p>
<table>
<tr><th>Variable</th><th>Value range</th><th>Comment</th></tr>
<tr><td>signal_restriction_info</td><td>bitmask(SIGNAL_RESTRICTION_INFO_XXX, ...)</td>
<td>
Information about the restricted signal status of the signal being drawn:
<dl>
<dt>RESTRICTED</dt>
<dd>The signal is restricted (has a routing restriction program attached)</dd>
<dt>RESERVE_THROUGH_ALWAYS</dt>
<dd>The attached routing restriction program unconditionally sets reserve through</dd>
<dt>MAY_REVERSE</dt>
<dd>The attached routing restriction program may allow trains to reverse behind this signal</dd>
</dl>
</td>
</tr>
<tr><td>signal_context</td><td>SIGNAL_CONTEXT_XXX</td>
<td>
Information about the context of the signal being drawn:
<dl>
<dt>GUI</dt>
<dd>The signal is being drawn in the GUI (signal window)</dd>
<dt>TRACK</dt>
<dd>The signal is being drawn on ordinary rail track</dd>
<dt>TUNNEL_BRIDGE_ENTRANCE</dt>
<dd>The signal is being drawn as a tunnel/bridge entrance signal</dd>
<dt>TUNNEL_BRIDGE_EXIT</dt>
<dd>The signal is being drawn as a tunnel/bridge exit signal</dd>
<dt>BRIDGE_MIDDLE</dt>
<dd>The signal is being drawn on the middle of a bridge</dd>
</dl>
</td>
</tr>
<tr><td>signal_context_is_tunnel</td><td>0 or 1</td>
<td>
The signal is being drawn on a tunnel entrance/exit (not a bridge)
</td>
</tr>
<tr><td>signal_context_info</td><td></td>
<td>
Above signal context variables in one variable (all of the railtype_signal_context variable)
</td>
</tr>
<tr><td>signal_side</td><td>SIGNAL_SIDE_XXX</td>
<td>
<dl>
<dt>LEFT</dt>
<dd>Signals are on the left</dd>
<dt>RIGHT</dt>
<dd>Signals are on the right</dd>
</dl>
</td>
</tr>
</table>
<h3 id="roadtype-properties"><a href="https://newgrf-specs.tt-wiki.net/wiki/NML:Roadtypes#Roadtype_properties">Roadtype properties</a></h3>
<table>
<tr><th>Property</th><th>Value range</th><th>Comment</th></tr>
<tr><td>roadtype_extra_flags</td><td>bitmask(ROADTYPE_EXTRA_FLAG_XXX, ...)</td>
<td>
<dl>
<dt>NO_SCRIPT_BUILD</dt>
<dd>Scripts (AI/GS) may not build this roadtype</dd>
<dt>NO_TOWN_MODIFY</dt>
<dd>Towns may not modify tiles of this roadtype in any way whatsoever</dd>
<dt>NO_TUNNELS</dt>
<dd>Disallow tunnels for this roadtype</dd>
<dt>NO_TRAIN_COLLISION</dt>
<dd>Disallow collisions with trains for vehicles of this roadtype</dd>
</dl>
</td>
</tr>
<tr><td>roadtype_collision_mode</td><td>ROADTYPE_COLLISION_MODE_XXX</td>
<td>
Sets the road vehicle collision mode for road vehicles of this road type.
<dl>
<dt>NORMAL</dt>
<dd>Normal road vehicle collision rules (this is the default)</dd>
<dt>NONE</dt>
<dd>Do not collide at all with other road vehicles</dd>
<dt>ELEVATED</dt>
<dd>Collide only with other elevated road vehicles</dd>
</dl>
</td>
</tr>
</table>
<h3 id="tramtype-properties"><a href="https://newgrf-specs.tt-wiki.net/wiki/NML:Tramtypes#Tramtype_properties">Tramtype properties</a></h3>
<table>
<tr><th>Property</th><th>Value range</th><th>Comment</th></tr>
<tr><td>tramtype_extra_flags</td><td>bitmask(TRAMTYPE_EXTRA_FLAG_XXX, ...)</td>
<td>
<dl>
<dt>NO_SCRIPT_BUILD</dt>
<dd>Scripts (AI/GS) may not build this tramtype</dd>
<dt>NO_TOWN_MODIFY</dt>
<dd>Towns may not modify tiles of this tramtype in any way whatsoever</dd>
<dt>NO_TUNNELS</dt>
<dd>Disallow tunnels for this tramtype</dd>
<dt>NO_TRAIN_COLLISION</dt>
<dd>Disallow collisions with trains for vehicles of this tramtype</dd>
</dl>
</td>
</tr>
<tr><td>tramtype_collision_mode</td><td>TRAMTYPE_COLLISION_MODE_XXX</td>
<td>
Sets the road vehicle collision mode for road vehicles of this tram type.
<dl>
<dt>NORMAL</dt>
<dd>Normal road vehicle collision rules (this is the default)</dd>
<dt>NONE</dt>
<dd>Do not collide at all with other road vehicles</dd>
<dt>ELEVATED</dt>
<dd>Collide only with other elevated road vehicles</dd>
</dl>
</td>
</tr>
</table>
<h3 id="object-ids"><a href="https://newgrf-specs.tt-wiki.net/wiki/NML:Objects#Object_IDs">Object IDs</a></h3>
<p>
Object IDs are NewGRF-local and can be freely chosen in the 0..63999 range, as of the <span class="code">more_objects_per_grf</span> feature.<br />
When loaded into a version of OpenTTD without this feature, IDs are limited to the range: 0..254.
Any objects with IDs outside this range will be skipped.
</p>
<h3 id="object-properties"><a href="https://newgrf-specs.tt-wiki.net/wiki/NML:Objects#Object_properties">Object properties</a></h3>
<table>
<tr><th>Property</th><th>Value range</th><th>Comment</th></tr>
<tr><td>use_land_ground</td><td>0 or 1</td><td>
Sets whether to use the underlying ground as the object ground sprite, ignoring the ground sprite provided in the sprite layout.<br />
When enabled, the ground sprite will be bare ground, grass, snow, desert, etc. as if it were a clear ground tile.<br />
In edge foundation mode, the ground may be coast/shore when flooded.
</td></tr>
<tr><td>edge_foundation_mode</td><td>[mode0, mode1, mode2, mode3]</td><td>
Enables edge foundation mode for the object.<br />
This property is intended for objects which are positioned at the edge of a tile, and only require a level edge, not a completely level tile.<br />
Foundations will only be added as required to get a suitable level edge.<br />
The format is one mode value per view. If the object has fewer than 4 views then some of the values provided in the property will not be used, and may be 0.
All four values must be constants.<br />
Each mode value should be one of:
<table>
<tr><th>Value</th><th>Meaning</th></tr>
<tr><td>DIAGDIR_NE</td><td>North-east edge</td></tr>
<tr><td>DIAGDIR_SE</td><td>South-east edge</td></tr>
<tr><td>DIAGDIR_SW</td><td>South-west edge</td></tr>
<tr><td>DIAGDIR_NW</td><td>North-west edge</td></tr>
</table>
combined with 0 or more flags using the | operator:
<table>
<tr><th>Value</th><th>Meaning</th></tr>
<tr><td>OBJECT_EF_FLAG_ADJUST_Z</td><td>Change z-position for the building sprite to the height of the edge</td></tr>
<tr><td>OBJECT_EF_FLAG_FOUNDATION_LOWER</td><td>If the height of the edge is lower than the maximum height of the tile, build a foundation</td></tr>
<tr><td>OBJECT_EF_FLAG_INCLINE_FOUNDATION</td><td>Use inclined instead of a flat foundations where possible. (Slopes with one corner raised where the height of the edge is at the maximum height of the tile).</td></tr>
</table>
</td></tr>
<tr><td>flood_resistant</td><td>0 or 1</td><td>
Sets whether the object is flood resistant.<br />
Flood resistance is always enabled for objects which can be built on water.<br />
This property can be used to enable flood resistance without enabling the object to be built on water.
</td></tr>
<tr><td>map_tile_type</td><td>OBJECT_VIEWPORT_MAP_TILE_TYPE_XXX</td><td>
Set tile type used for display in viewport map mode and the small-map window.<br />
The value should be one of:
<table>
<tr><th>Value</th><th>Meaning</th><th>Notes</th></tr>
<tr><td>OBJECT_VIEWPORT_MAP_TILE_TYPE_DEFAULT</td><td>Default object</td><td></td></tr>
<tr><td>OBJECT_VIEWPORT_MAP_TILE_TYPE_CLEAR</td><td>Clear/bare dirt</td><td>If use_land_ground is enabled, the underlying ground type will be used instead</td></tr>
<tr><td>OBJECT_VIEWPORT_MAP_TILE_TYPE_GRASS</td><td>Grass</td><td></td></tr>
<tr><td>OBJECT_VIEWPORT_MAP_TILE_TYPE_ROUGH</td><td>Rough ground</td><td></td></tr>
<tr><td>OBJECT_VIEWPORT_MAP_TILE_TYPE_ROCKS</td><td>Rocky ground</td><td></td></tr>
<tr><td>OBJECT_VIEWPORT_MAP_TILE_TYPE_FIELDS</td><td>Farm fields</td><td>The specific type of field can be set using map_tile_subtype</td></tr>
<tr><td>OBJECT_VIEWPORT_MAP_TILE_TYPE_SNOW</td><td>Snow</td><td></td></tr>
<tr><td>OBJECT_VIEWPORT_MAP_TILE_TYPE_DESERT</td><td>Desert</td><td></td></tr>
<tr><td>OBJECT_VIEWPORT_MAP_TILE_TYPE_TREES</td><td>Trees</td><td>The specific tree count and ground type/density can be set using map_tile_subtype</td></tr>
<tr><td>OBJECT_VIEWPORT_MAP_TILE_TYPE_HOUSE</td><td>House</td><td></td></tr>
<tr><td>OBJECT_VIEWPORT_MAP_TILE_TYPE_WATER</td><td>Water</td><td></td></tr>
</table>
</td></tr>
<tr><td>map_tile_subtype</td><td>0 .. 65535</td><td>
<p>This can be used to further refine the type set in map_tile_type.</p>
<p>Farm fields:
<table>
<tr><th>Bit</th><th>Meaning</th></tr>
<tr><td>0 - 2</td><td>
Which field type to use
</td></tr>
</table></p>
<p>Trees:
<table>
<tr><th>Bit</th><th>Meaning</th></tr>
<tr><td>0 - 3</td><td>
Tree ground type
<table>
<tr><th>Value</th><th>Meaning</th></tr>
<tr><td>OBJECT_VIEWPORT_MAP_TILE_TYPE_TREE_GROUND_GRASS</td><td>Grass</td></tr>
<tr><td>OBJECT_VIEWPORT_MAP_TILE_TYPE_TREE_GROUND_ROUGH</td><td>Rough ground</td></tr>
<tr><td>OBJECT_VIEWPORT_MAP_TILE_TYPE_TREE_GROUND_SNOW_DESERT</td><td>Snow/desert</td></tr>
<tr><td>OBJECT_VIEWPORT_MAP_TILE_TYPE_TREE_GROUND_SHORE</td><td>Shore</td></tr>
<tr><td>OBJECT_VIEWPORT_MAP_TILE_TYPE_TREE_GROUND_ROUGH_SNOW</td><td>Rough snow</td></tr>
</table>
</td></tr>
<tr><td>4 - 7</td><td>
Tree ground density (clamped to: 0 - 3)
</td></tr>
<tr><td>8 - 11</td><td>
Number of trees on the tile (clamped to: 1 - 4)
</td></tr>
</table></p>
</td></tr>
</table>
<h3 id="object-variables"><a href="https://newgrf-specs.tt-wiki.net/wiki/NML:Objects#Object_variables">Object variables</a></h3>
<p>Variables in the table below which are not supported by the version of OpenTTD being used return a value of 0.</p>
<table>
<tr><th>Variable</th><th>Value range</th><th>Comment</th></tr>
<tr><td>foundation_tile_slope</td><td><a href="https://newgrf-specs.tt-wiki.net/wiki/NML:List_of_tile_slopes">SLOPE_XXX</a></td><td>
Slope of the tile after any foundation has been applied.
</td></tr>
<tr><td>foundation_change_tile_slope</td><td><a href="https://newgrf-specs.tt-wiki.net/wiki/NML:List_of_tile_slopes">SLOPE_XXX</a></td><td>
Slope of the tile after any foundation has been applied xor the slope of the underlying tile.<br />
If this variable is non-zero a foundation is present.<br />
This is useful for xoring with the tile_slope variable, because if this variable is unavailable then the result is still the underlying tile slope.
</td></tr>
</table>
<h3 id="global-variable-properties">Global variables properties</h3>
<p>The variables listed below should set inside an item and property block of the form:<pre class="code">
item (FEAT_GLOBALVARS) {
property {
...
}
}</pre>
</p>
<table>
<tr><th>Property</th><th>Value range</th><th>Comment</th></tr>
<tr><td>lighthouse_generate_amount</td><td>0 .. 255</td><td>Sets the frequency at which lighthouse objects are generated during map generation</td></tr>
<tr><td>transmitter_generate_amount</td><td>0 .. 255</td><td>Sets the frequency at which transmitter objects are generated during map generation</td></tr>
<tr><td>extra_station_name</td><td>[string, bitmask(EXTRA_STATION_NAME_FLAG_XXX, ...)]</td>
<td>
<p>This adds an extra station name for use when all the available station names for a given town have been used.<br />
This property may be used as many times as required.<br />
Generally the referenced string should include a <span class="code">{STRING}</span> string code, this is used for the town name.
</p>
<dl>
<dt>EXTRA_STATION_NAME_FLAG_RAIL</dt>
<dd>May be used for rail stations</dd>
<dt>EXTRA_STATION_NAME_FLAG_ROAD</dt>
<dd>May be used for road stations</dd>
<dt>EXTRA_STATION_NAME_FLAG_AIRPORT</dt>
<dd>May be used for airport stations</dd>
<dt>EXTRA_STATION_NAME_FLAG_OIL_RIG</dt>
<dd>May be used for oil rig stations</dd>
<dt>EXTRA_STATION_NAME_FLAG_DOCK</dt>
<dd>May be used for dock stations</dd>
<dt>EXTRA_STATION_NAME_FLAG_HELIPORT</dt>
<dd>May be used for heliport stations</dd>
<dt>EXTRA_STATION_NAME_FLAG_TOWN_CENTRE_ONLY</dt>
<dd>May only be used for stations near the town centre</dd>
<dt>EXTRA_STATION_NAME_FLAG_NOT_TOWN_CENTRE</dt>
<dd>May not be used for stations near the town centre</dd>
<dt>EXTRA_STATION_NAME_FLAG_NEAR_WATER_ONLY</dt>
<dd>May only be used for stations near water</dd>
<dt>EXTRA_STATION_NAME_FLAG_NOT_NEAR_WATER</dt>
<dd>May not be used for stations near water</dd>
</dl>
</td>
</tr>
<tr><td>extra_station_names_probability</td><td>0 .. 255</td>
<td>
Sets the probability that an extra station name is used even when the available default names have not been exhausted.<br />
Some station names are always used first even when this is non-zero.
</td>
</tr>
<tr><td>allow_rocks_in_desert</td><td>0 or 1</td>
<td>
Sets whether rocky tiles are allowed to generate in and remain in desert zones (tropical climate).
</td>
</tr>
</table>
<p>Syntax example:
<pre class="code">
item (FEAT_GLOBALVARS) {
property {
lighthouse_generate_amount: 255;
transmitter_generate_amount: 0;
extra_station_name: [string(STR_STATION_NAME1), bitmask(EXTRA_STATION_NAME_FLAG_RAIL)];
extra_station_name: [string(STR_STATION_NAME2), bitmask(EXTRA_STATION_NAME_FLAG_ROAD, EXTRA_STATION_NAME_FLAG_TOWN_CENTRE_ONLY)];
}
}
</pre>
</p>
<h3 id="replace-new-sprites"><a href="https://newgrf-specs.tt-wiki.net/wiki/NML:Replace_new_sprites">Replace new sprites</a></h3>
<table>
<tr><th>Type</th><th>Number of sprites </th><th>Comment</th></tr>
<tr><td>PROGRAMMABLE_PRE_SIGNAL</td><td>32</td>
<td>
<b>Programmable pre-signals</b>
<p>Signal graphics come in groups of 16. These groups contain sprites in the same order as sprites 1275-1290 in trg1[r].grf and <a href="https://newgrf-specs.tt-wiki.net/wiki/Action5#04_Signal_graphics.">Action 5 type 4 (signals)</a>;
red, then green, for each of: SW-facing, NE-facing, NW-facing, SE-facing, E-facing, W-facing, S-facing, N-facing.
<table>
<tr><th>Group</th><th>Contents</th></tr>
<tr><td>0</td><td>Semaphore programmable pre-signals</td></tr>
<tr><td>1</td><td>Lighted programmable pre-signals</td></tr>
</table>
</td>
</tr>
<tr><td>NO_ENTRY_SIGNAL</td><td>16</td>
<td>
<b>No-entry signals</b>
<p>No-entry signal graphics come in groups of 8. These groups contain sprites in the same order as the red sprites of 1275-1290 in trg1[r].grf and <a href="https://newgrf-specs.tt-wiki.net/wiki/Action5#04_Signal_graphics.">Action 5 type 4 (signals)</a>;
red only, for each of: SW-facing, NE-facing, NW-facing, SE-facing, E-facing, W-facing, S-facing, N-facing.
<table>
<tr><th>Group</th><th>Contents</th></tr>
<tr><td>0</td><td>Semaphore no-entry signals</td></tr>
<tr><td>1</td><td>Lighted no-entry signals</td></tr>
</table>
</td>
</tr>
<tr><td>MISC_GUI</td><td>1</td>
<td>
<b>Miscellaneous GUI graphics</b>
<p>There is currently one misc GUI sprite.</p>
</td>
</tr>
<tr><td>ROAD_WAYPOINTS</td><td>4</td>
<td>
<b>Road waypoint graphics</b>
<p>This is the same order and format as the drive-through bus/truck road stop sprites.</p>
</td>
</tr>
</table>
<h3 id="signal-graphics">Signal graphics using switches</h3>
<p>
This feature allows signal sprites to be specified using switches in a very similar manner to <a href="https://newgrf-specs.tt-wiki.net/wiki/NML:Railtypes#signals">railtype signals</a> in
<span class="code">item (FEAT_RAILTYPES) { graphics { signals: ... } }</span> blocks.<br />
However this applies to all signals, not only those of a particular rail type.<br />
Railtype signal graphics have a higher priority than general signal graphics as set here.<br />
<br />
Variables: <span class="code">extra_callback_info1</span>, <span class="code">extra_callback_info2</span>, and <span class="code">terrain_type</span>
are the same as for <a href="https://newgrf-specs.tt-wiki.net/wiki/NML:Railtypes#signals">railtype signals</a>.<br />
<br />
This feature is not supported by standard OpenTTD or by standard NML.<br/>
If the use of this feature is not optional, the feature name: <span class="code">action3_signals_custom_signal_sprites</span> should be checked using the
<span class="code">extended_feature_test</span> function
and if necessary a suitable fallback used or error message shown.<br />
<br />
An <span class="code">item (FEAT_SIGNALS, custom_signals, 0) { }</span> block should be used to define properties and graphics.<br />
The graphics block should contain a single default switch.
</p>
<table>
<tr><th>Property</th><th>Value range</th><th>Comment</th></tr>
<tr><td>enable_programmable_pre_signals</td><td>0 or 1</td>
<td>
Enable programmable pre-signal graphics.<br />
Programmable pre-signals have a signal type (<span class="code">getbits(extra_callback_info2, 16, 8)</span>) of 6.
</td>
</tr>
<tr><td>enable_no_entry_signals</td><td>0 or 1</td>
<td>
Enable no-entry signal graphics.<br />
No-entry signals have a signal type (<span class="code">getbits(extra_callback_info2, 16, 8)</span>) of 7.<br />
No-entry signals always have a signal state of red.
</td>
</tr>
<tr><td>enable_restricted_signals</td><td>0 or 1</td>
<td>
Enable restricted signal flag.<br />
When enabled, bit 24 of variable <span class="code">extra_callback_info2</span> is set if the signal is restricted (has a routing restriction program attached).<br />
When enabled, the "Show restricted electric signals using default graphics" client setting and signal post recolouring is not applied.<br />
This flag must only be set if a different sprite is returned when bit 24 of <span class="code">extra_callback_info2</span> is set.
</td>
</tr>
<tr><td>enable_signal_recolour</td><td>0 or 1</td>
<td>
Enable recolouring of graphics<br />
When enabled, in addition to returning a sprite, register 0x100 may be set to the following using STORE_TEMP:
<table>
<tr><th>Bits</th><th>Meaning</th></tr>
<tr><td>0 - 23</td><td>Recolour sprite to use. Set to 0 for no recolouring.</td></tr>
<tr><td>24 - 31</td><td>Reserved, set to zero.</td></tr>
</table>
</td>
</tr>
<tr><td>extra_aspects</td><td>0 - 6</td>
<td>
The value is the number of additional signal aspects to use (e.g. 4-aspect signalling should use a value of 2).<br />
When set, the lowest byte of <span class="code">extra_callback_info2</span> (signal state) may have the given number of additional values starting from 02:
<table>
<tr><th>Value</th><th>Meaning</th></tr>
<tr><td>00</td><td>Red signal</td></tr>
<tr><td>01</td><td>Green signal</td></tr>
<tr><td>02</td><td>1st extra aspect (e.g. yellow)</td></tr>
<tr><td>03</td><td>2nd extra aspect (e.g. double yellow)</td></tr>
<tr><td>...</td><td>Further extra aspects...</td></tr>
</table>
<br />
The provided value is currently clamped to be within the range 0 - 6 (inclusive).<br />
N.B. Realistic braking must be enabled for additional signal aspects to be used
</td>
</tr>
<tr><td>define_style</td><td>1 - 255</td>
<td>
Define a custom signal style<br />
Signals using this style will only use this GRF, or the default graphics if no graphics are returned.<br />
The value supplied is returned in the signal_style variable.<br />
This property (and related signal style properties) may be used more than once.<br />
The total number of custom signal styles in a game is currently limited to 15.
</td>
</tr>
<tr><td>style_name</td><td>string</td>
<td>
Set the name of the most recently defined style (defined using the <span class="code">define_style</span> property).<br />
This property should be used if using the define_style property, as otherwise the style will have no name.
</td>
</tr>
<tr><td>style_electric_enabled</td><td>bitmask(SIGNAL_TYPE_XXX, ...)</td>
<td>
Set which electric signal types may be built using this signal style for the most recently defined style (defined using the <span class="code">define_style</span> property).<br />
At least one of this property and <span class="code">style_semaphore_enabled</span> should be set to a non-zero value, as otherwise
no signal types will be enabled for this custom signal style.<br />
If PROG or NO_ENTRY are set, it is not necessary to also set <span class="code">enable_programmable_pre_signals</span> or <span class="code">enable_no_entry_signals</span>.
<dl>
<dt>NORMAL</dt>
<dd>Normal/block signal</dd>
<dt>ENTRY</dt>
<dd>Pre-signal entry</dd>
<dt>EXIT</dt>
<dd>Pre-signal exit</dd>
<dt>COMBO</dt>
<dd>Pre-signal combo</dd>
<dt>PBS</dt>
<dd>Two-way PBS</dd>
<dt>PBS_ONEWAY</dt>
<dd>One-way PBS</dd>
<dt>PROG</dt>
<dd>Programmable pre-signal</dd>
<dt>NO_ENTRY</dt>
<dd>No-entry</dd>
</dl>
</td>
</tr>
<tr><td>style_semaphore_enabled</td><td>bitmask(SIGNAL_TYPE_XXX, ...)</td>
<td>
Set which semaphore signal types may be built using this signal style for the most recently defined style (defined using the <span class="code">define_style</span> property).<br />
See <span class="code">style_electric_enabled</span>, above.
</td>
</tr>
<tr><td>style_no_aspect_increase</td><td>0 or 1</td>
<td>
Set whether the most recently defined style (defined using the <span class="code">define_style</span> property) does not increase
the signal aspect with respect to the signals either side (i.e. function like a banner repeater).
</td>
</tr>
<tr><td>style_always_reserve_through</td><td>0 or 1</td>
<td>
Set whether reserve through is unconditionally enabled for the most recently defined style (defined using the <span class="code">define_style</span> property).
</td>
</tr>
<tr><td>style_lookahead_extra_aspects</td><td>0 - 6</td>
<td>
Set the look-ahead extra aspects for the most recently defined style (defined using the <span class="code">define_style</span> property).<br />
This property only makes a difference when the "limit train lookahead to signal aspect" game setting is enabled.<br />
This limits the signal aspect which the hypothetical train driver can "read" from the signal without affecting signal aspect propagation to other signals, or variable <span class="code">extra_callback_info2</span>.<br />
Example values could include: 1 for traditional banner repeater signals.<br />
Shunt signals should use <span class="code">style_lookahead_single_signal_only</span> instead.<br />
The value is clamped to be less than or equal to the value set in the <span class="code">extra_aspects</span> property.
</td>
</tr>
<tr><td>style_lookahead_single_signal_only</td><td>0 or 1</td>
<td>
Set the look-ahead to single signal only mode for the most recently defined style (defined using the <span class="code">define_style</span> property).<br />
This property only makes a difference when the "limit train lookahead to signal aspect" game setting is enabled, or when using a different signal
type which uses <span class="code">tyle_combined_normal_shunt</span>.<br />
This is similar to <span class="code">style_lookahead_extra_aspects</span> with a value of 0, except the lookahead always ends at the
next signal, even if that signal type sets <span class="code">style_no_aspect_increase</span>.<br />
If enabled, this property overrides <span class="code">style_lookahead_extra_aspects</span>.<br />
This can be used for shunt signals.
</td>
</tr>
<tr><td>style_combined_normal_shunt</td><td>0 or 1</td>
<td>
Enable functioning as a combined normal aspect and shunt signal for the most recently defined style (defined using the <span class="code">define_style</span> property).<br />
When enabled and displaying a shunt aspect, the signal state in the lowest byte of <span class="code">extra_callback_info2</span> will have the value: 0xFF.
</td>
</tr>
<tr><td>style_opposite_side</td><td>0 or 1</td>
<td>
Set whether signals should be drawn on the opposite side of the track for the most recently defined style (defined using the <span class="code">define_style</span> property).
</td>
</tr>
<tr><td>style_realistic_braking_only</td><td>0 or 1</td>
<td>
Set whether signals using this style may only be built when realistic braking is enabled, for the most recently defined style (defined using the <span class="code">define_style</span> property).
</td>
</tr>
<tr><td>no_default_style</td><td>0 or 1</td>
<td>
When enabled, custom signal graphics from this GRF are only used for custom signal styles, not the default style
</td>
</tr>
</table>
<br />
<table>
<tr><th>Variable</th><th>Value range</th><th>Comment</th></tr>
<tr><td>signal_restriction_info</td><td>bitmask(SIGNAL_RESTRICTION_INFO_XXX, ...)</td>
<td>
Information about the restricted signal status of the signal being drawn:
<dl>
<dt>RESTRICTED</dt>
<dd>The signal is restricted (has a routing restriction program attached)</dd>
<dt>RESERVE_THROUGH_ALWAYS</dt>
<dd>The attached routing restriction program unconditionally sets reserve through</dd>
<dt>MAY_REVERSE</dt>
<dd>The attached routing restriction program may allow trains to reverse behind this signal</dd>
</dl>
</td>
</tr>
<tr><td>signal_context</td><td>SIGNAL_CONTEXT_XXX</td>
<td>
Information about the context of the signal being drawn:
<dl>
<dt>GUI</dt>
<dd>The signal is being drawn in the GUI (signal window)</dd>
<dt>TRACK</dt>
<dd>The signal is being drawn on ordinary rail track</dd>
<dt>TUNNEL_BRIDGE_ENTRANCE</dt>
<dd>The signal is being drawn as a tunnel/bridge entrance signal</dd>
<dt>TUNNEL_BRIDGE_EXIT</dt>
<dd>The signal is being drawn as a tunnel/bridge exit signal</dd>
<dt>BRIDGE_MIDDLE</dt>
<dd>The signal is being drawn on the middle of a bridge</dd>
</dl>
</td>
</tr>
<tr><td>signal_context_is_tunnel</td><td>0 or 1</td>
<td>
The signal is being drawn on a tunnel entrance/exit (not a bridge)
</td>
</tr>
<tr><td>signal_context_info</td><td></td>
<td>
Above signal context variables in one variable (all of the signals_signal_context variable)
</td>
</tr>
<tr><td>signal_side</td><td>SIGNAL_SIDE_XXX</td>
<td>
<dl>
<dt>LEFT</dt>
<dd>Signals are on the left</dd>
<dt>RIGHT</dt>
<dd>Signals are on the right</dd>
</dl>
</td>
</tr>
<tr><td>signal_style</td><td>0 - 255</td>
<td>
The style ID defined using define_style for signals using a custom style, or 0 for signals using the default style
</td>
</tr>
</table>
<p>
Custom signal sprites example:
<pre class="code">
grf {
...
}
if (!extended_feature_test("action3_signals_custom_signal_sprites")) {
error(FATAL, string(STR_UNSUPPORTED_VERSION));
}
switch (FEAT_SIGNALS, SELF, switch_signals, ...) {
...
}
item (FEAT_SIGNALS, custom_signals, 0) {
property {
enable_signal_recolour: 1;
}
graphics {
switch_signals;
}
}
</pre>
</p>
</body>
</html>