aboutsummaryrefslogtreecommitdiff
path: root/src/r_data.c
diff options
context:
space:
mode:
Diffstat (limited to 'src/r_data.c')
-rw-r--r--src/r_data.c745
1 files changed, 745 insertions, 0 deletions
diff --git a/src/r_data.c b/src/r_data.c
new file mode 100644
index 0000000..bf2c6c7
--- /dev/null
+++ b/src/r_data.c
@@ -0,0 +1,745 @@
1/* Emacs style mode select -*- C++ -*-
2 *-----------------------------------------------------------------------------
3 *
4 *
5 * PrBoom: a Doom port merged with LxDoom and LSDLDoom
6 * based on BOOM, a modified and improved DOOM engine
7 * Copyright (C) 1999 by
8 * id Software, Chi Hoang, Lee Killough, Jim Flynn, Rand Phares, Ty Halderman
9 * Copyright (C) 1999-2002 by
10 * Jess Haas, Nicolas Kalkhof, Colin Phipps, Florian Schulze
11 * Copyright 2005, 2006 by
12 * Florian Schulze, Colin Phipps, Neil Stevens, Andrey Budko
13 *
14 * This program is free software; you can redistribute it and/or
15 * modify it under the terms of the GNU General Public License
16 * as published by the Free Software Foundation; either version 2
17 * of the License, or (at your option) any later version.
18 *
19 * This program is distributed in the hope that it will be useful,
20 * but WITHOUT ANY WARRANTY; without even the implied warranty of
21 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
22 * GNU General Public License for more details.
23 *
24 * You should have received a copy of the GNU General Public License
25 * along with this program; if not, write to the Free Software
26 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA
27 * 02111-1307, USA.
28 *
29 * DESCRIPTION:
30 * Preparation of data for rendering,
31 * generation of lookups, caching, retrieval by name.
32 *
33 *-----------------------------------------------------------------------------*/
34
35#include "doomstat.h"
36#include "w_wad.h"
37#include "r_draw.h"
38#include "r_main.h"
39#include "r_sky.h"
40#include "i_system.h"
41#include "r_bsp.h"
42#include "r_things.h"
43#include "p_tick.h"
44#include "lprintf.h" // jff 08/03/98 - declaration of lprintf
45#include "p_tick.h"
46
47//
48// Graphics.
49// DOOM graphics for walls and sprites
50// is stored in vertical runs of opaque pixels (posts).
51// A column is composed of zero or more posts,
52// a patch or sprite is composed of zero or more columns.
53//
54
55//
56// Texture definition.
57// Each texture is composed of one or more patches,
58// with patches being lumps stored in the WAD.
59// The lumps are referenced by number, and patched
60// into the rectangular texture space using origin
61// and possibly other attributes.
62//
63
64typedef struct
65{
66 short originx;
67 short originy;
68 short patch;
69 short stepdir; // unused in Doom but might be used in Phase 2 Boom
70 short colormap; // unused in Doom but might be used in Phase 2 Boom
71} PACKEDATTR mappatch_t;
72
73
74typedef struct
75{
76 char name[8];
77 char pad2[4]; // unused
78 short width;
79 short height;
80 char pad[4]; // unused in Doom but might be used in Boom Phase 2
81 short patchcount;
82 mappatch_t patches[1];
83} PACKEDATTR maptexture_t;
84
85// A maptexturedef_t describes a rectangular texture, which is composed
86// of one or more mappatch_t structures that arrange graphic patches.
87
88// killough 4/17/98: make firstcolormaplump,lastcolormaplump external
89int firstcolormaplump, lastcolormaplump; // killough 4/17/98
90
91int firstflat, lastflat, numflats;
92int firstspritelump, lastspritelump, numspritelumps;
93int numtextures;
94texture_t **textures; // proff - 04/05/2000 removed static for OpenGL
95fixed_t *textureheight; //needed for texture pegging (and TFE fix - killough)
96int *flattranslation; // for global animation
97int *texturetranslation;
98
99//
100// R_GetTextureColumn
101//
102
103const byte *R_GetTextureColumn(const rpatch_t *texpatch, int col) {
104 while (col < 0)
105 col += texpatch->width;
106 col &= texpatch->widthmask;
107
108 return texpatch->columns[col].pixels;
109}
110
111//
112// R_InitTextures
113// Initializes the texture list
114// with the textures from the world map.
115//
116
117static void R_InitTextures (void)
118{
119 const maptexture_t *mtexture;
120 texture_t *texture;
121 const mappatch_t *mpatch;
122 texpatch_t *patch;
123 int i, j;
124 int maptex_lump[2] = {-1, -1};
125 const int *maptex;
126 const int *maptex1, *maptex2;
127 char name[9];
128 int names_lump; // cph - new wad lump handling
129 const char *names; // cph -
130 const char *name_p;// const*'s
131 int *patchlookup;
132 int totalwidth;
133 int nummappatches;
134 int offset;
135 int maxoff, maxoff2;
136 int numtextures1, numtextures2;
137 const int *directory;
138 int errors = 0;
139
140 // Load the patch names from pnames.lmp.
141 name[8] = 0;
142 names = W_CacheLumpNum(names_lump = W_GetNumForName("PNAMES"));
143 nummappatches = LONG(*((const int *)names));
144 name_p = names+4;
145 patchlookup = malloc(nummappatches*sizeof(*patchlookup)); // killough
146
147 for (i=0 ; i<nummappatches ; i++)
148 {
149 strncpy (name,name_p+i*8, 8);
150 patchlookup[i] = W_CheckNumForName(name);
151 if (patchlookup[i] == -1)
152 {
153 // killough 4/17/98:
154 // Some wads use sprites as wall patches, so repeat check and
155 // look for sprites this time, but only if there were no wall
156 // patches found. This is the same as allowing for both, except
157 // that wall patches always win over sprites, even when they
158 // appear first in a wad. This is a kludgy solution to the wad
159 // lump namespace problem.
160
161 patchlookup[i] = (W_CheckNumForName)(name, ns_sprites);
162
163 if (patchlookup[i] == -1 && devparm)
164 //jff 8/3/98 use logical output routine
165 lprintf(LO_WARN,"\nWarning: patch %.8s, index %d does not exist",name,i);
166 }
167 }
168 W_UnlockLumpNum(names_lump); // cph - release the lump
169
170 // Load the map texture definitions from textures.lmp.
171 // The data is contained in one or two lumps,
172 // TEXTURE1 for shareware, plus TEXTURE2 for commercial.
173
174 maptex = maptex1 = W_CacheLumpNum(maptex_lump[0] = W_GetNumForName("TEXTURE1"));
175 numtextures1 = LONG(*maptex);
176 maxoff = W_LumpLength(maptex_lump[0]);
177 directory = maptex+1;
178
179 if (W_CheckNumForName("TEXTURE2") != -1)
180 {
181 maptex2 = W_CacheLumpNum(maptex_lump[1] = W_GetNumForName("TEXTURE2"));
182 numtextures2 = LONG(*maptex2);
183 maxoff2 = W_LumpLength(maptex_lump[1]);
184 }
185 else
186 {
187 maptex2 = NULL;
188 numtextures2 = 0;
189 maxoff2 = 0;
190 }
191 numtextures = numtextures1 + numtextures2;
192
193 // killough 4/9/98: make column offsets 32-bit;
194 // clean up malloc-ing to use sizeof
195
196 textures = Z_Malloc(numtextures*sizeof*textures, PU_STATIC, 0);
197 textureheight = Z_Malloc(numtextures*sizeof*textureheight, PU_STATIC, 0);
198
199 totalwidth = 0;
200
201 for (i=0 ; i<numtextures ; i++, directory++)
202 {
203 if (i == numtextures1)
204 {
205 // Start looking in second texture file.
206 maptex = maptex2;
207 maxoff = maxoff2;
208 directory = maptex+1;
209 }
210
211 offset = LONG(*directory);
212
213 if (offset > maxoff)
214 I_Error("R_InitTextures: Bad texture directory");
215
216 mtexture = (const maptexture_t *) ( (const byte *)maptex + offset);
217
218 texture = textures[i] =
219 Z_Malloc(sizeof(texture_t) +
220 sizeof(texpatch_t)*(SHORT(mtexture->patchcount)-1),
221 PU_STATIC, 0);
222
223 texture->width = SHORT(mtexture->width);
224 texture->height = SHORT(mtexture->height);
225 texture->patchcount = SHORT(mtexture->patchcount);
226
227 /* Mattias Engdegård emailed me of the following explenation of
228 * why memcpy doesnt work on some systems:
229 * "I suppose it is the mad unaligned allocation
230 * going on (and which gcc in some way manages to cope with
231 * through the __attribute__ ((packed))), and which it forgets
232 * when optimizing memcpy (to a single word move) since it appears
233 * to be aligned. Technically a gcc bug, but I can't blame it when
234 * it's stressed with that amount of
235 * non-standard nonsense."
236 * So in short the unaligned struct confuses gcc's optimizer so
237 * i took the memcpy out alltogether to avoid future problems-Jess
238 */
239 /* The above was #ifndef SPARC, but i got a mail from
240 * Putera Joseph F NPRI <PuteraJF@Npt.NUWC.Navy.Mil> containing:
241 * I had to use the memcpy function on a sparc machine. The
242 * other one would give me a core dump.
243 * cph - I find it hard to believe that sparc memcpy is broken,
244 * but I don't believe the pointers to memcpy have to be aligned
245 * either. Use fast memcpy on other machines anyway.
246 */
247/*
248 proff - I took this out, because Oli Kraus (olikraus@yahoo.com) told
249 me the memcpy produced a buserror. Since this function isn't time-
250 critical I'm using the for loop now.
251*/
252/*
253#ifndef GCC
254 memcpy(texture->name, mtexture->name, sizeof(texture->name));
255#else
256*/
257 {
258 int j;
259 for(j=0;j<sizeof(texture->name);j++)
260 texture->name[j]=mtexture->name[j];
261 }
262/* #endif */
263
264 mpatch = mtexture->patches;
265 patch = texture->patches;
266
267 for (j=0 ; j<texture->patchcount ; j++, mpatch++, patch++)
268 {
269 patch->originx = SHORT(mpatch->originx);
270 patch->originy = SHORT(mpatch->originy);
271 patch->patch = patchlookup[SHORT(mpatch->patch)];
272 if (patch->patch == -1)
273 {
274 //jff 8/3/98 use logical output routine
275 lprintf(LO_ERROR,"\nR_InitTextures: Missing patch %d in texture %.8s",
276 SHORT(mpatch->patch), texture->name); // killough 4/17/98
277 ++errors;
278 }
279 }
280
281 for (j=1; j*2 <= texture->width; j<<=1)
282 ;
283 texture->widthmask = j-1;
284 textureheight[i] = texture->height<<FRACBITS;
285
286 totalwidth += texture->width;
287 }
288
289 free(patchlookup); // killough
290
291 for (i=0; i<2; i++) // cph - release the TEXTUREx lumps
292 if (maptex_lump[i] != -1)
293 W_UnlockLumpNum(maptex_lump[i]);
294
295 if (errors)
296 I_Error("R_InitTextures: %d errors", errors);
297
298 // Precalculate whatever possible.
299 if (devparm) // cph - If in development mode, generate now so all errors are found at once
300 for (i=0 ; i<numtextures ; i++)
301 {
302 // proff - This is for the new renderer now
303 R_CacheTextureCompositePatchNum(i);
304 R_UnlockTextureCompositePatchNum(i);
305 }
306
307 if (errors)
308 I_Error("R_InitTextures: %d errors", errors);
309
310 // Create translation table for global animation.
311 // killough 4/9/98: make column offsets 32-bit;
312 // clean up malloc-ing to use sizeof
313
314 texturetranslation =
315 Z_Malloc((numtextures+1)*sizeof*texturetranslation, PU_STATIC, 0);
316
317 for (i=0 ; i<numtextures ; i++)
318 texturetranslation[i] = i;
319
320 // killough 1/31/98: Initialize texture hash table
321 for (i = 0; i<numtextures; i++)
322 textures[i]->index = -1;
323 while (--i >= 0)
324 {
325 int j = W_LumpNameHash(textures[i]->name) % (unsigned) numtextures;
326 textures[i]->next = textures[j]->index; // Prepend to chain
327 textures[j]->index = i;
328 }
329}
330
331//
332// R_InitFlats
333//
334static void R_InitFlats(void)
335{
336 int i;
337
338 firstflat = W_GetNumForName("F_START") + 1;
339 lastflat = W_GetNumForName("F_END") - 1;
340 numflats = lastflat - firstflat + 1;
341
342 // Create translation table for global animation.
343 // killough 4/9/98: make column offsets 32-bit;
344 // clean up malloc-ing to use sizeof
345
346 flattranslation =
347 Z_Malloc((numflats+1)*sizeof(*flattranslation), PU_STATIC, 0);
348
349 for (i=0 ; i<numflats ; i++)
350 flattranslation[i] = i;
351}
352
353//
354// R_InitSpriteLumps
355// Finds the width and hoffset of all sprites in the wad,
356// so the sprite does not need to be cached completely
357// just for having the header info ready during rendering.
358//
359static void R_InitSpriteLumps(void)
360{
361 firstspritelump = W_GetNumForName("S_START") + 1;
362 lastspritelump = W_GetNumForName("S_END") - 1;
363 numspritelumps = lastspritelump - firstspritelump + 1;
364}
365
366//
367// R_InitColormaps
368//
369// killough 3/20/98: rewritten to allow dynamic colormaps
370// and to remove unnecessary 256-byte alignment
371//
372// killough 4/4/98: Add support for C_START/C_END markers
373//
374
375static void R_InitColormaps(void)
376{
377 int i;
378 firstcolormaplump = W_GetNumForName("C_START");
379 lastcolormaplump = W_GetNumForName("C_END");
380 numcolormaps = lastcolormaplump - firstcolormaplump;
381 colormaps = Z_Malloc(sizeof(*colormaps) * numcolormaps, PU_STATIC, 0);
382 colormaps[0] = (const lighttable_t *)W_CacheLumpName("COLORMAP");
383 for (i=1; i<numcolormaps; i++)
384 colormaps[i] = (const lighttable_t *)W_CacheLumpNum(i+firstcolormaplump);
385 // cph - always lock
386}
387
388// killough 4/4/98: get colormap number from name
389// killough 4/11/98: changed to return -1 for illegal names
390// killough 4/17/98: changed to use ns_colormaps tag
391
392int R_ColormapNumForName(const char *name)
393{
394 register int i = 0;
395 if (strncasecmp(name,"COLORMAP",8)) // COLORMAP predefined to return 0
396 if ((i = (W_CheckNumForName)(name, ns_colormaps)) != -1)
397 i -= firstcolormaplump;
398 return i;
399}
400
401/*
402 * R_ColourMap
403 *
404 * cph 2001/11/17 - unify colour maping logic in a single place;
405 * obsoletes old c_scalelight stuff
406 */
407
408static inline int between(int l,int u,int x)
409{ return (l > x ? l : x > u ? u : x); }
410
411const lighttable_t* R_ColourMap(int lightlevel, fixed_t spryscale)
412{
413 if (fixedcolormap) return fixedcolormap;
414 else {
415 if (curline)
416 if (curline->v1->y == curline->v2->y)
417 lightlevel -= 1 << LIGHTSEGSHIFT;
418 else
419 if (curline->v1->x == curline->v2->x)
420 lightlevel += 1 << LIGHTSEGSHIFT;
421
422 lightlevel += extralight << LIGHTSEGSHIFT;
423
424 /* cph 2001/11/17 -
425 * Work out what colour map to use, remembering to clamp it to the number of
426 * colour maps we actually have. This formula is basically the one from the
427 * original source, just brought into one place. The main difference is it
428 * throws away less precision in the lightlevel half, so it supports 32
429 * light levels in WADs compared to Doom's 16.
430 *
431 * Note we can make it more accurate if we want - we should keep all the
432 * precision until the final step, so slight scale differences can count
433 * against slight light level variations.
434 */
435 return fullcolormap + between(0,NUMCOLORMAPS-1,
436 ((256-lightlevel)*2*NUMCOLORMAPS/256) - 4
437 - (FixedMul(spryscale,pspriteiscale)/2 >> LIGHTSCALESHIFT)
438 )*256;
439 }
440}
441
442//
443// R_InitTranMap
444//
445// Initialize translucency filter map
446//
447// By Lee Killough 2/21/98
448//
449
450int tran_filter_pct = 66; // filter percent
451
452#define TSC 12 /* number of fixed point digits in filter percent */
453
454void R_InitTranMap(int progress)
455{
456 int lump = W_CheckNumForName("TRANMAP");
457
458 // If a tranlucency filter map lump is present, use it
459
460 if (lump != -1) // Set a pointer to the translucency filter maps.
461 main_tranmap = W_CacheLumpNum(lump); // killough 4/11/98
462 else if (W_CheckNumForName("PLAYPAL")!=-1) // can be called before WAD loaded
463 { // Compose a default transparent filter map based on PLAYPAL.
464 const byte *playpal = W_CacheLumpName("PLAYPAL");
465 byte *my_tranmap;
466
467 char fname[PATH_MAX+1];
468 struct {
469 unsigned char pct;
470 unsigned char playpal[256];
471 } cache;
472 FILE *cachefp = fopen(strcat(strcpy(fname, I_DoomExeDir()), "/tranmap.dat"),"rb");
473
474 main_tranmap = my_tranmap = Z_Malloc(256*256, PU_STATIC, 0); // killough 4/11/98
475
476 // Use cached translucency filter if it's available
477
478 if (!cachefp ||
479 fread(&cache, 1, sizeof cache, cachefp) != sizeof cache ||
480 cache.pct != tran_filter_pct ||
481 memcmp(cache.playpal, playpal, sizeof cache.playpal) ||
482 fread(my_tranmap, 256, 256, cachefp) != 256 ) // killough 4/11/98
483 {
484 long pal[3][256], tot[256], pal_w1[3][256];
485 long w1 = ((unsigned long) tran_filter_pct<<TSC)/100;
486 long w2 = (1l<<TSC)-w1;
487
488 if (progress)
489 lprintf(LO_INFO, "Tranmap build [ ]\x08\x08\x08\x08\x08\x08\x08\x08\x08");
490
491 // First, convert playpal into long int type, and transpose array,
492 // for fast inner-loop calculations. Precompute tot array.
493
494 {
495 register int i = 255;
496 register const unsigned char *p = playpal+255*3;
497 do
498 {
499 register long t,d;
500 pal_w1[0][i] = (pal[0][i] = t = p[0]) * w1;
501 d = t*t;
502 pal_w1[1][i] = (pal[1][i] = t = p[1]) * w1;
503 d += t*t;
504 pal_w1[2][i] = (pal[2][i] = t = p[2]) * w1;
505 d += t*t;
506 p -= 3;
507 tot[i] = d << (TSC-1);
508 }
509 while (--i>=0);
510 }
511
512 // Next, compute all entries using minimum arithmetic.
513
514 {
515 int i,j;
516 byte *tp = my_tranmap;
517 for (i=0;i<256;i++)
518 {
519 long r1 = pal[0][i] * w2;
520 long g1 = pal[1][i] * w2;
521 long b1 = pal[2][i] * w2;
522 if (!(i & 31) && progress)
523 //jff 8/3/98 use logical output routine
524 lprintf(LO_INFO,".");
525 for (j=0;j<256;j++,tp++)
526 {
527 register int color = 255;
528 register long err;
529 long r = pal_w1[0][j] + r1;
530 long g = pal_w1[1][j] + g1;
531 long b = pal_w1[2][j] + b1;
532 long best = LONG_MAX;
533 do
534 if ((err = tot[color] - pal[0][color]*r
535 - pal[1][color]*g - pal[2][color]*b) < best)
536 best = err, *tp = color;
537 while (--color >= 0);
538 }
539 }
540 }
541 if ((cachefp = fopen(fname,"wb")) != NULL) // write out the cached translucency map
542 {
543 cache.pct = tran_filter_pct;
544 memcpy(cache.playpal, playpal, 256);
545 fseek(cachefp, 0, SEEK_SET);
546 fwrite(&cache, 1, sizeof cache, cachefp);
547 fwrite(main_tranmap, 256, 256, cachefp);
548 // CPhipps - leave close for a few lines...
549 }
550 }
551
552 if (cachefp) // killough 11/98: fix filehandle leak
553 fclose(cachefp);
554
555 W_UnlockLumpName("PLAYPAL");
556 }
557}
558
559//
560// R_InitData
561// Locates all the lumps
562// that will be used by all views
563// Must be called after W_Init.
564//
565
566void R_InitData(void)
567{
568 lprintf(LO_INFO, "Textures ");
569 R_InitTextures();
570 lprintf(LO_INFO, "Flats ");
571 R_InitFlats();
572 lprintf(LO_INFO, "Sprites ");
573 R_InitSpriteLumps();
574 if (default_translucency) // killough 3/1/98
575 R_InitTranMap(1); // killough 2/21/98, 3/6/98
576 R_InitColormaps(); // killough 3/20/98
577}
578
579//
580// R_FlatNumForName
581// Retrieval, get a flat number for a flat name.
582//
583// killough 4/17/98: changed to use ns_flats namespace
584//
585
586int R_FlatNumForName(const char *name) // killough -- const added
587{
588 int i = (W_CheckNumForName)(name, ns_flats);
589 if (i == -1)
590 I_Error("R_FlatNumForName: %.8s not found", name);
591 return i - firstflat;
592}
593
594//
595// R_CheckTextureNumForName
596// Check whether texture is available.
597// Filter out NoTexture indicator.
598//
599// Rewritten by Lee Killough to use hash table for fast lookup. Considerably
600// reduces the time needed to start new levels. See w_wad.c for comments on
601// the hashing algorithm, which is also used for lump searches.
602//
603// killough 1/21/98, 1/31/98
604//
605
606int PUREFUNC R_CheckTextureNumForName(const char *name)
607{
608 int i = NO_TEXTURE;
609 if (*name != '-') // "NoTexture" marker.
610 {
611 i = textures[W_LumpNameHash(name) % (unsigned) numtextures]->index;
612 while (i >= 0 && strncasecmp(textures[i]->name,name,8))
613 i = textures[i]->next;
614 }
615 return i;
616}
617
618//
619// R_TextureNumForName
620// Calls R_CheckTextureNumForName,
621// aborts with error message.
622//
623
624int PUREFUNC R_TextureNumForName(const char *name) // const added -- killough
625{
626 int i = R_CheckTextureNumForName(name);
627 if (i == -1)
628 I_Error("R_TextureNumForName: %.8s not found", name);
629 return i;
630}
631
632//
633// R_SafeTextureNumForName
634// Calls R_CheckTextureNumForName, and changes any error to NO_TEXTURE
635int PUREFUNC R_SafeTextureNumForName(const char *name, int snum)
636{
637 int i = R_CheckTextureNumForName(name);
638 if (i == -1) {
639 i = NO_TEXTURE; // e6y - return "no texture"
640 lprintf(LO_DEBUG,"bad texture '%s' in sidedef %d\n",name,snum);
641 }
642 return i;
643}
644
645//
646// R_PrecacheLevel
647// Preloads all relevant graphics for the level.
648//
649// Totally rewritten by Lee Killough to use less memory,
650// to avoid using alloca(), and to improve performance.
651// cph - new wad lump handling, calls cache functions but acquires no locks
652
653static inline void precache_lump(int l)
654{
655 W_CacheLumpNum(l); W_UnlockLumpNum(l);
656}
657
658void R_PrecacheLevel(void)
659{
660 register int i;
661 register byte *hitlist;
662
663 if (demoplayback)
664 return;
665
666 {
667 size_t size = numflats > numsprites ? numflats : numsprites;
668 hitlist = malloc((size_t)numtextures > size ? numtextures : size);
669 }
670
671 // Precache flats.
672
673 memset(hitlist, 0, numflats);
674
675 for (i = numsectors; --i >= 0; )
676 hitlist[sectors[i].floorpic] = hitlist[sectors[i].ceilingpic] = 1;
677
678 for (i = numflats; --i >= 0; )
679 if (hitlist[i])
680 precache_lump(firstflat + i);
681
682 // Precache textures.
683
684 memset(hitlist, 0, numtextures);
685
686 for (i = numsides; --i >= 0;)
687 hitlist[sides[i].bottomtexture] =
688 hitlist[sides[i].toptexture] =
689 hitlist[sides[i].midtexture] = 1;
690
691 // Sky texture is always present.
692 // Note that F_SKY1 is the name used to
693 // indicate a sky floor/ceiling as a flat,
694 // while the sky texture is stored like
695 // a wall texture, with an episode dependend
696 // name.
697
698 hitlist[skytexture] = 1;
699
700 for (i = numtextures; --i >= 0; )
701 if (hitlist[i])
702 {
703 texture_t *texture = textures[i];
704 int j = texture->patchcount;
705 while (--j >= 0)
706 precache_lump(texture->patches[j].patch);
707 }
708
709 // Precache sprites.
710 memset(hitlist, 0, numsprites);
711
712 {
713 thinker_t *th = NULL;
714 while ((th = P_NextThinker(th,th_all)) != NULL)
715 if (th->function == P_MobjThinker)
716 hitlist[((mobj_t *)th)->sprite] = 1;
717 }
718
719 for (i=numsprites; --i >= 0;)
720 if (hitlist[i])
721 {
722 int j = sprites[i].numframes;
723 while (--j >= 0)
724 {
725 short *sflump = sprites[i].spriteframes[j].lump;
726 int k = 7;
727 do
728 precache_lump(firstspritelump + sflump[k]);
729 while (--k >= 0);
730 }
731 }
732 free(hitlist);
733}
734
735// Proff - Added for OpenGL
736void R_SetPatchNum(patchnum_t *patchnum, const char *name)
737{
738 const rpatch_t *patch = R_CachePatchName(name);
739 patchnum->width = patch->width;
740 patchnum->height = patch->height;
741 patchnum->leftoffset = patch->leftoffset;
742 patchnum->topoffset = patch->topoffset;
743 patchnum->lumpnum = W_GetNumForName(name);
744 R_UnlockPatchName(name);
745}