X-Git-Url: http://git.mutantstargoat.com/user/nuclear/?a=blobdiff_plain;ds=sidebyside;f=progs%2Fdemos%2Fshapes%2Fshapes.c;h=e07312dfae225ddf52cf4520f301f1c0b26194b8;hb=aaa5cd53fa964494b8cadf024f64ac459f1874cc;hp=c6527fc8f30d62bc540b0c66144b0b7d4d08ac29;hpb=8c9773ab36947fcaad5826eb9962d203d914c86d;p=freeglut
diff --git a/progs/demos/shapes/shapes.c b/progs/demos/shapes/shapes.c
index c6527fc..e07312d 100644
--- a/progs/demos/shapes/shapes.c
+++ b/progs/demos/shapes/shapes.c
@@ -15,6 +15,8 @@
- i I Show info
- p P Toggle perspective or orthographic projection
- r R Toggle fixed or animated rotation around model X-axis
+ - s S Toggle toggle fixed function or shader render path
+ - n N Toggle visualization of object's normal vectors
- = + Increase \a slices
- - _ Decreate \a slices
- , < Decreate \a stacks
@@ -50,6 +52,15 @@
#include
#endif
+/* report GL errors, if any, to stderr */
+void checkError(const char *functionName)
+{
+ GLenum error;
+ while (( error = glGetError() ) != GL_NO_ERROR) {
+ fprintf (stderr, "GL error 0x%X detected in %s\n", error, functionName);
+ }
+}
+
/*
* OpenGL 2+ shader mode needs some function and macro definitions,
* avoiding a dependency on additional libraries like GLEW or the
@@ -82,9 +93,12 @@ typedef char ourGLchar;
#define APIENTRY
#endif
+#ifndef GL_VERSION_1_5
typedef void (APIENTRY *PFNGLGENBUFFERSPROC) (GLsizei n, GLuint *buffers);
typedef void (APIENTRY *PFNGLBINDBUFFERPROC) (GLenum target, GLuint buffer);
typedef void (APIENTRY *PFNGLBUFFERDATAPROC) (GLenum target, ourGLsizeiptr size, const GLvoid *data, GLenum usage);
+#endif
+#ifndef GL_VERSION_2_0
typedef GLuint (APIENTRY *PFNGLCREATESHADERPROC) (GLenum type);
typedef void (APIENTRY *PFNGLSHADERSOURCEPROC) (GLuint shader, GLsizei count, const ourGLchar **string, const GLint *length);
typedef void (APIENTRY *PFNGLCOMPILESHADERPROC) (GLuint shader);
@@ -100,6 +114,7 @@ typedef GLint (APIENTRY *PFNGLGETATTRIBLOCATIONPROC) (GLuint program, const ourG
typedef GLint (APIENTRY *PFNGLGETUNIFORMLOCATIONPROC) (GLuint program, const ourGLchar *name);
typedef void (APIENTRY *PFNGLUNIFORMMATRIX4FVPROC) (GLint location, GLsizei count, GLboolean transpose, const GLfloat *value);
typedef void (APIENTRY *PFNGLUNIFORMMATRIX3FVPROC) (GLint location, GLsizei count, GLboolean transpose, const GLfloat *value);
+#endif
PFNGLCREATESHADERPROC gl_CreateShader;
PFNGLSHADERSOURCEPROC gl_ShaderSource;
@@ -144,9 +159,9 @@ const ourGLchar *vertexShaderSource[] = {
" */",
"attribute vec3 fg_coord;",
"attribute vec3 fg_normal;",
- "varying vec4 position; // position of the vertex (and fragment) in world space",
- "varying vec3 varyingNormalDirection; // surface normal vector in world space",
- "uniform mat4 m, p; // don't need v, as always identity in our demo",
+ "varying vec4 position; /* position of the vertex (and fragment) in world space */",
+ "varying vec3 varyingNormalDirection; /* surface normal vector in world space */",
+ "uniform mat4 m, p; /* don't need v, as always identity in our demo */",
"uniform mat3 m_3x3_inv_transp;",
" ",
"void main()",
@@ -155,7 +170,7 @@ const ourGLchar *vertexShaderSource[] = {
" position = m * fg_coord4;",
" varyingNormalDirection = normalize(m_3x3_inv_transp * fg_normal);",
" ",
- " mat4 mvp = p*m; // normally p*v*m",
+ " mat4 mvp = p*m; /* normally p*v*m */",
" gl_Position = mvp * fg_coord4;",
"}"
};
@@ -166,9 +181,9 @@ const ourGLchar *fragmentShaderSource[] = {
" * This file is in the public domain.",
" * Contributors: Martin Kraus, Sylvain Beucler",
" */",
- "varying vec4 position; // position of the vertex (and fragment) in world space",
- "varying vec3 varyingNormalDirection; // surface normal vector in world space",
- "//uniform mat4 v_inv; // in this demo, the view matrix is always an identity matrix",
+ "varying vec4 position; /* position of the vertex (and fragment) in world space */",
+ "varying vec3 varyingNormalDirection; /* surface normal vector in world space */",
+ "/* uniform mat4 v_inv; // in this demo, the view matrix is always an identity matrix */",
" ",
"struct lightSource",
"{",
@@ -181,13 +196,13 @@ const ourGLchar *fragmentShaderSource[] = {
"};",
"lightSource light0 = lightSource(",
" vec4(2.0, 5.0, 5.0, 0.0),",
- " vec4(1.0, 1.0, 1.0, 1.0),",
- " vec4(1.0, 1.0, 1.0, 1.0),",
- " 0.0, 1.0, 0.0,",
+ " vec4(1.0, 1.0, 1.0, 1.0),",
+ " vec4(1.0, 1.0, 1.0, 1.0),",
+ " 0.0, 1.0, 0.0,",
" 180.0, 0.0,",
" vec3(0.0, 0.0, 0.0)",
");",
- "vec4 scene_ambient = vec4(1.0, 0.0, 0.0, 1.0);",
+ "vec4 scene_ambient = vec4(0.2, 0.2, 0.2, 1.0);",
" ",
"struct material",
"{",
@@ -197,8 +212,8 @@ const ourGLchar *fragmentShaderSource[] = {
" float shininess;",
"};",
"material frontMaterial = material(",
- " vec4(0.7, 0.7, 0.7, 1.0),",
- " vec4(0.8, 0.8, 0.8, 1.0),",
+ " vec4(1.0, 0.0, 0.0, 1.0),",
+ " vec4(1.0, 0.0, 0.0, 1.0),",
" vec4(1.0, 1.0, 1.0, 1.0),",
" 100.0",
");",
@@ -206,17 +221,17 @@ const ourGLchar *fragmentShaderSource[] = {
"void main()",
"{",
" vec3 normalDirection = normalize(varyingNormalDirection);",
- " //vec3 viewDirection = normalize(vec3(v_inv * vec4(0.0, 0.0, 0.0, 1.0) - position));",
- " vec3 viewDirection = normalize(vec3(vec4(0.0, 0.0, 0.0, 1.0) - position)); // in this demo, the view matrix is always an identity matrix",
+ " /* vec3 viewDirection = normalize(vec3(v_inv * vec4(0.0, 0.0, 0.0, 1.0) - position)); */",
+ " vec3 viewDirection = normalize(vec3(vec4(0.0, 0.0, 0.0, 1.0) - position)); /* in this demo, the view matrix is always an identity matrix */",
" vec3 lightDirection;",
" float attenuation;",
" ",
- " if (0.0 == light0.position.w) // directional light?",
+ " if (0.0 == light0.position.w) /* directional light? */",
" {",
- " attenuation = 1.0; // no attenuation",
+ " attenuation = 1.0; /* no attenuation */",
" lightDirection = normalize(vec3(light0.position));",
" } ",
- " else // point light or spotlight (or other kind of light) ",
+ " else /* point light or spotlight (or other kind of light) */",
" {",
" vec3 positionToLightSource = vec3(light0.position - position);",
" float distance = length(positionToLightSource);",
@@ -225,10 +240,10 @@ const ourGLchar *fragmentShaderSource[] = {
" + light0.linearAttenuation * distance",
" + light0.quadraticAttenuation * distance * distance);",
" ",
- " if (light0.spotCutoff <= 90.0) // spotlight?",
+ " if (light0.spotCutoff <= 90.0) /* spotlight? */",
" {",
" float clampedCosine = max(0.0, dot(-lightDirection, light0.spotDirection));",
- " if (clampedCosine < cos(radians(light0.spotCutoff))) // outside of spotlight cone?",
+ " if (clampedCosine < cos(radians(light0.spotCutoff))) /* outside of spotlight cone? */",
" {",
" attenuation = 0.0;",
" }",
@@ -246,11 +261,11 @@ const ourGLchar *fragmentShaderSource[] = {
" * max(0.0, dot(normalDirection, lightDirection));",
" ",
" vec3 specularReflection;",
- " if (dot(normalDirection, lightDirection) < 0.0) // light source on the wrong side?",
+ " if (dot(normalDirection, lightDirection) < 0.0) /* light source on the wrong side? */",
" {",
- " specularReflection = vec3(0.0, 0.0, 0.0); // no specular reflection",
+ " specularReflection = vec3(0.0, 0.0, 0.0); /* no specular reflection */",
" }",
- " else // light source on the right side",
+ " else /* light source on the right side */",
" {",
" specularReflection = attenuation * vec3(light0.specular) * vec3(frontMaterial.specular) ",
" * pow(max(0.0, dot(reflect(-lightDirection, normalDirection), viewDirection)), frontMaterial.shininess);",
@@ -282,12 +297,13 @@ GLint getAttribOrUniformLocation(const char* name, GLuint program, GLboolean isA
return uniform;
}
+ checkError ("getAttribOrUniformLocation");
}
GLuint program;
GLint attribute_fg_coord = -1, attribute_fg_normal = -1;
GLint uniform_m = -1, uniform_p = -1, uniform_m_3x3_inv_transp = -1;
-GLint shaderReady = 0; // Set to 1 when all initialization went well, to -1 when somehow unusable.
+GLint shaderReady = 0; /* Set to 1 when all initialization went well, to -1 when shader somehow unusable. */
@@ -305,12 +321,16 @@ void compileAndCheck(GLuint shader)
fprintf (stderr, "compile log: %s\n", infoLog);
free (infoLog);
}
+ checkError ("compileAndCheck");
}
GLuint compileShaderSource(GLenum type, GLsizei count, const ourGLchar **string)
{
GLuint shader = gl_CreateShader (type);
gl_ShaderSource (shader, count, string, NULL);
+
+ checkError ("compileShaderSource");
+
compileAndCheck (shader);
return shader;
}
@@ -329,6 +349,7 @@ void linkAndCheck(GLuint program)
fprintf (stderr, "link log: %s\n", infoLog);
free (infoLog);
}
+ checkError ("linkAndCheck");
}
void createProgram(GLuint vertexShader, GLuint fragmentShader)
@@ -340,6 +361,9 @@ void createProgram(GLuint vertexShader, GLuint fragmentShader)
if (fragmentShader != 0) {
gl_AttachShader (program, fragmentShader);
}
+
+ checkError ("createProgram");
+
linkAndCheck (program);
}
@@ -353,6 +377,8 @@ void initShader(void)
GLuint fragmentShader =
compileShaderSource (GL_FRAGMENT_SHADER, fragmentShaderLines, fragmentShaderSource);
+ checkError ("initShader - 1");
+
createProgram (vertexShader, fragmentShader);
gl_UseProgram (program);
@@ -370,6 +396,8 @@ void initShader(void)
shaderReady = -1;
else
shaderReady = 1;
+
+ checkError ("initShader - 2");
}
/*
@@ -394,6 +422,18 @@ static float ar;
static GLboolean persProject = GL_TRUE;
static GLboolean animateXRot = GL_FALSE;
static GLboolean useShader = GL_FALSE;
+static GLboolean visNormals = GL_FALSE;
+
+/*
+ * Enum to tell drawSizeInfo what to draw for each object
+ */
+#define GEO_NO_SIZE 0
+#define GEO_SIZE 1
+#define GEO_SCALE 2
+#define GEO_INNER_OUTER_RAD 4
+#define GEO_RAD 8
+#define GEO_BASE_HEIGHT 16
+#define GEO_RAD_HEIGHT 32
/*
* These one-liners draw particular objects, fetching appropriate
@@ -418,10 +458,10 @@ static void drawSolidTorus(void) { glutSolidTorus(irad,orad,slices
static void drawWireTorus(void) { glutWireTorus (irad,orad,slices,stacks); }
static void drawSolidSphere(void) { glutSolidSphere(orad,slices,stacks); } /* orad doubles as size input */
static void drawWireSphere(void) { glutWireSphere(orad,slices,stacks); } /* orad doubles as size input */
-static void drawSolidCone(void) { glutSolidCone(orad,orad,slices,stacks); } /* orad doubles as size input */
-static void drawWireCone(void) { glutWireCone(orad,orad,slices,stacks); } /* orad doubles as size input */
-static void drawSolidCylinder(void) { glutSolidCylinder(orad,orad,slices,stacks); } /* orad doubles as size input */
-static void drawWireCylinder(void) { glutWireCylinder(orad,orad,slices,stacks); } /* orad doubles as size input */
+static void drawSolidCone(void) { glutSolidCone(irad,orad,slices,stacks); } /* irad doubles as base input, and orad as height input */
+static void drawWireCone(void) { glutWireCone(irad,orad,slices,stacks); } /* irad doubles as base input, and orad as height input */
+static void drawSolidCylinder(void) { glutSolidCylinder(irad,orad,slices,stacks); } /* irad doubles as radius input, and orad as height input */
+static void drawWireCylinder(void) { glutWireCylinder(irad,orad,slices,stacks); } /* irad doubles as radius input, and orad as height input */
static void drawSolidTeapot(void)
{
/* per Glut manpage, it should be noted that the teapot is rendered
@@ -441,54 +481,56 @@ static void drawWireTeapot(void)
glFrontFace(GL_CCW);
}
-#define RADIUS 1.0f
+#define RADIUSFAC 0.70710678118654752440084436210485f
static void drawSolidCuboctahedron(void)
{
+ GLfloat radius = RADIUSFAC*(GLfloat)orad; /* orad doubles as size */
glBegin( GL_TRIANGLES );
- glNormal3d( 0.577350269189, 0.577350269189, 0.577350269189); glVertex3d( RADIUS, RADIUS, 0.0 ); glVertex3d( 0.0, RADIUS, RADIUS ); glVertex3d( RADIUS, 0.0, RADIUS );
- glNormal3d( 0.577350269189, 0.577350269189,-0.577350269189); glVertex3d( RADIUS, RADIUS, 0.0 ); glVertex3d( RADIUS, 0.0,-RADIUS ); glVertex3d( 0.0, RADIUS,-RADIUS );
- glNormal3d( 0.577350269189,-0.577350269189, 0.577350269189); glVertex3d( RADIUS,-RADIUS, 0.0 ); glVertex3d( RADIUS, 0.0, RADIUS ); glVertex3d( 0.0,-RADIUS, RADIUS );
- glNormal3d( 0.577350269189,-0.577350269189,-0.577350269189); glVertex3d( RADIUS,-RADIUS, 0.0 ); glVertex3d( 0.0,-RADIUS,-RADIUS ); glVertex3d( RADIUS, 0.0,-RADIUS );
- glNormal3d(-0.577350269189, 0.577350269189, 0.577350269189); glVertex3d(-RADIUS, RADIUS, 0.0 ); glVertex3d(-RADIUS, 0.0, RADIUS ); glVertex3d( 0.0, RADIUS, RADIUS );
- glNormal3d(-0.577350269189, 0.577350269189,-0.577350269189); glVertex3d(-RADIUS, RADIUS, 0.0 ); glVertex3d( 0.0, RADIUS,-RADIUS ); glVertex3d(-RADIUS, 0.0,-RADIUS );
- glNormal3d(-0.577350269189,-0.577350269189, 0.577350269189); glVertex3d(-RADIUS,-RADIUS, 0.0 ); glVertex3d( 0.0,-RADIUS, RADIUS ); glVertex3d(-RADIUS, 0.0, RADIUS );
- glNormal3d(-0.577350269189,-0.577350269189,-0.577350269189); glVertex3d(-RADIUS,-RADIUS, 0.0 ); glVertex3d(-RADIUS, 0.0,-RADIUS ); glVertex3d( 0.0,-RADIUS,-RADIUS );
+ glNormal3d( 0.577350269189, 0.577350269189, 0.577350269189); glVertex3d( radius, radius, 0.0 ); glVertex3d( 0.0, radius, radius ); glVertex3d( radius, 0.0, radius );
+ glNormal3d( 0.577350269189, 0.577350269189,-0.577350269189); glVertex3d( radius, radius, 0.0 ); glVertex3d( radius, 0.0,-radius ); glVertex3d( 0.0, radius,-radius );
+ glNormal3d( 0.577350269189,-0.577350269189, 0.577350269189); glVertex3d( radius,-radius, 0.0 ); glVertex3d( radius, 0.0, radius ); glVertex3d( 0.0,-radius, radius );
+ glNormal3d( 0.577350269189,-0.577350269189,-0.577350269189); glVertex3d( radius,-radius, 0.0 ); glVertex3d( 0.0,-radius,-radius ); glVertex3d( radius, 0.0,-radius );
+ glNormal3d(-0.577350269189, 0.577350269189, 0.577350269189); glVertex3d(-radius, radius, 0.0 ); glVertex3d(-radius, 0.0, radius ); glVertex3d( 0.0, radius, radius );
+ glNormal3d(-0.577350269189, 0.577350269189,-0.577350269189); glVertex3d(-radius, radius, 0.0 ); glVertex3d( 0.0, radius,-radius ); glVertex3d(-radius, 0.0,-radius );
+ glNormal3d(-0.577350269189,-0.577350269189, 0.577350269189); glVertex3d(-radius,-radius, 0.0 ); glVertex3d( 0.0,-radius, radius ); glVertex3d(-radius, 0.0, radius );
+ glNormal3d(-0.577350269189,-0.577350269189,-0.577350269189); glVertex3d(-radius,-radius, 0.0 ); glVertex3d(-radius, 0.0,-radius ); glVertex3d( 0.0,-radius,-radius );
glEnd();
glBegin( GL_QUADS );
- glNormal3d( 1.0, 0.0, 0.0 ); glVertex3d( RADIUS, RADIUS, 0.0 ); glVertex3d( RADIUS, 0.0, RADIUS ); glVertex3d( RADIUS,-RADIUS, 0.0 ); glVertex3d( RADIUS, 0.0,-RADIUS );
- glNormal3d(-1.0, 0.0, 0.0 ); glVertex3d(-RADIUS, RADIUS, 0.0 ); glVertex3d(-RADIUS, 0.0,-RADIUS ); glVertex3d(-RADIUS,-RADIUS, 0.0 ); glVertex3d(-RADIUS, 0.0, RADIUS );
- glNormal3d( 0.0, 1.0, 0.0 ); glVertex3d( RADIUS, RADIUS, 0.0 ); glVertex3d( 0.0, RADIUS,-RADIUS ); glVertex3d(-RADIUS, RADIUS, 0.0 ); glVertex3d( 0.0, RADIUS, RADIUS );
- glNormal3d( 0.0,-1.0, 0.0 ); glVertex3d( RADIUS,-RADIUS, 0.0 ); glVertex3d( 0.0,-RADIUS, RADIUS ); glVertex3d(-RADIUS,-RADIUS, 0.0 ); glVertex3d( 0.0,-RADIUS,-RADIUS );
- glNormal3d( 0.0, 0.0, 1.0 ); glVertex3d( RADIUS, 0.0, RADIUS ); glVertex3d( 0.0, RADIUS, RADIUS ); glVertex3d(-RADIUS, 0.0, RADIUS ); glVertex3d( 0.0,-RADIUS, RADIUS );
- glNormal3d( 0.0, 0.0,-1.0 ); glVertex3d( RADIUS, 0.0,-RADIUS ); glVertex3d( 0.0,-RADIUS,-RADIUS ); glVertex3d(-RADIUS, 0.0,-RADIUS ); glVertex3d( 0.0, RADIUS,-RADIUS );
+ glNormal3d( 1.0, 0.0, 0.0 ); glVertex3d( radius, radius, 0.0 ); glVertex3d( radius, 0.0, radius ); glVertex3d( radius,-radius, 0.0 ); glVertex3d( radius, 0.0,-radius );
+ glNormal3d(-1.0, 0.0, 0.0 ); glVertex3d(-radius, radius, 0.0 ); glVertex3d(-radius, 0.0,-radius ); glVertex3d(-radius,-radius, 0.0 ); glVertex3d(-radius, 0.0, radius );
+ glNormal3d( 0.0, 1.0, 0.0 ); glVertex3d( radius, radius, 0.0 ); glVertex3d( 0.0, radius,-radius ); glVertex3d(-radius, radius, 0.0 ); glVertex3d( 0.0, radius, radius );
+ glNormal3d( 0.0,-1.0, 0.0 ); glVertex3d( radius,-radius, 0.0 ); glVertex3d( 0.0,-radius, radius ); glVertex3d(-radius,-radius, 0.0 ); glVertex3d( 0.0,-radius,-radius );
+ glNormal3d( 0.0, 0.0, 1.0 ); glVertex3d( radius, 0.0, radius ); glVertex3d( 0.0, radius, radius ); glVertex3d(-radius, 0.0, radius ); glVertex3d( 0.0,-radius, radius );
+ glNormal3d( 0.0, 0.0,-1.0 ); glVertex3d( radius, 0.0,-radius ); glVertex3d( 0.0,-radius,-radius ); glVertex3d(-radius, 0.0,-radius ); glVertex3d( 0.0, radius,-radius );
glEnd();
}
static void drawWireCuboctahedron(void)
{
+ GLfloat radius = RADIUSFAC*(GLfloat)orad; /* orad doubles as size */
glBegin( GL_LINE_LOOP );
- glNormal3d( 1.0, 0.0, 0.0 ); glVertex3d( RADIUS, RADIUS, 0.0 ); glVertex3d( RADIUS, 0.0, RADIUS ); glVertex3d( RADIUS,-RADIUS, 0.0 ); glVertex3d( RADIUS, 0.0,-RADIUS );
+ glNormal3d( 1.0, 0.0, 0.0 ); glVertex3d( radius, radius, 0.0 ); glVertex3d( radius, 0.0, radius ); glVertex3d( radius,-radius, 0.0 ); glVertex3d( radius, 0.0,-radius );
glEnd();
glBegin( GL_LINE_LOOP );
- glNormal3d(-1.0, 0.0, 0.0 ); glVertex3d(-RADIUS, RADIUS, 0.0 ); glVertex3d(-RADIUS, 0.0,-RADIUS ); glVertex3d(-RADIUS,-RADIUS, 0.0 ); glVertex3d(-RADIUS, 0.0, RADIUS );
+ glNormal3d(-1.0, 0.0, 0.0 ); glVertex3d(-radius, radius, 0.0 ); glVertex3d(-radius, 0.0,-radius ); glVertex3d(-radius,-radius, 0.0 ); glVertex3d(-radius, 0.0, radius );
glEnd();
glBegin( GL_LINE_LOOP );
- glNormal3d( 0.0, 1.0, 0.0 ); glVertex3d( RADIUS, RADIUS, 0.0 ); glVertex3d( 0.0, RADIUS,-RADIUS ); glVertex3d(-RADIUS, RADIUS, 0.0 ); glVertex3d( 0.0, RADIUS, RADIUS );
+ glNormal3d( 0.0, 1.0, 0.0 ); glVertex3d( radius, radius, 0.0 ); glVertex3d( 0.0, radius,-radius ); glVertex3d(-radius, radius, 0.0 ); glVertex3d( 0.0, radius, radius );
glEnd();
glBegin( GL_LINE_LOOP );
- glNormal3d( 0.0,-1.0, 0.0 ); glVertex3d( RADIUS,-RADIUS, 0.0 ); glVertex3d( 0.0,-RADIUS, RADIUS ); glVertex3d(-RADIUS,-RADIUS, 0.0 ); glVertex3d( 0.0,-RADIUS,-RADIUS );
+ glNormal3d( 0.0,-1.0, 0.0 ); glVertex3d( radius,-radius, 0.0 ); glVertex3d( 0.0,-radius, radius ); glVertex3d(-radius,-radius, 0.0 ); glVertex3d( 0.0,-radius,-radius );
glEnd();
glBegin( GL_LINE_LOOP );
- glNormal3d( 0.0, 0.0, 1.0 ); glVertex3d( RADIUS, 0.0, RADIUS ); glVertex3d( 0.0, RADIUS, RADIUS ); glVertex3d(-RADIUS, 0.0, RADIUS ); glVertex3d( 0.0,-RADIUS, RADIUS );
+ glNormal3d( 0.0, 0.0, 1.0 ); glVertex3d( radius, 0.0, radius ); glVertex3d( 0.0, radius, radius ); glVertex3d(-radius, 0.0, radius ); glVertex3d( 0.0,-radius, radius );
glEnd();
glBegin( GL_LINE_LOOP );
- glNormal3d( 0.0, 0.0,-1.0 ); glVertex3d( RADIUS, 0.0,-RADIUS ); glVertex3d( 0.0,-RADIUS,-RADIUS ); glVertex3d(-RADIUS, 0.0,-RADIUS ); glVertex3d( 0.0, RADIUS,-RADIUS );
+ glNormal3d( 0.0, 0.0,-1.0 ); glVertex3d( radius, 0.0,-radius ); glVertex3d( 0.0,-radius,-radius ); glVertex3d(-radius, 0.0,-radius ); glVertex3d( 0.0, radius,-radius );
glEnd();
}
-#undef RADIUS
+#undef RADIUSFAC
/*
* This structure defines an entry in our function-table.
@@ -498,24 +540,25 @@ typedef struct
const char * const name;
void (*solid) (void);
void (*wire) (void);
+ int drawSizeInfoFlag;
} entry;
-#define ENTRY(e) {#e, drawSolid##e, drawWire##e}
+#define ENTRY(e,f) {#e, drawSolid##e, drawWire##e,f}
static const entry table [] =
{
- ENTRY (Tetrahedron),
- ENTRY (Cube),
- ENTRY (Octahedron),
- ENTRY (Dodecahedron),
- ENTRY (RhombicDodecahedron),
- ENTRY (Icosahedron),
- ENTRY (SierpinskiSponge),
- ENTRY (Teapot),
- ENTRY (Torus),
- ENTRY (Sphere),
- ENTRY (Cone),
- ENTRY (Cylinder),
- ENTRY (Cuboctahedron)
+ ENTRY (Tetrahedron,GEO_NO_SIZE),
+ ENTRY (Cube,GEO_SIZE),
+ ENTRY (Octahedron,GEO_NO_SIZE),
+ ENTRY (Dodecahedron,GEO_NO_SIZE),
+ ENTRY (RhombicDodecahedron,GEO_NO_SIZE),
+ ENTRY (Icosahedron,GEO_NO_SIZE),
+ ENTRY (SierpinskiSponge,GEO_SCALE),
+ ENTRY (Teapot,GEO_SIZE),
+ ENTRY (Torus,GEO_INNER_OUTER_RAD),
+ ENTRY (Sphere,GEO_RAD),
+ ENTRY (Cone,GEO_BASE_HEIGHT),
+ ENTRY (Cylinder,GEO_RAD_HEIGHT),
+ ENTRY (Cuboctahedron,GEO_SIZE) /* This one doesn't work when in shader mode and is then skipped */
};
#undef ENTRY
@@ -565,8 +608,61 @@ static void shapesPrintf (int row, int col, const char *fmt, ...)
glPopMatrix();
}
-/* GLUT callback Handlers */
+/* Print info about the about the current shape and render state on the screen */
+static void DrawSizeInfo(int *row)
+{
+ switch (table [function_index].drawSizeInfoFlag)
+ {
+ case GEO_NO_SIZE:
+ break;
+ case GEO_SIZE:
+ shapesPrintf ((*row)++, 1, "Size Up Down : %f", orad);
+ break;
+ case GEO_SCALE:
+ shapesPrintf ((*row)++, 1, "Scale Up Down : %f", orad);
+ break;
+ case GEO_INNER_OUTER_RAD:
+ shapesPrintf ((*row)++, 1, "Inner radius Left Right: %f", irad);
+ shapesPrintf ((*row)++, 1, "Outer radius Up Down : %f", orad);
+ break;
+ case GEO_RAD:
+ shapesPrintf ((*row)++, 1, "Radius Up Down : %f", orad);
+ break;
+ case GEO_BASE_HEIGHT:
+ shapesPrintf ((*row)++, 1, "Base Left Right: %f", irad);
+ shapesPrintf ((*row)++, 1, "Height Up Down : %f", orad);
+ break;
+ case GEO_RAD_HEIGHT:
+ shapesPrintf ((*row)++, 1, "Radius Left Right: %f", irad);
+ shapesPrintf ((*row)++, 1, "Height Up Down : %f", orad);
+ break;
+ }
+}
+
+static void drawInfo()
+{
+ int row = 1;
+ shapesPrintf (row++, 1, "Shape PgUp PgDn: %s", table [function_index].name);
+ shapesPrintf (row++, 1, "Slices +-: %d Stacks <>: %d", slices, stacks);
+ shapesPrintf (row++, 1, "nSides +-: %d nRings <>: %d", slices, stacks);
+ shapesPrintf (row++, 1, "Depth (): %d", depth);
+ DrawSizeInfo(&row);
+ if (persProject)
+ shapesPrintf (row++, 1, "Perspective projection (p)");
+ else
+ shapesPrintf (row++, 1, "Orthographic projection (p)");
+ if (useShader)
+ shapesPrintf (row++, 1, "Using shader (s)");
+ else
+ shapesPrintf (row++, 1, "Using fixed function pipeline (s)");
+ if (animateXRot)
+ shapesPrintf (row++, 1, "2D rotation (r)");
+ else
+ shapesPrintf (row++, 1, "1D rotation (r)");
+ shapesPrintf (row++, 1, "visualizing normals: %i (n)",visNormals);
+}
+/* GLUT callback Handlers */
static void
resize(int width, int height)
{
@@ -578,17 +674,19 @@ resize(int width, int height)
static void display(void)
{
const double t = glutGet(GLUT_ELAPSED_TIME) / 1000.0;
- const double a = t*90.0;
- const double b = (animateXRot?t:1)*60.0;
+ const double a = t*89.0;
+ const double b = (animateXRot?t:1)*67.0;
glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);
+ glutSetOption(GLUT_GEOMETRY_VISUALIZE_NORMALS,visNormals); /* Normals visualized or not? */
+
if (useShader && !shaderReady)
initShader();
if (useShader && shaderReady)
{
- // setup use of shader (and vertex buffer by FreeGLUT)
+ /* setup use of shader (and vertex buffer by FreeGLUT) */
gl_UseProgram (program);
glutSetVertexAttribCoord3(attribute_fg_coord);
glutSetVertexAttribNormal(attribute_fg_normal);
@@ -627,6 +725,8 @@ static void display(void)
gl_UseProgram (0);
glutSetVertexAttribCoord3(-1);
glutSetVertexAttribNormal(-1);
+
+ checkError ("display");
}
else
{
@@ -662,24 +762,12 @@ static void display(void)
glColor3d(0.1,0.1,0.4);
}
- if( show_info ) {
- shapesPrintf (1, 1, "Shape PgUp PgDn: %s", table [function_index].name);
- shapesPrintf (2, 1, "Slices +-: %d Stacks <>: %d", slices, stacks);
- shapesPrintf (3, 1, "nSides +-: %d nRings <>: %d", slices, stacks);
- shapesPrintf (4, 1, "Depth (): %d", depth);
- shapesPrintf (5, 1, "Outer radius Up Down : %f", orad);
- shapesPrintf (6, 1, "Inner radius Left Right: %f", irad);
- if (persProject)
- shapesPrintf (7, 1, "Perspective projection");
- else
- shapesPrintf (7, 1, "Orthographic projection");
- if (useShader)
- shapesPrintf (8, 1, "Using shader");
- else
- shapesPrintf (8, 1, "Using fixed function pipeline");
- } else {
+ if( show_info )
+ /* print info to screen */
+ drawInfo();
+ else
+ /* print to command line instead */
printf ( "Shape %d slides %d stacks %d\n", function_index, slices, stacks ) ;
- }
glutSwapBuffers();
}
@@ -722,7 +810,15 @@ key(unsigned char key, int x, int y)
case 'r': animateXRot=!animateXRot; break;
case 'S':
- case 's': useShader=!useShader; break;
+ case 's':
+ useShader=!useShader;
+ /* Cuboctahedron can't be shown when in shader mode, move to next */
+ if (useShader && NUMBEROF (table)-1 == ( unsigned )function_index)
+ function_index = 0;
+ break;
+
+ case 'N':
+ case 'n': visNormals=!visNormals; break;
default:
break;
@@ -752,6 +848,13 @@ static void special (int key, int x, int y)
if (NUMBEROF (table) <= ( unsigned )function_index)
function_index = 0;
+
+ /* Cuboctahedron can't be shown when in shader mode, skip it */
+ if (useShader && NUMBEROF (table)-1 == ( unsigned )function_index)
+ if (key==GLUT_KEY_PAGE_UP)
+ function_index = 0;
+ else
+ function_index -= 1;
}
@@ -776,7 +879,7 @@ const GLfloat high_shininess[] = { 100.0f };
int
main(int argc, char *argv[])
{
- glutInitWindowSize(640,480);
+ glutInitWindowSize(800,600);
glutInitWindowPosition(40,40);
glutInit(&argc, argv);
glutInitDisplayMode(GLUT_RGB | GLUT_DOUBLE | GLUT_DEPTH | GLUT_MULTISAMPLE);