aboutsummaryrefslogtreecommitdiffstatshomepage
path: root/ClientHamr
diff options
context:
space:
mode:
authorDavid Walter Seikel2014-04-08 01:53:49 +1000
committerDavid Walter Seikel2014-04-08 01:53:49 +1000
commite484034467394120225df9e2435a18355b97ce86 (patch)
tree4004436be1cbbed64dcc25be9dd8c918e920528e /ClientHamr
parentFix up getfenv() call for GuiLua, though it doesn't really make sense. (diff)
downloadSledjHamr-e484034467394120225df9e2435a18355b97ce86.zip
SledjHamr-e484034467394120225df9e2435a18355b97ce86.tar.gz
SledjHamr-e484034467394120225df9e2435a18355b97ce86.tar.bz2
SledjHamr-e484034467394120225df9e2435a18355b97ce86.tar.xz
Whip up a quick and dirty GuiLua test bed by cutting and pasting bits from LuaSL and test_c.
Diffstat (limited to 'ClientHamr')
-rw-r--r--ClientHamr/GuiLua/GuiLua.c341
1 files changed, 341 insertions, 0 deletions
diff --git a/ClientHamr/GuiLua/GuiLua.c b/ClientHamr/GuiLua/GuiLua.c
index d70aabc..03a7bd5 100644
--- a/ClientHamr/GuiLua/GuiLua.c
+++ b/ClientHamr/GuiLua/GuiLua.c
@@ -120,3 +120,344 @@ that has hard coded mappings between some basic "label", "button", etc.
120and ordinary elementary widgets. Proper introspection can come later. 120and ordinary elementary widgets. Proper introspection can come later.
121 121
122*/ 122*/
123
124
125
126#include <Eet.h>
127#include <Ecore.h>
128#include <Ecore_Evas.h>
129#include <Edje.h>
130#include <stdio.h>
131#include <ctype.h>
132
133#include <lua.h>
134#include <luajit.h>
135#include <lualib.h>
136#include <lauxlib.h>
137
138typedef struct _globals globals;
139
140
141#define WIDTH (300)
142#define HEIGHT (300)
143
144#define PC(...) EINA_LOG_DOM_CRIT(ourGlobals->logDom, __VA_ARGS__)
145#define PE(...) EINA_LOG_DOM_ERR(ourGlobals->logDom, __VA_ARGS__)
146#define PW(...) EINA_LOG_DOM_WARN(ourGlobals->logDom, __VA_ARGS__)
147#define PD(...) EINA_LOG_DOM_DBG(ourGlobals->logDom, __VA_ARGS__)
148#define PI(...) EINA_LOG_DOM_INFO(ourGlobals->logDom, __VA_ARGS__)
149
150#define PCm(...) EINA_LOG_DOM_CRIT(ourGlobals.logDom, __VA_ARGS__)
151#define PEm(...) EINA_LOG_DOM_ERR(ourGlobals.logDom, __VA_ARGS__)
152#define PWm(...) EINA_LOG_DOM_WARN(ourGlobals.logDom, __VA_ARGS__)
153#define PDm(...) EINA_LOG_DOM_DBG(ourGlobals.logDom, __VA_ARGS__)
154#define PIm(...) EINA_LOG_DOM_INFO(ourGlobals.logDom, __VA_ARGS__)
155
156#define D() PD("DEBUG")
157
158// "01:03:52 01-01-1973\n\0"
159#define DATE_TIME_LEN 21
160
161
162#ifndef FALSE
163// NEVER change this
164typedef enum
165{
166 FALSE = 0,
167 TRUE = 1
168} boolean;
169#endif
170
171struct _globals
172{
173 Ecore_Evas *ee; // Our window.
174 Evas *canvas; // The canvas for drawing directly onto.
175 Evas_Object *bg; // Our background edje.
176 lua_State *L; // Our Lua state.
177 int logDom;
178};
179
180
181
182static const char *ourName = "widget";
183int skang, _M;
184
185static int wfunc (lua_State *L)
186{
187 double arg1 = luaL_checknumber(L, 1);
188 const char *arg2 = luaL_checkstring(L, 2);
189
190 printf("Inside %s.wfunc(%f, %s)\n", ourName, arg1, arg2);
191 return 0;
192}
193
194
195
196char *getDateTime(struct tm **nowOut, char *dateOut, time_t *tiemOut);
197
198
199
200# define DATE_TIME_LEN 21
201
202char dateTime[DATE_TIME_LEN];
203
204static
205void _ggg_log_print_cb(const Eina_Log_Domain *d, Eina_Log_Level level, const char *file, const char *fnc, int line, const char *fmt, void *data, va_list args)
206{
207 FILE *f = data;
208 char dt[DATE_TIME_LEN + 1];
209 char fileTab[256], funcTab[256];
210
211 getDateTime(NULL, dt, NULL);
212 dt[19] = '\0';
213 if (12 > strlen(file))
214 snprintf(fileTab, sizeof(fileTab), "%s\t\t", file);
215 else
216 snprintf(fileTab, sizeof(fileTab), "%s\t", file);
217 snprintf(funcTab, sizeof(funcTab), "\t%s", fnc);
218 fprintf(f, "%s ", dt);
219 if (f == stderr)
220 eina_log_print_cb_stderr(d, level, fileTab, funcTab, line, fmt, data, args);
221 else if (f == stdout)
222 eina_log_print_cb_stdout(d, level, fileTab, funcTab, line, fmt, data, args);
223 fflush(f);
224}
225
226void loggingStartup(globals *ourGlobals)
227{
228 ourGlobals->logDom = eina_log_domain_register("GuiLua", NULL);
229 if (ourGlobals->logDom < 0)
230 {
231 EINA_LOG_CRIT("could not register log domain 'GuiLua'");
232 }
233 // TODO - should unregister this later.
234 eina_log_level_set(EINA_LOG_LEVEL_DBG);
235 eina_log_domain_level_set("GuiLua", EINA_LOG_LEVEL_DBG);
236 eina_log_print_cb_set(_ggg_log_print_cb, stderr);
237
238 // Shut up the excess debugging shit from EFL.
239 eina_log_domain_level_set("eo", EINA_LOG_LEVEL_WARN);
240 eina_log_domain_level_set("eet", EINA_LOG_LEVEL_WARN);
241 eina_log_domain_level_set("ecore", EINA_LOG_LEVEL_WARN);
242 eina_log_domain_level_set("ecore_audio", EINA_LOG_LEVEL_WARN);
243 eina_log_domain_level_set("ecore_evas", EINA_LOG_LEVEL_WARN);
244 eina_log_domain_level_set("ecore_input_evas", EINA_LOG_LEVEL_WARN);
245 eina_log_domain_level_set("ecore_system_upower", EINA_LOG_LEVEL_WARN);
246 eina_log_domain_level_set("ecore_x", EINA_LOG_LEVEL_WARN);
247 eina_log_domain_level_set("evas_main", EINA_LOG_LEVEL_WARN);
248 eina_log_domain_level_set("eldbus", EINA_LOG_LEVEL_WARN);
249}
250
251char *getDateTime(struct tm **nowOut, char *dateOut, time_t *timeOut)
252{
253 struct tm *newTime;
254 time_t szClock;
255 char *date = dateTime;
256
257 // Get time in seconds
258 time(&szClock);
259 // Convert time to struct tm form
260 newTime = localtime(&szClock);
261
262 if (nowOut)
263 *nowOut = newTime;
264 if (dateOut)
265 date = dateOut;
266 if (timeOut)
267 *timeOut = szClock;
268
269 // format
270 strftime(date, DATE_TIME_LEN, "%d/%m/%Y %H:%M:%S\r", newTime);
271 return (dateTime);
272}
273
274
275
276static void
277_on_delete(Ecore_Evas *ee /*__UNUSED__*/)
278{
279 ecore_main_loop_quit();
280}
281
282
283/* local widget = require 'widget'
284
285Lua's require() function will strip any stuff from the front of the name
286separated by a hyphen, so 'ClientHamr-GuiLua-test_c' -> 'test_c'. Then
287it will search through a path, and eventually find this test_c.so (or
288test_c.dll or whatever), then call luaopen_test_c(), which should return
289a table. The argument (only thing on the stack) for this function will
290be 'test_c'.
291
292Normally luaL_register() creates a table of functions, that is the table
293returned, but we want to do something different with skang.
294*/
295int luaopen_widget(lua_State *L)
296{
297 lua_Number i;
298
299 // In theory, the only thing on the stack now is 'widget' from the require() call.
300
301// pseudo-indices, special tables that can be accessed like the stack -
302// LUA_GLOBALSINDEX - thread environment, where globals are
303// LUA_ENVIRONINDEX - C function environment, in this case luaopen_test_c() is the C function
304// LUA_REGISTRYINDEX - C registry, global, for unique keys use the module name as a string, or a lightuserdata address to a C object in our module.
305// lua_upvalueindex(n) - C function upvalues
306
307// The only locals we care about are skang and _M.
308// All modules go into package.loaded[name] as well.
309// skang is essentially a global anyway.
310// _M we pass back as the result, and our functions get added to it by skang.thingasm()
311// Not entirely true, _M is a proxy table, getmetatable(_M).__values[cfunc] would be our function.
312
313// local skang = require 'skang'
314 lua_getglobal(L, "require");
315 lua_pushstring(L, "skang");
316 lua_call(L, 1, 1);
317 skang = lua_gettop(L);
318
319// local _M = skang.moduleBegin('widget', nil, 'Copyright 2014 David Seikel', '0.1', '2014-04-08 00:42:00', nil, false)
320 lua_getfield(L, skang, "moduleBegin");
321 lua_pushstring(L, ourName);
322 lua_pushnil(L); // Author comes from copyright.
323 lua_pushstring(L, "Copyright 2014 David Seikel");
324 lua_pushstring(L, "0.1");
325 lua_pushstring(L, "2014-04-08 00:42:00");
326 lua_pushnil(L); // No skin.
327 lua_pushboolean(L, 0); // We are not a Lua module.
328 lua_call(L, 7, 1); // call 'skang.moduleBegin' with 7 arguments and 1 result.
329
330 _M = lua_gettop(L);
331 // Save this module in the C registry.
332 lua_setfield(L, LUA_REGISTRYINDEX, ourName);
333
334// This uses function{} style.
335// skang.thingasm{_M, 'wfooble,c', 'wfooble help text', 1, widget=\"'edit', 'The wfooble:', 1, 1, 10, 50\", required=true}
336 lua_getfield(L, skang, "thingasm");
337 i = 1;
338 lua_newtable(L);
339 lua_pushnumber(L, i++);
340 lua_getfield(L, LUA_REGISTRYINDEX, ourName); // Coz getfenv() can't find C environment.
341 lua_settable(L, -3);
342
343 lua_pushnumber(L, i++);
344 lua_pushstring(L, "wfooble,w");
345 lua_settable(L, -3);
346
347 lua_pushnumber(L, i++);
348 lua_pushstring(L, "wfooble help text");
349 lua_settable(L, -3);
350
351 lua_pushnumber(L, i++);
352 lua_pushnumber(L, 1);
353 lua_settable(L, -3);
354
355 lua_pushstring(L, "'edit', 'The wfooble:', 1, 1, 10, 50");
356 lua_setfield(L, -2, "widget");
357 lua_pushboolean(L, 1); // Is required.
358 lua_setfield(L, -2, "required");
359 lua_call(L, 1, 0);
360
361// skang.thing(_M, 'wbar', 'Help text', 'Default')
362 lua_getfield(L, skang, "thingasm");
363 lua_getfield(L, LUA_REGISTRYINDEX, ourName); // Coz getfenv() can't find C environment.
364 lua_pushstring(L, "wbar");
365 lua_pushstring(L, "Help text");
366 lua_pushstring(L, "Default");
367 lua_call(L, 4, 0);
368
369// skang.thingasm(_M, 'cfoo')
370 lua_getfield(L, skang, "thingasm");
371 lua_getfield(L, LUA_REGISTRYINDEX, ourName); // Coz getfenv() can't find C environment.
372 lua_pushstring(L, "wfoo");
373 lua_call(L, 2, 0);
374
375// skang.thingasm(_M, 'cfunc', 'cfunc does nothing really', cfunc, 'number,string')
376 lua_getfield(L, skang, "thingasm");
377 lua_getfield(L, LUA_REGISTRYINDEX, ourName); // Coz getfenv() can't find C environment.
378 lua_pushstring(L, "wfunc");
379 lua_pushstring(L, "wfunc does nothing really");
380 lua_pushcfunction(L, wfunc);
381 lua_pushstring(L, "number,string");
382 lua_call(L, 5, 0);
383
384// skang.moduleEnd(_M)
385 lua_getfield(L, skang, "moduleEnd");
386 lua_getfield(L, LUA_REGISTRYINDEX, ourName);
387 lua_call(L, 1, 1);
388
389 return 1;
390}
391
392
393int main(int argc, char **argv)
394{
395 globals ourGlobals;
396 int result = EXIT_FAILURE;
397
398 memset(&ourGlobals, 0, sizeof(globals));
399
400 if (eina_init())
401 {
402 loggingStartup(&ourGlobals);
403
404 PIm("GuiLua running as an application.\n");
405
406 if (ecore_evas_init())
407 {
408 if (edje_init())
409 {
410 /* this will give you a window with an Evas canvas under the first engine available */
411 ourGlobals.ee = ecore_evas_new(NULL, 0, 0, WIDTH, HEIGHT, NULL);
412 if (!ourGlobals.ee)
413 {
414 PEm("You got to have at least one evas engine built and linked up to ecore-evas for this example to run properly.");
415 edje_shutdown();
416 ecore_evas_shutdown();
417 return -1;
418 }
419 ourGlobals.canvas = ecore_evas_get(ourGlobals.ee);
420 ecore_evas_title_set(ourGlobals.ee, "GuiLua test harness");
421 ecore_evas_show(ourGlobals.ee);
422
423 ourGlobals.bg = evas_object_rectangle_add(ourGlobals.canvas);
424 evas_object_color_set(ourGlobals.bg, 255, 255, 255, 255); /* white bg */
425 evas_object_move(ourGlobals.bg, 0, 0); /* at canvas' origin */
426 evas_object_size_hint_weight_set(ourGlobals.bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND);
427 evas_object_resize(ourGlobals.bg, WIDTH, HEIGHT); /* covers full canvas */
428 evas_object_show(ourGlobals.bg);
429 ecore_evas_object_associate(ourGlobals.ee, ourGlobals.bg, ECORE_EVAS_OBJECT_ASSOCIATE_BASE);
430 evas_object_focus_set(ourGlobals.bg, EINA_TRUE);
431
432 // Setup our callbacks.
433 ecore_evas_callback_delete_request_set(ourGlobals.ee, _on_delete);
434
435 ourGlobals.L = luaL_newstate();
436 if (ourGlobals.L)
437 {
438 luaL_openlibs(ourGlobals.L);
439 luaopen_widget(ourGlobals.L);
440
441 ecore_main_loop_begin();
442
443 lua_close(ourGlobals.L);
444 ecore_evas_free(ourGlobals.ee);
445 }
446 else
447 PCm("Failed to start Lua!");
448
449 edje_shutdown();
450 }
451 else
452 PCm("Failed to init edje!");
453
454 ecore_evas_shutdown();
455 }
456 else
457 PCm("Failed to init ecore_evas!");
458 }
459 else
460 fprintf(stderr, "Failed to init eina!");
461
462 return result;
463}