mirror of https://github.com/OpenRCT2/OpenRCT2.git
implement ride_modify and supporting methods
This commit is contained in:
parent
508ed131f7
commit
ad84e6d076
|
@ -827,7 +827,7 @@ static void game_handle_input_mouse(int x, int y, int state)
|
||||||
RCT2_CALLPROC_X(0x006B4857, eax, 0, ecx, (int)map_element, 0, 0, 0);
|
RCT2_CALLPROC_X(0x006B4857, eax, 0, ecx, (int)map_element, 0, 0, 0);
|
||||||
break;
|
break;
|
||||||
case 3:
|
case 3:
|
||||||
RCT2_CALLPROC_X(0x006CC056, eax, 0, ecx, (int)map_element, 0, 0, 0);
|
ride_modify(map_element, eax, ecx);
|
||||||
break;
|
break;
|
||||||
case 5:
|
case 5:
|
||||||
RCT2_CALLPROC_X(0x006E08D2, eax, 0, ecx, (int)map_element, 0, 0, 0);
|
RCT2_CALLPROC_X(0x006E08D2, eax, 0, ecx, (int)map_element, 0, 0, 0);
|
||||||
|
|
|
@ -1053,6 +1053,9 @@ enum {
|
||||||
|
|
||||||
STR_SELECT_MUSIC_STYLE_TIP = 3045,
|
STR_SELECT_MUSIC_STYLE_TIP = 3045,
|
||||||
|
|
||||||
|
STR_THIS_RIDE_CANNOT_BE_MODIFIED = 3046,
|
||||||
|
STR_LOCAL_AUTHORITY_FORBIDS_DEMOLITION_OR_MODIFICATIONS_TO_THIS_RIDE = 3047,
|
||||||
|
|
||||||
STR_WHITE = 3055,
|
STR_WHITE = 3055,
|
||||||
STR_TRANSLUCENT = 3056,
|
STR_TRANSLUCENT = 3056,
|
||||||
STR_CONSTRUCTION_MARKER = 3057,
|
STR_CONSTRUCTION_MARKER = 3057,
|
||||||
|
|
|
@ -182,6 +182,8 @@ enum PEEP_THOUGHT_TYPE {
|
||||||
};
|
};
|
||||||
|
|
||||||
enum PEEP_STATE {
|
enum PEEP_STATE {
|
||||||
|
PEEP_STATE_0 = 0,
|
||||||
|
|
||||||
PEEP_STATE_QUEUING_FRONT = 2,
|
PEEP_STATE_QUEUING_FRONT = 2,
|
||||||
PEEP_STATE_ON_RIDE = 3,
|
PEEP_STATE_ON_RIDE = 3,
|
||||||
PEEP_STATE_LEAVING_RIDE = 4,
|
PEEP_STATE_LEAVING_RIDE = 4,
|
||||||
|
@ -321,7 +323,7 @@ typedef struct {
|
||||||
sint16 var_18;
|
sint16 var_18;
|
||||||
sint16 var_1A;
|
sint16 var_1A;
|
||||||
sint16 var_1C;
|
sint16 var_1C;
|
||||||
uint8 sprite_direction;
|
uint8 sprite_direction; // 0x1E
|
||||||
uint8 pad_1F[3];
|
uint8 pad_1F[3];
|
||||||
uint16 name_string_idx; // 0x22
|
uint16 name_string_idx; // 0x22
|
||||||
uint16 next_x; // 0x24
|
uint16 next_x; // 0x24
|
||||||
|
|
510
src/ride/ride.c
510
src/ride/ride.c
|
@ -451,6 +451,42 @@ void reset_all_ride_build_dates()
|
||||||
|
|
||||||
#pragma region Construction
|
#pragma region Construction
|
||||||
|
|
||||||
|
static int ride_check_if_construction_allowed(rct_ride *ride)
|
||||||
|
{
|
||||||
|
if (ride->lifecycle_flags & RIDE_LIFECYCLE_BROKEN_DOWN) {
|
||||||
|
RCT2_GLOBAL(0x013CE952 + 6, uint16) = ride->name;
|
||||||
|
RCT2_GLOBAL(0x013CE952 + 8, uint32) = ride->name_arguments;
|
||||||
|
window_error_open(STR_CANT_START_CONSTRUCTION_ON, STR_HAS_BROKEN_DOWN_AND_REQUIRES_FIXING);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (ride->status != RIDE_STATUS_CLOSED) {
|
||||||
|
RCT2_GLOBAL(0x013CE952 + 6, uint16) = ride->name;
|
||||||
|
RCT2_GLOBAL(0x013CE952 + 8, uint32) = ride->name_arguments;
|
||||||
|
window_error_open(STR_CANT_START_CONSTRUCTION_ON, STR_MUST_BE_CLOSED_FIRST);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
static rct_window *ride_create_or_find_construction_window(int rideIndex)
|
||||||
|
{
|
||||||
|
rct_window *w;
|
||||||
|
|
||||||
|
w = window_find_by_class(WC_RIDE_CONSTRUCTION);
|
||||||
|
if (w == NULL || w->number != rideIndex) {
|
||||||
|
window_close_construction_windows();
|
||||||
|
RCT2_GLOBAL(0x00F440A7, uint8) = rideIndex;
|
||||||
|
w = window_construction_open(rideIndex);
|
||||||
|
} else {
|
||||||
|
RCT2_CALLPROC_X(0x006C9627, 0, 0, 0, 0, 0, 0, 0);
|
||||||
|
RCT2_GLOBAL(0x00F440A7, uint8) = rideIndex;
|
||||||
|
}
|
||||||
|
|
||||||
|
return w;
|
||||||
|
}
|
||||||
|
|
||||||
int ride_create_ride(ride_list_item listItem)
|
int ride_create_ride(ride_list_item listItem)
|
||||||
{
|
{
|
||||||
int eax, ebx, ecx, edx, esi, edi, ebp;
|
int eax, ebx, ecx, edx, esi, edi, ebp;
|
||||||
|
@ -490,54 +526,444 @@ void ride_construct_new(ride_list_item listItem)
|
||||||
window_close_by_number(WC_RIDE, rideIndex);
|
window_close_by_number(WC_RIDE, rideIndex);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* rct2: 0x006C84CE
|
||||||
|
*/
|
||||||
|
static void sub_6C84CE()
|
||||||
|
{
|
||||||
|
RCT2_CALLPROC_X(0x006C84CE, 0, 0, 0, 0, 0, 0, 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* rct2: 0x006DD4D5
|
||||||
|
*/
|
||||||
|
static void ride_remove_cable_lift(rct_ride *ride)
|
||||||
|
{
|
||||||
|
uint16 spriteIndex;
|
||||||
|
rct_vehicle *vehicle;
|
||||||
|
|
||||||
|
if (ride->lifecycle_flags & RIDE_LIFECYCLE_CABLE_LIFT) {
|
||||||
|
ride->lifecycle_flags &= ~RIDE_LIFECYCLE_CABLE_LIFT;
|
||||||
|
spriteIndex = ride->cable_lift;
|
||||||
|
do {
|
||||||
|
vehicle = &(g_sprite_list[spriteIndex].vehicle);
|
||||||
|
RCT2_CALLPROC_X(0x006EC473, 0, 0, 0, 0, (int)vehicle, 0, 0);
|
||||||
|
RCT2_CALLPROC_X(0x0069EDB6, 0, 0, 0, 0, (int)vehicle, 0, 0);
|
||||||
|
spriteIndex = vehicle->next_vehicle_on_train;
|
||||||
|
} while (spriteIndex != SPRITE_INDEX_NULL);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* rct2: 0x006DD506
|
||||||
|
*/
|
||||||
|
static void ride_remove_vehicles(rct_ride *ride)
|
||||||
|
{
|
||||||
|
int i;
|
||||||
|
uint16 spriteIndex;
|
||||||
|
rct_vehicle *vehicle;
|
||||||
|
|
||||||
|
if (ride->lifecycle_flags & RIDE_LIFECYCLE_ON_TRACK) {
|
||||||
|
ride->lifecycle_flags &= ~RIDE_LIFECYCLE_ON_TRACK;
|
||||||
|
ride->lifecycle_flags &= ~(RIDE_LIFECYCLE_TEST_IN_PROGRESS | RIDE_LIFECYCLE_11);
|
||||||
|
|
||||||
|
for (i = 0; i < 32; i++) {
|
||||||
|
spriteIndex = ride->vehicles[i];
|
||||||
|
while (spriteIndex != SPRITE_INDEX_NULL) {
|
||||||
|
vehicle = &(g_sprite_list[spriteIndex].vehicle);
|
||||||
|
RCT2_CALLPROC_X(0x006EC473, 0, 0, 0, 0, (int)vehicle, 0, 0);
|
||||||
|
RCT2_CALLPROC_X(0x0069EDB6, 0, 0, 0, 0, (int)vehicle, 0, 0);
|
||||||
|
spriteIndex = vehicle->next_vehicle_on_train;
|
||||||
|
}
|
||||||
|
|
||||||
|
ride->vehicles[i] = SPRITE_INDEX_NULL;
|
||||||
|
}
|
||||||
|
|
||||||
|
for (i = 0; i < 4; i++)
|
||||||
|
ride->var_066[i] = 255;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* rct2: 0x006DD4AC
|
||||||
|
*/
|
||||||
|
static void ride_clear_for_construction(int rideIndex)
|
||||||
|
{
|
||||||
|
rct_ride *ride;
|
||||||
|
rct_window *w;
|
||||||
|
|
||||||
|
ride = GET_RIDE(rideIndex);
|
||||||
|
|
||||||
|
ride_measurement_clear(ride);
|
||||||
|
|
||||||
|
ride->lifecycle_flags &= ~(RIDE_LIFECYCLE_BREAKDOWN_PENDING | RIDE_LIFECYCLE_BROKEN_DOWN);
|
||||||
|
ride->var_14D |= 0x0C;
|
||||||
|
|
||||||
|
ride_remove_cable_lift(ride);
|
||||||
|
ride_remove_vehicles(ride);
|
||||||
|
|
||||||
|
w = window_find_by_number(WC_RIDE, rideIndex);
|
||||||
|
if (w != NULL)
|
||||||
|
window_event_helper(w, 0, WE_RESIZE);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* rct2: 0x006664DF
|
||||||
|
*/
|
||||||
|
static void ride_remove_peeps(int rideIndex)
|
||||||
|
{
|
||||||
|
int i, stationIndex, x, y, z, exitX, exitY, exitZ, exitDirection;
|
||||||
|
uint16 xy, spriteIndex;
|
||||||
|
rct_ride *ride;
|
||||||
|
rct_map_element *mapElement;
|
||||||
|
rct_peep *peep;
|
||||||
|
|
||||||
|
ride = GET_RIDE(rideIndex);
|
||||||
|
|
||||||
|
// Find first station
|
||||||
|
stationIndex = -1;
|
||||||
|
for (i = 0; i < 4; i++) {
|
||||||
|
if (ride->station_starts[i] != 0xFFFF) {
|
||||||
|
stationIndex = i;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Get exit position and direction
|
||||||
|
exitDirection = 255;
|
||||||
|
if (stationIndex != -1) {
|
||||||
|
xy = ride->exits[stationIndex];
|
||||||
|
if (xy != 0xFFFF) {
|
||||||
|
exitX = xy & 0xFF;
|
||||||
|
exitY = xy >> 8;
|
||||||
|
exitZ = ride->station_heights[stationIndex];
|
||||||
|
mapElement = ride_get_station_exit_element(ride, exitX, exitY, exitZ);
|
||||||
|
|
||||||
|
exitDirection = mapElement->type & 3;
|
||||||
|
exitX = (exitX * 32) - (RCT2_ADDRESS(0x00981D6C, sint16)[exitDirection * 2] * 20) + 16;
|
||||||
|
exitY = (exitY * 32) - (RCT2_ADDRESS(0x00981D6E, sint16)[exitDirection * 2] * 20) + 16;
|
||||||
|
exitZ = (exitZ * 8) + 2;
|
||||||
|
|
||||||
|
// Reverse direction
|
||||||
|
exitDirection ^= 2;
|
||||||
|
|
||||||
|
exitDirection *= 8;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Place all the peeps at exit
|
||||||
|
FOR_ALL_PEEPS(spriteIndex, peep) {
|
||||||
|
if (
|
||||||
|
peep->state == PEEP_STATE_QUEUING_FRONT ||
|
||||||
|
peep->state == PEEP_STATE_ENTERING_RIDE ||
|
||||||
|
peep->state == PEEP_STATE_LEAVING_RIDE ||
|
||||||
|
peep->state == PEEP_STATE_ON_RIDE
|
||||||
|
) {
|
||||||
|
if (peep->current_ride != rideIndex)
|
||||||
|
continue;
|
||||||
|
|
||||||
|
RCT2_CALLPROC_X(0x0069A409, 0, 0, 0, 0, (int)peep, 0, 0);
|
||||||
|
if (peep->state == PEEP_STATE_QUEUING_FRONT && peep->var_2C == 0)
|
||||||
|
RCT2_CALLPROC_X(0x006966A9, 0, 0, 0, 0, (int)peep, 0, 0);
|
||||||
|
|
||||||
|
RCT2_CALLPROC_X(0x006EC473, 0, 0, 0, 0, (int)peep, 0, 0);
|
||||||
|
|
||||||
|
if (exitDirection == 255) {
|
||||||
|
x = peep->next_x + 16;
|
||||||
|
y = peep->next_y + 16;
|
||||||
|
z = (peep->next_z & 0xFF) * 8;
|
||||||
|
if ((peep->next_z >> 8) & 4)
|
||||||
|
z += 8;
|
||||||
|
z++;
|
||||||
|
RCT2_CALLPROC_X(0x0069E9D3, exitX, 0, exitY, exitZ, (int)peep, 0, 0);
|
||||||
|
} else {
|
||||||
|
RCT2_CALLPROC_X(0x0069E9D3, exitX, 0, exitY, exitZ, (int)peep, 0, 0);
|
||||||
|
peep->sprite_direction = exitDirection;
|
||||||
|
}
|
||||||
|
|
||||||
|
RCT2_CALLPROC_X(0x006EC473, 0, 0, 0, 0, (int)peep, 0, 0);
|
||||||
|
peep->state = PEEP_STATE_0;
|
||||||
|
RCT2_CALLPROC_X(0x00693BE5, 0, 0, 0, 0, (int)peep, 0, 0);
|
||||||
|
|
||||||
|
peep->happiness = min(peep->happiness, peep->happiness_growth_rate) / 2;
|
||||||
|
peep->happiness_growth_rate = peep->happiness;
|
||||||
|
peep->var_45 |= 2;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
ride->num_riders = 0;
|
||||||
|
ride->var_15D = 0;
|
||||||
|
ride->var_14D |= 4;
|
||||||
|
}
|
||||||
|
|
||||||
|
void sub_6C683D(int x, int y, int z, int direction, int type, int esi, int edi, int ebp)
|
||||||
|
{
|
||||||
|
RCT2_CALLPROC_X(0x006C683D, x, (direction << 8) | type, y, z, esi, edi, ebp);
|
||||||
|
}
|
||||||
|
|
||||||
|
void sub_6CE254()
|
||||||
|
{
|
||||||
|
RCT2_CALLPROC_X(0x006CE254, 0, 0, 0, 0, 0, 0, 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void sub_6C96C0()
|
||||||
|
{
|
||||||
|
RCT2_CALLPROC_X(0x006C96C0, 0, 0, 0, 0, 0, 0, 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void sub_6C9627()
|
||||||
|
{
|
||||||
|
switch (RCT2_GLOBAL(0x00F440A6, uint8)) {
|
||||||
|
case 3:
|
||||||
|
sub_6C683D(
|
||||||
|
RCT2_GLOBAL(0x00F440A8, uint16),
|
||||||
|
RCT2_GLOBAL(0x00F440AA, uint16),
|
||||||
|
RCT2_GLOBAL(0x00F440AC, uint16),
|
||||||
|
RCT2_GLOBAL(0x00F440AE, uint8) & 3,
|
||||||
|
RCT2_GLOBAL(0x00F440AF, uint8),
|
||||||
|
0,
|
||||||
|
0,
|
||||||
|
1
|
||||||
|
);
|
||||||
|
break;
|
||||||
|
case 6:
|
||||||
|
case 7:
|
||||||
|
case 8:
|
||||||
|
sub_6CE254();
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
if (RCT2_GLOBAL(0x00F440B0, uint8) & 1) {
|
||||||
|
RCT2_GLOBAL(0x00F440B0, uint8) &= ~1;
|
||||||
|
RCT2_GLOBAL(RCT2_ADDRESS_MAP_SELECTION_FLAGS, uint8) &= ~4;
|
||||||
|
map_invalidate_tile_full(RCT2_GLOBAL(0x00F440A8, uint16), RCT2_GLOBAL(0x00F440AA, uint16));
|
||||||
|
}
|
||||||
|
sub_6C96C0();
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* rct2: 0x006C9296
|
||||||
|
*/
|
||||||
|
static void sub_6C9296()
|
||||||
|
{
|
||||||
|
RCT2_CALLPROC_X(0x006C9296, 0, 0, 0, 0, 0, 0, 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* rct2: 0x006C93B8
|
||||||
|
*/
|
||||||
|
static void sub_6C93B8()
|
||||||
|
{
|
||||||
|
RCT2_CALLPROC_X(0x006C93B8, 0, 0, 0, 0, 0, 0, 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* rct2: 0x006CC2CA
|
||||||
|
*/
|
||||||
|
static int ride_modify_entrance_or_exit(rct_map_element *mapElement, int x, int y)
|
||||||
|
{
|
||||||
|
int rideIndex, entranceType;
|
||||||
|
rct_window *constructionWindow;
|
||||||
|
|
||||||
|
rideIndex = mapElement->properties.entrance.ride_index;
|
||||||
|
|
||||||
|
entranceType = mapElement->properties.entrance.type;
|
||||||
|
if (entranceType != ENTRANCE_TYPE_RIDE_ENTRANCE && entranceType != ENTRANCE_TYPE_RIDE_EXIT)
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
int bl = (mapElement->properties.entrance.index & 0x70) >> 4;
|
||||||
|
|
||||||
|
// Get or create construction window for ride
|
||||||
|
constructionWindow = window_find_by_class(WC_RIDE_CONSTRUCTION);
|
||||||
|
if (constructionWindow == NULL) {
|
||||||
|
if (!sub_6CC3FB(rideIndex))
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
constructionWindow = window_find_by_class(WC_RIDE_CONSTRUCTION);
|
||||||
|
if (constructionWindow == NULL)
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
sub_6C9627();
|
||||||
|
if (
|
||||||
|
RCT2_GLOBAL(0x00F440A6, uint8) != 5 ||
|
||||||
|
!(RCT2_GLOBAL(RCT2_ADDRESS_INPUT_FLAGS, uint8) & INPUT_FLAG_TOOL_ACTIVE) ||
|
||||||
|
RCT2_GLOBAL(RCT2_ADDRESS_TOOL_WINDOWCLASS, rct_windowclass) != WC_RIDE_CONSTRUCTION
|
||||||
|
) {
|
||||||
|
// Replace entrance / exit
|
||||||
|
tool_set(constructionWindow, entranceType == 0 ? 29 : 30, 12);
|
||||||
|
RCT2_GLOBAL(0x00F44191, uint8) = entranceType;
|
||||||
|
RCT2_GLOBAL(0x00F44192, uint8) = rideIndex;
|
||||||
|
RCT2_GLOBAL(0x00F44193, uint8) = bl;
|
||||||
|
RCT2_GLOBAL(RCT2_ADDRESS_INPUT_FLAGS, uint8) |= INPUT_FLAG_6;
|
||||||
|
int al = RCT2_GLOBAL(0x00F440A6, uint8);
|
||||||
|
if (al != 5) {
|
||||||
|
RCT2_GLOBAL(0x00F440A6, uint8) = 5;
|
||||||
|
RCT2_GLOBAL(0x00F440CC, uint8) = al;
|
||||||
|
}
|
||||||
|
|
||||||
|
sub_6C84CE();
|
||||||
|
RCT2_GLOBAL(RCT2_ADDRESS_MAP_SELECTION_FLAGS, uint16) &= ~2;
|
||||||
|
} else {
|
||||||
|
// Remove entrance / exit
|
||||||
|
game_do_command(x, 9, y, rideIndex, GAME_COMMAND_13, bl, 0);
|
||||||
|
RCT2_GLOBAL(RCT2_ADDRESS_TOOL_WIDGETINDEX, uint16) = entranceType == ENTRANCE_TYPE_RIDE_ENTRANCE ? 29 : 30;
|
||||||
|
RCT2_GLOBAL(0x00F44191, uint8) = entranceType;
|
||||||
|
}
|
||||||
|
|
||||||
|
window_invalidate_by_class(WC_RIDE_CONSTRUCTION);
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* rct2: 0x006CC287
|
||||||
|
*/
|
||||||
|
int ride_modify_maze(rct_map_element *mapElement, int x, int y)
|
||||||
|
{
|
||||||
|
RCT2_GLOBAL(0x00F440A7, uint8) = mapElement->properties.track.ride_index;
|
||||||
|
RCT2_GLOBAL(0x00F440A6, uint8) = 6;
|
||||||
|
RCT2_GLOBAL(0x00F440A8, uint16) = x;
|
||||||
|
RCT2_GLOBAL(0x00F440AA, uint16) = y;
|
||||||
|
RCT2_GLOBAL(0x00F440AC, uint16) = mapElement->base_height * 8;
|
||||||
|
RCT2_GLOBAL(0x00F440B0, uint8) = 0;
|
||||||
|
RCT2_GLOBAL(0x00F440B1, uint8) = 0;
|
||||||
|
RCT2_CALLPROC_X(0x006CD887, 0, 0, 0, 0, 0, 0, 0);
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
*
|
*
|
||||||
* rct2: 0x006CC056
|
* rct2: 0x006CC056
|
||||||
*/
|
*/
|
||||||
int ride_try_construct(rct_map_element *trackMapElement)
|
int ride_modify(rct_map_element *mapElement, int x, int y)
|
||||||
{
|
{
|
||||||
// Success stored in carry flag which can't be accessed after call using is macro
|
int rideIndex, z, direction, type;
|
||||||
RCT2_CALLPROC_X(0x006CC056, 0, 0, 0, (int)trackMapElement, 0, 0, 0);
|
rct_ride *ride;
|
||||||
|
rct_window *constructionWindow;
|
||||||
|
|
||||||
|
rideIndex = mapElement->properties.track.ride_index;
|
||||||
|
ride = GET_RIDE(rideIndex);
|
||||||
|
|
||||||
|
if (!ride_check_if_construction_allowed(ride))
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
if (ride->lifecycle_flags & RIDE_LIFECYCLE_INDESTRUCTIBLE) {
|
||||||
|
RCT2_GLOBAL(0x013CE952 + 6, uint16) = ride->name;
|
||||||
|
RCT2_GLOBAL(0x013CE952 + 8, uint32) = ride->name_arguments;
|
||||||
|
window_error_open(STR_CANT_START_CONSTRUCTION_ON, STR_LOCAL_AUTHORITY_FORBIDS_DEMOLITION_OR_MODIFICATIONS_TO_THIS_RIDE);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (ride->lifecycle_flags & RIDE_LIFECYCLE_19) {
|
||||||
|
RCT2_GLOBAL(0x013CE952 + 6, uint16) = ride->name;
|
||||||
|
RCT2_GLOBAL(0x013CE952 + 8, uint32) = ride->name_arguments;
|
||||||
|
window_error_open(STR_CANT_START_CONSTRUCTION_ON, STR_THIS_RIDE_CANNOT_BE_MODIFIED);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
ride_clear_for_construction(rideIndex);
|
||||||
|
ride_remove_peeps(rideIndex);
|
||||||
|
|
||||||
|
// Check if element is a station entrance or exit
|
||||||
|
if ((mapElement->type & MAP_ELEMENT_TYPE_MASK) == MAP_ELEMENT_TYPE_ENTRANCE)
|
||||||
|
return ride_modify_entrance_or_exit(mapElement, x, y);
|
||||||
|
|
||||||
|
constructionWindow = ride_create_or_find_construction_window(rideIndex);
|
||||||
|
|
||||||
|
if (ride->type == RIDE_TYPE_MAZE)
|
||||||
|
return ride_modify_maze(mapElement, x, y);
|
||||||
|
|
||||||
|
if (RCT2_GLOBAL(0x0097CF40 + (ride->type * 8), uint32) & 0x100) {
|
||||||
|
int outX, outY;
|
||||||
|
mapElement = ride_find_track_gap(mapElement, &outX, &outY);
|
||||||
|
}
|
||||||
|
|
||||||
|
z = mapElement->base_height * 8;
|
||||||
|
direction = mapElement->type & 3;
|
||||||
|
type = mapElement->properties.track.type;
|
||||||
|
sub_6C683D(x, y, z, direction, type, 0, 0, 0);
|
||||||
|
|
||||||
|
RCT2_GLOBAL(0x00F440A7, uint8) = rideIndex;
|
||||||
|
RCT2_GLOBAL(0x00F440A6, uint8) = 3;
|
||||||
|
RCT2_GLOBAL(0x00F440A8, uint16) = x;
|
||||||
|
RCT2_GLOBAL(0x00F440AA, uint16) = y;
|
||||||
|
RCT2_GLOBAL(0x00F440AC, uint16) = z;
|
||||||
|
RCT2_GLOBAL(0x00F440AE, uint8) = direction;
|
||||||
|
RCT2_GLOBAL(0x00F440AF, uint8) = type;
|
||||||
|
RCT2_GLOBAL(0x00F440B0, uint8) = 0;
|
||||||
|
RCT2_GLOBAL(0x00F440B1, uint8) = 0;
|
||||||
|
|
||||||
|
if (RCT2_GLOBAL(0x0097CF40 + (ride->type * 8), uint32) & 0x8000) {
|
||||||
|
sub_6C84CE();
|
||||||
return 1;
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
sub_6C9296();
|
||||||
|
if (RCT2_GLOBAL(0x00F440A6, uint8) == 1) {
|
||||||
|
sub_6C84CE();
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
RCT2_GLOBAL(0x00F440A6, uint8) = 3;
|
||||||
|
RCT2_GLOBAL(0x00F440A8, uint16) = x;
|
||||||
|
RCT2_GLOBAL(0x00F440AA, uint16) = y;
|
||||||
|
RCT2_GLOBAL(0x00F440AC, uint16) = z;
|
||||||
|
RCT2_GLOBAL(0x00F440AE, uint8) = direction;
|
||||||
|
RCT2_GLOBAL(0x00F440AF, uint8) = type;
|
||||||
|
RCT2_GLOBAL(0x00F440B0, uint8) = 0;
|
||||||
|
RCT2_GLOBAL(0x00F440B1, uint8) = 0;
|
||||||
|
|
||||||
|
sub_6C93B8();
|
||||||
|
|
||||||
|
if (RCT2_GLOBAL(0x00F440A6, uint8) != 2) {
|
||||||
|
RCT2_GLOBAL(0x00F440A6, uint8) = 3;
|
||||||
|
RCT2_GLOBAL(0x00F440A8, uint16) = x;
|
||||||
|
RCT2_GLOBAL(0x00F440AA, uint16) = y;
|
||||||
|
RCT2_GLOBAL(0x00F440AC, uint16) = z;
|
||||||
|
RCT2_GLOBAL(0x00F440AE, uint8) = direction;
|
||||||
|
RCT2_GLOBAL(0x00F440AF, uint8) = type;
|
||||||
|
RCT2_GLOBAL(0x00F440B0, uint8) = 0;
|
||||||
|
RCT2_GLOBAL(0x00F440B1, uint8) = 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
sub_6C84CE();
|
||||||
|
return 1;
|
||||||
|
|
||||||
|
// Success stored in carry flag which can't be accessed after call using is macro
|
||||||
|
// RCT2_CALLPROC_X(0x006CC056, 0, 0, 0, (int)trackMapElement, 0, 0, 0);
|
||||||
|
// return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
*
|
*
|
||||||
* rct2: 0x006CC3FB
|
* rct2: 0x006CC3FB
|
||||||
*/
|
*/
|
||||||
void sub_6CC3FB(int rideIndex)
|
int sub_6CC3FB(int rideIndex)
|
||||||
{
|
{
|
||||||
rct_ride *ride;
|
rct_ride *ride;
|
||||||
rct_window *w;
|
rct_window *w;
|
||||||
|
|
||||||
tool_cancel();
|
tool_cancel();
|
||||||
ride = GET_RIDE(rideIndex);
|
ride = GET_RIDE(rideIndex);
|
||||||
if (ride->lifecycle_flags & RIDE_LIFECYCLE_BROKEN_DOWN) {
|
|
||||||
RCT2_GLOBAL(0x013CE952 + 6, uint16) = ride->name;
|
|
||||||
RCT2_GLOBAL(0x013CE952 + 8, uint32) = ride->name_arguments;
|
|
||||||
window_error_open(STR_CANT_START_CONSTRUCTION_ON, STR_HAS_BROKEN_DOWN_AND_REQUIRES_FIXING);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (ride->status != RIDE_STATUS_CLOSED) {
|
if (!ride_check_if_construction_allowed(ride))
|
||||||
RCT2_GLOBAL(0x013CE952 + 6, uint16) = ride->name;
|
return 0;
|
||||||
RCT2_GLOBAL(0x013CE952 + 8, uint32) = ride->name_arguments;
|
|
||||||
window_error_open(STR_CANT_START_CONSTRUCTION_ON, STR_MUST_BE_CLOSED_FIRST);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
RCT2_CALLPROC_X(0x006DD4AC, 0, 0, 0, rideIndex, 0, 0, 0);
|
ride_clear_for_construction(rideIndex);
|
||||||
RCT2_CALLPROC_X(0x006664DF, 0, 0, 0, rideIndex, 0, 0, 0);
|
ride_remove_peeps(rideIndex);
|
||||||
|
|
||||||
w = window_find_by_class(WC_RIDE_CONSTRUCTION);
|
w = ride_create_or_find_construction_window(rideIndex);
|
||||||
if (w == NULL || w->number != rideIndex) {
|
|
||||||
window_close_construction_windows();
|
|
||||||
RCT2_GLOBAL(0x00F440A7, uint8) = rideIndex;
|
|
||||||
w = window_construction_open(rideIndex);
|
|
||||||
} else {
|
|
||||||
RCT2_CALLPROC_X(0x006C9627, 0, 0, 0, 0, 0, 0, 0);
|
|
||||||
RCT2_GLOBAL(0x00F440A7, uint8) = rideIndex;
|
|
||||||
}
|
|
||||||
|
|
||||||
tool_set(w, 23, 12);
|
tool_set(w, 23, 12);
|
||||||
RCT2_GLOBAL(RCT2_ADDRESS_INPUT_FLAGS, uint32) |= INPUT_FLAG_6;
|
RCT2_GLOBAL(RCT2_ADDRESS_INPUT_FLAGS, uint32) |= INPUT_FLAG_6;
|
||||||
|
@ -563,8 +989,8 @@ void sub_6CC3FB(int rideIndex)
|
||||||
RCT2_GLOBAL(0x00F44159, uint8) = 0;
|
RCT2_GLOBAL(0x00F44159, uint8) = 0;
|
||||||
RCT2_GLOBAL(0x00F4415C, uint8) = 0;
|
RCT2_GLOBAL(0x00F4415C, uint8) = 0;
|
||||||
|
|
||||||
RCT2_CALLPROC_X(0x006C84CE, 0, 0, 0, 0, 0, ride->type, 0);
|
sub_6C84CE();
|
||||||
// return 0;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
#pragma endregion
|
#pragma endregion
|
||||||
|
@ -1158,13 +1584,15 @@ rct_peep *ride_find_closest_mechanic(rct_ride *ride, int forInspection)
|
||||||
}
|
}
|
||||||
|
|
||||||
// Get station start track element and position
|
// Get station start track element and position
|
||||||
x = (xy & 0xFF) * 32;
|
x = xy & 0xFF;
|
||||||
y = (xy >> 8) * 32;
|
y = xy >> 8;
|
||||||
z = ride->station_heights[stationIndex] * 8;
|
z = ride->station_heights[stationIndex];
|
||||||
mapElement = ride_get_station_start_track_element(ride, stationIndex);
|
mapElement = ride_get_station_exit_element(ride, x, y, z);
|
||||||
if (mapElement == NULL)
|
if (mapElement == NULL)
|
||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
|
x *= 32;
|
||||||
|
y *= 32;
|
||||||
direction = mapElement->type & 3;
|
direction = mapElement->type & 3;
|
||||||
x -= RCT2_ADDRESS(0x00993CCC, sint16)[direction * 2];
|
x -= RCT2_ADDRESS(0x00993CCC, sint16)[direction * 2];
|
||||||
y -= RCT2_ADDRESS(0x00993CCE, sint16)[direction * 2];
|
y -= RCT2_ADDRESS(0x00993CCE, sint16)[direction * 2];
|
||||||
|
@ -1321,6 +1749,22 @@ static void ride_music_update(int rideIndex)
|
||||||
|
|
||||||
#pragma region Measurement functions
|
#pragma region Measurement functions
|
||||||
|
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* rct2: 0x006B642B
|
||||||
|
*/
|
||||||
|
void ride_measurement_clear(rct_ride *ride)
|
||||||
|
{
|
||||||
|
rct_ride_measurement *measurement;
|
||||||
|
|
||||||
|
if (ride->measurement_index == 255)
|
||||||
|
return;
|
||||||
|
|
||||||
|
measurement = GET_RIDE_MEASUREMENT(ride->measurement_index);
|
||||||
|
measurement->ride_index = 255;
|
||||||
|
ride->measurement_index = 255;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* rct2: 0x006B64F2
|
* rct2: 0x006B64F2
|
||||||
*/
|
*/
|
||||||
|
|
|
@ -98,7 +98,7 @@ typedef struct {
|
||||||
uint8 station_heights[4]; // 0x05A
|
uint8 station_heights[4]; // 0x05A
|
||||||
uint8 pad_05E[0x4];
|
uint8 pad_05E[0x4];
|
||||||
uint8 station_depart[4]; // 0x062
|
uint8 station_depart[4]; // 0x062
|
||||||
uint8 pad_066[0x4];
|
uint8 var_066[4];
|
||||||
uint16 entrances[4]; // 0x06A
|
uint16 entrances[4]; // 0x06A
|
||||||
uint16 exits[4]; // 0x072
|
uint16 exits[4]; // 0x072
|
||||||
uint8 pad_07A[0x0C];
|
uint8 pad_07A[0x0C];
|
||||||
|
@ -241,7 +241,8 @@ typedef struct {
|
||||||
uint16 total_air_time; // 0x1F4
|
uint16 total_air_time; // 0x1F4
|
||||||
uint8 pad_1F6;
|
uint8 pad_1F6;
|
||||||
uint8 num_circuits; // 0x1F7
|
uint8 num_circuits; // 0x1F7
|
||||||
uint8 pad_1F8[0x8];
|
uint8 pad_1F8[6];
|
||||||
|
uint16 cable_lift; // 0x1FE
|
||||||
uint16 queue_length[4]; // 0x200
|
uint16 queue_length[4]; // 0x200
|
||||||
uint8 pad_208[0x58];
|
uint8 pad_208[0x58];
|
||||||
} rct_ride;
|
} rct_ride;
|
||||||
|
@ -611,7 +612,7 @@ void ride_check_all_reachable();
|
||||||
rct_map_element *sub_6CAF80(int rideIndex, int *outX, int *outY);
|
rct_map_element *sub_6CAF80(int rideIndex, int *outX, int *outY);
|
||||||
rct_map_element *ride_find_track_gap(rct_map_element *startTrackElement, int *outX, int *outY);
|
rct_map_element *ride_find_track_gap(rct_map_element *startTrackElement, int *outX, int *outY);
|
||||||
void ride_construct_new(ride_list_item listItem);
|
void ride_construct_new(ride_list_item listItem);
|
||||||
int ride_try_construct(rct_map_element *trackMapElement);
|
int ride_modify(rct_map_element *trackMapElement, int x, int y);
|
||||||
void ride_get_status(int rideIndex, int *formatSecondary, int *argument);
|
void ride_get_status(int rideIndex, int *formatSecondary, int *argument);
|
||||||
rct_peep *ride_get_assigned_mechanic(rct_ride *ride);
|
rct_peep *ride_get_assigned_mechanic(rct_ride *ride);
|
||||||
int ride_get_total_length(rct_ride *ride);
|
int ride_get_total_length(rct_ride *ride);
|
||||||
|
@ -620,10 +621,11 @@ track_colour ride_get_track_colour(rct_ride *ride, int colourScheme);
|
||||||
vehicle_colour ride_get_vehicle_colour(rct_ride *ride, int vehicleIndex);
|
vehicle_colour ride_get_vehicle_colour(rct_ride *ride, int vehicleIndex);
|
||||||
rct_ride_type *ride_get_entry(rct_ride *ride);
|
rct_ride_type *ride_get_entry(rct_ride *ride);
|
||||||
uint8 *get_ride_entry_indices_for_ride_type(uint8 rideType);
|
uint8 *get_ride_entry_indices_for_ride_type(uint8 rideType);
|
||||||
|
void ride_measurement_clear(rct_ride *ride);
|
||||||
void ride_measurements_update();
|
void ride_measurements_update();
|
||||||
rct_ride_measurement *ride_get_measurement(int rideIndex, rct_string_id *message);
|
rct_ride_measurement *ride_get_measurement(int rideIndex, rct_string_id *message);
|
||||||
void ride_breakdown_add_news_item(int rideIndex);
|
void ride_breakdown_add_news_item(int rideIndex);
|
||||||
rct_peep *ride_find_closest_mechanic(rct_ride *ride, int forInspection);
|
rct_peep *ride_find_closest_mechanic(rct_ride *ride, int forInspection);
|
||||||
void sub_6CC3FB(int rideIndex);
|
int sub_6CC3FB(int rideIndex);
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
|
@ -307,3 +307,21 @@ rct_map_element *ride_get_station_start_track_element(rct_ride *ride, int statio
|
||||||
|
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
rct_map_element *ride_get_station_exit_element(rct_ride *ride, int x, int y, int z)
|
||||||
|
{
|
||||||
|
rct_map_element *mapElement;
|
||||||
|
|
||||||
|
// Get first element of the tile
|
||||||
|
mapElement = TILE_MAP_ELEMENT_POINTER(y * 256 + x);
|
||||||
|
|
||||||
|
// Find the station track element
|
||||||
|
do {
|
||||||
|
if ((mapElement->type & MAP_ELEMENT_TYPE_MASK) == MAP_ELEMENT_TYPE_ENTRANCE && z == mapElement->base_height)
|
||||||
|
return mapElement;
|
||||||
|
|
||||||
|
mapElement++;
|
||||||
|
} while (!((mapElement - 1)->flags & MAP_ELEMENT_FLAG_LAST_TILE));
|
||||||
|
|
||||||
|
return NULL;
|
||||||
|
}
|
|
@ -27,5 +27,6 @@
|
||||||
|
|
||||||
void ride_update_station(rct_ride *ride, int stationIndex);
|
void ride_update_station(rct_ride *ride, int stationIndex);
|
||||||
rct_map_element *ride_get_station_start_track_element(rct_ride *ride, int stationIndex);
|
rct_map_element *ride_get_station_start_track_element(rct_ride *ride, int stationIndex);
|
||||||
|
rct_map_element *ride_get_station_exit_element(rct_ride *ride, int x, int y, int z);
|
||||||
|
|
||||||
#endif
|
#endif
|
|
@ -1387,7 +1387,7 @@ void window_ride_construct(rct_window *w)
|
||||||
trackMapElement = ride_find_track_gap(trackMapElement, &trackX, &trackY);
|
trackMapElement = ride_find_track_gap(trackMapElement, &trackX, &trackY);
|
||||||
|
|
||||||
w = window_get_main();
|
w = window_get_main();
|
||||||
if (w != NULL && ride_try_construct(trackMapElement))
|
if (w != NULL && ride_modify(trackMapElement, trackX, trackY))
|
||||||
window_scroll_to_location(w, trackX, trackY, trackMapElement->base_height * 8);
|
window_scroll_to_location(w, trackX, trackY, trackMapElement->base_height * 8);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -534,7 +534,7 @@ money32 map_try_clear_scenery(int x, int y, rct_map_element *mapElement, int fla
|
||||||
|
|
||||||
// Remove element
|
// Remove element
|
||||||
if (flags & 1) {
|
if (flags & 1) {
|
||||||
RCT2_CALLPROC_X(0x006EC6D7, x, 0, y, 0, 0, 0, 0);
|
map_invalidate_tile_full(x, y);
|
||||||
RCT2_CALLPROC_X(0x0068B280, 0, 0, 0, 0, (int)mapElement, 0, 0);
|
RCT2_CALLPROC_X(0x0068B280, 0, 0, 0, 0, (int)mapElement, 0, 0);
|
||||||
}
|
}
|
||||||
return RCT2_GLOBAL(RCT2_ADDRESS_PARK_FLAGS, uint32) & PARK_FLAGS_NO_MONEY ? 0 : cost;
|
return RCT2_GLOBAL(RCT2_ADDRESS_PARK_FLAGS, uint32) & PARK_FLAGS_NO_MONEY ? 0 : cost;
|
||||||
|
@ -671,3 +671,12 @@ void game_command_clear_scenery(int* eax, int* ebx, int* ecx, int* edx, int* esi
|
||||||
*ebx & 0xFF
|
*ebx & 0xFF
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* rct2: 0x006EC6D7
|
||||||
|
*/
|
||||||
|
void map_invalidate_tile_full(int x, int y)
|
||||||
|
{
|
||||||
|
RCT2_CALLPROC_X(0x006EC6D7, x, 0, y, 0, 0, 0, 0);
|
||||||
|
}
|
|
@ -208,6 +208,7 @@ void sub_6A876D();
|
||||||
int sub_664F72(int x, int y, int z);
|
int sub_664F72(int x, int y, int z);
|
||||||
int map_is_location_in_park(int x, int y);
|
int map_is_location_in_park(int x, int y);
|
||||||
void map_invalidate_tile(int x, int y, int zLow, int zHigh);
|
void map_invalidate_tile(int x, int y, int zLow, int zHigh);
|
||||||
|
void map_invalidate_tile_full(int x, int y);
|
||||||
|
|
||||||
void fountain_update_all();
|
void fountain_update_all();
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue