Lua: player.* identity getters and setters

This commit is contained in:
Kae 2023-06-29 05:58:24 +10:00
parent 8a2de03b0f
commit fb0ab85089
10 changed files with 216 additions and 52 deletions

View File

@ -162,10 +162,7 @@ bool Directives::empty() const {
return !shared || shared->empty(); return !shared || shared->empty();
} }
Directives::operator bool() const { Directives::operator bool() const { return !empty(); }
return !empty();
}
DataStream& operator>>(DataStream& ds, Directives& directives) { DataStream& operator>>(DataStream& ds, Directives& directives) {
String string; String string;

View File

@ -9,6 +9,7 @@
#include "StarString.hpp" #include "StarString.hpp"
#include "StarJson.hpp" #include "StarJson.hpp"
#include "StarRefPtr.hpp" #include "StarRefPtr.hpp"
#include "StarDirectives.hpp"
namespace Star { namespace Star {
@ -825,6 +826,16 @@ struct LuaConverter<char[s]> {
} }
}; };
template <>
struct LuaConverter<Directives> {
static LuaValue from(LuaEngine& engine, Directives const& v) {
if (String const* ptr = v.stringPtr())
return engine.createString(*ptr);
else
return engine.createString("");
}
};
template <> template <>
struct LuaConverter<LuaString> { struct LuaConverter<LuaString> {
static LuaValue from(LuaEngine&, LuaString v) { static LuaValue from(LuaEngine&, LuaString v) {

View File

@ -354,7 +354,8 @@ void CharCreationPane::changed() {
m_previewPlayer->setGender(GenderNames.getLeft(gender.name)); m_previewPlayer->setGender(GenderNames.getLeft(gender.name));
m_previewPlayer->setHairType(gender.hairGroup, hair); m_previewPlayer->setHairGroup(gender.hairGroup);
m_previewPlayer->setHairType(hair);
m_previewPlayer->setHairDirectives(hairColor); m_previewPlayer->setHairDirectives(hairColor);
m_previewPlayer->setEmoteDirectives(bodyColor + altColor); m_previewPlayer->setEmoteDirectives(bodyColor + altColor);

View File

@ -27,10 +27,34 @@ extern EnumMap<HumanoidEmote> const HumanoidEmoteNames{
{HumanoidEmote::Sleep, "Sleep"} {HumanoidEmote::Sleep, "Sleep"}
}; };
Personality parsePersonality(Json const& config) { Personality parsePersonalityArray(Json const& config) {
return Personality{config.getString(0), config.getString(1), jsonToVec2F(config.get(2)), jsonToVec2F(config.get(3))}; return Personality{config.getString(0), config.getString(1), jsonToVec2F(config.get(2)), jsonToVec2F(config.get(3))};
} }
Personality& parsePersonality(Personality& personality, Json const& config) {
if (auto idle = config.get("idle"))
personality.idle = idle.toString();
if (auto armIdle = config.get("armIdle"))
personality.idle = armIdle.toString();
if (auto headOffset = config.get("headOffset"))
personality.headOffset = jsonToVec2F(headOffset);
if (auto armOffset = config.get("armOffset"))
personality.armOffset = jsonToVec2F(armOffset);
}
Personality parsePersonality(Json const& config) {
return parsePersonality(Personality(), config);
}
Json jsonFromPersonality(Personality const& personality) {
return JsonObject{
{ "idle", personality.idle },
{ "armIdle", personality.armIdle },
{ "headOffset", jsonFromVec2F(personality.headOffset) },
{ "armOffset", jsonFromVec2F(personality.armOffset) }
};
}
HumanoidIdentity::HumanoidIdentity(Json config) { HumanoidIdentity::HumanoidIdentity(Json config) {
if (config.isNull()) if (config.isNull())
config = JsonObject(); config = JsonObject();

View File

@ -38,14 +38,19 @@ extern EnumMap<HumanoidEmote> const HumanoidEmoteNames;
size_t const EmoteSize = 14; size_t const EmoteSize = 14;
struct Personality { struct Personality {
String idle; String idle = "idle.1";
String armIdle; String armIdle = "idle.1";
Vec2F headOffset; Vec2F headOffset = Vec2F();
Vec2F armOffset; Vec2F armOffset = Vec2F();
}; };
Personality parsePersonalityArray(Json const& config);
Personality& parsePersonality(Personality& personality, Json const& config);
Personality parsePersonality(Json const& config); Personality parsePersonality(Json const& config);
Json jsonFromPersonality(Personality const& personality);
struct HumanoidIdentity { struct HumanoidIdentity {
explicit HumanoidIdentity(Json config = Json()); explicit HumanoidIdentity(Json config = Json());

View File

@ -75,7 +75,7 @@ NpcVariant NpcDatabase::generateNpcVariant(
jsonToStringList(config.get("nameGen"))[(int)identity.gender], randSource); jsonToStringList(config.get("nameGen"))[(int)identity.gender], randSource);
} }
identity.personality = parsePersonality(randSource.randFrom(variant.humanoidConfig.getArray("personalities"))); identity.personality = parsePersonalityArray(randSource.randFrom(variant.humanoidConfig.getArray("personalities")));
if (config.contains("identity")) if (config.contains("identity"))
identity = HumanoidIdentity(jsonMerge(identity.toJson(), config.get("identity"))); identity = HumanoidIdentity(jsonMerge(identity.toJson(), config.get("identity")));

View File

@ -1843,8 +1843,7 @@ bool Player::isAdmin() const {
void Player::setFavoriteColor(Vec4B color) { void Player::setFavoriteColor(Vec4B color) {
m_identity.color = color; m_identity.color = color;
m_identityUpdated = true; updateIdentity();
m_humanoid->setIdentity(m_identity);
} }
Vec4B Player::favoriteColor() const { Vec4B Player::favoriteColor() const {
@ -1951,8 +1950,7 @@ String Player::name() const {
void Player::setName(String const& name) { void Player::setName(String const& name) {
m_identity.name = name; m_identity.name = name;
m_identityUpdated = true; updateIdentity();
m_humanoid->setIdentity(m_identity);
} }
Maybe<String> Player::statusText() const { Maybe<String> Player::statusText() const {
@ -1972,51 +1970,66 @@ Vec2F Player::nametagOrigin() const {
return mouthPosition(false); return mouthPosition(false);
} }
void Player::setBodyDirectives(String const& directives) { void Player::updateIdentity()
m_identity.bodyDirectives = directives; { m_identityUpdated = true; m_humanoid->setIdentity(m_identity); }
m_identityUpdated = true;
m_humanoid->setIdentity(m_identity);
}
void Player::setHairType(String const& group, String const& type) { void Player::setBodyDirectives(String const& directives)
{ m_identity.bodyDirectives = directives; updateIdentity(); }
void Player::setEmoteDirectives(String const& directives)
{ m_identity.emoteDirectives = directives; updateIdentity(); }
void Player::setHairGroup(String const& group)
{ m_identity.hairGroup = group; updateIdentity(); }
void Player::setHairType(String const& type)
{ m_identity.hairType = type; updateIdentity(); }
void Player::setHairDirectives(String const& directives)
{ m_identity.hairDirectives = directives; updateIdentity(); }
void Player::setFacialHairGroup(String const& group)
{ m_identity.facialHairGroup = group; updateIdentity(); }
void Player::setFacialHairType(String const& type)
{ m_identity.facialHairType = type; updateIdentity(); }
void Player::setFacialHairDirectives(String const& directives)
{ m_identity.facialHairDirectives = directives; updateIdentity(); }
void Player::setFacialMaskGroup(String const& group)
{ m_identity.facialMaskGroup = group; updateIdentity(); }
void Player::setFacialMaskType(String const& type)
{ m_identity.facialMaskType = type; updateIdentity(); }
void Player::setFacialMaskDirectives(String const& directives)
{ m_identity.facialMaskDirectives = directives; updateIdentity(); }
void Player::setHair(String const& group, String const& type, String const& directives) {
m_identity.hairGroup = group; m_identity.hairGroup = group;
m_identity.hairType = type; m_identity.hairType = type;
m_identityUpdated = true; m_identity.hairDirectives = directives;
m_humanoid->setIdentity(m_identity); updateIdentity();
} }
void Player::setFacialHair(String const& group, String const& type, String const& directives) { void Player::setFacialHair(String const& group, String const& type, String const& directives) {
m_identity.facialHairGroup = group; m_identity.facialHairGroup = group;
m_identity.facialHairType = type; m_identity.facialHairType = type;
m_identity.facialHairDirectives = directives; m_identity.facialHairDirectives = directives;
m_identityUpdated = true; updateIdentity();
m_humanoid->setIdentity(m_identity);
} }
void Player::setFacialMask(String const& group, String const& type, String const& directives) { void Player::setFacialMask(String const& group, String const& type, String const& directives) {
m_identity.facialMaskGroup = group; m_identity.facialMaskGroup = group;
m_identity.facialMaskType = type; m_identity.facialMaskType = type;
m_identity.facialMaskDirectives = directives; m_identity.facialMaskDirectives = directives;
m_identityUpdated = true; updateIdentity();
m_humanoid->setIdentity(m_identity);
}
void Player::setHairDirectives(String const& directives) {
m_identity.hairDirectives = directives;
m_identityUpdated = true;
m_humanoid->setIdentity(m_identity);
}
void Player::setEmoteDirectives(String const& directives) {
m_identity.emoteDirectives = directives;
m_identityUpdated = true;
m_humanoid->setIdentity(m_identity);
} }
void Player::setSpecies(String const& species) { void Player::setSpecies(String const& species) {
m_identity.species = species; m_identity.species = species;
m_identityUpdated = true; updateIdentity();
m_humanoid->setIdentity(m_identity);
} }
Gender Player::gender() const { Gender Player::gender() const {
@ -2025,8 +2038,7 @@ Gender Player::gender() const {
void Player::setGender(Gender const& gender) { void Player::setGender(Gender const& gender) {
m_identity.gender = gender; m_identity.gender = gender;
m_identityUpdated = true; updateIdentity();
m_humanoid->setIdentity(m_identity);
} }
String Player::species() const { String Player::species() const {
@ -2035,14 +2047,27 @@ String Player::species() const {
void Player::setPersonality(Personality const& personality) { void Player::setPersonality(Personality const& personality) {
m_identity.personality = personality; m_identity.personality = personality;
m_identityUpdated = true; updateIdentity();
m_humanoid->setIdentity(m_identity); }
void Player::setImagePath(Maybe<String> const& imagePath) {
m_identity.imagePath = imagePath;
updateIdentity();
} }
HumanoidPtr Player::humanoid() { HumanoidPtr Player::humanoid() {
return m_humanoid; return m_humanoid;
} }
HumanoidIdentity const& Player::identity() const {
return m_identity;
}
void Player::setIdentity(HumanoidIdentity identity) {
m_identity = move(identity);
updateIdentity();
}
List<String> Player::pullQueuedMessages() { List<String> Player::pullQueuedMessages() {
return take(m_queuedMessages); return take(m_queuedMessages);
} }

View File

@ -288,10 +288,24 @@ public:
Vec3B nametagColor() const override; Vec3B nametagColor() const override;
Vec2F nametagOrigin() const override; Vec2F nametagOrigin() const override;
void updateIdentity();
void setBodyDirectives(String const& directives); void setBodyDirectives(String const& directives);
void setHairType(String const& group, String const& type);
void setHairDirectives(String const& directives);
void setEmoteDirectives(String const& directives); void setEmoteDirectives(String const& directives);
void setHairGroup(String const& group);
void setHairType(String const& type);
void setHairDirectives(String const& directives);
void setFacialHairGroup(String const& group);
void setFacialHairType(String const& type);
void setFacialHairDirectives(String const& directives);
void setFacialMaskGroup(String const& group);
void setFacialMaskType(String const& type);
void setFacialMaskDirectives(String const& directives);
void setHair (String const& group, String const& type, String const& directives);
void setFacialHair(String const& group, String const& type, String const& directives); void setFacialHair(String const& group, String const& type, String const& directives);
void setFacialMask(String const& group, String const& type, String const& directives); void setFacialMask(String const& group, String const& type, String const& directives);
@ -300,8 +314,12 @@ public:
Gender gender() const; Gender gender() const;
void setGender(Gender const& gender); void setGender(Gender const& gender);
void setPersonality(Personality const& personality); void setPersonality(Personality const& personality);
void setImagePath(Maybe<String> const& imagePath);
HumanoidPtr humanoid(); HumanoidPtr humanoid();
HumanoidIdentity const& identity() const;
void setIdentity(HumanoidIdentity identity);
void setAdmin(bool isAdmin); void setAdmin(bool isAdmin);
bool isAdmin() const override; bool isAdmin() const override;

View File

@ -72,7 +72,7 @@ SpeciesDefinition::SpeciesDefinition(Json const& config) {
auto personalities = humanoidConfig().getArray("personalities"); auto personalities = humanoidConfig().getArray("personalities");
for (auto personality : personalities) { for (auto personality : personalities) {
m_personalities.push_back(parsePersonality(personality)); m_personalities.push_back(parsePersonalityArray(personality));
} }
m_statusEffects = config.getArray("statusEffects", {}).transformed(jsonToPersistentStatusEffect); m_statusEffects = config.getArray("statusEffects", {}).transformed(jsonToPersistentStatusEffect);

View File

@ -17,11 +17,94 @@ namespace Star {
LuaCallbacks LuaBindings::makePlayerCallbacks(Player* player) { LuaCallbacks LuaBindings::makePlayerCallbacks(Player* player) {
LuaCallbacks callbacks; LuaCallbacks callbacks;
callbacks.registerCallback("id", [player]() { return player->entityId(); }); callbacks.registerCallback("humanoidIdentity", [player]() { return player->humanoid()->identity().toJson(); });
callbacks.registerCallback("setHumanoidIdentity", [player](Json const& id) { player->setIdentity(HumanoidIdentity(id)); });
callbacks.registerCallback("bodyDirectives", [player]() { return player->identity().bodyDirectives; });
callbacks.registerCallback("setBodyDirectives", [player](String const& str) { player->setBodyDirectives(str); });
callbacks.registerCallback("emoteDirectives", [player]() { return player->identity().emoteDirectives; });
callbacks.registerCallback("setEmoteDirectives", [player](String const& str) { player->setEmoteDirectives(str); });
callbacks.registerCallback("hairGroup", [player]() { return player->identity().hairGroup; });
callbacks.registerCallback("setHairGroup", [player](String const& str) { player->setHairGroup(str); });
callbacks.registerCallback("hairType", [player]() { return player->identity().hairType; });
callbacks.registerCallback("setHairType", [player](String const& str) { player->setHairType(str); });
callbacks.registerCallback("hairDirectives", [player]() { return player->identity().hairDirectives; });
callbacks.registerCallback("setHairDirectives", [player](String const& str) { player->setHairDirectives(str); });
callbacks.registerCallback("facialHairGroup", [player]() { return player->identity().facialHairGroup; });
callbacks.registerCallback("setFacialHairGroup", [player](String const& str) { player->setFacialHairGroup(str); });
callbacks.registerCallback("facialHairType", [player]() { return player->identity().facialHairType; });
callbacks.registerCallback("setFacialHairType", [player](String const& str) { player->setFacialHairType(str); });
callbacks.registerCallback("facialHairDirectives", [player]() { return player->identity().facialHairDirectives; });
callbacks.registerCallback("setFacialHairDirectives", [player](String const& str) { player->setFacialHairDirectives(str); });
callbacks.registerCallback("hair", [player]() {
HumanoidIdentity const& identity = player->identity();
return luaTupleReturn(identity.hairGroup, identity.hairType, identity.hairDirectives);
});
callbacks.registerCallback("facialHair", [player]() {
HumanoidIdentity const& identity = player->identity();
return luaTupleReturn(identity.facialHairGroup, identity.facialHairType, identity.facialHairDirectives);
});
callbacks.registerCallback("facialMask", [player]() {
HumanoidIdentity const& identity = player->identity();
return luaTupleReturn(identity.facialMaskGroup, identity.facialMaskType, identity.facialMaskDirectives);
});
callbacks.registerCallback("setFacialHair", [player](Maybe<String> const& group, Maybe<String> const& type, Maybe<String> const& directives) {
if (group && type && directives)
player->setFacialHair(*group, *type, *directives);
else {
if (group) player->setFacialHairGroup(*group);
if (type) player->setFacialHairType(*type);
if (directives) player->setFacialHairDirectives(*directives);
}
});
callbacks.registerCallback("setFacialMask", [player](Maybe<String> const& group, Maybe<String> const& type, Maybe<String> const& directives) {
if (group && type && directives)
player->setFacialMask(*group, *type, *directives);
else {
if (group) player->setFacialMaskGroup(*group);
if (type) player->setFacialMaskType(*type);
if (directives) player->setFacialMaskDirectives(*directives);
}
});
callbacks.registerCallback("setHair", [player](Maybe<String> const& group, Maybe<String> const& type, Maybe<String> const& directives) {
if (group && type && directives)
player->setHair(*group, *type, *directives);
else {
if (group) player->setHairGroup(*group);
if (type) player->setHairType(*type);
if (directives) player->setHairDirectives(*directives);
}
});
callbacks.registerCallback("species", [player]() { return player->species(); });
callbacks.registerCallback("setSpecies", [player](String const& species) { player->setSpecies(species); });
callbacks.registerCallback("imagePath", [player]() { return player->identity().imagePath; });
callbacks.registerCallback("setImagePath", [player](Maybe<String> const& imagePath) { player->setImagePath(imagePath); });
callbacks.registerCallback("gender", [player]() { return GenderNames.getRight(player->gender()); });
callbacks.registerCallback("setGender", [player](String const& gender) { player->setGender(GenderNames.getLeft(gender)); });
callbacks.registerCallback("personality", [player]() { return jsonFromPersonality(player->identity().personality); });
callbacks.registerCallback("setPersonality", [player](Json const& personalityConfig) {
Personality const& oldPersonality = player->identity().personality;
player->setPersonality(parsePersonality(Personality(oldPersonality), personalityConfig));
});
void setPersonality(Personality const& personality);
callbacks.registerCallback("id", [player]() { return player->entityId(); });
callbacks.registerCallback("uniqueId", [player]() { return player->uniqueId(); }); callbacks.registerCallback("uniqueId", [player]() { return player->uniqueId(); });
callbacks.registerCallback("species", [player]() { return player->species(); }); callbacks.registerCallback("isAdmin", [player]() { return player->isAdmin(); });
callbacks.registerCallback("gender", [player]() { return GenderNames.getRight(player->gender()); });
callbacks.registerCallback("isAdmin", [player]() { return player->isAdmin(); });
callbacks.registerCallback("interact", [player](String const& type, Json const& configData, Maybe<EntityId> const& sourceEntityId) { callbacks.registerCallback("interact", [player](String const& type, Json const& configData, Maybe<EntityId> const& sourceEntityId) {
player->interact(InteractAction(type, sourceEntityId.value(NullEntityId), configData)); player->interact(InteractAction(type, sourceEntityId.value(NullEntityId), configData));