Annotation of doom/r_plane.c, revision 1.1.1.3

1.1.1.3 ! root        1: // Emacs style mode select   -*- C++ -*- 
        !             2: //-----------------------------------------------------------------------------
        !             3: //
        !             4: // $Id:$
        !             5: //
        !             6: // Copyright (C) 1993-1996 by id Software, Inc.
        !             7: //
        !             8: // This source is available for distribution and/or modification
        !             9: // only under the terms of the DOOM Source Code License as
        !            10: // published by id Software. All rights reserved.
        !            11: //
        !            12: // The source is distributed in the hope that it will be useful,
        !            13: // but WITHOUT ANY WARRANTY; without even the implied warranty of
        !            14: // FITNESS FOR A PARTICULAR PURPOSE. See the DOOM Source Code License
        !            15: // for more details.
        !            16: //
        !            17: // $Log:$
        !            18: //
        !            19: // DESCRIPTION:
        !            20: //     Here is a core component: drawing the floors and ceilings,
        !            21: //      while maintaining a per column clipping list only.
        !            22: //     Moreover, the sky areas have to be determined.
        !            23: //
        !            24: //-----------------------------------------------------------------------------
1.1       root       25: 
                     26: 
1.1.1.3 ! root       27: static const char
        !            28: rcsid[] = "$Id: r_plane.c,v 1.4 1997/02/03 16:47:55 b1 Exp $";
1.1       root       29: 
1.1.1.3 ! root       30: #include <stdlib.h>
1.1       root       31: 
1.1.1.3 ! root       32: #include "i_system.h"
        !            33: #include "z_zone.h"
        !            34: #include "w_wad.h"
1.1       root       35: 
1.1.1.3 ! root       36: #include "doomdef.h"
        !            37: #include "doomstat.h"
1.1       root       38: 
1.1.1.3 ! root       39: #include "r_local.h"
        !            40: #include "r_sky.h"
1.1       root       41: 
1.1.1.2   root       42: 
                     43: 
1.1.1.3 ! root       44: planefunction_t                floorfunc;
        !            45: planefunction_t                ceilingfunc;
1.1.1.2   root       46: 
1.1.1.3 ! root       47: //
        !            48: // opening
        !            49: //
1.1.1.2   root       50: 
1.1.1.3 ! root       51: // Here comes the obnoxious "visplane".
        !            52: #define MAXVISPLANES   128
        !            53: visplane_t             visplanes[MAXVISPLANES];
        !            54: visplane_t*            lastvisplane;
        !            55: visplane_t*            floorplane;
        !            56: visplane_t*            ceilingplane;
1.1.1.2   root       57: 
1.1.1.3 ! root       58: // ?
        !            59: #define MAXOPENINGS    SCREENWIDTH*64
        !            60: short                  openings[MAXOPENINGS];
        !            61: short*                 lastopening;
1.1.1.2   root       62: 
                     63: 
1.1.1.3 ! root       64: //
1.1.1.2   root       65: // Clip values are the solid pixel bounding the range.
1.1.1.3 ! root       66: //  floorclip starts out SCREENHEIGHT
        !            67: //  ceilingclip starts out -1
1.1.1.2   root       68: //
1.1.1.3 ! root       69: short                  floorclip[SCREENWIDTH];
        !            70: short                  ceilingclip[SCREENWIDTH];
        !            71: 
1.1.1.2   root       72: //
1.1.1.3 ! root       73: // spanstart holds the start of a plane span
        !            74: // initialized to 0 at start
1.1.1.2   root       75: //
1.1.1.3 ! root       76: int                    spanstart[SCREENHEIGHT];
        !            77: int                    spanstop[SCREENHEIGHT];
1.1       root       78: 
1.1.1.2   root       79: //
1.1.1.3 ! root       80: // texture mapping
1.1.1.2   root       81: //
1.1.1.3 ! root       82: lighttable_t**         planezlight;
        !            83: fixed_t                        planeheight;
        !            84: 
        !            85: fixed_t                        yslope[SCREENHEIGHT];
        !            86: fixed_t                        distscale[SCREENWIDTH];
        !            87: fixed_t                        basexscale;
        !            88: fixed_t                        baseyscale;
        !            89: 
        !            90: fixed_t                        cachedheight[SCREENHEIGHT];
        !            91: fixed_t                        cacheddistance[SCREENHEIGHT];
        !            92: fixed_t                        cachedxstep[SCREENHEIGHT];
        !            93: fixed_t                        cachedystep[SCREENHEIGHT];
        !            94: 
1.1       root       95: 
                     96: 
1.1.1.2   root       97: //
                     98: // R_InitPlanes
1.1.1.3 ! root       99: // Only at game startup.
1.1.1.2   root      100: //
1.1.1.3 ! root      101: void R_InitPlanes (void)
1.1       root      102: {
1.1.1.3 ! root      103:   // Doh!
1.1       root      104: }
                    105: 
1.1.1.3 ! root      106: 
1.1.1.2   root      107: //
                    108: // R_MapPlane
                    109: //
1.1.1.3 ! root      110: // Uses global vars:
        !           111: //  planeheight
        !           112: //  ds_source
        !           113: //  basexscale
        !           114: //  baseyscale
        !           115: //  viewx
        !           116: //  viewy
        !           117: //
        !           118: // BASIC PRIMITIVE
        !           119: //
        !           120: void
        !           121: R_MapPlane
        !           122: ( int          y,
        !           123:   int          x1,
        !           124:   int          x2 )
1.1       root      125: {
1.1.1.3 ! root      126:     angle_t    angle;
        !           127:     fixed_t    distance;
        !           128:     fixed_t    length;
        !           129:     unsigned   index;
        !           130:        
1.1       root      131: #ifdef RANGECHECK
1.1.1.3 ! root      132:     if (x2 < x1
        !           133:        || x1<0
        !           134:        || x2>=viewwidth
        !           135:        || (unsigned)y>viewheight)
        !           136:     {
        !           137:        I_Error ("R_MapPlane: %i, %i at %i",x1,x2,y);
        !           138:     }
1.1       root      139: #endif
                    140: 
1.1.1.3 ! root      141:     if (planeheight != cachedheight[y])
        !           142:     {
        !           143:        cachedheight[y] = planeheight;
        !           144:        distance = cacheddistance[y] = FixedMul (planeheight, yslope[y]);
        !           145:        ds_xstep = cachedxstep[y] = FixedMul (distance,basexscale);
        !           146:        ds_ystep = cachedystep[y] = FixedMul (distance,baseyscale);
        !           147:     }
        !           148:     else
        !           149:     {
        !           150:        distance = cacheddistance[y];
        !           151:        ds_xstep = cachedxstep[y];
        !           152:        ds_ystep = cachedystep[y];
        !           153:     }
1.1       root      154:        
1.1.1.3 ! root      155:     length = FixedMul (distance,distscale[x1]);
        !           156:     angle = (viewangle + xtoviewangle[x1])>>ANGLETOFINESHIFT;
        !           157:     ds_xfrac = viewx + FixedMul(finecosine[angle], length);
        !           158:     ds_yfrac = -viewy - FixedMul(finesine[angle], length);
        !           159: 
        !           160:     if (fixedcolormap)
        !           161:        ds_colormap = fixedcolormap;
        !           162:     else
        !           163:     {
        !           164:        index = distance >> LIGHTZSHIFT;
        !           165:        
        !           166:        if (index >= MAXLIGHTZ )
        !           167:            index = MAXLIGHTZ-1;
1.1.1.2   root      168: 
1.1.1.3 ! root      169:        ds_colormap = planezlight[index];
        !           170:     }
        !           171:        
        !           172:     ds_y = y;
        !           173:     ds_x1 = x1;
        !           174:     ds_x2 = x2;
1.1       root      175: 
1.1.1.3 ! root      176:     // high or low detail
        !           177:     spanfunc ();       
1.1.1.2   root      178: }
1.1       root      179: 
1.1.1.3 ! root      180: 
1.1.1.2   root      181: //
                    182: // R_ClearPlanes
1.1.1.3 ! root      183: // At begining of frame.
1.1.1.2   root      184: //
1.1.1.3 ! root      185: void R_ClearPlanes (void)
1.1       root      186: {
1.1.1.3 ! root      187:     int                i;
        !           188:     angle_t    angle;
        !           189:     
        !           190:     // opening / clipping determination
        !           191:     for (i=0 ; i<viewwidth ; i++)
        !           192:     {
        !           193:        floorclip[i] = viewheight;
        !           194:        ceilingclip[i] = -1;
        !           195:     }
        !           196: 
        !           197:     lastvisplane = visplanes;
        !           198:     lastopening = openings;
        !           199:     
        !           200:     // texture calculation
        !           201:     memset (cachedheight, 0, sizeof(cachedheight));
        !           202: 
        !           203:     // left to right mapping
        !           204:     angle = (viewangle-ANG90)>>ANGLETOFINESHIFT;
        !           205:        
        !           206:     // scale will be unit scale at SCREENWIDTH/2 distance
        !           207:     basexscale = FixedDiv (finecosine[angle],centerxfrac);
        !           208:     baseyscale = -FixedDiv (finesine[angle],centerxfrac);
        !           209: }
1.1.1.2   root      210: 
1.1       root      211: 
                    212: 
                    213: 
1.1.1.2   root      214: //
                    215: // R_FindPlane
                    216: //
1.1.1.3 ! root      217: visplane_t*
        !           218: R_FindPlane
        !           219: ( fixed_t      height,
        !           220:   int          picnum,
        !           221:   int          lightlevel )
1.1       root      222: {
1.1.1.3 ! root      223:     visplane_t*        check;
        !           224:        
        !           225:     if (picnum == skyflatnum)
        !           226:     {
        !           227:        height = 0;                     // all skys map together
        !           228:        lightlevel = 0;
        !           229:     }
        !           230:        
        !           231:     for (check=visplanes; check<lastvisplane; check++)
        !           232:     {
        !           233:        if (height == check->height
        !           234:            && picnum == check->picnum
        !           235:            && lightlevel == check->lightlevel)
        !           236:        {
        !           237:            break;
        !           238:        }
        !           239:     }
        !           240:     
        !           241:                        
        !           242:     if (check < lastvisplane)
        !           243:        return check;
        !           244:                
        !           245:     if (lastvisplane - visplanes == MAXVISPLANES)
        !           246:        I_Error ("R_FindPlane: no more visplanes");
        !           247:                
        !           248:     lastvisplane++;
        !           249: 
        !           250:     check->height = height;
        !           251:     check->picnum = picnum;
        !           252:     check->lightlevel = lightlevel;
        !           253:     check->minx = SCREENWIDTH;
        !           254:     check->maxx = -1;
        !           255:     
        !           256:     memset (check->top,0xff,sizeof(check->top));
        !           257:                
        !           258:     return check;
1.1       root      259: }
                    260: 
1.1.1.3 ! root      261: 
1.1.1.2   root      262: //
                    263: // R_CheckPlane
                    264: //
1.1.1.3 ! root      265: visplane_t*
        !           266: R_CheckPlane
        !           267: ( visplane_t*  pl,
        !           268:   int          start,
        !           269:   int          stop )
1.1       root      270: {
1.1.1.3 ! root      271:     int                intrl;
        !           272:     int                intrh;
        !           273:     int                unionl;
        !           274:     int                unionh;
        !           275:     int                x;
        !           276:        
        !           277:     if (start < pl->minx)
        !           278:     {
        !           279:        intrl = pl->minx;
        !           280:        unionl = start;
        !           281:     }
        !           282:     else
        !           283:     {
        !           284:        unionl = pl->minx;
        !           285:        intrl = start;
        !           286:     }
        !           287:        
        !           288:     if (stop > pl->maxx)
        !           289:     {
        !           290:        intrh = pl->maxx;
        !           291:        unionh = stop;
        !           292:     }
        !           293:     else
        !           294:     {
        !           295:        unionh = pl->maxx;
        !           296:        intrh = stop;
        !           297:     }
        !           298: 
        !           299:     for (x=intrl ; x<= intrh ; x++)
        !           300:        if (pl->top[x] != 0xff)
        !           301:            break;
        !           302: 
        !           303:     if (x > intrh)
        !           304:     {
        !           305:        pl->minx = unionl;
        !           306:        pl->maxx = unionh;
        !           307: 
        !           308:        // use the same one
        !           309:        return pl;              
        !           310:     }
        !           311:        
        !           312:     // make a new visplane
        !           313:     lastvisplane->height = pl->height;
        !           314:     lastvisplane->picnum = pl->picnum;
        !           315:     lastvisplane->lightlevel = pl->lightlevel;
        !           316:     
        !           317:     pl = lastvisplane++;
        !           318:     pl->minx = start;
        !           319:     pl->maxx = stop;
        !           320: 
        !           321:     memset (pl->top,0xff,sizeof(pl->top));
        !           322:                
        !           323:     return pl;
1.1       root      324: }
                    325: 
1.1.1.3 ! root      326: 
1.1.1.2   root      327: //
                    328: // R_MakeSpans
                    329: //
1.1.1.3 ! root      330: void
        !           331: R_MakeSpans
        !           332: ( int          x,
        !           333:   int          t1,
        !           334:   int          b1,
        !           335:   int          t2,
        !           336:   int          b2 )
1.1       root      337: {
1.1.1.3 ! root      338:     while (t1 < t2 && t1<=b1)
        !           339:     {
        !           340:        R_MapPlane (t1,spanstart[t1],x-1);
        !           341:        t1++;
        !           342:     }
        !           343:     while (b1 > b2 && b1>=t1)
        !           344:     {
        !           345:        R_MapPlane (b1,spanstart[b1],x-1);
        !           346:        b1--;
        !           347:     }
        !           348:        
        !           349:     while (t2 < t1 && t2<=b2)
        !           350:     {
        !           351:        spanstart[t2] = x;
        !           352:        t2++;
        !           353:     }
        !           354:     while (b2 > b1 && b2>=t2)
        !           355:     {
        !           356:        spanstart[b2] = x;
        !           357:        b2--;
        !           358:     }
1.1       root      359: }
                    360: 
1.1.1.3 ! root      361: 
        !           362: 
1.1.1.2   root      363: //
                    364: // R_DrawPlanes
1.1.1.3 ! root      365: // At the end of each frame.
1.1.1.2   root      366: //
1.1.1.3 ! root      367: void R_DrawPlanes (void)
1.1       root      368: {
1.1.1.3 ! root      369:     visplane_t*                pl;
        !           370:     int                        light;
        !           371:     int                        x;
        !           372:     int                        stop;
        !           373:     int                        angle;
        !           374:                                
1.1       root      375: #ifdef RANGECHECK
1.1.1.3 ! root      376:     if (ds_p - drawsegs > MAXDRAWSEGS)
        !           377:        I_Error ("R_DrawPlanes: drawsegs overflow (%i)",
        !           378:                 ds_p - drawsegs);
        !           379:     
        !           380:     if (lastvisplane - visplanes > MAXVISPLANES)
        !           381:        I_Error ("R_DrawPlanes: visplane overflow (%i)",
        !           382:                 lastvisplane - visplanes);
        !           383:     
        !           384:     if (lastopening - openings > MAXOPENINGS)
        !           385:        I_Error ("R_DrawPlanes: opening overflow (%i)",
        !           386:                 lastopening - openings);
1.1       root      387: #endif
                    388: 
1.1.1.3 ! root      389:     for (pl = visplanes ; pl < lastvisplane ; pl++)
        !           390:     {
        !           391:        if (pl->minx > pl->maxx)
        !           392:            continue;
        !           393: 
        !           394:        
        !           395:        // sky flat
        !           396:        if (pl->picnum == skyflatnum)
1.1       root      397:        {
1.1.1.3 ! root      398:            dc_iscale = pspriteiscale>>detailshift;
        !           399:            
        !           400:            // Sky is allways drawn full bright,
        !           401:            //  i.e. colormaps[0] is used.
        !           402:            // Because of this hack, sky is not affected
        !           403:            //  by INVUL inverse mapping.
        !           404:            dc_colormap = colormaps;
        !           405:            dc_texturemid = skytexturemid;
        !           406:            for (x=pl->minx ; x <= pl->maxx ; x++)
        !           407:            {
        !           408:                dc_yl = pl->top[x];
        !           409:                dc_yh = pl->bottom[x];
        !           410: 
        !           411:                if (dc_yl <= dc_yh)
1.1.1.2   root      412:                {
1.1.1.3 ! root      413:                    angle = (viewangle + xtoviewangle[x])>>ANGLETOSKYSHIFT;
        !           414:                    dc_x = x;
        !           415:                    dc_source = R_GetColumn(skytexture, angle);
        !           416:                    colfunc ();
1.1.1.2   root      417:                }
1.1.1.3 ! root      418:            }
        !           419:            continue;
        !           420:        }
        !           421:        
        !           422:        // regular flat
        !           423:        ds_source = W_CacheLumpNum(firstflat +
        !           424:                                   flattranslation[pl->picnum],
        !           425:                                   PU_STATIC);
        !           426:        
        !           427:        planeheight = abs(pl->height-viewz);
        !           428:        light = (pl->lightlevel >> LIGHTSEGSHIFT)+extralight;
1.1       root      429: 
1.1.1.3 ! root      430:        if (light >= LIGHTLEVELS)
        !           431:            light = LIGHTLEVELS-1;
1.1.1.2   root      432: 
1.1.1.3 ! root      433:        if (light < 0)
        !           434:            light = 0;
        !           435: 
        !           436:        planezlight = zlight[light];
        !           437: 
        !           438:        pl->top[pl->maxx+1] = 0xff;
        !           439:        pl->top[pl->minx-1] = 0xff;
        !           440:                
        !           441:        stop = pl->maxx + 1;
        !           442: 
        !           443:        for (x=pl->minx ; x<= stop ; x++)
        !           444:        {
        !           445:            R_MakeSpans(x,pl->top[x-1],
        !           446:                        pl->bottom[x-1],
        !           447:                        pl->top[x],
        !           448:                        pl->bottom[x]);
1.1       root      449:        }
1.1.1.3 ! root      450:        
        !           451:        Z_ChangeTag (ds_source, PU_CACHE);
        !           452:     }
1.1       root      453: }

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.