1 #ifdef GL_HERETIC
2 
3 //#define __DOOMTYPE__
4 
5 #include <stdio.h>
6 #include <string.h>
7 #include <math.h>
8 
9 #include "gl_syms.h"
10 
11 #include "gl_struct.h"
12 #include "gl_mem.h"
13 #ifndef GL_HEXEN
14 #include "doomdef.h"
15 #else
16 #include "h2def.h"
17 #endif
18 #include "r_local.h"
19 
20 #ifdef GL_HEXEN
21 #define F_SKY	"F_SKY"
22 extern int GL_Sky1Texture,GL_Sky2Texture;
23 char GLCurrentSky;
24 #else
25 #define F_SKY	"F_SKY1"
26 #endif
27 
28 #define GLCALLBACK
29 
30 extern lumpinfo_t	*lumpinfo;		// location of each lump on disk
31 extern GLTexture *p_stGLTextures;
32 extern GLTexArray *p_stGLTexArray;
33 
34 extern GLuint *texobjs;
35 
36 extern int *a_iGlDrawLine,*a_iGlDrawFloorCeil;
37 
38 extern int *a_iGLTexTranslation;
39 
40 //FloorCeilVertexesArray *a_stFloorVertexesArray;
41 //GLFloorCeilPolygon *a_stFCPolygons;
42 GLFloorCeilingPolygonArray *a_stFCPolygonArray;
43 
44 int iXMin,iXMax,iYMin,iYMax;
45 int xMapMin=0x7fffffff,xMapMax=-0x7fffffff,yMapMin=0x7fffffff,yMapMax=-0x7fffffff,iAltitudeMin=0x7fffffff,iAltitudeMax=-0x7fffffff;
46 int iLightLevelMin=0xffff,iLightLevelMax=-0xffff;
47 
48 GLFloorCeiling *a_stFloorCeiling;
49 //int startCeilingList,startFloorList;
50 int *a_iLineArray,*a_iLinePresent;
51 
52 //GLboolean bFloorCompute;
53 int iCurrentSector/*,iNbPoints*/;
54 
55 float fSkyRadius;
56 int iSkyList;
57 #ifdef GL_HEXEN
58 int iSkyList1,iSkyList2;
59 fixed_t Sky1ColumnOffset;
60 fixed_t Sky2ColumnOffset;
61 #endif
62 
63 int hVertexTmpHeap;
64 
65 /*typedef struct GLUtesselator GLUtriangulatorObj;
66 #define gluTessBeginPolygon(x,y) gluBeginPolygon(x)
67 #define gluTessEndPolygon gluEndPolygon
68 #define gluTessBeginContour
69 #define gluTessEndContour(x) gluNextContour(x,GLU_UNKNOWN)
70 */
71 int g_iSector;
72 
73 #ifndef DOOM_GL
74 H_boolean modifiedgame;
75 #endif
76 
77 
printLineInfo(line_t * lines,int l)78 void printLineInfo(line_t *lines, int l) {
79   printf("===================================\n");
80   printf("LINE-INFO of Line %u\n", l);
81   printf("iLineID: %d\n", lines[l].iLineID);
82   printf("v1[%.2f, %.2f] ; v2[%.2f, %.2f]\n",
83 	 ((GLdouble)lines[l].v1->x)/((GLdouble)MAP_SCALE),
84          ((GLdouble)lines[l].v1->y)/((GLdouble)MAP_SCALE),
85 	 ((GLdouble)lines[l].v2->x)/((GLdouble)MAP_SCALE),
86          ((GLdouble)lines[l].v2->y)/((GLdouble)MAP_SCALE));
87   printf("flags: %d ; special: %d ; tag: %d\n",
88 	 lines[l].flags, lines[l].special, lines[l].tag);
89   printf("===================================\n");
90 }
91 
printSectorInfo(sector_t * sectors,int s)92 void printSectorInfo(sector_t *sectors, int s) {
93   int l;
94   printf("------------------------------------\n");
95   printf("SECTOR-INFO of Sector %u\n", s);
96   printf("iSectorID: %d\n", sectors[s].iSectorID);
97   printf("floorheight: %d\n", sectors[s].floorheight/MAP_SCALE);
98   printf("ceilingheight: %d\n", sectors[s].ceilingheight/MAP_SCALE);
99   printf("floorpic: %d\n", sectors[s].floorpic);
100   printf("floorpic: %d\n", sectors[s].ceilingpic);
101   printf("lightlevel: %d\n", sectors[s].lightlevel);
102   printf("special: %d\n", sectors[s].special);
103   printf("tag: %d\n", sectors[s].tag);
104   printf("validcount: %d\n", sectors[s].validcount);
105   printf("linecount: %d\n", sectors[s].linecount);
106 
107   for (l=0; l<sectors[s].linecount; l++)
108     printLineInfo(*sectors[s].lines, l);
109 
110   printf("------------------------------------\n");
111 }
112 
errorCallback(GLenum errorCode)113 void GLCALLBACK errorCallback(GLenum errorCode)
114 {
115   //const GLubyte *estring;
116 
117   //estring = gluErrorString(errorCode);
118   //fprintf(stderr, "Tessellation Error: %s in sector %ul\n", estring,g_iSector);
119   fprintf(stderr, "[SDLGLdrv/floorceil] Tessellation Error: in sector %ul\n", g_iSector);
120   if (!modifiedgame)
121     exit(0);
122 }
123 
124 
fn_iGetUpperLeftLine(int * a_iLineArray,int * a_iLinePresent,int iNbLines,int sector)125 int fn_iGetUpperLeftLine(int *a_iLineArray,int *a_iLinePresent,int iNbLines,int sector)
126 { int i=0,iRet=-1,xMin,yMax,x,y;
127  GLboolean bBadSens=false;
128 
129  xMin=0x7fffffff;
130  yMax=-0x7fffffff;
131  iXMin=0x7fffffff;
132  iYMin=0x7fffffff;
133  iXMax=-0x7fffffff;
134  iYMax=-0x7fffffff;
135 
136  for (i=0;i<iNbLines;i++)
137    {	//if (a_iLineArray[i]==-1)
138      if (!a_iLinePresent[i])
139        continue;
140      //goto mapbound;
141 
142      x=-lines[a_iLineArray[i]].v1->x;
143      y=lines[a_iLineArray[i]].v1->y;
144 
145      if ((y==yMax)&&bBadSens&&(lines[a_iLineArray[i]].frontsector->iSectorID==sector))
146        {	yMax=y;
147        iRet=i;
148        bBadSens=false;
149        }
150 
151      //if ((x<=xMin)&&(y>=yMax))
152      if (/*(x<=xMin)||*/(y>yMax))
153        {	xMin=x;
154        yMax=y;
155        iRet=i;
156        if (lines[a_iLineArray[i]].frontsector->iSectorID==sector)
157 	 bBadSens=false;
158        else
159 	 bBadSens=true;
160        }
161 
162      x=-lines[a_iLineArray[i]].v2->x;
163      y=lines[a_iLineArray[i]].v2->y;
164 
165      if ((y==yMax)&&bBadSens&&lines[a_iLineArray[i]].frontsector->iSectorID==sector)
166        {	yMax=y;
167        iRet=i;
168        bBadSens=false;
169        }
170 
171      //if ((x<=xMin)&&(y>=yMax))
172      if (/*(x<=xMin)||*/(y>yMax))
173        {	xMin=x;
174        yMax=y;
175        iRet=i;
176        if (lines[a_iLineArray[i]].frontsector->iSectorID==sector)
177 	 bBadSens=false;
178        else
179 	 bBadSens=true;
180        }
181      if (x<iXMin)
182        iXMin=x;
183      if (x>iXMax)
184        iXMax=x;
185      if (y<iYMin)
186        iYMin=y;
187      if (y>iYMax)
188        iYMax=y;
189 
190 /*mapbound:
191   if (x<xMapMin)
192   xMapMin=x;
193   if (x>xMapMax)
194   xMapMax=x;
195   if (y<yMapMin)
196   yMapMin=y;
197   if (y>yMapMax)
198   yMapMax=y;*/
199    }
200  return iRet;
201 }
202 
fn_p_fVertex(GLdouble * p_dVertex)203 GLfloat *fn_p_fVertex(GLdouble *p_dVertex/*,GLfloat fLightLevel*/)
204 { GLfloat *p_fVertex;
205 
206  //p_fVertex=(GLfloat *)malloc(sizeof(GLfloat)*4);
207  p_fVertex=(GLfloat *)HeapAlloc(hVertexTmpHeap,0,sizeof(GLfloat)*4);
208 
209  p_fVertex[0]=(float)p_dVertex[0];
210  p_fVertex[1]=(float)p_dVertex[1];
211  p_fVertex[2]=(float)p_dVertex[2];
212  //p_fVertex[3]=fLightLevel;
213  p_fVertex[3]=(float)sectors[iCurrentSector].ceilingheight/MAP_SCALE;
214 
215  /*	if (bFloorCompute)
216 	{	a_stFloorVertexesArray[iCurrentSector].p_fFloor=(GLfloat **)Realloc(a_stFloorVertexesArray[iCurrentSector].p_fFloor,(iNbPoints+1)*sizeof(GLfloat *));
217 	a_stFloorVertexesArray[iCurrentSector].p_fCeiling=(GLfloat **)Realloc(a_stFloorVertexesArray[iCurrentSector].p_fCeiling,(iNbPoints+1)*sizeof(GLfloat *));
218 	a_stFloorVertexesArray[iCurrentSector].p_fFloor[iNbPoints++]=p_fVertex+1;
219 	}
220 	else
221 	a_stFloorVertexesArray[iCurrentSector].p_fCeiling[iNbPoints++]=p_fVertex+1;*/
222 
223  return p_fVertex;
224 }
225 
vertexArrayCallback(GLvoid * vertex)226 void GLCALLBACK vertexArrayCallback(GLvoid *vertex)
227 {
228  GLfloat *fVertex,fU,fV;
229  GLVertexArray *p_stVertexArray;
230 
231  /* ANDRE !!! */
232  /* fprintf(stderr, "vertexArrayCallback called.\n"); */
233 
234  p_stVertexArray=&a_stFCPolygonArray[iCurrentSector].p_stVertexArray[a_stFCPolygonArray[iCurrentSector].iNbArrays-1];
235  p_stVertexArray->iNbVertices++;
236  p_stVertexArray->p_fVertex=(GLfloat *)Realloc(p_stVertexArray->p_fVertex,3*p_stVertexArray->iNbVertices*sizeof(GLfloat));
237  p_stVertexArray->p_fUV=(GLfloat *)Realloc(p_stVertexArray->p_fUV,2*p_stVertexArray->iNbVertices*sizeof(GLfloat));
238  p_stVertexArray->p_fCeiling=(GLfloat *)Realloc(p_stVertexArray->p_fCeiling,p_stVertexArray->iNbVertices*sizeof(GLfloat));
239 
240  fVertex=(GLfloat *)vertex;
241  //fU=(float)(fVertex[0]*MAP_SCALE/*-iXMin*/)/FLAT_TEX_SIZE;
242  //fV=(float)(/*iYMax-*/fVertex[2]*MAP_SCALE)/FLAT_TEX_SIZE;
243  fU=(float)(fVertex[0]*(MAP_SCALE>>FRACBITS))/FLAT_TEX_SIZE;
244  fV=(float)(fVertex[2]*(MAP_SCALE>>FRACBITS))/FLAT_TEX_SIZE;
245 
246  p_stVertexArray->p_fVertex[3*(p_stVertexArray->iNbVertices-1)]=fVertex[0];
247  p_stVertexArray->p_fVertex[3*(p_stVertexArray->iNbVertices-1)+1]=fVertex[1];
248  p_stVertexArray->p_fVertex[3*(p_stVertexArray->iNbVertices-1)+2]=fVertex[2];
249 
250  /* ANDRE !!! */
251  /* printf("vertex info: vertex[%.2f, %.2f, %.2f]\n", fVertex[0], fVertex[1], fVertex[2]); */
252 
253  p_stVertexArray->p_fUV[2*(p_stVertexArray->iNbVertices-1)]=fU;
254  p_stVertexArray->p_fUV[2*(p_stVertexArray->iNbVertices-1)+1]=fV;
255 
256  p_stVertexArray->p_fCeiling[p_stVertexArray->iNbVertices-1]=fVertex[3];
257 
258  //free(fVertex);	// A voir
259 
260 /*	(*glTexCoord2f_s) (fU,fV);
261 	(*glVertex3fv_s) (fVertex);*/
262 }
263 
glArrayBegin(GLenum mode)264 void GLCALLBACK glArrayBegin(GLenum mode)
265 {
266  GLFloorCeilingPolygonArray *p_stPolyArray=a_stFCPolygonArray+iCurrentSector;
267 
268  /* ANDRE !!! */
269  /* fprintf(stderr, "glArrayBegin called.\n"); */
270 
271  p_stPolyArray->iNbArrays++;
272  p_stPolyArray->p_stVertexArray=(GLVertexArray *)Realloc(p_stPolyArray->p_stVertexArray,p_stPolyArray->iNbArrays*sizeof(GLVertexArray));
273 
274  p_stPolyArray->p_stVertexArray[p_stPolyArray->iNbArrays-1].mode=mode;
275  p_stPolyArray->p_stVertexArray[p_stPolyArray->iNbArrays-1].iNbVertices=0;
276  p_stPolyArray->p_stVertexArray[p_stPolyArray->iNbArrays-1].p_fVertex=(GLfloat *)Malloc(3*sizeof(GLfloat));
277  p_stPolyArray->p_stVertexArray[p_stPolyArray->iNbArrays-1].p_fUV=(GLfloat *)Malloc(2*sizeof(GLfloat));
278  p_stPolyArray->p_stVertexArray[p_stPolyArray->iNbArrays-1].p_fCeiling=(GLfloat *)Malloc(sizeof(GLfloat));
279 }
280 
glArrayEnd(void)281 void GLCALLBACK glArrayEnd(void)
282 {
283  /* ANDRE !!! */
284   /* fprintf(stderr, "glArrayEnd called.\n"); */
285 }
286 
VtxDist(vertex_t * v1,vertex_t * v2)287 int VtxDist(vertex_t *v1,vertex_t *v2)
288 {
289   return abs(v1->x-v2->x)+abs(v1->y-v2->y);
290 }
291 
292 #ifdef NDEBUG
293 #pragma optimize( "", off )
294 #endif
295 
fn_vCreatePolygonsForSector(int s)296 void fn_vCreatePolygonsForSector(int s)
297 { GLUtesselator *tobj;
298  int iLine,iRemainingLines,iNumLines,iDblLines;
299  vertex_t *vCurrentVertex,*vStartVertex,*vLastVertex;
300  GLdouble a_fVertex[2][3];
301  GLboolean bAbortSector;
302  int iLineCandidate;
303 
304  g_iSector=s;
305  tobj = gluNewTess();
306 
307  iCurrentSector=s;
308  a_stFCPolygonArray[s].iNbArrays=0;
309  a_stFCPolygonArray[s].p_stVertexArray=(GLVertexArray *)Malloc(sizeof(GLVertexArray));
310 
311  a_stFCPolygonArray[s].iCeilingTexture=fn_iGetGLFlatTexturef(sectors[s].ceilingpic);
312  a_stFCPolygonArray[s].iFloorTexture=fn_iGetGLFlatTexturef(sectors[s].floorpic);
313 
314  gluTessCallback(tobj, GLU_TESS_VERTEX,
315 		 vertexArrayCallback);
316 
317  gluTessCallback(tobj, GLU_TESS_BEGIN,
318 		 glArrayBegin);
319 
320  gluTessCallback(tobj, GLU_TESS_END,
321 	  	 glArrayEnd);
322 
323  gluTessCallback(tobj, GLU_TESS_ERROR,
324 		 errorCallback);
325 
326  gluTessBeginPolygon(tobj, NULL);
327 
328  iNumLines=sectors[s].linecount;
329  iDblLines=0;	// MR1006
330  for (iLine=0;iLine<iNumLines;iLine++)
331    { int i;
332 
333    i=sectors[s].lines[iLine]->iLineID;
334    a_iLineArray[iLine]=i;
335    if (modifiedgame)
336      {	if (lines[i].frontsector==lines[i].backsector)
337        {	// MR1006
338 				//a_iLinePresent[iLine]=2;
339 	 a_iLinePresent[iLine]=0;
340 	 iDblLines++;
341        }
342      else
343        a_iLinePresent[iLine]=1;
344      }
345    else
346      {
347 #ifdef DOOM_GL	// anti-bug...
348        if ((gamemap==22)&&(s==109)&&
349 	   ((i==530)||(i==607)||(i==542)||(i==610)))
350 	 {	a_iLinePresent[iLine]=0;
351 	 iDblLines++;
352 	 }
353        else
354 	 if ((gameepisode==4)&&(gamemap==3)&&(s==81)&&((i==757)||(i==759)))
355 	   {	a_iLinePresent[iLine]=0;
356 	   iDblLines++;
357 	   }
358 #elif GL_HEXEN
359        if ((gamemap==2)&&(i>1635)&&(i<1660))
360 	 {	// MR1006
361 				//a_iLinePresent[iLine]=2;
362 	   a_iLinePresent[iLine]=0;
363 	   iDblLines++;
364 	 }
365        else
366 	 if ((gamemap==8)&&
367 	     ((i>2147)&&(i<2152))||(i==2141)||(i==2142))
368 	   {
369 	     a_iLinePresent[iLine]=0;
370 	     iDblLines++;
371 	   }
372 	 else
373 	   if ((gamemap==10)&&(s==89)&&
374 	       ((i==107)||(i==123)||(i==708)))
375 	     {
376 	       a_iLinePresent[iLine]=0;
377 	       iDblLines++;
378 	     }
379 	   else
380 	     if ((gamemap==10)&&(s==91)&&
381 		 ((i==108)||(i==122)))
382 	       {
383 		 a_iLinePresent[iLine]=0;
384 		 iDblLines++;
385 	       }
386 	     else
387 	       if ((gamemap==10)&&(s==259)&&
388 		   ((i==1916)||(i==1925)||(i==1047)||((i>1048)&&(i<1053))||(i==1054)||(i==1056)))
389 		 {
390 		   a_iLinePresent[iLine]=0;
391 		   iDblLines++;
392 		 }
393 	       else
394 		 if ((gamemap==10)&&(s==189))
395 		   {	gluTessEndPolygon(tobj);
396 
397 		   gluDeleteTess(tobj);
398 		   return;
399 		   }
400 		 else
401 		   if ((gamemap==21)&&(s==114)&&
402 		       ((i==1179)||(i==1169)||
403 			((i>933)&&(i<938))||((i>946)&&(i<951)||((i>986)&&(i<991)))
404 			))
405 		     {
406 		       a_iLinePresent[iLine]=0;
407 		       iDblLines++;
408 		     }
409 		   else
410 #endif
411 		     if (lines[i].frontsector==lines[i].backsector)
412 		       {	// MR1006
413 				//a_iLinePresent[iLine]=2;
414 			 a_iLinePresent[iLine]=0;
415 			 iDblLines++;
416 		       }
417 		     else
418 		       a_iLinePresent[iLine]=1;
419      }
420    }
421 
422  if (!modifiedgame)
423    goto endantibugs;
424 #ifdef DOOM_GL	// Anti bug Doom1 E1M4 sector 61 :-((
425  if ((gameepisode==4)&&(gamemap==1)&&(s==61))
426    {	iNumLines+=2;
427    a_iLineArray[iLine]=403;
428    a_iLinePresent[iLine++]=1;
429    a_iLineArray[iLine]=404;
430    a_iLinePresent[iLine]=1;
431    }
432  if ((gameepisode==3)&&(gamemap==8)&&(s==1))	// anti bug E3M8 sectors 1 & 2
433    {	iNumLines+=2;
434    a_iLineArray[iLine]=57;
435    a_iLinePresent[iLine++]=1;
436    a_iLineArray[iLine]=21;
437    a_iLinePresent[iLine]=1;
438    }
439  if ((gameepisode==3)&&(gamemap==8)&&(s==2))
440    {	gluTessEndPolygon(tobj);
441 
442    gluDeleteTess(tobj);
443 
444    lines[57].backsector->iSectorID=1;
445    lines[21].frontsector->iSectorID=1;
446    return;
447    }
448  if ((gamemap==21)&&(s==49))
449    {	iNumLines+=2;
450    a_iLineArray[iLine]=134;
451    a_iLinePresent[iLine++]=1;
452    a_iLineArray[iLine]=114;
453    a_iLinePresent[iLine]=1;
454    }
455  if ((gamemap==50)||(gamemap==51))
456    {	gluTessEndPolygon(tobj);
457 
458    gluDeleteTess(tobj);
459    return;
460    }
461 #elif GL_HEXEN
462 	if ((gamemap==4)&&((s==140)||(s==152)))
463 	  {	gluTessEndPolygon(tobj);
464 
465 	  gluDeleteTess(tobj);
466 	  return;
467 	  }
468 	if ((gamemap==35)&&(s==23))
469 	  {	iNumLines++;
470 	  a_iLineArray[iLine]=1414;
471 	  a_iLinePresent[iLine]=1;
472 	  }
473 #else	// heretic
474 	if ((gameepisode==3)&&(gamemap==4)&&(s==112))
475 	  {	gluTessEndPolygon(tobj);
476 
477 	  gluDeleteTess(tobj);
478 	  return;
479 	  }
480 
481 #endif
482  endantibugs:
483 	iRemainingLines=iNumLines-iDblLines;
484 	bAbortSector=FALSE;
485 
486 	while (iRemainingLines)
487 	  {
488 	    /* fprintf(stderr,"in fn_vCreatePolygonsForSector- iRemainingLines: %d\n", iRemainingLines); */
489 
490 	    gluTessBeginContour(tobj);
491 
492 	    //glColor3f_s(fLightLevel, fLightLevel, fLightLevel);
493 	    /*iLine=0;
494 	      while (!a_iLinePresent[iLine]) iLine++;*/
495 	    iLine=fn_iGetUpperLeftLine(a_iLineArray,a_iLinePresent,iNumLines,s);
496 
497 	    // MR0906
498 	    if (lines[a_iLineArray[iLine]].frontsector->iSectorID==s)
499 	      {
500 		vStartVertex=lines[a_iLineArray[iLine]].v1;
501 		vCurrentVertex=lines[a_iLineArray[iLine]].v2;
502 		a_fVertex[0][0]=-(GLdouble)lines[a_iLineArray[iLine]].v1->x/MAP_SCALE;	// x
503 		a_fVertex[0][1]=(GLdouble)sectors[s].floorheight/MAP_SCALE;		// y
504 		a_fVertex[0][2]=(GLdouble)lines[a_iLineArray[iLine]].v1->y/MAP_SCALE;	// z
505 		a_fVertex[1][0]=-(GLdouble)lines[a_iLineArray[iLine]].v2->x/MAP_SCALE;	// x
506 		a_fVertex[1][1]=(GLdouble)sectors[s].floorheight/MAP_SCALE;		// y
507 		a_fVertex[1][2]=(GLdouble)lines[a_iLineArray[iLine]].v2->y/MAP_SCALE;	// z
508 	      }
509 	    else
510 	      {
511 		vStartVertex=lines[a_iLineArray[iLine]].v2;
512 		vCurrentVertex=lines[a_iLineArray[iLine]].v1;
513 		a_fVertex[1][0]=-(GLdouble)lines[a_iLineArray[iLine]].v1->x/MAP_SCALE;	// x
514 		a_fVertex[1][1]=(GLdouble)sectors[s].floorheight/MAP_SCALE;		// y
515 		a_fVertex[1][2]=(GLdouble)lines[a_iLineArray[iLine]].v1->y/MAP_SCALE;	// z
516 		a_fVertex[0][0]=-(GLdouble)lines[a_iLineArray[iLine]].v2->x/MAP_SCALE;	// x
517 		a_fVertex[0][1]=(GLdouble)sectors[s].floorheight/MAP_SCALE;		// y
518 		a_fVertex[0][2]=(GLdouble)lines[a_iLineArray[iLine]].v2->y/MAP_SCALE;	// z
519 	      }
520 
521 	    gluTessVertex(tobj, a_fVertex[0], fn_p_fVertex(a_fVertex[0]/*,fLightLevel*/));
522 	    gluTessVertex(tobj, a_fVertex[1], fn_p_fVertex(a_fVertex[1]/*,fLightLevel*/));
523 
524 	    a_iLinePresent[iLine]--;
525 	    if (!a_iLinePresent[iLine])
526 	      iRemainingLines--;
527 	    vLastVertex=NULL;
528 	    while (vCurrentVertex!=vStartVertex)
529 	      {
530 		// DOOM_GL: anti-bug (CF E1M3: linedefs 933 & 927 !!!)
531 		if (iLine==iNumLines)
532 		  { int dist, distMin=0x7fffffff, v=0, iLineMin=0;
533 
534 		  if (!iRemainingLines)	// Anti-bug 2: Cf MAP02 sector 39
535 		    {	vCurrentVertex=vStartVertex;
536 		    continue;
537 		    }
538 
539 		  for (iLine=0;iLine<iNumLines;iLine++)
540 		    {
541 		      if (!a_iLinePresent[iLine])
542 			continue;
543 		      if ((dist=VtxDist(lines[a_iLineArray[iLine]].v1,vCurrentVertex))<distMin)
544 			{
545 			  distMin=dist;
546 			  iLineMin=iLine;
547 			  v=1;
548 			}
549 		      if ((dist=VtxDist(lines[a_iLineArray[iLine]].v2,vCurrentVertex))<distMin)
550 			{
551 			  distMin=dist;
552 			  iLineMin=iLine;
553 			  v=2;
554 			}
555 		    }
556 		  iLine=iLineMin;
557 		  if (v==1)
558 		    {	vCurrentVertex=lines[a_iLineArray[iLine]].v2;
559 
560 		    if (vCurrentVertex!=vStartVertex)
561 		      {
562 			a_fVertex[0][0]=-(GLdouble)lines[a_iLineArray[iLine]].v2->x/MAP_SCALE;	// x
563 			a_fVertex[0][1]=(GLdouble)sectors[s].floorheight/MAP_SCALE;						// y
564 			a_fVertex[0][2]=(GLdouble)lines[a_iLineArray[iLine]].v2->y/MAP_SCALE;	// z
565 			gluTessVertex(tobj, a_fVertex[0], fn_p_fVertex(a_fVertex[0]/*,fLightLevel*/));
566 		      }
567 
568 		    //a_iLineArray[iLine]=-1;
569 		    a_iLinePresent[iLine]--;
570 		    if (!a_iLinePresent[iLine])
571 		      iRemainingLines--;
572 		    }
573 		  else
574 		    {
575 		      vCurrentVertex=lines[a_iLineArray[iLine]].v1;
576 
577 		      if (vCurrentVertex!=vStartVertex)
578 			{
579 			  a_fVertex[0][0]=-(GLdouble)lines[a_iLineArray[iLine]].v1->x/MAP_SCALE;	// x
580 			  a_fVertex[0][1]=(GLdouble)sectors[s].floorheight/MAP_SCALE;						// y
581 			  a_fVertex[0][2]=(GLdouble)lines[a_iLineArray[iLine]].v1->y/MAP_SCALE;	// z
582 			  gluTessVertex(tobj, a_fVertex[0], fn_p_fVertex(a_fVertex[0]/*,fLightLevel*/));
583 			}
584 
585 		      a_iLinePresent[iLine]--;
586 		      if (!a_iLinePresent[iLine])
587 			iRemainingLines--;
588 		    }
589 		  continue;
590 		  }
591 		// End DOOM_GL anti-bug...
592 		if (vCurrentVertex==vLastVertex)	// Invalid sector (not closed: Cf E1M9)
593 		  {	bAbortSector=TRUE;
594 		  break;
595 		  }
596 		vLastVertex=vCurrentVertex;
597 
598 		iLineCandidate=-1;	// MR1306
599 		for (iLine=0;iLine<iNumLines;iLine++)
600 		  {
601 		    if (!a_iLinePresent[iLine])
602 		      continue;
603 		    if (lines[a_iLineArray[iLine]].v1==vCurrentVertex)
604 		      {
605 			iLineCandidate=iLine;
606 			if (lines[a_iLineArray[iLine]].frontsector->iSectorID==s)
607 			  break;
608 			/*
609 							vCurrentVertex=lines[a_iLineArray[iLine]].v2;
610 
611 							if (vCurrentVertex!=vStartVertex)
612 							{
613 							a_fVertex[0][0]=-(GLdouble)lines[a_iLineArray[iLine]].v2->x/MAP_SCALE;	// x
614 							a_fVertex[0][1]=(GLdouble)sectors[s].floorheight/MAP_SCALE;						// y
615 							a_fVertex[0][2]=(GLdouble)lines[a_iLineArray[iLine]].v2->y/MAP_SCALE;	// z
616 							gluTessVertex(tobj, a_fVertex[0], fn_p_fVertex(a_fVertex[0]));
617 							}
618 
619 							//a_iLineArray[iLine]=-1;
620 							a_iLinePresent[iLine]--;
621 							if (!a_iLinePresent[iLine])
622 							iRemainingLines--;
623 							break;*/
624 		      }
625 		  }
626 		// MR1306
627 		//			if (iLine==iNumLines)
628 		if (iLineCandidate!=-1)
629 		  {	vCurrentVertex=lines[a_iLineArray[iLineCandidate]].v2;
630 
631 		  if (vCurrentVertex!=vStartVertex)
632 		    {
633 		      a_fVertex[0][0]=-(GLdouble)lines[a_iLineArray[iLineCandidate]].v2->x/MAP_SCALE;	// x
634 		      a_fVertex[0][1]=(GLdouble)sectors[s].floorheight/MAP_SCALE;						// y
635 		      a_fVertex[0][2]=(GLdouble)lines[a_iLineArray[iLineCandidate]].v2->y/MAP_SCALE;	// z
636 		      gluTessVertex(tobj, a_fVertex[0], fn_p_fVertex(a_fVertex[0]));
637 		    }
638 
639 				//a_iLineArray[iLine]=-1;
640 		  a_iLinePresent[iLineCandidate]--;
641 		  if (!a_iLinePresent[iLineCandidate])
642 		    iRemainingLines--;
643 		  }
644 		else
645 		  // End MR1306
646 		  for (iLine=0;iLine<iNumLines;iLine++)
647 		    {
648 		      /* fprintf(stderr,"in fn_vCreatePolygonsForSector- endLoop - iLine: %d ; iNumLines: %d\n",
649 			 iLine, iNumLines); */
650 		      if (!a_iLinePresent[iLine])
651 			continue;
652 
653 		      if (lines[a_iLineArray[iLine]].v2==vCurrentVertex)
654 			{
655 			  vCurrentVertex=lines[a_iLineArray[iLine]].v1;
656 
657 			  if (vCurrentVertex!=vStartVertex)
658 			    {
659 			      a_fVertex[0][0]=-(GLdouble)lines[a_iLineArray[iLine]].v1->x/MAP_SCALE;	// x
660 			      a_fVertex[0][1]=(GLdouble)sectors[s].floorheight/MAP_SCALE;						// y
661 			      a_fVertex[0][2]=(GLdouble)lines[a_iLineArray[iLine]].v1->y/MAP_SCALE;	// z
662 			      gluTessVertex(tobj, a_fVertex[0], fn_p_fVertex(a_fVertex[0]/*,fLightLevel*/));
663 			    }
664 
665 			  a_iLinePresent[iLine]--;
666 			  if (!a_iLinePresent[iLine])
667 			    iRemainingLines--;
668 			  break;
669 			}
670 		    }
671 	      }
672 	    gluTessEndContour(tobj);
673 	    if (bAbortSector)
674 	      break;
675 	  }
676 	gluTessEndPolygon(tobj);
677 	//glEndList();
678 
679 	gluDeleteTess(tobj);
680 }
681 
682 // MR0507
fn_vComputeBounds(int s)683 void fn_vComputeBounds(int s)
684 { int i,j;
685  float fUp,fDown,fLeft,fRight;
686 
687  for (i=0;i<a_stFCPolygonArray[s].iNbArrays;i++)
688    {	fUp=-1e+10;
689    fRight=-1e+10;
690    fDown=1e+10;
691    fLeft=1e+10;
692    for (j=0;j<a_stFCPolygonArray[s].p_stVertexArray[i].iNbVertices;j++)
693      {
694        if (a_stFCPolygonArray[s].p_stVertexArray[i].p_fVertex[j*3+2]>fUp)
695 	 fUp=a_stFCPolygonArray[s].p_stVertexArray[i].p_fVertex[j*3+2];
696        if (a_stFCPolygonArray[s].p_stVertexArray[i].p_fVertex[j*3+2]<fDown)
697 	 fDown=a_stFCPolygonArray[s].p_stVertexArray[i].p_fVertex[j*3+2];
698        if (a_stFCPolygonArray[s].p_stVertexArray[i].p_fVertex[j*3]>fRight)
699 	 fRight=a_stFCPolygonArray[s].p_stVertexArray[i].p_fVertex[j*3];
700        if (a_stFCPolygonArray[s].p_stVertexArray[i].p_fVertex[j*3]<fLeft)
701 	 fLeft=a_stFCPolygonArray[s].p_stVertexArray[i].p_fVertex[j*3];
702      }
703    a_stFCPolygonArray[s].p_stVertexArray[i].fUp=fUp;
704    a_stFCPolygonArray[s].p_stVertexArray[i].fDown=fDown;
705    a_stFCPolygonArray[s].p_stVertexArray[i].fLeft=fLeft;
706    a_stFCPolygonArray[s].p_stVertexArray[i].fRight=fRight;
707    }
708 }
709 
710 #ifdef NDEBUG
711 #pragma optimize( "", on )
712 #endif
713 
fn_vCreateFloorCeilingPolygons()714 void fn_vCreateFloorCeilingPolygons()
715 {
716   int s;
717 
718   xMapMin=0x7fffffff;
719   xMapMax=-0x7fffffff;
720   yMapMin=0x7fffffff;
721   yMapMax=-0x7fffffff;
722   iAltitudeMin=0x7fffffff;
723   iAltitudeMax=-0x7fffffff;
724 
725   hVertexTmpHeap=HeapCreate(OTHER);
726   /* fprintf(stderr, "hVertexTmpHeap: %d\n", hVertexTmpHeap); */
727 
728   a_iLineArray=(int *)Malloc(sizeof(int)*numlines);
729   a_iLinePresent=(int *)Malloc(sizeof(int)*numlines);
730 
731   a_stFCPolygonArray=(GLFloorCeilingPolygonArray *)Malloc(sizeof(GLFloorCeilingPolygonArray)*numsectors);
732 
733   a_iGlDrawFloorCeil=(int *)Malloc(sizeof(int)*numlines);
734 
735   for (s=0; s<numsectors; s++)
736     {
737       if (sectors[s].ceilingheight>iAltitudeMax)
738 	iAltitudeMax=sectors[s].ceilingheight;
739       if (sectors[s].floorheight<iAltitudeMin)
740 	iAltitudeMin=sectors[s].floorheight;
741 
742       iCurrentSector=s;
743 
744       /* ANDRE !!! */
745       /* fprintf(stderr, "numsectors: %u ; s: %u\n", numsectors, s); */
746       /* printSectorInfo(sectors, s); */
747 
748       /* E3M1 */
749       /* if ((s==8) || (s==14) || (s==49) || (s==103) || (s==105) || (s==106)) { */
750       /* E1M1 */
751       /* if ((s==6) || (s==34) || (s==52)) {
752 	printSectorInfo(sectors, s);
753       } else { */
754 
755       fn_vCreatePolygonsForSector(s);
756       // MR0507
757       fn_vComputeBounds(s);
758 
759       /* } */
760   }
761 
762   HeapDestroy(hVertexTmpHeap);
763 }
764 
765 #ifndef M_PI
766 #  define M_PI (3.1415926f)
767 #endif
768 #define TXTR_COORD(x,y)    /*if (qobj->TextureFlag)*/ (*glTexCoord2f_s) (x,y);
769 
fn_vGetMapExtremities()770 void fn_vGetMapExtremities()
771 { int i,x,y;
772 
773 	for (i=0;i<numlines;i++)
774 	{	x=-lines[i].v1->x;
775 		y=lines[i].v1->y;
776 		if (x<xMapMin)
777 			xMapMin=x;
778 		if (x>xMapMax)
779 			xMapMax=x;
780 		if (y<yMapMin)
781 			yMapMin=y;
782 		if (y>yMapMax)
783 			yMapMax=y;
784 		x=-lines[i].v2->x;
785 		y=lines[i].v2->y;
786 		if (x<xMapMin)
787 			xMapMin=x;
788 		if (x>xMapMax)
789 			xMapMax=x;
790 		if (y<yMapMin)
791 			yMapMin=y;
792 		if (y>yMapMax)
793 			yMapMax=y;
794 	}
795 }
796 
797 //#ifndef GL_HEXEN
798 #if 0		// For 3Dfx Minigl...
799 void MygluSphere( GLUquadricObj *qobj,
800                          GLdouble radius, GLint slices, GLint stacks )
801 {
802    GLfloat rho, drho, theta, dtheta;
803    GLfloat x, y, z;
804    GLfloat s, t, ds, dt;
805    GLint i, j, imin, imax;
806    GLboolean normals;
807    GLfloat nsign;
808 
809    normals = GL_TRUE;
810    nsign = -1.0f;
811 
812    drho = M_PI / (GLfloat) stacks;
813    dtheta = 2.0f * M_PI / (GLfloat) slices;
814 
815    /* texturing: s goes from 0.0/0.25/0.5/0.75/1.0 at +y/+x/-y/-x/+y axis */
816    /* t goes from -1.0/+1.0 at z = -radius/+radius (linear along longitudes) */
817    /* cannot use triangle fan on texturing (s coord. at top/bottom tip varies) */
818 
819    //if (qobj->DrawStyle==GLU_FILL)
820    {
821 
822       //ds = 1.0 / slices;
823       //dt = 1.0 / stacks;
824       ds = 5.0f / slices;
825 #ifndef DOOM_GL
826       dt = 1.0f / stacks;
827 #else
828 	  //dt = 1.2f / stacks;	// DOOM_GL
829 	  dt = 1.0f / stacks;	// DOOM_GL
830 #endif
831       t = 1.0f;  /* because loop now runs from 0 */
832       //if (qobj->TextureFlag)
833 	  {
834         imin = 0;
835         imax = stacks;
836       }
837       /*else
838 	  {
839         imin = 1;
840         imax = stacks-1;
841       }*/
842 
843       /* draw intermediate stacks as quad strips */
844       for (i=imin;i<imax;i++)
845 	  {
846 		 rho = i * drho;
847 		 (*glBegin_s) ( GL_QUAD_STRIP );
848 			 s = 0.0f;
849 		 for (j=0;j<=slices;j++)
850 		 {
851 			theta = (j==slices) ? 0.0f : j * dtheta;
852 			x = -(float)(sin(theta) * sin(rho));
853 			y = (float)(cos(theta) * sin(rho));
854 			z = nsign * (float)cos(rho);
855 			if (normals)  (*glNormal3f_s) ( x*nsign, y*nsign, z*nsign );
856 			TXTR_COORD(s,t);
857 			(*glVertex3f_s) ( x*(float)radius, y*(float)radius, z*(float)radius );
858 			x = -(float)(sin(theta) * sin(rho+drho));
859 			y = (float)(cos(theta) * sin(rho+drho));
860 			z = (float)(nsign * cos(rho+drho));
861 			if (normals)  (*glNormal3f_s) ( x*nsign, y*nsign, z*nsign );
862 			TXTR_COORD(s,t-dt);
863 				s += ds;
864 			(*glVertex3f_s) ( x*(float)radius, y*(float)radius, z*(float)radius );
865 		 }
866 		 (*glEnd_s) ();
867 		 t -= dt;
868 	 }
869 
870    }
871 }
872 
873 extern char szSkyName[4][8];
874 extern byte *p_bPalette;	// a virer
875 
876 void fn_vCreateSky(int episode)
877 { GLUquadricObj *qObj;
878   float fU1,fU2,fV1,fV2,fU1Off,fV2Off;
879   int iSubTex,iGLTex;
880   float xMapCenter,yMapCenter,zMapCenter;
881   float fX,fY,fAlt;
882 
883 	fn_vGetMapExtremities();
884 
885 	//xMapCenter=(float)(-xMapMin)/MAP_SCALE+(float)(-xMapMax+xMapMin)/(2*MAP_SCALE);
886 	xMapCenter=(GLdouble)xMapMin/MAP_SCALE+(GLdouble)(xMapMax-xMapMin)/(2*MAP_SCALE);
887 	yMapCenter=(GLdouble)iAltitudeMin/MAP_SCALE+(GLdouble)(iAltitudeMax-iAltitudeMin)/(2*MAP_SCALE);
888 #ifdef DOOM_GL
889 	zMapCenter=(GLdouble)yMapMin/MAP_SCALE+(GLdouble)(yMapMax-yMapMin)/(2*MAP_SCALE);		// DOOM_GL
890 #else
891 	zMapCenter=(GLdouble)yMapMin/MAP_SCALE+5.0f*(GLdouble)(yMapMax-yMapMin)/(6*MAP_SCALE);
892 #endif
893 
894 	fAlt=(float)((iAltitudeMax-iAltitudeMin)>>FRACBITS);
895 	fX=(float)((xMapMax-xMapMin)>>FRACBITS);
896 	fY=(float)((yMapMax-yMapMin)>>FRACBITS);
897 	fSkyRadius=(float)sqrt(fX*fX+fY*fY+fAlt*fAlt);
898 	fSkyRadius*=1.5f/MAP_COEFF;
899 	fSkyRadius=fSkyRadius>320.0f?fSkyRadius:320.0f;
900 
901 	iSkyList = (*glGenLists_s) (1);
902 #ifdef GL_HEXEN
903 	if (episode==1)
904 		iSkyList1 = iSkyList;
905 	else
906 		iSkyList2 = iSkyList;
907 #endif
908 	(*glNewList_s) (iSkyList, GL_COMPILE);
909 
910 	//fn_vLoadSkyTexture(episode);
911 	//(*glColor3f_s) (1.0f, 1.0f, 1.0f);
912 /*	qObj=gluNewQuadric();
913 	gluQuadricDrawStyle(qObj, GLU_FILL);
914 	gluQuadricOrientation(qObj,GLU_INSIDE);
915 	gluQuadricTexture(qObj,GL_TRUE);*/
916 
917 #ifndef GL_HEXEN
918 	iGLTex=fn_iGetGLTexturef(-2,0,0,&fU1,&fU2,&fV1,&fV2,&fU1Off,&fV2Off,&iSubTex);
919 	(*glBindTexture_s) (GL_TEXTURE_2D, texobjs[iGLTex]);
920 #else
921 	if (episode==1)
922 		(*glBindTexture_s) (GL_TEXTURE_2D, GL_Sky1Texture);
923 	else
924 		(*glBindTexture_s) (GL_TEXTURE_2D, GL_Sky2Texture);
925 #endif
926 	//(*glColor3f_s) (1.0f, 1.0f, 1.0f);	// MR1405
927 
928 	(*glMatrixMode_s) (GL_MODELVIEW);
929 	(*glPushMatrix_s) ();
930 	(*glLoadIdentity_s) ();
931 	(*glRotatef_s) (-90.0f,   1.0f, 0.0f, 0.0f);		// -90 for MygluSphere & 90 for gluSphere
932 	(*glTranslatef_s) (xMapCenter,yMapCenter,zMapCenter);
933 
934 	MygluSphere(qObj,fSkyRadius,10,10);
935 	(*glPopMatrix_s) ();
936 
937 	(*glEndList_s) ();
938 }
939 #else	// GL_HEXEN
940 GLSky *GLSky1;
941 
MygluSphere(GLdouble radius,GLint slices,GLint stacks)942 GLSky *MygluSphere( GLdouble radius, GLint slices, GLint stacks )
943 {
944    GLSky *p_stSky;
945    GLfloat rho, drho, theta, dtheta;
946    GLfloat x, y, z;
947    GLfloat s, t, ds, dt;
948    GLint i, j, imin, imax;
949    GLboolean normals;
950    GLfloat nsign;
951    GLint iPoint;
952 
953 
954    p_stSky=(GLSky *)Malloc(sizeof(GLSky));
955    normals = GL_TRUE;
956    nsign = -1.0f;
957 
958    drho = M_PI / (GLfloat) stacks;
959    dtheta = 2.0f * M_PI / (GLfloat) slices;
960 
961    /* texturing: s goes from 0.0/0.25/0.5/0.75/1.0 at +y/+x/-y/-x/+y axis */
962    /* t goes from -1.0/+1.0 at z = -radius/+radius (linear along longitudes) */
963    /* cannot use triangle fan on texturing (s coord. at top/bottom tip varies) */
964 
965    {
966 
967       ds = 5.0f / slices;
968       dt = 1.0f / stacks;
969       t = 1.0f;  /* because loop now runs from 0 */
970 	  {
971         imin = 0;
972         imax = stacks;
973       }
974 
975       p_stSky->iNbPoints=(imax-imin)*(slices+1)*2;
976 	  p_stSky->p_fVertex=(GLfloat *)Malloc(3*p_stSky->iNbPoints*sizeof(GLfloat));
977 	  p_stSky->p_fNormals=(GLfloat *)Malloc(3*p_stSky->iNbPoints*sizeof(GLfloat));
978 	  p_stSky->p_fV=(GLfloat *)Malloc(p_stSky->iNbPoints*sizeof(GLfloat));
979 	  p_stSky->slices=slices;
980 	  p_stSky->stacks=stacks;
981 	  iPoint=0;
982 	  /* draw intermediate stacks as quad strips */
983       for (i=imin;i<imax;i++)
984 	  {
985 		 rho = i * drho;
986 		 //(*glBegin_s) ( GL_QUAD_STRIP );
987 			 s = 0.0f;
988 		 for (j=0;j<=slices;j++)
989 		 {
990 			theta = (j==slices) ? 0.0f : j * dtheta;
991 			x = -(float)(sin(theta) * sin(rho));
992 			y = (float)(cos(theta) * sin(rho));
993 			z = nsign * (float)cos(rho);
994 			//if (normals)  (*glNormal3f_s) ( x*nsign, y*nsign, z*nsign );
995 			if (normals)
996 			{	p_stSky->p_fNormals[3*iPoint]=x*nsign;
997 				p_stSky->p_fNormals[3*iPoint+1]=y*nsign;
998 				p_stSky->p_fNormals[3*iPoint+2]=z*nsign;
999 			}
1000 			//TXTR_COORD(s,t);
1001 			//(*glVertex3f_s) ( x*(float)radius, y*(float)radius, z*(float)radius );
1002 			p_stSky->p_fV[iPoint]=t;
1003 			p_stSky->p_fVertex[3*iPoint]=x*radius;
1004 			p_stSky->p_fVertex[3*iPoint+1]=y*radius;
1005 			p_stSky->p_fVertex[3*iPoint+2]=z*radius;
1006 			iPoint++;
1007 
1008 			x = -(float)(sin(theta) * sin(rho+drho));
1009 			y = (float)(cos(theta) * sin(rho+drho));
1010 			z = (float)(nsign * cos(rho+drho));
1011 //			if (normals)  (*glNormal3f_s) ( x*nsign, y*nsign, z*nsign );
1012 			if (normals)
1013 			{	p_stSky->p_fNormals[3*iPoint]=x*nsign;
1014 				p_stSky->p_fNormals[3*iPoint+1]=y*nsign;
1015 				p_stSky->p_fNormals[3*iPoint+2]=z*nsign;
1016 			}
1017 //			TXTR_COORD(s,t-dt);
1018 				s += ds;
1019 //			(*glVertex3f_s) ( x*(float)radius, y*(float)radius, z*(float)radius );
1020 			p_stSky->p_fV[iPoint]=t-dt;
1021 			p_stSky->p_fVertex[3*iPoint]=x*radius;
1022 			p_stSky->p_fVertex[3*iPoint+1]=y*radius;
1023 			p_stSky->p_fVertex[3*iPoint+2]=z*radius;
1024 			iPoint++;
1025 		 }
1026 		 //(*glEnd_s) ();
1027 		 t -= dt;
1028 	 }
1029 
1030    }
1031    return p_stSky;
1032 }
1033 
fn_vCreateSky(int episode)1034 void fn_vCreateSky(int episode)
1035 { /* GLUquadricObj *qObj; */
1036   /* float fU1,fU2,fV1,fV2,fU1Off,fV2Off; */
1037   /* int iSubTex,iGLTex; */
1038   float xMapCenter,yMapCenter,zMapCenter;
1039   float fX,fY,fAlt;
1040 
1041 	fn_vGetMapExtremities();
1042 
1043 	xMapCenter=(GLdouble)xMapMin/MAP_SCALE+(GLdouble)(xMapMax-xMapMin)/(2*MAP_SCALE);
1044 	yMapCenter=(GLdouble)iAltitudeMin/MAP_SCALE+(GLdouble)(iAltitudeMax-iAltitudeMin)/(2*MAP_SCALE);
1045 	//zMapCenter=(GLdouble)yMapMin/MAP_SCALE+5.0f*(GLdouble)(yMapMax-yMapMin)/(6*MAP_SCALE);
1046 #ifdef DOOM_GL
1047 	zMapCenter=(GLdouble)yMapMin/MAP_SCALE+(GLdouble)(yMapMax-yMapMin)/(2*MAP_SCALE);		// DOOM_GL
1048 #elif GL_HEXEN
1049 	//zMapCenter=(GLdouble)yMapMin/MAP_SCALE+8.0f*((GLdouble)(yMapMax-yMapMin)/MAP_SCALE);
1050 	zMapCenter=(GLdouble)yMapMin/MAP_SCALE+7.5f*((GLdouble)(yMapMax-yMapMin)/MAP_SCALE);
1051 #else
1052 	zMapCenter=(GLdouble)yMapMin/MAP_SCALE+5.0f*(GLdouble)(yMapMax-yMapMin)/(6*MAP_SCALE);
1053 #endif
1054 
1055 	fAlt=(float)((iAltitudeMax-iAltitudeMin)>>FRACBITS);
1056 	fX=(float)((xMapMax-xMapMin)>>FRACBITS);
1057 	fY=(float)((yMapMax-yMapMin)>>FRACBITS);
1058 	fSkyRadius=(float)sqrt(fX*fX+fY*fY+fAlt*fAlt);
1059 	fSkyRadius*=1.5f/MAP_COEFF;
1060 	fSkyRadius=fSkyRadius>320.0f?fSkyRadius:320.0f;
1061 
1062 	GLSky1=MygluSphere(fSkyRadius,10,10);
1063 
1064 	GLSky1->xMapCenter=xMapCenter;
1065 	GLSky1->yMapCenter=yMapCenter;
1066 	GLSky1->zMapCenter=zMapCenter;
1067 #ifdef GL_HEXEN
1068 	GLCurrentSky=1;
1069 #endif
1070 }
1071 
fn_vDrawSky(int index)1072 void fn_vDrawSky(int index)
1073 { GLint iPoint,i,j;
1074   GLfloat ds,s;
1075   int offset,iTex;
1076 
1077 #ifdef GL_HEXEN
1078 	if (index==1)
1079 	{	(*glBindTexture_s) (GL_TEXTURE_2D, GL_Sky1Texture);
1080 		offset = Sky1ColumnOffset>>16;
1081 		iTex=GL_Sky1Texture-1;
1082 	}
1083 	else
1084 	{	(*glBindTexture_s) (GL_TEXTURE_2D, GL_Sky2Texture);
1085 		offset = Sky2ColumnOffset>>16;
1086 		iTex=GL_Sky2Texture-1;
1087 	}
1088 #else
1089 	int iSubTex;
1090 	float fU1,fU2,fV1,fV2,fU1Off,fV2Off;
1091 
1092 	iTex=fn_iGetGLTexturef(-2,0,0,&fU1,&fU2,&fV1,&fV2,&fU1Off,&fV2Off,&iSubTex);
1093 	(*glBindTexture_s) (GL_TEXTURE_2D, texobjs[iTex]);
1094 	offset=0;
1095 #endif
1096 	(*glMatrixMode_s) (GL_MODELVIEW);
1097 	(*glPushMatrix_s) ();
1098 	(*glLoadIdentity_s) ();
1099 	(*glRotatef_s) (-90.0f,   1.0f, 0.0f, 0.0f);		// -90 for MygluSphere & 90 for gluSphere
1100 	(*glTranslatef_s) (GLSky1->xMapCenter,GLSky1->yMapCenter,GLSky1->zMapCenter);
1101 
1102     iPoint=0;
1103 	ds = 5.0f / GLSky1->slices;
1104 
1105 	/* draw intermediate stacks as quad strips */
1106     for (i=0;i<GLSky1->stacks;i++)
1107 	{
1108 		 (*glBegin_s) ( GL_QUAD_STRIP );
1109 		 //s = 0.0f;
1110 		 s=(float)offset/(float)p_stGLTextures[iTex].iWidth;
1111 		 for (j=0;j<=GLSky1->slices;j++)
1112 		 {
1113 			(*glNormal3f_s) ( GLSky1->p_fNormals[3*iPoint], GLSky1->p_fNormals[3*iPoint+1], GLSky1->p_fNormals[3*iPoint+2] );
1114 			TXTR_COORD(s,GLSky1->p_fV[iPoint]);
1115 			(*glVertex3f_s) ( GLSky1->p_fVertex[3*iPoint], GLSky1->p_fVertex[3*iPoint+1], GLSky1->p_fVertex[3*iPoint+2] );
1116 			iPoint++;
1117 
1118 			(*glNormal3f_s) ( GLSky1->p_fNormals[3*iPoint], GLSky1->p_fNormals[3*iPoint+1], GLSky1->p_fNormals[3*iPoint+2] );
1119 			TXTR_COORD(s,GLSky1->p_fV[iPoint]);
1120 			(*glVertex3f_s) ( GLSky1->p_fVertex[3*iPoint], GLSky1->p_fVertex[3*iPoint+1], GLSky1->p_fVertex[3*iPoint+2] );
1121 			iPoint++;
1122 			s += ds;
1123 		 }
1124 		 (*glEnd_s) ();
1125 	 }
1126 
1127 	(*glPopMatrix_s) ();
1128 }
1129 #endif	// GL_HEXEN
1130 
1131 extern long g_bDynLight;
fn_vRenderSector(int s)1132 void fn_vRenderSector(int s)
1133 { int i,j,iGlTex;
1134   float fLightLevel;
1135 #ifdef GL_HEXEN
1136   short special;
1137   int scrollOffset,xOffset,yOffset;
1138   float fU,fV;
1139 #endif
1140 
1141    //(*glEnableClientState_s) (GL_VERTEX_ARRAY);
1142    //(*glEnableClientState_s) (GL_TEXTURE_COORD_ARRAY);
1143 
1144 	// MR0207
1145 	//fLightLevel=(float)(sectors[s].lightlevel-iLightLevelMin)/(float)(iLightLevelMax-iLightLevelMin);
1146 	//fLightLevel=(float)sectors[s].lightlevel/255.0f;
1147 	//fLightLevel=(float)(sectors[s].lightlevel-iLightLevelMin/2)/255.0f;
1148 	//fLightLevel=(1.0f+0.25f*(float)usegamma)*((float)sectors[s].lightlevel-0.5f)/512.0f;		// MR0706
1149 	fLightLevel=(1.0f+0.25f*(float)usegamma)*((float)(sectors[s].lightlevel+(extralight<<LIGHTSEGSHIFT))-0.5f)/512.0f;		// MR0706
1150 	//fLightLevel=(1.0f+0.25f*(float)usegamma)*(float)(sectors[s].lightlevel-iLightLevelMin)/(float)(iLightLevelMax-iLightLevelMin);
1151 
1152 	if (sectors[s].floorpic==R_FlatNumForName(F_SKY))
1153 	{
1154 		goto dceiling;
1155 	}
1156 	//iGlTex=a_iGLTexTranslation[fn_iGetGLFlatTexturef(sectors[s].floorpic)];
1157 
1158 	/* ANDRE !!! */
1159 	/* printf("POLYDRAW: a_stFCPolygonArray[%d].iFloorTexture: %d\n", s, a_stFCPolygonArray[s].iFloorTexture); */
1160 
1161 	iGlTex=a_iGLTexTranslation[a_stFCPolygonArray[s].iFloorTexture];
1162 	(*glBindTexture_s) (GL_TEXTURE_2D, texobjs[iGlTex]);
1163 
1164 #ifdef GL_HEXEN
1165 	special=sectors[s].special;
1166 	scrollOffset = leveltime>>1&63;
1167 	switch(special)
1168 	{ // Handle scrolling flats
1169 		case 201: case 202: case 203: // Scroll_North_xxx
1170 			/*ds_source = tempSource+((scrollOffset
1171 				<<(pl->special-201)&63)<<6);*/
1172 			xOffset=0;
1173 			yOffset=((63-scrollOffset)<<(special-201)&63);
1174 			break;
1175 		case 204: case 205: case 206: // Scroll_East_xxx
1176 			/*ds_source = tempSource+((63-scrollOffset)
1177 				<<(pl->special-204)&63);*/
1178 			xOffset=(scrollOffset<<(special-204)&63);
1179 			yOffset=0;
1180 			break;
1181 		case 207: case 208: case 209: // Scroll_South_xxx
1182 			/*ds_source = tempSource+(((63-scrollOffset)
1183 				<<(pl->special-207)&63)<<6);*/
1184 			xOffset=0;
1185 			yOffset=(scrollOffset<<(special-207)&63);
1186 			break;
1187 		case 210: case 211: case 212: // Scroll_West_xxx
1188 			/*ds_source = tempSource+(scrollOffset
1189 				<<(pl->special-210)&63);*/
1190 			xOffset=((63-scrollOffset)<<(special-210)&63);
1191 			yOffset=0;
1192 			break;
1193 		case 213: case 214: case 215: // Scroll_NorthWest_xxx
1194 			/*ds_source = tempSource+(scrollOffset
1195 				<<(pl->special-213)&63)+((scrollOffset
1196 				<<(pl->special-213)&63)<<6);*/
1197 			xOffset=((63-scrollOffset)<<(special-213)&63);
1198 			yOffset=((63-scrollOffset)<<(special-213)&63);
1199 			break;
1200 		case 216: case 217: case 218: // Scroll_NorthEast_xxx
1201 			/*ds_source = tempSource+((63-scrollOffset)
1202 				<<(pl->special-216)&63)+((scrollOffset
1203 				<<(pl->special-216)&63)<<6);*/
1204 			xOffset=(scrollOffset<<(special-216)&63);
1205 			yOffset=((63-scrollOffset)<<(special-216)&63);
1206 			break;
1207 		case 219: case 220: case 221: // Scroll_SouthEast_xxx
1208 			/*ds_source = tempSource+((63-scrollOffset)
1209 				<<(pl->special-219)&63)+(((63-scrollOffset)
1210 				<<(pl->special-219)&63)<<6);*/
1211 			xOffset=(scrollOffset<<(special-219)&63);
1212 			yOffset=(scrollOffset<<(special-219)&63);
1213 			break;
1214 		case 222: case 223: case 224: // Scroll_SouthWest_xxx
1215 			/*ds_source = tempSource+(scrollOffset
1216 				<<(pl->special-222)&63)+(((63-scrollOffset)
1217 				<<(pl->special-222)&63)<<6);*/
1218 			xOffset=((63-scrollOffset)<<(special-222)&63);
1219 			yOffset=(scrollOffset<<(special-222)&63);
1220 			break;
1221 		default:
1222 			xOffset=0;
1223 			yOffset=0;
1224 	}
1225 	fU=(float)xOffset/64.0f;
1226 	fV=(float)yOffset/64.0f;
1227 #endif
1228 
1229 	/* ANDRE !!! */
1230 	/* printf("POLYDRAW - FRONT a_stFCPolygonArray[%d].iNbArrays: %d\n", s, a_stFCPolygonArray[s].iNbArrays); */
1231 
1232 	// MR090699
1233 	(*glCullFace_s) (GL_FRONT);
1234 
1235 	if (g_bDynLight==1)
1236 	{
1237 		for (i=0;i<a_stFCPolygonArray[s].iNbArrays;i++)
1238 		{
1239 		  (*glBegin_s) (a_stFCPolygonArray[s].p_stVertexArray[i].mode);
1240 			for (j=0;j<a_stFCPolygonArray[s].p_stVertexArray[i].iNbVertices;j++)
1241 			{
1242 				GL_DynamicLight4f(a_stFCPolygonArray[s].p_stVertexArray[i].p_fVertex[j*3],
1243 							a_stFCPolygonArray[s].p_stVertexArray[i].p_fVertex[j*3+1],
1244 							a_stFCPolygonArray[s].p_stVertexArray[i].p_fVertex[j*3+2],
1245 							fLightLevel,1.0f );
1246 #ifndef GL_HEXEN
1247 				(*glTexCoord2f_s) (a_stFCPolygonArray[s].p_stVertexArray[i].p_fUV[j*2],
1248 							a_stFCPolygonArray[s].p_stVertexArray[i].p_fUV[j*2+1] );
1249 #else
1250 				(*glTexCoord2f_s) (a_stFCPolygonArray[s].p_stVertexArray[i].p_fUV[j*2]+fU,
1251 							a_stFCPolygonArray[s].p_stVertexArray[i].p_fUV[j*2+1]+fV );
1252 #endif
1253 				(*glVertex3f_s) ( a_stFCPolygonArray[s].p_stVertexArray[i].p_fVertex[j*3],
1254 							a_stFCPolygonArray[s].p_stVertexArray[i].p_fVertex[j*3+1],
1255 							a_stFCPolygonArray[s].p_stVertexArray[i].p_fVertex[j*3+2] );
1256 			}
1257 			(*glEnd_s) ();
1258 		}
1259 	}
1260 	else
1261 	{	GL_StaticLight3f(fLightLevel, fLightLevel, fLightLevel);
1262 		for (i=0;i<a_stFCPolygonArray[s].iNbArrays;i++)
1263 		{
1264 			//(*glVertexPointer_s) (3, GL_FLOAT, 0, a_stFCPolygonArray[s].p_stVertexArray[i].iNbVertices, a_stFCPolygonArray[s].p_stVertexArray[i].p_fVertex);
1265 			//(*glTexCoordPointer_s) (2, GL_FLOAT, 0, a_stFCPolygonArray[s].p_stVertexArray[i].iNbVertices, a_stFCPolygonArray[s].p_stVertexArray[i].p_fUV);
1266 			//(*glDrawArrays_s) (a_stFCPolygonArray[s].p_stVertexArray[i].mode,0,a_stFCPolygonArray[s].p_stVertexArray[i].iNbVertices);
1267 			(*glBegin_s) (a_stFCPolygonArray[s].p_stVertexArray[i].mode);
1268 			for (j=0;j<a_stFCPolygonArray[s].p_stVertexArray[i].iNbVertices;j++)
1269 			{
1270 				//(*glArrayElement_s) (j);
1271 #ifndef GL_HEXEN
1272 				(*glTexCoord2f_s) (a_stFCPolygonArray[s].p_stVertexArray[i].p_fUV[j*2],
1273 							a_stFCPolygonArray[s].p_stVertexArray[i].p_fUV[j*2+1] );
1274 #else
1275 				(*glTexCoord2f_s) (a_stFCPolygonArray[s].p_stVertexArray[i].p_fUV[j*2]+fU,
1276 							a_stFCPolygonArray[s].p_stVertexArray[i].p_fUV[j*2+1]+fV );
1277 #endif
1278 				(*glVertex3f_s) ( a_stFCPolygonArray[s].p_stVertexArray[i].p_fVertex[j*3],
1279 							a_stFCPolygonArray[s].p_stVertexArray[i].p_fVertex[j*3+1],
1280 							a_stFCPolygonArray[s].p_stVertexArray[i].p_fVertex[j*3+2] );
1281 			}
1282 			(*glEnd_s) ();
1283 		}
1284 	}
1285 dceiling:
1286 
1287 	/* ANDRE !!! */
1288 	/* printf("POLYDRAW - BACK a_stFCPolygonArray[%d].iNbArrays: %d\n", s, a_stFCPolygonArray[s].iNbArrays); */
1289 
1290 	// MR090699
1291 	(*glCullFace_s) (GL_BACK);
1292 
1293  	if (sectors[s].ceilingpic==R_FlatNumForName(F_SKY))
1294 	{
1295 		//return;
1296 		goto dynlight;
1297 	}
1298 	//iGlTex=a_iGLTexTranslation[fn_iGetGLFlatTexturef(sectors[s].ceilingpic)];
1299 	iGlTex=a_iGLTexTranslation[a_stFCPolygonArray[s].iCeilingTexture];
1300 	(*glBindTexture_s) (GL_TEXTURE_2D, texobjs[iGlTex]);
1301 
1302 	if (g_bDynLight==1)
1303 	{
1304 		for (i=0;i<a_stFCPolygonArray[s].iNbArrays;i++)
1305 		{
1306 		  (*glBegin_s) (a_stFCPolygonArray[s].p_stVertexArray[i].mode);
1307 			for (j=0;j<a_stFCPolygonArray[s].p_stVertexArray[i].iNbVertices;j++)
1308 			{
1309 				GL_DynamicLight4f(a_stFCPolygonArray[s].p_stVertexArray[i].p_fVertex[j*3],
1310 							a_stFCPolygonArray[s].p_stVertexArray[i].p_fCeiling[j],
1311 							a_stFCPolygonArray[s].p_stVertexArray[i].p_fVertex[j*3+2],
1312 							fLightLevel,1.0f );
1313 				(*glTexCoord2f_s) (a_stFCPolygonArray[s].p_stVertexArray[i].p_fUV[j*2],
1314 							a_stFCPolygonArray[s].p_stVertexArray[i].p_fUV[j*2+1] );
1315 				(*glVertex3f_s) ( a_stFCPolygonArray[s].p_stVertexArray[i].p_fVertex[j*3],
1316 							a_stFCPolygonArray[s].p_stVertexArray[i].p_fCeiling[j],
1317 							a_stFCPolygonArray[s].p_stVertexArray[i].p_fVertex[j*3+2] );
1318 			}
1319 			(*glEnd_s) ();
1320 		}
1321 	}
1322 	else
1323 	{
1324 		for (i=0;i<a_stFCPolygonArray[s].iNbArrays;i++)
1325 		{
1326 			(*glBegin_s) (a_stFCPolygonArray[s].p_stVertexArray[i].mode);
1327 			for (j=0;j<a_stFCPolygonArray[s].p_stVertexArray[i].iNbVertices;j++)
1328 			{
1329 				(*glTexCoord2f_s) (a_stFCPolygonArray[s].p_stVertexArray[i].p_fUV[j*2],
1330 							a_stFCPolygonArray[s].p_stVertexArray[i].p_fUV[j*2+1] );
1331 				(*glVertex3f_s) ( a_stFCPolygonArray[s].p_stVertexArray[i].p_fVertex[j*3],
1332 							a_stFCPolygonArray[s].p_stVertexArray[i].p_fCeiling[j],
1333 							a_stFCPolygonArray[s].p_stVertexArray[i].p_fVertex[j*3+2] );
1334 			}
1335 			(*glEnd_s) ();
1336 		}
1337 	}
1338 dynlight:
1339 	if (g_bDynLight==2)
1340 		GL_DrawLightForFloorCeiling(s);
1341    //(*glDisableClientState_s) (GL_VERTEX_ARRAY);
1342    //(*glDisableClientState_s) (GL_TEXTURE_COORD_ARRAY);
1343 }
1344 
1345 #ifdef GL_HEXEN
1346 GLint GL_vRegisterFlatTextureOnTheFly(int iTexNum);
1347 #endif
1348 
GL_vSetFloorTexture(int iSectorID,int texture)1349 void GL_vSetFloorTexture(int iSectorID,int texture)
1350 {
1351 #ifndef GL_HEXEN	// MR0309
1352 	a_stFCPolygonArray[iSectorID].iFloorTexture=fn_iGetGLFlatTexturef(texture);
1353 #else
1354 	if ((a_stFCPolygonArray[iSectorID].iFloorTexture=fn_iIsFlatTextureRegistered(texture))==-1)
1355 	{	a_stFCPolygonArray[iSectorID].iFloorTexture=GL_vRegisterFlatTextureOnTheFly(texture);
1356 		fn_vCheckIfFlatIsAnimated(texture);
1357 	}
1358 #endif
1359 }
1360 #ifdef GL_HEXEN
GL_vSetCeilingTexture(int iSectorID,int texture)1361 void GL_vSetCeilingTexture(int iSectorID,int texture)
1362 {
1363 	//a_stFCPolygonArray[iSectorID].iCeilingTexture=fn_iGetGLFlatTexturef(texture);
1364 	if ((a_stFCPolygonArray[iSectorID].iCeilingTexture=fn_iIsFlatTextureRegistered(texture))==-1)
1365 	{	a_stFCPolygonArray[iSectorID].iCeilingTexture=GL_vRegisterFlatTextureOnTheFly(texture);
1366 		fn_vCheckIfFlatIsAnimated(texture);
1367 	}
1368 }
1369 
fn_vUpdateFloorCeilingTexturesFromSavedGame()1370 void fn_vUpdateFloorCeilingTexturesFromSavedGame()
1371 { int s;
1372 
1373 	for (s=0;s<numsectors;s++)
1374 	{
1375 		GL_vSetFloorTexture(s,sectors[s].floorpic);
1376 		GL_vSetCeilingTexture(s,sectors[s].ceilingpic);
1377 	}
1378 }
1379 #endif
1380 
1381 #if 0
1382 void fn_vCreateFloorPolygons()
1383 {
1384   int s;
1385 
1386 	//bFloorCompute=TRUE;
1387 
1388 	//a_stFloorCeiling=(GLFloorCeiling *)Malloc(sizeof(GLFloorCeiling)*numsectors);
1389 	a_iLineArray=(int *)Malloc(sizeof(int)*numlines);
1390 	a_iLinePresent=(int *)Malloc(sizeof(int)*numlines);
1391 
1392 	//a_stFloorVertexesArray=(FloorCeilVertexesArray *)Malloc(sizeof(FloorCeilVertexesArray)*numsectors);
1393 	//a_stFCPolygons=(GLFloorCeilPolygon *)Malloc(sizeof(GLFloorCeilPolygon)*numsectors);
1394 	a_stFCPolygonArray=(GLFloorCeilingPolygonArray *)Malloc(sizeof(GLFloorCeilingPolygonArray)*numsectors);
1395 
1396 	a_iGlDrawFloorCeil=(int *)Malloc(sizeof(int)*numlines);;
1397 
1398 	//startFloorList = glGenLists(numsectors);
1399 	for (s=0;s<numsectors;s++)
1400 	{
1401 		if (sectors[s].ceilingheight>iAltitudeMax)
1402 			iAltitudeMax=sectors[s].ceilingheight;
1403 		if (sectors[s].floorheight<iAltitudeMin)
1404 			iAltitudeMin=sectors[s].floorheight;
1405 
1406 		iCurrentSector=s;
1407 		//a_stFloorVertexesArray[s].p_fFloor=(GLfloat **)Malloc(sizeof(GLfloat *));
1408 		//a_stFloorVertexesArray[s].p_fCeiling=(GLfloat **)Malloc(sizeof(GLfloat *));
1409 
1410 		//fn_vGeneratePolygonForSector(s);
1411 		//fn_vCreateFloorPolygonsForSector(s);
1412 		fn_vCreateFloorPolygonsForSectorWithArrays(s);
1413 
1414 		//a_stFloorVertexesArray[s].iNbPoints=iNbPoints;
1415 	}
1416 }
1417 
1418 void GLCALLBACK vertexCallback(GLvoid *vertex)
1419 { GLfloat *fVertex,fU,fV;
1420 
1421 	fVertex=(GLfloat *)vertex;
1422 	//fU=(float)(fVertex[0]*MAP_SCALE/*-iXMin*/)/FLAT_TEX_SIZE;
1423 	//fV=(float)(/*iYMax-*/fVertex[2]*MAP_SCALE)/FLAT_TEX_SIZE;
1424 	fU=(float)(fVertex[0]*(MAP_SCALE>>FRACBITS))/FLAT_TEX_SIZE;
1425 	fV=(float)(fVertex[2]*(MAP_SCALE>>FRACBITS))/FLAT_TEX_SIZE;
1426 	(*glTexCoord2f_s) (fU,fV);
1427 	(*glVertex3fv_s) (fVertex);
1428 }
1429 
1430 void fn_vAddVertexToContour(GLContour *p_stContour,GLdouble *p_fVertex)
1431 {
1432 	p_stContour->iNbVertexes++;
1433 	p_stContour->p_fVertex=(GLVertex *)Realloc(p_stContour->p_fVertex,p_stContour->iNbVertexes*sizeof(GLVertex));
1434 	p_stContour->p_fVertex[p_stContour->iNbVertexes-1].a_fCoord[0]=p_fVertex[0];
1435 	p_stContour->p_fVertex[p_stContour->iNbVertexes-1].a_fCoord[1]=p_fVertex[2];
1436 }
1437 
1438 void fn_vAddContourToPolygon(GLFloorCeilPolygon *p_stPolygon)
1439 {
1440 	p_stPolygon->iNbContours++;
1441 	p_stPolygon->p_stContours=(GLContour *)Realloc(p_stPolygon->p_stContours,p_stPolygon->iNbContours*sizeof(GLContour));
1442 	p_stPolygon->p_stContours[p_stPolygon->iNbContours-1].iNbVertexes=0;
1443 	p_stPolygon->p_stContours[p_stPolygon->iNbContours-1].p_fVertex=(GLVertex *)Malloc(sizeof(GLVertex));
1444 }
1445 
1446 void fn_vGeneratePolygonForSector(int s)
1447 {
1448   int iLine/*,iCurrentVertex,iStartVertex*/,iRemainingLines,iNumLines;
1449   vertex_t *vCurrentVertex,*vStartVertex,*vLastVertex;
1450   //int *a_iLineArray,*a_iLinePresent;
1451   GLdouble a_fVertex[2][3];
1452   //int iLastVertex;
1453   GLboolean bAbortSector;
1454 
1455 	iNbPoints=0;
1456 
1457 	a_stFCPolygons[s].iNbContours=0;
1458 	a_stFCPolygons[s].p_stContours=(GLContour *)Malloc(sizeof(GLContour));
1459 
1460 	if (sectors[s].floorpic==R_FlatNumForName(F_SKY))
1461 	{	(*glEndList_s) ();
1462 		return;
1463 	}
1464 
1465 	iNumLines=sectors[s].linecount;
1466 	for (iLine=0;iLine<iNumLines;iLine++)
1467 	{ int i;
1468 
1469 		i=sectors[s].lines[iLine]->iLineID;
1470 
1471 		a_iLineArray[iLine]=i;
1472 		if (lines[i].frontsector==lines[i].backsector)
1473 			a_iLinePresent[iLine]=2;
1474 		else
1475 			a_iLinePresent[iLine]=1;
1476 	}
1477 
1478 	iRemainingLines=iNumLines;
1479 	bAbortSector=FALSE;
1480 	while (iRemainingLines)
1481 	{
1482 		fn_vAddContourToPolygon(a_stFCPolygons+s);
1483 
1484 		/*iLine=0;
1485 		while (!a_iLinePresent[iLine]) iLine++;*/
1486 		iLine=fn_iGetUpperLeftLine(a_iLineArray,a_iLinePresent,iNumLines);
1487 
1488 		vStartVertex=lines[a_iLineArray[iLine]].v1;
1489 		vCurrentVertex=lines[a_iLineArray[iLine]].v2;
1490 		a_fVertex[0][0]=-(GLdouble)lines[a_iLineArray[iLine]].v1->x/MAP_SCALE;	// x
1491 		a_fVertex[0][1]=(GLdouble)sectors[s].floorheight/MAP_SCALE;				// y
1492 		a_fVertex[0][2]=(GLdouble)lines[a_iLineArray[iLine]].v1->y/MAP_SCALE;	// z
1493 		a_fVertex[1][0]=-(GLdouble)lines[a_iLineArray[iLine]].v2->x/MAP_SCALE;	// x
1494 		a_fVertex[1][1]=(GLdouble)sectors[s].floorheight/MAP_SCALE;				// y
1495 		a_fVertex[1][2]=(GLdouble)lines[a_iLineArray[iLine]].v2->y/MAP_SCALE;	// z
1496 
1497 		fn_vAddVertexToContour(&a_stFCPolygons[s].p_stContours[a_stFCPolygons[s].iNbContours-1],a_fVertex[0]);
1498 		fn_vAddVertexToContour(&a_stFCPolygons[s].p_stContours[a_stFCPolygons[s].iNbContours-1],a_fVertex[1]);
1499 
1500 		a_iLinePresent[iLine]--;
1501 		if (!a_iLinePresent[iLine])
1502 			iRemainingLines--;
1503 
1504 		vLastVertex=NULL;
1505 		while (vCurrentVertex!=vStartVertex)
1506 		{	if (vCurrentVertex==vLastVertex)	// Invalid sector (not closed: Cf E1M9)
1507 			{	bAbortSector=TRUE;
1508 				break;
1509 			}
1510 			vLastVertex=vCurrentVertex;
1511 
1512 			for (iLine=0;iLine<iNumLines;iLine++)
1513 			{	//if (a_iLineArray[iLine]==-1)
1514 				if (!a_iLinePresent[iLine])
1515 					continue;
1516 				if (lines[a_iLineArray[iLine]].v1==vCurrentVertex)
1517 				{
1518 					vCurrentVertex=lines[a_iLineArray[iLine]].v2;
1519 
1520 					if (vCurrentVertex!=vStartVertex)
1521 					{
1522 						/*a_fVertex[0][0]=-(GLdouble)vertexes[lines[a_iLineArray[iLine]].v2].x/MAP_SCALE;	// x
1523 						a_fVertex[0][1]=(GLdouble)sectors[s].floorheight/MAP_SCALE;						// y
1524 						a_fVertex[0][2]=(GLdouble)vertexes[lines[a_iLineArray[iLine]].v2].y/MAP_SCALE;	// z*/
1525 						a_fVertex[0][0]=-(GLdouble)lines[a_iLineArray[iLine]].v2->x/MAP_SCALE;	// x
1526 						a_fVertex[0][1]=(GLdouble)sectors[s].floorheight/MAP_SCALE;						// y
1527 						a_fVertex[0][2]=(GLdouble)lines[a_iLineArray[iLine]].v2->y/MAP_SCALE;	// z
1528 						fn_vAddVertexToContour(&a_stFCPolygons[s].p_stContours[a_stFCPolygons[s].iNbContours-1],a_fVertex[0]);
1529 
1530 					}
1531 
1532 					//a_iLineArray[iLine]=-1;
1533 					a_iLinePresent[iLine]--;
1534 					if (!a_iLinePresent[iLine])
1535 						iRemainingLines--;
1536 					break;
1537 				}
1538 				if (lines[a_iLineArray[iLine]].v2==vCurrentVertex)
1539 				{
1540 					vCurrentVertex=lines[a_iLineArray[iLine]].v1;
1541 
1542 					if (vCurrentVertex!=vStartVertex)
1543 					{
1544 						/*a_fVertex[0][0]=-(GLdouble)vertexes[lines[a_iLineArray[iLine]].v1].x/MAP_SCALE;	// x
1545 						a_fVertex[0][1]=(GLdouble)sectors[s].floorheight/MAP_SCALE;						// y
1546 						a_fVertex[0][2]=(GLdouble)vertexes[lines[a_iLineArray[iLine]].v1].y/MAP_SCALE;	// z*/
1547 						a_fVertex[0][0]=-(GLdouble)lines[a_iLineArray[iLine]].v1->x/MAP_SCALE;	// x
1548 						a_fVertex[0][1]=(GLdouble)sectors[s].floorheight/MAP_SCALE;						// y
1549 						a_fVertex[0][2]=(GLdouble)lines[a_iLineArray[iLine]].v1->y/MAP_SCALE;	// z
1550 						fn_vAddVertexToContour(&a_stFCPolygons[s].p_stContours[a_stFCPolygons[s].iNbContours-1],a_fVertex[0]);
1551 					}
1552 
1553 					//a_iLineArray[iLine]=-1;
1554 					a_iLinePresent[iLine]--;
1555 					if (!a_iLinePresent[iLine])
1556 						iRemainingLines--;
1557 					break;
1558 				}
1559 			}
1560 		}
1561 		if (bAbortSector)
1562 			break;
1563 	}
1564 }
1565 
1566 
1567 void Oldfn_vCreateFloorPolygonsForSectorWithArrays(int s)
1568 { GLUtesselator *tobj;
1569   int iLine/*,iCurrentVertex,iStartVertex*/,iRemainingLines,iNumLines;
1570   vertex_t *vCurrentVertex,*vStartVertex,*vLastVertex;
1571   //int *a_iLineArray,*a_iLinePresent;
1572   GLdouble a_fVertex[2][3];
1573   int iGlTex,i,j;
1574   float fLightLevel;
1575   //int iLastVertex;
1576   GLboolean bAbortSector;
1577 
1578 	tobj = gluNewTess();
1579 
1580 	iCurrentSector=s;
1581 	a_stFCPolygonArray[s].iNbArrays=0;
1582 	a_stFCPolygonArray[s].p_stVertexArray=(GLVertexArray *)Malloc(sizeof(GLVertexArray));
1583 
1584 	//fLightLevel=(float)(sectors[s].lightlevel-iLightLevelMin)/(float)(iLightLevelMax-iLightLevelMin);
1585 
1586 	//a_stFloorCeiling[s].iFloorCallList=startFloorList+s;
1587 
1588 	gluTessCallback(tobj, GLU_TESS_VERTEX,
1589 					   vertexArrayCallback);
1590 	gluTessCallback(tobj, GLU_TESS_BEGIN,
1591 					   glArrayBegin);
1592 	gluTessCallback(tobj, GLU_TESS_END,
1593 			                   glArrayEnd);
1594 	gluTessCallback(tobj, GLU_TESS_ERROR,
1595 					   errorCallback);
1596 
1597 	/*(*glNewList_s) (startFloorList+s, GL_COMPILE);
1598 
1599 	if (sectors[s].floorpic==R_FlatNumForName("F_SKY1"))
1600 	{	(*glEndList_s) ();
1601 		return;
1602 	}
1603 	iGlTex=fn_iGetGLFlatTexturef(sectors[s].floorpic);
1604 	(*glBindTexture_s) (GL_TEXTURE_2D, texobjs[iGlTex]);*/
1605 
1606 	gluTessBeginPolygon(tobj, NULL);
1607 
1608 	for (i=0;i<a_stFCPolygons[s].iNbContours;i++)
1609 	{
1610 		gluTessBeginContour(tobj);
1611 
1612 		//(*glColor3f_s) (fLightLevel, fLightLevel, fLightLevel);
1613 
1614 		for (j=0;j<a_stFCPolygons[s].p_stContours[i].iNbVertexes;j++)
1615 		{	a_fVertex[0][0]=a_stFCPolygons[s].p_stContours[i].p_fVertex[j].a_fCoord[0];
1616 			a_fVertex[0][1]=(GLdouble)sectors[s].floorheight/MAP_SCALE;
1617 			a_fVertex[0][2]=a_stFCPolygons[s].p_stContours[i].p_fVertex[j].a_fCoord[1];
1618 
1619 			gluTessVertex(tobj, a_fVertex[0], fn_p_fVertex(a_fVertex[0]/*,fLightLevel*/));
1620 		}
1621 		gluTessEndContour(tobj);
1622 	}
1623 	gluTessEndPolygon(tobj);
1624 //	(*glEndList_s) ();
1625 
1626 	gluDeleteTess(tobj);
1627 }
1628 
1629 void fn_vCreateFloorPolygonsForSector(int s)
1630 { GLUtesselator *tobj;
1631   int iLine/*,iCurrentVertex,iStartVertex*/,iRemainingLines,iNumLines;
1632   vertex_t *vCurrentVertex,*vStartVertex,*vLastVertex;
1633   //int *a_iLineArray,*a_iLinePresent;
1634   GLdouble a_fVertex[2][3];
1635   int iGlTex,i,j;
1636   float fLightLevel;
1637   //int iLastVertex;
1638   GLboolean bAbortSector;
1639 
1640 	tobj = gluNewTess();
1641 
1642 	//fLightLevel=(float)sectors[s].lightlevel/255;
1643 	fLightLevel=(float)(sectors[s].lightlevel-iLightLevelMin)/(float)(iLightLevelMax-iLightLevelMin);
1644 
1645 	a_stFloorCeiling[s].iFloorCallList=startFloorList+s;
1646 
1647 	gluTessCallback(tobj, GLU_TESS_VERTEX,
1648 					   vertexCallback);
1649 	gluTessCallback(tobj, GLU_TESS_BEGIN,
1650 					   glBegin);
1651 	gluTessCallback(tobj, GLU_TESS_END,
1652 					   glEnd);
1653 	gluTessCallback(tobj, GLU_TESS_ERROR,
1654 					   errorCallback);
1655 
1656 	(*glNewList_s) (startFloorList+s, GL_COMPILE);
1657 
1658 	//if (!strncmp(sectors[s].floorpic,"F_SKY1",8))
1659 	if (sectors[s].floorpic==R_FlatNumForName(F_SKY))
1660 	{	(*glEndList_s) ();
1661 		return;
1662 	}
1663 	iGlTex=fn_iGetGLFlatTexturef(sectors[s].floorpic);
1664 	(*glBindTexture_s) (GL_TEXTURE_2D, texobjs[iGlTex]);
1665 
1666 	gluTessBeginPolygon(tobj, NULL);
1667 
1668 	for (i=0;i<a_stFCPolygons[s].iNbContours;i++)
1669 	{
1670 		gluTessBeginContour(tobj);
1671 
1672 		GL_StaticLight3f(fLightLevel, fLightLevel, fLightLevel);
1673 
1674 		for (j=0;j<a_stFCPolygons[s].p_stContours[i].iNbVertexes;j++)
1675 		{	a_fVertex[0][0]=a_stFCPolygons[s].p_stContours[i].p_fVertex[j].a_fCoord[0];
1676 			a_fVertex[0][1]=(GLdouble)sectors[s].floorheight/MAP_SCALE;
1677 			a_fVertex[0][2]=a_stFCPolygons[s].p_stContours[i].p_fVertex[j].a_fCoord[1];
1678 
1679 			gluTessVertex(tobj, a_fVertex[0], fn_p_fVertex(a_fVertex[0]/*,fLightLevel*/));
1680 		}
1681 		gluTessEndContour(tobj);
1682 	}
1683 	gluTessEndPolygon(tobj);
1684 	(*glEndList_s) ();
1685 
1686 	gluDeleteTess(tobj);
1687 }
1688 
1689 void Oldfn_vCreateFloorPolygonsForSector(int s)
1690 { GLUtesselator *tobj;
1691   int iLine/*,iCurrentVertex,iStartVertex*/,iRemainingLines,iNumLines;
1692   vertex_t *vCurrentVertex,*vStartVertex,*vLastVertex;
1693   //int *a_iLineArray,*a_iLinePresent;
1694   GLdouble a_fVertex[2][3];
1695   int iGlTex;
1696   float fLightLevel;
1697   //int iLastVertex;
1698   GLboolean bAbortSector;
1699 
1700 	tobj = gluNewTess();
1701 
1702 	iNbPoints=0;
1703 
1704 	//fLightLevel=(float)sectors[s].lightlevel/255;
1705 	fLightLevel=(float)(sectors[s].lightlevel-iLightLevelMin)/(float)(iLightLevelMax-iLightLevelMin);
1706 
1707 	a_stFloorCeiling[s].iFloorCallList=startFloorList+s;
1708 
1709 	gluTessCallback(tobj, GLU_TESS_VERTEX,
1710 					   vertexCallback);
1711 	gluTessCallback(tobj, GLU_TESS_BEGIN,
1712 					   glBegin);
1713 	gluTessCallback(tobj, GLU_TESS_END,
1714 					   glEnd);
1715 	gluTessCallback(tobj, GLU_TESS_ERROR,
1716 					   errorCallback);
1717 
1718 	(*glNewList_s) (startFloorList+s, GL_COMPILE);
1719 
1720 	//if (!strncmp(sectors[s].floorpic,"F_SKY1",8))
1721 	if (sectors[s].floorpic==R_FlatNumForName(F_SKY))
1722 	{	(*glEndList_s) ();
1723 		return;
1724 	}
1725 	iGlTex=fn_iGetGLFlatTexturef(sectors[s].floorpic);
1726 	(*glBindTexture_s) (GL_TEXTURE_2D, texobjs[iGlTex]);
1727 
1728 	gluTessBeginPolygon(tobj, NULL);
1729 
1730 	iNumLines=sectors[s].linecount;
1731 	for (iLine=0;iLine<iNumLines;iLine++)
1732 	{ int i;
1733 
1734 #ifdef GL_HERETIC
1735 		i=sectors[s].lines[iLine]->iLineID;
1736 #endif
1737 		a_iLineArray[iLine]=i;
1738 		if (lines[i].frontsector==lines[i].backsector)
1739 			a_iLinePresent[iLine]=2;
1740 		else
1741 			a_iLinePresent[iLine]=1;
1742 	}
1743 	/*iNumLines=0;
1744 	for (iLine=0;iLine<numlines;iLine++)
1745 		//if ((sides[lines[iLine].sidenum[0]].sector==&sectors[s])||
1746 		//	((lines[iLine].sidenum[1]!=-1)&&(sides[lines[iLine].sidenum[1]].sector==&sectors[s])))
1747 		if ((lines[iLine].frontsector==&sectors[s])||
1748 			(lines[iLine].backsector==&sectors[s]))
1749 		{	a_iLineArray[iNumLines++]=iLine;
1750 			//if ((lines[iLine].sidenum[1]!=-1)&&
1751 			//	(sides[lines[iLine].sidenum[0]].sector==sides[lines[iLine].sidenum[1]].sector))
1752 			if (lines[iLine].frontsector==lines[iLine].backsector)
1753 				a_iLinePresent[iNumLines-1]=2;
1754 			else
1755 				a_iLinePresent[iNumLines-1]=1;
1756 		}*/
1757 
1758 	iRemainingLines=iNumLines;
1759 	bAbortSector=FALSE;
1760 	while (iRemainingLines)
1761 	{
1762 		gluTessBeginContour(tobj);
1763 
1764 		GL_StaticLight3f(fLightLevel, fLightLevel, fLightLevel);
1765 		iLine=0;
1766 		while (!a_iLinePresent[iLine]) iLine++;
1767 		//iLine=fn_iGetUpperLeftLine(a_iLineArray,a_iLinePresent,iNumLines);
1768 
1769 /*			iStartVertex=lines[a_iLineArray[iLine]].v1;
1770 		iCurrentVertex=lines[a_iLineArray[iLine]].v2;
1771 		a_fVertex[0][0]=-(GLdouble)vertexes[lines[a_iLineArray[iLine]].v1].x/MAP_SCALE;	// x
1772 		a_fVertex[0][1]=(GLdouble)sectors[s].floorheight/MAP_SCALE;						// y
1773 		a_fVertex[0][2]=(GLdouble)vertexes[lines[a_iLineArray[iLine]].v1].y/MAP_SCALE;	// z
1774 		a_fVertex[1][0]=-(GLdouble)vertexes[lines[a_iLineArray[iLine]].v2].x/MAP_SCALE;	// x
1775 		a_fVertex[1][1]=(GLdouble)sectors[s].floorheight/MAP_SCALE;						// y
1776 		a_fVertex[1][2]=(GLdouble)vertexes[lines[a_iLineArray[iLine]].v2].y/MAP_SCALE;	// z*/
1777 		vStartVertex=lines[a_iLineArray[iLine]].v1;
1778 		vCurrentVertex=lines[a_iLineArray[iLine]].v2;
1779 		a_fVertex[0][0]=-(GLdouble)lines[a_iLineArray[iLine]].v1->x/MAP_SCALE;	// x
1780 		a_fVertex[0][1]=(GLdouble)sectors[s].floorheight/MAP_SCALE;				// y
1781 		a_fVertex[0][2]=(GLdouble)lines[a_iLineArray[iLine]].v1->y/MAP_SCALE;	// z
1782 		a_fVertex[1][0]=-(GLdouble)lines[a_iLineArray[iLine]].v2->x/MAP_SCALE;	// x
1783 		a_fVertex[1][1]=(GLdouble)sectors[s].floorheight/MAP_SCALE;				// y
1784 		a_fVertex[1][2]=(GLdouble)lines[a_iLineArray[iLine]].v2->y/MAP_SCALE;	// z
1785 
1786 		gluTessVertex(tobj, a_fVertex[0], fn_p_fVertex(a_fVertex[0]/*,fLightLevel*/));
1787 		gluTessVertex(tobj, a_fVertex[1], fn_p_fVertex(a_fVertex[1]/*,fLightLevel*/));
1788 
1789 		//a_iLineArray[iLine]=-1;
1790 		a_iLinePresent[iLine]--;
1791 		if (!a_iLinePresent[iLine])
1792 			iRemainingLines--;
1793 		//iLastVertex=-1;
1794 		vLastVertex=NULL;
1795 		while (vCurrentVertex!=vStartVertex)
1796 		{	if (vCurrentVertex==vLastVertex)	// Invalid sector (not closed: Cf E1M9)
1797 			{	bAbortSector=TRUE;
1798 				break;
1799 			}
1800 			vLastVertex=vCurrentVertex;
1801 
1802 			for (iLine=0;iLine<iNumLines;iLine++)
1803 			{	//if (a_iLineArray[iLine]==-1)
1804 				if (!a_iLinePresent[iLine])
1805 					continue;
1806 				if (lines[a_iLineArray[iLine]].v1==vCurrentVertex)
1807 				{
1808 					vCurrentVertex=lines[a_iLineArray[iLine]].v2;
1809 
1810 					if (vCurrentVertex!=vStartVertex)
1811 					{
1812 						/*a_fVertex[0][0]=-(GLdouble)vertexes[lines[a_iLineArray[iLine]].v2].x/MAP_SCALE;	// x
1813 						a_fVertex[0][1]=(GLdouble)sectors[s].floorheight/MAP_SCALE;						// y
1814 						a_fVertex[0][2]=(GLdouble)vertexes[lines[a_iLineArray[iLine]].v2].y/MAP_SCALE;	// z*/
1815 						a_fVertex[0][0]=-(GLdouble)lines[a_iLineArray[iLine]].v2->x/MAP_SCALE;	// x
1816 						a_fVertex[0][1]=(GLdouble)sectors[s].floorheight/MAP_SCALE;						// y
1817 						a_fVertex[0][2]=(GLdouble)lines[a_iLineArray[iLine]].v2->y/MAP_SCALE;	// z
1818 						gluTessVertex(tobj, a_fVertex[0], fn_p_fVertex(a_fVertex[0]/*,fLightLevel*/));
1819 					}
1820 
1821 					//a_iLineArray[iLine]=-1;
1822 					a_iLinePresent[iLine]--;
1823 					if (!a_iLinePresent[iLine])
1824 						iRemainingLines--;
1825 					break;
1826 				}
1827 				if (lines[a_iLineArray[iLine]].v2==vCurrentVertex)
1828 				{
1829 					vCurrentVertex=lines[a_iLineArray[iLine]].v1;
1830 
1831 					if (vCurrentVertex!=vStartVertex)
1832 					{
1833 						/*a_fVertex[0][0]=-(GLdouble)vertexes[lines[a_iLineArray[iLine]].v1].x/MAP_SCALE;	// x
1834 						a_fVertex[0][1]=(GLdouble)sectors[s].floorheight/MAP_SCALE;						// y
1835 						a_fVertex[0][2]=(GLdouble)vertexes[lines[a_iLineArray[iLine]].v1].y/MAP_SCALE;	// z*/
1836 						a_fVertex[0][0]=-(GLdouble)lines[a_iLineArray[iLine]].v1->x/MAP_SCALE;	// x
1837 						a_fVertex[0][1]=(GLdouble)sectors[s].floorheight/MAP_SCALE;						// y
1838 						a_fVertex[0][2]=(GLdouble)lines[a_iLineArray[iLine]].v1->y/MAP_SCALE;	// z
1839 						gluTessVertex(tobj, a_fVertex[0], fn_p_fVertex(a_fVertex[0]/*,fLightLevel*/));
1840 					}
1841 
1842 					//a_iLineArray[iLine]=-1;
1843 					a_iLinePresent[iLine]--;
1844 					if (!a_iLinePresent[iLine])
1845 						iRemainingLines--;
1846 					break;
1847 				}
1848 			}
1849 		}
1850 		gluTessEndContour(tobj);
1851 		if (bAbortSector)
1852 			break;
1853 	}
1854 	gluTessEndPolygon(tobj);
1855 	(*glEndList_s) ();
1856 
1857 	gluDeleteTess(tobj);
1858 }
1859 
1860 
1861 // --- Must be called after FLOOR ---
1862 void fn_vCreateCeilingPolygonsForSector(int s)
1863 { GLUtesselator *tobj;
1864   int iLine/*,iCurrentVertex,iStartVertex*/,iRemainingLines,iNumLines;
1865   vertex_t *vCurrentVertex,*vStartVertex,*vLastVertex;
1866   GLdouble a_fVertex[2][3];
1867   int iGlTex;
1868   float fLightLevel;
1869   //int iLastVertex;
1870   GLboolean bAbortSector;
1871 
1872 	tobj = gluNewTess();
1873 
1874 	iNbPoints=0;
1875 
1876 	//fLightLevel=(float)sectors[s].lightlevel/255;
1877 	fLightLevel=(float)(sectors[s].lightlevel-iLightLevelMin)/(float)(iLightLevelMax-iLightLevelMin);
1878 
1879 	a_stFloorCeiling[s].iCeilingCallList=startCeilingList+s;
1880 
1881 	gluTessCallback(tobj, GLU_TESS_VERTEX,
1882 					   vertexCallback);
1883 	gluTessCallback(tobj, GLU_TESS_BEGIN,
1884 					   glBegin);
1885 	gluTessCallback(tobj, GLU_TESS_END,
1886 					   glEnd);
1887 	gluTessCallback(tobj, GLU_TESS_ERROR,
1888 					   errorCallback);
1889 
1890 	(*glNewList_s) (startCeilingList+s, GL_COMPILE);
1891 
1892 	//if (!strncmp(sectors[s].ceilingpic,"F_SKY1",8))
1893 	if (sectors[s].ceilingpic==R_FlatNumForName(F_SKY))
1894 	{	(*glEndList_s) ();
1895 		return;
1896 	}
1897 	iGlTex=fn_iGetGLFlatTexturef(sectors[s].ceilingpic);
1898 	(*glBindTexture_s) (GL_TEXTURE_2D, texobjs[iGlTex]);
1899 
1900 	gluTessBeginPolygon(tobj, NULL);
1901 
1902 	iNumLines=0;
1903 	for (iLine=0;iLine<numlines;iLine++)
1904 		if ((lines[iLine].frontsector==&sectors[s])||
1905 			(lines[iLine].backsector==&sectors[s]))
1906 		{	a_iLineArray[iNumLines++]=iLine;
1907 			//if ((lines[iLine].sidenum[1]!=-1)&&
1908 			//	(sides[lines[iLine].sidenum[0]].sector==sides[lines[iLine].sidenum[1]].sector))
1909 			if (lines[iLine].frontsector==lines[iLine].backsector)
1910 				a_iLinePresent[iNumLines-1]=2;
1911 			else
1912 				a_iLinePresent[iNumLines-1]=1;
1913 		}
1914 
1915 	iRemainingLines=iNumLines;
1916 	while (iRemainingLines)
1917 	{
1918 		gluTessBeginContour(tobj);
1919 
1920 		GL_StaticLight3f(fLightLevel, fLightLevel, fLightLevel);
1921 		/*iLine=0;
1922 		while (a_iLineArray[iLine]==-1) iLine++;*/
1923 		iLine=fn_iGetUpperLeftLine(a_iLineArray,a_iLinePresent,iNumLines);
1924 
1925 		vStartVertex=lines[a_iLineArray[iLine]].v1;
1926 		vCurrentVertex=lines[a_iLineArray[iLine]].v2;
1927 		/*a_fVertex[0][0]=-(GLdouble)vertexes[lines[a_iLineArray[iLine]].v1].x/MAP_SCALE;	// x
1928 		a_fVertex[0][1]=(GLdouble)sectors[s].ceilingheight/MAP_SCALE;						// y
1929 		a_fVertex[0][2]=(GLdouble)vertexes[lines[a_iLineArray[iLine]].v1].y/MAP_SCALE;	// z
1930 		a_fVertex[1][0]=-(GLdouble)vertexes[lines[a_iLineArray[iLine]].v2].x/MAP_SCALE;	// x
1931 		a_fVertex[1][1]=(GLdouble)sectors[s].ceilingheight/MAP_SCALE;						// y
1932 		a_fVertex[1][2]=(GLdouble)vertexes[lines[a_iLineArray[iLine]].v2].y/MAP_SCALE;	// z*/
1933 		a_fVertex[0][0]=-(GLdouble)lines[a_iLineArray[iLine]].v1->x/MAP_SCALE;	// x
1934 		a_fVertex[0][1]=(GLdouble)sectors[s].ceilingheight/MAP_SCALE;			// y
1935 		a_fVertex[0][2]=(GLdouble)lines[a_iLineArray[iLine]].v1->y/MAP_SCALE;	// z
1936 		a_fVertex[1][0]=-(GLdouble)lines[a_iLineArray[iLine]].v2->x/MAP_SCALE;	// x
1937 		a_fVertex[1][1]=(GLdouble)sectors[s].ceilingheight/MAP_SCALE;			// y
1938 		a_fVertex[1][2]=(GLdouble)lines[a_iLineArray[iLine]].v2->y/MAP_SCALE;	// z
1939 
1940 		gluTessVertex(tobj, a_fVertex[0], fn_p_fVertex(a_fVertex[0]/*,fLightLevel*/));
1941 		gluTessVertex(tobj, a_fVertex[1], fn_p_fVertex(a_fVertex[1]/*,fLightLevel*/));
1942 		//a_iLineArray[iLine]=-1;
1943 		a_iLinePresent[iLine]--;
1944 		if (!a_iLinePresent[iLine])
1945 			iRemainingLines--;
1946 		while (vCurrentVertex!=vStartVertex)
1947 		{	if (vCurrentVertex==vLastVertex)
1948 			{	bAbortSector=TRUE;
1949 				break;
1950 			}
1951 			vLastVertex=vCurrentVertex;
1952 
1953 			for (iLine=0;iLine<iNumLines;iLine++)
1954 			{	//if (a_iLineArray[iLine]==-1)
1955 				if (!a_iLinePresent[iLine])
1956 					continue;
1957 				if (lines[a_iLineArray[iLine]].v1==vCurrentVertex)
1958 				{
1959 					vCurrentVertex=lines[a_iLineArray[iLine]].v2;
1960 
1961 					if (vCurrentVertex!=vStartVertex)
1962 					{
1963 						/*a_fVertex[0][0]=-(GLdouble)vertexes[lines[a_iLineArray[iLine]].v2].x/MAP_SCALE;	// x
1964 						a_fVertex[0][1]=(GLdouble)sectors[s].ceilingheight/MAP_SCALE;						// y
1965 						a_fVertex[0][2]=(GLdouble)vertexes[lines[a_iLineArray[iLine]].v2].y/MAP_SCALE;	// z*/
1966 						a_fVertex[0][0]=-(GLdouble)lines[a_iLineArray[iLine]].v2->x/MAP_SCALE;	// x
1967 						a_fVertex[0][1]=(GLdouble)sectors[s].ceilingheight/MAP_SCALE;						// y
1968 						a_fVertex[0][2]=(GLdouble)lines[a_iLineArray[iLine]].v2->y/MAP_SCALE;	// z
1969 						gluTessVertex(tobj, a_fVertex[0], fn_p_fVertex(a_fVertex[0]/*,fLightLevel*/));
1970 					}
1971 
1972 					//a_iLineArray[iLine]=-1;
1973 					a_iLinePresent[iLine]--;
1974 					if (!a_iLinePresent[iLine])
1975 						iRemainingLines--;
1976 					break;
1977 				}
1978 				if (lines[a_iLineArray[iLine]].v2==vCurrentVertex)
1979 				{
1980 					vCurrentVertex=lines[a_iLineArray[iLine]].v1;
1981 
1982 					if (vCurrentVertex!=vStartVertex)
1983 					{
1984 						/*a_fVertex[0][0]=-(GLdouble)vertexes[lines[a_iLineArray[iLine]].v1].x/MAP_SCALE;	// x
1985 						a_fVertex[0][1]=(GLdouble)sectors[s].ceilingheight/MAP_SCALE;						// y
1986 						a_fVertex[0][2]=(GLdouble)vertexes[lines[a_iLineArray[iLine]].v1].y/MAP_SCALE;	// z*/
1987 						a_fVertex[0][0]=-(GLdouble)lines[a_iLineArray[iLine]].v1->x/MAP_SCALE;	// x
1988 						a_fVertex[0][1]=(GLdouble)sectors[s].ceilingheight/MAP_SCALE;						// y
1989 						a_fVertex[0][2]=(GLdouble)lines[a_iLineArray[iLine]].v1->y/MAP_SCALE;	// z
1990 						gluTessVertex(tobj, a_fVertex[0], fn_p_fVertex(a_fVertex[0]/*,fLightLevel*/));
1991 					}
1992 
1993 					//a_iLineArray[iLine]=-1;
1994 					a_iLinePresent[iLine]--;
1995 					if (!a_iLinePresent[iLine])
1996 						iRemainingLines--;
1997 					break;
1998 				}
1999 			}
2000 		}
2001 		gluTessEndContour(tobj);
2002 		if (bAbortSector)
2003 			break;
2004 	}
2005 	gluTessEndPolygon(tobj);
2006 	(*glEndList_s)();
2007 
2008 	gluDeleteTess(tobj);
2009 }
2010 
2011 void fn_vCreateCeilingPolygons()
2012 {
2013   int s;
2014 
2015 	bFloorCompute=FALSE;
2016 
2017 	startCeilingList = glGenLists(numsectors);
2018 
2019 	for (s=0;s<numsectors;s++)
2020 	{
2021 		iCurrentSector=s;
2022 
2023 		fn_vCreateCeilingPolygonsForSector(s);
2024 	}
2025 }
2026 
2027 #endif	// 0
2028 
2029 #endif	// GL_HERETIC
2030