oculus1

annotate src/teapot.c @ 29:9a973ef0e2a3

fixed the performance issue under MacOSX by replacing glutSolidTeapot (which uses glEvalMesh) with my own teapot generator.
author John Tsiombikas <nuclear@member.fsf.org>
date Sun, 27 Oct 2013 06:31:18 +0200
parents
children
rev   line source
nuclear@29 1 #ifndef __APPLE__
nuclear@29 2 #include <GL/gl.h>
nuclear@29 3 #else
nuclear@29 4 #include <OpenGL/gl.h>
nuclear@29 5 #endif
nuclear@29 6
nuclear@29 7 #include "teapot.h"
nuclear@29 8 #include "teapot_data.h"
nuclear@29 9
nuclear@29 10 static void draw_patch(struct vec3 *bez_cp, int *index, int flip, int useg, int vseg, float scale);
nuclear@29 11
nuclear@29 12 int patch_subdivision = 6;
nuclear@29 13
nuclear@29 14 void bezier_teapot(float scale)
nuclear@29 15 {
nuclear@29 16 int i;
nuclear@29 17
nuclear@29 18 scale /= 2.0;
nuclear@29 19
nuclear@29 20 for(i=0; i<NUM_TEAPOT_PATCHES; i++) {
nuclear@29 21 float flip = teapot_part_flip[i];
nuclear@29 22 float rot = teapot_part_rot[i];
nuclear@29 23
nuclear@29 24 glMatrixMode(GL_MODELVIEW);
nuclear@29 25 glPushMatrix();
nuclear@29 26 glTranslatef(0, -3.15 * scale * 0.5, 0);
nuclear@29 27 glRotatef(rot, 0, 1, 0);
nuclear@29 28 glScalef(1, 1, flip);
nuclear@29 29 glRotatef(-90, 1, 0, 0);
nuclear@29 30
nuclear@29 31 draw_patch(teapot_verts, teapot_index + i * 16, flip < 0.0 ? 1 : 0, patch_subdivision, patch_subdivision, scale);
nuclear@29 32
nuclear@29 33 glPopMatrix();
nuclear@29 34 }
nuclear@29 35 }
nuclear@29 36
nuclear@29 37 static void draw_patch(struct vec3 *bez_cp, int *index, int flip, int useg, int vseg, float scale)
nuclear@29 38 {
nuclear@29 39 static const float uoffs[2][4] = {{0, 0, 1, 1}, {1, 1, 0, 0}};
nuclear@29 40 static const float voffs[4] = {0, 1, 1, 0};
nuclear@29 41
nuclear@29 42 int i, j, k;
nuclear@29 43 struct vec3 cp[16];
nuclear@29 44 struct vec3 pt, n;
nuclear@29 45 float u, v;
nuclear@29 46 float du = 1.0 / useg;
nuclear@29 47 float dv = 1.0 / vseg;
nuclear@29 48
nuclear@29 49 /* collect control points */
nuclear@29 50 for(i=0; i<16; i++) {
nuclear@29 51 cp[i] = bez_cp[index[i]];
nuclear@29 52 }
nuclear@29 53
nuclear@29 54 glBegin(GL_QUADS);
nuclear@29 55 glColor3f(1, 1, 1);
nuclear@29 56
nuclear@29 57 u = 0;
nuclear@29 58 for(i=0; i<useg; i++) {
nuclear@29 59 v = 0;
nuclear@29 60 for(j=0; j<vseg; j++) {
nuclear@29 61
nuclear@29 62 for(k=0; k<4; k++) {
nuclear@29 63 pt = bezier_patch(cp, u + uoffs[flip][k] * du, v + voffs[k] * dv);
nuclear@29 64
nuclear@29 65 /* top/bottom normal hack */
nuclear@29 66 if(pt.z > 3.14) {
nuclear@29 67 n.x = n.y = 0.0f;
nuclear@29 68 n.z = 1.0f;
nuclear@29 69 } else if(pt.z < 0.00001) {
nuclear@29 70 n.x = n.y = 0.0f;
nuclear@29 71 n.z = -1.0f;
nuclear@29 72 } else {
nuclear@29 73 n = bezier_patch_norm(cp, u + uoffs[flip][k] * du, v + voffs[k] * dv);
nuclear@29 74 }
nuclear@29 75
nuclear@29 76 glTexCoord2f(u, v);
nuclear@29 77 glNormal3f(n.x, n.y, n.z);
nuclear@29 78 glVertex3f(pt.x * scale, pt.y * scale, pt.z * scale);
nuclear@29 79 }
nuclear@29 80
nuclear@29 81 v += dv;
nuclear@29 82 }
nuclear@29 83 u += du;
nuclear@29 84 }
nuclear@29 85
nuclear@29 86 glEnd();
nuclear@29 87 }