TrackAndDirection (#1017)
* Create new helper struct for trackdirection * Split up into clear road or track * Try name offsets where possible * Update with knowledge from track branch
This commit is contained in:
parent
6e74345b08
commit
055def4215
|
@ -43,7 +43,7 @@ namespace OpenLoco::Vehicles
|
|||
static loco_global<int32_t, 0x011360FC> _11360FC;
|
||||
static loco_global<VehicleHead*, 0x01136240> _backupVeh0;
|
||||
static loco_global<int16_t, 0x01136248> _backup2E;
|
||||
static loco_global<int16_t, 0x0113624C> _backup2C;
|
||||
static loco_global<TrackAndDirection, 0x0113624C> _backup2C;
|
||||
static loco_global<int16_t, 0x01136250> _backupX;
|
||||
static loco_global<int16_t, 0x01136254> _backupY;
|
||||
static loco_global<uint8_t, 0x01136258> _backupZ;
|
||||
|
@ -139,7 +139,7 @@ namespace OpenLoco::Vehicles
|
|||
newBogie->tile_y = 0;
|
||||
newBogie->tile_base_z = 0;
|
||||
newBogie->var_2E = 0;
|
||||
newBogie->var_2C = 0;
|
||||
newBogie->var_2C = TrackAndDirection(0, 0);
|
||||
newBogie->var_36 = lastVeh->getVar36();
|
||||
newBogie->object_id = vehicleTypeId;
|
||||
|
||||
|
@ -258,7 +258,7 @@ namespace OpenLoco::Vehicles
|
|||
newBody->tile_y = 0;
|
||||
newBody->tile_base_z = 0;
|
||||
newBody->var_2E = 0;
|
||||
newBody->var_2C = 0;
|
||||
newBody->var_2C = TrackAndDirection(0, 0);
|
||||
newBody->var_36 = lastVeh->getVar36();
|
||||
newBody->var_38 = Flags38::unk_0; // different to create bogie
|
||||
newBody->object_id = vehicleTypeId;
|
||||
|
@ -468,7 +468,7 @@ namespace OpenLoco::Vehicles
|
|||
newHead->tile_base_z = 0;
|
||||
newHead->var_28 = 0;
|
||||
newHead->var_2E = 0;
|
||||
newHead->var_2C = 0;
|
||||
newHead->var_2C = TrackAndDirection(0, 0);
|
||||
newHead->var_36 = orderId * max_num_routing_steps;
|
||||
newHead->var_14 = 0;
|
||||
newHead->var_09 = 0;
|
||||
|
@ -506,7 +506,7 @@ namespace OpenLoco::Vehicles
|
|||
newVeh1->tile_base_z = 0;
|
||||
newVeh1->var_28 = 0;
|
||||
newVeh1->var_2E = 0;
|
||||
newVeh1->var_2C = 0;
|
||||
newVeh1->var_2C = TrackAndDirection(0, 0);
|
||||
newVeh1->var_36 = lastVeh->getVar36();
|
||||
newVeh1->var_14 = 0;
|
||||
newVeh1->var_09 = 0;
|
||||
|
@ -537,7 +537,7 @@ namespace OpenLoco::Vehicles
|
|||
newVeh2->tile_base_z = 0;
|
||||
newVeh2->var_28 = 0;
|
||||
newVeh2->var_2E = 0;
|
||||
newVeh2->var_2C = 0;
|
||||
newVeh2->var_2C = TrackAndDirection(0, 0);
|
||||
newVeh2->var_36 = lastVeh->getVar36();
|
||||
newVeh2->var_14 = 0;
|
||||
newVeh2->var_09 = 0;
|
||||
|
@ -574,7 +574,7 @@ namespace OpenLoco::Vehicles
|
|||
newTail->tile_base_z = 0;
|
||||
newTail->var_28 = 0;
|
||||
newTail->var_2E = 0;
|
||||
newTail->var_2C = 0;
|
||||
newTail->var_2C = TrackAndDirection(0, 0);
|
||||
newTail->var_36 = lastVeh->getVar36();
|
||||
newTail->var_14 = 0;
|
||||
newTail->var_09 = 0;
|
||||
|
@ -640,7 +640,7 @@ namespace OpenLoco::Vehicles
|
|||
}
|
||||
|
||||
// 0x004B05E4
|
||||
static void placeDownVehicle(VehicleHead* const head, const coord_t x, const coord_t y, const uint8_t baseZ, const uint16_t unk1, const uint16_t unk2)
|
||||
static void placeDownVehicle(VehicleHead* const head, const coord_t x, const coord_t y, const uint8_t baseZ, const TrackAndDirection unk1, const uint16_t unk2)
|
||||
{
|
||||
registers regs{};
|
||||
regs.esi = X86Pointer(head);
|
||||
|
@ -648,7 +648,7 @@ namespace OpenLoco::Vehicles
|
|||
regs.cx = y;
|
||||
regs.bx = unk2;
|
||||
regs.dl = baseZ;
|
||||
regs.ebp = unk1;
|
||||
regs.ebp = unk1.track._data;
|
||||
call(0x004B05E4, regs);
|
||||
}
|
||||
|
||||
|
|
|
@ -99,6 +99,54 @@ namespace OpenLoco::Vehicles
|
|||
constexpr uint8_t cAirportMovementNodeNull = 0xFF;
|
||||
|
||||
#pragma pack(push, 1)
|
||||
struct TrackAndDirection
|
||||
{
|
||||
struct _TrackAndDirection
|
||||
{
|
||||
uint16_t _data;
|
||||
constexpr _TrackAndDirection(uint8_t id, uint8_t direction)
|
||||
: _data((id << 3) | direction)
|
||||
{
|
||||
}
|
||||
constexpr uint8_t id() const { return (_data >> 3) & 0x3F; }
|
||||
constexpr uint8_t cardinalDirection() const { return _data & 0x3; }
|
||||
constexpr bool isReversed() const { return _data & (1 << 2); }
|
||||
constexpr bool operator==(const _TrackAndDirection other) const { return _data == other._data; }
|
||||
constexpr bool operator!=(const _TrackAndDirection other) const { return !(_data == other._data); }
|
||||
};
|
||||
struct _RoadAndDirection
|
||||
{
|
||||
uint16_t _data;
|
||||
constexpr _RoadAndDirection(uint8_t id, uint8_t direction)
|
||||
: _data((id << 3) | direction)
|
||||
{
|
||||
}
|
||||
constexpr uint8_t id() const { return (_data >> 3) & 0xF; }
|
||||
constexpr uint8_t cardinalDirection() const { return _data & 0x3; }
|
||||
// Used by road and tram vehicles to indicate side
|
||||
constexpr bool isReversed() const { return _data & (1 << 2); }
|
||||
// Road vehicles are briefly back to front when reaching dead ends
|
||||
// Trams can stay back to front
|
||||
constexpr bool isBackToFront() const { return _data & (1 << 7); }
|
||||
// Related to road vehicles turning around
|
||||
constexpr bool isUnk8() const { return _data & (1 << 8); }
|
||||
constexpr bool operator==(const _RoadAndDirection other) const { return _data == other._data; }
|
||||
constexpr bool operator!=(const _RoadAndDirection other) const { return !(_data == other._data); }
|
||||
};
|
||||
|
||||
union
|
||||
{
|
||||
_TrackAndDirection track;
|
||||
_RoadAndDirection road;
|
||||
};
|
||||
|
||||
constexpr TrackAndDirection(uint8_t id, uint8_t direction)
|
||||
: track(id, direction)
|
||||
{
|
||||
}
|
||||
};
|
||||
static_assert(sizeof(TrackAndDirection) == 2);
|
||||
|
||||
struct VehicleBase : EntityBase
|
||||
{
|
||||
private:
|
||||
|
@ -205,7 +253,7 @@ namespace OpenLoco::Vehicles
|
|||
uint8_t pad_24[0x26 - 0x24];
|
||||
EntityId_t head; // 0x26
|
||||
uint32_t var_28;
|
||||
uint16_t var_2C;
|
||||
TrackAndDirection var_2C;
|
||||
uint16_t var_2E;
|
||||
int16_t tile_x; // 0x30
|
||||
int16_t tile_y; // 0x32
|
||||
|
@ -348,7 +396,7 @@ namespace OpenLoco::Vehicles
|
|||
uint8_t pad_24[0x26 - 0x24];
|
||||
EntityId_t head; // 0x26
|
||||
uint32_t var_28;
|
||||
uint16_t var_2C;
|
||||
TrackAndDirection var_2C;
|
||||
uint16_t var_2E;
|
||||
int16_t tile_x; // 0x30
|
||||
int16_t tile_y; // 0x32
|
||||
|
@ -380,7 +428,7 @@ namespace OpenLoco::Vehicles
|
|||
uint8_t pad_24[0x26 - 0x24];
|
||||
EntityId_t head; // 0x26
|
||||
uint32_t var_28;
|
||||
uint16_t var_2C;
|
||||
TrackAndDirection var_2C;
|
||||
uint16_t var_2E;
|
||||
int16_t tile_x; // 0x30
|
||||
int16_t tile_y; // 0x32
|
||||
|
@ -426,7 +474,7 @@ namespace OpenLoco::Vehicles
|
|||
ColourScheme colour_scheme; // 0x24
|
||||
EntityId_t head; // 0x26
|
||||
uint8_t pad_28[0x2C - 0x28];
|
||||
uint16_t var_2C;
|
||||
TrackAndDirection var_2C;
|
||||
uint16_t var_2E;
|
||||
int16_t tile_x; // 0x30
|
||||
int16_t tile_y; // 0x32
|
||||
|
@ -481,7 +529,7 @@ namespace OpenLoco::Vehicles
|
|||
ColourScheme colour_scheme; // 0x24
|
||||
EntityId_t head; // 0x26
|
||||
uint8_t pad_28[0x2C - 0x28];
|
||||
uint16_t var_2C;
|
||||
TrackAndDirection var_2C;
|
||||
uint16_t var_2E;
|
||||
int16_t tile_x; // 0x30
|
||||
int16_t tile_y; // 0x32
|
||||
|
@ -524,7 +572,7 @@ namespace OpenLoco::Vehicles
|
|||
uint8_t pad_24[0x26 - 0x24];
|
||||
EntityId_t head; // 0x26
|
||||
uint32_t var_28;
|
||||
uint16_t var_2C;
|
||||
TrackAndDirection var_2C;
|
||||
uint16_t var_2E;
|
||||
int16_t tile_x; // 0x30
|
||||
int16_t tile_y; // 0x32
|
||||
|
|
|
@ -165,8 +165,8 @@ namespace OpenLoco::Vehicles
|
|||
}
|
||||
else
|
||||
{
|
||||
ah = vehicle_arr_4F865C[frontBogie->var_2C >> 2];
|
||||
if (((frontBogie->var_2C >> 3) == 12) || ((frontBogie->var_2C >> 3) == 13))
|
||||
ah = vehicle_arr_4F865C[frontBogie->var_2C.track._data >> 2];
|
||||
if ((frontBogie->var_2C.track.id() == 12) || (frontBogie->var_2C.track.id() == 13))
|
||||
{
|
||||
if (frontBogie->var_2E >= 48)
|
||||
{
|
||||
|
@ -982,9 +982,9 @@ namespace OpenLoco::Vehicles
|
|||
continue;
|
||||
if (track->baseZ() != frontBogie->tile_base_z)
|
||||
continue;
|
||||
if (track->trackId() != ((frontBogie->var_2C >> 3) & 0x3F))
|
||||
if (track->trackId() != frontBogie->var_2C.track.id())
|
||||
continue;
|
||||
if (track->unkDirection() != (frontBogie->var_2C & 0x3))
|
||||
if (track->unkDirection() != frontBogie->var_2C.track.cardinalDirection())
|
||||
continue;
|
||||
if (!track->hasStationElement())
|
||||
continue;
|
||||
|
@ -1225,12 +1225,12 @@ namespace OpenLoco::Vehicles
|
|||
auto yaw = (sprite_yaw + 16) & 0x3F;
|
||||
auto firstBogie = var_38 & Flags38::isReversed ? backBogie : frontBogie;
|
||||
auto unkFactor = 5;
|
||||
if (!trackIdToSparkDirection[firstBogie->var_2C / 8])
|
||||
if (!trackIdToSparkDirection[(firstBogie->var_2C.road._data >> 3)])
|
||||
{
|
||||
unkFactor = -5;
|
||||
}
|
||||
|
||||
if (firstBogie->var_2C & (1 << 2))
|
||||
if (firstBogie->var_2C.road.isReversed())
|
||||
{
|
||||
unkFactor = -unkFactor;
|
||||
}
|
||||
|
|
|
@ -932,7 +932,7 @@ namespace OpenLoco::Vehicles
|
|||
|
||||
if (track_type == 0xFF || ObjectManager::get<RoadObject>(track_type)->flags & Flags12::isRoad)
|
||||
{
|
||||
if (train.veh1->var_2C & (1 << 7))
|
||||
if (train.veh1->var_2C.road.isBackToFront())
|
||||
{
|
||||
param1 = 128;
|
||||
turnaroundAtSignalTimeout = 544;
|
||||
|
@ -942,7 +942,7 @@ namespace OpenLoco::Vehicles
|
|||
{
|
||||
// Tram
|
||||
turnaroundAtSignalTimeout = tramSignalTimeout;
|
||||
if (train.veh1->var_2C & (1 << 7))
|
||||
if (train.veh1->var_2C.road.isBackToFront())
|
||||
{
|
||||
param1 = 64;
|
||||
turnaroundAtSignalTimeout = 128;
|
||||
|
@ -2526,8 +2526,8 @@ namespace OpenLoco::Vehicles
|
|||
case TransportMode::rail:
|
||||
{
|
||||
auto tile = Map::TileManager::get(Pos2{ bogie->tile_x, bogie->tile_y });
|
||||
auto direction = bogie->var_2C & 3;
|
||||
auto trackId = (bogie->var_2C >> 3) & 0x3F;
|
||||
auto direction = bogie->var_2C.track.cardinalDirection();
|
||||
auto trackId = bogie->var_2C.track.id();
|
||||
auto loadingModifier = 12;
|
||||
auto* elStation = tile.trackStation(trackId, direction, bogie->tile_base_z);
|
||||
if (elStation != nullptr)
|
||||
|
@ -2545,8 +2545,8 @@ namespace OpenLoco::Vehicles
|
|||
case TransportMode::road:
|
||||
{
|
||||
auto tile = Map::TileManager::get(Pos2{ bogie->tile_x, bogie->tile_y });
|
||||
auto direction = bogie->var_2C & 3;
|
||||
auto roadId = (bogie->var_2C >> 3) & 0xF;
|
||||
auto direction = bogie->var_2C.road.cardinalDirection();
|
||||
auto roadId = bogie->var_2C.road.id();
|
||||
auto loadingModifier = 2;
|
||||
auto* elStation = tile.roadStation(roadId, direction, bogie->tile_base_z);
|
||||
if (elStation != nullptr)
|
||||
|
@ -3204,8 +3204,8 @@ namespace OpenLoco::Vehicles
|
|||
|
||||
static StationId_t tryFindStationAt(VehicleBogie* bogie)
|
||||
{
|
||||
auto direction = bogie->var_2C & 3;
|
||||
auto trackId = (bogie->var_2C >> 3) & 0x3F;
|
||||
auto direction = bogie->var_2C.track.cardinalDirection();
|
||||
auto trackId = bogie->var_2C.track.id();
|
||||
|
||||
auto tile = TileManager::get(Map::Pos2{ bogie->tile_x, bogie->tile_y });
|
||||
auto* elStation = tile.trackStation(trackId, direction, bogie->tile_base_z);
|
||||
|
@ -3332,7 +3332,7 @@ namespace OpenLoco::Vehicles
|
|||
if (elRoad->isGhost() || elRoad->isFlag5())
|
||||
continue;
|
||||
|
||||
if (elRoad->roadId() != ((veh->var_2C >> 3) & 0xF))
|
||||
if (elRoad->roadId() != veh->var_2C.road.id())
|
||||
continue;
|
||||
|
||||
return true;
|
||||
|
@ -3354,10 +3354,10 @@ namespace OpenLoco::Vehicles
|
|||
if (elTrack->isGhost() || elTrack->isFlag5())
|
||||
continue;
|
||||
|
||||
if (elTrack->unkDirection() != (veh->var_2C & 0x3))
|
||||
if (elTrack->unkDirection() != veh->var_2C.track.cardinalDirection())
|
||||
continue;
|
||||
|
||||
if (elTrack->trackId() != ((veh->var_2C >> 3) & 0x3F))
|
||||
if (elTrack->trackId() != veh->var_2C.track.id())
|
||||
continue;
|
||||
|
||||
return true;
|
||||
|
|
Loading…
Reference in New Issue