diff --git a/README.md b/README.md index 9a84c92..d87cfae 100644 --- a/README.md +++ b/README.md @@ -15,7 +15,10 @@ To make a retro styled game, the whole process of creation and execution takes p ![TIC-80](https://user-images.githubusercontent.com/1101448/29687467-3ddc432e-8925-11e7-8156-5cec3700cc04.gif) ### Features -- Multiple progamming languages: Lua, Moonscript, Javascript and Wren +- Multiple progamming languages: [Lua](https://www.lua.org), + [Moonscript](https://moonscript.org), + [Javascript](https://developer.mozilla.org/en-US/docs/Web/JavaScript), + [Wren](http://wren.io/), and [Fennel](https://fennel-lang.org). - Games can have mouse and keyboard as input - Games can have up to 4 controllers as input - Builtin editors: for code, sprites, world maps, sound effects and music diff --git a/src/console.c b/src/console.c index 950508a..73e3b53 100644 --- a/src/console.c +++ b/src/console.c @@ -2216,6 +2216,16 @@ static void onConsoleResumeCommand(Console* console, const char* param) resumeRunMode(); } +static void onConsoleEvalCommand(Console* console, const char* param) +{ + printLine(console); + + const tic_script_config* script_config = console->tic->api.get_script_config(console->tic); + script_config->eval(console->tic, param); + + commandDone(console); +} + static void onAddFile(const char* name, AddResult result, void* data) { Console* console = (Console*)data; @@ -2418,6 +2428,7 @@ static const struct {"save", NULL, "save cart", onConsoleSaveCommand}, {"run", NULL, "run loaded cart", onConsoleRunCommand}, {"resume", NULL, "resume run cart", onConsoleResumeCommand}, + {"eval", "=", "run code", onConsoleEvalCommand}, {"dir", "ls", "show list of files", onConsoleDirCommand}, {"cd", NULL, "change directory", onConsoleChangeDirectory}, {"mkdir", NULL, "make directory", onConsoleMakeDirectory}, @@ -3310,4 +3321,4 @@ void initConsole(Console* console, tic_mem* tic, FileSystem* fs, Config* config, #endif console->active = !console->embed.yes; -} \ No newline at end of file +} diff --git a/src/jsapi.c b/src/jsapi.c index b99f8ce..388e7b8 100644 --- a/src/jsapi.c +++ b/src/jsapi.c @@ -1002,6 +1002,10 @@ static const tic_outline_item* getJsOutline(const char* code, s32* size) return items; } +void evalJs(tic_mem* tic, const char* code) { + printf("TODO: JS eval not yet implemented\n."); +} + static const tic_script_config JsSyntaxConfig = { .init = initJavascript, @@ -1012,6 +1016,7 @@ static const tic_script_config JsSyntaxConfig = .getOutline = getJsOutline, .parse = parseCode, + .eval = evalJs, .blockCommentStart = "/*", .blockCommentEnd = "*/", diff --git a/src/luaapi.c b/src/luaapi.c index 156e0b7..1a61080 100644 --- a/src/luaapi.c +++ b/src/luaapi.c @@ -1402,6 +1402,22 @@ static const tic_outline_item* getLuaOutline(const char* code, s32* size) return items; } +void evalLua(tic_mem* tic, const char* code) { + tic_machine* machine = (tic_machine*)tic; + lua_State* lua = machine->lua; + + lua_settop(lua, 0); + + if(luaL_loadstring(lua, code) != LUA_OK || lua_pcall(lua, 0, LUA_MULTRET, 0) != LUA_OK) + { + machine->data->error(machine->data->data, lua_tostring(lua, -1)); + } +} + +void evalPlaceholder(tic_mem* tic, const char* code) { + printf("TODO: not yet implemented\n."); +} + static const tic_script_config LuaSyntaxConfig = { .init = initLua, @@ -1412,6 +1428,7 @@ static const tic_script_config LuaSyntaxConfig = .getOutline = getLuaOutline, .parse = parseCode, + .eval = evalLua, .blockCommentStart = "--[[", .blockCommentEnd = "]]", @@ -1580,6 +1597,7 @@ static const tic_script_config MoonSyntaxConfig = .getOutline = getMoonOutline, .parse = parseCode, + .eval = evalPlaceholder, .blockCommentStart = NULL, .blockCommentEnd = NULL, @@ -1720,6 +1738,28 @@ static const tic_outline_item* getFennelOutline(const char* code, s32* size) return items; } +void evalFennel(tic_mem* tic, const char* code) { + tic_machine* machine = (tic_machine*)tic; + lua_State* fennel = machine->lua; + + lua_settop(fennel, 0); + + if (luaL_loadbuffer(fennel, execute_fennel_src, strlen(execute_fennel_src), "execute_fennel") != LUA_OK) + { + machine->data->error(machine->data->data, "failed to load fennel compiler"); + } + + lua_pushstring(fennel, code); + lua_call(fennel, 1, 1); + const char* err = lua_tostring(fennel, -1); + + if (err) + { + machine->data->error(machine->data->data, err); + } +} + + static const tic_script_config FennelSyntaxConfig = { .init = initFennel, @@ -1730,6 +1770,7 @@ static const tic_script_config FennelSyntaxConfig = .getOutline = getFennelOutline, .parse = parseCode, + .eval = evalFennel, .blockCommentStart = NULL, .blockCommentEnd = NULL, diff --git a/src/ticapi.h b/src/ticapi.h index 05c5baa..8128d9d 100644 --- a/src/ticapi.h +++ b/src/ticapi.h @@ -106,6 +106,7 @@ struct tic_script_config const tic_outline_item* (*getOutline)(const char* code, s32* size); void (*parse)(const tic_script_config* config, const char* start, u8* color, const tic_code_theme* theme); + void (*eval)(tic_mem* tic, const char* code); const char* blockCommentStart; const char* blockCommentEnd; diff --git a/src/wrenapi.c b/src/wrenapi.c index f0ae7f4..b93cda6 100644 --- a/src/wrenapi.c +++ b/src/wrenapi.c @@ -1344,6 +1344,10 @@ static const tic_outline_item* getWrenOutline(const char* code, s32* size) return items; } +void evalWren(tic_mem* tic, const char* code) { + printf("TODO: Wren eval not yet implemented\n."); +} + static const tic_script_config WrenSyntaxConfig = { .init = initWren, @@ -1354,6 +1358,7 @@ static const tic_script_config WrenSyntaxConfig = .getOutline = getWrenOutline, .parse = parseCode, + .eval = evalWren, .blockCommentStart = "/*", .blockCommentEnd = "*/",