- shaders for both lightmapped objects with or without albedo maps
authorJohn Tsiombikas <nuclear@mutantstargoat.com>
Tue, 15 Nov 2016 14:52:01 +0000 (16:52 +0200)
committerJohn Tsiombikas <nuclear@mutantstargoat.com>
Tue, 15 Nov 2016 14:52:01 +0000 (16:52 +0200)
- logger with colored messages
- logger also puts up notifications on screen

19 files changed:
RUNVR [new file with mode: 0755]
sdr/lightmap-notex.p.glsl [new file with mode: 0644]
sdr/lightmap-tex.p.glsl [new file with mode: 0644]
sdr/lightmap.v.glsl [new file with mode: 0644]
sdr/test.p.glsl [deleted file]
sdr/test.v.glsl [deleted file]
src/app.cc
src/app.h
src/dataset.inl
src/logger.cc [new file with mode: 0644]
src/logger.h [new file with mode: 0644]
src/material.cc
src/mesh.cc
src/metascene.cc
src/sceneload.cc
src/sdr.c
src/texture.cc
src/ui.cc
src/ui.h

diff --git a/RUNVR b/RUNVR
new file mode 100755 (executable)
index 0000000..755a00a
--- /dev/null
+++ b/RUNVR
@@ -0,0 +1,3 @@
+#!/bin/sh
+
+DISPLAY=:0.1 ./demo -vr $*
diff --git a/sdr/lightmap-notex.p.glsl b/sdr/lightmap-notex.p.glsl
new file mode 100644 (file)
index 0000000..19cd2b1
--- /dev/null
@@ -0,0 +1,13 @@
+/* vi: set ft=glsl */
+uniform sampler2D lightmap;
+
+void main()
+{
+       vec3 lumel = texture2D(lightmap, gl_TexCoord[1].st).rgb;
+
+       vec3 diffuse = gl_FrontMaterial.diffuse.rgb * lumel * 1.8;
+
+       vec3 ambient = gl_LightModel.ambient.rgb * gl_FrontMaterial.diffuse.rgb;
+       gl_FragColor.rgb = ambient + diffuse;
+       gl_FragColor.a = gl_FrontMaterial.diffuse.a;
+}
diff --git a/sdr/lightmap-tex.p.glsl b/sdr/lightmap-tex.p.glsl
new file mode 100644 (file)
index 0000000..4983963
--- /dev/null
@@ -0,0 +1,15 @@
+/* vi: set ft=glsl */
+uniform sampler2D texmap;
+uniform sampler2D lightmap;
+
+void main()
+{
+       vec3 texel = texture2D(texmap, gl_TexCoord[0].st).rgb;
+       vec3 lumel = texture2D(lightmap, gl_TexCoord[1].st).rgb;
+
+       vec3 diffuse = lumel * texel * 1.8;
+
+       vec3 ambient = gl_LightModel.ambient.rgb * texel;
+       gl_FragColor.rgb = ambient + diffuse;
+       gl_FragColor.a = gl_FrontMaterial.diffuse.a;
+}
diff --git a/sdr/lightmap.v.glsl b/sdr/lightmap.v.glsl
new file mode 100644 (file)
index 0000000..8c1e01c
--- /dev/null
@@ -0,0 +1,7 @@
+void main()
+{
+       gl_Position = ftransform();
+
+       gl_TexCoord[0] = gl_MultiTexCoord0;
+       gl_TexCoord[1] = gl_MultiTexCoord1;
+}
diff --git a/sdr/test.p.glsl b/sdr/test.p.glsl
deleted file mode 100644 (file)
index 87ca201..0000000
+++ /dev/null
@@ -1,51 +0,0 @@
-/* vi: set ft=glsl */
-uniform sampler2D texmap;
-uniform sampler2D lightmap;
-
-varying vec3 vdir, ldir[3], normal;
-
-//#define KD gl_FrontMaterial.diffuse.rgb
-#define KD vec3(1.0, 1.0, 1.0)
-
-#define KS gl_FrontMaterial.specular.rgb
-#define SPOW gl_FrontMaterial.shininess
-
-#define LD(i) gl_LightSource[i].diffuse.rgb
-#define LS(i) gl_LightSource[i].specular.rgb
-
-vec3 calc_diffuse(in vec3 n, in vec3 l, in vec3 lcol)
-{
-       float ndotl = max(dot(n, l), 0.0);
-       return KD * lcol * ndotl;
-}
-
-vec3 calc_specular(in vec3 n, in vec3 l, in vec3 v, in vec3 lcol)
-{
-       vec3 h = normalize(l + v);
-       float ndoth = max(dot(n, h), 0.0);
-       return KS * lcol * pow(ndoth, SPOW);
-}
-
-void main()
-{
-       vec3 texel = texture2D(texmap, gl_TexCoord[0].st).rgb;
-       vec3 lumel = texture2D(lightmap, gl_TexCoord[1].st).rgb;
-
-       vec3 n = normalize(normal);
-       vec3 v = normalize(vdir);
-
-       vec3 diffuse = lumel * texel * 1.8;
-       vec3 specular = vec3(0.0, 0.0, 0.0);
-
-       /*
-       for(int i=0; i<3; i++) {
-               vec3 l = normalize(ldir[i]);
-               diffuse += calc_diffuse(n, l, LD(i)) * texel;
-               specular += calc_specular(n, l, v, LS(i));
-       }
-       */
-
-       vec3 ambient = gl_LightModel.ambient.rgb * KD * texel;
-       gl_FragColor.rgb = ambient + diffuse;// + specular;
-       gl_FragColor.a = gl_FrontMaterial.diffuse.a;
-}
diff --git a/sdr/test.v.glsl b/sdr/test.v.glsl
deleted file mode 100644 (file)
index a8c7159..0000000
+++ /dev/null
@@ -1,15 +0,0 @@
-varying vec3 vdir, ldir[3], normal;
-
-void main()
-{
-       gl_Position = ftransform();
-       vec3 vpos = (gl_ModelViewMatrix * gl_Vertex).xyz;
-       normal = gl_NormalMatrix * gl_Normal;
-       vdir = -vpos;
-       ldir[0] = gl_LightSource[0].position.xyz - vpos;
-       ldir[1] = gl_LightSource[1].position.xyz - vpos;
-       ldir[2] = gl_LightSource[2].position.xyz - vpos;
-
-       gl_TexCoord[0] = gl_MultiTexCoord0;
-       gl_TexCoord[1] = gl_MultiTexCoord1;
-}
index 9245f06..330241c 100644 (file)
@@ -25,6 +25,8 @@ float win_aspect;
 bool fb_srgb;
 bool opt_gear_wireframe;
 
+unsigned int sdr_ltmap, sdr_ltmap_notex;
+
 static float cam_dist = 0.0;
 static float cam_theta, cam_phi = 20;
 static Vec3 cam_pos;
@@ -44,7 +46,7 @@ static bool keystate[256];
 static Mat4 view_matrix, mouse_view_matrix, proj_matrix;
 static TextureSet texman;
 static Scene *scn;
-static unsigned int sdr, sdr_post_gamma;
+static unsigned int sdr_post_gamma;
 
 static long prev_msec;
 
@@ -106,12 +108,15 @@ bool app_init(int argc, char **argv)
                cam_pos = bcent + Vec3(0, user_eye_height, 0);
        }
 
-       if(!(sdr = create_program_load("sdr/test.v.glsl", "sdr/test.p.glsl"))) {
-               fprintf(stderr, "failed to load test shaders\n");
+       if(!(sdr_ltmap_notex = create_program_load("sdr/lightmap.v.glsl", "sdr/lightmap-notex.p.glsl"))) {
+               return false;
+       }
+
+       if(!(sdr_ltmap = create_program_load("sdr/lightmap.v.glsl", "sdr/lightmap-tex.p.glsl"))) {
                return false;
        }
-       set_uniform_int(sdr, "texmap", 0);
-       set_uniform_int(sdr, "lightmap", 1);
+       set_uniform_int(sdr_ltmap, "texmap", 0);
+       set_uniform_int(sdr_ltmap, "lightmap", 1);
 
        if(!fb_srgb) {
                sdr_post_gamma = create_program_load("sdr/post_gamma.v.glsl", "sdr/post_gamma.p.glsl");
@@ -295,9 +300,7 @@ static void draw_scene()
        set_light(1, lpos[1], Vec3(0.6, 0.7, 1.0) * 0.6);
        set_light(2, lpos[2], Vec3(0.8, 1.0, 0.8) * 0.3);
 
-       glUseProgram(sdr);
        scn->draw();
-       glUseProgram(0);
 
        if(show_walk_mesh && scn->walk_mesh) {
                glPushAttrib(GL_ENABLE_BIT);
@@ -337,8 +340,11 @@ void app_keyboard(int key, bool pressed)
                        app_quit();
                        break;
 
-               case 'f':
-                       app_toggle_fullscreen();
+               case '\n':
+               case '\r':
+                       if(mod & MOD_ALT) {
+                               app_toggle_fullscreen();
+                       }
                        break;
 
                case '`':
@@ -360,6 +366,23 @@ void app_keyboard(int key, bool pressed)
                        }
                        break;
 
+               case 'f':
+                       {
+                               static float prev_walk_speed = -1.0;
+                               if(prev_walk_speed < 0.0) {
+                                       noclip = true;
+                                       prev_walk_speed = walk_speed;
+                                       walk_speed = 1000.0;
+                                       show_message("fly mode\n");
+                               } else {
+                                       noclip = false;
+                                       walk_speed = prev_walk_speed;
+                                       prev_walk_speed = -1.0;
+                                       show_message("walk mode\n");
+                               }
+                       }
+                       break;
+
                case 'p':
                        if(mod & MOD_CTRL) {
                                fb_srgb = !fb_srgb;
index 5e65394..09b1c82 100644 (file)
--- a/src/app.h
+++ b/src/app.h
@@ -7,6 +7,8 @@ extern float win_aspect;
 extern bool opt_gear_wireframe;
 extern bool fb_srgb;
 
+extern unsigned int sdr_ltmap, sdr_ltmap_notex;
+
 enum {
        MOD_SHIFT       = 1,
        MOD_ALT         = 2,
index 1df20d5..bf6140c 100644 (file)
@@ -1,5 +1,6 @@
 #include <stdio.h>
 #include <string.h>
+#include "logger.h"
 
 template <typename T>
 DataSet<T>::DataSet(T (*create_func)(), bool (*load_func)(T, const char*), bool (*done_func)(T), void (*destr_func)(T))
@@ -74,9 +75,9 @@ int DataSet<T>::dataset_done_func(int id, void *cls)
        int load_res = resman_get_res_result(dset->rman, id);
 
        if(load_res != 0) {
-               fprintf(stderr, "failed to load resource %d (%s)\n", id, resman_get_res_name(dset->rman, id));
+               error_log("failed to load resource %d (%s)\n", id, resman_get_res_name(dset->rman, id));
        } else {
-               printf("done loading resource %d (%s)\n", id, resman_get_res_name(dset->rman, id));
+               info_log("done loading resource %d (%s)\n", id, resman_get_res_name(dset->rman, id));
        }
 
        if(dset->done) {
diff --git a/src/logger.cc b/src/logger.cc
new file mode 100644 (file)
index 0000000..015c9bd
--- /dev/null
@@ -0,0 +1,129 @@
+#include <stdio.h>
+#include <stdarg.h>
+#include "logger.h"
+#include "ui.h"
+
+#if defined(unix) || defined(__unix__) || defined(__APPLE__)
+#include <unistd.h>
+#elif defined(WIN32)
+#include <windows.h>
+#endif
+
+#define UI_MSG_TIMEOUT 4000
+
+enum { LOG_INFO, LOG_WARNING, LOG_ERROR, LOG_FATAL, LOG_DEBUG };
+
+static int typecolor(int type);
+
+static FILE *fp = stdout;
+
+static void logmsg(int type, const char *fmt, va_list ap)
+{
+#if defined(unix) || defined(__unix__) || (defined(__APPLE__) && !defined(TARGET_IPHONE))
+       if(isatty(fileno(fp)) && type != LOG_INFO) {
+               int c = typecolor(type);
+               fprintf(fp, "\033[%dm", c);
+               vfprintf(fp, fmt, ap);
+               fprintf(fp, "\033[0m");
+       } else
+#endif
+       {
+               vfprintf(fp, fmt, ap);
+       }
+       if(type == LOG_ERROR || type == LOG_FATAL || type == LOG_DEBUG) {
+               fflush(fp);
+       }
+
+#ifdef WIN32
+       if(type == LOG_FATAL) {
+               static char msgbuf[1024];
+               vsnprintf(msgbuf, sizeof msgbuf - 1, fmt, ap);
+               msgbuf[sizeof msgbuf - 1] = 0;
+               MessageBox(0, msgbuf, "Fatal error", MB_OK | MB_ICONSTOP);
+       }
+#endif
+}
+
+extern "C" void info_log(const char *fmt, ...)
+{
+       va_list ap;
+
+       va_start(ap, fmt);
+       logmsg(LOG_INFO, fmt, ap);
+       va_end(ap);
+}
+
+extern "C" void warning_log(const char *fmt, ...)
+{
+       va_list ap;
+
+       va_start(ap, fmt);
+       logmsg(LOG_WARNING, fmt, ap);
+       va_end(ap);
+
+       va_start(ap, fmt);
+       show_messagev(UI_MSG_TIMEOUT, Vec3(1.0, 0.8, 0.1), fmt, ap);
+       va_end(ap);
+}
+
+extern "C" void error_log(const char *fmt, ...)
+{
+       va_list ap;
+
+       va_start(ap, fmt);
+       logmsg(LOG_ERROR, fmt, ap);
+       va_end(ap);
+
+       va_start(ap, fmt);
+       show_messagev(UI_MSG_TIMEOUT, Vec3(1.0, 0.1, 0.1), fmt, ap);
+       va_end(ap);
+}
+
+extern "C" void fatal_log(const char *fmt, ...)
+{
+       va_list ap;
+
+       va_start(ap, fmt);
+       logmsg(LOG_FATAL, fmt, ap);
+       va_end(ap);
+}
+
+extern "C" void debug_log(const char *fmt, ...)
+{
+       va_list ap;
+
+       va_start(ap, fmt);
+       logmsg(LOG_DEBUG, fmt, ap);
+       va_end(ap);
+}
+
+enum {
+       BLACK = 0,
+       RED,
+       GREEN,
+       YELLOW,
+       BLUE,
+       MAGENTA,
+       CYAN,
+       WHITE
+};
+
+#define ANSI_FGCOLOR(x)        (30 + (x))
+#define ANSI_BGCOLOR(x)        (40 + (x))
+
+static int typecolor(int type)
+{
+       switch(type) {
+       case LOG_ERROR:
+               return ANSI_FGCOLOR(RED);
+       case LOG_FATAL:
+               return ANSI_FGCOLOR(RED);       // TODO differentiate from LOG_ERROR
+       case LOG_WARNING:
+               return ANSI_FGCOLOR(YELLOW);
+       case LOG_DEBUG:
+               return ANSI_FGCOLOR(MAGENTA);
+       default:
+               break;
+       }
+       return 37;
+}
diff --git a/src/logger.h b/src/logger.h
new file mode 100644 (file)
index 0000000..978d634
--- /dev/null
@@ -0,0 +1,18 @@
+#ifndef LOGGER_H_
+#define LOGGER_H_
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+void info_log(const char *fmt, ...);
+void warning_log(const char *fmt, ...);
+void error_log(const char *fmt, ...);
+void fatal_log(const char *fmt, ...);
+void debug_log(const char *fmt, ...);
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif // LOGGER_H_
index ac8c112..0aa83cd 100644 (file)
@@ -2,6 +2,8 @@
 #include <string.h>
 #include "opengl.h"
 #include "material.h"
+#include "sdr.h"
+#include "app.h"
 
 Material::Material()
        : diffuse(1.0f, 1.0f, 1.0f)
@@ -24,6 +26,10 @@ void Material::setup() const
        for(int i=0; i<ntex; i++) {
                bind_texture(textures[i], i);
        }
+
+       if(stdtex[MTL_TEX_LIGHTMAP]) {
+               bind_program(stdtex[MTL_TEX_DIFFUSE] ? sdr_ltmap : sdr_ltmap_notex);
+       }
 }
 
 void Material::add_texture(Texture *tex, int type)
index e17b909..6a1faa7 100644 (file)
@@ -4,6 +4,7 @@
 #include <assert.h>
 #include "opengl.h"
 #include "mesh.h"
+#include "logger.h"
 //#include "xform_node.h"
 
 #define USE_OLDGL
@@ -154,12 +155,12 @@ void Mesh::clear()
 float *Mesh::set_attrib_data(int attrib, int nelem, unsigned int num, const float *data)
 {
        if(attrib < 0 || attrib >= NUM_MESH_ATTR) {
-               fprintf(stderr, "%s: invalid attrib: %d\n", __FUNCTION__, attrib);
+               error_log("%s: invalid attrib: %d\n", __FUNCTION__, attrib);
                return 0;
        }
 
        if(nverts && num != nverts) {
-               fprintf(stderr, "%s: attribute count missmatch (%d instead of %d)\n", __FUNCTION__, num, nverts);
+               error_log("%s: attribute count missmatch (%d instead of %d)\n", __FUNCTION__, num, nverts);
                return 0;
        }
        nverts = num;
@@ -180,7 +181,7 @@ float *Mesh::set_attrib_data(int attrib, int nelem, unsigned int num, const floa
 float *Mesh::get_attrib_data(int attrib)
 {
        if(attrib < 0 || attrib >= NUM_MESH_ATTR) {
-               fprintf(stderr, "%s: invalid attrib: %d\n", __FUNCTION__, attrib);
+               error_log("%s: invalid attrib: %d\n", __FUNCTION__, attrib);
                return 0;
        }
 
@@ -191,17 +192,17 @@ float *Mesh::get_attrib_data(int attrib)
 const float *Mesh::get_attrib_data(int attrib) const
 {
        if(attrib < 0 || attrib >= NUM_MESH_ATTR) {
-               fprintf(stderr, "%s: invalid attrib: %d\n", __FUNCTION__, attrib);
+               error_log("%s: invalid attrib: %d\n", __FUNCTION__, attrib);
                return 0;
        }
 
        if(!vattr[attrib].data_valid) {
 #if GL_ES_VERSION_2_0
-               fprintf(stderr, "%s: can't read back attrib data on CrippledGL ES\n", __FUNCTION__);
+               error_log("%s: can't read back attrib data on CrippledGL ES\n", __FUNCTION__);
                return 0;
 #else
                if(!vattr[attrib].vbo_valid) {
-                       fprintf(stderr, "%s: unavailable attrib: %d\n", __FUNCTION__, attrib);
+                       error_log("%s: unavailable attrib: %d\n", __FUNCTION__, attrib);
                        return 0;
                }
 
@@ -255,7 +256,7 @@ unsigned int *Mesh::set_index_data(int num, const unsigned int *indices)
 {
        int nidx = nfaces * 3;
        if(nidx && num != nidx) {
-               fprintf(stderr, "%s: index count mismatch (%d instead of %d)\n", __FUNCTION__, num, nidx);
+               error_log("%s: index count mismatch (%d instead of %d)\n", __FUNCTION__, num, nidx);
                return 0;
        }
        nfaces = num / 3;
@@ -283,11 +284,11 @@ const unsigned int *Mesh::get_index_data() const
 {
        if(!idata_valid) {
 #if GL_ES_VERSION_2_0
-               fprintf(stderr, "%s: can't read back index data in CrippledGL ES\n", __FUNCTION__);
+               error_log("%s: can't read back index data in CrippledGL ES\n", __FUNCTION__);
                return 0;
 #else
                if(!ibo_valid) {
-                       fprintf(stderr, "%s: indices unavailable\n", __FUNCTION__);
+                       error_log("%s: indices unavailable\n", __FUNCTION__);
                        return 0;
                }
 
@@ -631,14 +632,14 @@ bool Mesh::pre_draw() const
        ((Mesh*)this)->update_buffers();
 
        if(!vattr[MESH_ATTR_VERTEX].vbo_valid) {
-               fprintf(stderr, "%s: invalid vertex buffer\n", __FUNCTION__);
+               error_log("%s: invalid vertex buffer\n", __FUNCTION__);
                return false;
        }
 
        if(cur_sdr && use_custom_sdr_attr) {
                // rendering with shaders
                if(global_sdr_loc[MESH_ATTR_VERTEX] == -1) {
-                       fprintf(stderr, "%s: shader attribute location for vertices unset\n", __FUNCTION__);
+                       error_log("%s: shader attribute location for vertices unset\n", __FUNCTION__);
                        return false;
                }
 
index aae7482..cf4d788 100644 (file)
@@ -2,6 +2,7 @@
 #include "scene.h"
 #include "datamap.h"
 #include "treestore.h"
+#include "logger.h"
 
 #ifdef WIN32
 #include <malloc.h>
@@ -20,15 +21,15 @@ bool load_scene(Scene *scn, const char *fname)
        struct ts_node *root = ts_load(fname);
        if(!root || strcmp(root->name, "scene") != 0) {
                ts_free_tree(root);
-               fprintf(stderr, "failed to load scene metadata: %s\n", fname);
+               error_log("failed to load scene metadata: %s\n", fname);
                return false;
        }
 
        bool res = proc_node(scn, root);
        ts_free_tree(root);
 
-       printf("loaded scene: %s\n", fname);
-       printf("scene graph:\n");
+       info_log("loaded scene: %s\n", fname);
+       info_log("scene graph:\n");
        print_scene_graph(scn->nodes, 0);
        return res;
 }
@@ -65,7 +66,7 @@ static bool proc_scenefile(Scene *scn, struct ts_node *node)
                // datapath
                struct ts_attr *adpath = attr_inscope(node, "datapath");
                if(adpath && adpath->val.type == TS_STRING) {
-                       printf("adding data path: %s\n", adpath->val.str);
+                       info_log("adding data path: %s\n", adpath->val.str);
                        datamap_set_path(adpath->val.str);
                }
 
@@ -128,14 +129,14 @@ static void print_scene_graph(SceneNode *n, int level)
        if(!n) return;
 
        for(int i=0; i<level; i++) {
-               fputs("  ", stdout);
+               info_log("  ");
        }
 
        int nobj = n->get_num_objects();
        if(nobj) {
-               printf("%s - %d obj\n", n->get_name(), n->get_num_objects());
+               info_log("%s - %d obj\n", n->get_name(), n->get_num_objects());
        } else {
-               printf("%s\n", n->get_name());
+               info_log("%s\n", n->get_name());
        }
 
        for(int i=0; i<n->get_num_children(); i++) {
index 6fb17d4..b491cf0 100644 (file)
@@ -15,6 +15,7 @@
 #include "scene.h"
 #include "objmesh.h"
 #include "datamap.h"
+#include "logger.h"
 
 static bool load_material(Scene *scn, Material *mat, const aiMaterial *aimat);
 static SceneNode *load_node(Scene *scn, const aiScene *aiscn, unsigned int flags, const aiNode *ainode);
@@ -50,11 +51,11 @@ bool Scene::load(const char *fname, unsigned int flags)
                ppflags |= aiProcess_FlipUVs;
        }
 
-       printf("Loading scene file: %s\n", fname);
+       info_log("Loading scene file: %s\n", fname);
 
        const aiScene *aiscn = aiImportFile(fname, ppflags);
        if(!aiscn) {
-               fprintf(stderr, "failed to load scene file: %s\n", fname);
+               error_log("failed to load scene file: %s\n", fname);
                return false;
        }
 
@@ -83,7 +84,7 @@ bool Scene::load(const char *fname, unsigned int flags)
                        break;
 
                default:
-                       fprintf(stderr, "unsupported primitive type: %u\n", aimesh->mPrimitiveTypes);
+                       error_log("unsupported primitive type: %u\n", aimesh->mPrimitiveTypes);
                        break;
                }
        }
@@ -109,7 +110,7 @@ bool Scene::load(const char *fname, unsigned int flags)
        mesh_by_aimesh.clear();
 
        aiReleaseImport(aiscn);
-       printf("loaded scene file: %s, %d meshes\n", fname, (int)meshes.size());
+       info_log("loaded scene file: %s, %d meshes\n", fname, (int)meshes.size());
        nodes->update(0);
        return true;
 }
@@ -125,7 +126,7 @@ static bool load_material(Scene *scn, Material *mat, const aiMaterial *aimat)
        } else {
                mat->name = "unknown";
        }
-       //printf("load_material: %s\n", mat->name.c_str());
+       //info_log("load_material: %s\n", mat->name.c_str());
 
        if(aiGetMaterialColor(aimat, AI_MATKEY_COLOR_DIFFUSE, &aicol) == 0) {
                mat->diffuse = Vec3(aicol[0], aicol[1], aicol[2]);
@@ -171,7 +172,7 @@ static bool load_material(Scene *scn, Material *mat, const aiMaterial *aimat)
                        }
 
                        int textype = assimp_textype(aitype);
-                       printf("loading %s texture: %s\n", assimp_textypestr(aitype), fname);
+                       info_log("loading %s texture: %s\n", assimp_textypestr(aitype), fname);
 
                        Texture *tex = scn->texset->get_texture(fname, TEX_2D);
                        assert(tex);
index 0152a6e..6b06991 100644 (file)
--- a/src/sdr.c
+++ b/src/sdr.c
@@ -5,6 +5,7 @@
 #include <stdarg.h>
 #include <assert.h>
 #include "opengl.h"
+#include "logger.h"
 
 #if defined(unix) || defined(__unix__)
 #include <unistd.h>
@@ -93,9 +94,9 @@ unsigned int create_shader(const char *src, unsigned int sdr_type)
        }
 
        if(success) {
-               fprintf(stderr, info_str ? "done: %s\n" : "done\n", info_str);
+               info_log(info_str ? "done: %s\n" : "done\n", info_str);
        } else {
-               fprintf(stderr, info_str ? "failed: %s\n" : "failed\n", info_str);
+               error_log(info_str ? "failed: %s\n" : "failed\n", info_str);
                glDeleteShader(sdr);
                sdr = 0;
        }
@@ -154,7 +155,7 @@ unsigned int load_shader(const char *fname, unsigned int sdr_type)
        char *src;
 
        if(!(fp = fopen(fname, "rb"))) {
-               fprintf(stderr, "failed to open shader %s: %s\n", fname, strerror(errno));
+               error_log("failed to open shader %s: %s\n", fname, strerror(errno));
                return 0;
        }
 
@@ -170,7 +171,7 @@ unsigned int load_shader(const char *fname, unsigned int sdr_type)
        src[filesize] = 0;
        fclose(fp);
 
-       fprintf(stderr, "compiling %s shader: %s... ", sdrtypestr(sdr_type), fname);
+       info_log("compiling %s shader: %s... ", sdrtypestr(sdr_type), fname);
        sdr = create_shader(src, sdr_type);
 
        free(src);
@@ -243,7 +244,7 @@ void attach_shader(unsigned int prog, unsigned int sdr)
                assert(glGetError() == GL_NO_ERROR);
                glAttachShader(prog, sdr);
                if((err = glGetError()) != GL_NO_ERROR) {
-                       fprintf(stderr, "failed to attach shader %u to program %u (err: 0x%x)\n", sdr, prog, err);
+                       error_log("failed to attach shader %u to program %u (err: 0x%x)\n", sdr, prog, err);
                        abort();
                }
        }
@@ -270,9 +271,9 @@ int link_program(unsigned int prog)
        }
 
        if(linked) {
-               fprintf(stderr, info_str ? "linking done: %s\n" : "linking done\n", info_str);
+               info_log(info_str ? "linking done: %s\n" : "linking done\n", info_str);
        } else {
-               fprintf(stderr, info_str ? "linking failed: %s\n" : "linking failed\n", info_str);
+               error_log(info_str ? "linking failed: %s\n" : "linking failed\n", info_str);
                retval = -1;
        }
 
@@ -433,7 +434,7 @@ static void append_string(struct string *str, const char *s)
        len = strlen(s);
        newlen = str->len + len;
        if(!(newstr = malloc(newlen + 2))) {    /* leave space for a possible newline */
-               fprintf(stderr, "shader composition: failed to append string of size %d\n", len);
+               error_log("shader composition: failed to append string of size %d\n", len);
                abort();
        }
 
index dddc0d1..cbbd11d 100644 (file)
@@ -4,6 +4,7 @@
 #include "image.h"
 #include "opengl.h"
 #include "imago2.h"
+#include "logger.h"
 
 static int glifmt_from_ifmt(unsigned int ifmt);
 static int glfmt_from_ifmt(unsigned int ifmt);
@@ -148,7 +149,7 @@ void Texture::bind(int tex_unit) const
 void Texture::create(int xsz, int ysz, TextureType textype, unsigned int ifmt)
 {
        if(textype == TEX_CUBE && xsz != ysz) {
-               fprintf(stderr, "trying to create cubemap with different width and height (%dx%d)\n", xsz, ysz);
+               error_log("trying to create cubemap with different width and height (%dx%d)\n", xsz, ysz);
                return;
        }
 
@@ -321,12 +322,12 @@ bool Texture::load(const char *fname)
 {
        Image img;
        if(!img.load(fname)) {
-               fprintf(stderr, "failed to load 2D texture: %s\n", fname);
+               error_log("failed to load 2D texture: %s\n", fname);
                return false;
        }
        set_image(img);
 
-       printf("loaded 2D texture: %s\n", fname);
+       info_log("loaded 2D texture: %s\n", fname);
        return true;
 }
 
index 33fbccf..1a18324 100644 (file)
--- a/src/ui.cc
+++ b/src/ui.cc
@@ -14,6 +14,7 @@ static bool init();
 struct Message {
        long start_time, show_until;
        char *str;
+       Vec3 color;
        Message *next;
 };
 static Message *msglist;
@@ -30,13 +31,26 @@ void set_message_timeout(long tm)
 void show_message(const char *fmt, ...)
 {
        va_list ap;
+       va_start(ap, fmt);
+       show_messagev(timeout, Vec3(1, 1, 1), fmt, ap);
+       va_end(ap);
+}
+
+void show_message(long timeout, const Vec3 &color, const char *fmt, ...)
+{
+       va_list ap;
+       va_start(ap, fmt);
+       show_messagev(timeout, color, fmt, ap);
+       va_end(ap);
+}
+
+void show_messagev(long timeout, const Vec3 &color, const char *fmt, va_list ap)
+{
        char buf[512];
 
        init();
 
-       va_start(ap, fmt);
        vsnprintf(buf, sizeof buf, fmt, ap);
-       va_end(ap);
 
        Message *msg = new Message;
        int len = strlen(buf);
@@ -44,6 +58,7 @@ void show_message(const char *fmt, ...)
        memcpy(msg->str, buf, len + 1);
        msg->start_time = time_msec;
        msg->show_until = time_msec + timeout;
+       msg->color = color;
 
        Message dummy;
        dummy.next = msglist;
@@ -90,7 +105,7 @@ void draw_ui()
                long dur = msg->show_until - msg->start_time;
                float alpha = smoothstep(0, trans_time, t) *
                        (1.0 - smoothstep(dur - trans_time, dur, t));
-               glColor4f(1.0, 0.5, 0.1, alpha);
+               glColor4f(msg->color.x, msg->color.y, msg->color.z, alpha);
                glTranslatef(0, -dtx_line_height(), 0);
                dtx_string(msg->str);
                msg = msg->next;
index 1ed6c27..dbd693d 100644 (file)
--- a/src/ui.h
+++ b/src/ui.h
@@ -1,8 +1,13 @@
 #ifndef UI_H_
 #define UI_H_
 
+#include <stdarg.h>
+#include <gmath/gmath.h>
+
 void set_message_timeout(long timeout);
 void show_message(const char *fmt, ...);
+void show_message(long timeout, const Vec3 &color, const char *fmt, ...);
+void show_messagev(long timeout, const Vec3 &color, const char *fmt, va_list ap);
 
 void draw_ui();