Start implementing clear_funcs

This commit is contained in:
duncanspumpkin 2016-02-13 13:10:55 +00:00
parent 71b65e9880
commit f6797181b5
2 changed files with 71 additions and 8 deletions

View File

@ -1582,6 +1582,20 @@ const uint8 map_element_lower_styles[5][32] = {
{ 0x20, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x07, 0x00, 0x00, 0x00, 0x0B, 0x00, 0x0D, 0x0E, 0x00 },
};
/**
*
* rct2: 0x00663CB9
*/
int map_set_land_height_clear_func(rct_map_element** map_element) {
if (map_element_get_type(*map_element) == MAP_ELEMENT_TYPE_SURFACE)
return 0;
if (map_element_get_type(*map_element) == MAP_ELEMENT_TYPE_SCENERY)
return 0;
return 1;
}
static money32 map_set_land_height(int flags, int x, int y, int height, int style, int selectionType)
{
if (RCT2_GLOBAL(RCT2_ADDRESS_GAME_PAUSED, uint8) != 0 && !gCheatsBuildInPauseMode) {
@ -1722,7 +1736,7 @@ static money32 map_set_land_height(int flags, int x, int y, int height, int styl
}
}
if(map_can_construct_with_clear_at(x, y, height, zCorner, RCT2_ADDRESS(0x663CB9, void), 0xF) == false)
if(map_can_construct_with_clear_at(x, y, height, zCorner, &map_set_land_height_clear_func, 0xF) == false)
return MONEY32_UNDEFINED;
mapElement = map_get_first_element_at(x / 32, y / 32);
@ -2772,6 +2786,52 @@ void game_command_place_banner(int* eax, int* ebx, int* ecx, int* edx, int* esi,
*ebx = MONEY32_UNDEFINED;
}
/**
*
* rct2: 0x006E0D6E
*/
int map_place_scenery_clear_func(rct_map_element** map_element) {
if (map_element_get_type(*map_element) != MAP_ELEMENT_TYPE_SCENERY)
return 1;
// Change so that hack is not required
uint8* ebp = RCT2_GLOBAL(0x00F64F1E, uint8*);
if (!(ebp[4] & (1 << 7)))
return 1;
rct_scenery_entry* scenery = g_smallSceneryEntries[(*map_element)->properties.scenery.type];
if (RCT2_GLOBAL(RCT2_ADDRESS_PARK_FLAGS, uint32) & PARK_FLAGS_FORBID_TREE_REMOVAL) {
if (scenery->small_scenery.height > 64)
return 1;
}
money32 price = scenery->small_scenery.removal_price * 10;
if (RCT2_GLOBAL(RCT2_ADDRESS_PARK_FLAGS, uint32) & PARK_FLAGS_NO_MONEY)
price = 0;
RCT2_GLOBAL(0x00F64F26, money32) += price;
if (ebp[4] & (1 << 6))
return 0;
if (!(ebp[4] & (1 << 0)))
return 0;
rct_xy16 location = {
.x = RCT2_GLOBAL(0x00F64F22, sint16),
.y = RCT2_GLOBAL(0x00F64F24, uint16)
};
map_invalidate_tile(location.x, location.y, (*map_element)->base_height * 8, (*map_element)->clearance_height * 8);
map_element_remove(*map_element);
(*map_element)--;
return 0;
}
/**
*
* rct2: 0x006E08F4
@ -2787,6 +2847,7 @@ void game_command_place_scenery(int* eax, int* ebx, int* ecx, int* edx, int* esi
uint8 scenery_type = *ebx >> 8;
uint8 quadrant = *edx;
uint8 color1 = *edx >> 8;
RCT2_GLOBAL(0x00F64F26, money32) = 0;
int F64F1D = 0;
int F64EC8 = z;
int base_height = map_element_height(x, y);
@ -2908,7 +2969,7 @@ void game_command_place_scenery(int* eax, int* ebx, int* ecx, int* edx, int* esi
RCT2_GLOBAL(0x00F64F22, uint16) = x;
RCT2_GLOBAL(0x00F64F24, uint16) = y;
RCT2_GLOBAL(0x00F64F1E, uint32) = (uint32)(ebx - 1); //0x006E0D6E uses [F64F1E+4] to read ebx value
if(gCheatsDisableClearanceChecks || map_can_construct_with_clear_at(x, y, zLow, zHigh, (void*)0x006E0D6E, bl)){
if(gCheatsDisableClearanceChecks || map_can_construct_with_clear_at(x, y, zLow, zHigh, &map_place_scenery_clear_func, bl)){
RCT2_GLOBAL(0x00F64F14, uint8) = RCT2_GLOBAL(RCT2_ADDRESS_ELEMENT_LOCATION_COMPARED_TO_GROUND_AND_WATER, uint8) & 0x3;
if(*ebx & GAME_COMMAND_FLAG_APPLY){
if (RCT2_GLOBAL(0x009A8C28, uint8) == 1 && !(*ebx & GAME_COMMAND_FLAG_GHOST)) {
@ -2941,7 +3002,7 @@ void game_command_place_scenery(int* eax, int* ebx, int* ecx, int* edx, int* esi
map_animation_create(2, x, y, new_map_element->base_height);
}
}
*ebx = (scenery_entry->small_scenery.price * 10);
*ebx = (scenery_entry->small_scenery.price * 10) + RCT2_GLOBAL(0x00F64F26, money32);
if(RCT2_GLOBAL(RCT2_ADDRESS_PARK_FLAGS, uint32) & PARK_FLAGS_NO_MONEY){
*ebx = 0;
}
@ -3961,9 +4022,9 @@ static void map_obstruction_set_error_text(rct_map_element *mapElement)
* ebp = clearFunc
* bl = bl
*/
int map_can_construct_with_clear_at(int x, int y, int zLow, int zHigh, void *clearFunc, uint8 bl)
int map_can_construct_with_clear_at(int x, int y, int zLow, int zHigh, CLEAR_FUNC *clearFunc, uint8 bl)
{
RCT2_GLOBAL(0x00F1AD40, void*) = clearFunc;
RCT2_GLOBAL(0x00F1AD40, CLEAR_FUNC*) = clearFunc;
RCT2_GLOBAL(RCT2_ADDRESS_ELEMENT_LOCATION_COMPARED_TO_GROUND_AND_WATER, uint8) = 1;
if (x >= RCT2_GLOBAL(RCT2_ADDRESS_MAP_SIZE_UNITS, sint16) || y >= RCT2_GLOBAL(RCT2_ADDRESS_MAP_SIZE_UNITS, sint16) || x < 32 || y < 32) {
RCT2_GLOBAL(RCT2_ADDRESS_GAME_COMMAND_ERROR_TEXT, rct_string_id) = STR_OFF_EDGE_OF_MAP;
@ -4037,7 +4098,7 @@ int map_can_construct_with_clear_at(int x, int y, int zLow, int zHigh, void *cle
loc_68BABC:
if (RCT2_GLOBAL(0x00F1AD40, void*) != (void*)0xFFFFFFFF) {
int zero = 0;
if (!(RCT2_CALLFUNC_X((int)RCT2_GLOBAL(0x00F1AD40, void*), &zero, &zero, &zero, &zero, (int*)&map_element, &zero, &zero) & 0x100)) {
if (!clearFunc(&map_element)) {
continue;
}
}
@ -4048,7 +4109,7 @@ int map_can_construct_with_clear_at(int x, int y, int zLow, int zHigh, void *cle
loc_68BAE6:
if (RCT2_GLOBAL(0x00F1AD40, void*) != (void*)0xFFFFFFFF) {
int zero = 0;
if (!(RCT2_CALLFUNC_X((int)RCT2_GLOBAL(0x00F1AD40, void*), &zero, &zero, &zero, &zero, (int*)&map_element, &zero, &zero) & 0x100)) {
if (!clearFunc(&map_element)) {
goto loc_68B9B7;
}
}

View File

@ -311,7 +311,9 @@ void map_invalidate_selection_rect();
void map_reorganise_elements();
int sub_68B044();
rct_map_element *map_element_insert(int x, int y, int z, int flags);
int map_can_construct_with_clear_at(int x, int y, int zLow, int zHigh, void *clearFunc, uint8 bl);
typedef int (CLEAR_FUNC)(rct_map_element** map_element);
int map_can_construct_with_clear_at(int x, int y, int zLow, int zHigh, CLEAR_FUNC *clearFunc, uint8 bl);
int map_can_construct_at(int x, int y, int zLow, int zHigh, uint8 bl);
void rotate_map_coordinates(sint16 *x, sint16 *y, int rotation);
rct_xy16 coordinate_3d_to_2d(const rct_xyz16* coordinate_3d, int rotation);