mirror of
https://github.com/Kelsidavis/WoWee.git
synced 2026-04-25 21:03:51 +00:00
Implement immediate settings application and fix escape menu behavior
Settings Changes: - All settings now apply immediately without Apply button - Each slider/checkbox instantly updates the game state and saves - Escape key closes settings window if open (no longer shows escape menu behind it) - Restore Defaults buttons now also apply settings immediately Audio Changes: - Increased NPC voice volume from 0.6 to 1.0 (60% to 100% base volume) - Helper lambda in Audio tab for efficient volume application - Master volume multiplier applied to all audio systems in real-time UX Improvements: - Removed redundant Apply button - Settings save automatically on every change - More intuitive settings flow - see changes instantly - Cleaner escape key handling priority
This commit is contained in:
parent
9741c8ee7c
commit
016cc01c68
2 changed files with 181 additions and 120 deletions
|
|
@ -306,7 +306,7 @@ void NpcVoiceManager::playSound(uint64_t npcGuid, VoiceType voiceType, SoundCate
|
|||
bool success = AudioEngine::instance().playSound3D(
|
||||
sample.data,
|
||||
position,
|
||||
0.6f * volumeScale_,
|
||||
1.0f * volumeScale_,
|
||||
pitchDist(rng_),
|
||||
60.0f
|
||||
);
|
||||
|
|
|
|||
|
|
@ -677,10 +677,12 @@ void GameScreen::processTargetInput(game::GameHandler& gameHandler) {
|
|||
}
|
||||
|
||||
if (input.isKeyJustPressed(SDL_SCANCODE_ESCAPE)) {
|
||||
if (showEscapeMenu) {
|
||||
if (showSettingsWindow) {
|
||||
// Close settings window if open
|
||||
showSettingsWindow = false;
|
||||
} else if (showEscapeMenu) {
|
||||
showEscapeMenu = false;
|
||||
showEscapeSettingsNotice = false;
|
||||
showSettingsWindow = false;
|
||||
} else if (gameHandler.isCasting()) {
|
||||
gameHandler.cancelCast();
|
||||
} else if (gameHandler.isLootWindowOpen()) {
|
||||
|
|
@ -4122,9 +4124,19 @@ void GameScreen::renderSettingsWindow() {
|
|||
// ============================================================
|
||||
if (ImGui::BeginTabItem("Video")) {
|
||||
ImGui::Spacing();
|
||||
ImGui::Checkbox("Fullscreen", &pendingFullscreen);
|
||||
ImGui::Checkbox("VSync", &pendingVsync);
|
||||
ImGui::Checkbox("Shadows", &pendingShadows);
|
||||
|
||||
if (ImGui::Checkbox("Fullscreen", &pendingFullscreen)) {
|
||||
window->setFullscreen(pendingFullscreen);
|
||||
saveSettings();
|
||||
}
|
||||
if (ImGui::Checkbox("VSync", &pendingVsync)) {
|
||||
window->setVsync(pendingVsync);
|
||||
saveSettings();
|
||||
}
|
||||
if (ImGui::Checkbox("Shadows", &pendingShadows)) {
|
||||
if (renderer) renderer->setShadowsEnabled(pendingShadows);
|
||||
saveSettings();
|
||||
}
|
||||
|
||||
const char* resLabel = "Resolution";
|
||||
const char* resItems[kResCount];
|
||||
|
|
@ -4133,7 +4145,10 @@ void GameScreen::renderSettingsWindow() {
|
|||
snprintf(resBuf[i], sizeof(resBuf[i]), "%dx%d", kResolutions[i][0], kResolutions[i][1]);
|
||||
resItems[i] = resBuf[i];
|
||||
}
|
||||
ImGui::Combo(resLabel, &pendingResIndex, resItems, kResCount);
|
||||
if (ImGui::Combo(resLabel, &pendingResIndex, resItems, kResCount)) {
|
||||
window->applyResolution(kResolutions[pendingResIndex][0], kResolutions[pendingResIndex][1]);
|
||||
saveSettings();
|
||||
}
|
||||
|
||||
ImGui::Spacing();
|
||||
ImGui::Separator();
|
||||
|
|
@ -4144,6 +4159,11 @@ void GameScreen::renderSettingsWindow() {
|
|||
pendingVsync = kDefaultVsync;
|
||||
pendingShadows = kDefaultShadows;
|
||||
pendingResIndex = defaultResIndex;
|
||||
window->setFullscreen(pendingFullscreen);
|
||||
window->setVsync(pendingVsync);
|
||||
window->applyResolution(kResolutions[pendingResIndex][0], kResolutions[pendingResIndex][1]);
|
||||
if (renderer) renderer->setShadowsEnabled(pendingShadows);
|
||||
saveSettings();
|
||||
}
|
||||
|
||||
ImGui::EndTabItem();
|
||||
|
|
@ -4156,128 +4176,9 @@ void GameScreen::renderSettingsWindow() {
|
|||
ImGui::Spacing();
|
||||
ImGui::BeginChild("AudioSettings", ImVec2(0, 360), true);
|
||||
|
||||
ImGui::Text("Master Volume");
|
||||
ImGui::SliderInt("##MasterVolume", &pendingMasterVolume, 0, 100, "%d%%");
|
||||
ImGui::Separator();
|
||||
|
||||
ImGui::Text("Music");
|
||||
ImGui::SliderInt("##MusicVolume", &pendingMusicVolume, 0, 100, "%d%%");
|
||||
|
||||
ImGui::Spacing();
|
||||
ImGui::Text("Ambient Sounds");
|
||||
ImGui::SliderInt("##AmbientVolume", &pendingAmbientVolume, 0, 100, "%d%%");
|
||||
ImGui::TextWrapped("Weather, zones, cities, emitters");
|
||||
|
||||
ImGui::Spacing();
|
||||
ImGui::Text("UI Sounds");
|
||||
ImGui::SliderInt("##UiVolume", &pendingUiVolume, 0, 100, "%d%%");
|
||||
ImGui::TextWrapped("Buttons, loot, quest complete");
|
||||
|
||||
ImGui::Spacing();
|
||||
ImGui::Text("Combat Sounds");
|
||||
ImGui::SliderInt("##CombatVolume", &pendingCombatVolume, 0, 100, "%d%%");
|
||||
ImGui::TextWrapped("Weapon swings, impacts, grunts");
|
||||
|
||||
ImGui::Spacing();
|
||||
ImGui::Text("Spell Sounds");
|
||||
ImGui::SliderInt("##SpellVolume", &pendingSpellVolume, 0, 100, "%d%%");
|
||||
ImGui::TextWrapped("Magic casting and impacts");
|
||||
|
||||
ImGui::Spacing();
|
||||
ImGui::Text("Movement Sounds");
|
||||
ImGui::SliderInt("##MovementVolume", &pendingMovementVolume, 0, 100, "%d%%");
|
||||
ImGui::TextWrapped("Water splashes, jump/land");
|
||||
|
||||
ImGui::Spacing();
|
||||
ImGui::Text("Footsteps");
|
||||
ImGui::SliderInt("##FootstepVolume", &pendingFootstepVolume, 0, 100, "%d%%");
|
||||
|
||||
ImGui::Spacing();
|
||||
ImGui::Text("NPC Voices");
|
||||
ImGui::SliderInt("##NpcVoiceVolume", &pendingNpcVoiceVolume, 0, 100, "%d%%");
|
||||
|
||||
ImGui::Spacing();
|
||||
ImGui::Text("Mount Sounds");
|
||||
ImGui::SliderInt("##MountVolume", &pendingMountVolume, 0, 100, "%d%%");
|
||||
|
||||
ImGui::Spacing();
|
||||
ImGui::Text("Activity Sounds");
|
||||
ImGui::SliderInt("##ActivityVolume", &pendingActivityVolume, 0, 100, "%d%%");
|
||||
ImGui::TextWrapped("Swimming, eating, drinking");
|
||||
|
||||
ImGui::EndChild();
|
||||
|
||||
if (ImGui::Button("Restore Audio Defaults", ImVec2(-1, 0))) {
|
||||
pendingMasterVolume = 100;
|
||||
pendingMusicVolume = kDefaultMusicVolume;
|
||||
pendingAmbientVolume = 100;
|
||||
pendingUiVolume = 100;
|
||||
pendingCombatVolume = 100;
|
||||
pendingSpellVolume = 100;
|
||||
pendingMovementVolume = 100;
|
||||
pendingFootstepVolume = 100;
|
||||
pendingNpcVoiceVolume = 100;
|
||||
pendingMountVolume = 100;
|
||||
pendingActivityVolume = 100;
|
||||
}
|
||||
|
||||
ImGui::EndTabItem();
|
||||
}
|
||||
|
||||
// ============================================================
|
||||
// GAMEPLAY TAB
|
||||
// ============================================================
|
||||
if (ImGui::BeginTabItem("Gameplay")) {
|
||||
ImGui::Spacing();
|
||||
|
||||
ImGui::Text("Controls");
|
||||
ImGui::Separator();
|
||||
ImGui::SliderFloat("Mouse Sensitivity", &pendingMouseSensitivity, 0.05f, 1.0f, "%.2f");
|
||||
ImGui::Checkbox("Invert Mouse", &pendingInvertMouse);
|
||||
|
||||
ImGui::Spacing();
|
||||
ImGui::Spacing();
|
||||
|
||||
ImGui::Text("Interface");
|
||||
ImGui::Separator();
|
||||
ImGui::SliderInt("UI Opacity", &pendingUiOpacity, 20, 100, "%d%%");
|
||||
ImGui::Checkbox("Rotate Minimap", &pendingMinimapRotate);
|
||||
|
||||
ImGui::Spacing();
|
||||
ImGui::Separator();
|
||||
ImGui::Spacing();
|
||||
|
||||
if (ImGui::Button("Restore Gameplay Defaults", ImVec2(-1, 0))) {
|
||||
pendingMouseSensitivity = kDefaultMouseSensitivity;
|
||||
pendingInvertMouse = kDefaultInvertMouse;
|
||||
pendingUiOpacity = 65;
|
||||
pendingMinimapRotate = false;
|
||||
}
|
||||
|
||||
ImGui::EndTabItem();
|
||||
}
|
||||
|
||||
ImGui::EndTabBar();
|
||||
}
|
||||
|
||||
ImGui::Spacing();
|
||||
ImGui::Separator();
|
||||
ImGui::Spacing();
|
||||
|
||||
if (ImGui::Button("Apply", ImVec2(-1, 0))) {
|
||||
uiOpacity_ = static_cast<float>(pendingUiOpacity) / 100.0f;
|
||||
minimapRotate_ = pendingMinimapRotate;
|
||||
saveSettings();
|
||||
window->setVsync(pendingVsync);
|
||||
window->setFullscreen(pendingFullscreen);
|
||||
window->applyResolution(kResolutions[pendingResIndex][0], kResolutions[pendingResIndex][1]);
|
||||
if (renderer) {
|
||||
renderer->setShadowsEnabled(pendingShadows);
|
||||
if (auto* minimap = renderer->getMinimap()) {
|
||||
minimap->setRotateWithCamera(minimapRotate_);
|
||||
}
|
||||
|
||||
// Apply all audio volume settings
|
||||
// Helper lambda to apply audio settings
|
||||
auto applyAudioSettings = [&]() {
|
||||
if (!renderer) return;
|
||||
float masterScale = static_cast<float>(pendingMasterVolume) / 100.0f;
|
||||
if (auto* music = renderer->getMusicManager()) {
|
||||
music->setVolume(static_cast<int>(pendingMusicVolume * masterScale));
|
||||
|
|
@ -4309,13 +4210,173 @@ void GameScreen::renderSettingsWindow() {
|
|||
if (auto* activity = renderer->getActivitySoundManager()) {
|
||||
activity->setVolumeScale(pendingActivityVolume / 100.0f * masterScale);
|
||||
}
|
||||
saveSettings();
|
||||
};
|
||||
|
||||
ImGui::Text("Master Volume");
|
||||
if (ImGui::SliderInt("##MasterVolume", &pendingMasterVolume, 0, 100, "%d%%")) {
|
||||
applyAudioSettings();
|
||||
}
|
||||
ImGui::Separator();
|
||||
|
||||
ImGui::Text("Music");
|
||||
if (ImGui::SliderInt("##MusicVolume", &pendingMusicVolume, 0, 100, "%d%%")) {
|
||||
applyAudioSettings();
|
||||
}
|
||||
|
||||
ImGui::Spacing();
|
||||
ImGui::Text("Ambient Sounds");
|
||||
if (ImGui::SliderInt("##AmbientVolume", &pendingAmbientVolume, 0, 100, "%d%%")) {
|
||||
applyAudioSettings();
|
||||
}
|
||||
ImGui::TextWrapped("Weather, zones, cities, emitters");
|
||||
|
||||
ImGui::Spacing();
|
||||
ImGui::Text("UI Sounds");
|
||||
if (ImGui::SliderInt("##UiVolume", &pendingUiVolume, 0, 100, "%d%%")) {
|
||||
applyAudioSettings();
|
||||
}
|
||||
ImGui::TextWrapped("Buttons, loot, quest complete");
|
||||
|
||||
ImGui::Spacing();
|
||||
ImGui::Text("Combat Sounds");
|
||||
if (ImGui::SliderInt("##CombatVolume", &pendingCombatVolume, 0, 100, "%d%%")) {
|
||||
applyAudioSettings();
|
||||
}
|
||||
ImGui::TextWrapped("Weapon swings, impacts, grunts");
|
||||
|
||||
ImGui::Spacing();
|
||||
ImGui::Text("Spell Sounds");
|
||||
if (ImGui::SliderInt("##SpellVolume", &pendingSpellVolume, 0, 100, "%d%%")) {
|
||||
applyAudioSettings();
|
||||
}
|
||||
ImGui::TextWrapped("Magic casting and impacts");
|
||||
|
||||
ImGui::Spacing();
|
||||
ImGui::Text("Movement Sounds");
|
||||
if (ImGui::SliderInt("##MovementVolume", &pendingMovementVolume, 0, 100, "%d%%")) {
|
||||
applyAudioSettings();
|
||||
}
|
||||
ImGui::TextWrapped("Water splashes, jump/land");
|
||||
|
||||
ImGui::Spacing();
|
||||
ImGui::Text("Footsteps");
|
||||
if (ImGui::SliderInt("##FootstepVolume", &pendingFootstepVolume, 0, 100, "%d%%")) {
|
||||
applyAudioSettings();
|
||||
}
|
||||
|
||||
ImGui::Spacing();
|
||||
ImGui::Text("NPC Voices");
|
||||
if (ImGui::SliderInt("##NpcVoiceVolume", &pendingNpcVoiceVolume, 0, 100, "%d%%")) {
|
||||
applyAudioSettings();
|
||||
}
|
||||
|
||||
ImGui::Spacing();
|
||||
ImGui::Text("Mount Sounds");
|
||||
if (ImGui::SliderInt("##MountVolume", &pendingMountVolume, 0, 100, "%d%%")) {
|
||||
applyAudioSettings();
|
||||
}
|
||||
|
||||
ImGui::Spacing();
|
||||
ImGui::Text("Activity Sounds");
|
||||
if (ImGui::SliderInt("##ActivityVolume", &pendingActivityVolume, 0, 100, "%d%%")) {
|
||||
applyAudioSettings();
|
||||
}
|
||||
ImGui::TextWrapped("Swimming, eating, drinking");
|
||||
|
||||
ImGui::EndChild();
|
||||
|
||||
if (ImGui::Button("Restore Audio Defaults", ImVec2(-1, 0))) {
|
||||
pendingMasterVolume = 100;
|
||||
pendingMusicVolume = kDefaultMusicVolume;
|
||||
pendingAmbientVolume = 100;
|
||||
pendingUiVolume = 100;
|
||||
pendingCombatVolume = 100;
|
||||
pendingSpellVolume = 100;
|
||||
pendingMovementVolume = 100;
|
||||
pendingFootstepVolume = 100;
|
||||
pendingNpcVoiceVolume = 100;
|
||||
pendingMountVolume = 100;
|
||||
pendingActivityVolume = 100;
|
||||
applyAudioSettings();
|
||||
}
|
||||
|
||||
ImGui::EndTabItem();
|
||||
}
|
||||
|
||||
// ============================================================
|
||||
// GAMEPLAY TAB
|
||||
// ============================================================
|
||||
if (ImGui::BeginTabItem("Gameplay")) {
|
||||
ImGui::Spacing();
|
||||
|
||||
ImGui::Text("Controls");
|
||||
ImGui::Separator();
|
||||
if (ImGui::SliderFloat("Mouse Sensitivity", &pendingMouseSensitivity, 0.05f, 1.0f, "%.2f")) {
|
||||
if (renderer) {
|
||||
if (auto* cameraController = renderer->getCameraController()) {
|
||||
cameraController->setMouseSensitivity(pendingMouseSensitivity);
|
||||
}
|
||||
}
|
||||
saveSettings();
|
||||
}
|
||||
if (ImGui::Checkbox("Invert Mouse", &pendingInvertMouse)) {
|
||||
if (renderer) {
|
||||
if (auto* cameraController = renderer->getCameraController()) {
|
||||
cameraController->setInvertMouse(pendingInvertMouse);
|
||||
}
|
||||
}
|
||||
saveSettings();
|
||||
}
|
||||
|
||||
ImGui::Spacing();
|
||||
ImGui::Spacing();
|
||||
|
||||
ImGui::Text("Interface");
|
||||
ImGui::Separator();
|
||||
if (ImGui::SliderInt("UI Opacity", &pendingUiOpacity, 20, 100, "%d%%")) {
|
||||
uiOpacity_ = static_cast<float>(pendingUiOpacity) / 100.0f;
|
||||
saveSettings();
|
||||
}
|
||||
if (ImGui::Checkbox("Rotate Minimap", &pendingMinimapRotate)) {
|
||||
minimapRotate_ = pendingMinimapRotate;
|
||||
if (renderer) {
|
||||
if (auto* minimap = renderer->getMinimap()) {
|
||||
minimap->setRotateWithCamera(minimapRotate_);
|
||||
}
|
||||
}
|
||||
saveSettings();
|
||||
}
|
||||
|
||||
ImGui::Spacing();
|
||||
ImGui::Separator();
|
||||
ImGui::Spacing();
|
||||
|
||||
if (ImGui::Button("Restore Gameplay Defaults", ImVec2(-1, 0))) {
|
||||
pendingMouseSensitivity = kDefaultMouseSensitivity;
|
||||
pendingInvertMouse = kDefaultInvertMouse;
|
||||
pendingUiOpacity = 65;
|
||||
pendingMinimapRotate = false;
|
||||
uiOpacity_ = 0.65f;
|
||||
minimapRotate_ = false;
|
||||
if (renderer) {
|
||||
if (auto* cameraController = renderer->getCameraController()) {
|
||||
cameraController->setMouseSensitivity(pendingMouseSensitivity);
|
||||
cameraController->setInvertMouse(pendingInvertMouse);
|
||||
}
|
||||
if (auto* minimap = renderer->getMinimap()) {
|
||||
minimap->setRotateWithCamera(minimapRotate_);
|
||||
}
|
||||
}
|
||||
saveSettings();
|
||||
}
|
||||
|
||||
ImGui::EndTabItem();
|
||||
}
|
||||
|
||||
ImGui::EndTabBar();
|
||||
}
|
||||
|
||||
ImGui::Spacing();
|
||||
ImGui::PushStyleVar(ImGuiStyleVar_FramePadding, ImVec2(10.0f, 10.0f));
|
||||
if (ImGui::Button("Back to Game", ImVec2(-1, 0))) {
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue