From 90a85c0d8def4e9b5d847124a80506c1ceab76c3 Mon Sep 17 00:00:00 2001 From: David Walter Seikel Date: Sun, 22 Apr 2012 09:21:55 +1000 Subject: Some actual extantz source code. With test data for now. --- ClientHamr/extantz/README | 58 +- ClientHamr/extantz/extantz.c | 868 ++++++++++++++++++++++++++++ ClientHamr/extantz/images/animated_logo.gif | Bin 0 -> 81411 bytes ClientHamr/extantz/images/bubble.png | Bin 0 -> 4878 bytes ClientHamr/extantz/images/bubble_sh.png | Bin 0 -> 1600 bytes ClientHamr/extantz/images/logo.png | Bin 0 -> 81162 bytes ClientHamr/extantz/images/logo_small.png | Bin 0 -> 5655 bytes ClientHamr/extantz/images/plant_01.jpg | Bin 0 -> 165867 bytes ClientHamr/extantz/images/pt.png | Bin 0 -> 875 bytes ClientHamr/extantz/images/rock_01.jpg | Bin 0 -> 330094 bytes ClientHamr/extantz/images/rock_02.jpg | Bin 0 -> 285555 bytes ClientHamr/extantz/images/sky_01.jpg | Bin 0 -> 134813 bytes ClientHamr/extantz/images/sky_02.jpg | Bin 0 -> 31413 bytes ClientHamr/extantz/images/sky_03.jpg | Bin 0 -> 73364 bytes ClientHamr/extantz/images/sky_04.jpg | Bin 0 -> 25078 bytes ClientHamr/extantz/images/wood_01.jpg | Bin 0 -> 96136 bytes ClientHamr/extantz/make.sh | 3 + 17 files changed, 928 insertions(+), 1 deletion(-) create mode 100644 ClientHamr/extantz/extantz.c create mode 100644 ClientHamr/extantz/images/animated_logo.gif create mode 100644 ClientHamr/extantz/images/bubble.png create mode 100644 ClientHamr/extantz/images/bubble_sh.png create mode 100644 ClientHamr/extantz/images/logo.png create mode 100644 ClientHamr/extantz/images/logo_small.png create mode 100644 ClientHamr/extantz/images/plant_01.jpg create mode 100644 ClientHamr/extantz/images/pt.png create mode 100644 ClientHamr/extantz/images/rock_01.jpg create mode 100644 ClientHamr/extantz/images/rock_02.jpg create mode 100644 ClientHamr/extantz/images/sky_01.jpg create mode 100644 ClientHamr/extantz/images/sky_02.jpg create mode 100644 ClientHamr/extantz/images/sky_03.jpg create mode 100644 ClientHamr/extantz/images/sky_04.jpg create mode 100644 ClientHamr/extantz/images/wood_01.jpg create mode 100755 ClientHamr/extantz/make.sh diff --git a/ClientHamr/extantz/README b/ClientHamr/extantz/README index b6ba67a..ddd284a 100644 --- a/ClientHamr/extantz/README +++ b/ClientHamr/extantz/README @@ -38,7 +38,7 @@ custom viewers, but the user wants to use a more generic viewer for all the other grids. Or if the user wants to use one viewer for OpenSim grids, but another for LL (Linden Labs) grids. Coz perhaps their chosen viewer is not TPVP (Third Party Viewer Policy, an LL thing) compliant, -and Ll are just more anal than the rest of the universe. +and LL are just more anal than the rest of the universe. The grid manager will also include some sort of search capability, as is currently being discussed by various people in the OpenSim universe. @@ -102,6 +102,62 @@ which is different from the "gets out of the way" it usually does, still running, just not on screen. +The problem with the web. +------------------------- +At least that's the theory. In practice, a web browser takes up almost +one third of the viewer, and is only used for three things. Login +pages, simple built in browser window, and MOAP (Media On A Prim). For +the first two full blown web browsers are massive overkill. MOAP is not +supported by meta-impy yet anyway. +WebKit is a pain to compile at the moment, for reasons I wont go into +right now. At the opposite of the spectrum is dillo, which is not quite +up to spec enough for login pages that have fancy stuff. There does not +appear to be any middle ground. So right now, I'll work on using random +web browsers as external windows. That will suffice for everything but +MOAP, which I can leave until later. + +The web is a bloated mess, so it's not surprising that a fully featured +web browser component like WebKit is also a bloated mess. + + +Design. +------- + +A thin window on the left. + +Menus across the top. +View tabs. + Grids Accounts Viewers Landmarks + +Grids tab is the grid manager, though you can also drill down / tree out +the accounts list per grid. + +Accounts shows accounts, though can drill down to grid list per account. +Also consider launching thin viewers, text only ones and such. The +account view is almost a natural for extending into a IM style thingy. + +Viewers lists the installed viewers, can install more, and allows +preferences editing. It can handle viewer installs, upgrades, even +compiling them from source. + +Landmarks manages LMs from viewers, or log in spots, or SLURLs etc. + +A user configurable web browser can open up to fill the right of the +screen. + +Might be good to allow Lua scripting. One way of dealing with viewer +prefs perhaps? Certainly think about Lua for the UI, and a built in +editor, etc. ala skang. All the fancy stuff like development and such +should be kept in some sort of module, so as not to bloat the main +proggy. See if it's possible to disable the Emerald/Phoenix/Firestorm +LSL bridge when connecting to OpenSim. See if we can do it from Lua, +with some sort of generic Lua system for munging things. + +Log file management features, including viewer stdout, check if only +Linux viewers do that. Including chat logs. + +Dillo and uzbl can insert themselves into the windows of others. Should +check that out. diff --git a/ClientHamr/extantz/extantz.c b/ClientHamr/extantz/extantz.c new file mode 100644 index 0000000..3f6a296 --- /dev/null +++ b/ClientHamr/extantz/extantz.c @@ -0,0 +1,868 @@ +#include +#ifndef M_PI +#define M_PI 3.14159265 +#endif + +typedef enum +{ + EZP_NONE, + EZP_AURORA, + EZP_OPENSIM, + EZP_SECOND_LIFE, + EZP_SLEDJHAMR, + EZP_TRITIUM +} ezPlatform; + +typedef struct +{ + char *name; + char *version; // Version string. + char *path; // OS filesystem path to the viewer install. + char *icon; + uint16_t tag; // The UUID of the texture used in the avatar bake hack. + uint8_t r, g, b; // Colour used for the in world tag. +} ezViewer; + +typedef struct +{ + Eina_Clist accounts; + Eina_Clist landmarks; + char *name; + char *loginURI; + char *splashPage; + char *helperURI; + char *website; + char *supportPage; + char *registerPage; + char *passwordPage; + char *icon; + ezPlatform platform; + ezViewer *viewer; + Elm_Object_Item *item; +} ezGrid; + +typedef struct +{ + Eina_Clist grid; + char *name; + char *password; // Think we need to pass unencrypted passwords to the viewer. B-( + char *icon; + ezViewer *viewer; +} ezAccount; + +typedef struct +{ + Eina_Clist grid; + char *name; + char *sim; + char *screenshot; + short x, y, z; +} ezLandmark; + +Eina_Hash *grids; +Eina_Hash *viewers; + +static char *gridTest[][3] = +{ + {"3rd Rock Grid", "http://grid.3rdrockgrid.com:8002/", "http://grid.3rdrockgrid.com/3rg_login"}, + {"Infinite Grid", "http://grid.infinitegrid.org:8002/", "http://www.infinitegrid.org/loginscreen.php"}, + {"Second Life Grid", "https://login.agni.lindenlab.com/cgi-bin/login.cgi", "http://secondlife.com/"}, + {NULL, NULL, NULL} +}; + +static char *accountTest[][3] = +{ + {"3rd Rock Grid", "onefang rejected", "password"}, + {"Infinite Grid", "infinite onefang", "MyB1GSecrit"}, + {"Infinite Grid", "onefang rejected", "MySecrit"}, + {NULL, NULL, NULL} +}; + + +static Elm_Genlist_Item_Class *grid_gic = NULL; +static Elm_Genlist_Item_Class *account_gic = NULL; + +static int x, y, w, h; + + +static const char *img0 = PACKAGE_DATA_DIR "/images/logo.png"; +static const char *img1 = PACKAGE_DATA_DIR "/images/plant_01.jpg"; +static const char *img2 = PACKAGE_DATA_DIR "/images/rock_01.jpg"; +static const char *img3 = PACKAGE_DATA_DIR "/images/sky_01.jpg"; + + +typedef struct _Gear Gear; +typedef struct _GLData GLData; +struct _Gear +{ + GLfloat *vertices; + GLuint vbo; + int count; +}; + +// GL related data here.. +struct _GLData +{ + Evas_GL_API *glapi; + GLuint program; + GLuint vtx_shader; + GLuint fgmt_shader; + int initialized : 1; + int mouse_down : 1; + + // Gear Stuff + GLfloat view_rotx; + GLfloat view_roty; + GLfloat view_rotz; + + Gear *gear1; + Gear *gear2; + Gear *gear3; + + GLfloat angle; + + GLuint proj_location; + GLuint light_location; + GLuint color_location; + + GLfloat proj[16]; + GLfloat light[3]; +}; + +static void gears_init(GLData *gld); +static void free_gear(Gear *gear); +static void gears_reshape(GLData *gld, int width, int height); +static void render_gears(GLData *gld); + +//--------------------------------// +// Gear Stuff.... +static GLfloat *vert(GLfloat *p, GLfloat x, GLfloat y, GLfloat z, GLfloat *n) +{ + p[0] = x; + p[1] = y; + p[2] = z; + p[3] = n[0]; + p[4] = n[1]; + p[5] = n[2]; + + return p + 6; +} + +/* Draw a gear wheel. You'll probably want to call this function when + * building a display list since we do a lot of trig here. + * + * Input: inner_radius - radius of hole at center + * outer_radius - radius at center of teeth + * width - width of gear + * teeth - number of teeth + * tooth_depth - depth of tooth + */ +static Gear *make_gear(GLData *gld, GLfloat inner_radius, GLfloat outer_radius, GLfloat width, GLint teeth, GLfloat tooth_depth) +{ + GLint i; + GLfloat r0, r1, r2; + GLfloat da; + GLfloat *v; + Gear *gear; + double s[5], c[5]; + GLfloat normal[3]; + const int tris_per_tooth = 20; + Evas_GL_API *gl = gld->glapi; + + gear = (Gear*)malloc(sizeof(Gear)); + if (gear == NULL) + return NULL; + + r0 = inner_radius; + r1 = outer_radius - tooth_depth / 2.0; + r2 = outer_radius + tooth_depth / 2.0; + + da = 2.0 * M_PI / teeth / 4.0; + + gear->vertices = calloc(teeth * tris_per_tooth * 3 * 6, sizeof *gear->vertices); + s[4] = 0; + c[4] = 1; + v = gear->vertices; + for (i = 0; i < teeth; i++) + { + s[0] = s[4]; + c[0] = c[4]; + s[1] = sin(i * 2.0 * M_PI / teeth + da); + c[1] = cos(i * 2.0 * M_PI / teeth + da); + s[2] = sin(i * 2.0 * M_PI / teeth + da * 2); + c[2] = cos(i * 2.0 * M_PI / teeth + da * 2); + s[3] = sin(i * 2.0 * M_PI / teeth + da * 3); + c[3] = cos(i * 2.0 * M_PI / teeth + da * 3); + s[4] = sin(i * 2.0 * M_PI / teeth + da * 4); + c[4] = cos(i * 2.0 * M_PI / teeth + da * 4); + + normal[0] = 0.0; + normal[1] = 0.0; + normal[2] = 1.0; + + v = vert(v, r2 * c[1], r2 * s[1], width * 0.5, normal); + + v = vert(v, r2 * c[1], r2 * s[1], width * 0.5, normal); + v = vert(v, r2 * c[2], r2 * s[2], width * 0.5, normal); + v = vert(v, r1 * c[0], r1 * s[0], width * 0.5, normal); + v = vert(v, r1 * c[3], r1 * s[3], width * 0.5, normal); + v = vert(v, r0 * c[0], r0 * s[0], width * 0.5, normal); + v = vert(v, r1 * c[4], r1 * s[4], width * 0.5, normal); + v = vert(v, r0 * c[4], r0 * s[4], width * 0.5, normal); + + v = vert(v, r0 * c[4], r0 * s[4], width * 0.5, normal); + v = vert(v, r0 * c[0], r0 * s[0], width * 0.5, normal); + v = vert(v, r0 * c[4], r0 * s[4], -width * 0.5, normal); + v = vert(v, r0 * c[0], r0 * s[0], -width * 0.5, normal); + + normal[0] = 0.0; + normal[1] = 0.0; + normal[2] = -1.0; + + v = vert(v, r0 * c[4], r0 * s[4], -width * 0.5, normal); + + v = vert(v, r0 * c[4], r0 * s[4], -width * 0.5, normal); + v = vert(v, r1 * c[4], r1 * s[4], -width * 0.5, normal); + v = vert(v, r0 * c[0], r0 * s[0], -width * 0.5, normal); + v = vert(v, r1 * c[3], r1 * s[3], -width * 0.5, normal); + v = vert(v, r1 * c[0], r1 * s[0], -width * 0.5, normal); + v = vert(v, r2 * c[2], r2 * s[2], -width * 0.5, normal); + v = vert(v, r2 * c[1], r2 * s[1], -width * 0.5, normal); + + v = vert(v, r1 * c[0], r1 * s[0], width * 0.5, normal); + + v = vert(v, r1 * c[0], r1 * s[0], width * 0.5, normal); + v = vert(v, r1 * c[0], r1 * s[0], -width * 0.5, normal); + v = vert(v, r2 * c[1], r2 * s[1], width * 0.5, normal); + v = vert(v, r2 * c[1], r2 * s[1], -width * 0.5, normal); + v = vert(v, r2 * c[2], r2 * s[2], width * 0.5, normal); + v = vert(v, r2 * c[2], r2 * s[2], -width * 0.5, normal); + v = vert(v, r1 * c[3], r1 * s[3], width * 0.5, normal); + v = vert(v, r1 * c[3], r1 * s[3], -width * 0.5, normal); + v = vert(v, r1 * c[4], r1 * s[4], width * 0.5, normal); + v = vert(v, r1 * c[4], r1 * s[4], -width * 0.5, normal); + + v = vert(v, r1 * c[4], r1 * s[4], -width * 0.5, normal); + } + + gear->count = (v - gear->vertices) / 6; + + gl->glGenBuffers(1, &gear->vbo); + gl->glBindBuffer(GL_ARRAY_BUFFER, gear->vbo); + gl->glBufferData(GL_ARRAY_BUFFER, gear->count * 6 * 4, gear->vertices, GL_STATIC_DRAW); + + + return gear; +} + +static void free_gear(Gear *gear) +{ + free(gear->vertices); + free(gear); + gear = NULL; +} + +static void multiply(GLfloat *m, const GLfloat *n) +{ + GLfloat tmp[16]; + const GLfloat *row, *column; + div_t d; + int i, j; + + for (i = 0; i < 16; i++) + { + tmp[i] = 0; + d = div(i, 4); + row = n + d.quot * 4; + column = m + d.rem; + for (j = 0; j < 4; j++) + tmp[i] += row[j] * column[j * 4]; + } + memcpy(m, &tmp, sizeof tmp); +} + +static void rotate(GLfloat *m, GLfloat angle, GLfloat x, GLfloat y, GLfloat z) +{ + double s, c; + + s = sin(angle); + c = cos(angle); + GLfloat r[16] = + { + x * x * (1 - c) + c, y * x * (1 - c) + z * s, x * z * (1 - c) - y * s, 0, + x * y * (1 - c) - z * s, y * y * (1 - c) + c, y * z * (1 - c) + x * s, 0, + x * z * (1 - c) + y * s, y * z * (1 - c) - x * s, z * z * (1 - c) + c, 0, + 0, 0, 0, 1 + }; + + multiply(m, r); +} + +static void translate(GLfloat *m, GLfloat x, GLfloat y, GLfloat z) +{ + GLfloat t[16] = { 1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 0, x, y, z, 1 }; + + multiply(m, t); +} + +static void draw_gear(GLData *gld, Gear *gear, GLfloat *m, GLfloat x, GLfloat y, GLfloat angle, const GLfloat *color) +{ + Evas_GL_API *gl = gld->glapi; + GLfloat tmp[16]; + + memcpy(tmp, m, sizeof tmp); + translate(tmp, x, y, 0); + rotate(tmp, 2 * M_PI * angle / 360.0, 0, 0, 1); + gl->glUniformMatrix4fv(gld->proj_location, 1, GL_FALSE, tmp); + gl->glUniform3fv(gld->light_location, 1, gld->light); + gl->glUniform4fv(gld->color_location, 1, color); + + gl->glBindBuffer(GL_ARRAY_BUFFER, gear->vbo); + + gl->glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 6 * sizeof(GLfloat), NULL); + gl->glVertexAttribPointer(1, 3, GL_FLOAT, GL_FALSE, 6 * sizeof(GLfloat), (GLfloat *) 0 + 3); + gl->glEnableVertexAttribArray(0); + gl->glEnableVertexAttribArray(1); + gl->glDrawArrays(GL_TRIANGLE_STRIP, 0, gear->count); +} + +static void gears_draw(GLData *gld) +{ + Evas_GL_API *gl = gld->glapi; + + static const GLfloat red[4] = { 0.8, 0.1, 0.0, 1.0 }; + static const GLfloat green[4] = { 0.0, 0.8, 0.2, 1.0 }; + static const GLfloat blue[4] = { 0.2, 0.2, 1.0, 1.0 }; + GLfloat m[16]; + + gl->glClearColor(0.8, 0.8, 0.1, 0.5); + gl->glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); + + memcpy(m, gld->proj, sizeof m); + rotate(m, 2 * M_PI * gld->view_rotx / 360.0, 1, 0, 0); + rotate(m, 2 * M_PI * gld->view_roty / 360.0, 0, 1, 0); + rotate(m, 2 * M_PI * gld->view_rotz / 360.0, 0, 0, 1); + + draw_gear(gld, gld->gear1, m, -3.0, -2.0, gld->angle, red); + draw_gear(gld, gld->gear2, m, 3.1, -2.0, -2 * gld->angle - 9.0, green); + draw_gear(gld, gld->gear3, m, -3.1, 4.2, -2 * gld->angle - 25.0, blue); +} + +static void render_gears(GLData *gld) +{ + gears_draw(gld); + + gld->angle += 2.0; +} + +/* new window size or exposure */ +static void gears_reshape(GLData *gld, int width, int height) +{ + Evas_GL_API *gl = gld->glapi; + + GLfloat ar, m[16] = { + 1.0, 0.0, 0.0, 0.0, + 0.0, 1.0, 0.0, 0.0, + 0.0, 0.0, 0.1, 0.0, + 0.0, 0.0, 0.0, 1.0 + }; + + if (width < height) + ar = width; + else + ar = height; + + m[0] = 0.1 * ar / width; + m[5] = 0.1 * ar / height; + memcpy(gld->proj, m, sizeof gld->proj); + gl->glViewport(0, 0, (GLint) width, (GLint) height); +} + +static const char vertex_shader[] = + "uniform mat4 proj;\n" + "attribute vec4 position;\n" + "attribute vec4 normal;\n" + "varying vec3 rotated_normal;\n" + "varying vec3 rotated_position;\n" + "vec4 tmp;\n" + "void main()\n" + "{\n" + " gl_Position = proj * position;\n" + " rotated_position = gl_Position.xyz;\n" + " tmp = proj * normal;\n" + " rotated_normal = tmp.xyz;\n" + "}\n"; + + static const char fragment_shader[] = + "#ifdef GL_ES\n" + "precision mediump float;\n" + "#endif\n" + "uniform vec4 color;\n" + "uniform vec3 light;\n" + "varying vec3 rotated_normal;\n" + "varying vec3 rotated_position;\n" + "vec3 light_direction;\n" + "vec4 white = vec4(0.5, 0.5, 0.5, 1.0);\n" + "void main()\n" + "{\n" + " light_direction = normalize(light - rotated_position);\n" + " gl_FragColor = color + white * dot(light_direction, rotated_normal);\n" + "}\n"; + +static void gears_init(GLData *gld) +{ + Evas_GL_API *gl = gld->glapi; + + const char *p; + char msg[512]; + + gl->glEnable(GL_CULL_FACE); + gl->glEnable(GL_DEPTH_TEST); + + p = vertex_shader; + gld->vtx_shader = gl->glCreateShader(GL_VERTEX_SHADER); + gl->glShaderSource(gld->vtx_shader, 1, &p, NULL); + gl->glCompileShader(gld->vtx_shader); + gl->glGetShaderInfoLog(gld->vtx_shader, sizeof msg, NULL, msg); + printf("vertex shader info: %s\n", msg); + + p = fragment_shader; + gld->fgmt_shader = gl->glCreateShader(GL_FRAGMENT_SHADER); + gl->glShaderSource(gld->fgmt_shader, 1, &p, NULL); + gl->glCompileShader(gld->fgmt_shader); + gl->glGetShaderInfoLog(gld->fgmt_shader, sizeof msg, NULL, msg); + printf("fragment shader info: %s\n", msg); + + gld->program = gl->glCreateProgram(); + gl->glAttachShader(gld->program, gld->vtx_shader); + gl->glAttachShader(gld->program, gld->fgmt_shader); + gl->glBindAttribLocation(gld->program, 0, "position"); + gl->glBindAttribLocation(gld->program, 1, "normal"); + + gl->glLinkProgram(gld->program); + gl->glGetProgramInfoLog(gld->program, sizeof msg, NULL, msg); + printf("info: %s\n", msg); + + gl->glUseProgram(gld->program); + gld->proj_location = gl->glGetUniformLocation(gld->program, "proj"); + gld->light_location = gl->glGetUniformLocation(gld->program, "light"); + gld->color_location = gl->glGetUniformLocation(gld->program, "color"); + + /* make the gears */ + gld->gear1 = make_gear(gld, 1.0, 4.0, 1.0, 20, 0.7); + gld->gear2 = make_gear(gld, 0.5, 2.0, 2.0, 10, 0.7); + gld->gear3 = make_gear(gld, 1.3, 2.0, 0.5, 10, 0.7); +} + +static void gldata_init(GLData *gld) +{ + gld->initialized = 0; + gld->mouse_down = 0; + + gld->view_rotx = -20.0; + gld->view_roty = -30.0; + gld->view_rotz = 0.0; + gld->angle = 0.0; + + gld->light[0] = 1.0; + gld->light[1] = 1.0; + gld->light[2] = -5.0; +} + + +//-------------------------// + +static void _init_gl(Evas_Object *obj) +{ + GLData *gld = evas_object_data_get(obj, "gld"); + + gears_init(gld); +} + +static void _del_gl(Evas_Object *obj) +{ + GLData *gld = evas_object_data_get(obj, "gld"); + if (!gld) + { + printf("Unable to get GLData. \n"); + return; + } + Evas_GL_API *gl = gld->glapi; + + gl->glDeleteShader(gld->vtx_shader); + gl->glDeleteShader(gld->fgmt_shader); + gl->glDeleteProgram(gld->program); + gl->glDeleteBuffers(1, &gld->gear1->vbo); + gl->glDeleteBuffers(1, &gld->gear2->vbo); + gl->glDeleteBuffers(1, &gld->gear3->vbo); + + free_gear(gld->gear1); + free_gear(gld->gear2); + free_gear(gld->gear3); + + evas_object_data_del((Evas_Object*)obj, "..gld"); + free(gld); +} + +static void _resize_gl(Evas_Object *obj) +{ + int w, h; + GLData *gld = evas_object_data_get(obj, "gld"); + + elm_glview_size_get(obj, &w, &h); + + // GL Viewport stuff. you can avoid doing this if viewport is all the + // same as last frame if you want + gears_reshape(gld, w, h); +} + +static void _draw_gl(Evas_Object *obj) +{ + Evas_GL_API *gl = elm_glview_gl_api_get(obj); + GLData *gld = evas_object_data_get(obj, "gld"); + if (!gld) return; + + render_gears(gld); + gl->glFinish(); +} + +static Eina_Bool _anim(void *data) +{ + elm_glview_changed_set(data); + return EINA_TRUE; +} + +static void _del(void *data , Evas *evas , Evas_Object *obj, void *event_info ) +{ + Ecore_Animator *ani = evas_object_data_get(obj, "ani"); + ecore_animator_del(ani); +} + +static void _key_down(void *data , Evas *e , Evas_Object *obj, void *event_info) +{ + Evas_Event_Key_Down *ev; + ev = (Evas_Event_Key_Down *)event_info; + GLData *gld = evas_object_data_get(obj, "gld"); + + if (strcmp(ev->keyname, "Left") == 0) + { + gld->view_roty += 5.0; + return; + } + + if (strcmp(ev->keyname, "Right") == 0) + { + gld->view_roty -= 5.0; + return; + } + + if (strcmp(ev->keyname, "Up") == 0) + { + gld->view_rotx += 5.0; + return; + } + + if (strcmp(ev->keyname, "Down") == 0) + { + gld->view_rotx -= 5.0; + return; + } + if ((strcmp(ev->keyname, "Escape") == 0) || + (strcmp(ev->keyname, "Return") == 0)) + { + //_on_done(data, obj, event_info); + return; + } +} + +static void _mouse_down(void *data , Evas *e , Evas_Object *obj, void *event_info ) +{ + GLData *gld = evas_object_data_get(obj, "gld"); + gld->mouse_down = 1; +} + +static void _mouse_move(void *data , Evas *e , Evas_Object *obj, void *event_info ) +{ + Evas_Event_Mouse_Move *ev; + ev = (Evas_Event_Mouse_Move *)event_info; + GLData *gld = evas_object_data_get(obj, "gld"); + float dx = 0, dy = 0; + + if (gld->mouse_down) + { + dx = ev->cur.canvas.x - ev->prev.canvas.x; + dy = ev->cur.canvas.y - ev->prev.canvas.y; + + gld->view_roty += -1.0 * dx; + gld->view_rotx += -1.0 * dy; + } +} + +static void _mouse_up(void *data , Evas *e , Evas_Object *obj, void *event_info ) +{ + GLData *gld = evas_object_data_get(obj, "gld"); + gld->mouse_down = 0; +} + +static Evas_Object *_content_image_new(Evas_Object *parent, const char *img) +{ + Evas_Object *ic; + + ic = elm_icon_add(parent); + elm_icon_file_set(ic, img, NULL); + return ic; +} + +static void _promote(void *data, Evas_Object *obj , void *event_info ) +{ + elm_naviframe_item_promote(data); +} + +static void _on_done(void *data, Evas_Object *obj, void *event_info) +{ + evas_object_del((Evas_Object*)data); + elm_exit(); +} + +static char *_grid_label_get(void *data, Evas_Object *obj, const char *part) +{ + ezGrid *thisGrid = data; + char buf[256]; + + if (!strcmp(part, "elm.text")) + { + int count = eina_clist_count(&(thisGrid->accounts)); + + if (0 == count) + snprintf(buf, sizeof(buf), "%s (no accounts)", thisGrid->name); + else if (1 == count) + snprintf(buf, sizeof(buf), "%s (%d account)", thisGrid->name, count); + else + snprintf(buf, sizeof(buf), "%s (%d accounts)", thisGrid->name, count); + } + else + snprintf(buf, sizeof(buf), "%s", thisGrid->loginURI); + return strdup(buf); +} + +static Evas_Object *_grid_content_get(void *data, Evas_Object *obj, const char *part) +{ + ezGrid *thisGrid = data; + Evas_Object *ic = elm_icon_add(obj); + + if (!strcmp(part, "elm.swallow.icon")) + elm_icon_standard_set(ic, thisGrid->icon); + + evas_object_size_hint_aspect_set(ic, EVAS_ASPECT_CONTROL_VERTICAL, 1, 1); + return ic; +} + +static char * _account_label_get(void *data, Evas_Object *obj, const char *part) +{ + ezAccount *thisAccount = data; + char buf[256]; + + buf[0] = '\0'; + if (!strcmp(part, "elm.text")) + snprintf(buf, sizeof(buf), "%s", thisAccount->name); + + return strdup(buf); +} + +static Evas_Object *_account_content_get(void *data, Evas_Object *obj, const char *part) +{ + ezAccount *thisAccount = data; + Evas_Object *ic = elm_icon_add(obj); + + if (!strcmp(part, "elm.swallow.icon")) + elm_icon_standard_set(ic, thisAccount->icon); + + evas_object_size_hint_aspect_set(ic, EVAS_ASPECT_CONTROL_VERTICAL, 1, 1); + return ic; +} + +static void _grid_sel_cb(void *data, Evas_Object *obj, void *event_info) +{ + ezGrid *thisGrid = data; + char buf[PATH_MAX]; + +// sprintf(buf, "dillo -f -g '%dx%d+%d+%d' %s", w - (w / 5), h - 30, w / 5, y, thisGrid->splashPage); + sprintf(buf, "uzbl -g '%dx%d+%d+%d' -u %s", w - (w / 5), h - 30, w / 5, y, thisGrid->splashPage); + printf("%s ### genlist obj [%p], item pointer [%p]\n", buf, obj, event_info); + system(buf); +} + + +EAPI_MAIN int elm_main(int argc, char **argv) +{ + Evas_Object *win, *bg, *bx, *mn, *tb, *bt, *menu, *gl, *nf, *tab, *list; + Elm_Object_Item *tb_it, *menu_it, *tab_it; + Ecore_Animator *ani; + GLData *gld = NULL; + int i; + Eina_Bool gotWebKit = elm_need_web(); // Initialise ewebkit if it exists, or return EINA_FALSE if it don't. + + elm_config_finger_size_set(0); + elm_config_scale_set(1.0); + + // alloc a data struct to hold our relevant gl info in + if (!(gld = calloc(1, sizeof(GLData)))) return; + gldata_init(gld); + + // new window - do the usual and give it a name, title and delete handler + // Set the engine to opengl_x11 + elm_config_preferred_engine_set("opengl_x11"); + win = elm_win_util_standard_add("extantz", "GLView"); + // Set preferred engine back to default from config + elm_config_preferred_engine_set(NULL); + + elm_win_title_set(win, "extantz virtual world manager"); + evas_object_smart_callback_add(win, "delete,request", _on_done, NULL); + + elm_win_screen_size_get(win, &x, &y, &w, &h); + + bg = elm_bg_add(win); + elm_win_resize_object_add(win, bg); + evas_object_size_hint_weight_set(bg, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_show(bg); + + bx = elm_box_add(win); + elm_win_resize_object_add(win, bx); + evas_object_size_hint_weight_set(bx, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(bx, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_show(bx); + + // A tab thingy. + tb = elm_toolbar_add(win); + evas_object_size_hint_weight_set(tb, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(tb, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_show(tb); + + // Menu. + evas_object_size_hint_weight_set(tb, EVAS_HINT_EXPAND, 0.0); + evas_object_size_hint_align_set(tb, EVAS_HINT_FILL, EVAS_HINT_FILL); + tb_it = elm_toolbar_item_append(tb, NULL, "Menu", NULL, NULL); elm_toolbar_item_menu_set(tb_it, EINA_TRUE); menu = elm_toolbar_item_menu_get(tb_it); + elm_menu_item_add(menu, NULL, NULL, "preferences", NULL, NULL); + menu_it = elm_menu_item_add(menu, NULL, NULL, "advanced", NULL, NULL); + elm_menu_item_add(menu, menu_it, NULL, "debug settings", NULL, NULL); + elm_menu_item_separator_add(menu, NULL); + menu_it = elm_menu_item_add(menu, NULL, NULL, "help", NULL, NULL); + elm_menu_item_add(menu, menu_it, NULL, "grid help", NULL, NULL); + elm_menu_item_separator_add(menu, menu_it); + elm_menu_item_add(menu, menu_it, NULL, "extantz blogs", NULL, NULL); + elm_menu_item_add(menu, menu_it, NULL, "extantz forum", NULL, NULL); + elm_menu_item_separator_add(menu, menu_it); + elm_menu_item_add(menu, menu_it, NULL, "about extantz", NULL, NULL); + elm_menu_item_separator_add(menu, menu_it); + elm_menu_item_add(menu, NULL, NULL, "quit", _on_done, win); + elm_toolbar_menu_parent_set(tb, win); + + nf = elm_naviframe_add(win); + evas_object_size_hint_weight_set(nf, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + evas_object_size_hint_align_set(nf, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_show(nf); + + grid_gic = elm_genlist_item_class_new(); + grid_gic->item_style = "double_label"; + grid_gic->func.text_get = _grid_label_get; + grid_gic->func.content_get = _grid_content_get; + grid_gic->func.state_get = NULL; + grid_gic->func.del = NULL; + + account_gic = elm_genlist_item_class_new(); + account_gic->item_style = "default"; + account_gic->func.text_get = _account_label_get; + account_gic->func.content_get = _account_content_get; + account_gic->func.state_get = NULL; + account_gic->func.del = NULL; + + list = elm_genlist_add(win); + tab = list; tab_it = elm_naviframe_item_push(nf, NULL, NULL, NULL, tab, NULL); elm_naviframe_item_title_visible_set(tab_it, EINA_FALSE); elm_toolbar_item_append(tb, NULL, "Grids", _promote, tab_it); + tab = _content_image_new(win, img1); tab_it = elm_naviframe_item_push(nf, NULL, NULL, NULL, tab, NULL); elm_naviframe_item_title_visible_set(tab_it, EINA_FALSE); elm_toolbar_item_append(tb, NULL, "Accounts", _promote, tab_it); + tab = _content_image_new(win, img2); tab_it = elm_naviframe_item_push(nf, NULL, NULL, NULL, tab, NULL); elm_naviframe_item_title_visible_set(tab_it, EINA_FALSE); elm_toolbar_item_append(tb, NULL, "Viewers", _promote, tab_it); + tab = _content_image_new(win, img3); tab_it = elm_naviframe_item_push(nf, NULL, NULL, NULL, tab, NULL); elm_naviframe_item_title_visible_set(tab_it, EINA_FALSE); elm_toolbar_item_append(tb, NULL, "Landmarks", _promote, tab_it); + + grids = eina_hash_stringshared_new(free); + for (i = 0; NULL != gridTest[i][0]; i++) + { + ezGrid *thisGrid = calloc(1, sizeof(ezGrid)); + + if (thisGrid) + { + eina_clist_init(&(thisGrid->accounts)); + eina_clist_init(&(thisGrid->landmarks)); + thisGrid->name = gridTest[i][0]; + thisGrid->loginURI = gridTest[i][1]; + thisGrid->splashPage = gridTest[i][2]; + thisGrid->icon = "folder"; + thisGrid->item = elm_genlist_item_append(list, grid_gic, thisGrid, NULL, ELM_GENLIST_ITEM_TREE, _grid_sel_cb, thisGrid); + eina_hash_add(grids, thisGrid->name, thisGrid); + } + } + + for (i = 0; NULL != accountTest[i][0]; i++) + { + ezAccount *thisAccount = calloc(1, sizeof(ezAccount)); + ezGrid *grid = eina_hash_find(grids, accountTest[i][0]); + + if (thisAccount && grid) + { + thisAccount->name = accountTest[i][1]; + thisAccount->password = accountTest[i][2]; + thisAccount->icon = "file"; + elm_genlist_item_append(list, account_gic, thisAccount, grid->item, ELM_GENLIST_ITEM_NONE, NULL, NULL); + eina_clist_add_tail(&(grid->accounts), &(thisAccount->grid)); + } + } + + // Add a GLView + gl = elm_glview_add(win); + evas_object_size_hint_align_set(gl, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(gl, EVAS_HINT_EXPAND, EVAS_HINT_EXPAND); + elm_glview_mode_set(gl, ELM_GLVIEW_ALPHA|ELM_GLVIEW_DEPTH); + elm_glview_resize_policy_set(gl, ELM_GLVIEW_RESIZE_POLICY_RECREATE); + elm_glview_render_policy_set(gl, ELM_GLVIEW_RENDER_POLICY_ALWAYS); + elm_glview_init_func_set(gl, _init_gl); + elm_glview_del_func_set(gl, _del_gl); + elm_glview_resize_func_set(gl, _resize_gl); + elm_glview_render_func_set(gl, (Elm_GLView_Func_Cb)_draw_gl); + evas_object_show(gl); + + // Add Mouse/Key Event Callbacks + elm_object_focus_set(gl, EINA_TRUE); + evas_object_event_callback_add(gl, EVAS_CALLBACK_KEY_DOWN, _key_down, gl); + evas_object_event_callback_add(gl, EVAS_CALLBACK_MOUSE_DOWN, _mouse_down, gl); + evas_object_event_callback_add(gl, EVAS_CALLBACK_MOUSE_UP, _mouse_up, gl); + evas_object_event_callback_add(gl, EVAS_CALLBACK_MOUSE_MOVE, _mouse_move, gl); + + // Animator and other vars + ani = ecore_animator_add(_anim, gl); + gld->glapi = elm_glview_gl_api_get(gl); + evas_object_data_set(gl, "ani", ani); + evas_object_data_set(gl, "gld", gld); + evas_object_event_callback_add(gl, EVAS_CALLBACK_DEL, _del, gl); + + bt = elm_button_add(win); + elm_object_text_set(bt, "Login"); + evas_object_size_hint_align_set(bt, EVAS_HINT_FILL, EVAS_HINT_FILL); + evas_object_size_hint_weight_set(bt, EVAS_HINT_EXPAND, 0.0); + evas_object_show(bt); +// evas_object_smart_callback_add(bt, "clicked", NULL, NULL); + + elm_box_pack_end(bx, mn); + elm_box_pack_end(bx, tb); + elm_box_pack_end(bx, nf); + elm_box_pack_end(bx, bt); + elm_box_pack_end(bx, gl); + + evas_object_move(win, x, y); + evas_object_resize(win, w / 5, h - 30); + evas_object_show(win); + + elm_run(); + elm_shutdown(); + + return 0; +} +ELM_MAIN() + diff --git a/ClientHamr/extantz/images/animated_logo.gif b/ClientHamr/extantz/images/animated_logo.gif new file mode 100644 index 0000000..ef201af Binary files /dev/null and b/ClientHamr/extantz/images/animated_logo.gif differ diff --git a/ClientHamr/extantz/images/bubble.png b/ClientHamr/extantz/images/bubble.png new file mode 100644 index 0000000..dfb71b7 Binary files /dev/null and b/ClientHamr/extantz/images/bubble.png differ diff --git a/ClientHamr/extantz/images/bubble_sh.png b/ClientHamr/extantz/images/bubble_sh.png new file mode 100644 index 0000000..b66c1e6 Binary files /dev/null and b/ClientHamr/extantz/images/bubble_sh.png differ diff --git a/ClientHamr/extantz/images/logo.png b/ClientHamr/extantz/images/logo.png new file mode 100644 index 0000000..7dbae67 Binary files /dev/null and b/ClientHamr/extantz/images/logo.png differ diff --git a/ClientHamr/extantz/images/logo_small.png b/ClientHamr/extantz/images/logo_small.png new file mode 100644 index 0000000..c7dc665 Binary files /dev/null and b/ClientHamr/extantz/images/logo_small.png differ diff --git a/ClientHamr/extantz/images/plant_01.jpg b/ClientHamr/extantz/images/plant_01.jpg new file mode 100644 index 0000000..f1714dd Binary files /dev/null and b/ClientHamr/extantz/images/plant_01.jpg differ diff --git a/ClientHamr/extantz/images/pt.png b/ClientHamr/extantz/images/pt.png new file mode 100644 index 0000000..612d117 Binary files /dev/null and b/ClientHamr/extantz/images/pt.png differ diff --git a/ClientHamr/extantz/images/rock_01.jpg b/ClientHamr/extantz/images/rock_01.jpg new file mode 100644 index 0000000..c50ccb3 Binary files /dev/null and b/ClientHamr/extantz/images/rock_01.jpg differ diff --git a/ClientHamr/extantz/images/rock_02.jpg b/ClientHamr/extantz/images/rock_02.jpg new file mode 100644 index 0000000..04aea8a Binary files /dev/null and b/ClientHamr/extantz/images/rock_02.jpg differ diff --git a/ClientHamr/extantz/images/sky_01.jpg b/ClientHamr/extantz/images/sky_01.jpg new file mode 100644 index 0000000..22f3050 Binary files /dev/null and b/ClientHamr/extantz/images/sky_01.jpg differ diff --git a/ClientHamr/extantz/images/sky_02.jpg b/ClientHamr/extantz/images/sky_02.jpg new file mode 100644 index 0000000..d0d7448 Binary files /dev/null and b/ClientHamr/extantz/images/sky_02.jpg differ diff --git a/ClientHamr/extantz/images/sky_03.jpg b/ClientHamr/extantz/images/sky_03.jpg new file mode 100644 index 0000000..cbad02a Binary files /dev/null and b/ClientHamr/extantz/images/sky_03.jpg differ diff --git a/ClientHamr/extantz/images/sky_04.jpg b/ClientHamr/extantz/images/sky_04.jpg new file mode 100644 index 0000000..c5cbc18 Binary files /dev/null and b/ClientHamr/extantz/images/sky_04.jpg differ diff --git a/ClientHamr/extantz/images/wood_01.jpg b/ClientHamr/extantz/images/wood_01.jpg new file mode 100644 index 0000000..89f1006 Binary files /dev/null and b/ClientHamr/extantz/images/wood_01.jpg differ diff --git a/ClientHamr/extantz/make.sh b/ClientHamr/extantz/make.sh new file mode 100755 index 0000000..2c729b8 --- /dev/null +++ b/ClientHamr/extantz/make.sh @@ -0,0 +1,3 @@ +gcc -g -DPACKAGE_DATA_DIR="\"$(pwd)\"" extantz.c -o extantz $(pkg-config --cflags --libs elementary) && ./extantz + + -- cgit v1.1