Selene
Selene copied to clipboard
const member function support
Are const methods meant to be supported? I'm finding that adding them to an object via SetObj isn't working, and if there's a const and a non-const overload of a method, it won't work either (although I assume this is expected; I can't see a reasonable way to get function overloading to work at all!)
Is this intentional? If not, is it fixable? I'm no expert with C++11 or type magic, but this doesn't seem like a simple problem.
test case:
class Foo {
private:
int constCall() const { return 3; }
};
void main(void) {
Foo f;
sel::State state;
state["Foo"].SetObj(f, "ConstCall", &Foo::constCall);
}
Looking at the source, I can see that const data members should be handled, but I'm not sure if there's a simple way to extend this to methods.
Semi-fixed this by adding some code to Obj.h.
This allows registering const methods, but not methods that return pointers or references to const objects. However, if there is a const and a non-const version of a method, it seems to select the const overload preferentially.
template <typename Ret, typename... Args>
void _register_member(lua_State *state,
T *t,
const char *fun_name,
Ret(T::*fun)(Args...) const) { // <-- note the const
std::function<Ret(Args...)> lambda = [t, fun](Args... args) {
return (t->*fun)(args...);
};
constexpr int arity = detail::_arity<Ret>::value;
_funs.emplace_back(
new ObjFun<arity, Ret, Args...>
{state, std::string(fun_name), lambda});
}
template <typename Ret, typename... Args>
void _register_member(lua_State *state,
T *t,
const char *fun_name,
Ret(T::*fun)(Args&&...) const) { //<-- and again
std::function<Ret(Args&&...)> lambda = [t, fun](Args&&... args) {
return (t->*fun)(std::forward<Args>(args)...);
};
constexpr int arity = detail::_arity<Ret>::value;
_funs.emplace_back(
new ObjFun<arity, Ret, Args...>
{state, std::string(fun_name), lambda});
}
Const member functions were overlooked actually. There were a ton of overloads that needed matching signatures so it doesn't surprise me that there are still some missing. Selecting the const member function preferentially is a property of correct C++ function overload resolution. I think it would be a welcome addition to the library although it would also need to be added to the test suite and to the Class registration code paths for consistency.
Thanks for the quick answer. I'm going on holiday soon, but when I'm back I can attempt to fix all of that and make a pull request :)
Is there a way to force use of the non-const version of a function when both are available? I couldn't find a way to cast the function pointer to do this.
Also I didn't get the chance to look at how to get functions with return values of const reference/pointer type to work, but I'm guessing it would require making the signature something like const Ret(T::*fun)(Args...), presumably with const and non- variants for the function too? Either way, I'll try to get all the const stuff working in a week or so!
Would be nice to see a fix for this. I just ran into this issue and it took me quite a while to figure out what's going on.