mirror of
https://github.com/Kelsidavis/WoWee.git
synced 2026-05-09 02:23:52 +00:00
chore(refactor): god-object decomposition and mega-file splits
Split all mega-files by single-responsibility concern and partially extracting AudioCoordinator and OverlaySystem from the Renderer facade. No behavioral changes. Splits: - game_handler.cpp (5,247 LOC) → core + callbacks + packets (3 files) - world_packets.cpp (4,453 LOC) → economy/entity/social/world (4 files) - game_screen.cpp (5,786 LOC) → core + frames + hud + minimap (4 files) - m2_renderer.cpp (3,343 LOC) → core + instance + particles + render (4 files) - chat_panel.cpp (3,140 LOC) → core + commands + utils (3 files) - entity_spawner.cpp (2,750 LOC) → core + player + processing (3 files) Extractions: - AudioCoordinator: include/audio/ + src/audio/ (owned by Renderer) - OverlaySystem: include/rendering/ + src/rendering/overlay_system.* CMakeLists.txt: registered all 17 new translation units. Related handler/callback files: minor include fixups post-split.
This commit is contained in:
parent
6dcc06697b
commit
34c0e3ca28
49 changed files with 29113 additions and 28109 deletions
File diff suppressed because it is too large
Load diff
2803
src/ui/chat_panel_commands.cpp
Normal file
2803
src/ui/chat_panel_commands.cpp
Normal file
File diff suppressed because it is too large
Load diff
480
src/ui/chat_panel_utils.cpp
Normal file
480
src/ui/chat_panel_utils.cpp
Normal file
|
|
@ -0,0 +1,480 @@
|
|||
#include "ui/chat_panel.hpp"
|
||||
#include "ui/ui_colors.hpp"
|
||||
#include "rendering/vk_context.hpp"
|
||||
#include "core/application.hpp"
|
||||
#include "rendering/renderer.hpp"
|
||||
#include "rendering/camera.hpp"
|
||||
#include "rendering/camera_controller.hpp"
|
||||
#include "audio/audio_coordinator.hpp"
|
||||
#include "audio/ui_sound_manager.hpp"
|
||||
#include "pipeline/asset_manager.hpp"
|
||||
#include "pipeline/dbc_loader.hpp"
|
||||
#include "pipeline/dbc_layout.hpp"
|
||||
#include "game/expansion_profile.hpp"
|
||||
#include "game/character.hpp"
|
||||
#include "core/logger.hpp"
|
||||
#include <imgui.h>
|
||||
#include <imgui_internal.h>
|
||||
#include "core/coordinates.hpp"
|
||||
#include <algorithm>
|
||||
#include <cmath>
|
||||
#include <sstream>
|
||||
#include <cstring>
|
||||
#include <unordered_map>
|
||||
|
||||
namespace {
|
||||
using namespace wowee::ui::colors;
|
||||
constexpr auto& kColorRed = kRed;
|
||||
constexpr auto& kColorBrightGreen= kBrightGreen;
|
||||
constexpr auto& kColorYellow = kYellow;
|
||||
} // namespace
|
||||
|
||||
namespace wowee { namespace ui {
|
||||
|
||||
const char* ChatPanel::getChatTypeName(game::ChatType type) const {
|
||||
switch (type) {
|
||||
case game::ChatType::SAY: return "Say";
|
||||
case game::ChatType::YELL: return "Yell";
|
||||
case game::ChatType::EMOTE: return "Emote";
|
||||
case game::ChatType::TEXT_EMOTE: return "Emote";
|
||||
case game::ChatType::PARTY: return "Party";
|
||||
case game::ChatType::GUILD: return "Guild";
|
||||
case game::ChatType::OFFICER: return "Officer";
|
||||
case game::ChatType::RAID: return "Raid";
|
||||
case game::ChatType::RAID_LEADER: return "Raid Leader";
|
||||
case game::ChatType::RAID_WARNING: return "Raid Warning";
|
||||
case game::ChatType::BATTLEGROUND: return "Battleground";
|
||||
case game::ChatType::BATTLEGROUND_LEADER: return "Battleground Leader";
|
||||
case game::ChatType::WHISPER: return "Whisper";
|
||||
case game::ChatType::WHISPER_INFORM: return "To";
|
||||
case game::ChatType::SYSTEM: return "System";
|
||||
case game::ChatType::MONSTER_SAY: return "Say";
|
||||
case game::ChatType::MONSTER_YELL: return "Yell";
|
||||
case game::ChatType::MONSTER_EMOTE: return "Emote";
|
||||
case game::ChatType::CHANNEL: return "Channel";
|
||||
case game::ChatType::ACHIEVEMENT: return "Achievement";
|
||||
case game::ChatType::DND: return "DND";
|
||||
case game::ChatType::AFK: return "AFK";
|
||||
case game::ChatType::BG_SYSTEM_NEUTRAL:
|
||||
case game::ChatType::BG_SYSTEM_ALLIANCE:
|
||||
case game::ChatType::BG_SYSTEM_HORDE: return "System";
|
||||
default: return "Unknown";
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
ImVec4 ChatPanel::getChatTypeColor(game::ChatType type) const {
|
||||
switch (type) {
|
||||
case game::ChatType::SAY:
|
||||
return ui::colors::kWhite; // White
|
||||
case game::ChatType::YELL:
|
||||
return kColorRed; // Red
|
||||
case game::ChatType::EMOTE:
|
||||
return ImVec4(1.0f, 0.7f, 0.3f, 1.0f); // Orange
|
||||
case game::ChatType::TEXT_EMOTE:
|
||||
return ImVec4(1.0f, 0.7f, 0.3f, 1.0f); // Orange
|
||||
case game::ChatType::PARTY:
|
||||
return ImVec4(0.5f, 0.5f, 1.0f, 1.0f); // Light blue
|
||||
case game::ChatType::GUILD:
|
||||
return kColorBrightGreen; // Green
|
||||
case game::ChatType::OFFICER:
|
||||
return ImVec4(0.3f, 0.8f, 0.3f, 1.0f); // Dark green
|
||||
case game::ChatType::RAID:
|
||||
return ImVec4(1.0f, 0.5f, 0.0f, 1.0f); // Orange
|
||||
case game::ChatType::RAID_LEADER:
|
||||
return ImVec4(1.0f, 0.4f, 0.0f, 1.0f); // Darker orange
|
||||
case game::ChatType::RAID_WARNING:
|
||||
return ImVec4(1.0f, 0.0f, 0.0f, 1.0f); // Red
|
||||
case game::ChatType::BATTLEGROUND:
|
||||
return ImVec4(1.0f, 0.6f, 0.0f, 1.0f); // Orange-gold
|
||||
case game::ChatType::BATTLEGROUND_LEADER:
|
||||
return ImVec4(1.0f, 0.5f, 0.0f, 1.0f); // Orange
|
||||
case game::ChatType::WHISPER:
|
||||
return ImVec4(1.0f, 0.5f, 1.0f, 1.0f); // Pink
|
||||
case game::ChatType::WHISPER_INFORM:
|
||||
return ImVec4(1.0f, 0.5f, 1.0f, 1.0f); // Pink
|
||||
case game::ChatType::SYSTEM:
|
||||
return kColorYellow; // Yellow
|
||||
case game::ChatType::MONSTER_SAY:
|
||||
return ui::colors::kWhite; // White (same as SAY)
|
||||
case game::ChatType::MONSTER_YELL:
|
||||
return kColorRed; // Red (same as YELL)
|
||||
case game::ChatType::MONSTER_EMOTE:
|
||||
return ImVec4(1.0f, 0.7f, 0.3f, 1.0f); // Orange (same as EMOTE)
|
||||
case game::ChatType::CHANNEL:
|
||||
return ImVec4(1.0f, 0.7f, 0.7f, 1.0f); // Light pink
|
||||
case game::ChatType::ACHIEVEMENT:
|
||||
return ImVec4(1.0f, 1.0f, 0.0f, 1.0f); // Bright yellow
|
||||
case game::ChatType::GUILD_ACHIEVEMENT:
|
||||
return colors::kWarmGold; // Gold
|
||||
case game::ChatType::SKILL:
|
||||
return colors::kCyan; // Cyan
|
||||
case game::ChatType::LOOT:
|
||||
return ImVec4(0.8f, 0.5f, 1.0f, 1.0f); // Light purple
|
||||
case game::ChatType::MONSTER_WHISPER:
|
||||
case game::ChatType::RAID_BOSS_WHISPER:
|
||||
return ImVec4(1.0f, 0.5f, 1.0f, 1.0f); // Pink (same as WHISPER)
|
||||
case game::ChatType::RAID_BOSS_EMOTE:
|
||||
return ImVec4(1.0f, 0.7f, 0.3f, 1.0f); // Orange (same as EMOTE)
|
||||
case game::ChatType::MONSTER_PARTY:
|
||||
return ImVec4(0.5f, 0.5f, 1.0f, 1.0f); // Light blue (same as PARTY)
|
||||
case game::ChatType::BG_SYSTEM_NEUTRAL:
|
||||
return colors::kWarmGold; // Gold
|
||||
case game::ChatType::BG_SYSTEM_ALLIANCE:
|
||||
return ImVec4(0.3f, 0.6f, 1.0f, 1.0f); // Blue
|
||||
case game::ChatType::BG_SYSTEM_HORDE:
|
||||
return kColorRed; // Red
|
||||
case game::ChatType::AFK:
|
||||
case game::ChatType::DND:
|
||||
return ImVec4(0.85f, 0.85f, 0.85f, 0.8f); // Light gray
|
||||
default:
|
||||
return ui::colors::kLightGray; // Gray
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
std::string ChatPanel::replaceGenderPlaceholders(const std::string& text, game::GameHandler& gameHandler) {
|
||||
// Get player gender, pronouns, and name
|
||||
game::Gender gender = game::Gender::NONBINARY;
|
||||
std::string playerName = "Adventurer";
|
||||
const auto* character = gameHandler.getActiveCharacter();
|
||||
if (character) {
|
||||
gender = character->gender;
|
||||
if (!character->name.empty()) {
|
||||
playerName = character->name;
|
||||
}
|
||||
}
|
||||
game::Pronouns pronouns = game::Pronouns::forGender(gender);
|
||||
|
||||
std::string result = text;
|
||||
|
||||
// Helper to trim whitespace
|
||||
auto trim = [](std::string& s) {
|
||||
const char* ws = " \t\n\r";
|
||||
size_t start = s.find_first_not_of(ws);
|
||||
if (start == std::string::npos) { s.clear(); return; }
|
||||
size_t end = s.find_last_not_of(ws);
|
||||
s = s.substr(start, end - start + 1);
|
||||
};
|
||||
|
||||
// Replace $g/$G placeholders first.
|
||||
size_t pos = 0;
|
||||
while ((pos = result.find('$', pos)) != std::string::npos) {
|
||||
if (pos + 1 >= result.length()) break;
|
||||
char marker = result[pos + 1];
|
||||
if (marker != 'g' && marker != 'G') { pos++; continue; }
|
||||
|
||||
size_t endPos = result.find(';', pos);
|
||||
if (endPos == std::string::npos) { pos += 2; continue; }
|
||||
|
||||
std::string placeholder = result.substr(pos + 2, endPos - pos - 2);
|
||||
|
||||
// Split by colons
|
||||
std::vector<std::string> parts;
|
||||
size_t start = 0;
|
||||
size_t colonPos;
|
||||
while ((colonPos = placeholder.find(':', start)) != std::string::npos) {
|
||||
std::string part = placeholder.substr(start, colonPos - start);
|
||||
trim(part);
|
||||
parts.push_back(part);
|
||||
start = colonPos + 1;
|
||||
}
|
||||
// Add the last part
|
||||
std::string lastPart = placeholder.substr(start);
|
||||
trim(lastPart);
|
||||
parts.push_back(lastPart);
|
||||
|
||||
// Select appropriate text based on gender
|
||||
std::string replacement;
|
||||
if (parts.size() >= 3) {
|
||||
// Three options: male, female, nonbinary
|
||||
switch (gender) {
|
||||
case game::Gender::MALE:
|
||||
replacement = parts[0];
|
||||
break;
|
||||
case game::Gender::FEMALE:
|
||||
replacement = parts[1];
|
||||
break;
|
||||
case game::Gender::NONBINARY:
|
||||
replacement = parts[2];
|
||||
break;
|
||||
}
|
||||
} else if (parts.size() >= 2) {
|
||||
// Two options: male, female (use first for nonbinary)
|
||||
switch (gender) {
|
||||
case game::Gender::MALE:
|
||||
replacement = parts[0];
|
||||
break;
|
||||
case game::Gender::FEMALE:
|
||||
replacement = parts[1];
|
||||
break;
|
||||
case game::Gender::NONBINARY:
|
||||
// Default to gender-neutral: use the shorter/simpler option
|
||||
replacement = parts[0].length() <= parts[1].length() ? parts[0] : parts[1];
|
||||
break;
|
||||
}
|
||||
} else {
|
||||
// Malformed placeholder
|
||||
pos = endPos + 1;
|
||||
continue;
|
||||
}
|
||||
|
||||
result.replace(pos, endPos - pos + 1, replacement);
|
||||
pos += replacement.length();
|
||||
}
|
||||
|
||||
// Resolve class and race names for $C and $R placeholders
|
||||
std::string className = "Adventurer";
|
||||
std::string raceName = "Unknown";
|
||||
if (character) {
|
||||
className = game::getClassName(character->characterClass);
|
||||
raceName = game::getRaceName(character->race);
|
||||
}
|
||||
|
||||
// Replace simple placeholders.
|
||||
// $n/$N = player name, $c/$C = class name, $r/$R = race name
|
||||
// $p = subject pronoun (he/she/they)
|
||||
// $o = object pronoun (him/her/them)
|
||||
// $s = possessive adjective (his/her/their)
|
||||
// $S = possessive pronoun (his/hers/theirs)
|
||||
// $b/$B = line break
|
||||
pos = 0;
|
||||
while ((pos = result.find('$', pos)) != std::string::npos) {
|
||||
if (pos + 1 >= result.length()) break;
|
||||
|
||||
char code = result[pos + 1];
|
||||
std::string replacement;
|
||||
switch (code) {
|
||||
case 'n': case 'N': replacement = playerName; break;
|
||||
case 'c': case 'C': replacement = className; break;
|
||||
case 'r': case 'R': replacement = raceName; break;
|
||||
case 'p': replacement = pronouns.subject; break;
|
||||
case 'o': replacement = pronouns.object; break;
|
||||
case 's': replacement = pronouns.possessive; break;
|
||||
case 'S': replacement = pronouns.possessiveP; break;
|
||||
case 'b': case 'B': replacement = "\n"; break;
|
||||
case 'g': case 'G': pos++; continue;
|
||||
default: pos++; continue;
|
||||
}
|
||||
|
||||
result.replace(pos, 2, replacement);
|
||||
pos += replacement.length();
|
||||
}
|
||||
|
||||
// WoW markup linebreak token.
|
||||
pos = 0;
|
||||
while ((pos = result.find("|n", pos)) != std::string::npos) {
|
||||
result.replace(pos, 2, "\n");
|
||||
pos += 1;
|
||||
}
|
||||
pos = 0;
|
||||
while ((pos = result.find("|N", pos)) != std::string::npos) {
|
||||
result.replace(pos, 2, "\n");
|
||||
pos += 1;
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
void ChatPanel::renderBubbles(game::GameHandler& gameHandler) {
|
||||
if (chatBubbles_.empty()) return;
|
||||
|
||||
auto* renderer = services_.renderer;
|
||||
auto* camera = renderer ? renderer->getCamera() : nullptr;
|
||||
if (!camera) return;
|
||||
|
||||
auto* window = services_.window;
|
||||
float screenW = window ? static_cast<float>(window->getWidth()) : 1280.0f;
|
||||
float screenH = window ? static_cast<float>(window->getHeight()) : 720.0f;
|
||||
|
||||
// Get delta time from ImGui
|
||||
float dt = ImGui::GetIO().DeltaTime;
|
||||
|
||||
glm::mat4 viewProj = camera->getProjectionMatrix() * camera->getViewMatrix();
|
||||
|
||||
// Update and render bubbles
|
||||
for (int i = static_cast<int>(chatBubbles_.size()) - 1; i >= 0; --i) {
|
||||
auto& bubble = chatBubbles_[i];
|
||||
bubble.timeRemaining -= dt;
|
||||
if (bubble.timeRemaining <= 0.0f) {
|
||||
chatBubbles_.erase(chatBubbles_.begin() + i);
|
||||
continue;
|
||||
}
|
||||
|
||||
// Get entity position
|
||||
auto entity = gameHandler.getEntityManager().getEntity(bubble.senderGuid);
|
||||
if (!entity) continue;
|
||||
|
||||
// Convert canonical → render coordinates, offset up by 2.5 units for bubble above head
|
||||
glm::vec3 canonical(entity->getX(), entity->getY(), entity->getZ() + 2.5f);
|
||||
glm::vec3 renderPos = core::coords::canonicalToRender(canonical);
|
||||
|
||||
// Project to screen
|
||||
glm::vec4 clipPos = viewProj * glm::vec4(renderPos, 1.0f);
|
||||
if (clipPos.w <= 0.0f) continue; // Behind camera
|
||||
|
||||
glm::vec2 ndc(clipPos.x / clipPos.w, clipPos.y / clipPos.w);
|
||||
float screenX = (ndc.x * 0.5f + 0.5f) * screenW;
|
||||
// Camera bakes the Vulkan Y-flip into the projection matrix:
|
||||
// NDC y=-1 is top, y=1 is bottom — same convention as nameplate/minimap projection.
|
||||
float screenY = (ndc.y * 0.5f + 0.5f) * screenH;
|
||||
|
||||
// Skip if off-screen
|
||||
if (screenX < -200.0f || screenX > screenW + 200.0f ||
|
||||
screenY < -100.0f || screenY > screenH + 100.0f) continue;
|
||||
|
||||
// Fade alpha over last 2 seconds
|
||||
float alpha = 1.0f;
|
||||
if (bubble.timeRemaining < 2.0f) {
|
||||
alpha = bubble.timeRemaining / 2.0f;
|
||||
}
|
||||
|
||||
// Draw bubble window
|
||||
std::string winId = "##ChatBubble" + std::to_string(bubble.senderGuid);
|
||||
ImGui::SetNextWindowPos(ImVec2(screenX, screenY), ImGuiCond_Always, ImVec2(0.5f, 1.0f));
|
||||
ImGui::SetNextWindowBgAlpha(0.7f * alpha);
|
||||
ImGuiWindowFlags flags = ImGuiWindowFlags_NoTitleBar | ImGuiWindowFlags_NoResize |
|
||||
ImGuiWindowFlags_NoMove | ImGuiWindowFlags_NoScrollbar |
|
||||
ImGuiWindowFlags_AlwaysAutoResize | ImGuiWindowFlags_NoInputs |
|
||||
ImGuiWindowFlags_NoFocusOnAppearing | ImGuiWindowFlags_NoNav;
|
||||
|
||||
ImGui::PushStyleVar(ImGuiStyleVar_WindowRounding, 8.0f);
|
||||
ImGui::PushStyleVar(ImGuiStyleVar_WindowPadding, ImVec2(8, 4));
|
||||
|
||||
ImGui::Begin(winId.c_str(), nullptr, flags);
|
||||
|
||||
ImVec4 textColor = bubble.isYell
|
||||
? ImVec4(1.0f, 0.2f, 0.2f, alpha)
|
||||
: ImVec4(1.0f, 1.0f, 1.0f, alpha);
|
||||
|
||||
ImGui::PushStyleColor(ImGuiCol_Text, textColor);
|
||||
ImGui::PushTextWrapPos(200.0f);
|
||||
ImGui::TextWrapped("%s", bubble.message.c_str());
|
||||
ImGui::PopTextWrapPos();
|
||||
ImGui::PopStyleColor();
|
||||
|
||||
ImGui::End();
|
||||
ImGui::PopStyleVar(2);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// ---- Public interface methods ----
|
||||
|
||||
void ChatPanel::setupCallbacks(game::GameHandler& gameHandler) {
|
||||
if (!chatBubbleCallbackSet_) {
|
||||
gameHandler.setChatBubbleCallback([this](uint64_t guid, const std::string& msg, bool isYell) {
|
||||
float duration = 8.0f + static_cast<float>(msg.size()) * 0.06f;
|
||||
if (isYell) duration += 2.0f;
|
||||
if (duration > 15.0f) duration = 15.0f;
|
||||
|
||||
// Replace existing bubble for same sender
|
||||
for (auto& b : chatBubbles_) {
|
||||
if (b.senderGuid == guid) {
|
||||
b.message = msg;
|
||||
b.timeRemaining = duration;
|
||||
b.totalDuration = duration;
|
||||
b.isYell = isYell;
|
||||
return;
|
||||
}
|
||||
}
|
||||
// Evict oldest if too many
|
||||
if (chatBubbles_.size() >= 10) {
|
||||
chatBubbles_.erase(chatBubbles_.begin());
|
||||
}
|
||||
chatBubbles_.push_back({guid, msg, duration, duration, isYell});
|
||||
});
|
||||
chatBubbleCallbackSet_ = true;
|
||||
}
|
||||
}
|
||||
|
||||
void ChatPanel::insertChatLink(const std::string& link) {
|
||||
if (link.empty()) return;
|
||||
size_t curLen = strlen(chatInputBuffer_);
|
||||
if (curLen + link.size() + 1 < sizeof(chatInputBuffer_)) {
|
||||
strncat(chatInputBuffer_, link.c_str(), sizeof(chatInputBuffer_) - curLen - 1);
|
||||
chatInputMoveCursorToEnd_ = true;
|
||||
refocusChatInput_ = true;
|
||||
}
|
||||
}
|
||||
|
||||
void ChatPanel::activateSlashInput() {
|
||||
refocusChatInput_ = true;
|
||||
chatInputBuffer_[0] = '/';
|
||||
chatInputBuffer_[1] = '\0';
|
||||
chatInputMoveCursorToEnd_ = true;
|
||||
}
|
||||
|
||||
void ChatPanel::activateInput() {
|
||||
refocusChatInput_ = true;
|
||||
}
|
||||
|
||||
void ChatPanel::setWhisperTarget(const std::string& name) {
|
||||
selectedChatType_ = 4; // WHISPER
|
||||
strncpy(whisperTargetBuffer_, name.c_str(), sizeof(whisperTargetBuffer_) - 1);
|
||||
whisperTargetBuffer_[sizeof(whisperTargetBuffer_) - 1] = '\0';
|
||||
refocusChatInput_ = true;
|
||||
}
|
||||
|
||||
ChatPanel::SlashCommands ChatPanel::consumeSlashCommands() {
|
||||
SlashCommands result = slashCmds_;
|
||||
slashCmds_ = {};
|
||||
return result;
|
||||
}
|
||||
|
||||
void ChatPanel::renderSettingsTab(std::function<void()> saveSettingsFn) {
|
||||
ImGui::Spacing();
|
||||
|
||||
ImGui::Text("Appearance");
|
||||
ImGui::Separator();
|
||||
|
||||
if (ImGui::Checkbox("Show Timestamps", &chatShowTimestamps)) {
|
||||
saveSettingsFn();
|
||||
}
|
||||
ImGui::SetItemTooltip("Show [HH:MM] before each chat message");
|
||||
|
||||
const char* fontSizes[] = { "Small", "Medium", "Large" };
|
||||
if (ImGui::Combo("Chat Font Size", &chatFontSize, fontSizes, 3)) {
|
||||
saveSettingsFn();
|
||||
}
|
||||
|
||||
ImGui::Spacing();
|
||||
ImGui::Spacing();
|
||||
ImGui::Text("Auto-Join Channels");
|
||||
ImGui::Separator();
|
||||
|
||||
if (ImGui::Checkbox("General", &chatAutoJoinGeneral)) saveSettingsFn();
|
||||
if (ImGui::Checkbox("Trade", &chatAutoJoinTrade)) saveSettingsFn();
|
||||
if (ImGui::Checkbox("LocalDefense", &chatAutoJoinLocalDefense)) saveSettingsFn();
|
||||
if (ImGui::Checkbox("LookingForGroup", &chatAutoJoinLFG)) saveSettingsFn();
|
||||
if (ImGui::Checkbox("Local", &chatAutoJoinLocal)) saveSettingsFn();
|
||||
|
||||
ImGui::Spacing();
|
||||
ImGui::Spacing();
|
||||
ImGui::Text("Joined Channels");
|
||||
ImGui::Separator();
|
||||
|
||||
ImGui::TextDisabled("Use /join and /leave commands in chat to manage channels.");
|
||||
|
||||
ImGui::Spacing();
|
||||
ImGui::Separator();
|
||||
ImGui::Spacing();
|
||||
|
||||
if (ImGui::Button("Restore Chat Defaults", ImVec2(-1, 0))) {
|
||||
restoreDefaults();
|
||||
saveSettingsFn();
|
||||
}
|
||||
}
|
||||
|
||||
void ChatPanel::restoreDefaults() {
|
||||
chatShowTimestamps = false;
|
||||
chatFontSize = 1;
|
||||
chatAutoJoinGeneral = true;
|
||||
chatAutoJoinTrade = true;
|
||||
chatAutoJoinLocalDefense = true;
|
||||
chatAutoJoinLFG = true;
|
||||
chatAutoJoinLocal = true;
|
||||
}
|
||||
|
||||
} // namespace ui
|
||||
} // namespace wowee
|
||||
File diff suppressed because it is too large
Load diff
2432
src/ui/game_screen_frames.cpp
Normal file
2432
src/ui/game_screen_frames.cpp
Normal file
File diff suppressed because it is too large
Load diff
1719
src/ui/game_screen_hud.cpp
Normal file
1719
src/ui/game_screen_hud.cpp
Normal file
File diff suppressed because it is too large
Load diff
1918
src/ui/game_screen_minimap.cpp
Normal file
1918
src/ui/game_screen_minimap.cpp
Normal file
File diff suppressed because it is too large
Load diff
|
|
@ -10,6 +10,7 @@
|
|||
#include "core/application.hpp"
|
||||
#include "core/logger.hpp"
|
||||
#include "rendering/renderer.hpp"
|
||||
#include "rendering/post_process_pipeline.hpp"
|
||||
#include "rendering/camera.hpp"
|
||||
#include "rendering/camera_controller.hpp"
|
||||
#include "rendering/minimap.hpp"
|
||||
|
|
@ -739,7 +740,7 @@ void SettingsPanel::renderSettingsWindow(InventoryScreen& inventoryScreen, ChatP
|
|||
}
|
||||
{
|
||||
const char* aaLabels[] = { "Off", "2x MSAA", "4x MSAA", "8x MSAA" };
|
||||
bool fsr2Active = renderer && renderer->isFSR2Enabled();
|
||||
bool fsr2Active = renderer && renderer->getPostProcessPipeline()->isFSR2Enabled();
|
||||
if (fsr2Active) {
|
||||
ImGui::BeginDisabled();
|
||||
int disabled = 0;
|
||||
|
|
@ -757,7 +758,7 @@ void SettingsPanel::renderSettingsWindow(InventoryScreen& inventoryScreen, ChatP
|
|||
// FXAA — post-process, combinable with MSAA or FSR3
|
||||
{
|
||||
if (ImGui::Checkbox("FXAA (post-process)", &pendingFXAA)) {
|
||||
if (renderer) renderer->setFXAAEnabled(pendingFXAA);
|
||||
if (renderer) renderer->getPostProcessPipeline()->setFXAAEnabled(pendingFXAA);
|
||||
updateGraphicsPresetFromCurrentSettings();
|
||||
saveCallback();
|
||||
}
|
||||
|
|
@ -786,24 +787,24 @@ void SettingsPanel::renderSettingsWindow(InventoryScreen& inventoryScreen, ChatP
|
|||
if (fsrMode > 0) {
|
||||
if (fsrMode == 2 && renderer) {
|
||||
ImGui::TextDisabled("FSR3 backend: %s",
|
||||
renderer->isAmdFsr2SdkAvailable() ? "AMD FidelityFX SDK" : "Internal fallback");
|
||||
if (renderer->isAmdFsr3FramegenSdkAvailable()) {
|
||||
renderer->getPostProcessPipeline()->isAmdFsr2SdkAvailable() ? "AMD FidelityFX SDK" : "Internal fallback");
|
||||
if (renderer->getPostProcessPipeline()->isAmdFsr3FramegenSdkAvailable()) {
|
||||
if (ImGui::Checkbox("AMD FSR3 Frame Generation (Experimental)", &pendingAMDFramegen)) {
|
||||
renderer->setAmdFsr3FramegenEnabled(pendingAMDFramegen);
|
||||
renderer->getPostProcessPipeline()->setAmdFsr3FramegenEnabled(pendingAMDFramegen);
|
||||
saveCallback();
|
||||
}
|
||||
const char* runtimeStatus = "Unavailable";
|
||||
if (renderer->isAmdFsr3FramegenRuntimeActive()) {
|
||||
if (renderer->getPostProcessPipeline()->isAmdFsr3FramegenRuntimeActive()) {
|
||||
runtimeStatus = "Active";
|
||||
} else if (renderer->isAmdFsr3FramegenRuntimeReady()) {
|
||||
} else if (renderer->getPostProcessPipeline()->isAmdFsr3FramegenRuntimeReady()) {
|
||||
runtimeStatus = "Ready";
|
||||
} else {
|
||||
runtimeStatus = "Unavailable";
|
||||
}
|
||||
ImGui::TextDisabled("Runtime: %s (%s)",
|
||||
runtimeStatus, renderer->getAmdFsr3FramegenRuntimePath());
|
||||
if (!renderer->isAmdFsr3FramegenRuntimeReady()) {
|
||||
const std::string& runtimeErr = renderer->getAmdFsr3FramegenRuntimeError();
|
||||
runtimeStatus, renderer->getPostProcessPipeline()->getAmdFsr3FramegenRuntimePath());
|
||||
if (!renderer->getPostProcessPipeline()->isAmdFsr3FramegenRuntimeReady()) {
|
||||
const std::string& runtimeErr = renderer->getPostProcessPipeline()->getAmdFsr3FramegenRuntimeError();
|
||||
if (!runtimeErr.empty()) {
|
||||
ImGui::TextDisabled("Reason: %s", runtimeErr.c_str());
|
||||
}
|
||||
|
|
@ -829,18 +830,18 @@ void SettingsPanel::renderSettingsWindow(InventoryScreen& inventoryScreen, ChatP
|
|||
}
|
||||
if (ImGui::Combo("FSR Quality", &fsrQualityDisplay, fsrQualityLabels, 4)) {
|
||||
pendingFSRQuality = displayToInternal[fsrQualityDisplay];
|
||||
if (renderer) renderer->setFSRQuality(fsrScaleFactors[pendingFSRQuality]);
|
||||
if (renderer) renderer->getPostProcessPipeline()->setFSRQuality(fsrScaleFactors[pendingFSRQuality]);
|
||||
saveCallback();
|
||||
}
|
||||
if (ImGui::SliderFloat("FSR Sharpness", &pendingFSRSharpness, 0.0f, 2.0f, "%.1f")) {
|
||||
if (renderer) renderer->setFSRSharpness(pendingFSRSharpness);
|
||||
if (renderer) renderer->getPostProcessPipeline()->setFSRSharpness(pendingFSRSharpness);
|
||||
saveCallback();
|
||||
}
|
||||
if (fsrMode == 2) {
|
||||
ImGui::SeparatorText("FSR3 Tuning");
|
||||
if (ImGui::SliderFloat("Jitter Sign", &pendingFSR2JitterSign, -2.0f, 2.0f, "%.2f")) {
|
||||
if (renderer) {
|
||||
renderer->setFSR2DebugTuning(
|
||||
renderer->getPostProcessPipeline()->setFSR2DebugTuning(
|
||||
pendingFSR2JitterSign,
|
||||
pendingFSR2MotionVecScaleX,
|
||||
pendingFSR2MotionVecScaleY);
|
||||
|
|
@ -927,7 +928,7 @@ void SettingsPanel::renderSettingsWindow(InventoryScreen& inventoryScreen, ChatP
|
|||
|
||||
ImGui::SetNextItemWidth(200.0f);
|
||||
if (ImGui::SliderInt("Brightness", &pendingBrightness, 0, 100, "%d%%")) {
|
||||
if (renderer) renderer->setBrightness(static_cast<float>(pendingBrightness) / 50.0f);
|
||||
if (renderer) renderer->getPostProcessPipeline()->setBrightness(static_cast<float>(pendingBrightness) / 50.0f);
|
||||
saveCallback();
|
||||
}
|
||||
|
||||
|
|
@ -951,7 +952,7 @@ void SettingsPanel::renderSettingsWindow(InventoryScreen& inventoryScreen, ChatP
|
|||
window->setFullscreen(pendingFullscreen);
|
||||
window->setVsync(pendingVsync);
|
||||
window->applyResolution(kResolutions[pendingResIndex][0], kResolutions[pendingResIndex][1]);
|
||||
if (renderer) renderer->setBrightness(1.0f);
|
||||
if (renderer) renderer->getPostProcessPipeline()->setBrightness(1.0f);
|
||||
pendingWaterRefraction = false;
|
||||
if (renderer) {
|
||||
renderer->setShadowsEnabled(pendingShadows);
|
||||
|
|
@ -1150,7 +1151,7 @@ void SettingsPanel::applyGraphicsPreset(GraphicsPreset preset) {
|
|||
renderer->setShadowsEnabled(true);
|
||||
renderer->setShadowDistance(500.0f);
|
||||
renderer->setMsaaSamples(VK_SAMPLE_COUNT_8_BIT);
|
||||
renderer->setFXAAEnabled(true);
|
||||
renderer->getPostProcessPipeline()->setFXAAEnabled(true);
|
||||
if (auto* wr = renderer->getWMORenderer()) {
|
||||
wr->setNormalMappingEnabled(true);
|
||||
wr->setNormalMapStrength(1.2f);
|
||||
|
|
|
|||
|
|
@ -2,6 +2,7 @@
|
|||
#include "game/game_handler.hpp"
|
||||
#include "core/application.hpp"
|
||||
#include "rendering/renderer.hpp"
|
||||
#include "rendering/animation_controller.hpp"
|
||||
#include "audio/audio_coordinator.hpp"
|
||||
#include "audio/ui_sound_manager.hpp"
|
||||
|
||||
|
|
@ -469,7 +470,7 @@ void ToastManager::triggerDing(uint32_t newLevel, uint32_t hpDelta, uint32_t man
|
|||
}
|
||||
}
|
||||
if (auto* renderer = services_.renderer) {
|
||||
renderer->playEmote("cheer");
|
||||
if (auto* ac = renderer->getAnimationController()) ac->playEmote("cheer");
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue