diff --git a/rts/Sim/Weapons/WeaponDef.cpp b/rts/Sim/Weapons/WeaponDef.cpp index 9dad7e8c611..1c4515f0a84 100644 --- a/rts/Sim/Weapons/WeaponDef.cpp +++ b/rts/Sim/Weapons/WeaponDef.cpp @@ -574,27 +574,61 @@ void WeaponDef::ParseWeaponSounds(const LuaTable& wdTable) { +/** + * @brief Loads sound entries for a given sound key from a weapon Lua table into a GuiSoundSet. + * + * Reads a single filename or an indexed subtable under `soundKey` and appends each resolved entry + * to `soundData`. Volume is taken from `Volume` or falls back to `soundHitVolume` (default 1.0). + * For hit-sound keys `soundHitDry` and `soundHitWet`, a fallback to the `soundHit` key is attempted + * when no direct entry for the specific key exists. + * + * @param wdTable Lua table containing weapon definition sound fields. + * @param soundKey Key to look up (e.g., "soundStart", "soundHitDry", "soundHitWet"). + * @param[out] soundData Target sound set to which resolved filenames and volumes are added. + */ void WeaponDef::LoadSound( const LuaTable& wdTable, const std::string& soundKey, GuiSoundSet& soundData ) { RECOIL_DETAILED_TRACY_ZONE; - switch (hashString(soundKey.c_str())) { - case hashString("soundStart"): { - CommonDefHandler::AddSoundSetData(soundData, wdTable.GetString(soundKey, ""), wdTable.GetFloat(soundKey + "Volume", 1.0f)); - } break; - - case hashString("soundHitDry"): { - CommonDefHandler::AddSoundSetData(soundData, wdTable.GetString(soundKey, wdTable.GetString("soundHit", "")), wdTable.GetFloat(soundKey + "Volume", wdTable.GetFloat("soundHitVolume", 1.0f))); - } break; - case hashString("soundHitWet"): { - CommonDefHandler::AddSoundSetData(soundData, wdTable.GetString(soundKey, wdTable.GetString("soundHit", "")), wdTable.GetFloat(soundKey + "Volume", wdTable.GetFloat("soundHitVolume", 1.0f))); - } break; - - default: { - } break; - } + + std::string hitFallbackKey = "soundHit"; + + uint32_t hash = hashString(soundKey.c_str()); + bool useHitFallback = hash == hashString("soundHitWet") || hash == hashString("soundHitDry"); + + float volume = wdTable.GetFloat(soundKey + "Volume", wdTable.GetFloat("soundHitVolume", 1.0f)); + + std::string fileName = wdTable.GetString(soundKey, ""); + if (!fileName.empty()) { + CommonDefHandler::AddSoundSetData(soundData, fileName, volume); + return; + } + + LuaTable tbl = wdTable.SubTable(soundKey); + + if (!tbl.IsValid() && useHitFallback) + tbl = wdTable.SubTable(hitFallbackKey); + + if (tbl.IsValid()) { + for (int i = 1; true; i++) { + fileName = tbl.GetString(i, ""); + + if (fileName.empty()) + break; + + CommonDefHandler::AddSoundSetData(soundData, fileName, volume); + } + return; + } + + if (useHitFallback) { + fileName = wdTable.GetString(hitFallbackKey, ""); + if (!fileName.empty()) { + CommonDefHandler::AddSoundSetData(soundData, fileName, volume); + } + } } @@ -633,4 +667,4 @@ void WeaponDef::PreloadModel() const RECOIL_DETAILED_TRACY_ZONE; //not very sweet, but still better than replacing "const WeaponDef" _everywhere_ const_cast(this)->PreloadModel(); -} +} \ No newline at end of file