diff --git a/src/interface/viewport.c b/src/interface/viewport.c index 7a6d591cac..59b7e387ea 100644 --- a/src/interface/viewport.c +++ b/src/interface/viewport.c @@ -1453,18 +1453,55 @@ void viewport_paint(rct_viewport* viewport, rct_drawpixelinfo* dpi, int left, in //RCT2_CALLPROC_X(0x00685CBF, left, top, 0, right, (int)viewport, (int)dpi, bottom); } +/** + * + * rct2: 0x00688972 + * In: + * screen_x: eax + * screen_y: ebx + * Out: + * x: ax + * y: bx + * map_element: edx ? + * viewport: edi + */ +void sub_688972(int screenX, int screenY, sint16 *x, sint16 *y, rct_viewport **viewport) { + int z; + rct_viewport *myViewport; + get_map_coordinates_from_pos(screenX, screenY, 0xFFFE, x, y, &z, NULL, &myViewport); + if (z == 0) { + *x = 0x8000; + return; + } + + RCT2_GLOBAL(0x00F1AD34, uint16) = *x; + RCT2_GLOBAL(0x00F1AD36, uint16) = *y; + RCT2_GLOBAL(0x00F1AD38, uint16) = *x + 31; + RCT2_GLOBAL(0x00F1AD3A, uint16) = *y + 31; + + rct_xy16 start_vp_pos = screen_coord_to_viewport_coord(myViewport, screenX, screenY); + rct_xy16 map_pos = { *x + 16, *y + 16 }; + + for (int i = 0; i < 5; i++) { + z = map_element_height(map_pos.x, map_pos.y); + map_pos = viewport_coord_to_map_coord(start_vp_pos.x, start_vp_pos.y, z); + map_pos.x = clamp(RCT2_GLOBAL(0x00F1AD34, uint16), map_pos.x, RCT2_GLOBAL(0x00F1AD38, uint16)); + map_pos.y = clamp(RCT2_GLOBAL(0x00F1AD36, uint16), map_pos.y, RCT2_GLOBAL(0x00F1AD3A, uint16)); + } + + *x = map_pos.x; + *y = map_pos.y; + + if (viewport != NULL) *viewport = myViewport; +} + /** * * rct2: 0x0068958D */ -void screen_pos_to_map_pos(short *x, short *y, int *direction) +void screen_pos_to_map_pos(sint16 *x, sint16 *y, int *direction) { - int eax, ebx, ecx, edx, esi, edi, ebp; - eax = *x; - ebx = *y; - RCT2_CALLFUNC_X(0x00688972, &eax, &ebx, &ecx, &edx, &esi, &edi, &ebp); - *x = eax & ~0x1F; - *y = ebx & ~0x1F; + sub_688972(*x, *y, x, y, NULL); if (*x == 0x8000) return; @@ -1492,6 +1529,8 @@ void screen_pos_to_map_pos(short *x, short *y, int *direction) } } + *x = *x & ~0x1F; + *y = *y & ~0x1F; if (direction != NULL) *direction = my_direction; } diff --git a/src/interface/viewport.h b/src/interface/viewport.h index b6e9d047f8..e53019738f 100644 --- a/src/interface/viewport.h +++ b/src/interface/viewport.h @@ -86,7 +86,8 @@ void sub_689174(sint16* x, sint16* y, sint16 *z); rct_xy16 screen_coord_to_viewport_coord(rct_viewport *viewport, uint16 x, uint16 y); rct_xy16 viewport_coord_to_map_coord(int x, int y, int z); -void screen_pos_to_map_pos(short *x, short *y, int *direction); +void sub_688972(int screenX, int screenY, sint16 *x, sint16 *y, rct_viewport **viewport); +void screen_pos_to_map_pos(sint16 *x, sint16 *y, int *direction); void show_gridlines(); void hide_gridlines(); diff --git a/src/interface/window.c b/src/interface/window.c index ed5d376165..ea66ace556 100644 --- a/src/interface/window.c +++ b/src/interface/window.c @@ -1156,10 +1156,9 @@ void window_rotate_camera(rct_window *w) sint16 y = (viewport->height >> 1) + viewport->y; sint16 z; - int ecx, edx, esi, edi = (int)viewport, ebp; //has something to do with checking if middle of the viewport is obstructed - RCT2_CALLFUNC_X(0x00688972, (int*)&x, (int*)&y, &ecx, &edx, &esi, &edi, &ebp); - rct_viewport *other = (rct_viewport*)edi; + rct_viewport *other; + sub_688972(x, y, &x, &y, &other); // other != viewport probably triggers on viewports in ride or guest window? // x is 0x8000 if middle of viewport is obstructed by another window?