Enable recolouring of custom signal graphics (global and per-railtype)

pull/306/head
Jonathan G Rennison 3 years ago
parent 322a046f49
commit f1fde8c684

@ -227,10 +227,20 @@
<p>This applies to <a href="https://newgrf-specs.tt-wiki.net/wiki/Action3/Railtypes#Signal_sprites_.280B.29">Action 2/3 - Railtype custom signal sprites</a>.<br />
When enabled, bit 24 of variable 18 (extra callback info) 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 should only be set if the Action 2/3 actually returns a different sprite when bit 24 of variable 18 is set.
This flag should only be set if the Action 2/3 actually returns a different sprite when bit 24 of variable 18 is set.<br />
The property length is 1 byte. 0 is disabled (default). 1 is enabled.
</p>
<p>This is indicated by the feature name: <font face="monospace">action0_railtype_restricted_signals</font>, version 1</p>
<h4 id="railtype_enable_signal_recolour">Enable recolouring for custom signal sprites (mappable property: railtype_enable_signal_recolour)</h4>
<p>This applies to <a href="https://newgrf-specs.tt-wiki.net/wiki/Action3/Railtypes#Signal_sprites_.280B.29">Action 2/3 - Railtype custom signal sprites</a>.<br />
When enabled, in addition to returning a sprite, register 0x100 may be set to the following:
<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></p>
<p>The property length is 1 byte. 0 is disabled (default). 1 is enabled.</p>
<p>This is indicated by the feature name: <font face="monospace">action0_railtype_recolour</font>, version 1</p>
<h4 id="railtype_disable_realistic_braking">Disable use of realistic braking with this rail type (mappable property: railtype_disable_realistic_braking)</h4>
<p>When this property is set realistic braking is disabled for trains of this railtype even when realistic braking is otherwise in effect.<br />
The property length is 1 byte. 0 is realistic braking is not disabled for this railtype. 1 is disable realistic braking for this railtype.
@ -297,6 +307,18 @@
The Action 0 Id field is not used, the value is ignored.
</p>
<p>This is indicated by the feature name: <font face="monospace">action0_signals_restricted_signals</font>, version 1</p>
<h4 id="signals_enable_signal_recolour">Enable recolouring for custom signal sprites (mappable property: signals_enable_signal_recolour)</h4>
<p>This applies to <a href="#a3signals_custom_signal_sprites">Action 2/3 Signals (Feature 0E) custom signal sprites</a> for this GRF.<br />
When enabled, in addition to returning a sprite, register 0x100 may be set to the following:
<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></p>
<p>The property length is 1 byte. 0 is disabled (default). 1 is enabled.<br />
The Action 0 Id field is not used, the value is ignored.
</p>
<p>This is indicated by the feature name: <font face="monospace">action0_signals_recolour</font>, version 1</p>
<br />
<br />
<h3 id="varaction2_station"><a href="https://newgrf-specs.tt-wiki.net/wiki/VariationalAction2/Stations">Variational Action 2 - Stations</a></h3>

@ -4083,6 +4083,11 @@ static ChangeInfoResult SignalsChangeInfo(uint id, int numinfo, int prop, const
SB(_cur.grffile->new_signal_ctrl_flags, NSCF_RESTRICTEDSIG, 1, (buf->ReadByte() != 0 ? 1 : 0));
break;
case A0RPI_SIGNALS_ENABLE_SIGNAL_RECOLOUR:
if (MappedPropertyLengthMismatch(buf, 1, mapping_entry)) break;
SB(_cur.grffile->new_signal_ctrl_flags, NSCF_RECOLOUR_ENABLED, 1, (buf->ReadByte() != 0 ? 1 : 0));
break;
default:
ret = HandleAction0PropertyDefault(buf, prop);
break;
@ -4416,6 +4421,11 @@ static ChangeInfoResult RailTypeChangeInfo(uint id, int numinfo, int prop, const
SB(rti->ctrl_flags, RTCF_NOREALISTICBRAKING, 1, (buf->ReadByte() != 0 ? 1 : 0));
break;
case A0RPI_RAILTYPE_ENABLE_SIGNAL_RECOLOUR:
if (MappedPropertyLengthMismatch(buf, 1, mapping_entry)) break;
SB(rti->ctrl_flags, RTCF_RECOLOUR_ENABLED, 1, (buf->ReadByte() != 0 ? 1 : 0));
break;
default:
ret = HandleAction0PropertyDefault(buf, prop);
break;
@ -4499,6 +4509,7 @@ static ChangeInfoResult RailTypeReserveInfo(uint id, int numinfo, int prop, cons
case A0RPI_RAILTYPE_ENABLE_PROGRAMMABLE_SIGNALS:
case A0RPI_RAILTYPE_ENABLE_RESTRICTED_SIGNALS:
case A0RPI_RAILTYPE_DISABLE_REALISTIC_BRAKING:
case A0RPI_RAILTYPE_ENABLE_SIGNAL_RECOLOUR:
buf->Skip(buf->ReadExtendedByte());
break;
@ -8468,10 +8479,12 @@ static const GRFFeatureInfo _grf_feature_list[] = {
GRFFeatureInfo("action0_railtype_programmable_signals", 1),
GRFFeatureInfo("action0_railtype_restricted_signals", 1),
GRFFeatureInfo("action0_railtype_disable_realistic_braking", 1),
GRFFeatureInfo("action0_railtype_recolour", 1),
GRFFeatureInfo("action0_roadtype_extra_flags", 1),
GRFFeatureInfo("action0_global_extra_station_names", 1),
GRFFeatureInfo("action0_signals_programmable_signals", 1),
GRFFeatureInfo("action0_signals_restricted_signals", 1),
GRFFeatureInfo("action0_signals_recolour", 1),
GRFFeatureInfo("action3_signals_custom_signal_sprites", 1),
GRFFeatureInfo(),
};
@ -8592,11 +8605,13 @@ static const GRFPropertyMapDefinition _grf_action0_remappable_properties[] = {
GRFPropertyMapDefinition(GSF_RAILTYPES, A0RPI_RAILTYPE_ENABLE_PROGRAMMABLE_SIGNALS, "railtype_enable_programmable_signals"),
GRFPropertyMapDefinition(GSF_RAILTYPES, A0RPI_RAILTYPE_ENABLE_RESTRICTED_SIGNALS, "railtype_enable_restricted_signals"),
GRFPropertyMapDefinition(GSF_RAILTYPES, A0RPI_RAILTYPE_DISABLE_REALISTIC_BRAKING, "railtype_disable_realistic_braking"),
GRFPropertyMapDefinition(GSF_RAILTYPES, A0RPI_RAILTYPE_ENABLE_SIGNAL_RECOLOUR, "railtype_enable_signal_recolour"),
GRFPropertyMapDefinition(GSF_ROADTYPES, A0RPI_ROADTYPE_EXTRA_FLAGS, "roadtype_extra_flags"),
GRFPropertyMapDefinition(GSF_TRAMTYPES, A0RPI_ROADTYPE_EXTRA_FLAGS, "roadtype_extra_flags"),
GRFPropertyMapDefinition(GSF_GLOBALVAR, A0RPI_GLOBALVAR_EXTRA_STATION_NAMES, "global_extra_station_names"),
GRFPropertyMapDefinition(GSF_SIGNALS, A0RPI_SIGNALS_ENABLE_PROGRAMMABLE_SIGNALS, "signals_enable_programmable_signals"),
GRFPropertyMapDefinition(GSF_SIGNALS, A0RPI_SIGNALS_ENABLE_RESTRICTED_SIGNALS, "signals_enable_restricted_signals"),
GRFPropertyMapDefinition(GSF_SIGNALS, A0RPI_SIGNALS_ENABLE_SIGNAL_RECOLOUR, "signals_enable_signal_recolour"),
GRFPropertyMapDefinition(),
};

@ -118,10 +118,12 @@ enum Action0RemapPropertyIds {
A0RPI_RAILTYPE_ENABLE_PROGRAMMABLE_SIGNALS,
A0RPI_RAILTYPE_ENABLE_RESTRICTED_SIGNALS,
A0RPI_RAILTYPE_DISABLE_REALISTIC_BRAKING,
A0RPI_RAILTYPE_ENABLE_SIGNAL_RECOLOUR,
A0RPI_ROADTYPE_EXTRA_FLAGS,
A0RPI_GLOBALVAR_EXTRA_STATION_NAMES,
A0RPI_SIGNALS_ENABLE_PROGRAMMABLE_SIGNALS,
A0RPI_SIGNALS_ENABLE_RESTRICTED_SIGNALS,
A0RPI_SIGNALS_ENABLE_SIGNAL_RECOLOUR,
};
enum GRFPropertyMapFallbackMode {
@ -222,6 +224,7 @@ enum NewSignalCtrlFlags {
NSCF_GROUPSET = 0, ///< Custom signal sprites group set.
NSCF_PROGSIG = 1, ///< Custom signal sprites enabled for programmable pre-signals.
NSCF_RESTRICTEDSIG = 2, ///< Custom signal sprite flag enabled for restricted signals.
NSCF_RECOLOUR_ENABLED = 3, ///< Recolour sprites enabled
};
/** New signal control flags. */

@ -115,10 +115,10 @@ SpriteID GetCustomRailSprite(const RailtypeInfo *rti, TileIndex tile, RailTypeSp
return group->GetResult();
}
static SpriteID GetRailTypeCustomSignalSprite(const RailtypeInfo *rti, TileIndex tile, SignalType type, SignalVariant var, SignalState state, bool gui, bool restricted)
static PalSpriteID GetRailTypeCustomSignalSprite(const RailtypeInfo *rti, TileIndex tile, SignalType type, SignalVariant var, SignalState state, bool gui, bool restricted)
{
if (rti->group[RTSG_SIGNALS] == nullptr) return 0;
if (type == SIGTYPE_PROG && !HasBit(rti->ctrl_flags, RTCF_PROGSIG)) return 0;
if (rti->group[RTSG_SIGNALS] == nullptr) return { 0, PAL_NONE };
if (type == SIGTYPE_PROG && !HasBit(rti->ctrl_flags, RTCF_PROGSIG)) return { 0, PAL_NONE };
uint32 param1 = gui ? 0x10 : 0x00;
uint32 param2 = (type << 16) | (var << 8) | state;
@ -126,9 +126,10 @@ static SpriteID GetRailTypeCustomSignalSprite(const RailtypeInfo *rti, TileIndex
RailTypeResolverObject object(rti, tile, TCX_NORMAL, RTSG_SIGNALS, param1, param2);
const SpriteGroup *group = object.Resolve();
if (group == nullptr || group->GetNumResults() == 0) return 0;
if (group == nullptr || group->GetNumResults() == 0) return { 0, PAL_NONE };
return group->GetResult();
PaletteID pal = HasBit(rti->ctrl_flags, RTCF_RECOLOUR_ENABLED) ? GB(GetRegister(0x100), 0, 24) : PAL_NONE;
return { group->GetResult(), pal };
}
/**
@ -143,8 +144,8 @@ static SpriteID GetRailTypeCustomSignalSprite(const RailtypeInfo *rti, TileIndex
*/
CustomSignalSpriteResult GetCustomSignalSprite(const RailtypeInfo *rti, TileIndex tile, SignalType type, SignalVariant var, SignalState state, bool gui, bool restricted)
{
SpriteID spr = GetRailTypeCustomSignalSprite(rti, tile, type, var, state, gui, restricted);
if (spr != 0) return { spr, HasBit(rti->ctrl_flags, RTCF_PROGSIG) };
PalSpriteID spr = GetRailTypeCustomSignalSprite(rti, tile, type, var, state, gui, restricted);
if (spr.sprite != 0) return { spr, HasBit(rti->ctrl_flags, RTCF_PROGSIG) };
for (const GRFFile *grf : _new_signals_grfs) {
if (type == SIGTYPE_PROG && !HasBit(grf->new_signal_ctrl_flags, NSCF_PROGSIG)) continue;
@ -155,10 +156,13 @@ CustomSignalSpriteResult GetCustomSignalSprite(const RailtypeInfo *rti, TileInde
NewSignalsResolverObject object(grf, tile, TCX_NORMAL, param1, param2);
const SpriteGroup *group = object.Resolve();
if (group != nullptr && group->GetNumResults() != 0) return { group->GetResult(), HasBit(grf->new_signal_ctrl_flags, NSCF_RESTRICTEDSIG) };
if (group != nullptr && group->GetNumResults() != 0) {
PaletteID pal = HasBit(grf->new_signal_ctrl_flags, NSCF_RECOLOUR_ENABLED) ? GB(GetRegister(0x100), 0, 24) : PAL_NONE;
return { { group->GetResult(), pal }, HasBit(grf->new_signal_ctrl_flags, NSCF_RESTRICTEDSIG) };
}
}
return { 0, false };
return { { 0, PAL_NONE }, false };
}
/**

@ -56,7 +56,7 @@ struct RailTypeResolverObject : public ResolverObject {
};
struct CustomSignalSpriteResult {
SpriteID sprite_id;
PalSpriteID sprite;
bool restricted_valid;
};

@ -46,6 +46,7 @@ enum RailTypeCtrlFlags {
RTCF_PROGSIG = 0, ///< Custom signal sprites enabled for programmable pre-signals.
RTCF_RESTRICTEDSIG = 1, ///< Custom signal sprite flag enabled for restricted signals.
RTCF_NOREALISTICBRAKING = 2, ///< Realistic braking disabled for this track type
RTCF_RECOLOUR_ENABLED = 3, ///< Recolour sprites enabled
};
struct SpriteGroup;
@ -163,7 +164,7 @@ public:
SpriteID build_depot; ///< button for building depots
SpriteID build_tunnel; ///< button for building a tunnel
SpriteID convert_rail; ///< button for converting rail
SpriteID signals[SIGTYPE_END][2][2]; ///< signal GUI sprites (type, variant, state)
PalSpriteID signals[SIGTYPE_END][2][2]; ///< signal GUI sprites (type, variant, state)
} gui_sprites;
struct {

@ -113,10 +113,18 @@ void ResolveRailTypeGUISprites(RailtypeInfo *rti)
for (SignalType type = SIGTYPE_NORMAL; type < SIGTYPE_END; type = (SignalType)(type + 1)) {
for (SignalVariant var = SIG_ELECTRIC; var <= SIG_SEMAPHORE; var = (SignalVariant)(var + 1)) {
SpriteID red = GetCustomSignalSprite(rti, INVALID_TILE, type, var, SIGNAL_STATE_RED, true).sprite_id;
SpriteID green = GetCustomSignalSprite(rti, INVALID_TILE, type, var, SIGNAL_STATE_GREEN, true).sprite_id;
rti->gui_sprites.signals[type][var][0] = (red != 0) ? red + SIGNAL_TO_SOUTH : _signal_lookup[var][type];
rti->gui_sprites.signals[type][var][1] = (green != 0) ? green + SIGNAL_TO_SOUTH : _signal_lookup[var][type] + 1;
PalSpriteID red = GetCustomSignalSprite(rti, INVALID_TILE, type, var, SIGNAL_STATE_RED, true).sprite;
PalSpriteID green = GetCustomSignalSprite(rti, INVALID_TILE, type, var, SIGNAL_STATE_GREEN, true).sprite;
if (red.sprite != 0) {
rti->gui_sprites.signals[type][var][0] = { red.sprite + SIGNAL_TO_SOUTH, red.pal };
} else {
rti->gui_sprites.signals[type][var][0] = { _signal_lookup[var][type], PAL_NONE };
}
if (green.sprite != 0) {
rti->gui_sprites.signals[type][var][1] = { green.sprite + SIGNAL_TO_SOUTH, green.pal };
} else {
rti->gui_sprites.signals[type][var][1] = { _signal_lookup[var][type] + 1, PAL_NONE };
}
}
}
}
@ -2671,10 +2679,12 @@ void DrawSingleSignal(TileIndex tile, const RailtypeInfo *rti, Track track, Sign
GetSignalXY(tile, pos, x, y);
const CustomSignalSpriteResult result = GetCustomSignalSprite(rti, tile, type, variant, condition, false, show_restricted);
SpriteID sprite = result.sprite_id;
SpriteID sprite = result.sprite.sprite;
PaletteID pal = PAL_NONE;
bool is_custom_sprite = (sprite != 0);
if (sprite != 0) {
sprite += image;
pal = result.sprite.pal;
} else if (type == SIGTYPE_PROG) {
if (variant == SIG_SEMAPHORE) {
sprite = SPR_PROGSIGNAL_BASE + image * 2 + condition;
@ -2705,6 +2715,7 @@ void DrawSingleSignal(TileIndex tile, const RailtypeInfo *rti, Track track, Sign
sprite = (type == SIGTYPE_NORMAL && variant == SIG_ELECTRIC) ? SPR_DUP_ORIGINAL_SIGNALS_BASE : SPR_DUP_SIGNALS_BASE - 16;
sprite += type * 16 + variant * 64 + image * 2 + condition + (IsSignalSpritePBS(type) ? 64 : 0);
}
pal = PAL_NONE;
is_custom_sprite = false;
}
@ -2719,7 +2730,7 @@ void DrawSingleSignal(TileIndex tile, const RailtypeInfo *rti, Track track, Sign
AddSortableSpriteToDraw(sprite, SPR_TRACERESTRICT_BASE + 1, x, y, 1, 1, BB_HEIGHT_UNDER_BRIDGE, GetSaveSlopeZ(x, y, track));
}
} else {
AddSortableSpriteToDraw(sprite, PAL_NONE, x, y, 1, 1, BB_HEIGHT_UNDER_BRIDGE, GetSaveSlopeZ(x, y, track));
AddSortableSpriteToDraw(sprite, pal, x, y, 1, 1, BB_HEIGHT_UNDER_BRIDGE, GetSaveSlopeZ(x, y, track));
}
const Sprite *sp = GetSprite(sprite, ST_NORMAL);
if (sp->x_offs < -SIGNAL_DIRTY_LEFT || sp->x_offs + sp->width > SIGNAL_DIRTY_RIGHT || sp->y_offs < -SIGNAL_DIRTY_TOP || sp->y_offs + sp->height > SIGNAL_DIRTY_BOTTOM) {

@ -1790,17 +1790,17 @@ private:
* @param widget_index index of this widget in the window
* @param image the sprite to draw
*/
void DrawSignalSprite(byte widget_index, SpriteID image) const
void DrawSignalSprite(byte widget_index, PalSpriteID image) const
{
Point offset;
Dimension sprite_size = GetSpriteSize(image, &offset);
Dimension sprite_size = GetSpriteSize(image.sprite, &offset);
const NWidgetBase *widget = this->GetWidget<NWidgetBase>(widget_index);
int x = widget->pos_x - offset.x +
(widget->current_x - sprite_size.width + offset.x) / 2; // centered
int y = widget->pos_y - sig_sprite_bottom_offset + WD_IMGBTN_TOP +
(widget->current_y - WD_IMGBTN_TOP - WD_IMGBTN_BOTTOM + sig_sprite_size.height) / 2; // aligned to bottom
DrawSprite(image, PAL_NONE,
DrawSprite(image.sprite, image.pal,
x + this->IsWidgetLowered(widget_index),
y + this->IsWidgetLowered(widget_index));
}
@ -1847,7 +1847,7 @@ public:
for (uint variant = SIG_ELECTRIC; variant <= SIG_SEMAPHORE; variant++) {
for (uint lowered = 0; lowered < 2; lowered++) {
Point offset;
Dimension sprite_size = GetSpriteSize(rti->gui_sprites.signals[type][variant][lowered], &offset);
Dimension sprite_size = GetSpriteSize(rti->gui_sprites.signals[type][variant][lowered].sprite, &offset);
this->sig_sprite_bottom_offset = std::max<int>(this->sig_sprite_bottom_offset, sprite_size.height);
this->sig_sprite_size.width = std::max<int>(this->sig_sprite_size.width, sprite_size.width - offset.x);
this->sig_sprite_size.height = std::max<int>(this->sig_sprite_size.height, sprite_size.height - offset.y);
@ -1882,7 +1882,7 @@ public:
/* Extract signal from widget number. */
SignalType type = TypeForClick((widget - WID_BS_SEMAPHORE_NORM) % SIGTYPE_END);
int var = SIG_SEMAPHORE - (widget - WID_BS_SEMAPHORE_NORM) / SIGTYPE_END; // SignalVariant order is reversed compared to the widgets.
SpriteID sprite = GetRailTypeInfo(_cur_railtype)->gui_sprites.signals[type][var][this->IsWidgetLowered(widget)];
PalSpriteID sprite = GetRailTypeInfo(_cur_railtype)->gui_sprites.signals[type][var][this->IsWidgetLowered(widget)];
this->DrawSignalSprite(widget, sprite);
}

@ -1719,22 +1719,22 @@ static void DrawTunnelBridgeRampSingleSignal(const TileInfo *ti, bool is_green,
SignalVariant variant = IsTunnelBridgeSemaphore(ti->tile) ? SIG_SEMAPHORE : SIG_ELECTRIC;
const RailtypeInfo *rti = GetRailTypeInfo(GetRailType(ti->tile));
SpriteID sprite = GetCustomSignalSprite(rti, ti->tile, type, variant, is_green ? SIGNAL_STATE_GREEN : SIGNAL_STATE_RED).sprite_id;
bool is_custom_sprite = (sprite != 0);
PalSpriteID sprite = GetCustomSignalSprite(rti, ti->tile, type, variant, is_green ? SIGNAL_STATE_GREEN : SIGNAL_STATE_RED).sprite;
bool is_custom_sprite = (sprite.sprite != 0);
if (is_custom_sprite) {
sprite += position;
sprite.sprite += position;
} else {
if (variant == SIG_ELECTRIC && type == SIGTYPE_NORMAL) {
/* Normal electric signals are picked from original sprites. */
sprite = SPR_ORIGINAL_SIGNALS_BASE + ((position << 1) + is_green);
sprite = { SPR_ORIGINAL_SIGNALS_BASE + ((position << 1) + is_green), PAL_NONE };
} else {
/* All other signals are picked from add on sprites. */
sprite = SPR_SIGNALS_BASE + ((type - 1) * 16 + variant * 64 + (position << 1) + is_green) + (IsSignalSpritePBS(type) ? 64 : 0);
sprite = { SPR_SIGNALS_BASE + ((type - 1) * 16 + variant * 64 + (position << 1) + is_green) + (IsSignalSpritePBS(type) ? 64 : 0), PAL_NONE };
}
}
AddSortableSpriteToDraw(sprite, PAL_NONE, x, y, 1, 1, TILE_HEIGHT, z, false, 0, 0, BB_Z_SEPARATOR);
AddSortableSpriteToDraw(sprite.sprite, sprite.pal, x, y, 1, 1, TILE_HEIGHT, z, false, 0, 0, BB_Z_SEPARATOR);
}
/* Draws a signal on tunnel / bridge entrance tile. */
@ -1804,21 +1804,22 @@ static void DrawBridgeSignalOnMiddlePart(const TileInfo *ti, TileIndex bridge_st
SignalState state = GetBridgeEntranceSimulatedSignalState(bridge_start_tile, m2_position);
const RailtypeInfo *rti = GetRailTypeInfo(GetRailType(bridge_start_tile));
SpriteID sprite = GetCustomSignalSprite(rti, bridge_start_tile, SIGTYPE_NORMAL, variant, state);
PalSpriteID sprite = GetCustomSignalSprite(rti, bridge_start_tile, SIGTYPE_NORMAL, variant, state).sprite;
if (sprite != 0) {
sprite += position;
if (sprite.sprite != 0) {
sprite.sprite += position;
} else {
if (variant == SIG_ELECTRIC) {
/* Normal electric signals are picked from original sprites. */
sprite = SPR_ORIGINAL_SIGNALS_BASE + (position << 1) + (state == SIGNAL_STATE_GREEN ? 1 : 0);
sprite.sprite = SPR_ORIGINAL_SIGNALS_BASE + (position << 1) + (state == SIGNAL_STATE_GREEN ? 1 : 0);
} else {
/* All other signals are picked from add on sprites. */
sprite = SPR_SIGNALS_BASE + (variant * 64) + (position << 1) - 16 + (state == SIGNAL_STATE_GREEN ? 1 : 0);
sprite.sprite = SPR_SIGNALS_BASE + (variant * 64) + (position << 1) - 16 + (state == SIGNAL_STATE_GREEN ? 1 : 0);
}
sprite.pal = PAL_NONE;
}
AddSortableSpriteToDraw(sprite, PAL_NONE, x, y, 1, 1, TILE_HEIGHT, z, false, 0, 0, BB_Z_SEPARATOR);
AddSortableSpriteToDraw(sprite.sprite, sprite.pal, x, y, 1, 1, TILE_HEIGHT, z, false, 0, 0, BB_Z_SEPARATOR);
}
m2_position++;
}

Loading…
Cancel
Save