feat(menu): sons de navegació i acceptació al menú de servei
This commit is contained in:
1 parent
0847e9c544
commit
45514ae2f4
9 files changed
+62
No files matched your search
Binary file not shown.
Binary file not shown.
@@ -75,3 +75,10 @@ pause:
|
||||
exit_ms: 250
|
||||
enter_curve: outCubic
|
||||
exit_curve: inCubic
|
||||
|
||||
# Sons del menú de servei. Els fitxers viuen a data/sounds/. SELECT
|
||||
# acompanya navegació (amunt/avall) i back; ACCEPT acompanya modificació
|
||||
# d'opció (esquerra/dreta/retorn) o entrada a un submenú.
|
||||
sounds:
|
||||
menu_select: "menu_select.wav"
|
||||
menu_accept: "menu_accept.wav"
|
||||
@@ -145,6 +145,14 @@ Director::Director() {
|
||||
Resource::Cache::get().loadMusic("playing.ogg", "data/music/playing.ogg");
|
||||
Resource::Cache::get().loadMusic("room_outro.ogg", "data/music/room_outro.ogg");
|
||||
|
||||
// Sons del menú de servei. Els noms venen de `data/ui.yaml` (amb
|
||||
// fallback a `Defaults::UI::MENU_*_SOUND`); el ServiceMenu els
|
||||
// dispara via Audio::Group::INTERFACE.
|
||||
const auto& menu_select = UiConfig::get().menuSelectSound();
|
||||
const auto& menu_accept = UiConfig::get().menuAcceptSound();
|
||||
Resource::Cache::get().loadSound(menu_select, "data/sounds/" + menu_select);
|
||||
Resource::Cache::get().loadSound(menu_accept, "data/sounds/" + menu_accept);
|
||||
|
||||
// Catàleg de presets d'efectes per als sons. Es carrega abans d'Audio
|
||||
// perquè els primers playSoundWith* (al començament del joc) ja
|
||||
// troben els presets disponibles.
|
||||
|
||||
@@ -96,6 +96,8 @@ UiConfig::UiConfig()
|
||||
pause_exit_ms_(Defaults::UI::PAUSE_EXIT_MS),
|
||||
pause_enter_curve_(curveByName(Defaults::UI::PAUSE_ENTER_CURVE)),
|
||||
pause_exit_curve_(curveByName(Defaults::UI::PAUSE_EXIT_CURVE)),
|
||||
menu_select_sound_(Defaults::UI::MENU_SELECT_SOUND),
|
||||
menu_accept_sound_(Defaults::UI::MENU_ACCEPT_SOUND),
|
||||
hud_font_{.name = Defaults::UI::Font::HUD_NAME, .gif = Defaults::UI::Font::HUD_GIF, .fnt = Defaults::UI::Font::HUD_FNT, .kerning = Defaults::UI::Font::HUD_KERNING},
|
||||
placeholder_font_{.name = Defaults::UI::Font::PLACEHOLDER_NAME, .gif = Defaults::UI::Font::PLACEHOLDER_GIF, .fnt = Defaults::UI::Font::PLACEHOLDER_FNT, .kerning = Defaults::UI::Font::PLACEHOLDER_KERNING},
|
||||
room_text_font_{.name = Defaults::UI::Font::ROOM_TEXT_NAME, .gif = Defaults::UI::Font::ROOM_TEXT_GIF, .fnt = Defaults::UI::Font::ROOM_TEXT_FNT, .kerning = Defaults::UI::Font::ROOM_TEXT_KERNING},
|
||||
@@ -185,6 +187,12 @@ void UiConfig::load(const std::string& file_path) {
|
||||
readCurve(p, "exit_curve", pause_exit_curve_);
|
||||
}
|
||||
|
||||
if (yaml.contains("sounds")) {
|
||||
const auto& s = yaml["sounds"];
|
||||
readField(s, "menu_select", menu_select_sound_);
|
||||
readField(s, "menu_accept", menu_accept_sound_);
|
||||
}
|
||||
|
||||
std::cout << "UiConfig: carregat des de " << file_path << '\n';
|
||||
} catch (const std::exception& e) {
|
||||
std::cerr << "UiConfig: error parsejant " << file_path << ": " << e.what() << '\n';
|
||||
|
||||
@@ -76,6 +76,11 @@ class UiConfig {
|
||||
// retorna Easing::linear i deixa un warning al log.
|
||||
[[nodiscard]] static auto curveByName(const std::string& name) -> CurveFn;
|
||||
|
||||
// Sons del menú de servei. Claus de Resource::Cache::loadSound (els
|
||||
// fitxers viuen a `data/sounds/`).
|
||||
[[nodiscard]] auto menuSelectSound() const -> const std::string& { return menu_select_sound_; }
|
||||
[[nodiscard]] auto menuAcceptSound() const -> const std::string& { return menu_accept_sound_; }
|
||||
|
||||
// Fonts de UI.
|
||||
[[nodiscard]] auto hudFont() const -> const Font& { return hud_font_; }
|
||||
[[nodiscard]] auto placeholderFont() const -> const Font& { return placeholder_font_; }
|
||||
@@ -121,6 +126,9 @@ class UiConfig {
|
||||
CurveFn pause_enter_curve_;
|
||||
CurveFn pause_exit_curve_;
|
||||
|
||||
std::string menu_select_sound_;
|
||||
std::string menu_accept_sound_;
|
||||
|
||||
Font hud_font_;
|
||||
Font placeholder_font_;
|
||||
Font room_text_font_;
|
||||
|
||||
@@ -459,6 +459,14 @@ namespace {
|
||||
|
||||
} // namespace
|
||||
|
||||
void ServiceMenu::playSelectSound() {
|
||||
Audio::get()->playSound(UiConfig::get().menuSelectSound(), Audio::Group::INTERFACE);
|
||||
}
|
||||
|
||||
void ServiceMenu::playAcceptSound() {
|
||||
Audio::get()->playSound(UiConfig::get().menuAcceptSound(), Audio::Group::INTERFACE);
|
||||
}
|
||||
|
||||
void ServiceMenu::handleGamepadButtonDown(const SDL_GamepadButtonEvent& ev) {
|
||||
// El botó SERVICE (per defecte BACK; remapejable per dispositiu via
|
||||
// `GamepadBindings`) tanca el menú sencer. Cada mando pot tenir el
|
||||
@@ -466,26 +474,32 @@ void ServiceMenu::handleGamepadButtonDown(const SDL_GamepadButtonEvent& ev) {
|
||||
const int SERVICE_BTN = serviceButtonForEvent(ev.which);
|
||||
if (SERVICE_BTN >= 0 && static_cast<int>(ev.button) == SERVICE_BTN) {
|
||||
close();
|
||||
playSelectSound();
|
||||
return;
|
||||
}
|
||||
switch (ev.button) {
|
||||
case SDL_GAMEPAD_BUTTON_DPAD_UP:
|
||||
moveCursor(-1);
|
||||
playSelectSound();
|
||||
break;
|
||||
case SDL_GAMEPAD_BUTTON_DPAD_DOWN:
|
||||
moveCursor(+1);
|
||||
playSelectSound();
|
||||
break;
|
||||
case SDL_GAMEPAD_BUTTON_DPAD_LEFT:
|
||||
activateCurrent(-1);
|
||||
playAcceptSound();
|
||||
break;
|
||||
case SDL_GAMEPAD_BUTTON_DPAD_RIGHT:
|
||||
case SDL_GAMEPAD_BUTTON_EAST:
|
||||
case SDL_GAMEPAD_BUTTON_NORTH:
|
||||
activateCurrent(+1);
|
||||
playAcceptSound();
|
||||
break;
|
||||
case SDL_GAMEPAD_BUTTON_WEST:
|
||||
case SDL_GAMEPAD_BUTTON_SOUTH:
|
||||
popPage();
|
||||
playSelectSound();
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
@@ -567,21 +581,26 @@ auto ServiceMenu::handleEvent(const SDL_Event& ev) -> bool {
|
||||
switch (SC) {
|
||||
case SDL_SCANCODE_UP:
|
||||
moveCursor(-1);
|
||||
playSelectSound();
|
||||
break;
|
||||
case SDL_SCANCODE_DOWN:
|
||||
moveCursor(+1);
|
||||
playSelectSound();
|
||||
break;
|
||||
case SDL_SCANCODE_LEFT:
|
||||
activateCurrent(-1);
|
||||
playAcceptSound();
|
||||
break;
|
||||
case SDL_SCANCODE_RIGHT:
|
||||
case SDL_SCANCODE_RETURN:
|
||||
case SDL_SCANCODE_KP_ENTER:
|
||||
activateCurrent(+1);
|
||||
playAcceptSound();
|
||||
break;
|
||||
case SDL_SCANCODE_BACKSPACE:
|
||||
case SDL_SCANCODE_ESCAPE:
|
||||
popPage();
|
||||
playSelectSound();
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
|
||||
@@ -207,6 +207,12 @@ class ServiceMenu {
|
||||
// mètode propi per a mantenir la complexitat cognitiva d'`handleEvent`
|
||||
// sota el llindar de clang-tidy.
|
||||
void handleGamepadButtonDown(const SDL_GamepadButtonEvent& ev);
|
||||
|
||||
// Sons d'UI: SELECT acompanya navegació (amunt/avall) i back; ACCEPT
|
||||
// acompanya modificació d'opció (esquerra/dreta/retorn). Els noms de
|
||||
// recurs venen d'`UiConfig` i el preload el fa el Director.
|
||||
static void playSelectSound();
|
||||
static void playAcceptSound();
|
||||
[[nodiscard]] auto top() -> Page&;
|
||||
[[nodiscard]] auto topConst() const -> const Page&;
|
||||
[[nodiscard]] static auto isItemVisible(const Item& item) -> bool;
|
||||
|
||||
@@ -216,6 +216,12 @@ namespace Defaults {
|
||||
constexpr int PAUSE_EXIT_MS = 250;
|
||||
constexpr const char* PAUSE_ENTER_CURVE = "outCubic";
|
||||
constexpr const char* PAUSE_EXIT_CURVE = "inCubic";
|
||||
|
||||
// Sons del menú de servei. SELECT acompanya navegació (amunt/avall)
|
||||
// i back; ACCEPT acompanya modificació d'opció (esq/dret/retorn).
|
||||
// Els fitxers viuen a `data/sounds/`; només es referencia el nom.
|
||||
constexpr const char* MENU_SELECT_SOUND = "menu_select.wav";
|
||||
constexpr const char* MENU_ACCEPT_SOUND = "menu_accept.wav";
|
||||
} // namespace UI
|
||||
|
||||
#ifdef _DEBUG
|
||||
|
||||
Reference in new issue
Block a user