erebus

annotate src/main.cc @ 21:e49f4d7ad04c

started adding BRDFs
author John Tsiombikas <nuclear@member.fsf.org>
date Wed, 28 May 2014 07:06:29 +0300
parents 6204e4d3f445
children 56d504cc555a
rev   line source
nuclear@2 1 #include <stdio.h>
nuclear@2 2 #include <stdlib.h>
nuclear@2 3 #include <assert.h>
nuclear@19 4 #include <vector>
nuclear@2 5 #include "opengl.h"
nuclear@4 6 #include "erebus.h"
nuclear@2 7
nuclear@2 8 static bool init();
nuclear@2 9 static void cleanup();
nuclear@2 10 static void resize_rtarget(int xsz, int ysz);
nuclear@2 11 static void update_rect(int x, int y, int xsz, int ysz, float *pixels);
nuclear@4 12 static void idle();
nuclear@2 13 static void display();
nuclear@2 14 static void reshape(int x, int y);
nuclear@2 15 static void keyb(unsigned char key, int x, int y);
nuclear@9 16 static void keyb_up(unsigned char key, int x, int y);
nuclear@2 17 static void mouse(int bn, int st, int x, int y);
nuclear@9 18 static void motion(int x, int y);
nuclear@9 19 static void sball_button(int bn, int st);
nuclear@9 20 static void sball_motion(int x, int y, int z);
nuclear@2 21 static int next_pow2(int x);
nuclear@2 22
nuclear@2 23 static int width, height, rtex_width, rtex_height;
nuclear@2 24 static unsigned int rtex;
nuclear@2 25
nuclear@4 26 static erebus *erb;
nuclear@4 27 static bool render_pending;
nuclear@4 28
nuclear@19 29 static std::vector<char*> sfiles;
nuclear@4 30
nuclear@2 31 int main(int argc, char **argv)
nuclear@2 32 {
nuclear@2 33 glutInitWindowSize(1024, 600);
nuclear@2 34 glutInit(&argc, argv);
nuclear@19 35
nuclear@19 36 for(int i=1; i<argc; i++) {
nuclear@19 37 sfiles.push_back(argv[i]);
nuclear@19 38 }
nuclear@19 39
nuclear@2 40 glutInitDisplayMode(GLUT_RGB | GLUT_DOUBLE);
nuclear@2 41 glutCreateWindow("erebus OpenGL frontend");
nuclear@2 42
nuclear@2 43 glutDisplayFunc(display);
nuclear@2 44 glutReshapeFunc(reshape);
nuclear@2 45 glutKeyboardFunc(keyb);
nuclear@9 46 glutKeyboardUpFunc(keyb_up);
nuclear@2 47 glutMouseFunc(mouse);
nuclear@9 48 glutMotionFunc(motion);
nuclear@9 49 glutSpaceballButtonFunc(sball_button);
nuclear@9 50 glutSpaceballMotionFunc(sball_motion);
nuclear@2 51
nuclear@2 52 if(!init()) {
nuclear@2 53 return 1;
nuclear@2 54 }
nuclear@2 55 atexit(cleanup);
nuclear@2 56
nuclear@2 57 glutMainLoop();
nuclear@2 58 }
nuclear@2 59
nuclear@2 60 static bool init()
nuclear@2 61 {
nuclear@8 62 width = glutGet(GLUT_WINDOW_WIDTH) / 2;
nuclear@8 63 height = glutGet(GLUT_WINDOW_HEIGHT) / 2;
nuclear@5 64
nuclear@4 65 if(!(erb = erb_init())) {
nuclear@4 66 return false;
nuclear@4 67 }
nuclear@4 68 erb_setopti(erb, ERB_OPT_WIDTH, width);
nuclear@4 69 erb_setopti(erb, ERB_OPT_HEIGHT, height);
nuclear@4 70
nuclear@19 71 for(size_t i=0; i<sfiles.size(); i++) {
nuclear@19 72 printf("loading scene file: %s\n", sfiles[i]);
nuclear@19 73 if(erb_load_scene(erb, sfiles[i]) == -1) {
nuclear@19 74 return false;
nuclear@19 75 }
nuclear@4 76 }
nuclear@4 77
nuclear@21 78 if(!sfiles.empty()) {
nuclear@21 79 printf("begin rendering\n");
nuclear@21 80 render_pending = true;
nuclear@21 81 glutIdleFunc(idle);
nuclear@21 82 erb_begin_frame(erb, 0);
nuclear@21 83 }
nuclear@4 84
nuclear@8 85 glEnable(GL_TEXTURE_2D);
nuclear@2 86 return true;
nuclear@2 87 }
nuclear@2 88
nuclear@2 89 static void cleanup()
nuclear@2 90 {
nuclear@4 91 erb_destroy(erb);
nuclear@2 92 }
nuclear@2 93
nuclear@2 94 static void resize_rtarget(int xsz, int ysz)
nuclear@2 95 {
nuclear@2 96 static unsigned char *defpix;
nuclear@2 97
nuclear@8 98 width = xsz / 2;
nuclear@8 99 height = ysz / 2;
nuclear@2 100
nuclear@8 101 if(width <= rtex_width && height <= rtex_height) {
nuclear@2 102 return;
nuclear@2 103 }
nuclear@8 104 rtex_width = next_pow2(width);
nuclear@8 105 rtex_height = next_pow2(height);
nuclear@2 106
nuclear@2 107 printf("resizing framebuffer texture: %dx%d\n", rtex_width, rtex_height);
nuclear@2 108
nuclear@2 109 if(!rtex) {
nuclear@2 110 glGenTextures(1, &rtex);
nuclear@2 111 }
nuclear@2 112
nuclear@2 113 delete [] defpix;
nuclear@2 114 defpix = new unsigned char[rtex_width * rtex_height * 4];
nuclear@2 115 unsigned char *ptr = defpix;
nuclear@2 116 for(int i=0; i<rtex_height; i++) {
nuclear@2 117 for(int j=0; j<rtex_width; j++) {
nuclear@2 118 bool chess = ((i >> 4) & 1) == ((j >> 4) & 1);
nuclear@2 119
nuclear@2 120 int val = chess ? 64 : 48;
nuclear@2 121
nuclear@2 122 *ptr++ = val;
nuclear@2 123 *ptr++ = val;
nuclear@2 124 *ptr++ = val;
nuclear@2 125 *ptr++ = 255;
nuclear@2 126 }
nuclear@2 127 }
nuclear@2 128
nuclear@2 129 glBindTexture(GL_TEXTURE_2D, rtex);
nuclear@2 130 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
nuclear@2 131 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_NEAREST);
nuclear@2 132 glTexImage2D(GL_TEXTURE_2D, 0, GL_RGBA32F_ARB, rtex_width, rtex_height, 0, GL_RGBA, GL_UNSIGNED_BYTE, defpix);
nuclear@2 133 }
nuclear@2 134
nuclear@2 135 static void update_rect(int x, int y, int xsz, int ysz, float *pixels)
nuclear@2 136 {
nuclear@2 137 glBindTexture(GL_TEXTURE_2D, rtex);
nuclear@2 138 glTexSubImage2D(GL_TEXTURE_2D, 0, x, y, xsz, ysz, GL_RGBA, GL_FLOAT, pixels);
nuclear@2 139 }
nuclear@2 140
nuclear@4 141 static void idle()
nuclear@4 142 {
nuclear@4 143 glutPostRedisplay();
nuclear@4 144 }
nuclear@4 145
nuclear@2 146 static void display()
nuclear@2 147 {
nuclear@4 148 if(render_pending) {
nuclear@8 149 if(erb_render(erb, 64) == 0) {
nuclear@4 150 render_pending = false;
nuclear@4 151 glutIdleFunc(0);
nuclear@4 152 }
nuclear@4 153 update_rect(0, 0, width, height, erb_get_framebuffer(erb));
nuclear@4 154 }
nuclear@4 155
nuclear@2 156 float maxu = (float)width / (float)rtex_width;
nuclear@2 157 float maxv = (float)height / (float)rtex_height;
nuclear@2 158
nuclear@2 159 glBegin(GL_QUADS);
nuclear@2 160 glTexCoord2f(0, maxv); glVertex2f(-1, -1);
nuclear@2 161 glTexCoord2f(maxu, maxv); glVertex2f(1, -1);
nuclear@2 162 glTexCoord2f(maxu, 0); glVertex2f(1, 1);
nuclear@2 163 glTexCoord2f(0, 0); glVertex2f(-1, 1);
nuclear@2 164 glEnd();
nuclear@2 165
nuclear@2 166 glutSwapBuffers();
nuclear@2 167 assert(glGetError() == GL_NO_ERROR);
nuclear@2 168 }
nuclear@2 169
nuclear@2 170 static void reshape(int x, int y)
nuclear@2 171 {
nuclear@2 172 glViewport(0, 0, x, y);
nuclear@2 173 resize_rtarget(x, y);
nuclear@4 174
nuclear@4 175 erb_setopti(erb, ERB_OPT_WIDTH, width);
nuclear@4 176 erb_setopti(erb, ERB_OPT_HEIGHT, height);
nuclear@2 177 }
nuclear@2 178
nuclear@2 179 static void keyb(unsigned char key, int x, int y)
nuclear@2 180 {
nuclear@2 181 switch(key) {
nuclear@2 182 case 27:
nuclear@2 183 exit(0);
nuclear@4 184
nuclear@4 185 case ' ':
nuclear@4 186 printf("begin rendering\n");
nuclear@4 187 render_pending = true;
nuclear@4 188 glutIdleFunc(idle);
nuclear@4 189 erb_begin_frame(erb, 0);
nuclear@4 190 break;
nuclear@2 191 }
nuclear@9 192
nuclear@10 193 if(erb_input_keyboard(erb, key, true)) {
nuclear@9 194 glutPostRedisplay();
nuclear@9 195 }
nuclear@9 196 }
nuclear@9 197
nuclear@9 198 static void keyb_up(unsigned char key, int x, int y)
nuclear@9 199 {
nuclear@10 200 if(erb_input_keyboard(erb, key, false)) {
nuclear@9 201 glutPostRedisplay();
nuclear@9 202 }
nuclear@2 203 }
nuclear@2 204
nuclear@2 205 static void mouse(int bn, int st, int x, int y)
nuclear@2 206 {
nuclear@10 207 if(erb_input_mouse_button(erb, bn - GLUT_LEFT_BUTTON, st == GLUT_DOWN, x, y)) {
nuclear@9 208 glutPostRedisplay();
nuclear@9 209 }
nuclear@9 210 }
nuclear@9 211
nuclear@9 212 static void motion(int x, int y)
nuclear@9 213 {
nuclear@15 214 if(erb_input_mouse_motion(erb, x, y)) {
nuclear@9 215 glutPostRedisplay();
nuclear@9 216 }
nuclear@9 217 }
nuclear@9 218
nuclear@9 219 static void sball_button(int bn, int state)
nuclear@9 220 {
nuclear@10 221 if(erb_input_6dof_button(erb, bn, state == GLUT_DOWN)) {
nuclear@9 222 glutPostRedisplay();
nuclear@9 223 }
nuclear@9 224 }
nuclear@9 225
nuclear@9 226 static void sball_motion(int x, int y, int z)
nuclear@9 227 {
nuclear@10 228 if(erb_input_6dof_motion(erb, x / 65536.0, y / 65536.0, z / 65536.0)) {
nuclear@9 229 glutPostRedisplay();
nuclear@9 230 }
nuclear@2 231 }
nuclear@2 232
nuclear@2 233 static int next_pow2(int x)
nuclear@2 234 {
nuclear@2 235 int res = 2;
nuclear@2 236 while(res < x) {
nuclear@2 237 res <<= 1;
nuclear@2 238 }
nuclear@2 239 return res;
nuclear@2 240 }