- Adding Hotkeys

This commit is contained in:
Burai Mu 2025-09-16 23:12:22 +08:00
parent f1964baff2
commit 81f0228b3c
8 changed files with 109 additions and 24 deletions

View File

@ -231,6 +231,7 @@ export class BattleScene extends SceneBase {
public fusionPaletteSwaps = true; public fusionPaletteSwaps = true;
public enableTouchControls = false; public enableTouchControls = false;
public enableVibration = false; public enableVibration = false;
public enableHotkeyTip = false;
public showBgmBar = true; public showBgmBar = true;
public hideUsername = false; public hideUsername = false;
/** Determines the selected battle style. */ /** Determines the selected battle style. */

View File

@ -92,6 +92,17 @@ export function getIconWithSettingName(config, settingName) {
return getIconWithKey(config, key); return getIconWithKey(config, key);
} }
export function getKeyForLatestInput(configs, source, devices, settingName) {
let config: any; // TODO: refine type
if (source === "gamepad") {
config = configs[devices[Device.GAMEPAD]];
} else {
config = configs[devices[Device.KEYBOARD]];
}
const key = Object.keys(config["custom"]).find(k => config["custom"][k] === settingName);
return key?.slice(4)
}
export function getIconForLatestInput(configs, source, devices, settingName) { export function getIconForLatestInput(configs, source, devices, settingName) {
let config: any; // TODO: refine type let config: any; // TODO: refine type
if (source === "gamepad") { if (source === "gamepad") {

View File

@ -4,7 +4,7 @@ import { Button } from "#enums/buttons";
import { Device } from "#enums/devices"; import { Device } from "#enums/devices";
import { UiMode } from "#enums/ui-mode"; import { UiMode } from "#enums/ui-mode";
import cfg_keyboard_qwerty from "#inputs/cfg-keyboard-qwerty"; import cfg_keyboard_qwerty from "#inputs/cfg-keyboard-qwerty";
import { assign, getButtonWithKeycode, getIconForLatestInput, swap } from "#inputs/config-handler"; import { assign, getButtonWithKeycode, getIconForLatestInput, getKeyForLatestInput, getKeyWithKeycode, swap } from "#inputs/config-handler";
import pad_dualshock from "#inputs/pad-dualshock"; import pad_dualshock from "#inputs/pad-dualshock";
import pad_generic from "#inputs/pad-generic"; import pad_generic from "#inputs/pad-generic";
import pad_procon from "#inputs/pad-procon"; import pad_procon from "#inputs/pad-procon";
@ -540,6 +540,14 @@ export class InputsController {
return getIconForLatestInput(this.configs, this.lastSource, this.selectedDevice, settingName); return getIconForLatestInput(this.configs, this.lastSource, this.selectedDevice, settingName);
} }
getKeyForLatestInputRecorded(settingName) {
if (this.lastSource === "keyboard") {
this.ensureKeyboardIsInit();
}
return getKeyForLatestInput(this.configs, this.lastSource, this.selectedDevice, settingName);
}
getLastSourceDevice(): Device { getLastSourceDevice(): Device {
if (this.lastSource === "gamepad") { if (this.lastSource === "gamepad") {
return Device.GAMEPAD; return Device.GAMEPAD;

View File

@ -151,6 +151,7 @@ export const SettingKeys = {
Tutorials: "TUTORIALS", Tutorials: "TUTORIALS",
Touch_Controls: "TOUCH_CONTROLS", Touch_Controls: "TOUCH_CONTROLS",
Vibration: "VIBRATION", Vibration: "VIBRATION",
HotkeyTips: "HOTKEY_TIPS",
Language: "LANGUAGE", Language: "LANGUAGE",
UI_Theme: "UI_THEME", UI_Theme: "UI_THEME",
Window_Type: "WINDOW_TYPE", Window_Type: "WINDOW_TYPE",
@ -386,6 +387,13 @@ export const Setting: Array<Setting> = [
default: 0, default: 0,
type: SettingType.GENERAL, type: SettingType.GENERAL,
}, },
{
key: SettingKeys.HotkeyTips,
label: i18next.t("settings:hotkeyTips"),
options: OFF_ON,
default: 0,
type: SettingType.GENERAL,
},
{ {
key: SettingKeys.Touch_Controls, key: SettingKeys.Touch_Controls,
label: i18next.t("settings:touchControls"), label: i18next.t("settings:touchControls"),
@ -906,6 +914,9 @@ export function setSetting(setting: string, value: number): boolean {
case SettingKeys.Vibration: case SettingKeys.Vibration:
globalScene.enableVibration = Setting[index].options[value].value !== "Disabled" && hasTouchscreen(); globalScene.enableVibration = Setting[index].options[value].value !== "Disabled" && hasTouchscreen();
break; break;
case SettingKeys.HotkeyTips:
globalScene.enableHotkeyTip = Setting[index].options[value].value !== "On";
break;
case SettingKeys.Type_Hints: case SettingKeys.Type_Hints:
globalScene.typeHints = Setting[index].options[value].value === "On"; globalScene.typeHints = Setting[index].options[value].value === "On";
break; break;

View File

@ -87,8 +87,8 @@ export class UiInputs {
[Button.LEFT]: () => this.buttonDirection(Button.LEFT), [Button.LEFT]: () => this.buttonDirection(Button.LEFT),
[Button.RIGHT]: () => this.buttonDirection(Button.RIGHT), [Button.RIGHT]: () => this.buttonDirection(Button.RIGHT),
[Button.SUBMIT]: () => this.buttonTouch(), [Button.SUBMIT]: () => this.buttonTouch(),
[Button.ACTION]: () => this.buttonAb(Button.ACTION), [Button.ACTION]: () => this.buttonAB(Button.ACTION),
[Button.CANCEL]: () => this.buttonAb(Button.CANCEL), [Button.CANCEL]: () => this.buttonAB(Button.CANCEL),
[Button.MENU]: () => this.buttonMenu(), [Button.MENU]: () => this.buttonMenu(),
[Button.STATS]: () => this.buttonGoToFilter(Button.STATS), [Button.STATS]: () => this.buttonGoToFilter(Button.STATS),
[Button.CYCLE_SHINY]: () => this.buttonCycleOption(Button.CYCLE_SHINY), [Button.CYCLE_SHINY]: () => this.buttonCycleOption(Button.CYCLE_SHINY),
@ -132,7 +132,15 @@ export class UiInputs {
this.doVibration(inputSuccess, vibrationLength); this.doVibration(inputSuccess, vibrationLength);
} }
buttonAb(button: Button): void { buttonAB(button: Button): void {
if (this.isInSettings()) {
const whiteListUIModes : UiMode[] = [
UiMode.MODIFIER_SELECT
]
for (const uiMode of whiteListUIModes){
globalScene.ui.handlers[uiMode].updateInstructionsText()
}
}
globalScene.ui.processInput(button); globalScene.ui.processInput(button);
} }
@ -250,4 +258,12 @@ export class UiInputs {
(globalScene.ui.getHandler() as SettingsUiHandler).show([]); (globalScene.ui.getHandler() as SettingsUiHandler).show([]);
} }
} }
private isInSettings(){
return globalScene.ui?.getMode() === UiMode.SETTINGS ||
globalScene.ui?.getMode() === UiMode.SETTINGS_AUDIO ||
globalScene.ui?.getMode() === UiMode.SETTINGS_DISPLAY ||
globalScene.ui?.getMode() === UiMode.SETTINGS_GAMEPAD ||
globalScene.ui?.getMode() === UiMode.SETTINGS_KEYBOARD
}
} }

View File

@ -11,6 +11,7 @@ import { UiMode } from "#enums/ui-mode";
import { HealShopCostModifier, LockModifierTiersModifier, PokemonHeldItemModifier } from "#modifiers/modifier"; import { HealShopCostModifier, LockModifierTiersModifier, PokemonHeldItemModifier } from "#modifiers/modifier";
import type { ModifierTypeOption } from "#modifiers/modifier-type"; import type { ModifierTypeOption } from "#modifiers/modifier-type";
import { getPlayerShopModifierTypeOptionsForWave, TmModifierType } from "#modifiers/modifier-type"; import { getPlayerShopModifierTypeOptionsForWave, TmModifierType } from "#modifiers/modifier-type";
import { SettingKeyboard } from "#system/settings-keyboard";
import { AwaitableUiHandler } from "#ui/awaitable-ui-handler"; import { AwaitableUiHandler } from "#ui/awaitable-ui-handler";
import { MoveInfoOverlay } from "#ui/move-info-overlay"; import { MoveInfoOverlay } from "#ui/move-info-overlay";
import { addTextObject, getModifierTierTextTint, getTextColor, getTextStyleOptions } from "#ui/text"; import { addTextObject, getModifierTierTextTint, getTextColor, getTextStyleOptions } from "#ui/text";
@ -31,6 +32,7 @@ export class ModifierSelectUiHandler extends AwaitableUiHandler {
private checkButtonContainer: Phaser.GameObjects.Container; private checkButtonContainer: Phaser.GameObjects.Container;
private continueButtonContainer: Phaser.GameObjects.Container; private continueButtonContainer: Phaser.GameObjects.Container;
private rerollCostText: Phaser.GameObjects.Text; private rerollCostText: Phaser.GameObjects.Text;
private rerollButtonText: Phaser.GameObjects.Text;
private lockRarityButtonText: Phaser.GameObjects.Text; private lockRarityButtonText: Phaser.GameObjects.Text;
private moveInfoOverlay: MoveInfoOverlay; private moveInfoOverlay: MoveInfoOverlay;
private moveInfoOverlayActive = false; private moveInfoOverlayActive = false;
@ -100,26 +102,28 @@ export class ModifierSelectUiHandler extends AwaitableUiHandler {
this.rerollButtonContainer.setName("reroll-brn"); this.rerollButtonContainer.setName("reroll-brn");
this.rerollButtonContainer.setVisible(false); this.rerollButtonContainer.setVisible(false);
ui.add(this.rerollButtonContainer); ui.add(this.rerollButtonContainer);
const rerollButtonText = addTextObject(-4, -2, i18next.t("modifierSelectUiHandler:reroll"), TextStyle.PARTY); const Reroll_Key = !globalScene.enableHotkeyTip ? globalScene.inputController?.getKeyForLatestInputRecorded( SettingKeyboard.Button_Cycle_Shiny) ? `(${globalScene.inputController?.getKeyForLatestInputRecorded( SettingKeyboard.Button_Cycle_Shiny)}) ` : "" : "";
rerollButtonText.setName("text-reroll-btn"); this.rerollButtonText = addTextObject(-4, -2, i18next.t("modifierSelectUiHandler:reroll", {Reroll_Key}), TextStyle.PARTY);
rerollButtonText.setOrigin(0, 0); this.rerollButtonText.setName("text-reroll-btn");
this.rerollButtonContainer.add(rerollButtonText); this.rerollButtonText.setOrigin(0, 0);
this.rerollButtonContainer.add(this.rerollButtonText);
this.rerollCostText = addTextObject(0, 0, "", TextStyle.MONEY); this.rerollCostText = addTextObject(0, 0, "", TextStyle.MONEY);
this.rerollCostText.setName("text-reroll-cost"); this.rerollCostText.setName("text-reroll-cost");
this.rerollCostText.setOrigin(0, 0); this.rerollCostText.setOrigin(0, 0);
this.rerollCostText.setPositionRelative(rerollButtonText, rerollButtonText.displayWidth + 5, 1); this.rerollCostText.setPositionRelative(this.rerollButtonText, this.rerollButtonText.displayWidth + 5, 1);
this.rerollButtonContainer.add(this.rerollCostText); this.rerollButtonContainer.add(this.rerollCostText);
this.lockRarityButtonContainer = globalScene.add.container(16, OPTION_BUTTON_YPOSITION); this.lockRarityButtonContainer = globalScene.add.container(16, OPTION_BUTTON_YPOSITION);
this.lockRarityButtonContainer.setVisible(false); this.lockRarityButtonContainer.setVisible(false);
ui.add(this.lockRarityButtonContainer); ui.add(this.lockRarityButtonContainer);
const Lock_Rarity_Key = !globalScene.enableHotkeyTip ? globalScene.inputController?.getKeyForLatestInputRecorded( SettingKeyboard.Button_Cycle_Ability) ? `(${globalScene.inputController?.getKeyForLatestInputRecorded( SettingKeyboard.Button_Cycle_Ability)}) ` : "" : "";
this.lockRarityButtonText = addTextObject( this.lockRarityButtonText = addTextObject(
-4, -4,
-2, -2,
i18next.t("modifierSelectUiHandler:lockRarities"), i18next.t("modifierSelectUiHandler:lockRarities", {Lock_Rarity_Key}),
TextStyle.PARTY, TextStyle.PARTY,
); );
this.lockRarityButtonText.setOrigin(0, 0); this.lockRarityButtonText.setOrigin(0, 0);
@ -156,6 +160,11 @@ export class ModifierSelectUiHandler extends AwaitableUiHandler {
globalScene.addInfoToggle(this.moveInfoOverlay); globalScene.addInfoToggle(this.moveInfoOverlay);
} }
updateInstructionsText() : void {
this.updateRerollText();
this.updateRerollCostPosition();
}
show(args: any[]): boolean { show(args: any[]): boolean {
globalScene.disableMenu = false; globalScene.disableMenu = false;
@ -181,7 +190,7 @@ export class ModifierSelectUiHandler extends AwaitableUiHandler {
const partyHasHeldItem = const partyHasHeldItem =
this.player this.player
&& globalScene.findModifiers(m => m instanceof PokemonHeldItemModifier && m.isTransferable).length > 0; && globalScene.findModifiers(m => m instanceof PokemonHeldItemModifier && m.isTransferable).length > 0;
const canLockRarities = !!globalScene.findModifier(m => m instanceof LockModifierTiersModifier); const canLockRarities = !(!!globalScene.findModifier(m => m instanceof LockModifierTiersModifier));
this.transferButtonContainer.setVisible(false); this.transferButtonContainer.setVisible(false);
this.transferButtonContainer.setAlpha(0); this.transferButtonContainer.setAlpha(0);
@ -201,7 +210,7 @@ export class ModifierSelectUiHandler extends AwaitableUiHandler {
this.rerollButtonContainer.setPositionRelative(this.lockRarityButtonContainer, 0, canLockRarities ? -12 : 0); this.rerollButtonContainer.setPositionRelative(this.lockRarityButtonContainer, 0, canLockRarities ? -12 : 0);
this.rerollCost = args[3] as number; this.rerollCost = args[3] as number;
this.updateRerollText();
this.updateRerollCostText(); this.updateRerollCostText();
const typeOptions = args[1] as ModifierTypeOption[]; const typeOptions = args[1] as ModifierTypeOption[];
@ -682,10 +691,28 @@ export class ModifierSelectUiHandler extends AwaitableUiHandler {
for (const shopOption of shopOptions) { for (const shopOption of shopOptions) {
shopOption.updateCostText(); shopOption.updateCostText();
} }
this.updateRerollText();
this.updateRerollCostText(); this.updateRerollCostText();
} }
updateRerollText(): void {
const Reroll_Key = !globalScene.enableHotkeyTip ? globalScene.inputController?.getKeyForLatestInputRecorded( SettingKeyboard.Button_Cycle_Shiny) ? `(${globalScene.inputController?.getKeyForLatestInputRecorded( SettingKeyboard.Button_Cycle_Shiny)}) ` : "" : "";
this.rerollButtonText.setText(i18next.t("modifierSelectUiHandler:reroll", { Reroll_Key }));
if (this.lockRarityButtonText.visible){
const Lock_Rarity_Key = !globalScene.enableHotkeyTip ? globalScene.inputController?.getKeyForLatestInputRecorded( SettingKeyboard.Button_Cycle_Ability) ? `(${globalScene.inputController?.getKeyForLatestInputRecorded( SettingKeyboard.Button_Cycle_Ability)}) ` : "" : "";
this.lockRarityButtonText.setText(i18next.t("modifierSelectUiHandler:lockRarities", { Lock_Rarity_Key }));
}
}
updateRerollCostPosition(): void {
if (globalScene.inputController?.getKeyForLatestInputRecorded( SettingKeyboard.Button_Cycle_Shiny)){
const Reroll_Key = globalScene.inputController?.getKeyForLatestInputRecorded( SettingKeyboard.Button_Cycle_Shiny)
this.rerollCostText.setPositionRelative(this.rerollButtonText, this.rerollButtonText.displayWidth + 5 + Reroll_Key?.length, 1);
}
}
updateRerollCostText(): void { updateRerollCostText(): void {
const rerollDisabled = this.rerollCost < 0; const rerollDisabled = this.rerollCost < 0;
if (rerollDisabled) { if (rerollDisabled) {
@ -700,6 +727,10 @@ export class ModifierSelectUiHandler extends AwaitableUiHandler {
this.rerollCostText.setText(i18next.t("modifierSelectUiHandler:rerollCost", { formattedMoney })); this.rerollCostText.setText(i18next.t("modifierSelectUiHandler:rerollCost", { formattedMoney }));
this.rerollCostText.setColor(getTextColor(canReroll ? TextStyle.MONEY : TextStyle.PARTY_RED)); this.rerollCostText.setColor(getTextColor(canReroll ? TextStyle.MONEY : TextStyle.PARTY_RED));
this.rerollCostText.setShadowColor(getTextColor(canReroll ? TextStyle.MONEY : TextStyle.PARTY_RED, true)); this.rerollCostText.setShadowColor(getTextColor(canReroll ? TextStyle.MONEY : TextStyle.PARTY_RED, true));
if (globalScene.inputController?.getKeyForLatestInputRecorded( SettingKeyboard.Button_Cycle_Shiny)){
const Reroll_Key = globalScene.inputController?.getKeyForLatestInputRecorded( SettingKeyboard.Button_Cycle_Shiny)
this.rerollCostText.setPositionRelative(this.rerollButtonText, this.rerollButtonText.displayWidth + 5 + Reroll_Key?.length, 1);
}
} }
updateLockRaritiesText(): void { updateLockRaritiesText(): void {

View File

@ -25,6 +25,8 @@ export abstract class UiHandler {
return true; return true;
} }
abstract updateInstructionsText(): void;
abstract processInput(button: Button): boolean; abstract processInput(button: Button): boolean;
getUi() { getUi() {

View File

@ -451,16 +451,21 @@ export abstract class AbstractControlSettingsUiHandler extends UiHandler {
// Retrieve the layout settings based on the type of the gamepad. // Retrieve the layout settings based on the type of the gamepad.
const layout = this.layout[configType]; const layout = this.layout[configType];
// Update the main controller with configuration details from the selected layout. // Update the main controller with configuration details from the selected layout.
this.keys = layout.keys; if (layout){
this.optionsContainer = layout.optionsContainer; this.keys = layout.keys;
this.optionsContainer.setVisible(true); this.optionsContainer = layout.optionsContainer;
this.settingLabels = layout.settingLabels; this.optionsContainer.setVisible(true);
this.optionValueLabels = layout.optionValueLabels; this.settingLabels = layout.settingLabels;
this.optionCursors = layout.optionCursors; this.optionValueLabels = layout.optionValueLabels;
this.inputsIcons = layout.inputsIcons; this.optionCursors = layout.optionCursors;
this.bindingSettings = layout.bindingSettings; this.inputsIcons = layout.inputsIcons;
this.scrollBar.setTotalRows(layout.settingLabels.length); this.bindingSettings = layout.bindingSettings;
this.scrollBar.setScrollCursor(0); this.scrollBar.setTotalRows(layout.settingLabels.length);
this.scrollBar.setScrollCursor(0);
}else{
return false
}
// Return true indicating the layout was successfully applied. // Return true indicating the layout was successfully applied.
return true; return true;