1
0
mirror of https://github.com/minetest/minetest.git synced 2024-11-13 22:10:28 +01:00

LuaItemStack: Add __tostring metamethod (#8785)

* LuaItemStack: Add __tostring metamethod

* Clean up LuaItemStack::checkobject
This commit is contained in:
Paul Ouellette 2020-06-09 13:37:25 -04:00 committed by GitHub
parent 09e285f38c
commit b16f841756
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
5 changed files with 41 additions and 22 deletions

View File

@ -20,6 +20,8 @@ local function basic_dump(o)
-- dump's output is intended for humans.
--elseif tp == "function" then
-- return string.format("loadstring(%q)", string.dump(o))
elseif tp == "userdata" then
return tostring(o)
else
return string.format("<%s>", tp)
end

View File

@ -56,28 +56,31 @@ ItemStack::ItemStack(const std::string &name_, u16 count_,
count = 1;
}
void ItemStack::serialize(std::ostream &os) const
void ItemStack::serialize(std::ostream &os, bool serialize_meta) const
{
if (empty())
return;
// Check how many parts of the itemstring are needed
int parts = 1;
if(count != 1)
parts = 2;
if(wear != 0)
parts = 3;
if (!metadata.empty())
parts = 4;
else if (wear != 0)
parts = 3;
else if (count != 1)
parts = 2;
os<<serializeJsonStringIfNeeded(name);
if(parts >= 2)
os<<" "<<count;
if(parts >= 3)
os<<" "<<wear;
os << serializeJsonStringIfNeeded(name);
if (parts >= 2)
os << " " << count;
if (parts >= 3)
os << " " << wear;
if (parts >= 4) {
os << " ";
metadata.serialize(os);
if (serialize_meta)
metadata.serialize(os);
else
os << "<metadata size=" << metadata.size() << ">";
}
}
@ -240,10 +243,10 @@ void ItemStack::deSerialize(const std::string &str, IItemDefManager *itemdef)
deSerialize(is, itemdef);
}
std::string ItemStack::getItemString() const
std::string ItemStack::getItemString(bool include_meta) const
{
std::ostringstream os(std::ios::binary);
serialize(os);
serialize(os, include_meta);
return os.str();
}

View File

@ -40,13 +40,13 @@ struct ItemStack
~ItemStack() = default;
// Serialization
void serialize(std::ostream &os) const;
void serialize(std::ostream &os, bool serialize_meta = true) const;
// Deserialization. Pass itemdef unless you don't want aliases resolved.
void deSerialize(std::istream &is, IItemDefManager *itemdef = NULL);
void deSerialize(const std::string &s, IItemDefManager *itemdef = NULL);
// Returns the string used for inventory
std::string getItemString() const;
std::string getItemString(bool include_meta = true) const;
// Returns the tooltip
std::string getDescription(IItemDefManager *itemdef) const;

View File

@ -37,6 +37,15 @@ int LuaItemStack::gc_object(lua_State *L)
return 0;
}
// __tostring metamethod
int LuaItemStack::mt_tostring(lua_State *L)
{
LuaItemStack *o = checkobject(L, 1);
std::string itemstring = o->m_stack.getItemString(false);
lua_pushfstring(L, "ItemStack(\"%s\")", itemstring.c_str());
return 1;
}
// is_empty(self) -> true/false
int LuaItemStack::l_is_empty(lua_State *L)
{
@ -433,12 +442,9 @@ int LuaItemStack::create(lua_State *L, const ItemStack &item)
return 1;
}
LuaItemStack* LuaItemStack::checkobject(lua_State *L, int narg)
LuaItemStack *LuaItemStack::checkobject(lua_State *L, int narg)
{
luaL_checktype(L, narg, LUA_TUSERDATA);
void *ud = luaL_checkudata(L, narg, className);
if(!ud) luaL_typerror(L, narg, className);
return *(LuaItemStack**)ud; // unbox pointer
return *(LuaItemStack **)luaL_checkudata(L, narg, className);
}
void LuaItemStack::Register(lua_State *L)
@ -448,9 +454,10 @@ void LuaItemStack::Register(lua_State *L)
luaL_newmetatable(L, className);
int metatable = lua_gettop(L);
// hide metatable from Lua getmetatable()
lua_pushliteral(L, "__metatable");
lua_pushvalue(L, methodtable);
lua_settable(L, metatable); // hide metatable from Lua getmetatable()
lua_settable(L, metatable);
lua_pushliteral(L, "__index");
lua_pushvalue(L, methodtable);
@ -460,12 +467,16 @@ void LuaItemStack::Register(lua_State *L)
lua_pushcfunction(L, gc_object);
lua_settable(L, metatable);
lua_pushliteral(L, "__tostring");
lua_pushcfunction(L, mt_tostring);
lua_settable(L, metatable);
lua_pop(L, 1); // drop metatable
luaL_openlib(L, 0, methods, 0); // fill methodtable
lua_pop(L, 1); // drop methodtable
// Can be created from Lua (LuaItemStack(itemstack or itemstring or table or nil))
// Can be created from Lua (ItemStack(itemstack or itemstring or table or nil))
lua_register(L, className, create_object);
}

View File

@ -34,6 +34,9 @@ private:
// garbage collector
static int gc_object(lua_State *L);
// __tostring metamethod
static int mt_tostring(lua_State *L);
// is_empty(self) -> true/false
static int l_is_empty(lua_State *L);