Home | Info | Community | Development | myReactOS | Contact Us
ReactOS Development > Doxygenmesher.cc
Go to the documentation of this file.
00001 /* 00002 ** License Applicability. Except to the extent portions of this file are 00003 ** made subject to an alternative license as permitted in the SGI Free 00004 ** Software License B, Version 1.1 (the "License"), the contents of this 00005 ** file are subject only to the provisions of the License. You may not use 00006 ** this file except in compliance with the License. You may obtain a copy 00007 ** of the License at Silicon Graphics, Inc., attn: Legal Services, 1600 00008 ** Amphitheatre Parkway, Mountain View, CA 94043-1351, or at: 00009 ** 00010 ** http://oss.sgi.com/projects/FreeB 00011 ** 00012 ** Note that, as provided in the License, the Software is distributed on an 00013 ** "AS IS" basis, with ALL EXPRESS AND IMPLIED WARRANTIES AND CONDITIONS 00014 ** DISCLAIMED, INCLUDING, WITHOUT LIMITATION, ANY IMPLIED WARRANTIES AND 00015 ** CONDITIONS OF MERCHANTABILITY, SATISFACTORY QUALITY, FITNESS FOR A 00016 ** PARTICULAR PURPOSE, AND NON-INFRINGEMENT. 00017 ** 00018 ** Original Code. The Original Code is: OpenGL Sample Implementation, 00019 ** Version 1.2.1, released January 26, 2000, developed by Silicon Graphics, 00020 ** Inc. The Original Code is Copyright (c) 1991-2000 Silicon Graphics, Inc. 00021 ** Copyright in any portions created by third parties is as indicated 00022 ** elsewhere herein. All Rights Reserved. 00023 ** 00024 ** Additional Notice Provisions: The application programming interfaces 00025 ** established by SGI in conjunction with the Original Code are The 00026 ** OpenGL(R) Graphics System: A Specification (Version 1.2.1), released 00027 ** April 1, 1999; The OpenGL(R) Graphics System Utility Library (Version 00028 ** 1.3), released November 4, 1998; and OpenGL(R) Graphics with the X 00029 ** Window System(R) (Version 1.3), released October 19, 1998. This software 00030 ** was created using the OpenGL(R) version 1.2.1 Sample Implementation 00031 ** published by SGI, but has not been independently verified as being 00032 ** compliant with the OpenGL(R) version 1.2.1 Specification. 00033 */ 00034 00035 /* 00036 * mesher.c++ 00037 * 00038 * $Date: 2006-03-12 00:07:02 +0000 (Sun, 12 Mar 2006) $ $Revision: 1.1 $ 00039 * $Header: /cygdrive/c/RCVS/CVS/ReactOS/reactos/lib/glu32/libnurbs/internals/mesher.cc,v 1.1 2004/02/02 16:39:11 navaraf Exp $ 00040 */ 00041 00042 #include "glimports.h" 00043 #include "myassert.h" 00044 #include "mystdio.h" 00045 #include "gridvertex.h" 00046 #include "gridtrimvertex.h" 00047 #include "jarcloc.h" 00048 #include "gridline.h" 00049 #include "trimline.h" 00050 #include "uarray.h" 00051 #include "backend.h" 00052 #include "mesher.h" 00053 00054 00055 const float Mesher::ZERO = 0.0; 00056 00057 Mesher::Mesher( Backend& b ) 00058 : backend( b ), 00059 p( sizeof( GridTrimVertex ), 100, "GridTrimVertexPool" ) 00060 { 00061 stacksize = 0; 00062 vdata = 0; 00063 lastedge = 0; //needed to prevent purify UMR 00064 } 00065 00066 Mesher::~Mesher( void ) 00067 { 00068 if( vdata ) delete[] vdata; 00069 } 00070 00071 void 00072 Mesher::init( unsigned int npts ) 00073 { 00074 p.clear(); 00075 if( stacksize < npts ) { 00076 stacksize = 2 * npts; 00077 if( vdata ) delete[] vdata; 00078 vdata = new GridTrimVertex_p[stacksize]; 00079 } 00080 } 00081 00082 inline void 00083 Mesher::push( GridTrimVertex *gt ) 00084 { 00085 assert( itop+1 != (int)stacksize ); 00086 vdata[++itop] = gt; 00087 } 00088 00089 inline void 00090 Mesher::pop( long ) 00091 { 00092 } 00093 00094 inline void 00095 Mesher::openMesh() 00096 { 00097 backend.bgntmesh( "addedge" ); 00098 } 00099 00100 inline void 00101 Mesher::closeMesh() 00102 { 00103 backend.endtmesh(); 00104 } 00105 00106 inline void 00107 Mesher::swapMesh() 00108 { 00109 backend.swaptmesh(); 00110 } 00111 00112 inline void 00113 Mesher::clearStack() 00114 { 00115 itop = -1; 00116 last[0] = 0; 00117 } 00118 00119 void 00120 Mesher::finishLower( GridTrimVertex *gtlower ) 00121 { 00122 for( push(gtlower); 00123 nextlower( gtlower=new(p) GridTrimVertex ); 00124 push(gtlower) ) 00125 addLower(); 00126 addLast(); 00127 } 00128 00129 void 00130 Mesher::finishUpper( GridTrimVertex *gtupper ) 00131 { 00132 for( push(gtupper); 00133 nextupper( gtupper=new(p) GridTrimVertex ); 00134 push(gtupper) ) 00135 addUpper(); 00136 addLast(); 00137 } 00138 00139 void 00140 Mesher::mesh( void ) 00141 { 00142 GridTrimVertex *gtlower, *gtupper; 00143 00144 Hull::init( ); 00145 nextupper( gtupper = new(p) GridTrimVertex ); 00146 nextlower( gtlower = new(p) GridTrimVertex ); 00147 00148 clearStack(); 00149 openMesh(); 00150 push(gtupper); 00151 00152 nextupper( gtupper = new(p) GridTrimVertex ); 00153 nextlower( gtlower ); 00154 00155 assert( gtupper->t && gtlower->t ); 00156 00157 if( gtupper->t->param[0] < gtlower->t->param[0] ) { 00158 push(gtupper); 00159 lastedge = 1; 00160 if( nextupper( gtupper=new(p) GridTrimVertex ) == 0 ) { 00161 finishLower(gtlower); 00162 return; 00163 } 00164 } else if( gtupper->t->param[0] > gtlower->t->param[0] ) { 00165 push(gtlower); 00166 lastedge = 0; 00167 if( nextlower( gtlower=new(p) GridTrimVertex ) == 0 ) { 00168 finishUpper(gtupper); 00169 return; 00170 } 00171 } else { 00172 if( lastedge == 0 ) { 00173 push(gtupper); 00174 lastedge = 1; 00175 if( nextupper(gtupper=new(p) GridTrimVertex) == 0 ) { 00176 finishLower(gtlower); 00177 return; 00178 } 00179 } else { 00180 push(gtlower); 00181 lastedge = 0; 00182 if( nextlower( gtlower=new(p) GridTrimVertex ) == 0 ) { 00183 finishUpper(gtupper); 00184 return; 00185 } 00186 } 00187 } 00188 00189 while ( 1 ) { 00190 if( gtupper->t->param[0] < gtlower->t->param[0] ) { 00191 push(gtupper); 00192 addUpper(); 00193 if( nextupper( gtupper=new(p) GridTrimVertex ) == 0 ) { 00194 finishLower(gtlower); 00195 return; 00196 } 00197 } else if( gtupper->t->param[0] > gtlower->t->param[0] ) { 00198 push(gtlower); 00199 addLower(); 00200 if( nextlower( gtlower=new(p) GridTrimVertex ) == 0 ) { 00201 finishUpper(gtupper); 00202 return; 00203 } 00204 } else { 00205 if( lastedge == 0 ) { 00206 push(gtupper); 00207 addUpper(); 00208 if( nextupper( gtupper=new(p) GridTrimVertex ) == 0 ) { 00209 finishLower(gtlower); 00210 return; 00211 } 00212 } else { 00213 push(gtlower); 00214 addLower(); 00215 if( nextlower( gtlower=new(p) GridTrimVertex ) == 0 ) { 00216 finishUpper(gtupper); 00217 return; 00218 } 00219 } 00220 } 00221 } 00222 } 00223 00224 inline int 00225 Mesher::isCcw( int ilast ) 00226 { 00227 REAL area = det3( vdata[ilast]->t, vdata[itop-1]->t, vdata[itop-2]->t ); 00228 return (area < ZERO) ? 0 : 1; 00229 } 00230 00231 inline int 00232 Mesher::isCw( int ilast ) 00233 { 00234 REAL area = det3( vdata[ilast]->t, vdata[itop-1]->t, vdata[itop-2]->t ); 00235 return (area > -ZERO) ? 0 : 1; 00236 } 00237 00238 inline int 00239 Mesher::equal( int x, int y ) 00240 { 00241 return( last[0] == vdata[x] && last[1] == vdata[y] ); 00242 } 00243 00244 inline void 00245 Mesher::copy( int x, int y ) 00246 { 00247 last[0] = vdata[x]; last[1] = vdata[y]; 00248 } 00249 00250 inline void 00251 Mesher::move( int x, int y ) 00252 { 00253 vdata[x] = vdata[y]; 00254 } 00255 00256 inline void 00257 Mesher::output( int x ) 00258 { 00259 backend.tmeshvert( vdata[x] ); 00260 } 00261 00262 /*--------------------------------------------------------------------------- 00263 * addedge - addedge an edge to the triangulation 00264 * 00265 * This code has been re-written to generate large triangle meshes 00266 * from a monotone polygon. Although smaller triangle meshes 00267 * could be generated faster and with less code, larger meshes 00268 * actually give better SYSTEM performance. This is because 00269 * vertices are processed in the backend slower than they are 00270 * generated by this code and any decrease in the number of vertices 00271 * results in a decrease in the time spent in the backend. 00272 *--------------------------------------------------------------------------- 00273 */ 00274 00275 void 00276 Mesher::addLast( ) 00277 { 00278 register int ilast = itop; 00279 00280 if( lastedge == 0 ) { 00281 if( equal( 0, 1 ) ) { 00282 output( ilast ); 00283 swapMesh(); 00284 for( register int i = 2; i < ilast; i++ ) { 00285 swapMesh(); 00286 output( i ); 00287 } 00288 copy( ilast, ilast-1 ); 00289 } else if( equal( ilast-2, ilast-1) ) { 00290 swapMesh(); 00291 output( ilast ); 00292 for( register int i = ilast-3; i >= 0; i-- ) { 00293 output( i ); 00294 swapMesh(); 00295 } 00296 copy( 0, ilast ); 00297 } else { 00298 closeMesh(); openMesh(); 00299 output( ilast ); 00300 output( 0 ); 00301 for( register int i = 1; i < ilast; i++ ) { 00302 swapMesh(); 00303 output( i ); 00304 } 00305 copy( ilast, ilast-1 ); 00306 } 00307 } else { 00308 if( equal( 1, 0) ) { 00309 swapMesh(); 00310 output( ilast ); 00311 for( register int i = 2; i < ilast; i++ ) { 00312 output( i ); 00313 swapMesh(); 00314 } 00315 copy( ilast-1, ilast ); 00316 } else if( equal( ilast-1, ilast-2) ) { 00317 output( ilast ); 00318 swapMesh(); 00319 for( register int i = ilast-3; i >= 0; i-- ) { 00320 swapMesh(); 00321 output( i ); 00322 } 00323 copy( ilast, 0 ); 00324 } else { 00325 closeMesh(); openMesh(); 00326 output( 0 ); 00327 output( ilast ); 00328 for( register int i = 1; i < ilast; i++ ) { 00329 output( i ); 00330 swapMesh(); 00331 } 00332 copy( ilast-1, ilast ); 00333 } 00334 } 00335 closeMesh(); 00336 //for( register long k=0; k<=ilast; k++ ) pop( k ); 00337 } 00338 00339 void 00340 Mesher::addUpper( ) 00341 { 00342 register int ilast = itop; 00343 00344 if( lastedge == 0 ) { 00345 if( equal( 0, 1 ) ) { 00346 output( ilast ); 00347 swapMesh(); 00348 for( register int i = 2; i < ilast; i++ ) { 00349 swapMesh(); 00350 output( i ); 00351 } 00352 copy( ilast, ilast-1 ); 00353 } else if( equal( ilast-2, ilast-1) ) { 00354 swapMesh(); 00355 output( ilast ); 00356 for( register int i = ilast-3; i >= 0; i-- ) { 00357 output( i ); 00358 swapMesh(); 00359 } 00360 copy( 0, ilast ); 00361 } else { 00362 closeMesh(); openMesh(); 00363 output( ilast ); 00364 output( 0 ); 00365 for( register int i = 1; i < ilast; i++ ) { 00366 swapMesh(); 00367 output( i ); 00368 } 00369 copy( ilast, ilast-1 ); 00370 } 00371 lastedge = 1; 00372 //for( register long k=0; k<ilast-1; k++ ) pop( k ); 00373 move( 0, ilast-1 ); 00374 move( 1, ilast ); 00375 itop = 1; 00376 } else { 00377 if( ! isCcw( ilast ) ) return; 00378 do { 00379 itop--; 00380 } while( (itop > 1) && isCcw( ilast ) ); 00381 00382 if( equal( ilast-1, ilast-2 ) ) { 00383 output( ilast ); 00384 swapMesh(); 00385 for( register int i=ilast-3; i>=itop-1; i-- ) { 00386 swapMesh(); 00387 output( i ); 00388 } 00389 copy( ilast, itop-1 ); 00390 } else if( equal( itop, itop-1 ) ) { 00391 swapMesh(); 00392 output( ilast ); 00393 for( register int i = itop+1; i < ilast; i++ ) { 00394 output( i ); 00395 swapMesh(); 00396 } 00397 copy( ilast-1, ilast ); 00398 } else { 00399 closeMesh(); openMesh(); 00400 output( ilast ); 00401 output( ilast-1 ); 00402 for( register int i=ilast-2; i>=itop-1; i-- ) { 00403 swapMesh(); 00404 output( i ); 00405 } 00406 copy( ilast, itop-1 ); 00407 } 00408 //for( register int k=itop; k<ilast; k++ ) pop( k ); 00409 move( itop, ilast ); 00410 } 00411 } 00412 00413 void 00414 Mesher::addLower() 00415 { 00416 register int ilast = itop; 00417 00418 if( lastedge == 1 ) { 00419 if( equal( 1, 0) ) { 00420 swapMesh(); 00421 output( ilast ); 00422 for( register int i = 2; i < ilast; i++ ) { 00423 output( i ); 00424 swapMesh(); 00425 } 00426 copy( ilast-1, ilast ); 00427 } else if( equal( ilast-1, ilast-2) ) { 00428 output( ilast ); 00429 swapMesh(); 00430 for( register int i = ilast-3; i >= 0; i-- ) { 00431 swapMesh(); 00432 output( i ); 00433 } 00434 copy( ilast, 0 ); 00435 } else { 00436 closeMesh(); openMesh(); 00437 output( 0 ); 00438 output( ilast ); 00439 for( register int i = 1; i < ilast; i++ ) { 00440 output( i ); 00441 swapMesh(); 00442 } 00443 copy( ilast-1, ilast ); 00444 } 00445 00446 lastedge = 0; 00447 //for( register long k=0; k<ilast-1; k++ ) pop( k ); 00448 move( 0, ilast-1 ); 00449 move( 1, ilast ); 00450 itop = 1; 00451 } else { 00452 if( ! isCw( ilast ) ) return; 00453 do { 00454 itop--; 00455 } while( (itop > 1) && isCw( ilast ) ); 00456 00457 if( equal( ilast-2, ilast-1) ) { 00458 swapMesh(); 00459 output( ilast ); 00460 for( register int i=ilast-3; i>=itop-1; i--) { 00461 output( i ); 00462 swapMesh( ); 00463 } 00464 copy( itop-1, ilast ); 00465 } else if( equal( itop-1, itop) ) { 00466 output( ilast ); 00467 swapMesh(); 00468 for( register int i=itop+1; i<ilast; i++ ) { 00469 swapMesh( ); 00470 output( i ); 00471 } 00472 copy( ilast, ilast-1 ); 00473 } else { 00474 closeMesh(); openMesh(); 00475 output( ilast-1 ); 00476 output( ilast ); 00477 for( register int i=ilast-2; i>=itop-1; i-- ) { 00478 output( i ); 00479 swapMesh( ); 00480 } 00481 copy( itop-1, ilast ); 00482 } 00483 //for( register int k=itop; k<ilast; k++ ) pop( k ); 00484 move( itop, ilast ); 00485 } 00486 } 00487 00488 Generated on Thu May 24 2012 04:24:12 for ReactOS by
1.7.6.1
|