📄 r_things.c
字号:
// Emacs style mode select -*- C++ -*- //-----------------------------------------------------------------------------//// $Id: r_things.c,v 1.2 2003/09/08 22:34:31 jasonk Exp $//// Copyright (C) 1993-1996 by id Software, Inc.//// This source is available for distribution and/or modification// only under the terms of the DOOM Source Code License as// published by id Software. All rights reserved.//// The source is distributed in the hope that it will be useful,// but WITHOUT ANY WARRANTY; without even the implied warranty of// FITNESS FOR A PARTICULAR PURPOSE. See the DOOM Source Code License// for more details.//// $Log: r_things.c,v $// Revision 1.2 2003/09/08 22:34:31 jasonk// Updated files because this fucker won't build for no fucking good reason.//// Revision 1.1.1.1 2003/09/04 21:08:13 jasonk// Initial import//// Revision 1.1 2000/12/08 21:07:54 jeffw// nxdoom initial entry -- No nxdoom/Makefile so it won't build automatically////// DESCRIPTION:// Refresh of things, i.e. objects represented by sprites.////-----------------------------------------------------------------------------static const charrcsid[] = "$Id: r_things.c,v 1.2 2003/09/08 22:34:31 jasonk Exp $";#include <stdio.h>#include <stdlib.h>#include "doomdef.h"#include "m_swap.h"#include "i_system.h"#include "z_zone.h"#include "w_wad.h"#include "r_local.h"#include "doomstat.h"#define MINZ (FRACUNIT*4)#define BASEYCENTER 100//void R_DrawColumn (void);//void R_DrawFuzzColumn (void);typedef struct{ int x1; int x2; int column; int topclip; int bottomclip;} maskdraw_t;//// Sprite rotation 0 is facing the viewer,// rotation 1 is one angle turn CLOCKWISE around the axis.// This is not the same as the angle,// which increases counter clockwise (protractor).// There was a lot of stuff grabbed wrong, so I changed it...//fixed_t pspritescale;fixed_t pspriteiscale;lighttable_t** spritelights;// constant arrays// used for psprite clipping and initializing clippingshort negonearray[SCREENWIDTH];short screenheightarray[SCREENWIDTH];//// INITIALIZATION FUNCTIONS//// variables used to look up// and range check thing_t sprites patchesspritedef_t* sprites;int numsprites;spriteframe_t sprtemp[29];int maxframe;char* spritename;//// R_InstallSpriteLump// Local function for R_InitSprites.//voidR_InstallSpriteLump( int lump, unsigned frame, unsigned rotation, boolean flipped ){ int r; if (frame >= 29 || rotation > 8) I_Error("R_InstallSpriteLump: " "Bad frame characters in lump %i", lump); if ((int)frame > maxframe) maxframe = frame; if (rotation == 0) { // the lump should be used for all rotations if (sprtemp[frame].rotate == false) I_Error ("R_InitSprites: Sprite %s frame %c has " "multip rot=0 lump", spritename, 'A'+frame); if (sprtemp[frame].rotate == true) I_Error ("R_InitSprites: Sprite %s frame %c has rotations " "and a rot=0 lump", spritename, 'A'+frame); sprtemp[frame].rotate = false; for (r=0 ; r<8 ; r++) { sprtemp[frame].lump[r] = lump - firstspritelump; sprtemp[frame].flip[r] = (byte)flipped; } return; } // the lump is only used for one rotation if (sprtemp[frame].rotate == false) I_Error ("R_InitSprites: Sprite %s frame %c has rotations " "and a rot=0 lump", spritename, 'A'+frame); sprtemp[frame].rotate = true; // make 0 based rotation--; if (sprtemp[frame].lump[rotation] != -1) I_Error ("R_InitSprites: Sprite %s : %c : %c " "has two lumps mapped to it", spritename, 'A'+frame, '1'+rotation); sprtemp[frame].lump[rotation] = lump - firstspritelump; sprtemp[frame].flip[rotation] = (byte)flipped;}//// R_InitSpriteDefs// Pass a null terminated list of sprite names// (4 chars exactly) to be used.// Builds the sprite rotation matrixes to account// for horizontally flipped sprites.// Will report an error if the lumps are inconsistant. // Only called at startup.//// Sprite lump names are 4 characters for the actor,// a letter for the frame, and a number for the rotation.// A sprite that is flippable will have an additional// letter/number appended.// The rotation character can be 0 to signify no rotations.//void R_InitSpriteDefs (char** namelist) { char** check; int i; int l; int intname; int frame; int rotation; int start; int end; int patched; // count the number of sprite names check = namelist; while (*check != NULL) check++; numsprites = check-namelist; if (!numsprites) return; sprites = Z_Malloc(numsprites *sizeof(*sprites), PU_STATIC, NULL); start = firstspritelump-1; end = lastspritelump+1; // scan all the lump names for each of the names, // noting the highest frame letter. // Just compare 4 characters as ints for (i=0 ; i<numsprites ; i++) { spritename = namelist[i]; memset (sprtemp,-1, sizeof(sprtemp)); maxframe = -1; intname = *(int *)namelist[i]; // scan the lumps, // filling in the frames for whatever is found for (l=start+1 ; l<end ; l++) { if (*(int *)lumpinfo[l].name == intname) { frame = lumpinfo[l].name[4] - 'A'; rotation = lumpinfo[l].name[5] - '0'; if (modifiedgame) patched = W_GetNumForName (lumpinfo[l].name); else patched = l; R_InstallSpriteLump (patched, frame, rotation, false); if (lumpinfo[l].name[6]) { frame = lumpinfo[l].name[6] - 'A'; rotation = lumpinfo[l].name[7] - '0'; R_InstallSpriteLump (l, frame, rotation, true); } } } // check the frames that were found for completeness if (maxframe == -1) { sprites[i].numframes = 0; continue; } maxframe++; for (frame = 0 ; frame < maxframe ; frame++) { switch ((int)sprtemp[frame].rotate) { case -1: // no rotations were found for that frame at all I_Error ("R_InitSprites: No patches found " "for %s frame %c", namelist[i], frame+'A'); break; case 0: // only the first rotation is needed break; case 1: // must have all 8 frames for (rotation=0 ; rotation<8 ; rotation++) if (sprtemp[frame].lump[rotation] == -1) I_Error ("R_InitSprites: Sprite %s frame %c " "is missing rotations", namelist[i], frame+'A'); break; } } // allocate space for the frames present and copy sprtemp to it sprites[i].numframes = maxframe; sprites[i].spriteframes = Z_Malloc (maxframe * sizeof(spriteframe_t), PU_STATIC, NULL); memcpy (sprites[i].spriteframes, sprtemp, maxframe*sizeof(spriteframe_t)); }}//// GAME FUNCTIONS//vissprite_t vissprites[MAXVISSPRITES];vissprite_t* vissprite_p;int newvissprite;//// R_InitSprites// Called at program start.//void R_InitSprites (char** namelist){ int i; for (i=0 ; i<SCREENWIDTH ; i++) { negonearray[i] = -1; } R_InitSpriteDefs (namelist);}//// R_ClearSprites// Called at frame start.//void R_ClearSprites (void){ vissprite_p = vissprites;}//// R_NewVisSprite//vissprite_t overflowsprite;vissprite_t* R_NewVisSprite (void){ if (vissprite_p == &vissprites[MAXVISSPRITES]) return &overflowsprite; vissprite_p++; return vissprite_p-1;}//// R_DrawMaskedColumn// Used for sprites and masked mid textures.// Masked means: partly transparent, i.e. stored// in posts/runs of opaque pixels.//short* mfloorclip;short* mceilingclip;fixed_t spryscale;fixed_t sprtopscreen;void R_DrawMaskedColumn (column_t* column){ int topscreen; int bottomscreen; fixed_t basetexturemid; basetexturemid = dc_texturemid; for ( ; column->topdelta != 0xff ; ) { // calculate unclipped screen coordinates // for post topscreen = sprtopscreen + spryscale*column->topdelta; bottomscreen = topscreen + spryscale*column->length; dc_yl = (topscreen+FRACUNIT-1)>>FRACBITS; dc_yh = (bottomscreen-1)>>FRACBITS; if (dc_yh >= mfloorclip[dc_x]) dc_yh = mfloorclip[dc_x]-1; if (dc_yl <= mceilingclip[dc_x]) dc_yl = mceilingclip[dc_x]+1; if (dc_yl <= dc_yh) { dc_source = (byte *)column + 3; dc_texturemid = basetexturemid - (column->topdelta<<FRACBITS); // dc_source = (byte *)column + 3 - column->topdelta; // Drawn by either R_DrawColumn // or (SHADOW) R_DrawFuzzColumn. colfunc (); } column = (column_t *)( (byte *)column + column->length + 4); } dc_texturemid = basetexturemid;}//// R_DrawVisSprite// mfloorclip and mceilingclip should also be set.//voidR_DrawVisSprite( vissprite_t* vis, int x1, int x2 ){ column_t* column; int texturecolumn; fixed_t frac; patch_t* patch; patch = W_CacheLumpNum (vis->patch+firstspritelump, PU_CACHE); dc_colormap = vis->colormap; if (!dc_colormap) { // NULL colormap = shadow draw colfunc = fuzzcolfunc; } else if (vis->mobjflags & MF_TRANSLATION) { colfunc = R_DrawTranslatedColumn; dc_translation = translationtables - 256 + ( (vis->mobjflags & MF_TRANSLATION) >> (MF_TRANSSHIFT-8) ); } dc_iscale = abs(vis->xiscale)>>detailshift; dc_texturemid = vis->texturemid; frac = vis->startfrac; spryscale = vis->scale; sprtopscreen = centeryfrac - FixedMul(dc_texturemid,spryscale); for (dc_x=vis->x1 ; dc_x<=vis->x2 ; dc_x++, frac += vis->xiscale) { texturecolumn = frac>>FRACBITS;#ifdef RANGECHECK if (texturecolumn < 0 || texturecolumn >= SHORT(patch->width)) I_Error ("R_DrawSpriteRange: bad texturecolumn");#endif column = (column_t *) ((byte *)patch + LONG(patch->columnofs[texturecolumn])); R_DrawMaskedColumn (column); } colfunc = basecolfunc;}//// R_ProjectSprite// Generates a vissprite for a thing// if it might be visible.//void R_ProjectSprite (mobj_t* thing){ fixed_t tr_x; fixed_t tr_y; fixed_t gxt; fixed_t gyt; fixed_t tx; fixed_t tz; fixed_t xscale; int x1; int x2; spritedef_t* sprdef; spriteframe_t* sprframe; int lump; unsigned rot; boolean flip; int index; vissprite_t* vis; angle_t ang; fixed_t iscale; // transform the origin point tr_x = thing->x - viewx; tr_y = thing->y - viewy; gxt = FixedMul(tr_x,viewcos); gyt = -FixedMul(tr_y,viewsin); tz = gxt-gyt; // thing is behind view plane?
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -