mirror of https://github.com/OpenRCT2/OpenRCT2.git
game_command_raise_water, game_command_lower_water, suggested changes
This commit is contained in:
parent
af46537667
commit
9bd620cd99
|
@ -1427,13 +1427,8 @@ int sound_play_panned(int sound_id, int ebx, sint16 x, sint16 y, sint16 z)
|
|||
RCT2_GLOBAL(0x00F438AD, uint8) = 0;
|
||||
int volume = 0;
|
||||
if (ebx == 0x8001) {
|
||||
sint16 x2 = x & 0xFFE0; // round by 32
|
||||
sint16 y2 = y & 0xFFE0;
|
||||
if (x2 < 0x1FFF && y2 < 0x1FFF) {
|
||||
rct_map_element* mapelement = RCT2_ADDRESS(RCT2_ADDRESS_TILE_MAP_ELEMENT_POINTERS, rct_map_element*)[((y2 * 256 + x2) & 0xFFFF) / 8];
|
||||
while (map_element_get_type(mapelement) != MAP_ELEMENT_TYPE_SURFACE) {
|
||||
mapelement++;
|
||||
}
|
||||
rct_map_element* mapelement = map_get_surface_element_at(x / 32, y / 32);
|
||||
if (mapelement) {
|
||||
if ((mapelement->base_height * 8) - 5 > z) {
|
||||
RCT2_GLOBAL(0x00F438AD, uint8) = 10;
|
||||
}
|
||||
|
|
|
@ -900,8 +900,8 @@ static uint32 game_do_command_table[58] = {
|
|||
0,
|
||||
0,
|
||||
0x0068BC01,
|
||||
0x006E66A0,
|
||||
0x006E6878,
|
||||
0,
|
||||
0,
|
||||
0x006C5AE9,
|
||||
0, // use new_game_command_table, original: 0x006BEFA1, 29
|
||||
0, // 30
|
||||
|
@ -963,8 +963,8 @@ static GAME_COMMAND_POINTER* new_game_command_table[58] = {
|
|||
game_command_raise_land,
|
||||
game_command_lower_land,
|
||||
game_command_emptysub,
|
||||
game_command_emptysub,
|
||||
game_command_emptysub,
|
||||
game_command_raise_water,
|
||||
game_command_lower_water,
|
||||
game_command_emptysub,
|
||||
game_command_hire_new_staff_member, //game_command_emptysub,
|
||||
game_command_set_staff_patrol, // 30
|
||||
|
|
205
src/world/map.c
205
src/world/map.c
|
@ -912,38 +912,30 @@ void game_command_raise_land(int* eax, int* ebx, int* ecx, int* edx, int* esi, i
|
|||
sound_play_panned(SOUND_PLACE_ITEM, 0x8001, x, y, z);
|
||||
}
|
||||
|
||||
uint8 dh = 0xFF;
|
||||
uint8 min_height = 0xFF;
|
||||
|
||||
// find lowest map element in selection
|
||||
for(int yi = ay; yi <= by; yi += 32){
|
||||
for(int xi = ax; xi <= bx; xi += 32){
|
||||
int tile_idx = (((yi & 0x1FE0) * 256) + (xi & 0x1FE0)) / 32;
|
||||
rct_map_element* map_element = RCT2_ADDRESS(RCT2_ADDRESS_TILE_MAP_ELEMENT_POINTERS, rct_map_element*)[tile_idx];
|
||||
while(map_element->type & MAP_ELEMENT_TYPE_MASK){
|
||||
map_element++;
|
||||
}
|
||||
if(dh > map_element->base_height){
|
||||
dh = map_element->base_height;
|
||||
rct_map_element* map_element = map_get_surface_element_at(xi / 32, yi / 32);
|
||||
if(min_height > map_element->base_height){
|
||||
min_height = map_element->base_height;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
for(int yi = ay; yi <= by; yi += 32){
|
||||
for(int xi = ax; xi <= bx; xi += 32){
|
||||
int tile_idx = (((yi & 0x1FE0) * 256) + (xi & 0x1FE0)) / 32;
|
||||
rct_map_element* map_element = RCT2_ADDRESS(RCT2_ADDRESS_TILE_MAP_ELEMENT_POINTERS, rct_map_element*)[tile_idx];
|
||||
while(map_element->type & MAP_ELEMENT_TYPE_MASK){
|
||||
map_element++;
|
||||
}
|
||||
uint8 dl = map_element->base_height;
|
||||
if(dl <= dh){
|
||||
rct_map_element* map_element = map_get_surface_element_at(xi / 32, yi / 32);
|
||||
uint8 height = map_element->base_height;
|
||||
if(height <= min_height){
|
||||
uint8 dh = RCT2_ADDRESS(0x00981A1E, uint8)[(selection_type * 32) + (map_element->properties.surface.slope & MAP_ELEMENT_SLOPE_MASK)]; // lookup table
|
||||
if(dh & 0x20){ // needs to be raised, otherwise just the slope type changes
|
||||
dl += 2;
|
||||
height += 2;
|
||||
dh &= ~0x20;
|
||||
}
|
||||
int ebx2 = *ebx;
|
||||
int edx2 = (dh << 8) + dl;
|
||||
int edx2 = (dh << 8) + height;
|
||||
int edi2 = selection_type * 32;
|
||||
RCT2_CALLFUNC_X(0x0066397F, &xi, &ebx2, &yi, &edx2, (int*)&map_element, &edi2, ebp); // actually apply the change
|
||||
if(ebx2 != 0x80000000){
|
||||
|
@ -984,52 +976,44 @@ void game_command_lower_land(int* eax, int* ebx, int* ecx, int* edx, int* esi, i
|
|||
sound_play_panned(SOUND_PLACE_ITEM, 0x8001, x, y, z);
|
||||
}
|
||||
|
||||
uint8 dh = 0;
|
||||
uint8 max_height = 0;
|
||||
|
||||
// find highest map element in selection
|
||||
for(int yi = ay; yi <= by; yi += 32){
|
||||
for(int xi = ax; xi <= bx; xi += 32){
|
||||
int tile_idx = (((yi & 0x1FE0) * 256) + (xi & 0x1FE0)) / 32;
|
||||
rct_map_element* map_element = RCT2_ADDRESS(RCT2_ADDRESS_TILE_MAP_ELEMENT_POINTERS, rct_map_element*)[tile_idx];
|
||||
while(map_element->type & MAP_ELEMENT_TYPE_MASK){
|
||||
map_element++;
|
||||
}
|
||||
uint8 dl = map_element->base_height;
|
||||
rct_map_element* map_element = map_get_surface_element_at(xi / 32, yi / 32);
|
||||
uint8 base_height = map_element->base_height;
|
||||
if(map_element->properties.surface.slope & 0xF){
|
||||
dl += 2;
|
||||
base_height += 2;
|
||||
}
|
||||
if(map_element->properties.surface.slope & 0x10){
|
||||
dl += 2;
|
||||
base_height += 2;
|
||||
}
|
||||
if(dh < dl){
|
||||
dh = dl;
|
||||
if(max_height < base_height){
|
||||
max_height = base_height;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
for(int yi = ay; yi <= by; yi += 32){
|
||||
for(int xi = ax; xi <= bx; xi += 32){
|
||||
int tile_idx = (((yi & 0x1FE0) * 256) + (xi & 0x1FE0)) / 32;
|
||||
rct_map_element* map_element = RCT2_ADDRESS(RCT2_ADDRESS_TILE_MAP_ELEMENT_POINTERS, rct_map_element*)[tile_idx];
|
||||
while(map_element->type & MAP_ELEMENT_TYPE_MASK){
|
||||
map_element++;
|
||||
}
|
||||
uint8 dl = map_element->base_height;
|
||||
rct_map_element* map_element = map_get_surface_element_at(xi / 32, yi / 32);
|
||||
uint8 height = map_element->base_height;
|
||||
if(map_element->properties.surface.slope & 0xF){
|
||||
dl += 2;
|
||||
height += 2;
|
||||
}
|
||||
if(map_element->properties.surface.slope & 0x10){
|
||||
dl += 2;
|
||||
height += 2;
|
||||
}
|
||||
if(dl >= dh){
|
||||
dl = map_element->base_height;
|
||||
if(height >= max_height){
|
||||
height = map_element->base_height;
|
||||
uint8 dh = RCT2_ADDRESS(0x00981ABE, uint8)[(selection_type * 32) + (map_element->properties.surface.slope & MAP_ELEMENT_SLOPE_MASK)]; // lookup table
|
||||
if(dh & 0x20){ // needs to be lowered, otherwise just the slope type changes
|
||||
dl -= 2;
|
||||
height -= 2;
|
||||
dh &= ~0x20;
|
||||
}
|
||||
int ebx2 = *ebx;
|
||||
int edx2 = (dh << 8) + dl;
|
||||
int edx2 = (dh << 8) + height;
|
||||
int edi2 = selection_type * 32;
|
||||
RCT2_CALLFUNC_X(0x0066397F, &xi, &ebx2, &yi, &edx2, (int*)&map_element, &edi2, ebp); // actually apply the change
|
||||
if(ebx2 != 0x80000000){
|
||||
|
@ -1049,6 +1033,147 @@ void game_command_lower_land(int* eax, int* ebx, int* ecx, int* edx, int* esi, i
|
|||
*ebx = cost;
|
||||
}
|
||||
|
||||
/**
|
||||
*
|
||||
* rct2: 0x006E66A0
|
||||
*/
|
||||
void game_command_raise_water(int* eax, int* ebx, int* ecx, int* edx, int* esi, int* edi, int* ebp)
|
||||
{
|
||||
int ax = (uint16)*eax;
|
||||
int ay = (uint16)*ecx;
|
||||
int bx = (uint16)*edi;
|
||||
int by = (uint16)*ebp;
|
||||
|
||||
int cost = 0;
|
||||
|
||||
uint8 max_height = 0xFF;
|
||||
|
||||
for(int yi = ay; yi <= by; yi += 32){
|
||||
for(int xi = ax; xi <= bx; xi += 32){
|
||||
rct_map_element* map_element = map_get_surface_element_at(xi / 32, yi / 32);
|
||||
uint8 height = map_element->base_height;
|
||||
if(map_element->properties.surface.terrain & 0x1F){
|
||||
height = (map_element->properties.surface.terrain & 0x1F) * 2;
|
||||
}
|
||||
if(max_height > height){
|
||||
max_height = height;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
for(int yi = ay; yi <= by; yi += 32){
|
||||
for(int xi = ax; xi <= bx; xi += 32){
|
||||
rct_map_element* map_element = map_get_surface_element_at(xi / 32, yi / 32);
|
||||
|
||||
if(map_element->base_height <= max_height){
|
||||
uint8 height = (map_element->properties.surface.terrain & 0x1F);
|
||||
if(height){
|
||||
height *= 2;
|
||||
if(height > max_height){
|
||||
continue;
|
||||
}
|
||||
height += 2;
|
||||
}else{
|
||||
height = map_element->base_height + 2;
|
||||
}
|
||||
int eax2 = xi, ebx2 = *ebx, ecx2 = yi, edx2 = (max_height << 8) + height, esi2, edi2, ebp2;
|
||||
ebx2 = game_do_command_p(GAME_COMMAND_16, &eax2, &ebx2, &ecx2, &edx2, &esi2, &edi2, &ebp2);
|
||||
if(ebx2 == 0x80000000){
|
||||
*ebx = 0x80000000;
|
||||
return;
|
||||
}else{
|
||||
cost += ebx2;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
if(*ebx & GAME_COMMAND_FLAG_APPLY){
|
||||
int x = ((ax + bx) / 2) + 16;
|
||||
int y = ((ay + by) / 2) + 16;
|
||||
int z = map_element_height(x, y);
|
||||
sint16 water_height_z = z >> 16;
|
||||
sint16 base_height_z = z;
|
||||
z = water_height_z;
|
||||
if(!z){
|
||||
z = base_height_z;
|
||||
}
|
||||
RCT2_GLOBAL(0x009DEA5E, uint32) = x;
|
||||
RCT2_GLOBAL(0x009DEA60, uint32) = y;
|
||||
RCT2_GLOBAL(0x009DEA62, uint32) = z;
|
||||
sound_play_panned(SOUND_LAYING_OUT_WATER, 0x8001, x, y, z);
|
||||
}
|
||||
*ebx = cost;
|
||||
}
|
||||
|
||||
/**
|
||||
*
|
||||
* rct2: 0x006E6878
|
||||
*/
|
||||
void game_command_lower_water(int* eax, int* ebx, int* ecx, int* edx, int* esi, int* edi, int* ebp)
|
||||
{
|
||||
int ax = (uint16)*eax;
|
||||
int ay = (uint16)*ecx;
|
||||
int bx = (uint16)*edi;
|
||||
int by = (uint16)*ebp;
|
||||
|
||||
int cost = 0;
|
||||
|
||||
uint8 min_height = 0;
|
||||
|
||||
for(int yi = ay; yi <= by; yi += 32){
|
||||
for(int xi = ax; xi <= bx; xi += 32){
|
||||
rct_map_element* map_element = map_get_surface_element_at(xi / 32, yi / 32);
|
||||
|
||||
uint8 height = map_element->properties.surface.terrain & 0x1F;
|
||||
if(height){
|
||||
height *= 2;
|
||||
if(height > min_height){
|
||||
min_height = height;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
for(int yi = ay; yi <= by; yi += 32){
|
||||
for(int xi = ax; xi <= bx; xi += 32){
|
||||
rct_map_element* map_element = map_get_surface_element_at(xi / 32, yi / 32);
|
||||
|
||||
uint8 height = (map_element->properties.surface.terrain & 0x1F);
|
||||
if(height){
|
||||
height *= 2;
|
||||
if(height < min_height){
|
||||
continue;
|
||||
}
|
||||
height -= 2;
|
||||
int eax2 = xi, ebx2 = *ebx, ecx2 = yi, edx2 = (min_height << 8) + height, esi2, edi2, ebp2;
|
||||
ebx2 = game_do_command_p(GAME_COMMAND_16, &eax2, &ebx2, &ecx2, &edx2, &esi2, &edi2, &ebp2);
|
||||
if(ebx2 == 0x80000000){
|
||||
*ebx = 0x80000000;
|
||||
return;
|
||||
}else{
|
||||
cost += ebx2;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
if(*ebx & GAME_COMMAND_FLAG_APPLY){
|
||||
int x = ((ax + bx) / 2) + 16;
|
||||
int y = ((ay + by) / 2) + 16;
|
||||
int z = map_element_height(x, y);
|
||||
sint16 water_height_z = z >> 16;
|
||||
sint16 base_height_z = z;
|
||||
z = water_height_z;
|
||||
if(!z){
|
||||
z = base_height_z;
|
||||
}
|
||||
RCT2_GLOBAL(0x009DEA5E, uint32) = x;
|
||||
RCT2_GLOBAL(0x009DEA60, uint32) = y;
|
||||
RCT2_GLOBAL(0x009DEA62, uint32) = z;
|
||||
sound_play_panned(SOUND_LAYING_OUT_WATER, 0x8001, x, y, z);
|
||||
}
|
||||
*ebx = cost;
|
||||
}
|
||||
|
||||
/**
|
||||
*
|
||||
* rct2: 0x006EC6D7
|
||||
|
|
|
@ -277,6 +277,8 @@ void game_command_clear_scenery(int* eax, int* ebx, int* ecx, int* edx, int* esi
|
|||
void game_command_change_surface_style(int* eax, int* ebx, int* ecx, int* edx, int* esi, int* edi, int* ebp);
|
||||
void game_command_raise_land(int* eax, int* ebx, int* ecx, int* edx, int* esi, int* edi, int* ebp);
|
||||
void game_command_lower_land(int* eax, int* ebx, int* ecx, int* edx, int* esi, int* edi, int* ebp);
|
||||
void game_command_raise_water(int* eax, int* ebx, int* ecx, int* edx, int* esi, int* edi, int* ebp);
|
||||
void game_command_lower_water(int* eax, int* ebx, int* ecx, int* edx, int* esi, int* edi, int* ebp);
|
||||
|
||||
#define GET_MAP_ELEMENT(x) (&(RCT2_ADDRESS(RCT2_ADDRESS_MAP_ELEMENTS, rct_map_element)[x]))
|
||||
#define TILE_MAP_ELEMENT_POINTER(x) (RCT2_ADDRESS(RCT2_ADDRESS_TILE_MAP_ELEMENT_POINTERS, rct_map_element*)[x])
|
||||
|
|
Loading…
Reference in New Issue