Add a hack to improve menu usability in Alice's Cottage 3

Some screens in Alice's Cottage 3 have menus implemented on the script
side. The script does not know the absolute position of the mouse
pointer (cursor movement is done by obtaining the relative movement
distance of the mouse), so the mouse pointer and the selected item were
often misaligned, and the cursor could not be moved by touch operation.

This adds a hack to the K3 command that emulates cursor movements by
absolute mouse pointer location.
This commit is contained in:
kichikuou
2023-02-25 14:29:04 +09:00
parent 6e4a0bacaf
commit 3a13f27dcf
3 changed files with 127 additions and 2 deletions
+1 -2
View File
@@ -68,8 +68,6 @@ private:
void draw_char_antialias(int dest, int dest_x, int dest_y, uint16 code, TTF_Font* font, uint8 color, uint8 cache[]);
void draw_gaiji(int dest, int dest_x, int dest_y, uint16 code, int size, uint8 color);
void draw_window(int sx, int sy, int ex, int ey, bool frame, uint8 frame_color, uint8 back_color);
void draw_screen(int sx, int sy, int width, int heignt);
void invalidate_screen(int sx, int sy, int width, int height);
@@ -111,6 +109,7 @@ public:
void draw_mesh(int sx, int sy, int width, int height);
void box_fill(int dest, int sx, int sy, int ex, int ey, uint8 color);
void box_line(int dest, int sx, int sy, int ex, int ey, uint8 color);
void draw_window(int sx, int sy, int ex, int ey, bool frame, uint8 frame_color, uint8 back_color);
void draw_text(const char* string, bool text_wait = false);
+5
View File
@@ -429,6 +429,11 @@ protected:
void cmd_z() override;
uint16 cali() override;
uint16 cali2() override;
private:
struct K3HackInfo;
static const K3HackInfo yakata3cd_k3_hack_table[];
static const K3HackInfo yakata3fd_k3_hack_table[];
bool k3_hack(const K3HackInfo* info_table);
};
#endif // _NACT_H_
+121
View File
@@ -517,6 +517,19 @@ void NACT_Sys3::cmd_k()
return;
}
if (cmd == 3) {
switch (crc32_a) {
case CRC32_YAKATA3_CD:
if (k3_hack(yakata3cd_k3_hack_table))
return;
break;
case CRC32_YAKATA3_FD:
if (k3_hack(yakata3fd_k3_hack_table))
return;
break;
}
}
// マウスの初期取得
int mx, my;
get_cursor(&mx, &my);
@@ -1507,3 +1520,111 @@ uint16 NACT_Sys3::cali2()
}
return val;
}
struct NACT_Sys3::K3HackInfo {
int page;
int var; // variable that holds the current selection
int left;
int top;
int rows;
int cols;
int w; // column width
int h; // row height
bool draw_window;
};
const NACT_Sys3::K3HackInfo NACT_Sys3::yakata3cd_k3_hack_table[] = {
//page, var, left, top, rows, cols, w, h, draw_win
{ 71, 61, 463, 28, 5, 1, 162, 48, false }, // main menu
{ 72, 60, 32, 0, 2, 3, 192, 138, false }, // game selection
{ 35, 61, 192, 136, 3, 1, 256, 56, false }, // quiz
{ 37, 61, 192, 136, 3, 1, 256, 56, false }, // quiz
{ 39, 61, 192, 136, 3, 1, 256, 56, false }, // quiz
{ 36, 61, 200, 200, 1, 5, 48, 48, true }, // quiz (CG selection)
{ -1 }
};
const NACT_Sys3::K3HackInfo NACT_Sys3::yakata3fd_k3_hack_table[] = {
//page, var, left, top, rows, cols, w, h, draw_win
{ 71, 59, 463, 28, 5, 1, 162, 48, false }, // main menu
{ 72, 58, 32, 0, 2, 3, 192, 138, false }, // game selection
{ 35, 59, 192, 136, 3, 1, 256, 56, false }, // quiz
{ 37, 59, 192, 136, 3, 1, 256, 56, false }, // quiz
{ 39, 59, 192, 136, 3, 1, 256, 56, false }, // quiz
{ 36, 59, 200, 200, 1, 5, 48, 48, true }, // quiz (CG selection)
{ -1 }
};
bool NACT_Sys3::k3_hack(const K3HackInfo* info_table)
{
const K3HackInfo* info;
for (info = info_table; info->page >= 0; info++) {
if (scenario_page == info->page)
break;
}
if (info->page < 0)
return false;
if (info->draw_window) {
// Draw a simple menu to indicate clickable areas.
ags->draw_window(
info->left - 6, info->top - 6,
info->left + info->w * info->cols + 6, info->top + info->h + 6,
true, ags->menu_frame_color, ags->menu_back_color);
int orig_font_size = ags->text_font_size;
ags->text_dest_x = info->left;
ags->text_dest_y = info->top;
ags->text_font_size = info->w;
ags->draw_text("12345");
ags->text_font_size = orig_font_size;
int left = info->left + info->w * (var[info->var] - 1);
ags->box_line(0, left, info->top, left + info->w, info->top + info->h, ags->text_font_color);
}
while (!terminate) {
int mx, my;
get_cursor(&mx, &my);
if (info->left <= mx && mx < info->left + info->w * info->cols &&
info->top <= my && my < info->top + info->h * info->rows) {
int target_row = (my - info->top) / info->h;
int target_col = (mx - info->left) / info->w;
int current_row = (var[info->var] - 1) / info->cols;
int current_col = (var[info->var] - 1) % info->cols;
if (target_row < current_row) {
RND = 1; // UP
break;
}
if (target_row > current_row) {
RND = 2; // DOWN
break;
}
if (target_col < current_col) {
RND = 4; // LEFT
break;
}
if (target_col > current_col) {
RND = 8; // RIGHT
break;
}
}
int key = get_key();
if (key) {
// Wait for key release
while (!terminate && get_key())
sys_sleep(16);
RND = key;
break;
}
sys_sleep(16);
}
if (info->draw_window) {
// Clear the menu window.
ags->box_fill(
0, info->left - 6, info->top - 6,
info->left + info->w * info->cols + 6, info->top + info->h + 6, 0);
}
return true;
}