mirror of
https://github.com/luanti-org/luanti.git
synced 2025-08-11 17:51:04 +00:00
Implement player attribute backend (#4155)
* This backend permit mods to store extra players attributes to a common interface. * Add the obj:set_attribute(attr, value) Lua call * Add the obj:get_attribute(attr) Lua call Examples: * player:set_attribute("home:home", "10,25,-78") * player:get_attribute("default:mana") Attributes are saved as a json in the player file in extended_attributes key They are saved only if a modification on the attributes occurs and loaded when emergePlayer is called (they are attached to PlayerSAO).
This commit is contained in:
parent
2a89531071
commit
b7a98e9850
9 changed files with 128 additions and 6 deletions
|
@ -19,13 +19,14 @@ with this program; if not, write to the Free Software Foundation, Inc.,
|
|||
*/
|
||||
|
||||
#include "remoteplayer.h"
|
||||
#include <json/json.h>
|
||||
#include "content_sao.h"
|
||||
#include "filesys.h"
|
||||
#include "gamedef.h"
|
||||
#include "porting.h" // strlcpy
|
||||
#include "server.h"
|
||||
#include "settings.h"
|
||||
|
||||
|
||||
/*
|
||||
RemotePlayer
|
||||
*/
|
||||
|
@ -112,9 +113,23 @@ void RemotePlayer::save(std::string savedir, IGameDef *gamedef)
|
|||
}
|
||||
|
||||
infostream << "Didn't find free file for player " << m_name << std::endl;
|
||||
return;
|
||||
}
|
||||
|
||||
void RemotePlayer::serializeExtraAttributes(std::string &output)
|
||||
{
|
||||
assert(m_sao);
|
||||
Json::Value json_root;
|
||||
const PlayerAttributes &attrs = m_sao->getExtendedAttributes();
|
||||
for (PlayerAttributes::const_iterator it = attrs.begin(); it != attrs.end(); ++it) {
|
||||
json_root[(*it).first] = (*it).second;
|
||||
}
|
||||
|
||||
Json::FastWriter writer;
|
||||
output = writer.write(json_root);
|
||||
m_sao->setExtendedAttributeModified(false);
|
||||
}
|
||||
|
||||
|
||||
void RemotePlayer::deSerialize(std::istream &is, const std::string &playername,
|
||||
PlayerSAO *sao)
|
||||
{
|
||||
|
@ -150,6 +165,20 @@ void RemotePlayer::deSerialize(std::istream &is, const std::string &playername,
|
|||
try {
|
||||
sao->setBreath(args.getS32("breath"), false);
|
||||
} catch (SettingNotFoundException &e) {}
|
||||
|
||||
try {
|
||||
std::string extended_attributes = args.get("extended_attributes");
|
||||
Json::Reader reader;
|
||||
Json::Value attr_root;
|
||||
reader.parse(extended_attributes, attr_root);
|
||||
|
||||
const Json::Value::Members attr_list = attr_root.getMemberNames();
|
||||
for (Json::Value::Members::const_iterator it = attr_list.begin();
|
||||
it != attr_list.end(); ++it) {
|
||||
Json::Value attr_value = attr_root[*it];
|
||||
sao->setExtendedAttribute(*it, attr_value.asString());
|
||||
}
|
||||
} catch (SettingNotFoundException &e) {}
|
||||
}
|
||||
|
||||
inventory.deSerialize(is);
|
||||
|
@ -175,7 +204,6 @@ void RemotePlayer::serialize(std::ostream &os)
|
|||
Settings args;
|
||||
args.setS32("version", 1);
|
||||
args.set("name", m_name);
|
||||
//args.set("password", m_password);
|
||||
|
||||
// This should not happen
|
||||
assert(m_sao);
|
||||
|
@ -185,6 +213,10 @@ void RemotePlayer::serialize(std::ostream &os)
|
|||
args.setFloat("yaw", m_sao->getYaw());
|
||||
args.setS32("breath", m_sao->getBreath());
|
||||
|
||||
std::string extended_attrs = "";
|
||||
serializeExtraAttributes(extended_attrs);
|
||||
args.set("extended_attributes", extended_attrs);
|
||||
|
||||
args.writeLines(os);
|
||||
|
||||
os<<"PlayerArgsEnd\n";
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue