diff options
-rw-r--r-- | src/main.cpp | 4 | ||||
-rw-r--r-- | src/script-squirrel.cpp | 109 | ||||
-rw-r--r-- | src/script-squirrel.h | 3 | ||||
-rw-r--r-- | src/script.h | 30 |
4 files changed, 118 insertions, 28 deletions
diff --git a/src/main.cpp b/src/main.cpp index d30501b1..db9b6ae7 100644 --- a/src/main.cpp +++ b/src/main.cpp @@ -106,14 +106,10 @@ void initialize() // Initialize scripting subsystem #ifdef SCRIPT_SUPPORT - logger->log("Script Language %s", scriptLanguage.c_str()); if (scriptLanguage == "squirrel") - { script = new ScriptSquirrel("main.nut"); - script->init(); - } #endif } diff --git a/src/script-squirrel.cpp b/src/script-squirrel.cpp index d8001de4..cb3d7601 100644 --- a/src/script-squirrel.cpp +++ b/src/script-squirrel.cpp @@ -20,7 +20,7 @@ void printfunc(HSQUIRRELVM v, const SQChar *s, ...) * 'i' = Integer * 'f' = Float */ -void functionCall(HSQUIRRELVM v, char *fn, char *args, ...) +bool functionCall(HSQUIRRELVM v, const char *fn, const char *args, ...) { int argCount = 0; va_list arglist; @@ -62,38 +62,118 @@ void functionCall(HSQUIRRELVM v, char *fn, char *args, ...) } sq_call(v, argCount + 1, 0); - } + } else + return false; sq_settop(v, top); va_end(arglist); + return true; } -ScriptSquirrel::ScriptSquirrel(const std::string &file) : - Script(file) +/* + * functionRegister + * Registers a function in Squirrel VM + */ +void functionRegister(HSQUIRRELVM v, SQFUNCTION f, const char *name) { + sq_pushroottable(v); + sq_pushstring(v, name, -1); + sq_newclosure(v, f, 0); + sq_createslot(v, -3); + sq_pop(v, 1); } -ScriptSquirrel::~ScriptSquirrel() +/* + * Test function called from Squirrel (modified form Squirrel docs) + * Prints the type of all arguments. + */ +int testFunc(HSQUIRRELVM v) { - sq_pop(vm, 1); - sq_close(vm); + int nargs = sq_gettop(v); + + for (int n = 1; n <= nargs; n++) { + printf("arg: %d is ", n); + switch (sq_gettype(v, n)) + { + case OT_NULL: + printf("null"); + break; + case OT_INTEGER: + printf("integer"); + break; + case OT_FLOAT: + printf("float"); + break; + case OT_STRING: + printf("string"); + break; + case OT_TABLE: + printf("table"); + break; + case OT_ARRAY: + printf("array"); + break; + case OT_USERDATA: + printf("userdata"); + break; + case OT_CLOSURE: + printf("closure"); + break; + case OT_NATIVECLOSURE: + printf("nativeclosure"); + break; + case OT_GENERATOR: + printf("generator"); + break; + case OT_USERPOINTER: + printf("userpointer"); + break; + default: + printf("unknown"); + } + } + printf("\n"); + sq_pushinteger(v, nargs); + return 1; } -void ScriptSquirrel::init() +/* + * Another test function + */ +int worldTime(HSQUIRRELVM v) { - vm = sq_open(2048); + sq_pushinteger(v, 10); + return 1; +} + +/******/ + +ScriptSquirrel::ScriptSquirrel(const std::string &file) : + Script(file) +{ + vm = sq_open(1024); //1024 byte stack sqstd_seterrorhandlers(vm); sq_setprintfunc(vm, printfunc); sq_pushroottable(vm); - sqstd_dofile(vm, _SC(scriptName.c_str()), 0, 1); - if (SQ_SUCCEEDED(sqstd_dofile(vm, _SC("test.nut"), 0, 1))) + if (!SQ_SUCCEEDED(sqstd_dofile(vm, _SC(scriptName.c_str()), 0, 1))) { + std::cerr << "Error: ScriptSquirrel: could not execute " << + scriptName << std::endl; + } else { + functionRegister(vm, testFunc, "printargs"); + functionRegister(vm, worldTime, "worldtime"); + + functionCall(vm, "", NULL); functionCall(vm, "init", NULL); + } } -void ScriptSquirrel::destroy() +ScriptSquirrel::~ScriptSquirrel() { functionCall(vm, "destroy", NULL); + + sq_pop(vm, 1); + sq_close(vm); } void ScriptSquirrel::update() @@ -101,6 +181,11 @@ void ScriptSquirrel::update() functionCall(vm, "update", NULL); } +bool ScriptSquirrel::execute(const std::string &functionName) +{ + return functionCall(vm, functionName.c_str(), NULL); +} + void ScriptSquirrel::message(char *msg) { functionCall(vm, "message", "s", msg); diff --git a/src/script-squirrel.h b/src/script-squirrel.h index e0413d3d..c17608ff 100644 --- a/src/script-squirrel.h +++ b/src/script-squirrel.h @@ -39,9 +39,8 @@ class ScriptSquirrel : public Script public: ScriptSquirrel(const std::string &); ~ScriptSquirrel(); - void init(); - void destroy(); void update(); + bool execute(const std::string &); void message(char *); }; diff --git a/src/script.h b/src/script.h index ea696b38..4a003611 100644 --- a/src/script.h +++ b/src/script.h @@ -27,31 +27,41 @@ #include <iostream> /* + * Script * Script provides a simple class which is a simple interface - * for defining a scripting backend. + * for defining a scripting backend. Each Script object consists + * of an independant scripting environment. + * + * Requirements of Script Object: + * - Each script object is independant from any other script object. + * - A script is to be executed upon instantiation. + * - A initialization and destruction function should be executed in + * the script if such a function is defined (the interface should + * provide default methods in case they are missing or not needed.) */ class Script { protected: + // Filename of the script corresponding to the script object std::string scriptName; public: - Script(const std::string &file) : - scriptName(file) - { - } + Script(const std::string &file) + : scriptName(file) + { } virtual ~Script() { } - //Initialization - virtual void init() = 0; - //Destruction - virtual void destroy() = 0; + //State update virtual void update() = 0; + + //Execute specified function + virtual bool execute(const std::string &) = 0; + //Script sent raw message virtual void message(char *) = 0; }; -extern Script *script; +extern Script *script; // Global script (temporary? #endif |