forked from Mirrorlandia_minetest/minetest
LuaItemStack: Add __tostring metamethod (#8785)
* LuaItemStack: Add __tostring metamethod * Clean up LuaItemStack::checkobject
This commit is contained in:
parent
09e285f38c
commit
b16f841756
@ -20,6 +20,8 @@ local function basic_dump(o)
|
|||||||
-- dump's output is intended for humans.
|
-- dump's output is intended for humans.
|
||||||
--elseif tp == "function" then
|
--elseif tp == "function" then
|
||||||
-- return string.format("loadstring(%q)", string.dump(o))
|
-- return string.format("loadstring(%q)", string.dump(o))
|
||||||
|
elseif tp == "userdata" then
|
||||||
|
return tostring(o)
|
||||||
else
|
else
|
||||||
return string.format("<%s>", tp)
|
return string.format("<%s>", tp)
|
||||||
end
|
end
|
||||||
|
@ -56,28 +56,31 @@ ItemStack::ItemStack(const std::string &name_, u16 count_,
|
|||||||
count = 1;
|
count = 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
void ItemStack::serialize(std::ostream &os) const
|
void ItemStack::serialize(std::ostream &os, bool serialize_meta) const
|
||||||
{
|
{
|
||||||
if (empty())
|
if (empty())
|
||||||
return;
|
return;
|
||||||
|
|
||||||
// Check how many parts of the itemstring are needed
|
// Check how many parts of the itemstring are needed
|
||||||
int parts = 1;
|
int parts = 1;
|
||||||
if(count != 1)
|
|
||||||
parts = 2;
|
|
||||||
if(wear != 0)
|
|
||||||
parts = 3;
|
|
||||||
if (!metadata.empty())
|
if (!metadata.empty())
|
||||||
parts = 4;
|
parts = 4;
|
||||||
|
else if (wear != 0)
|
||||||
|
parts = 3;
|
||||||
|
else if (count != 1)
|
||||||
|
parts = 2;
|
||||||
|
|
||||||
os<<serializeJsonStringIfNeeded(name);
|
os << serializeJsonStringIfNeeded(name);
|
||||||
if(parts >= 2)
|
if (parts >= 2)
|
||||||
os<<" "<<count;
|
os << " " << count;
|
||||||
if(parts >= 3)
|
if (parts >= 3)
|
||||||
os<<" "<<wear;
|
os << " " << wear;
|
||||||
if (parts >= 4) {
|
if (parts >= 4) {
|
||||||
os << " ";
|
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);
|
deSerialize(is, itemdef);
|
||||||
}
|
}
|
||||||
|
|
||||||
std::string ItemStack::getItemString() const
|
std::string ItemStack::getItemString(bool include_meta) const
|
||||||
{
|
{
|
||||||
std::ostringstream os(std::ios::binary);
|
std::ostringstream os(std::ios::binary);
|
||||||
serialize(os);
|
serialize(os, include_meta);
|
||||||
return os.str();
|
return os.str();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -40,13 +40,13 @@ struct ItemStack
|
|||||||
~ItemStack() = default;
|
~ItemStack() = default;
|
||||||
|
|
||||||
// Serialization
|
// 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.
|
// Deserialization. Pass itemdef unless you don't want aliases resolved.
|
||||||
void deSerialize(std::istream &is, IItemDefManager *itemdef = NULL);
|
void deSerialize(std::istream &is, IItemDefManager *itemdef = NULL);
|
||||||
void deSerialize(const std::string &s, IItemDefManager *itemdef = NULL);
|
void deSerialize(const std::string &s, IItemDefManager *itemdef = NULL);
|
||||||
|
|
||||||
// Returns the string used for inventory
|
// Returns the string used for inventory
|
||||||
std::string getItemString() const;
|
std::string getItemString(bool include_meta = true) const;
|
||||||
// Returns the tooltip
|
// Returns the tooltip
|
||||||
std::string getDescription(IItemDefManager *itemdef) const;
|
std::string getDescription(IItemDefManager *itemdef) const;
|
||||||
|
|
||||||
|
@ -37,6 +37,15 @@ int LuaItemStack::gc_object(lua_State *L)
|
|||||||
return 0;
|
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
|
// is_empty(self) -> true/false
|
||||||
int LuaItemStack::l_is_empty(lua_State *L)
|
int LuaItemStack::l_is_empty(lua_State *L)
|
||||||
{
|
{
|
||||||
@ -433,12 +442,9 @@ int LuaItemStack::create(lua_State *L, const ItemStack &item)
|
|||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
LuaItemStack* LuaItemStack::checkobject(lua_State *L, int narg)
|
LuaItemStack *LuaItemStack::checkobject(lua_State *L, int narg)
|
||||||
{
|
{
|
||||||
luaL_checktype(L, narg, LUA_TUSERDATA);
|
return *(LuaItemStack **)luaL_checkudata(L, narg, className);
|
||||||
void *ud = luaL_checkudata(L, narg, className);
|
|
||||||
if(!ud) luaL_typerror(L, narg, className);
|
|
||||||
return *(LuaItemStack**)ud; // unbox pointer
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void LuaItemStack::Register(lua_State *L)
|
void LuaItemStack::Register(lua_State *L)
|
||||||
@ -448,9 +454,10 @@ void LuaItemStack::Register(lua_State *L)
|
|||||||
luaL_newmetatable(L, className);
|
luaL_newmetatable(L, className);
|
||||||
int metatable = lua_gettop(L);
|
int metatable = lua_gettop(L);
|
||||||
|
|
||||||
|
// hide metatable from Lua getmetatable()
|
||||||
lua_pushliteral(L, "__metatable");
|
lua_pushliteral(L, "__metatable");
|
||||||
lua_pushvalue(L, methodtable);
|
lua_pushvalue(L, methodtable);
|
||||||
lua_settable(L, metatable); // hide metatable from Lua getmetatable()
|
lua_settable(L, metatable);
|
||||||
|
|
||||||
lua_pushliteral(L, "__index");
|
lua_pushliteral(L, "__index");
|
||||||
lua_pushvalue(L, methodtable);
|
lua_pushvalue(L, methodtable);
|
||||||
@ -460,12 +467,16 @@ void LuaItemStack::Register(lua_State *L)
|
|||||||
lua_pushcfunction(L, gc_object);
|
lua_pushcfunction(L, gc_object);
|
||||||
lua_settable(L, metatable);
|
lua_settable(L, metatable);
|
||||||
|
|
||||||
|
lua_pushliteral(L, "__tostring");
|
||||||
|
lua_pushcfunction(L, mt_tostring);
|
||||||
|
lua_settable(L, metatable);
|
||||||
|
|
||||||
lua_pop(L, 1); // drop metatable
|
lua_pop(L, 1); // drop metatable
|
||||||
|
|
||||||
luaL_openlib(L, 0, methods, 0); // fill methodtable
|
luaL_openlib(L, 0, methods, 0); // fill methodtable
|
||||||
lua_pop(L, 1); // drop 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);
|
lua_register(L, className, create_object);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -34,6 +34,9 @@ private:
|
|||||||
// garbage collector
|
// garbage collector
|
||||||
static int gc_object(lua_State *L);
|
static int gc_object(lua_State *L);
|
||||||
|
|
||||||
|
// __tostring metamethod
|
||||||
|
static int mt_tostring(lua_State *L);
|
||||||
|
|
||||||
// is_empty(self) -> true/false
|
// is_empty(self) -> true/false
|
||||||
static int l_is_empty(lua_State *L);
|
static int l_is_empty(lua_State *L);
|
||||||
|
|
||||||
|
Loading…
Reference in New Issue
Block a user