00001
00002
00003
00004
00005
00006
00007
00038
00039
00040
00041
00042 #ifdef _WIN32
00043 #include <windows.h>
00044 #endif
00045 #include <stdlib.h>
00046 #include <stdio.h>
00047 #include <math.h>
00048 #include <GL/gl.h>
00049 #include <GL/glu.h>
00050
00051 #include "prm.h"
00052 #include "quad.h"
00053 #include "cd.h"
00054 #include "wd.h"
00055 #include "dsp.h"
00056
00057
00058
00059
00060
00061
00064 struct _quad {
00066 Coord p[4];
00067 };
00068
00069
00070
00071
00072
00073
00074 static void quadPickCode( double x, double y, double xmin, double xmax,
00075 double ymin, double ymax, int cod[4] );
00076 static int quadPickLine( double x, double y, double pick_tol,
00077 double x0, double y0, double x1, double y1 );
00078 static void quadFaceNormal( Pnt3d *p0, Pnt3d *p1, Pnt3d *p2, Pnt3d *p3,
00079 Vec3d *normal );
00080 static void quadBuildSolidPrm( Quad *quad, double height, Pnt3d *solid_prm );
00081
00082
00083
00096 static void quadPickCode( double x, double y, double xmin, double xmax,
00097 double ymin, double ymax, int cod[4] )
00098 {
00099 cod[0] = x < xmin;
00100 cod[1] = x > xmax;
00101 cod[2] = y < ymin;
00102 cod[3] = y > ymax;
00103 }
00104
00105
00106
00126 static int quadPickLine( double x, double y, double pick_tol,
00127 double x0, double y0, double x1, double y1 )
00128 {
00129 int cod0[4], cod1[4];
00130 double xmin, xmax, ymin, ymax;
00131 int j;
00132
00133 xmin = x - pick_tol;
00134 xmax = x + pick_tol;
00135 ymin = y - pick_tol;
00136 ymax = y + pick_tol;
00137
00138 quadPickCode( x1, y1, xmin, xmax, ymin, ymax, cod1 );
00139 do
00140 {
00141 quadPickCode( x0, y0, xmin, xmax, ymin, ymax, cod0 );
00142 for( j = 0; j < 4; j++ )
00143 {
00144 if( cod0[j] && cod1[j] )
00145 break;
00146 }
00147 if( j != 4 )
00148 break;
00149
00150
00151
00152 if( cod0[0] )
00153 {
00154 y0 += (xmin - x0) * (y1 - y0) / (x1 - x0);
00155 x0 = xmin;
00156 }
00157 else if( cod0[1] )
00158 {
00159 y0 += (xmax - x0) * (y1 - y0) / (x1 - x0);
00160 x0 = xmax;
00161 }
00162 else if( cod0[2] )
00163 {
00164 x0 += (ymin - y0 ) * (x1 - x0) / (y1 - y0);
00165 y0 = ymin;
00166 }
00167 else if( cod0[3] )
00168 {
00169 x0 += (ymax - y0) * (x1 - x0) / (y1 - y0);
00170 y0 = ymax;
00171 }
00172 else
00173 {
00174 return( 1 );
00175 }
00176 } while( 1 );
00177
00178 return( 0 );
00179 }
00180
00181
00182
00193 static void quadFaceNormal( Pnt3d *p0, Pnt3d *p1, Pnt3d *p2, Pnt3d *p3,
00194 Vec3d *normal )
00195 {
00196 double len;
00197
00198 normal->x = 0.0;
00199 normal->y = 0.0;
00200 normal->z = 0.0;
00201
00202 normal->x += (p1->y - p0->y) * (p2->z - p0->z) -
00203 (p1->z - p0->z) * (p2->y - p0->y);
00204 normal->y += -(p1->x - p0->x) * (p2->z - p0->z) +
00205 (p1->z - p0->z) * (p2->x - p0->x);
00206 normal->z += (p1->x - p0->x) * (p2->y - p0->y) -
00207 (p1->y - p0->y) * (p2->x - p0->x);
00208
00209 normal->x += (p2->y - p0->y) * (p3->z - p0->z) -
00210 (p2->z - p0->z) * (p3->y - p0->y);
00211 normal->y += -(p2->x - p0->x) * (p3->z - p0->z) +
00212 (p2->z - p0->z) * (p3->x - p0->x);
00213 normal->z += (p2->x - p0->x) * (p3->y - p0->y) -
00214 (p2->y - p0->y) * (p3->x - p0->x);
00215
00216 len = sqrt( normal->x*normal->x + normal->y*normal->y + normal->z*normal->z );
00217
00218 if( len != 0.0 )
00219 {
00220 normal->x /= len;
00221 normal->y /= len;
00222 normal->z /= len;
00223 }
00224 }
00225
00226
00227
00240 static void quadBuildSolidPrm( Quad *quad, double height, Pnt3d *solid_prm )
00241 {
00242 Pnt3d face[4];
00243 Vec3d prm_norm;
00244
00245
00246
00247 face[0].x = quad->p[0].x;
00248 face[0].y = quad->p[0].y;
00249 face[0].z = 0.0;
00250 face[1].x = quad->p[1].x;
00251 face[1].y = quad->p[1].y;
00252 face[1].z = 0.0;
00253 face[2].x = quad->p[2].x;
00254 face[2].y = quad->p[2].y;
00255 face[2].z = 0.0;
00256 face[3].x = quad->p[3].x;
00257 face[3].y = quad->p[3].y;
00258 face[3].z = 0.0;
00259
00260
00261
00262
00263
00264
00265 quadFaceNormal( &face[0], &face[1], &face[2], &face[3], &prm_norm );
00266
00267
00268
00269
00270
00271 if( prm_norm.z < 0.0 )
00272 {
00273 solid_prm[0] = face[0];
00274 solid_prm[1] = face[1];
00275 solid_prm[2] = face[2];
00276 solid_prm[3] = face[3];
00277
00278 solid_prm[4] = face[0];
00279 solid_prm[5] = face[3];
00280 solid_prm[6] = face[2];
00281 solid_prm[7] = face[1];
00282 }
00283 else
00284 {
00285 solid_prm[0] = face[0];
00286 solid_prm[1] = face[3];
00287 solid_prm[2] = face[2];
00288 solid_prm[3] = face[1];
00289
00290 solid_prm[4] = face[0];
00291 solid_prm[5] = face[1];
00292 solid_prm[6] = face[2];
00293 solid_prm[7] = face[3];
00294 }
00295 solid_prm[4].z += height;
00296 solid_prm[5].z += height;
00297 solid_prm[6].z += height;
00298 solid_prm[7].z += height;
00299 }
00300
00301
00302
00303
00304
00305
00306
00307
00308
00309 Quad *quadCreate( void )
00310 {
00311 Quad *quad;
00312
00313
00314
00315 quad = malloc( sizeof( Quad ) );
00316 if( quad == NULL )
00317 return( NULL );
00318
00319
00320
00321 quad->p[0].x = 0.0;
00322 quad->p[0].y = 0.0;
00323 quad->p[1].x = 1.0;
00324 quad->p[1].y = 1.0;
00325 quad->p[2].x = 1.0;
00326 quad->p[2].y = 0.0;
00327 quad->p[3].x = 0.0;
00328 quad->p[3].y = 1.0;
00329
00330 return( quad );
00331 }
00332
00333
00334
00335 void quadDelete( Quad *quad )
00336 {
00337 free( quad );
00338 }
00339
00340
00341
00342 void quadRead( Quad *quad, FILE *fd )
00343 {
00344
00345 }
00346
00347
00348
00349 void quadWrite( Quad *quad, FILE *fd )
00350 {
00351
00352 }
00353
00354
00355
00356 int quadGetNPts( Quad *quad )
00357 {
00358 return( 4 );
00359 }
00360
00361
00362
00363 void quadSetCoords( Quad *quad, int id, double x, double y )
00364 {
00365
00366 }
00367
00368
00369
00370 void quadGetCoords( Quad *quad, int id, double *x, double *y )
00371 {
00372
00373 }
00374
00375
00376
00377 void quadSet1stPt( Quad *quad, double x, double y )
00378 {
00379
00380 }
00381
00382
00383
00384 void quadSet2ndPt( Quad *quad, double x, double y )
00385 {
00386
00387 }
00388
00389
00390
00391 int quadPickArea( Quad *quad, double x, double y )
00392 {
00393 int ni = 0;
00394 double px0, py0;
00395 double px1, py1;
00396 double xc;
00397 int i;
00398
00399 for( i = 0; i < 4; i++ )
00400 {
00401 quadGetCoords( quad, i, &px0, &py0 );
00402 quadGetCoords( quad, (i+1)%4, &px1, &py1 );
00403 if( !(py0 == py1) &&
00404 !((py0 > y) && (py1 > y)) &&
00405 !((py0 < y) && (py1 < y)) &&
00406 !((px0 < x) && (px1 < x)) )
00407 {
00408 if( py0 == y )
00409 {
00410 if( (px0 > x) && (py1 > y) )
00411 ni++;
00412 }
00413 else
00414 {
00415 if( py1 == y )
00416 {
00417 if( (px1 > x) && (py0 > y) )
00418 ni++;
00419 }
00420 else
00421 {
00422 if( (px0 > x) && (px1 > x) )
00423 ni++;
00424 else
00425 {
00426 double dx = px0 - px1;
00427 xc = px0;
00428 if( dx != 0.0 )
00429 xc += ( y - py0 ) * dx / ( py0 - py1 );
00430 if( xc > x )
00431 ni++;
00432 }
00433 }
00434 }
00435 }
00436 }
00437
00438 return( ni % 2 );
00439 }
00440
00441
00442
00443 int quadPickVertex( Quad *quad, double x, double y, double tol,
00444 int *id )
00445 {
00446
00447
00448 return( 0 );
00449 }
00450
00451
00452
00453 int quadPickSide( Quad *quad, double x, double y, double tol,
00454 int *id )
00455 {
00456
00457
00458 return( 0 );
00459 }
00460
00461
00462
00463 void quadTranslate( Quad *quad, double dx, double dy )
00464 {
00465
00466 }
00467
00468
00469
00470 void quadTranslateVertex( Quad *quad, int id, double dx, double dy )
00471 {
00472
00473 }
00474
00475
00476
00477 void quadTranslateSide( Quad *quad, int id, double dx, double dy )
00478 {
00479
00480 }
00481
00482
00483
00484 void quadGetBox( Quad *quad, double *xmin, double *xmax,
00485 double *ymin, double *ymax )
00486 {
00487
00488 }
00489
00490
00491
00492 void quadDisplayBoundary( Quad *quad )
00493 {
00494
00495 }
00496
00497
00498
00499 void quadDisplayInterior( Quad *quad )
00500 {
00501
00502 }
00503
00504
00505
00506 void quadDisplaySolid( Quad *quad, double height )
00507 {
00508
00509
00510
00511 }
00512
00513
00514
00515 void quadHighltSolid( Quad *quad, double height )
00516 {
00517
00518
00519 }
00520
00521
00522
00523 void quadDisplayZbuffer( Quad *quad, double height, long int color )
00524 {
00525 Pnt3d solid_prm[8];
00526 Vec3d normal;
00527
00528
00529
00530
00531
00532 if( height == 0.0 )
00533 {
00534 dspZbfBeginPoly( color, 0.0, 0.0, 1.0 );
00535 dspZbfVertex( quad->p[0].x, quad->p[0].y, 0.0 );
00536 dspZbfVertex( quad->p[1].x, quad->p[1].y, 0.0 );
00537 dspZbfVertex( quad->p[2].x, quad->p[2].y, 0.0 );
00538 dspZbfVertex( quad->p[3].x, quad->p[3].y, 0.0 );
00539 dspZbfEndPoly( );
00540 return;
00541 }
00542
00543
00544
00545 quadBuildSolidPrm( quad, height, solid_prm );
00546
00547
00548
00549 dspZbfBeginPoly( color, 0.0, 0.0, -1.0 );
00550 dspZbfVertex( solid_prm[0].x, solid_prm[0].y, solid_prm[0].z );
00551 dspZbfVertex( solid_prm[1].x, solid_prm[1].y, solid_prm[1].z );
00552 dspZbfVertex( solid_prm[2].x, solid_prm[2].y, solid_prm[2].z );
00553 dspZbfVertex( solid_prm[3].x, solid_prm[3].y, solid_prm[3].z );
00554 dspZbfEndPoly( );
00555
00556 dspZbfBeginPoly( color, 0.0, 0.0, 1.0 );
00557 dspZbfVertex( solid_prm[4].x, solid_prm[4].y, solid_prm[4].z );
00558 dspZbfVertex( solid_prm[5].x, solid_prm[5].y, solid_prm[5].z );
00559 dspZbfVertex( solid_prm[6].x, solid_prm[6].y, solid_prm[6].z );
00560 dspZbfVertex( solid_prm[7].x, solid_prm[7].y, solid_prm[7].z );
00561 dspZbfEndPoly( );
00562
00563
00564
00565 quadFaceNormal( &solid_prm[0], &solid_prm[4], &solid_prm[7], &solid_prm[1],
00566 &normal );
00567 dspZbfBeginPoly( color, normal.x, normal.y, normal.z );
00568 dspZbfVertex( solid_prm[0].x, solid_prm[0].y, solid_prm[0].z );
00569 dspZbfVertex( solid_prm[4].x, solid_prm[4].y, solid_prm[4].z );
00570 dspZbfVertex( solid_prm[7].x, solid_prm[7].y, solid_prm[7].z );
00571 dspZbfVertex( solid_prm[1].x, solid_prm[1].y, solid_prm[1].z );
00572 dspZbfEndPoly( );
00573
00574 quadFaceNormal( &solid_prm[1], &solid_prm[7], &solid_prm[6], &solid_prm[2],
00575 &normal );
00576 dspZbfBeginPoly( color, normal.x, normal.y, normal.z );
00577 dspZbfVertex( solid_prm[1].x, solid_prm[1].y, solid_prm[1].z );
00578 dspZbfVertex( solid_prm[7].x, solid_prm[7].y, solid_prm[7].z );
00579 dspZbfVertex( solid_prm[6].x, solid_prm[6].y, solid_prm[6].z );
00580 dspZbfVertex( solid_prm[2].x, solid_prm[2].y, solid_prm[2].z );
00581 dspZbfEndPoly( );
00582
00583 quadFaceNormal( &solid_prm[2], &solid_prm[6], &solid_prm[5], &solid_prm[3],
00584 &normal );
00585 dspZbfBeginPoly( color, normal.x, normal.y, normal.z );
00586 dspZbfVertex( solid_prm[2].x, solid_prm[2].y, solid_prm[2].z );
00587 dspZbfVertex( solid_prm[6].x, solid_prm[6].y, solid_prm[6].z );
00588 dspZbfVertex( solid_prm[5].x, solid_prm[5].y, solid_prm[5].z );
00589 dspZbfVertex( solid_prm[3].x, solid_prm[3].y, solid_prm[3].z );
00590 dspZbfEndPoly( );
00591
00592 quadFaceNormal( &solid_prm[3], &solid_prm[5], &solid_prm[4], &solid_prm[0],
00593 &normal );
00594 dspZbfBeginPoly( color, normal.x, normal.y, normal.z );
00595 dspZbfVertex( solid_prm[3].x, solid_prm[3].y, solid_prm[3].z );
00596 dspZbfVertex( solid_prm[5].x, solid_prm[5].y, solid_prm[5].z );
00597 dspZbfVertex( solid_prm[4].x, solid_prm[4].y, solid_prm[4].z );
00598 dspZbfVertex( solid_prm[0].x, solid_prm[0].y, solid_prm[0].z );
00599 dspZbfEndPoly( );
00600 }
00601
00603 solid_prm[5].x, solid_prm[5].y, solid_prm[5].z );
00604 dspZbfVertex( solid_prm[3].x, solid_prm[3].y, solid_prm[3].z );
00605 dspZbfEndPoly( );
00606
00607 quadFaceNormal( &solid_prm[3], &solid_prm[5], &solid_prm[4], &solid_prm[0],
00608 &normal );
00609 dspZbfBeginPoly( color, normal.x, normal.y, normal.z );
00610 dspZbfVertex( solid_prm[3].x, solid_prm[3].y, solid_prm[3].z );
00611 dspZbfVertex( solid_prm[5].x, solid_prm[5].y, solid_prm[5].z );
00612 dspZbfVertex( solid_prm[4].x, solid_prm[4].y, solid_prm[4].z );
00613 dspZbfVertex( solid_prm[0].x, solid_prm[0].y, solid_prm[0].z );
00614 dspZbfEndPoly( );
00615 }
00616