// https://github.com/vinniefalco/LuaBridge // // Copyright 2012, Vinnie Falco // Copyright 2007, Nathan Reed // SPDX-License-Identifier: MIT // A set of tests of different types' communication with Lua #include "TestBase.h" #include "LuaBridge/RefCountedPtr.h" #include "JuceLibraryCode/BinaryData.h" #include #include #include #include namespace LuaBridgeTests { using namespace std; using namespace luabridge; //============================================================================== /* * Test classes */ bool g_success = true; bool testSucceeded () { bool b = g_success; g_success = false; return b; } typedef int fn_type; enum { FN_CTOR, FN_DTOR, FN_STATIC, FN_VIRTUAL, FN_PROPGET, FN_PROPSET, FN_STATIC_PROPGET, FN_STATIC_PROPSET, FN_OPERATOR, NUM_FN_TYPES }; struct fn_called { bool called [NUM_FN_TYPES]; fn_called () { memset(called, 0, NUM_FN_TYPES * sizeof(bool)); } }; fn_called A_functions, B_functions; bool testAFnCalled (fn_type f) { bool b = A_functions.called[f]; A_functions.called [f] = false; return b; } bool testBFnCalled (fn_type f) { bool b = B_functions.called[f]; B_functions.called [f] = false; return b; } class A { protected: string name; mutable bool success; public: A (string const& name_) : name (name_), success (false), testProp (47) { A_functions.called [FN_CTOR] = true; } virtual ~A () { A_functions.called [FN_DTOR] = true; } virtual void testVirtual () { A_functions.called [FN_VIRTUAL] = true; } const char * getName () const { return name.c_str(); } void setSuccess () const { success = true; } bool testSucceeded () const { bool b = success; success = false; return b; } static void testStatic () { A_functions.called [FN_STATIC] = true; } int testProp; int testPropGet () const { A_functions.called [FN_PROPGET] = true; return testProp; } void testPropSet (int x) { A_functions.called [FN_PROPSET] = true; testProp = x; } static int testStaticProp; static int testStaticPropGet () { A_functions.called [FN_STATIC_PROPGET] = true; return testStaticProp; } static void testStaticPropSet (int x) { A_functions.called [FN_STATIC_PROPSET] = true; testStaticProp = x; } RefCountedPtr operator + (A const& other) { A_functions.called [FN_OPERATOR] = true; return new A (name + " + " + other.name); } }; int A::testStaticProp = 47; class B: public A { public: explicit B (string const& name_) : A (name_) { B_functions.called [FN_CTOR] = true; } virtual ~B () { B_functions.called [FN_DTOR] = true; } virtual void testVirtual () { B_functions.called [FN_VIRTUAL] = true; } static void testStatic2 () { B_functions.called [FN_STATIC] = true; } }; /* * Test functions */ int testRetInt () { return 47; } float testRetFloat () { return 47.0f; } char const* testRetConstCharPtr () { return "Hello, world"; } string testRetStdString () { static string ret ("Hello, world"); return ret; } void testParamInt (int a) { g_success = (a == 47); } void testParamBool (bool b) { g_success = b; } void testParamFloat (float f) { g_success = (f == 47.0f); } void testParamConstCharPtr (char const* str) { g_success = !strcmp (str, "Hello, world"); } void testParamStdString (string str) { g_success = !strcmp (str.c_str(), "Hello, world"); } void testParamStdStringRef (const string &str) { g_success = !strcmp (str.c_str(), "Hello, world"); } void testParamAPtr (A * a) { a->setSuccess(); } void testParamAPtrConst (A * const a) { a->setSuccess(); } void testParamConstAPtr (const A * a) { a->setSuccess(); } void testParamSharedPtrA (RefCountedPtr a) { a->setSuccess(); } RefCountedPtr testRetSharedPtrA () { static RefCountedPtr sp_A (new A("from C")); return sp_A; } RefCountedPtr testRetSharedPtrConstA () { static RefCountedPtr sp_A (new A("const A")); return sp_A; } // add our own functions and classes to a Lua environment void addToState (lua_State *L) { getGlobalNamespace (L) .addFunction ("testSucceeded", &testSucceeded) .addFunction ("testAFnCalled", &testAFnCalled) .addFunction ("testBFnCalled", &testBFnCalled) .addFunction ("testRetInt", &testRetInt) .addFunction ("testRetFloat", &testRetFloat) .addFunction ("testRetConstCharPtr", &testRetConstCharPtr) .addFunction ("testRetStdString", &testRetStdString) .addFunction ("testParamInt", &testParamInt) .addFunction ("testParamBool", &testParamBool) .addFunction ("testParamFloat", &testParamFloat) .addFunction ("testParamConstCharPtr", &testParamConstCharPtr) .addFunction ("testParamStdString", &testParamStdString) .addFunction ("testParamStdStringRef", &testParamStdStringRef) .beginClass ("A") .addConstructor > () .addFunction ("testVirtual", &A::testVirtual) .addFunction ("getName", &A::getName) .addFunction ("testSucceeded", &A::testSucceeded) .addFunction ("__add", &A::operator+) .addData ("testProp", &A::testProp) .addProperty ("testProp2", &A::testPropGet, &A::testPropSet) .addStaticFunction ("testStatic", &A::testStatic) .addStaticData ("testStaticProp", &A::testStaticProp) .addStaticProperty ("testStaticProp2", &A::testStaticPropGet, &A::testStaticPropSet) .endClass () .deriveClass ("B") .addConstructor > () .addStaticFunction ("testStatic2", &B::testStatic2) .endClass () .addFunction ("testParamAPtr", &testParamAPtr) .addFunction ("testParamAPtrConst", &testParamAPtrConst) .addFunction ("testParamConstAPtr", &testParamConstAPtr) .addFunction ("testParamSharedPtrA", &testParamSharedPtrA) .addFunction ("testRetSharedPtrA", &testRetSharedPtrA) .addFunction ("testRetSharedPtrConstA", &testRetSharedPtrConstA) ; } void resetTests () { g_success = true; A::testStaticProp = 47; } void printValue (lua_State* L, int index) { int type = lua_type (L, index); switch (type) { case LUA_TBOOLEAN: std::cerr << std::boolalpha << (lua_toboolean (L, index) != 0); break; case LUA_TSTRING: std::cerr << lua_tostring (L, index); break; case LUA_TNUMBER: std::cerr << lua_tonumber (L, index); break; case LUA_TTABLE: case LUA_TTHREAD: case LUA_TFUNCTION: std::cerr << lua_topointer (L, index); break; } std::cerr << ": " << lua_typename (L, type) << " (" << type << ")" << std::endl; } } // namespace LuaBridgeTests struct LegacyTests : TestBase { }; TEST_F (LegacyTests, AllTests) { LuaBridgeTests::addToState (L); // Execute lua files in order if (luaL_loadstring (L, BinaryData::Tests_lua) != 0) { // compile-time error FAIL () << lua_tostring (L, -1); } if (lua_pcall (L, 0, 0, -2) != 0) { // runtime error FAIL () << lua_tostring (L, -1); } }