mirror of
https://github.com/OpenMW/openmw.git
synced 2026-05-06 07:56:40 -04:00
Merge branch 'noitsnotdehardcoded' into 'master'
Add magic effects to openmw.content Closes #8962 See merge request OpenMW/openmw!5248
This commit is contained in:
+1
-1
@@ -82,7 +82,7 @@ message(STATUS "Configuring OpenMW...")
|
||||
set(OPENMW_VERSION_MAJOR 0)
|
||||
set(OPENMW_VERSION_MINOR 51)
|
||||
set(OPENMW_VERSION_RELEASE 0)
|
||||
set(OPENMW_LUA_API_REVISION 123)
|
||||
set(OPENMW_LUA_API_REVISION 124)
|
||||
set(OPENMW_POSTPROCESSING_API_REVISION 5)
|
||||
|
||||
set(OPENMW_VERSION_COMMITHASH "")
|
||||
|
||||
@@ -297,6 +297,27 @@ namespace MWLua
|
||||
return LuaUtil::makeReadOnly(api);
|
||||
}
|
||||
|
||||
sol::table initMagicEffectBindings(sol::state_view& lua, MWWorld::Store<ESM::MagicEffect>& store)
|
||||
{
|
||||
addRecordStoreBindings<ESM::MagicEffect>(lua, &MWLua::tableToMagicEffect);
|
||||
addMutableMagicEffectType(lua);
|
||||
sol::table api(lua, sol::create);
|
||||
api["records"] = MutableStore<ESM::MagicEffect>{ store };
|
||||
// We can't get rid of the GMST table engine side because mwscript needs it, so intead of copying it into a
|
||||
// Lua file we've got this hidden function to generate it
|
||||
api["_getGMSTs"] = [](sol::this_state state) {
|
||||
sol::table gmsts(state, sol::create);
|
||||
for (int i = 0; i < ESM::MagicEffect::Length; ++i)
|
||||
{
|
||||
const ESM::RefId effect = ESM::MagicEffect::indexToRefId(i);
|
||||
const std::string_view gmst = ESM::MagicEffect::refIdToGmstString(effect);
|
||||
gmsts[effect] = gmst;
|
||||
}
|
||||
return gmsts;
|
||||
};
|
||||
return LuaUtil::makeReadOnly(api);
|
||||
}
|
||||
|
||||
sol::table initMiscBindings(sol::state_view& lua, MWWorld::Store<ESM::Miscellaneous>& store)
|
||||
{
|
||||
addRecordStoreBindings<ESM::Miscellaneous>(lua, &MWLua::tableToMisc);
|
||||
@@ -364,6 +385,7 @@ namespace MWLua
|
||||
api["gameSettings"] = initGameSettingBindings(lua, esmStore.getWritable<ESM::GameSetting>());
|
||||
api["globals"] = initGlobalVariableBindings(lua, esmStore.getWritable<ESM::Global>());
|
||||
api["ingredients"] = initIngredientBindings(lua, esmStore.getWritable<ESM::Ingredient>());
|
||||
api["magicEffects"] = initMagicEffectBindings(lua, esmStore.getWritable<ESM::MagicEffect>());
|
||||
api["miscs"] = initMiscBindings(lua, esmStore.getWritable<ESM::Miscellaneous>());
|
||||
api["potions"] = initPotionBindings(lua, esmStore.getWritable<ESM::Potion>());
|
||||
api["spells"] = initSpellBindings(lua, esmStore.getWritable<ESM::Spell>());
|
||||
|
||||
@@ -142,10 +142,6 @@ namespace MWLua
|
||||
|
||||
namespace sol
|
||||
{
|
||||
template <>
|
||||
struct is_automagical<ESM::MagicEffect> : std::false_type
|
||||
{
|
||||
};
|
||||
template <typename T>
|
||||
struct is_automagical<MWLua::ActorStore<T>> : std::false_type
|
||||
{
|
||||
@@ -266,63 +262,7 @@ namespace MWLua
|
||||
addEffectParamsBindings(state);
|
||||
|
||||
// MagicEffect record
|
||||
auto magicEffectT = state.new_usertype<ESM::MagicEffect>("ESM3_MagicEffect");
|
||||
|
||||
magicEffectT[sol::meta_function::to_string]
|
||||
= [](const ESM::MagicEffect& rec) { return std::format("ESM3_MagicEffect[{}]", rec.mId.toDebugString()); };
|
||||
magicEffectT["id"] = sol::readonly_property([](const ESM::MagicEffect& rec) -> ESM::RefId { return rec.mId; });
|
||||
magicEffectT["icon"] = sol::readonly_property([](const ESM::MagicEffect& rec) -> std::string {
|
||||
auto vfs = MWBase::Environment::get().getResourceSystem()->getVFS();
|
||||
return Misc::ResourceHelpers::correctIconPath(VFS::Path::toNormalized(rec.mIcon), *vfs);
|
||||
});
|
||||
magicEffectT["particle"]
|
||||
= sol::readonly_property([](const ESM::MagicEffect& rec) -> std::string_view { return rec.mParticle; });
|
||||
magicEffectT["continuousVfx"] = sol::readonly_property([](const ESM::MagicEffect& rec) -> bool {
|
||||
return (rec.mData.mFlags & ESM::MagicEffect::ContinuousVfx) != 0;
|
||||
});
|
||||
magicEffectT["areaSound"] = sol::readonly_property(
|
||||
[](const ESM::MagicEffect& rec) -> std::string { return rec.mAreaSound.serializeText(); });
|
||||
magicEffectT["boltSound"] = sol::readonly_property(
|
||||
[](const ESM::MagicEffect& rec) -> std::string { return rec.mBoltSound.serializeText(); });
|
||||
magicEffectT["castSound"] = sol::readonly_property(
|
||||
[](const ESM::MagicEffect& rec) -> std::string { return rec.mCastSound.serializeText(); });
|
||||
magicEffectT["hitSound"] = sol::readonly_property(
|
||||
[](const ESM::MagicEffect& rec) -> std::string { return rec.mHitSound.serializeText(); });
|
||||
magicEffectT["areaStatic"] = sol::readonly_property(
|
||||
[](const ESM::MagicEffect& rec) -> std::string { return rec.mArea.serializeText(); });
|
||||
magicEffectT["bolt"] = sol::readonly_property(
|
||||
[](const ESM::MagicEffect& rec) -> std::string { return rec.mBolt.serializeText(); });
|
||||
magicEffectT["castStatic"] = sol::readonly_property(
|
||||
[](const ESM::MagicEffect& rec) -> std::string { return rec.mCasting.serializeText(); });
|
||||
magicEffectT["hitStatic"] = sol::readonly_property(
|
||||
[](const ESM::MagicEffect& rec) -> std::string { return rec.mHit.serializeText(); });
|
||||
magicEffectT["name"]
|
||||
= sol::readonly_property([](const ESM::MagicEffect& rec) -> std::string_view { return rec.mName; });
|
||||
magicEffectT["school"] = sol::readonly_property(
|
||||
[](const ESM::MagicEffect& rec) -> std::string { return rec.mData.mSchool.serializeText(); });
|
||||
magicEffectT["baseCost"]
|
||||
= sol::readonly_property([](const ESM::MagicEffect& rec) -> float { return rec.mData.mBaseCost; });
|
||||
magicEffectT["color"] = sol::readonly_property([](const ESM::MagicEffect& rec) -> Misc::Color {
|
||||
return Misc::Color(rec.mData.mRed / 255.f, rec.mData.mGreen / 255.f, rec.mData.mBlue / 255.f, 1.f);
|
||||
});
|
||||
magicEffectT["hasDuration"] = sol::readonly_property(
|
||||
[](const ESM::MagicEffect& rec) -> bool { return !(rec.mData.mFlags & ESM::MagicEffect::NoDuration); });
|
||||
magicEffectT["hasMagnitude"] = sol::readonly_property(
|
||||
[](const ESM::MagicEffect& rec) -> bool { return !(rec.mData.mFlags & ESM::MagicEffect::NoMagnitude); });
|
||||
// TODO: Not self-explanatory. Needs either a better name or documentation. The description in
|
||||
// loadmgef.hpp is uninformative.
|
||||
magicEffectT["isAppliedOnce"] = sol::readonly_property(
|
||||
[](const ESM::MagicEffect& rec) -> bool { return rec.mData.mFlags & ESM::MagicEffect::AppliedOnce; });
|
||||
magicEffectT["harmful"] = sol::readonly_property(
|
||||
[](const ESM::MagicEffect& rec) -> bool { return rec.mData.mFlags & ESM::MagicEffect::Harmful; });
|
||||
magicEffectT["casterLinked"] = sol::readonly_property(
|
||||
[](const ESM::MagicEffect& rec) -> bool { return rec.mData.mFlags & ESM::MagicEffect::CasterLinked; });
|
||||
magicEffectT["nonRecastable"] = sol::readonly_property(
|
||||
[](const ESM::MagicEffect& rec) -> bool { return rec.mData.mFlags & ESM::MagicEffect::NonRecastable; });
|
||||
|
||||
// TODO: Should we expose it? What happens if a spell has several effects with different projectileSpeed?
|
||||
// magicEffectT["projectileSpeed"]
|
||||
// = sol::readonly_property([](const ESM::MagicEffect& rec) -> float { return rec.mData.mSpeed; });
|
||||
addMagicEffectType(state);
|
||||
|
||||
auto activeSpellEffectT = state.new_usertype<ESM::ActiveEffect>("ActiveSpellEffect");
|
||||
activeSpellEffectT[sol::meta_function::to_string] = [](const ESM::ActiveEffect& self) {
|
||||
|
||||
@@ -5,6 +5,7 @@
|
||||
#include <components/esm3/loadmgef.hpp>
|
||||
#include <components/esm3/loadspel.hpp>
|
||||
#include <components/lua/util.hpp>
|
||||
#include <components/misc/color.hpp>
|
||||
|
||||
#include "../mwbase/environment.hpp"
|
||||
#include "../mwworld/esmstore.hpp"
|
||||
@@ -55,6 +56,10 @@ namespace sol
|
||||
{
|
||||
};
|
||||
template <>
|
||||
struct is_automagical<ESM::MagicEffect> : std::false_type
|
||||
{
|
||||
};
|
||||
template <>
|
||||
struct is_automagical<ESM::Potion> : std::false_type
|
||||
{
|
||||
};
|
||||
@@ -132,7 +137,7 @@ namespace MWLua
|
||||
addEffectsProperty(lua, record);
|
||||
}
|
||||
|
||||
void addPropertyFromTable(const sol::lua_table& rec, std::string_view key, ESM::RefId& value)
|
||||
void addPropertyFromTable(const sol::table& rec, std::string_view key, ESM::RefId& value)
|
||||
{
|
||||
if (rec[key] != sol::nil)
|
||||
{
|
||||
@@ -293,6 +298,100 @@ namespace MWLua
|
||||
flags &= ~flag;
|
||||
}
|
||||
}
|
||||
|
||||
void setReverseFlagProperty(const sol::table& rec, std::string_view key, int32_t& flags, int flag)
|
||||
{
|
||||
if (rec[key] != sol::nil)
|
||||
{
|
||||
if (!rec[key])
|
||||
flags |= flag;
|
||||
else
|
||||
flags &= ~flag;
|
||||
}
|
||||
}
|
||||
|
||||
void assignColor(ESM::MagicEffect& effect, const Misc::Color& color)
|
||||
{
|
||||
effect.mData.mRed = std::clamp(static_cast<int32_t>(color.r() * 255), 0, 255);
|
||||
effect.mData.mGreen = std::clamp(static_cast<int32_t>(color.g() * 255), 0, 255);
|
||||
effect.mData.mBlue = std::clamp(static_cast<int32_t>(color.b() * 255), 0, 255);
|
||||
}
|
||||
|
||||
template <class T>
|
||||
void addMagicEffectType(sol::state_view& lua, std::string_view name)
|
||||
{
|
||||
sol::usertype<T> record = lua.new_usertype<T>(name);
|
||||
|
||||
record[sol::meta_function::to_string]
|
||||
= [](const T& rec) -> std::string { return "ESM3_MagicEffect[" + rec.mId.toDebugString() + "]"; };
|
||||
record["id"] = sol::readonly_property([](const T& rec) -> ESM::RefId { return rec.mId; });
|
||||
|
||||
Types::addIconProperty(record);
|
||||
Types::addProperty(record, "particle", &ESM::MagicEffect::mParticle);
|
||||
Types::addFlagProperty(record, "continuousVfx", ESM::MagicEffect::ContinuousVfx, &ESM::MagicEffect::mData,
|
||||
&ESM::MagicEffect::MEDTstruct::mFlags);
|
||||
Types::addProperty(record, "areaSound", &ESM::MagicEffect::mAreaSound);
|
||||
Types::addProperty(record, "boltSound", &ESM::MagicEffect::mBoltSound);
|
||||
Types::addProperty(record, "castSound", &ESM::MagicEffect::mCastSound);
|
||||
Types::addProperty(record, "hitSound", &ESM::MagicEffect::mHitSound);
|
||||
Types::addProperty(record, "areaStatic", &ESM::MagicEffect::mArea);
|
||||
Types::addProperty(record, "bolt", &ESM::MagicEffect::mBolt);
|
||||
Types::addProperty(record, "castStatic", &ESM::MagicEffect::mCasting);
|
||||
Types::addProperty(record, "hitStatic", &ESM::MagicEffect::mHit);
|
||||
Types::addProperty(record, "name", &ESM::MagicEffect::mName);
|
||||
Types::addProperty(record, "school", &ESM::MagicEffect::mData, &ESM::MagicEffect::MEDTstruct::mSchool);
|
||||
Types::addProperty(record, "baseCost", &ESM::MagicEffect::mData, &ESM::MagicEffect::MEDTstruct::mBaseCost);
|
||||
const auto getColor = [](const T& rec) -> Misc::Color {
|
||||
const ESM::MagicEffect& effect = Types::RecordType<T>::asRecord(rec);
|
||||
return Misc::Color(
|
||||
effect.mData.mRed / 255.f, effect.mData.mGreen / 255.f, effect.mData.mBlue / 255.f, 1.f);
|
||||
};
|
||||
if constexpr (Types::RecordType<T>::isMutable)
|
||||
{
|
||||
record["color"] = sol::property(std::move(getColor), [](T& rec, const Misc::Color& color) {
|
||||
ESM::MagicEffect& effect = rec.find();
|
||||
assignColor(effect, color);
|
||||
});
|
||||
}
|
||||
else
|
||||
{
|
||||
record["color"] = sol::readonly_property(std::move(getColor));
|
||||
}
|
||||
Types::addReverseFlagProperty(record, "hasDuration", ESM::MagicEffect::NoDuration, &ESM::MagicEffect::mData,
|
||||
&ESM::MagicEffect::MEDTstruct::mFlags);
|
||||
Types::addReverseFlagProperty(record, "hasMagnitude", ESM::MagicEffect::NoMagnitude,
|
||||
&ESM::MagicEffect::mData, &ESM::MagicEffect::MEDTstruct::mFlags);
|
||||
// TODO: Not self-explanatory. Needs either a better name or documentation. The description in
|
||||
// loadmgef.hpp is uninformative.
|
||||
Types::addFlagProperty(record, "isAppliedOnce", ESM::MagicEffect::AppliedOnce, &ESM::MagicEffect::mData,
|
||||
&ESM::MagicEffect::MEDTstruct::mFlags);
|
||||
Types::addFlagProperty(record, "harmful", ESM::MagicEffect::Harmful, &ESM::MagicEffect::mData,
|
||||
&ESM::MagicEffect::MEDTstruct::mFlags);
|
||||
Types::addFlagProperty(record, "casterLinked", ESM::MagicEffect::CasterLinked, &ESM::MagicEffect::mData,
|
||||
&ESM::MagicEffect::MEDTstruct::mFlags);
|
||||
Types::addFlagProperty(record, "nonRecastable", ESM::MagicEffect::NonRecastable, &ESM::MagicEffect::mData,
|
||||
&ESM::MagicEffect::MEDTstruct::mFlags);
|
||||
|
||||
Types::addFlagProperty(record, "hasAttribute", ESM::MagicEffect::TargetAttribute, &ESM::MagicEffect::mData,
|
||||
&ESM::MagicEffect::MEDTstruct::mFlags);
|
||||
Types::addFlagProperty(record, "hasSkill", ESM::MagicEffect::TargetSkill, &ESM::MagicEffect::mData,
|
||||
&ESM::MagicEffect::MEDTstruct::mFlags);
|
||||
Types::addFlagProperty(record, "onSelf", ESM::MagicEffect::CastSelf, &ESM::MagicEffect::mData,
|
||||
&ESM::MagicEffect::MEDTstruct::mFlags);
|
||||
Types::addFlagProperty(record, "onTouch", ESM::MagicEffect::CastTouch, &ESM::MagicEffect::mData,
|
||||
&ESM::MagicEffect::MEDTstruct::mFlags);
|
||||
Types::addFlagProperty(record, "onTarget", ESM::MagicEffect::CastTarget, &ESM::MagicEffect::mData,
|
||||
&ESM::MagicEffect::MEDTstruct::mFlags);
|
||||
Types::addFlagProperty(record, "unreflectable", ESM::MagicEffect::Unreflectable, &ESM::MagicEffect::mData,
|
||||
&ESM::MagicEffect::MEDTstruct::mFlags);
|
||||
Types::addFlagProperty(record, "allowsSpellmaking", ESM::MagicEffect::AllowSpellmaking,
|
||||
&ESM::MagicEffect::mData, &ESM::MagicEffect::MEDTstruct::mFlags);
|
||||
Types::addFlagProperty(record, "allowsEnchanting", ESM::MagicEffect::AllowEnchanting,
|
||||
&ESM::MagicEffect::mData, &ESM::MagicEffect::MEDTstruct::mFlags);
|
||||
Types::addFlagProperty(record, "negativeLight", ESM::MagicEffect::NegativeLight, &ESM::MagicEffect::mData,
|
||||
&ESM::MagicEffect::MEDTstruct::mFlags);
|
||||
Types::addProperty(record, "speed", &ESM::MagicEffect::mData, &ESM::MagicEffect::MEDTstruct::mSpeed);
|
||||
}
|
||||
}
|
||||
|
||||
void addSpellBindings(sol::state_view& state)
|
||||
@@ -382,4 +481,60 @@ namespace MWLua
|
||||
out.updateIndexes();
|
||||
return out;
|
||||
}
|
||||
|
||||
void addMagicEffectType(sol::state_view& lua)
|
||||
{
|
||||
addMagicEffectType<ESM::MagicEffect>(lua, "ESM3_MagicEffect");
|
||||
}
|
||||
|
||||
void addMutableMagicEffectType(sol::state_view& lua)
|
||||
{
|
||||
addMagicEffectType<MutableRecord<ESM::MagicEffect>>(lua, "ESM3_MutableMagicEffect");
|
||||
}
|
||||
|
||||
ESM::MagicEffect tableToMagicEffect(const sol::table& rec)
|
||||
{
|
||||
auto effect = Types::initFromTemplate<ESM::MagicEffect>(rec);
|
||||
if (rec["icon"] != sol::nil)
|
||||
effect.mIcon = rec["icon"];
|
||||
if (rec["particle"] != sol::nil)
|
||||
effect.mParticle = rec["particle"];
|
||||
setFlagProperty(rec, "continuousVfx", effect.mData.mFlags, ESM::MagicEffect::ContinuousVfx);
|
||||
addPropertyFromTable(rec, "areaSound", effect.mAreaSound);
|
||||
addPropertyFromTable(rec, "boltSound", effect.mBoltSound);
|
||||
addPropertyFromTable(rec, "castSound", effect.mCastSound);
|
||||
addPropertyFromTable(rec, "hitSound", effect.mHitSound);
|
||||
addPropertyFromTable(rec, "areaStatic", effect.mArea);
|
||||
addPropertyFromTable(rec, "bolt", effect.mBolt);
|
||||
addPropertyFromTable(rec, "castStatic", effect.mCasting);
|
||||
addPropertyFromTable(rec, "hitStatic", effect.mHit);
|
||||
if (rec["name"] != sol::nil)
|
||||
effect.mName = rec["name"];
|
||||
addPropertyFromTable(rec, "school", effect.mData.mSchool);
|
||||
if (rec["baseCost"] != sol::nil)
|
||||
effect.mData.mBaseCost = rec["baseCost"];
|
||||
if (rec["color"] != sol::nil)
|
||||
{
|
||||
const auto color = LuaUtil::cast<Misc::Color>(rec["color"]);
|
||||
assignColor(effect, color);
|
||||
}
|
||||
setReverseFlagProperty(rec, "hasDuration", effect.mData.mFlags, ESM::MagicEffect::NoDuration);
|
||||
setReverseFlagProperty(rec, "hasMagnitude", effect.mData.mFlags, ESM::MagicEffect::NoMagnitude);
|
||||
setFlagProperty(rec, "isAppliedOnce", effect.mData.mFlags, ESM::MagicEffect::AppliedOnce);
|
||||
setFlagProperty(rec, "harmful", effect.mData.mFlags, ESM::MagicEffect::Harmful);
|
||||
setFlagProperty(rec, "casterLinked", effect.mData.mFlags, ESM::MagicEffect::CasterLinked);
|
||||
setFlagProperty(rec, "nonRecastable", effect.mData.mFlags, ESM::MagicEffect::NonRecastable);
|
||||
setFlagProperty(rec, "hasAttribute", effect.mData.mFlags, ESM::MagicEffect::TargetAttribute);
|
||||
setFlagProperty(rec, "hasSkill", effect.mData.mFlags, ESM::MagicEffect::TargetSkill);
|
||||
setFlagProperty(rec, "onSelf", effect.mData.mFlags, ESM::MagicEffect::CastSelf);
|
||||
setFlagProperty(rec, "onTouch", effect.mData.mFlags, ESM::MagicEffect::CastTouch);
|
||||
setFlagProperty(rec, "onTarget", effect.mData.mFlags, ESM::MagicEffect::CastTarget);
|
||||
setFlagProperty(rec, "unreflectable", effect.mData.mFlags, ESM::MagicEffect::Unreflectable);
|
||||
setFlagProperty(rec, "allowsSpellmaking", effect.mData.mFlags, ESM::MagicEffect::AllowSpellmaking);
|
||||
setFlagProperty(rec, "allowsEnchanting", effect.mData.mFlags, ESM::MagicEffect::AllowEnchanting);
|
||||
setFlagProperty(rec, "negativeLight", effect.mData.mFlags, ESM::MagicEffect::NegativeLight);
|
||||
if (rec["speed"] != sol::nil)
|
||||
effect.mData.mSpeed = rec["speed"];
|
||||
return effect;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -7,6 +7,7 @@ namespace ESM
|
||||
{
|
||||
struct EffectList;
|
||||
struct Enchantment;
|
||||
struct MagicEffect;
|
||||
struct Potion;
|
||||
struct Spell;
|
||||
}
|
||||
@@ -25,6 +26,10 @@ namespace MWLua
|
||||
void addMutablePotionType(sol::state_view& lua);
|
||||
|
||||
ESM::EffectList tableToEffectList(const sol::table&);
|
||||
|
||||
void addMagicEffectType(sol::state_view&);
|
||||
void addMutableMagicEffectType(sol::state_view& lua);
|
||||
ESM::MagicEffect tableToMagicEffect(const sol::table&);
|
||||
}
|
||||
|
||||
#endif // MWLUA_MAGICTYPEBINDINGS_H
|
||||
@@ -111,6 +111,27 @@ namespace MWLua::Types
|
||||
type[key] = sol::readonly_property(std::move(getter));
|
||||
}
|
||||
|
||||
template <class Type, class Flag, class... Member>
|
||||
void addReverseFlagProperty(sol::usertype<Type>& type, std::string_view key, Flag flag, Member... members)
|
||||
{
|
||||
using Record = RecordType<Type>::Record;
|
||||
const auto getter = [=](const Type& rec) -> bool {
|
||||
const Record& record = RecordType<Type>::asRecord(rec);
|
||||
return !((record.*....*members) & flag);
|
||||
};
|
||||
if constexpr (RecordType<Type>::isMutable)
|
||||
type[key] = sol::property(std::move(getter), [=](Type& rec, bool value) {
|
||||
Record& record = rec.find();
|
||||
auto& data = (record.*....*members);
|
||||
if (value)
|
||||
data &= ~flag;
|
||||
else
|
||||
data |= flag;
|
||||
});
|
||||
else
|
||||
type[key] = sol::readonly_property(std::move(getter));
|
||||
}
|
||||
|
||||
template <class T>
|
||||
void addModelProperty(sol::usertype<T>& type)
|
||||
{
|
||||
|
||||
@@ -525,7 +525,6 @@ namespace MWWorld
|
||||
store->setUp();
|
||||
|
||||
getWritable<ESM::Skill>().setUp(get<ESM::GameSetting>());
|
||||
getWritable<ESM::MagicEffect>().setUp(get<ESM::GameSetting>());
|
||||
getWritable<ESM::Attribute>().setUp(get<ESM::GameSetting>());
|
||||
getWritable<ESM4::Land>().updateLandPositions(get<ESM4::Cell>());
|
||||
getWritable<ESM4::Reference>().preprocessReferences(get<ESM4::Cell>());
|
||||
|
||||
@@ -999,19 +999,6 @@ namespace MWWorld
|
||||
.mWerewolfValue = getGMSTFloat(settings, "fWerewolfLuck") });
|
||||
}
|
||||
|
||||
// Magic Effect
|
||||
//=========================================================================
|
||||
|
||||
void Store<ESM::MagicEffect>::setUp(const MWWorld::Store<ESM::GameSetting>& settings)
|
||||
{
|
||||
for (ESM::MagicEffect* mgef : mShared)
|
||||
{
|
||||
std::string_view gmst = ESM::MagicEffect::refIdToGmstString(mgef->mId);
|
||||
if (!gmst.empty())
|
||||
mgef->mName = getGMSTString(settings, gmst);
|
||||
}
|
||||
}
|
||||
|
||||
// Dialogue
|
||||
//=========================================================================
|
||||
|
||||
|
||||
@@ -466,8 +466,6 @@ namespace MWWorld
|
||||
|
||||
public:
|
||||
Store() = default;
|
||||
|
||||
void setUp(const MWWorld::Store<ESM::GameSetting>& settings);
|
||||
};
|
||||
|
||||
template <>
|
||||
|
||||
@@ -82,12 +82,28 @@ local function generateDefaultDoors()
|
||||
end
|
||||
end
|
||||
|
||||
local function setMagicEffectNames()
|
||||
local gmsts = content.gameSettings.records
|
||||
local effects = content.magicEffects.records
|
||||
for id, gmst in pairs(content.magicEffects._getGMSTs()) do
|
||||
local effect = effects[id]
|
||||
if effect ~= nil then
|
||||
local name = gmsts[gmst]
|
||||
if type(name) ~= 'string' or name == '' then
|
||||
name = gmst
|
||||
end
|
||||
effect.name = name
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
return {
|
||||
engineHandlers = {
|
||||
onContentFilesLoaded = function()
|
||||
generateDefaultDoors()
|
||||
generateDefaultGMSTs()
|
||||
generateDefaultStatics()
|
||||
setMagicEffectNames()
|
||||
end
|
||||
}
|
||||
}
|
||||
|
||||
@@ -76,6 +76,15 @@
|
||||
--- @{#MiscContent}: Misc manipulation.
|
||||
-- @field [parent=#content] #MiscContent miscs
|
||||
|
||||
--- @{#MagicEffectContent}: Magic effect manipulation.
|
||||
-- @field [parent=#content] #MagicEffectContent magicEffects
|
||||
|
||||
---
|
||||
-- A mutable list of all @{openmw.core#MagicEffect}s.
|
||||
-- @field [parent=#MagicEffectContent] #list<openmw.core#MagicEffect> records
|
||||
-- @usage
|
||||
-- content.magicEffects.records.MyMagicEffect = { template = content.magicEffects.records['summonscamp'], name = 'Summon Nothing' }
|
||||
|
||||
---
|
||||
-- A mutable list of all @{openmw.types#MiscellaneousRecord}s.
|
||||
-- @field [parent=#MiscContent] #list<openmw.types#MiscellaneousRecord> records
|
||||
|
||||
@@ -772,6 +772,16 @@
|
||||
-- @field #string hitSound Identifier of the sound used on hit
|
||||
-- @field #string areaSound Identifier of the sound used for AOE spells
|
||||
-- @field #string boltSound Identifier of the projectile sound used for ranged spells
|
||||
-- @field #boolean hasAttribute True if the effect requires an attribute parameter
|
||||
-- @field #boolean hasSkill True if the effect requires a skill parameter
|
||||
-- @field #boolean onSelf True if the effect can be cast on self
|
||||
-- @field #boolean onTouch True if the effect can be cast on touch
|
||||
-- @field #boolean onTarget True if the effect can be cast on target
|
||||
-- @field #boolean unreflectable True if the effect cannot be reflected
|
||||
-- @field #boolean allowsSpellmaking True if the effect is available for spellmaking
|
||||
-- @field #boolean allowsEnchanting True if the effect is available for enchanting
|
||||
-- @field #boolean negativeLight True if the effect casts negative light
|
||||
-- @field #number speed Unused
|
||||
|
||||
|
||||
---
|
||||
|
||||
Reference in New Issue
Block a user