From 7aa045930611848e11152ad1f7b447c04d0719c9 Mon Sep 17 00:00:00 2001 From: nmlgc Date: Wed, 29 Nov 2023 21:02:38 +0100 Subject: [PATCH] [Decompilation] [th04/th05] Setup menu: BGM and SE mode menus I think this is the first time that function pointers as `inline` function parameters actually inlined perfectly? Part of P0263, funded by [Anonymous]. --- th04/op/m_setup.cpp | 117 +++++++++++++++++++++- th04/setup.asm | 16 +-- th04/setup[data].asm | 7 +- th04/shiftjis/m_setup.hpp | 8 +- th04_op.asm | 206 +------------------------------------- th05_op.asm | 206 +------------------------------------- 6 files changed, 130 insertions(+), 430 deletions(-) diff --git a/th04/op/m_setup.cpp b/th04/op/m_setup.cpp index 5077928c..7b194b41 100644 --- a/th04/op/m_setup.cpp +++ b/th04/op/m_setup.cpp @@ -2,11 +2,19 @@ #include "pc98.h" #include "master.hpp" #include "shiftjis.hpp" +#include "th01/math/clamp.hpp" #include "th01/hardware/egc.h" #include "th02/v_colors.hpp" extern "C" { #include "th02/hardware/frmdelay.h" +#include "th04/score.h" +#if (GAME == 5) + #include "th05/resident.hpp" +#else + #include "th04/resident.hpp" +#endif #include "th04/hardware/grppsafx.h" +#include "th04/hardware/input.h" #include "th04/snd/snd.h" } #include "th04/shiftjis/m_setup.hpp" @@ -24,6 +32,9 @@ enum setup_window_patnum_t { MSWIN_RIGHT_TOP, }; +static const vc2 COL_INACTIVE = 0; +static const vc2 COL_ACTIVE = V_WHITE; + // Coordinates // ----------- @@ -38,11 +49,15 @@ static const pixel_t MSWIN_H = 16; static const pixel_t DROP_SPEED = (MSWIN_H / 2); static const int DROP_FRAMES_PER_TILE = (MSWIN_H / DROP_SPEED); +static const screen_x_t CAPTION_LEFT = ((RES_X / 2) - (CAPTION_W / 2)); +static const screen_y_t CAPTION_TOP = 88; + inline void assert_that_all_choices_are_equally_wide(void) { static_assert(shiftjis_w(BGM_CHOICE_FM86) == shiftjis_w(BGM_CHOICE_FM26)); static_assert(shiftjis_w(BGM_CHOICE_FM86) == shiftjis_w(BGM_CHOICE_OFF)); static_assert(shiftjis_w(BGM_CHOICE_FM86) == shiftjis_w(SE_CHOICE_BEEP)); static_assert(shiftjis_w(BGM_CHOICE_FM86) == shiftjis_w(SE_CHOICE_FM)); + static_assert(shiftjis_w(BGM_CHOICE_FM86) == shiftjis_w(SE_CHOICE_OFF)); } static const pixel_t CHOICE_W = shiftjis_w(BGM_CHOICE_FM86); @@ -56,7 +71,6 @@ static const screen_x_t HELP_TOP = CHOICE_TOP; typedef int mswin_tile_amount_t; -#define window window_tiles static Palette8 palette_unused; // ZUN bloat struct { mswin_tile_amount_t w; @@ -154,6 +168,22 @@ void pascal near rollup(screen_x_t left, screen_y_t top) } } +inline void window_animate( + screen_x_t content_left, + screen_y_t content_top, + pixel_t content_w, + int content_lines, + void (near pascal *near animate_func)(screen_x_t, screen_y_t) +) { + window.w = (window_w_for_content_w(content_w) / MSWIN_W); + if(content_lines != 1) { + window.h = ( + ((MSWIN_BORDER_H * 2) + (content_lines * GLYPH_H)) / MSWIN_H + ); + } + animate_func((content_left - MSWIN_W), (content_top - MSWIN_BORDER_H)); +} + // ZUN bloat: Could have been a single function with a value/string array // parameter. void pascal near bgm_choice_put(int bgm_mode, vc2 col) @@ -182,7 +212,7 @@ void pascal near se_choice_put(int se_mode, vc2 col) graph_putsa_fx(CHOICE_LEFT, top, col, str); } -// ZUN bloat: Could have been a single function with a string array parameter. +// ZUN bloat: Could have been inlined into setup_submenu(). void near bgm_help_put(void) { screen_y_t top = HELP_TOP; @@ -198,3 +228,86 @@ void near se_help_put(void) graph_putsa_fx(HELP_LEFT, top, V_WHITE, SE_HELP[i]); } } + +#define setup_submenu( \ + sel, \ + caption, \ + choice_count, \ + choice_default, \ + choice_put, \ + help_put, \ + increment_input \ +) { \ + window_animate(CAPTION_LEFT, CAPTION_TOP, CAPTION_W, 1, singleline); \ + graph_putsa_fx(CAPTION_LEFT, CAPTION_TOP, V_WHITE, caption); \ + \ + window_animate(CHOICE_LEFT, CHOICE_TOP, CHOICE_W, choice_count, dropdown); \ + for(sel = 0; sel < choice_count; sel++) { \ + choice_put( \ + sel, ((sel == choice_default) ? COL_ACTIVE : COL_INACTIVE) \ + ); \ + } \ + \ + window_animate(HELP_LEFT, HELP_TOP, HELP_W, HELP_LINES, dropdown); \ + help_put(); \ + \ + sel = choice_default; \ + while(1) { \ + input_wait_for_change(0); \ + frame_delay(1); \ + if((key_det & INPUT_OK) || (key_det & INPUT_SHOT)) { \ + break; \ + } \ + if(key_det & increment_input) { \ + choice_put(sel, COL_INACTIVE); \ + if(sel == (choice_count - 1)) { \ + sel = 0; \ + } else { \ + sel++; \ + } \ + choice_put(sel, COL_ACTIVE); \ + } \ + if(key_det & (~increment_input & (INPUT_UP | INPUT_DOWN))) { \ + choice_put(sel, COL_INACTIVE); \ + if(sel == 0) { \ + sel = (choice_count - 1); \ + } else { \ + sel--; \ + } \ + choice_put(sel, COL_ACTIVE); \ + } \ + } \ + \ + window_animate(HELP_LEFT, HELP_TOP, HELP_W, HELP_LINES, rollup); \ + window_animate(CHOICE_LEFT, CHOICE_TOP, CHOICE_W, choice_count, rollup); \ +} + +void near setup_bgm_menu(void) +{ + int sel; + setup_submenu( + sel, + SETUP_BGM_CAPTION, + SND_BGM_MODE_COUNT, + SND_BGM_FM86, + bgm_choice_put, + bgm_help_put, + INPUT_UP + ); + resident->bgm_mode = sel; +} + +void near setup_se_menu(void) +{ + int sel; + setup_submenu( + sel, + SETUP_SE_CAPTION, + SND_SE_MODE_COUNT, + SND_SE_FM, + se_choice_put, + se_help_put, + INPUT_DOWN + ); + resident->se_mode = sel; +} diff --git a/th04/setup.asm b/th04/setup.asm index cfba9988..1cfb8761 100644 --- a/th04/setup.asm +++ b/th04/setup.asm @@ -1,14 +1,2 @@ - @DROPDOWN$QII procdesc pascal near \ - topleft:dword - @SINGLELINE$QII procdesc pascal near \ - topleft:dword - @ROLLUP$QII procdesc pascal near \ - topleft:dword - @BGM_CHOICE_PUT$QIUI procdesc pascal near \ - se_mode:word, col:word - @SE_CHOICE_PUT$QIUI procdesc pascal near \ - se_mode:word, col:word - @bgm_help_put$qv procdesc near - @se_help_put$qv procdesc near - -WINDOW_TILE_W = 16 + @setup_bgm_menu$qv procdesc near + @setup_se_menu$qv procdesc near diff --git a/th04/setup[data].asm b/th04/setup[data].asm index 5526df60..f46e24bc 100644 --- a/th04/setup[data].asm +++ b/th04/setup[data].asm @@ -1,5 +1,2 @@ -aSETUP_BGM_HEAD = $ - 43 -aSETUP_SE_HEAD db '    効果音に使用する音源を選択してね☆',0 -aMswin_bft db 'mswin.bft',0 -aMs_pi db 'ms.pi',0 - even +aMswin_bft = $ - 17 +aMs_pi = $ - 7 diff --git a/th04/shiftjis/m_setup.hpp b/th04/shiftjis/m_setup.hpp index b7d1944d..4a9ca359 100644 --- a/th04/shiftjis/m_setup.hpp +++ b/th04/shiftjis/m_setup.hpp @@ -1,4 +1,5 @@ static const int HELP_LINES = 9; +static const pixel_t HELP_W = (46 * GLYPH_HALF_W); shiftjis_t* BGM_HELP[HELP_LINES] = { "ステレオFM音源:PC-9801-86(互換)ボード   ", @@ -30,6 +31,11 @@ shiftjis_t* SE_HELP[HELP_LINES] = { #define SE_CHOICE_FM "  FM音源  " #define SE_CHOICE_BEEP " Beep音源 " -#define SE_CHOICE_OFF "  効果音無し  \0" SETUP_BGM_CAPTION +#define SE_CHOICE_OFF "  効果音無し  " +// ZUN bloat: Why not centered? That's why we have to hardcode the length for +// those as well, even though we could infer it. #define SETUP_BGM_CAPTION "     使用する音源を選択して下さいね☆" +#define SETUP_SE_CAPTION "    効果音に使用する音源を選択してね☆\0mswin.bft\0ms.pi" + +static const pixel_t CAPTION_W = (52 * GLYPH_HALF_W); diff --git a/th04_op.asm b/th04_op.asm index 80b3ea14..4f5f402c 100644 --- a/th04_op.asm +++ b/th04_op.asm @@ -67,206 +67,6 @@ OP_SETUP_TEXT segment byte public 'CODE' use16 include th04/setup.asm -; =============== S U B R O U T I N E ======================================= - -; Attributes: bp-based frame - -sub_B794 proc near - -var_2 = word ptr -2 - - enter 2, 0 - mov _window_tiles.x, (448 / WINDOW_TILE_W) - call @singleline$qii pascal, (96 shl 16) or 80 - call graph_putsa_fx pascal, (112 shl 16) or 88, V_WHITE, ds, offset aSETUP_BGM_HEAD - mov _window_tiles.x, (160 / WINDOW_TILE_W) - mov _window_tiles.y, 1 + 3 - call @dropdown$qii pascal, ( 32 shl 16) or 128 - mov [bp+var_2], 0 - jmp short loc_B7EB -; --------------------------------------------------------------------------- - -loc_B7D4: - push [bp+var_2] - cmp [bp+var_2], 2 - jnz short loc_B7E2 - mov ax, V_WHITE - jmp short loc_B7E4 -; --------------------------------------------------------------------------- - -loc_B7E2: - xor ax, ax - -loc_B7E4: - push ax - call @bgm_choice_put$qiui - inc [bp+var_2] - -loc_B7EB: - cmp [bp+var_2], 3 - jl short loc_B7D4 - mov _window_tiles.x, (400 / WINDOW_TILE_W) - mov _window_tiles.y, 1 + 9 - call @dropdown$qii pascal, (192 shl 16) or 128 - call @bgm_help_put$qv - mov [bp+var_2], 2 - -loc_B80E: - call input_wait_for_change pascal, 0 - push 1 - call frame_delay - test _key_det.hi, high INPUT_OK - jnz short loc_B87A - test _key_det.lo, low INPUT_SHOT - jnz short loc_B87A - test _key_det.lo, low INPUT_UP - jz short loc_B851 - call @bgm_choice_put$qiui pascal, [bp+var_2], 0 - cmp [bp+var_2], 2 - jnz short loc_B846 - mov [bp+var_2], 0 - jmp short loc_B849 -; --------------------------------------------------------------------------- - -loc_B846: - inc [bp+var_2] - -loc_B849: - call @bgm_choice_put$qiui pascal, [bp+var_2], V_WHITE - -loc_B851: - test _key_det.lo, low INPUT_DOWN - jz short loc_B80E - call @bgm_choice_put$qiui pascal, [bp+var_2], 0 - cmp [bp+var_2], 0 - jnz short loc_B86D - mov [bp+var_2], 2 - jmp short loc_B870 -; --------------------------------------------------------------------------- - -loc_B86D: - dec [bp+var_2] - -loc_B870: - call @bgm_choice_put$qiui pascal, [bp+var_2], V_WHITE - jmp short loc_B80E -; --------------------------------------------------------------------------- - -loc_B87A: - mov _window_tiles.x, (400 / WINDOW_TILE_W) - mov _window_tiles.y, 1 + 9 - call @rollup$qii pascal, (192 shl 16) or 128 - mov _window_tiles.x, (160 / WINDOW_TILE_W) - mov _window_tiles.y, 1 + 3 - call @rollup$qii pascal, ( 32 shl 16) or 128 - les bx, _resident - mov al, byte ptr [bp+var_2] - mov es:[bx+resident_t.bgm_mode], al - leave - retn -sub_B794 endp - - -; =============== S U B R O U T I N E ======================================= - -; Attributes: bp-based frame - -sub_B8B1 proc near - -var_2 = word ptr -2 - - enter 2, 0 - mov _window_tiles.x, (448 / WINDOW_TILE_W) - call @singleline$qii pascal, (96 shl 16) or 80 - call graph_putsa_fx pascal, (112 shl 16) or 88, V_WHITE, ds, offset aSETUP_SE_HEAD - mov _window_tiles.x, (160 / WINDOW_TILE_W) - mov _window_tiles.y, 1 + 3 - call @dropdown$qii pascal, ( 32 shl 16) or 128 - mov [bp+var_2], 0 - jmp short loc_B908 -; --------------------------------------------------------------------------- - -loc_B8F1: - push [bp+var_2] - cmp [bp+var_2], 1 - jnz short loc_B8FF - mov ax, V_WHITE - jmp short loc_B901 -; --------------------------------------------------------------------------- - -loc_B8FF: - xor ax, ax - -loc_B901: - push ax - call @se_choice_put$qiui - inc [bp+var_2] - -loc_B908: - cmp [bp+var_2], 3 - jl short loc_B8F1 - mov _window_tiles.x, (400 / WINDOW_TILE_W) - mov _window_tiles.y, 1 + 9 - call @dropdown$qii pascal, (192 shl 16) or 128 - call @se_help_put$qv - mov [bp+var_2], 1 - -loc_B92B: - call input_wait_for_change pascal, 0 - push 1 - call frame_delay - test _key_det.hi, high INPUT_OK - jnz short loc_B997 - test _key_det.lo, low INPUT_SHOT - jnz short loc_B997 - test _key_det.lo, low INPUT_DOWN - jz short loc_B96E - call @se_choice_put$qiui pascal, [bp+var_2], 0 - cmp [bp+var_2], 2 - jnz short loc_B963 - mov [bp+var_2], 0 - jmp short loc_B966 -; --------------------------------------------------------------------------- - -loc_B963: - inc [bp+var_2] - -loc_B966: - call @se_choice_put$qiui pascal, [bp+var_2], V_WHITE - -loc_B96E: - test _key_det.lo, low INPUT_UP - jz short loc_B92B - call @se_choice_put$qiui pascal, [bp+var_2], 0 - cmp [bp+var_2], 0 - jnz short loc_B98A - mov [bp+var_2], 2 - jmp short loc_B98D -; --------------------------------------------------------------------------- - -loc_B98A: - dec [bp+var_2] - -loc_B98D: - call @se_choice_put$qiui pascal, [bp+var_2], V_WHITE - jmp short loc_B92B -; --------------------------------------------------------------------------- - -loc_B997: - mov _window_tiles.x, (400 / WINDOW_TILE_W) - mov _window_tiles.y, 1 + 9 - call @rollup$qii pascal, (192 shl 16) or 128 - mov _window_tiles.x, (160 / WINDOW_TILE_W) - mov _window_tiles.y, 1 + 3 - call @rollup$qii pascal, ( 32 shl 16) or 128 - les bx, _resident - mov al, byte ptr [bp+var_2] - mov es:[bx+resident_t.se_mode], al - leave - retn -sub_B8B1 endp - - ; =============== S U B R O U T I N E ======================================= ; Attributes: bp-based frame @@ -285,11 +85,11 @@ _setup_menu proc near call graph_copy_page pascal, 0 push 1 call palette_black_in - call sub_B794 + call @setup_bgm_menu$qv push 1 call frame_delay call graph_copy_page pascal, 0 - call sub_B8B1 + call @setup_se_menu$qv push 1 call palette_black_out call super_free @@ -1380,7 +1180,6 @@ include th02/snd/snd.inc extern PI_PALETTE_APPLY:proc extern PI_PUT_8:proc extern PI_LOAD:proc - extern INPUT_WAIT_FOR_CHANGE:proc extern @POLAR$QIII:proc extern SND_KAJA_INTERRUPT:proc extern SND_DELAY_UNTIL_MEASURE:proc @@ -1555,7 +1354,6 @@ aOp1_pi_1 db 'op1.pi',0 ; th02/hardware/input_sense[bss].asm extern _key_det:word - extern _window_tiles:Point include th04/zunsoft[bss].asm db 56 dup(?) include th02/op/music[bss].asm diff --git a/th05_op.asm b/th05_op.asm index f1d7b074..4e30e301 100644 --- a/th05_op.asm +++ b/th05_op.asm @@ -70,206 +70,6 @@ CFG_TEXT segment byte public 'CODE' use16 include th04/setup.asm -; =============== S U B R O U T I N E ======================================= - -; Attributes: bp-based frame - -sub_B36C proc near - -var_2 = word ptr -2 - - enter 2, 0 - mov _window_tiles.x, (448 / WINDOW_TILE_W) - call @singleline$qii pascal, (96 shl 16) or 80 - call graph_putsa_fx pascal, (112 shl 16) or 88, V_WHITE, ds, offset aSETUP_BGM_HEAD - mov _window_tiles.x, (160 / WINDOW_TILE_W) - mov _window_tiles.y, 1 + 3 - call @dropdown$qii pascal, ( 32 shl 16) or 128 - mov [bp+var_2], 0 - jmp short loc_B3C3 -; --------------------------------------------------------------------------- - -loc_B3AC: - push [bp+var_2] - cmp [bp+var_2], 2 - jnz short loc_B3BA - mov ax, V_WHITE - jmp short loc_B3BC -; --------------------------------------------------------------------------- - -loc_B3BA: - xor ax, ax - -loc_B3BC: - push ax - call @bgm_choice_put$qiui - inc [bp+var_2] - -loc_B3C3: - cmp [bp+var_2], 3 - jl short loc_B3AC - mov _window_tiles.x, (400 / WINDOW_TILE_W) - mov _window_tiles.y, 1 + 9 - call @dropdown$qii pascal, (192 shl 16) or 128 - call @bgm_help_put$qv - mov [bp+var_2], 2 - -loc_B3E6: - call input_wait_for_change pascal, 0 - push 1 - call frame_delay - test _key_det.hi, high INPUT_OK - jnz short loc_B452 - test _key_det.lo, low INPUT_SHOT - jnz short loc_B452 - test _key_det.lo, low INPUT_UP - jz short loc_B429 - call @bgm_choice_put$qiui pascal, [bp+var_2], 0 - cmp [bp+var_2], 2 - jnz short loc_B41E - mov [bp+var_2], 0 - jmp short loc_B421 -; --------------------------------------------------------------------------- - -loc_B41E: - inc [bp+var_2] - -loc_B421: - call @bgm_choice_put$qiui pascal, [bp+var_2], V_WHITE - -loc_B429: - test _key_det.lo, low INPUT_DOWN - jz short loc_B3E6 - call @bgm_choice_put$qiui pascal, [bp+var_2], 0 - cmp [bp+var_2], 0 - jnz short loc_B445 - mov [bp+var_2], 2 - jmp short loc_B448 -; --------------------------------------------------------------------------- - -loc_B445: - dec [bp+var_2] - -loc_B448: - call @bgm_choice_put$qiui pascal, [bp+var_2], V_WHITE - jmp short loc_B3E6 -; --------------------------------------------------------------------------- - -loc_B452: - mov _window_tiles.x, (400 / WINDOW_TILE_W) - mov _window_tiles.y, 1 + 9 - call @rollup$qii pascal, (192 shl 16) or 128 - mov _window_tiles.x, (160 / WINDOW_TILE_W) - mov _window_tiles.y, 1 + 3 - call @rollup$qii pascal, ( 32 shl 16) or 128 - les bx, _resident - mov al, byte ptr [bp+var_2] - mov es:[bx+resident_t.bgm_mode], al - leave - retn -sub_B36C endp - - -; =============== S U B R O U T I N E ======================================= - -; Attributes: bp-based frame - -sub_B489 proc near - -var_2 = word ptr -2 - - enter 2, 0 - mov _window_tiles.x, (448 / WINDOW_TILE_W) - call @singleline$qii pascal, (96 shl 16) or 80 - call graph_putsa_fx pascal, (112 shl 16) or 88, V_WHITE, ds, offset aSETUP_SE_HEAD - mov _window_tiles.x, (160 / WINDOW_TILE_W) - mov _window_tiles.y, 1 + 3 - call @dropdown$qii pascal, ( 32 shl 16) or 128 - mov [bp+var_2], 0 - jmp short loc_B4E0 -; --------------------------------------------------------------------------- - -loc_B4C9: - push [bp+var_2] - cmp [bp+var_2], 1 - jnz short loc_B4D7 - mov ax, V_WHITE - jmp short loc_B4D9 -; --------------------------------------------------------------------------- - -loc_B4D7: - xor ax, ax - -loc_B4D9: - push ax - call @se_choice_put$qiui - inc [bp+var_2] - -loc_B4E0: - cmp [bp+var_2], 3 - jl short loc_B4C9 - mov _window_tiles.x, (400 / WINDOW_TILE_W) - mov _window_tiles.y, 1 + 9 - call @dropdown$qii pascal, (192 shl 16) or 128 - call @se_help_put$qv - mov [bp+var_2], 1 - -loc_B503: - call input_wait_for_change pascal, 0 - push 1 - call frame_delay - test _key_det.hi, high INPUT_OK - jnz short loc_B56F - test _key_det.lo, low INPUT_SHOT - jnz short loc_B56F - test _key_det.lo, low INPUT_DOWN - jz short loc_B546 - call @se_choice_put$qiui pascal, [bp+var_2], 0 - cmp [bp+var_2], 2 - jnz short loc_B53B - mov [bp+var_2], 0 - jmp short loc_B53E -; --------------------------------------------------------------------------- - -loc_B53B: - inc [bp+var_2] - -loc_B53E: - call @se_choice_put$qiui pascal, [bp+var_2], V_WHITE - -loc_B546: - test _key_det.lo, low INPUT_UP - jz short loc_B503 - call @se_choice_put$qiui pascal, [bp+var_2], 0 - cmp [bp+var_2], 0 - jnz short loc_B562 - mov [bp+var_2], 2 - jmp short loc_B565 -; --------------------------------------------------------------------------- - -loc_B562: - dec [bp+var_2] - -loc_B565: - call @se_choice_put$qiui pascal, [bp+var_2], V_WHITE - jmp short loc_B503 -; --------------------------------------------------------------------------- - -loc_B56F: - mov _window_tiles.x, (400 / WINDOW_TILE_W) - mov _window_tiles.y, 1 + 9 - call @rollup$qii pascal, (192 shl 16) or 128 - mov _window_tiles.x, (160 / WINDOW_TILE_W) - mov _window_tiles.y, 1 + 3 - call @rollup$qii pascal, ( 32 shl 16) or 128 - les bx, _resident - mov al, byte ptr [bp+var_2] - mov es:[bx+resident_t.se_mode], al - leave - retn -sub_B489 endp - - ; =============== S U B R O U T I N E ======================================= ; Attributes: bp-based frame @@ -288,11 +88,11 @@ _setup_menu proc near call graph_copy_page pascal, 0 push 1 call palette_black_in - call sub_B36C + call @setup_bgm_menu$qv push 1 call frame_delay call graph_copy_page pascal, 0 - call sub_B489 + call @setup_se_menu$qv push 1 call palette_black_out call super_free @@ -1421,7 +1221,6 @@ include th02/snd/snd.inc extern PI_PALETTE_APPLY:proc extern PI_FREE:proc extern _input_reset_sense_held:proc - extern INPUT_WAIT_FOR_CHANGE:proc extern SND_DELAY_UNTIL_MEASURE:proc extern FRAME_DELAY:proc extern CDG_LOAD_SINGLE_NOALPHA:proc @@ -2015,7 +1814,6 @@ aOp_1 db 'op',0 ; th02/hardware/input_sense[bss].asm extern _key_det:word - extern _window_tiles:Point include th04/zunsoft[bss].asm db 104 dup(?) include th02/op/music[bss].asm