istereo

annotate src/sanegl.c @ 1:4d25539806d2

bollocks
author John Tsiombikas <nuclear@mutantstargoat.com>
date Tue, 06 Sep 2011 12:48:39 +0300
parents
children bb68fac22579
rev   line source
nuclear@1 1 #include <math.h>
nuclear@1 2 #include <string.h>
nuclear@1 3 #include "sanegl.h"
nuclear@1 4
nuclear@1 5 #define MMODE_IDX(x) ((x) - GL_MODELVIEW)
nuclear@1 6 #define MAT_STACK_SIZE 32
nuclear@1 7 #define MAT_IDENT {1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1}
nuclear@1 8
nuclear@1 9 #define MAX_VERTS 512
nuclear@1 10
nuclear@1 11 typedef struct { float x, y; } vec2_t;
nuclear@1 12 typedef struct { float x, y, z; } vec3_t;
nuclear@1 13 typedef struct { float x, y, z, w; } vec4_t;
nuclear@1 14
nuclear@1 15 static int mm_idx = 0;
nuclear@1 16 static float mat_stack[3][MAT_STACK_SIZE][16] = {{MAT_IDENT}, {MAT_IDENT}, {MAT_IDENT}};
nuclear@1 17 static int stack_top[3];
nuclear@1 18 static float mat_mvp[16];
nuclear@1 19 static int mvp_valid;
nuclear@1 20 static int prim = -1;
nuclear@1 21
nuclear@1 22 static vec3_t cur_normal;
nuclear@1 23 static vec4_t cur_color, cur_attrib;
nuclear@1 24 static vec2_t cur_texcoord;
nuclear@1 25
nuclear@1 26 static vec4_t *vert_arr, *col_arr, *attr_arr;
nuclear@1 27 static vec3_t *norm_arr;
nuclear@1 28 static vec2_t *texc_arr;
nuclear@1 29 static int vloc, nloc, cloc, tloc, aloc;
nuclear@1 30
nuclear@1 31
nuclear@1 32 void gl_matrix_mode(int mm)
nuclear@1 33 {
nuclear@1 34 mm_idx = MMODE_IDX(mm);
nuclear@1 35 }
nuclear@1 36
nuclear@1 37 void gl_push_matrix(void)
nuclear@1 38 {
nuclear@1 39 int top = stack_top[mm_idx];
nuclear@1 40
nuclear@1 41 memcpy(mat_stack[mm_idx][top + 1], mat_stack[mm_idx][top], 16 * sizeof(float));
nuclear@1 42 stack_top[mm_idx]++;
nuclear@1 43 mvp_valid = 0;
nuclear@1 44 }
nuclear@1 45
nuclear@1 46 void gl_pop_matrix(void)
nuclear@1 47 {
nuclear@1 48 stack_top[mm_idx]--;
nuclear@1 49 mvp_valid = 0;
nuclear@1 50 }
nuclear@1 51
nuclear@1 52 void gl_load_identity(void)
nuclear@1 53 {
nuclear@1 54 static const float idmat[] = MAT_IDENT;
nuclear@1 55 int top = stack_top[mm_idx];
nuclear@1 56 float *mat = mat_stack[mm_idx][top];
nuclear@1 57
nuclear@1 58 memcpy(mat, idmat, sizeof idmat);
nuclear@1 59 mvp_valid = 0;
nuclear@1 60 }
nuclear@1 61
nuclear@1 62 void gl_load_matrixf(const float *m)
nuclear@1 63 {
nuclear@1 64 int top = stack_top[mm_idx];
nuclear@1 65 float *mat = mat_stack[mm_idx][top];
nuclear@1 66
nuclear@1 67 memcpy(mat, m, 16 * sizeof *mat);
nuclear@1 68 mvp_valid = 0;
nuclear@1 69 }
nuclear@1 70
nuclear@1 71 #define M(i, j) ((i << 2) + j)
nuclear@1 72
nuclear@1 73 void gl_mult_matrixf(const float *m2)
nuclear@1 74 {
nuclear@1 75 int i, j;
nuclear@1 76 int top = stack_top[mm_idx];
nuclear@1 77 float *m1 = mat_stack[mm_idx][top];
nuclear@1 78 float res[16];
nuclear@1 79
nuclear@1 80 for(i=0; i<4; i++) {
nuclear@1 81 for(j=0; j<4; j++) {
nuclear@1 82 res[M(i,j)] = m1[M(i,0)] * m2[M(0,j)] +
nuclear@1 83 m1[M(i,1)] * m2[M(1,j)] +
nuclear@1 84 m1[M(i,2)] * m2[M(2,j)] +
nuclear@1 85 m1[M(i,3)] * m2[M(3,j)];
nuclear@1 86 }
nuclear@1 87 }
nuclear@1 88
nuclear@1 89 memcpy(m1, res, sizeof res);
nuclear@1 90 mvp_valid = 0;
nuclear@1 91 }
nuclear@1 92
nuclear@1 93 void gl_translatef(float x, float y, float z)
nuclear@1 94 {
nuclear@1 95 float mat[] = MAT_IDENT;
nuclear@1 96
nuclear@1 97 mat[12] = x;
nuclear@1 98 mat[13] = y;
nuclear@1 99 mat[14] = z;
nuclear@1 100
nuclear@1 101 gl_mult_matrixf(mat);
nuclear@1 102 }
nuclear@1 103
nuclear@1 104 void gl_rotatef(float angle, float x, float y, float z)
nuclear@1 105 {
nuclear@1 106 float mat[] = MAT_IDENT;
nuclear@1 107
nuclear@1 108 float angle_rad = M_PI * angle / 180.0;
nuclear@1 109 float sina = sin(angle_rad);
nuclear@1 110 float cosa = cos(angle_rad);
nuclear@1 111 float one_minus_cosa = 1.0 - cosa;
nuclear@1 112 float nxsq = x * x;
nuclear@1 113 float nysq = y * y;
nuclear@1 114 float nzsq = z * z;
nuclear@1 115
nuclear@1 116 mat[0] = nxsq + (1.0 - nxsq) * cosa;
nuclear@1 117 mat[4] = x * y * one_minus_cosa - z * sina;
nuclear@1 118 mat[8] = x * z * one_minus_cosa + y * sina;
nuclear@1 119 mat[1] = x * y * one_minus_cosa + z * sina;
nuclear@1 120 mat[5] = nysq + (1.0 - nysq) * cosa;
nuclear@1 121 mat[9] = y * z * one_minus_cosa - x * sina;
nuclear@1 122 mat[2] = x * z * one_minus_cosa - y * sina;
nuclear@1 123 mat[6] = y * z * one_minus_cosa + x * sina;
nuclear@1 124 mat[10] = nzsq + (1.0 - nzsq) * cosa;
nuclear@1 125
nuclear@1 126 gl_mult_matrixf(mat);
nuclear@1 127 }
nuclear@1 128
nuclear@1 129 void gl_scalef(float x, float y, float z)
nuclear@1 130 {
nuclear@1 131 float mat[] = MAT_IDENT;
nuclear@1 132
nuclear@1 133 mat[0] = x;
nuclear@1 134 mat[5] = y;
nuclear@1 135 mat[10] = z;
nuclear@1 136
nuclear@1 137 gl_mult_matrixf(mat);
nuclear@1 138 }
nuclear@1 139
nuclear@1 140 void gl_ortho(float left, float right, float bottom, float top, float near, float far)
nuclear@1 141 {
nuclear@1 142 float mat[] = MAT_IDENT;
nuclear@1 143
nuclear@1 144 float dx = right - left;
nuclear@1 145 float dy = top - bottom;
nuclear@1 146 float dz = far - near;
nuclear@1 147
nuclear@1 148 float tx = -(right + left) / dx;
nuclear@1 149 float ty = -(top + bottom) / dy;
nuclear@1 150 float tz = -(far + near) / dz;
nuclear@1 151
nuclear@1 152 float sx = 2.0 / dx;
nuclear@1 153 float sy = 2.0 / dy;
nuclear@1 154 float sz = -2.0 / dz;
nuclear@1 155
nuclear@1 156 mat[0] = sx;
nuclear@1 157 mat[5] = sy;
nuclear@1 158 mat[10] = sz;
nuclear@1 159 mat[12] = tx;
nuclear@1 160 mat[13] = ty;
nuclear@1 161 mat[14] = tz;
nuclear@1 162
nuclear@1 163 gl_mult_matrixf(mat);
nuclear@1 164 }
nuclear@1 165
nuclear@1 166 void gl_frustum(float left, float right, float bottom, float top, float near, float far)
nuclear@1 167 {
nuclear@1 168 float mat[] = MAT_IDENT;
nuclear@1 169
nuclear@1 170 float dx = right - left;
nuclear@1 171 float dy = top - bottom;
nuclear@1 172 float dz = far - near;
nuclear@1 173
nuclear@1 174 float a = (right + left) / dx;
nuclear@1 175 float b = (top + bottom) / dy;
nuclear@1 176 float c = -(far + near) / dz;
nuclear@1 177 float d = -2.0 * far * near / dz;
nuclear@1 178
nuclear@1 179 mat[0] = 2.0 * near / dx;
nuclear@1 180 mat[5] = 2.0 * near / dy;
nuclear@1 181 mat[8] = a;
nuclear@1 182 mat[9] = b;
nuclear@1 183 mat[10] = c;
nuclear@1 184 mat[11] = -1.0;
nuclear@1 185 mat[14] = d;
nuclear@1 186
nuclear@1 187 gl_mult_matrixf(mat);
nuclear@1 188 }
nuclear@1 189
nuclear@1 190 void glu_perspective(float vfov, float aspect, float near, float far)
nuclear@1 191 {
nuclear@1 192 float x = near * tan(vfov / 2.0);
nuclear@1 193 gl_frustum(-aspect * x, aspect * x, -x, x, near, far);
nuclear@1 194 }
nuclear@1 195
nuclear@1 196 void gl_apply_xform(unsigned int prog)
nuclear@1 197 {
nuclear@1 198 int loc, mvidx, pidx, tidx, mvtop, ptop, ttop;
nuclear@1 199
nuclear@1 200 mvidx = MMODE_IDX(GL_MODELVIEW);
nuclear@1 201 pidx = MMODE_IDX(GL_PROJECTION);
nuclear@1 202 tidx = MMODE_IDX(GL_TEXTURE);
nuclear@1 203
nuclear@1 204 mvtop = stack_top[mvidx];
nuclear@1 205 ptop = stack_top[pidx];
nuclear@1 206 ttop = stack_top[tidx];
nuclear@1 207
nuclear@1 208 if((loc = glGetUniformLocation(prog, "matrix_modelview")) != -1) {
nuclear@1 209 glUniformMatrix4fv(loc, 16, 0, mat_stack[mvidx][mvtop]);
nuclear@1 210 }
nuclear@1 211
nuclear@1 212 if((loc = glGetUniformLocation(prog, "matrix_projection")) != -1) {
nuclear@1 213 glUniformMatrix4fv(loc, 16, 0, mat_stack[pidx][ptop]);
nuclear@1 214 }
nuclear@1 215
nuclear@1 216 if((loc = glGetUniformLocation(prog, "matrix_texture")) != -1) {
nuclear@1 217 glUniformMatrix4fv(loc, 16, 0, mat_stack[tidx][ttop]);
nuclear@1 218 }
nuclear@1 219
nuclear@1 220 if((loc = glGetUniformLocation(prog, "matrix_normal")) != -1) {
nuclear@1 221 float nmat[9];
nuclear@1 222
nuclear@1 223 nmat[0] = mat_stack[mvidx][mvtop][0];
nuclear@1 224 nmat[1] = mat_stack[mvidx][mvtop][1];
nuclear@1 225 nmat[2] = mat_stack[mvidx][mvtop][2];
nuclear@1 226 nmat[3] = mat_stack[mvidx][mvtop][4];
nuclear@1 227 nmat[4] = mat_stack[mvidx][mvtop][5];
nuclear@1 228 nmat[5] = mat_stack[mvidx][mvtop][6];
nuclear@1 229 nmat[6] = mat_stack[mvidx][mvtop][8];
nuclear@1 230 nmat[7] = mat_stack[mvidx][mvtop][9];
nuclear@1 231 nmat[8] = mat_stack[mvidx][mvtop][10];
nuclear@1 232 glUniformMatrix3fv(loc, 9, 0, nmat);
nuclear@1 233 }
nuclear@1 234
nuclear@1 235 if((loc = glGetUniformLocation(prog, "matrix_modelview_projection")) != -1) {
nuclear@1 236 if(!mvp_valid) {
nuclear@1 237 /* TODO calc mvp */
nuclear@1 238 }
nuclear@1 239 glUniformMatrix4fv(loc, 16, 0, mat_mvp);
nuclear@1 240 }
nuclear@1 241 }