Main Page   Alphabetical List   Compound List   File List   Compound Members   File Members  

gtcmesh.h

Go to the documentation of this file.
00001 /*
00002     Sebastien Loisel's Toolchest
00003     Copyright (C) 1998 Sebastien Loisel
00004 
00005     $Header: /home/gtc/public_html/gtc-cvs/toolchest/include/gtcmesh.h,v 1.11 2000/06/25 05:11:52 loisel Exp $
00006     */
00007 
00027 /* Meshes! */
00028 
00029 #ifndef Z_BASEMESH_H
00030 #define Z_BASEMESH_H
00031 
00032 #include <gtcutils.h>
00033 
00034 /* gtcSimpleMesh: a 3d graphical mesh.
00035    This holds all the information that GTC needs to draw a textured mesh
00036    with vertex normals and all that. A special feature is also the vertex
00037    weights. The crucial API function is gtc_put_simple_mesh. If you fill in the
00038    various fields properly, you won't need any function but
00039    gtc_put_mesh() (and
00040    some OpenGL setup code). Here is a description of all the entries of the
00041    struct and what gtc_put_mesh does with it.
00042 
00043    name: This field isn't used by gtc_put_mesh but is useful to have around for
00044    some of the mesh loading facilities (more specifically, the .asc and .ase
00045    import functions).
00046 
00047    v: vertices, an array of gtcReal[3] -- each vertex is given an x, y and z
00048    coordinate.
00049 
00050    n: normals, an array of gtcReal[3] -- each vertex is given a normal, and
00051    this is the (x,y,z) coordinates of a given vertex's normal. If this pointer
00052    is zero, normals aren't sent to OpenGL.
00053 
00054    t: texture coordinates, an array of gtcReal[3] -- each vertex is given
00055    some texture coordinates. If the pointer is zero, texture coordinates are
00056    not sent to OpenGL.
00057 
00058    w: weights: an array of gtcReal[numw]. This is for skeleton animations.
00059    In a skeleton animation, each bone is represented by an affine transform.
00060    Each vertex is affected by one or more bones. If there are n bones, there
00061    are n affine transforms, A[0] through A[n-1], that can affect a vertex v.
00062    The net affine transform affecting vertex v[k] is given by the formula
00063    A = w[k][0]*A[0] + w[k][1]*A[1] + ... + w[k][n-1]*A[n-1].
00064    That is, with the above A, the transformed vertex v will be Av.
00065 
00066    f: face index. The k_th triangle of the mesh is (f[k][0],f[k][1],f[k][2]),
00067    these three integers tell you which vertices to use to form that triangle.
00068    To use backface culling, try to orient these properly.
00069 
00070    numf: number of faces.
00071 
00072    numv: number of vertices.
00073 
00074    numw: number of weights. If zero, there's one affine transform and the
00075    weight is one for all vertices. This is the fast path (if the hardware
00076    supports it, this has a shot at being hardware accelerated and transformed
00077    by the hardware geometry engine). If there are weights, unless some
00078    geometry accelerated card manufacturer puts in an extension for this
00079    precise purpose, the vertices have to be transformed in software.
00080 
00081    texid: a texture id. If zero, unused, otherwise, this is the OpenGL texture
00082    id to use for the mesh. Note there's only one texture per gtcSimpleMesh.
00083 
00084    Note. If a vertex is transformed by a 3x3 matrix A then its normal needs
00085    to be transformed by (A^-1)' (' is transpose). Sadly, there's a matrix
00086    inverse in that computation. If every vertex is transformed through the
00087    same matrix, that's ok. If every vertex is transformed through a different
00088    matrix (as is the case when weights are used), that would involve one
00089    matrix inversion per vertex, which is expensive. An approximation is used.
00090 */
00091 
00102 typedef struct
00103 {
00105   char *name;
00107   gtcReal (*v)[3];
00109   gtcReal (*n)[3];
00111   gtcReal (*t)[2];
00113   gtcReal *w;
00115   int (*f)[3];
00117   int numf,
00119     numv,
00121     numw,
00123     texid;
00124 } gtcSimpleMesh;
00125 
00126 /* gtc_put_simple_mesh_wremap: puts the mesh to the screen. The matrices
00127    are sent by pointer, that is, A[0] is a pointer to the first matrix,
00128    A[1] a pointer to the second, etc... If m->numw=1, you only need to
00129    send a single matrix. An[k] needs to point to a matrix whose linear part is
00130    equal to (A[k]^-1)' where the apostrophe denotes the matrix transpose. This
00131    functions will never use hardware geometry transform -- the vertices and
00132    normals are transformed in software. Don't use this function if m->numw=0.
00133 */
00134 
00136 void gtc_put_mesh(int f[][3], gtcReal v[][3], gtcReal n[][3], int texid,
00137                   gtcReal t[][2], int numf);
00143 void gtc_put_simple_mesh_wremap(gtcSimpleMesh *m, gtcReal (*A[])[4][4],
00144                                 gtcReal (*An[])[4][4]);
00154 void gtc_put_simple_mesh(gtcSimpleMesh *m, gtcReal A[][4][4]);
00156 typedef gtcReal (*I_dont_know_all_I_need_to_know)[4][4];
00158 I_dont_know_all_I_need_to_know gtc_prep_An(int numw, gtcReal A[][4][4]);
00160 void gtc_put_simple_mesh_easy(gtcSimpleMesh *m, gtcReal A[4][4]);
00161 
00163 void gtc_normalize_mesh(gtcReal v[][3], int numv);
00165 void gtc_normalize_simple_mesh(gtcSimpleMesh *m);
00166 
00168 gtcSimpleMesh *gtc_simple_mesh_new(char *name, int numf, int numv);
00170 gtcSimpleMesh *gtc_simple_mesh_tex_new(char *name, int numf, int numv);
00172 gtcSimpleMesh *gtc_simple_mesh_w_new(char *name, int numf, int numv, int numw);
00174 gtcSimpleMesh *gtc_simple_mesh_wtex_new(char *name, int numf,
00175                                         int numv, int numw);
00177 void gtc_simple_texcoord(gtcSimpleMesh *m);
00179 void gtc_simple_mesh_free(gtcSimpleMesh *m);
00180 
00181 /* Basic vector functionality here */
00183 gtcReal gtc_dot(gtcReal a[], gtcReal b[], int n); /* dot product */
00185 void gtc_cross(gtcReal a[3], gtcReal b[3], gtcReal r[3]); /* cross product */
00187 void gtc_add(gtcReal a[], gtcReal b[], gtcReal r[], int n); /* vector addition */
00189 void gtc_sub(gtcReal a[], gtcReal b[], gtcReal r[], int n); /* difference */
00191 gtcReal gtc_norm(gtcReal a[], int n); /* norm */
00193 void gtc_addscale(gtcReal s, gtcReal a[], gtcReal r[], int n);
00194 /* add and scale: r+=s*a; */
00196 void gtc_zero(gtcReal z[], int n); /* zeroes the vector */
00198 void gtc_copy(gtcReal a[], gtcReal r[], int n); /* copies the vector */
00199 
00200 /* Setting normals */
00202 void gtc_cum_face(int f[3], gtcReal v[][3], gtcReal n[][3]);
00203 /* Adds a face's normal (properly scaled) to its vertices */
00205 void gtc_set_normals(int f[][3], gtcReal v[][3], gtcReal n[][3],
00206                      int numf, int numv); /* Set all vertex normals. */
00207 
00209 void gtc_make_face(int f[], int a, int b, int c);
00210 /* This one takes four vertices and spits back a mesh of the tetrahedron
00211    of these four vertices. */
00213 void gtc_tetrahedron(gtcReal v[4][3], int f[4][3]);
00214 
00216 void gtc_simple_GL_setup(void);
00217 /* Before calling putmesh, you should set up GL so that it understands what
00218    you're saying. This function does exactly that, for a simple example
00219    with some lights. */
00220 
00221 /* gtc_GL_setup: I know I'm against wrappers but this one was very useful
00222    so I made it anyway. You tell it if you want the various options
00223    (GL_NORMALIZE, GL_SMOOTH, GL_LIGHTING, GL_CULL) by passing a 1 (for yes)
00224    or a zero (for no) in the appropriate parameter. near, far are the near
00225    and far clipping planes. fov is the (vertical) field of vision in degrees,
00226    the horizontal field of vision is computed from the vertical one, the
00227    width of the viewport and assuming that the aspect ratio is 1:1. if
00228    clear==1 then it will also call glClear. */
00253 void gtc_GL_setup(int normalize, int smooth, int lighting, int cull, int clear,
00254                   gtcReal near, gtcReal far, gtcReal fov, gtcReal w_div_h);
00255 /* gtc_GL_setupall: calls gtc_GL_setup with all options and reasonable near,
00256    far, fov. */
00258 void gtc_GL_setupall(gtcReal w_div_h);
00259 
00260 #if 0
00261 int gtctricollide(gtcvec u1, gtcvec u2, gtcvec u3,
00262                   gtcvec v1, gtcvec v2, gtcvec v3);
00263 #endif
00264 
00265 /* Mesh transform */
00267 void gtc_apply(gtcReal A[4][4], gtcReal v[3], gtcReal r[3]);
00268 /* transform a single vector */
00270 void gtc_xform_pos(gtcReal A[4][4], gtcReal v[][3], gtcReal r[][3], int numv);
00272 void gtc_combine(gtcReal a[4][4], gtcReal b[4][4], gtcReal r[4][4]);
00273 /* affine group multiplication */
00275 void gtc_rot(gtcReal x, gtcReal y, gtcReal z, gtcReal theta, gtcReal R[4][4]);
00276 /* generates a rotation about (x,y,z) by theta (in radians). */
00278 void gtc_redress(gtcReal r[4][4]);
00280 void gtc_xlat(gtcReal x, gtcReal y, gtcReal z, gtcReal T[4][4]);
00281 /* makes a translation */
00283 void gtc_ident(gtcReal I[4][4]); /* returns the identity */
00285 void gtcaffinecopy(gtcReal A[4][4], gtcReal R[4][4]); /* copies */
00287 gtcReal gtc_determinant_3(gtcReal A[4][4]);
00288 /* Computes the determinant of the 3x3 linear transform */
00290 void gtc_invert(gtcReal A[4][4], gtcReal R[4][4]); /* inverses */
00292 int gtc_check_ortho(gtcReal A[4][4], gtcReal epsilon);
00293 /* Checks if the linear part of A is orthogonal. Tolerance epsilon. */
00295 int gtc_check_rot(gtcReal A[4][4], gtcReal epsilon);
00296 /* Checks if the linear part of A is a rotation
00297    (=orthogonal of determinant 1). */
00298 
00300 char *gtc_first_tok(char *s);
00302 char *gtc_next_tok(char *s);
00303 
00304 /* Quaternions. Quaternions can be used to represent rotations. If
00305    a matrix is not a rotation then do not try to convert it to a
00306    quaternion, you'll get garbage. To check if a matrix is a rotation,
00307    use gtc_check_rot above. */
00308 
00310 void gtc_quaternion_to_matrix(gtcReal Q[4], gtcReal M[4][4]);
00312 void gtc_matrix_to_quaternion(gtcReal M[4][4], gtcReal Q[4]);
00313 
00315 gtcSimpleMesh *gtc_stars(void);
00316 
00317 #endif
00318  

Generated at Sat Jul 14 18:53:52 2001 for GTC by doxygen1.2.8.1 written by Dimitri van Heesch, © 1997-2001