From 1f5591aae5b2ffbd4e1c96aa4ca9442857921264 Mon Sep 17 00:00:00 2001 From: Pavel Labath Date: Thu, 19 May 2011 12:59:50 +0200 Subject: c++ lua binding: replace std::function with FbTk::Slot std::function is superior, but not supported on old compilers --- src/FbTk/Luamm.cc | 11 ++++------- src/FbTk/Luamm.hh | 49 ++++++++++++++++++++++++++++++++----------------- 2 files changed, 36 insertions(+), 24 deletions(-) diff --git a/src/FbTk/Luamm.cc b/src/FbTk/Luamm.cc index a4a6eca..81a8fb3 100644 --- a/src/FbTk/Luamm.cc +++ b/src/FbTk/Luamm.cc @@ -30,7 +30,7 @@ namespace lua { const char cpp_exception_metatable[] = "lua::cpp_exception_metatable"; const char cpp_function_metatable [] = "lua::cpp_function_metatable"; const char lua_exception_namespace[] = "lua::lua_exception_namespace"; - const char this_cpp_object [] = "lua::this_cpp_object"; + const char this_cpp_object [] = "lua::this_cpp_object"; // converts C++ exceptions to strings, so lua can do something with them int exception_to_string(lua_State *l) @@ -245,7 +245,7 @@ namespace lua { newmetatable(cpp_function_metatable); pushboolean(false); rawsetfield(-2, "__metatable"); - pushdestructor(); + pushdestructor >(); rawsetfield(-2, "__gc"); pop(); @@ -399,16 +399,13 @@ namespace lua { return r; } - void state::pushclosure(const cpp_function &fn, int n) + void state::do_pushclosure(int n) { - checkstack(2); - - createuserdata(fn); rawgetfield(REGISTRYINDEX, cpp_function_metatable); setmetatable(-2); insert(-n-1); - lua_pushcclosure(cobj.get(), &closure_trampoline, n+1); + lua_pushcclosure(cobj, &closure_trampoline, n+1); } void state::rawgetfield(int index, const char *k) throw(std::bad_alloc) diff --git a/src/FbTk/Luamm.hh b/src/FbTk/Luamm.hh index 1df5825..5c8d382 100644 --- a/src/FbTk/Luamm.hh +++ b/src/FbTk/Luamm.hh @@ -27,13 +27,15 @@ #include #include +#include + +#include "Slot.hh" namespace lua { class state; typedef lua_Integer integer; typedef lua_Number number; - typedef std::function cpp_function; enum { ENVIRONINDEX = LUA_ENVIRONINDEX, @@ -175,7 +177,9 @@ namespace lua { } bool safe_compare(lua_CFunction trampoline, int index1, int index2); - public: + void do_pushclosure(int n); + + public: state(); /* @@ -244,10 +248,12 @@ namespace lua { bool newmetatable(const char *tname) { return luaL_newmetatable(cobj.get(), tname); } void newtable() { lua_newtable(cobj.get()); } void *newuserdata(size_t size) { return lua_newuserdata(cobj.get(), size); } - // cpp_function can be anything that std::function can handle, everything else remains + // Functor can be anything that FbTk::Slot can handle, everything else remains // identical - void pushclosure(const cpp_function &fn, int n); - void pushfunction(const cpp_function &fn) { pushclosure(fn, 0); } + template + void pushclosure(const Functor &fn, int n); + template + void pushfunction(const Functor &fn) { pushclosure(fn, 0); } void pushstring(const char *s) { lua_pushstring(cobj.get(), s); } void pushstring(const char *s, size_t len) { lua_pushlstring(cobj.get(), s, len); } void pushstring(const std::string &s) { lua_pushlstring(cobj.get(), s.c_str(), s.size()); } @@ -262,8 +268,7 @@ namespace lua { // std::function before we get a chance to call it. This pushes a function that simply // calls ~T when the time comes. Only set it as __gc on userdata of type T. template - void pushdestructor() - { lua_pushcfunction(cobj.get(), &destroy_cpp_object); } + void pushdestructor() { lua_pushcfunction(cobj.get(), &destroy_cpp_object); } // type c, throw everything but the kitchen sink // call() is a protected mode call, we don't allow unprotected calls @@ -279,7 +284,8 @@ namespace lua { void loadstring(const char *s) throw(lua::syntax_error, std::bad_alloc); bool next(int index); // register is a reserved word :/ - void register_fn(const char *name, const cpp_function &f) { pushfunction(f); setglobal(name); } + template + void register_fn(const char *name, const Functor &f) { pushfunction(f); setglobal(name); } void setfield(int index, const char *k); void setglobal(const char *name) { setfield(GLOBALSINDEX, name); } void settable(int index); @@ -327,15 +333,24 @@ namespace lua { }; template - T* state::createuserdata(Args&&... args) - { - stack_sentry s(*this); - - void *t = newuserdata(sizeof(T)); - new(t) T(std::forward(args)...); - ++s; - return static_cast(t); - } + T* state::createuserdata(Args&&... args) + { + stack_sentry s(*this); + + void *t = newuserdata(sizeof(T)); + new(t) T(std::forward(args)...); + ++s; + return static_cast(t); + } + + template + void state::pushclosure(const Functor &fn, int n) + { + checkstack(2); + + createuserdata >(fn); + do_pushclosure(n); + } } #endif // FBTK_LUAMM_HH -- cgit v0.11.2