Group owner bindings into a table

pull/3234/head
uramer 11 months ago
parent 66b2d428c8
commit 6792cf02b2

@ -71,6 +71,12 @@ namespace MWLua
{
Obj mObj;
};
template <typename Obj>
struct Owner
{
Obj mObj;
};
}
#endif // MWLUA_OBJECT_H

@ -200,6 +200,80 @@ namespace MWLua
return Misc::Convert::makeOsgQuat(pos.rot);
}
template <class ObjectT>
void addOwnerbindings(sol::usertype<ObjectT>& objectT, const std::string& prefix, const Context& context)
{
using OwnerT = Owner<ObjectT>;
sol::usertype<OwnerT> ownerT = context.mLua->sol().new_usertype<OwnerT>(prefix + "Owner");
ownerT[sol::meta_function::to_string] = [](const OwnerT& o) { return "Owner[" + o.mObj.toString() + "]"; };
auto getOwnerRecordId = [](const OwnerT& o) -> sol::optional<std::string> {
ESM::RefId owner = o.mObj.ptr().getCellRef().getOwner();
if (owner.empty())
return sol::nullopt;
else
return owner.serializeText();
};
auto setOwnerRecordId = [](const OwnerT& o, sol::optional<std::string_view> ownerId) {
if (std::is_same_v<ObjectT, LObject> && !dynamic_cast<const SelfObject*>(&o.mObj))
throw std::runtime_error("Local scripts can set an owner only on self");
const MWWorld::Ptr& ptr = o.mObj.ptr();
if (!ownerId)
{
ptr.getCellRef().setOwner(ESM::RefId());
return;
}
ESM::RefId owner = ESM::RefId::deserializeText(*ownerId);
const MWWorld::ESMStore& store = *MWBase::Environment::get().getESMStore();
if (!store.get<ESM::NPC>().search(owner))
throw std::runtime_error("Invalid owner record id");
ptr.getCellRef().setOwner(owner);
};
ownerT["recordId"] = sol::property(getOwnerRecordId, setOwnerRecordId);
auto getOwnerFactionId = [](const OwnerT& o) -> sol::optional<std::string> {
ESM::RefId owner = o.mObj.ptr().getCellRef().getFaction();
if (owner.empty())
return sol::nullopt;
else
return owner.serializeText();
};
auto setOwnerFactionId = [](const OwnerT& o, sol::optional<std::string> ownerId) {
ESM::RefId ownerFac;
if (std::is_same_v<ObjectT, LObject> && !dynamic_cast<const SelfObject*>(&o.mObj))
throw std::runtime_error("Local scripts can set an owner faction only on self");
if (!ownerId)
{
o.mObj.ptr().getCellRef().setFaction(ESM::RefId());
return;
}
ownerFac = ESM::RefId::deserializeText(*ownerId);
const MWWorld::ESMStore& store = *MWBase::Environment::get().getESMStore();
if (!store.get<ESM::Faction>().search(ownerFac))
throw std::runtime_error("Invalid owner faction id");
o.mObj.ptr().getCellRef().setFaction(ownerFac);
};
ownerT["factionId"] = sol::property(getOwnerFactionId, setOwnerFactionId);
auto getOwnerFactionRank = [](const OwnerT& o) -> sol::optional<int> {
int rank = o.mObj.ptr().getCellRef().getFactionRank();
if (rank < 0)
return sol::nullopt;
else
return rank;
};
auto setOwnerFactionRank = [](const OwnerT& o, sol::optional<int> factionRank) {
if (std::is_same_v<ObjectT, LObject> && !dynamic_cast<const SelfObject*>(&o.mObj))
throw std::runtime_error("Local scripts can set an owner faction rank only on self");
o.mObj.ptr().getCellRef().setFactionRank(factionRank.value_or(-1));
};
ownerT["factionRank"] = sol::property(getOwnerFactionRank, setOwnerFactionRank);
objectT["owner"] = sol::readonly_property([](const ObjectT& object) { return OwnerT{ object }; });
}
template <class ObjectT>
void addBasicBindings(sol::usertype<ObjectT>& objectT, const Context& context)
{
@ -266,68 +340,6 @@ namespace MWLua
context.mLuaEvents->addLocalEvent(
{ dest.id(), std::move(eventName), LuaUtil::serialize(eventData, context.mSerializer) });
};
auto getOwnerRecordId = [](const ObjectT& o) -> sol::optional<std::string> {
ESM::RefId owner = o.ptr().getCellRef().getOwner();
if (owner.empty())
return sol::nullopt;
else
return owner.serializeText();
};
auto setOwnerRecordId = [](const ObjectT& obj, sol::optional<std::string_view> ownerId) {
if (std::is_same_v<ObjectT, LObject> && !dynamic_cast<const SelfObject*>(&obj))
throw std::runtime_error("Local scripts can set an owner only on self");
const MWWorld::Ptr& ptr = obj.ptr();
if (!ownerId)
{
ptr.getCellRef().setOwner(ESM::RefId());
return;
}
ESM::RefId owner = ESM::RefId::deserializeText(*ownerId);
const MWWorld::ESMStore& store = *MWBase::Environment::get().getESMStore();
if (!store.get<ESM::NPC>().search(owner))
throw std::runtime_error("Invalid owner record id");
ptr.getCellRef().setOwner(owner);
};
objectT["ownerRecordId"] = sol::property(getOwnerRecordId, setOwnerRecordId);
auto getOwnerFactionId = [](const ObjectT& o) -> sol::optional<std::string> {
ESM::RefId owner = o.ptr().getCellRef().getFaction();
if (owner.empty())
return sol::nullopt;
else
return owner.serializeText();
};
auto setOwnerFactionId = [](const ObjectT& object, sol::optional<std::string> ownerId) {
ESM::RefId ownerFac;
if (std::is_same_v<ObjectT, LObject> && !dynamic_cast<const SelfObject*>(&object))
throw std::runtime_error("Local scripts can set an owner faction only on self");
if (!ownerId)
{
object.ptr().getCellRef().setFaction(ESM::RefId());
return;
}
ownerFac = ESM::RefId::deserializeText(*ownerId);
const MWWorld::ESMStore& store = *MWBase::Environment::get().getESMStore();
if (!store.get<ESM::Faction>().search(ownerFac))
throw std::runtime_error("Invalid owner faction id");
object.ptr().getCellRef().setFaction(ownerFac);
};
objectT["ownerFactionId"] = sol::property(getOwnerFactionId, setOwnerFactionId);
auto getOwnerFactionRank = [](const ObjectT& o) -> sol::optional<int> {
int rank = o.ptr().getCellRef().getFactionRank();
if (rank < 0)
return sol::nullopt;
else
return rank;
};
auto setOwnerFactionRank = [](const ObjectT& object, sol::optional<int> factionRank) {
if (std::is_same_v<ObjectT, LObject> && !dynamic_cast<const SelfObject*>(&object))
throw std::runtime_error("Local scripts can set an owner faction rank only on self");
object.ptr().getCellRef().setFactionRank(factionRank.value_or(-1));
};
objectT["ownerFactionRank"] = sol::property(getOwnerFactionRank, setOwnerFactionRank);
objectT["activateBy"] = [](const ObjectT& object, const ObjectT& actor) {
const MWWorld::Ptr& objPtr = object.ptr();
@ -672,6 +684,7 @@ namespace MWLua
= context.mLua->sol().new_usertype<ObjectT>(prefix + "Object", sol::base_classes, sol::bases<Object>());
addBasicBindings<ObjectT>(objectT, context);
addInventoryBindings<ObjectT>(objectT, prefix, context);
addOwnerbindings<ObjectT>(objectT, prefix, context);
registerObjectList<ObjectT>(prefix, context);
}

@ -164,9 +164,7 @@
-- @field openmw.util#Transform rotation Object rotation.
-- @field openmw.util#Vector3 startingPosition The object original position
-- @field openmw.util#Transform startingRotation The object original rotation
-- @field #string ownerRecordId NPC who owns the object (nil if missing). Global and self scripts can set the value.
-- @field #string ownerFactionId Faction who owns the object (nil if missing). Global and self scripts can set the value.
-- @field #number ownerFactionRank Rank required to be allowed to pick up the object (`nil` if any rank is allowed). Global and self scripts can set the value.
-- @field #ObjectOwner owner Ownership information
-- @field #Cell cell The cell where the object currently is. During loading a game and for objects in an inventory or a container `cell` is nil.
-- @field #GameObject parentContainer Container or actor that contains (or has in inventory) this object. It is nil if the object is in a cell.
-- @field #any type Type of the object (one of the tables from the package @{openmw.types#types}).
@ -174,6 +172,14 @@
-- @field #string recordId Returns record ID of the object in lowercase.
-- @field #string globalVariable Global Variable associated with this object(read only).
---
-- Object owner information
-- @type ObjectOwner
-- @field #string recordId NPC who owns the object (nil if missing). Global and self scripts can set the value.
-- @field #string factionId Faction who owns the object (nil if missing). Global and self scripts can set the value.
-- @field #number factionRank Rank required to be allowed to pick up the object (`nil` if any rank is allowed). Global and self scripts can set the value.
---
-- Does the object still exist and is available.
-- Returns true if the object exists and loaded, and false otherwise. If false, then every

Loading…
Cancel
Save