gl_model.c 41 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135113611371138113911401141114211431144114511461147114811491150115111521153115411551156115711581159116011611162116311641165116611671168116911701171117211731174117511761177117811791180118111821183118411851186118711881189119011911192119311941195119611971198119912001201120212031204120512061207120812091210121112121213121412151216121712181219122012211222122312241225122612271228122912301231123212331234123512361237123812391240124112421243124412451246124712481249125012511252125312541255125612571258125912601261126212631264126512661267126812691270127112721273127412751276127712781279128012811282128312841285128612871288128912901291129212931294129512961297129812991300130113021303130413051306130713081309131013111312131313141315131613171318131913201321132213231324132513261327132813291330133113321333133413351336133713381339134013411342134313441345134613471348134913501351135213531354135513561357135813591360136113621363136413651366136713681369137013711372137313741375137613771378137913801381138213831384138513861387138813891390139113921393139413951396139713981399140014011402140314041405140614071408140914101411141214131414141514161417141814191420142114221423142414251426142714281429143014311432143314341435143614371438143914401441144214431444144514461447144814491450145114521453145414551456145714581459146014611462146314641465146614671468146914701471147214731474147514761477147814791480148114821483148414851486148714881489149014911492149314941495149614971498149915001501150215031504150515061507150815091510151115121513151415151516151715181519152015211522152315241525152615271528152915301531153215331534153515361537153815391540154115421543154415451546154715481549155015511552155315541555155615571558155915601561156215631564156515661567156815691570157115721573157415751576157715781579158015811582158315841585158615871588158915901591159215931594159515961597159815991600160116021603160416051606160716081609161016111612161316141615161616171618161916201621162216231624162516261627162816291630163116321633163416351636163716381639164016411642164316441645164616471648164916501651165216531654165516561657165816591660166116621663166416651666166716681669167016711672167316741675167616771678167916801681168216831684168516861687168816891690169116921693169416951696169716981699170017011702170317041705170617071708170917101711171217131714171517161717171817191720172117221723172417251726172717281729173017311732173317341735173617371738173917401741174217431744174517461747174817491750175117521753175417551756175717581759176017611762176317641765176617671768176917701771177217731774177517761777177817791780178117821783178417851786178717881789179017911792179317941795179617971798179918001801180218031804180518061807180818091810181118121813181418151816181718181819182018211822182318241825182618271828182918301831183218331834183518361837183818391840184118421843184418451846184718481849185018511852185318541855185618571858185918601861186218631864186518661867186818691870187118721873187418751876187718781879188018811882188318841885
  1. /*
  2. Copyright (C) 1996-1997 Id Software, Inc.
  3. This program is free software; you can redistribute it and/or
  4. modify it under the terms of the GNU General Public License
  5. as published by the Free Software Foundation; either version 2
  6. of the License, or (at your option) any later version.
  7. This program is distributed in the hope that it will be useful,
  8. but WITHOUT ANY WARRANTY; without even the implied warranty of
  9. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
  10. See the GNU General Public License for more details.
  11. You should have received a copy of the GNU General Public License
  12. along with this program; if not, write to the Free Software
  13. Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
  14. */
  15. // models.c -- model loading and caching
  16. // models are the only shared resource between a client and server running
  17. // on the same machine.
  18. #include "quakedef.h"
  19. model_t *loadmodel;
  20. char loadname[32]; // for hunk tags
  21. void Mod_LoadSpriteModel (model_t *mod, void *buffer);
  22. void Mod_LoadBrushModel (model_t *mod, void *buffer);
  23. void Mod_LoadAliasModel (model_t *mod, void *buffer);
  24. model_t *Mod_LoadModel (model_t *mod, qboolean crash);
  25. byte mod_novis[MAX_MAP_LEAFS/8];
  26. #define MAX_MOD_KNOWN 512
  27. model_t mod_known[MAX_MOD_KNOWN];
  28. int mod_numknown;
  29. cvar_t gl_subdivide_size = {"gl_subdivide_size", "128", true};
  30. /*
  31. ===============
  32. Mod_Init
  33. ===============
  34. */
  35. void Mod_Init (void)
  36. {
  37. Cvar_RegisterVariable (&gl_subdivide_size);
  38. memset (mod_novis, 0xff, sizeof(mod_novis));
  39. }
  40. /*
  41. ===============
  42. Mod_Init
  43. Caches the data if needed
  44. ===============
  45. */
  46. void *Mod_Extradata (model_t *mod)
  47. {
  48. void *r;
  49. r = Cache_Check (&mod->cache);
  50. if (r)
  51. return r;
  52. Mod_LoadModel (mod, true);
  53. if (!mod->cache.data)
  54. Sys_Error ("Mod_Extradata: caching failed");
  55. return mod->cache.data;
  56. }
  57. /*
  58. ===============
  59. Mod_PointInLeaf
  60. ===============
  61. */
  62. mleaf_t *Mod_PointInLeaf (vec3_t p, model_t *model)
  63. {
  64. mnode_t *node;
  65. float d;
  66. mplane_t *plane;
  67. if (!model || !model->nodes)
  68. Sys_Error ("Mod_PointInLeaf: bad model");
  69. node = model->nodes;
  70. while (1)
  71. {
  72. if (node->contents < 0)
  73. return (mleaf_t *)node;
  74. plane = node->plane;
  75. d = DotProduct (p,plane->normal) - plane->dist;
  76. if (d > 0)
  77. node = node->children[0];
  78. else
  79. node = node->children[1];
  80. }
  81. return NULL; // never reached
  82. }
  83. /*
  84. ===================
  85. Mod_DecompressVis
  86. ===================
  87. */
  88. byte *Mod_DecompressVis (byte *in, model_t *model)
  89. {
  90. static byte decompressed[MAX_MAP_LEAFS/8];
  91. int c;
  92. byte *out;
  93. int row;
  94. row = (model->numleafs+7)>>3;
  95. out = decompressed;
  96. #if 0
  97. memcpy (out, in, row);
  98. #else
  99. if (!in)
  100. { // no vis info, so make all visible
  101. while (row)
  102. {
  103. *out++ = 0xff;
  104. row--;
  105. }
  106. return decompressed;
  107. }
  108. do
  109. {
  110. if (*in)
  111. {
  112. *out++ = *in++;
  113. continue;
  114. }
  115. c = in[1];
  116. in += 2;
  117. while (c)
  118. {
  119. *out++ = 0;
  120. c--;
  121. }
  122. } while (out - decompressed < row);
  123. #endif
  124. return decompressed;
  125. }
  126. byte *Mod_LeafPVS (mleaf_t *leaf, model_t *model)
  127. {
  128. if (leaf == model->leafs)
  129. return mod_novis;
  130. return Mod_DecompressVis (leaf->compressed_vis, model);
  131. }
  132. /*
  133. ===================
  134. Mod_ClearAll
  135. ===================
  136. */
  137. void Mod_ClearAll (void)
  138. {
  139. int i;
  140. model_t *mod;
  141. for (i=0 , mod=mod_known ; i<mod_numknown ; i++, mod++)
  142. if (mod->type != mod_alias)
  143. mod->needload = true;
  144. }
  145. /*
  146. ==================
  147. Mod_FindName
  148. ==================
  149. */
  150. model_t *Mod_FindName (char *name)
  151. {
  152. int i;
  153. model_t *mod;
  154. if (!name[0])
  155. Sys_Error ("Mod_ForName: NULL name");
  156. //
  157. // search the currently loaded models
  158. //
  159. for (i=0 , mod=mod_known ; i<mod_numknown ; i++, mod++)
  160. if (!strcmp (mod->name, name) )
  161. break;
  162. if (i == mod_numknown)
  163. {
  164. if (mod_numknown == MAX_MOD_KNOWN)
  165. Sys_Error ("mod_numknown == MAX_MOD_KNOWN");
  166. strcpy (mod->name, name);
  167. mod->needload = true;
  168. mod_numknown++;
  169. }
  170. return mod;
  171. }
  172. /*
  173. ==================
  174. Mod_TouchModel
  175. ==================
  176. */
  177. void Mod_TouchModel (char *name)
  178. {
  179. model_t *mod;
  180. mod = Mod_FindName (name);
  181. if (!mod->needload)
  182. {
  183. if (mod->type == mod_alias)
  184. Cache_Check (&mod->cache);
  185. }
  186. }
  187. /*
  188. ==================
  189. Mod_LoadModel
  190. Loads a model into the cache
  191. ==================
  192. */
  193. model_t *Mod_LoadModel (model_t *mod, qboolean crash)
  194. {
  195. void *d;
  196. unsigned *buf;
  197. byte stackbuf[1024]; // avoid dirtying the cache heap
  198. if (!mod->needload)
  199. {
  200. if (mod->type == mod_alias)
  201. {
  202. d = Cache_Check (&mod->cache);
  203. if (d)
  204. return mod;
  205. }
  206. else
  207. return mod; // not cached at all
  208. }
  209. //
  210. // because the world is so huge, load it one piece at a time
  211. //
  212. if (!crash)
  213. {
  214. }
  215. //
  216. // load the file
  217. //
  218. buf = (unsigned *)COM_LoadStackFile (mod->name, stackbuf, sizeof(stackbuf));
  219. if (!buf)
  220. {
  221. if (crash)
  222. Sys_Error ("Mod_NumForName: %s not found", mod->name);
  223. return NULL;
  224. }
  225. //
  226. // allocate a new model
  227. //
  228. COM_FileBase (mod->name, loadname);
  229. loadmodel = mod;
  230. //
  231. // fill it in
  232. //
  233. // call the apropriate loader
  234. mod->needload = false;
  235. switch (LittleLong(*(unsigned *)buf))
  236. {
  237. case IDPOLYHEADER:
  238. Mod_LoadAliasModel (mod, buf);
  239. break;
  240. case IDSPRITEHEADER:
  241. Mod_LoadSpriteModel (mod, buf);
  242. break;
  243. default:
  244. Mod_LoadBrushModel (mod, buf);
  245. break;
  246. }
  247. return mod;
  248. }
  249. /*
  250. ==================
  251. Mod_ForName
  252. Loads in a model for the given name
  253. ==================
  254. */
  255. model_t *Mod_ForName (char *name, qboolean crash)
  256. {
  257. model_t *mod;
  258. mod = Mod_FindName (name);
  259. return Mod_LoadModel (mod, crash);
  260. }
  261. /*
  262. ===============================================================================
  263. BRUSHMODEL LOADING
  264. ===============================================================================
  265. */
  266. byte *mod_base;
  267. /*
  268. =================
  269. Mod_LoadTextures
  270. =================
  271. */
  272. void Mod_LoadTextures (lump_t *l)
  273. {
  274. int i, j, pixels, num, max, altmax;
  275. miptex_t *mt;
  276. texture_t *tx, *tx2;
  277. texture_t *anims[10];
  278. texture_t *altanims[10];
  279. dmiptexlump_t *m;
  280. if (!l->filelen)
  281. {
  282. loadmodel->textures = NULL;
  283. return;
  284. }
  285. m = (dmiptexlump_t *)(mod_base + l->fileofs);
  286. m->nummiptex = LittleLong (m->nummiptex);
  287. loadmodel->numtextures = m->nummiptex;
  288. loadmodel->textures = Hunk_AllocName (m->nummiptex * sizeof(*loadmodel->textures) , loadname);
  289. for (i=0 ; i<m->nummiptex ; i++)
  290. {
  291. m->dataofs[i] = LittleLong(m->dataofs[i]);
  292. if (m->dataofs[i] == -1)
  293. continue;
  294. mt = (miptex_t *)((byte *)m + m->dataofs[i]);
  295. mt->width = LittleLong (mt->width);
  296. mt->height = LittleLong (mt->height);
  297. for (j=0 ; j<MIPLEVELS ; j++)
  298. mt->offsets[j] = LittleLong (mt->offsets[j]);
  299. if ( (mt->width & 15) || (mt->height & 15) )
  300. Sys_Error ("Texture %s is not 16 aligned", mt->name);
  301. pixels = mt->width*mt->height/64*85;
  302. tx = Hunk_AllocName (sizeof(texture_t) +pixels, loadname );
  303. loadmodel->textures[i] = tx;
  304. memcpy (tx->name, mt->name, sizeof(tx->name));
  305. tx->width = mt->width;
  306. tx->height = mt->height;
  307. for (j=0 ; j<MIPLEVELS ; j++)
  308. tx->offsets[j] = mt->offsets[j] + sizeof(texture_t) - sizeof(miptex_t);
  309. // the pixels immediately follow the structures
  310. memcpy ( tx+1, mt+1, pixels);
  311. if (!Q_strncmp(mt->name,"sky",3))
  312. R_InitSky (tx);
  313. else
  314. {
  315. texture_mode = GL_LINEAR_MIPMAP_NEAREST; //_LINEAR;
  316. tx->gl_texturenum = GL_LoadTexture (mt->name, tx->width, tx->height, (byte *)(tx+1), true, false);
  317. texture_mode = GL_LINEAR;
  318. }
  319. }
  320. //
  321. // sequence the animations
  322. //
  323. for (i=0 ; i<m->nummiptex ; i++)
  324. {
  325. tx = loadmodel->textures[i];
  326. if (!tx || tx->name[0] != '+')
  327. continue;
  328. if (tx->anim_next)
  329. continue; // allready sequenced
  330. // find the number of frames in the animation
  331. memset (anims, 0, sizeof(anims));
  332. memset (altanims, 0, sizeof(altanims));
  333. max = tx->name[1];
  334. altmax = 0;
  335. if (max >= 'a' && max <= 'z')
  336. max -= 'a' - 'A';
  337. if (max >= '0' && max <= '9')
  338. {
  339. max -= '0';
  340. altmax = 0;
  341. anims[max] = tx;
  342. max++;
  343. }
  344. else if (max >= 'A' && max <= 'J')
  345. {
  346. altmax = max - 'A';
  347. max = 0;
  348. altanims[altmax] = tx;
  349. altmax++;
  350. }
  351. else
  352. Sys_Error ("Bad animating texture %s", tx->name);
  353. for (j=i+1 ; j<m->nummiptex ; j++)
  354. {
  355. tx2 = loadmodel->textures[j];
  356. if (!tx2 || tx2->name[0] != '+')
  357. continue;
  358. if (strcmp (tx2->name+2, tx->name+2))
  359. continue;
  360. num = tx2->name[1];
  361. if (num >= 'a' && num <= 'z')
  362. num -= 'a' - 'A';
  363. if (num >= '0' && num <= '9')
  364. {
  365. num -= '0';
  366. anims[num] = tx2;
  367. if (num+1 > max)
  368. max = num + 1;
  369. }
  370. else if (num >= 'A' && num <= 'J')
  371. {
  372. num = num - 'A';
  373. altanims[num] = tx2;
  374. if (num+1 > altmax)
  375. altmax = num+1;
  376. }
  377. else
  378. Sys_Error ("Bad animating texture %s", tx->name);
  379. }
  380. #define ANIM_CYCLE 2
  381. // link them all together
  382. for (j=0 ; j<max ; j++)
  383. {
  384. tx2 = anims[j];
  385. if (!tx2)
  386. Sys_Error ("Missing frame %i of %s",j, tx->name);
  387. tx2->anim_total = max * ANIM_CYCLE;
  388. tx2->anim_min = j * ANIM_CYCLE;
  389. tx2->anim_max = (j+1) * ANIM_CYCLE;
  390. tx2->anim_next = anims[ (j+1)%max ];
  391. if (altmax)
  392. tx2->alternate_anims = altanims[0];
  393. }
  394. for (j=0 ; j<altmax ; j++)
  395. {
  396. tx2 = altanims[j];
  397. if (!tx2)
  398. Sys_Error ("Missing frame %i of %s",j, tx->name);
  399. tx2->anim_total = altmax * ANIM_CYCLE;
  400. tx2->anim_min = j * ANIM_CYCLE;
  401. tx2->anim_max = (j+1) * ANIM_CYCLE;
  402. tx2->anim_next = altanims[ (j+1)%altmax ];
  403. if (max)
  404. tx2->alternate_anims = anims[0];
  405. }
  406. }
  407. }
  408. /*
  409. =================
  410. Mod_LoadLighting
  411. =================
  412. */
  413. void Mod_LoadLighting (lump_t *l)
  414. {
  415. if (!l->filelen)
  416. {
  417. loadmodel->lightdata = NULL;
  418. return;
  419. }
  420. loadmodel->lightdata = Hunk_AllocName ( l->filelen, loadname);
  421. memcpy (loadmodel->lightdata, mod_base + l->fileofs, l->filelen);
  422. }
  423. /*
  424. =================
  425. Mod_LoadVisibility
  426. =================
  427. */
  428. void Mod_LoadVisibility (lump_t *l)
  429. {
  430. if (!l->filelen)
  431. {
  432. loadmodel->visdata = NULL;
  433. return;
  434. }
  435. loadmodel->visdata = Hunk_AllocName ( l->filelen, loadname);
  436. memcpy (loadmodel->visdata, mod_base + l->fileofs, l->filelen);
  437. }
  438. /*
  439. =================
  440. Mod_LoadEntities
  441. =================
  442. */
  443. void Mod_LoadEntities (lump_t *l)
  444. {
  445. if (!l->filelen)
  446. {
  447. loadmodel->entities = NULL;
  448. return;
  449. }
  450. loadmodel->entities = Hunk_AllocName ( l->filelen, loadname);
  451. memcpy (loadmodel->entities, mod_base + l->fileofs, l->filelen);
  452. }
  453. /*
  454. =================
  455. Mod_LoadVertexes
  456. =================
  457. */
  458. void Mod_LoadVertexes (lump_t *l)
  459. {
  460. dvertex_t *in;
  461. mvertex_t *out;
  462. int i, count;
  463. in = (void *)(mod_base + l->fileofs);
  464. if (l->filelen % sizeof(*in))
  465. Sys_Error ("MOD_LoadBmodel: funny lump size in %s",loadmodel->name);
  466. count = l->filelen / sizeof(*in);
  467. out = Hunk_AllocName ( count*sizeof(*out), loadname);
  468. loadmodel->vertexes = out;
  469. loadmodel->numvertexes = count;
  470. for ( i=0 ; i<count ; i++, in++, out++)
  471. {
  472. out->position[0] = LittleFloat (in->point[0]);
  473. out->position[1] = LittleFloat (in->point[1]);
  474. out->position[2] = LittleFloat (in->point[2]);
  475. }
  476. }
  477. /*
  478. =================
  479. Mod_LoadSubmodels
  480. =================
  481. */
  482. void Mod_LoadSubmodels (lump_t *l)
  483. {
  484. dmodel_t *in;
  485. dmodel_t *out;
  486. int i, j, count;
  487. in = (void *)(mod_base + l->fileofs);
  488. if (l->filelen % sizeof(*in))
  489. Sys_Error ("MOD_LoadBmodel: funny lump size in %s",loadmodel->name);
  490. count = l->filelen / sizeof(*in);
  491. out = Hunk_AllocName ( count*sizeof(*out), loadname);
  492. loadmodel->submodels = out;
  493. loadmodel->numsubmodels = count;
  494. for ( i=0 ; i<count ; i++, in++, out++)
  495. {
  496. for (j=0 ; j<3 ; j++)
  497. { // spread the mins / maxs by a pixel
  498. out->mins[j] = LittleFloat (in->mins[j]) - 1;
  499. out->maxs[j] = LittleFloat (in->maxs[j]) + 1;
  500. out->origin[j] = LittleFloat (in->origin[j]);
  501. }
  502. for (j=0 ; j<MAX_MAP_HULLS ; j++)
  503. out->headnode[j] = LittleLong (in->headnode[j]);
  504. out->visleafs = LittleLong (in->visleafs);
  505. out->firstface = LittleLong (in->firstface);
  506. out->numfaces = LittleLong (in->numfaces);
  507. }
  508. }
  509. /*
  510. =================
  511. Mod_LoadEdges
  512. =================
  513. */
  514. void Mod_LoadEdges (lump_t *l)
  515. {
  516. dedge_t *in;
  517. medge_t *out;
  518. int i, count;
  519. in = (void *)(mod_base + l->fileofs);
  520. if (l->filelen % sizeof(*in))
  521. Sys_Error ("MOD_LoadBmodel: funny lump size in %s",loadmodel->name);
  522. count = l->filelen / sizeof(*in);
  523. out = Hunk_AllocName ( (count + 1) * sizeof(*out), loadname);
  524. loadmodel->edges = out;
  525. loadmodel->numedges = count;
  526. for ( i=0 ; i<count ; i++, in++, out++)
  527. {
  528. out->v[0] = (unsigned short)LittleShort(in->v[0]);
  529. out->v[1] = (unsigned short)LittleShort(in->v[1]);
  530. }
  531. }
  532. /*
  533. =================
  534. Mod_LoadTexinfo
  535. =================
  536. */
  537. void Mod_LoadTexinfo (lump_t *l)
  538. {
  539. texinfo_t *in;
  540. mtexinfo_t *out;
  541. int i, j, count;
  542. int miptex;
  543. float len1, len2;
  544. in = (void *)(mod_base + l->fileofs);
  545. if (l->filelen % sizeof(*in))
  546. Sys_Error ("MOD_LoadBmodel: funny lump size in %s",loadmodel->name);
  547. count = l->filelen / sizeof(*in);
  548. out = Hunk_AllocName ( count*sizeof(*out), loadname);
  549. loadmodel->texinfo = out;
  550. loadmodel->numtexinfo = count;
  551. for ( i=0 ; i<count ; i++, in++, out++)
  552. {
  553. for (j=0 ; j<8 ; j++)
  554. out->vecs[0][j] = LittleFloat (in->vecs[0][j]);
  555. len1 = Length (out->vecs[0]);
  556. len2 = Length (out->vecs[1]);
  557. len1 = (len1 + len2)/2;
  558. if (len1 < 0.32)
  559. out->mipadjust = 4;
  560. else if (len1 < 0.49)
  561. out->mipadjust = 3;
  562. else if (len1 < 0.99)
  563. out->mipadjust = 2;
  564. else
  565. out->mipadjust = 1;
  566. #if 0
  567. if (len1 + len2 < 0.001)
  568. out->mipadjust = 1; // don't crash
  569. else
  570. out->mipadjust = 1 / floor( (len1+len2)/2 + 0.1 );
  571. #endif
  572. miptex = LittleLong (in->miptex);
  573. out->flags = LittleLong (in->flags);
  574. if (!loadmodel->textures)
  575. {
  576. out->texture = r_notexture_mip; // checkerboard texture
  577. out->flags = 0;
  578. }
  579. else
  580. {
  581. if (miptex >= loadmodel->numtextures)
  582. Sys_Error ("miptex >= loadmodel->numtextures");
  583. out->texture = loadmodel->textures[miptex];
  584. if (!out->texture)
  585. {
  586. out->texture = r_notexture_mip; // texture not found
  587. out->flags = 0;
  588. }
  589. }
  590. }
  591. }
  592. /*
  593. ================
  594. CalcSurfaceExtents
  595. Fills in s->texturemins[] and s->extents[]
  596. ================
  597. */
  598. void CalcSurfaceExtents (msurface_t *s)
  599. {
  600. float mins[2], maxs[2], val;
  601. int i,j, e;
  602. mvertex_t *v;
  603. mtexinfo_t *tex;
  604. int bmins[2], bmaxs[2];
  605. mins[0] = mins[1] = 999999;
  606. maxs[0] = maxs[1] = -99999;
  607. tex = s->texinfo;
  608. for (i=0 ; i<s->numedges ; i++)
  609. {
  610. e = loadmodel->surfedges[s->firstedge+i];
  611. if (e >= 0)
  612. v = &loadmodel->vertexes[loadmodel->edges[e].v[0]];
  613. else
  614. v = &loadmodel->vertexes[loadmodel->edges[-e].v[1]];
  615. for (j=0 ; j<2 ; j++)
  616. {
  617. val = v->position[0] * tex->vecs[j][0] +
  618. v->position[1] * tex->vecs[j][1] +
  619. v->position[2] * tex->vecs[j][2] +
  620. tex->vecs[j][3];
  621. if (val < mins[j])
  622. mins[j] = val;
  623. if (val > maxs[j])
  624. maxs[j] = val;
  625. }
  626. }
  627. for (i=0 ; i<2 ; i++)
  628. {
  629. bmins[i] = floor(mins[i]/16);
  630. bmaxs[i] = ceil(maxs[i]/16);
  631. s->texturemins[i] = bmins[i] * 16;
  632. s->extents[i] = (bmaxs[i] - bmins[i]) * 16;
  633. if ( !(tex->flags & TEX_SPECIAL) && s->extents[i] > 512 /* 256 */ )
  634. Sys_Error ("Bad surface extents");
  635. }
  636. }
  637. /*
  638. =================
  639. Mod_LoadFaces
  640. =================
  641. */
  642. void Mod_LoadFaces (lump_t *l)
  643. {
  644. dface_t *in;
  645. msurface_t *out;
  646. int i, count, surfnum;
  647. int planenum, side;
  648. in = (void *)(mod_base + l->fileofs);
  649. if (l->filelen % sizeof(*in))
  650. Sys_Error ("MOD_LoadBmodel: funny lump size in %s",loadmodel->name);
  651. count = l->filelen / sizeof(*in);
  652. out = Hunk_AllocName ( count*sizeof(*out), loadname);
  653. loadmodel->surfaces = out;
  654. loadmodel->numsurfaces = count;
  655. for ( surfnum=0 ; surfnum<count ; surfnum++, in++, out++)
  656. {
  657. out->firstedge = LittleLong(in->firstedge);
  658. out->numedges = LittleShort(in->numedges);
  659. out->flags = 0;
  660. planenum = LittleShort(in->planenum);
  661. side = LittleShort(in->side);
  662. if (side)
  663. out->flags |= SURF_PLANEBACK;
  664. out->plane = loadmodel->planes + planenum;
  665. out->texinfo = loadmodel->texinfo + LittleShort (in->texinfo);
  666. CalcSurfaceExtents (out);
  667. // lighting info
  668. for (i=0 ; i<MAXLIGHTMAPS ; i++)
  669. out->styles[i] = in->styles[i];
  670. i = LittleLong(in->lightofs);
  671. if (i == -1)
  672. out->samples = NULL;
  673. else
  674. out->samples = loadmodel->lightdata + i;
  675. // set the drawing flags flag
  676. if (!Q_strncmp(out->texinfo->texture->name,"sky",3)) // sky
  677. {
  678. out->flags |= (SURF_DRAWSKY | SURF_DRAWTILED);
  679. #ifndef QUAKE2
  680. GL_SubdivideSurface (out); // cut up polygon for warps
  681. #endif
  682. continue;
  683. }
  684. if (!Q_strncmp(out->texinfo->texture->name,"*",1)) // turbulent
  685. {
  686. out->flags |= (SURF_DRAWTURB | SURF_DRAWTILED);
  687. for (i=0 ; i<2 ; i++)
  688. {
  689. out->extents[i] = 16384;
  690. out->texturemins[i] = -8192;
  691. }
  692. GL_SubdivideSurface (out); // cut up polygon for warps
  693. continue;
  694. }
  695. }
  696. }
  697. /*
  698. =================
  699. Mod_SetParent
  700. =================
  701. */
  702. void Mod_SetParent (mnode_t *node, mnode_t *parent)
  703. {
  704. node->parent = parent;
  705. if (node->contents < 0)
  706. return;
  707. Mod_SetParent (node->children[0], node);
  708. Mod_SetParent (node->children[1], node);
  709. }
  710. /*
  711. =================
  712. Mod_LoadNodes
  713. =================
  714. */
  715. void Mod_LoadNodes (lump_t *l)
  716. {
  717. int i, j, count, p;
  718. dnode_t *in;
  719. mnode_t *out;
  720. in = (void *)(mod_base + l->fileofs);
  721. if (l->filelen % sizeof(*in))
  722. Sys_Error ("MOD_LoadBmodel: funny lump size in %s",loadmodel->name);
  723. count = l->filelen / sizeof(*in);
  724. out = Hunk_AllocName ( count*sizeof(*out), loadname);
  725. loadmodel->nodes = out;
  726. loadmodel->numnodes = count;
  727. for ( i=0 ; i<count ; i++, in++, out++)
  728. {
  729. for (j=0 ; j<3 ; j++)
  730. {
  731. out->minmaxs[j] = LittleShort (in->mins[j]);
  732. out->minmaxs[3+j] = LittleShort (in->maxs[j]);
  733. }
  734. p = LittleLong(in->planenum);
  735. out->plane = loadmodel->planes + p;
  736. out->firstsurface = LittleShort (in->firstface);
  737. out->numsurfaces = LittleShort (in->numfaces);
  738. for (j=0 ; j<2 ; j++)
  739. {
  740. p = LittleShort (in->children[j]);
  741. if (p >= 0)
  742. out->children[j] = loadmodel->nodes + p;
  743. else
  744. out->children[j] = (mnode_t *)(loadmodel->leafs + (-1 - p));
  745. }
  746. }
  747. Mod_SetParent (loadmodel->nodes, NULL); // sets nodes and leafs
  748. }
  749. /*
  750. =================
  751. Mod_LoadLeafs
  752. =================
  753. */
  754. void Mod_LoadLeafs (lump_t *l)
  755. {
  756. dleaf_t *in;
  757. mleaf_t *out;
  758. int i, j, count, p;
  759. char s[80];
  760. qboolean isnotmap = true;
  761. in = (void *)(mod_base + l->fileofs);
  762. if (l->filelen % sizeof(*in))
  763. Sys_Error ("MOD_LoadBmodel: funny lump size in %s",loadmodel->name);
  764. count = l->filelen / sizeof(*in);
  765. out = Hunk_AllocName ( count*sizeof(*out), loadname);
  766. loadmodel->leafs = out;
  767. loadmodel->numleafs = count;
  768. sprintf(s, "maps/%s.bsp", Info_ValueForKey(cl.serverinfo,"map"));
  769. if (!strcmp(s, loadmodel->name))
  770. isnotmap = false;
  771. for ( i=0 ; i<count ; i++, in++, out++)
  772. {
  773. for (j=0 ; j<3 ; j++)
  774. {
  775. out->minmaxs[j] = LittleShort (in->mins[j]);
  776. out->minmaxs[3+j] = LittleShort (in->maxs[j]);
  777. }
  778. p = LittleLong(in->contents);
  779. out->contents = p;
  780. out->firstmarksurface = loadmodel->marksurfaces +
  781. LittleShort(in->firstmarksurface);
  782. out->nummarksurfaces = LittleShort(in->nummarksurfaces);
  783. p = LittleLong(in->visofs);
  784. if (p == -1)
  785. out->compressed_vis = NULL;
  786. else
  787. out->compressed_vis = loadmodel->visdata + p;
  788. out->efrags = NULL;
  789. for (j=0 ; j<4 ; j++)
  790. out->ambient_sound_level[j] = in->ambient_level[j];
  791. // gl underwater warp
  792. if (out->contents != CONTENTS_EMPTY)
  793. {
  794. for (j=0 ; j<out->nummarksurfaces ; j++)
  795. out->firstmarksurface[j]->flags |= SURF_UNDERWATER;
  796. }
  797. if (isnotmap)
  798. {
  799. for (j=0 ; j<out->nummarksurfaces ; j++)
  800. out->firstmarksurface[j]->flags |= SURF_DONTWARP;
  801. }
  802. }
  803. }
  804. /*
  805. =================
  806. Mod_LoadClipnodes
  807. =================
  808. */
  809. void Mod_LoadClipnodes (lump_t *l)
  810. {
  811. dclipnode_t *in, *out;
  812. int i, count;
  813. hull_t *hull;
  814. in = (void *)(mod_base + l->fileofs);
  815. if (l->filelen % sizeof(*in))
  816. Sys_Error ("MOD_LoadBmodel: funny lump size in %s",loadmodel->name);
  817. count = l->filelen / sizeof(*in);
  818. out = Hunk_AllocName ( count*sizeof(*out), loadname);
  819. loadmodel->clipnodes = out;
  820. loadmodel->numclipnodes = count;
  821. hull = &loadmodel->hulls[1];
  822. hull->clipnodes = out;
  823. hull->firstclipnode = 0;
  824. hull->lastclipnode = count-1;
  825. hull->planes = loadmodel->planes;
  826. hull->clip_mins[0] = -16;
  827. hull->clip_mins[1] = -16;
  828. hull->clip_mins[2] = -24;
  829. hull->clip_maxs[0] = 16;
  830. hull->clip_maxs[1] = 16;
  831. hull->clip_maxs[2] = 32;
  832. hull = &loadmodel->hulls[2];
  833. hull->clipnodes = out;
  834. hull->firstclipnode = 0;
  835. hull->lastclipnode = count-1;
  836. hull->planes = loadmodel->planes;
  837. hull->clip_mins[0] = -32;
  838. hull->clip_mins[1] = -32;
  839. hull->clip_mins[2] = -24;
  840. hull->clip_maxs[0] = 32;
  841. hull->clip_maxs[1] = 32;
  842. hull->clip_maxs[2] = 64;
  843. for (i=0 ; i<count ; i++, out++, in++)
  844. {
  845. out->planenum = LittleLong(in->planenum);
  846. out->children[0] = LittleShort(in->children[0]);
  847. out->children[1] = LittleShort(in->children[1]);
  848. }
  849. }
  850. /*
  851. =================
  852. Mod_MakeHull0
  853. Deplicate the drawing hull structure as a clipping hull
  854. =================
  855. */
  856. void Mod_MakeHull0 (void)
  857. {
  858. mnode_t *in, *child;
  859. dclipnode_t *out;
  860. int i, j, count;
  861. hull_t *hull;
  862. hull = &loadmodel->hulls[0];
  863. in = loadmodel->nodes;
  864. count = loadmodel->numnodes;
  865. out = Hunk_AllocName ( count*sizeof(*out), loadname);
  866. hull->clipnodes = out;
  867. hull->firstclipnode = 0;
  868. hull->lastclipnode = count-1;
  869. hull->planes = loadmodel->planes;
  870. for (i=0 ; i<count ; i++, out++, in++)
  871. {
  872. out->planenum = in->plane - loadmodel->planes;
  873. for (j=0 ; j<2 ; j++)
  874. {
  875. child = in->children[j];
  876. if (child->contents < 0)
  877. out->children[j] = child->contents;
  878. else
  879. out->children[j] = child - loadmodel->nodes;
  880. }
  881. }
  882. }
  883. /*
  884. =================
  885. Mod_LoadMarksurfaces
  886. =================
  887. */
  888. void Mod_LoadMarksurfaces (lump_t *l)
  889. {
  890. int i, j, count;
  891. short *in;
  892. msurface_t **out;
  893. in = (void *)(mod_base + l->fileofs);
  894. if (l->filelen % sizeof(*in))
  895. Sys_Error ("MOD_LoadBmodel: funny lump size in %s",loadmodel->name);
  896. count = l->filelen / sizeof(*in);
  897. out = Hunk_AllocName ( count*sizeof(*out), loadname);
  898. loadmodel->marksurfaces = out;
  899. loadmodel->nummarksurfaces = count;
  900. for ( i=0 ; i<count ; i++)
  901. {
  902. j = LittleShort(in[i]);
  903. if (j >= loadmodel->numsurfaces)
  904. Sys_Error ("Mod_ParseMarksurfaces: bad surface number");
  905. out[i] = loadmodel->surfaces + j;
  906. }
  907. }
  908. /*
  909. =================
  910. Mod_LoadSurfedges
  911. =================
  912. */
  913. void Mod_LoadSurfedges (lump_t *l)
  914. {
  915. int i, count;
  916. int *in, *out;
  917. in = (void *)(mod_base + l->fileofs);
  918. if (l->filelen % sizeof(*in))
  919. Sys_Error ("MOD_LoadBmodel: funny lump size in %s",loadmodel->name);
  920. count = l->filelen / sizeof(*in);
  921. out = Hunk_AllocName ( count*sizeof(*out), loadname);
  922. loadmodel->surfedges = out;
  923. loadmodel->numsurfedges = count;
  924. for ( i=0 ; i<count ; i++)
  925. out[i] = LittleLong (in[i]);
  926. }
  927. /*
  928. =================
  929. Mod_LoadPlanes
  930. =================
  931. */
  932. void Mod_LoadPlanes (lump_t *l)
  933. {
  934. int i, j;
  935. mplane_t *out;
  936. dplane_t *in;
  937. int count;
  938. int bits;
  939. in = (void *)(mod_base + l->fileofs);
  940. if (l->filelen % sizeof(*in))
  941. Sys_Error ("MOD_LoadBmodel: funny lump size in %s",loadmodel->name);
  942. count = l->filelen / sizeof(*in);
  943. out = Hunk_AllocName ( count*2*sizeof(*out), loadname);
  944. loadmodel->planes = out;
  945. loadmodel->numplanes = count;
  946. for ( i=0 ; i<count ; i++, in++, out++)
  947. {
  948. bits = 0;
  949. for (j=0 ; j<3 ; j++)
  950. {
  951. out->normal[j] = LittleFloat (in->normal[j]);
  952. if (out->normal[j] < 0)
  953. bits |= 1<<j;
  954. }
  955. out->dist = LittleFloat (in->dist);
  956. out->type = LittleLong (in->type);
  957. out->signbits = bits;
  958. }
  959. }
  960. /*
  961. =================
  962. RadiusFromBounds
  963. =================
  964. */
  965. float RadiusFromBounds (vec3_t mins, vec3_t maxs)
  966. {
  967. int i;
  968. vec3_t corner;
  969. for (i=0 ; i<3 ; i++)
  970. {
  971. corner[i] = fabs(mins[i]) > fabs(maxs[i]) ? fabs(mins[i]) : fabs(maxs[i]);
  972. }
  973. return Length (corner);
  974. }
  975. /*
  976. =================
  977. Mod_LoadBrushModel
  978. =================
  979. */
  980. void Mod_LoadBrushModel (model_t *mod, void *buffer)
  981. {
  982. int i, j;
  983. dheader_t *header;
  984. dmodel_t *bm;
  985. loadmodel->type = mod_brush;
  986. header = (dheader_t *)buffer;
  987. i = LittleLong (header->version);
  988. if (i != BSPVERSION)
  989. Sys_Error ("Mod_LoadBrushModel: %s has wrong version number (%i should be %i)", mod->name, i, BSPVERSION);
  990. // swap all the lumps
  991. mod_base = (byte *)header;
  992. for (i=0 ; i<sizeof(dheader_t)/4 ; i++)
  993. ((int *)header)[i] = LittleLong ( ((int *)header)[i]);
  994. // checksum all of the map, except for entities
  995. mod->checksum = 0;
  996. mod->checksum2 = 0;
  997. for (i = 0; i < HEADER_LUMPS; i++) {
  998. if (i == LUMP_ENTITIES)
  999. continue;
  1000. mod->checksum ^= Com_BlockChecksum(mod_base + header->lumps[i].fileofs,
  1001. header->lumps[i].filelen);
  1002. if (i == LUMP_VISIBILITY || i == LUMP_LEAFS || i == LUMP_NODES)
  1003. continue;
  1004. mod->checksum2 ^= Com_BlockChecksum(mod_base + header->lumps[i].fileofs,
  1005. header->lumps[i].filelen);
  1006. }
  1007. // load into heap
  1008. Mod_LoadVertexes (&header->lumps[LUMP_VERTEXES]);
  1009. Mod_LoadEdges (&header->lumps[LUMP_EDGES]);
  1010. Mod_LoadSurfedges (&header->lumps[LUMP_SURFEDGES]);
  1011. Mod_LoadTextures (&header->lumps[LUMP_TEXTURES]);
  1012. Mod_LoadLighting (&header->lumps[LUMP_LIGHTING]);
  1013. Mod_LoadPlanes (&header->lumps[LUMP_PLANES]);
  1014. Mod_LoadTexinfo (&header->lumps[LUMP_TEXINFO]);
  1015. Mod_LoadFaces (&header->lumps[LUMP_FACES]);
  1016. Mod_LoadMarksurfaces (&header->lumps[LUMP_MARKSURFACES]);
  1017. Mod_LoadVisibility (&header->lumps[LUMP_VISIBILITY]);
  1018. Mod_LoadLeafs (&header->lumps[LUMP_LEAFS]);
  1019. Mod_LoadNodes (&header->lumps[LUMP_NODES]);
  1020. Mod_LoadClipnodes (&header->lumps[LUMP_CLIPNODES]);
  1021. Mod_LoadEntities (&header->lumps[LUMP_ENTITIES]);
  1022. Mod_LoadSubmodels (&header->lumps[LUMP_MODELS]);
  1023. Mod_MakeHull0 ();
  1024. mod->numframes = 2; // regular and alternate animation
  1025. //
  1026. // set up the submodels (FIXME: this is confusing)
  1027. //
  1028. for (i=0 ; i<mod->numsubmodels ; i++)
  1029. {
  1030. bm = &mod->submodels[i];
  1031. mod->hulls[0].firstclipnode = bm->headnode[0];
  1032. for (j=1 ; j<MAX_MAP_HULLS ; j++)
  1033. {
  1034. mod->hulls[j].firstclipnode = bm->headnode[j];
  1035. mod->hulls[j].lastclipnode = mod->numclipnodes-1;
  1036. }
  1037. mod->firstmodelsurface = bm->firstface;
  1038. mod->nummodelsurfaces = bm->numfaces;
  1039. VectorCopy (bm->maxs, mod->maxs);
  1040. VectorCopy (bm->mins, mod->mins);
  1041. mod->radius = RadiusFromBounds (mod->mins, mod->maxs);
  1042. mod->numleafs = bm->visleafs;
  1043. if (i < mod->numsubmodels-1)
  1044. { // duplicate the basic information
  1045. char name[10];
  1046. sprintf (name, "*%i", i+1);
  1047. loadmodel = Mod_FindName (name);
  1048. *loadmodel = *mod;
  1049. strcpy (loadmodel->name, name);
  1050. mod = loadmodel;
  1051. }
  1052. }
  1053. }
  1054. /*
  1055. ==============================================================================
  1056. ALIAS MODELS
  1057. ==============================================================================
  1058. */
  1059. aliashdr_t *pheader;
  1060. stvert_t stverts[MAXALIASVERTS];
  1061. mtriangle_t triangles[MAXALIASTRIS];
  1062. // a pose is a single set of vertexes. a frame may be
  1063. // an animating sequence of poses
  1064. trivertx_t *poseverts[MAXALIASFRAMES];
  1065. int posenum;
  1066. byte player_8bit_texels[320*200];
  1067. /*
  1068. =================
  1069. Mod_LoadAliasFrame
  1070. =================
  1071. */
  1072. void * Mod_LoadAliasFrame (void * pin, maliasframedesc_t *frame)
  1073. {
  1074. trivertx_t *pinframe;
  1075. int i;
  1076. daliasframe_t *pdaliasframe;
  1077. pdaliasframe = (daliasframe_t *)pin;
  1078. strcpy (frame->name, pdaliasframe->name);
  1079. frame->firstpose = posenum;
  1080. frame->numposes = 1;
  1081. for (i=0 ; i<3 ; i++)
  1082. {
  1083. // these are byte values, so we don't have to worry about
  1084. // endianness
  1085. frame->bboxmin.v[i] = pdaliasframe->bboxmin.v[i];
  1086. frame->bboxmin.v[i] = pdaliasframe->bboxmax.v[i];
  1087. }
  1088. pinframe = (trivertx_t *)(pdaliasframe + 1);
  1089. poseverts[posenum] = pinframe;
  1090. posenum++;
  1091. pinframe += pheader->numverts;
  1092. return (void *)pinframe;
  1093. }
  1094. /*
  1095. =================
  1096. Mod_LoadAliasGroup
  1097. =================
  1098. */
  1099. void *Mod_LoadAliasGroup (void * pin, maliasframedesc_t *frame)
  1100. {
  1101. daliasgroup_t *pingroup;
  1102. int i, numframes;
  1103. daliasinterval_t *pin_intervals;
  1104. void *ptemp;
  1105. pingroup = (daliasgroup_t *)pin;
  1106. numframes = LittleLong (pingroup->numframes);
  1107. frame->firstpose = posenum;
  1108. frame->numposes = numframes;
  1109. for (i=0 ; i<3 ; i++)
  1110. {
  1111. // these are byte values, so we don't have to worry about endianness
  1112. frame->bboxmin.v[i] = pingroup->bboxmin.v[i];
  1113. frame->bboxmin.v[i] = pingroup->bboxmax.v[i];
  1114. }
  1115. pin_intervals = (daliasinterval_t *)(pingroup + 1);
  1116. frame->interval = LittleFloat (pin_intervals->interval);
  1117. pin_intervals += numframes;
  1118. ptemp = (void *)pin_intervals;
  1119. for (i=0 ; i<numframes ; i++)
  1120. {
  1121. poseverts[posenum] = (trivertx_t *)((daliasframe_t *)ptemp + 1);
  1122. posenum++;
  1123. ptemp = (trivertx_t *)((daliasframe_t *)ptemp + 1) + pheader->numverts;
  1124. }
  1125. return ptemp;
  1126. }
  1127. //=========================================================
  1128. /*
  1129. =================
  1130. Mod_FloodFillSkin
  1131. Fill background pixels so mipmapping doesn't have haloes - Ed
  1132. =================
  1133. */
  1134. typedef struct
  1135. {
  1136. short x, y;
  1137. } floodfill_t;
  1138. extern unsigned d_8to24table[];
  1139. // must be a power of 2
  1140. #define FLOODFILL_FIFO_SIZE 0x1000
  1141. #define FLOODFILL_FIFO_MASK (FLOODFILL_FIFO_SIZE - 1)
  1142. #define FLOODFILL_STEP( off, dx, dy ) \
  1143. { \
  1144. if (pos[off] == fillcolor) \
  1145. { \
  1146. pos[off] = 255; \
  1147. fifo[inpt].x = x + (dx), fifo[inpt].y = y + (dy); \
  1148. inpt = (inpt + 1) & FLOODFILL_FIFO_MASK; \
  1149. } \
  1150. else if (pos[off] != 255) fdc = pos[off]; \
  1151. }
  1152. void Mod_FloodFillSkin( byte *skin, int skinwidth, int skinheight )
  1153. {
  1154. byte fillcolor = *skin; // assume this is the pixel to fill
  1155. floodfill_t fifo[FLOODFILL_FIFO_SIZE];
  1156. int inpt = 0, outpt = 0;
  1157. int filledcolor = -1;
  1158. int i;
  1159. if (filledcolor == -1)
  1160. {
  1161. filledcolor = 0;
  1162. // attempt to find opaque black
  1163. for (i = 0; i < 256; ++i)
  1164. if (d_8to24table[i] == (255 << 0)) // alpha 1.0
  1165. {
  1166. filledcolor = i;
  1167. break;
  1168. }
  1169. }
  1170. // can't fill to filled color or to transparent color (used as visited marker)
  1171. if ((fillcolor == filledcolor) || (fillcolor == 255))
  1172. {
  1173. //printf( "not filling skin from %d to %d\n", fillcolor, filledcolor );
  1174. return;
  1175. }
  1176. fifo[inpt].x = 0, fifo[inpt].y = 0;
  1177. inpt = (inpt + 1) & FLOODFILL_FIFO_MASK;
  1178. while (outpt != inpt)
  1179. {
  1180. int x = fifo[outpt].x, y = fifo[outpt].y;
  1181. int fdc = filledcolor;
  1182. byte *pos = &skin[x + skinwidth * y];
  1183. outpt = (outpt + 1) & FLOODFILL_FIFO_MASK;
  1184. if (x > 0) FLOODFILL_STEP( -1, -1, 0 );
  1185. if (x < skinwidth - 1) FLOODFILL_STEP( 1, 1, 0 );
  1186. if (y > 0) FLOODFILL_STEP( -skinwidth, 0, -1 );
  1187. if (y < skinheight - 1) FLOODFILL_STEP( skinwidth, 0, 1 );
  1188. skin[x + skinwidth * y] = fdc;
  1189. }
  1190. }
  1191. /*
  1192. ===============
  1193. Mod_LoadAllSkins
  1194. ===============
  1195. */
  1196. void *Mod_LoadAllSkins (int numskins, daliasskintype_t *pskintype)
  1197. {
  1198. int i, j, k;
  1199. char name[32];
  1200. int s;
  1201. byte *skin;
  1202. daliasskingroup_t *pinskingroup;
  1203. int groupskins;
  1204. daliasskininterval_t *pinskinintervals;
  1205. skin = (byte *)(pskintype + 1);
  1206. if (numskins < 1 || numskins > MAX_SKINS)
  1207. Sys_Error ("Mod_LoadAliasModel: Invalid # of skins: %d\n", numskins);
  1208. s = pheader->skinwidth * pheader->skinheight;
  1209. for (i=0 ; i<numskins ; i++)
  1210. {
  1211. if (pskintype->type == ALIAS_SKIN_SINGLE) {
  1212. Mod_FloodFillSkin( skin, pheader->skinwidth, pheader->skinheight );
  1213. // save 8 bit texels for the player model to remap
  1214. // save 8 bit texels for the player model to remap
  1215. if (!strcmp(loadmodel->name,"progs/player.mdl"))
  1216. {
  1217. if (s > sizeof(player_8bit_texels))
  1218. Sys_Error ("Player skin too large");
  1219. memcpy (player_8bit_texels, (byte *)(pskintype + 1), s);
  1220. }
  1221. sprintf (name, "%s_%i", loadmodel->name, i);
  1222. pheader->gl_texturenum[i][0] =
  1223. pheader->gl_texturenum[i][1] =
  1224. pheader->gl_texturenum[i][2] =
  1225. pheader->gl_texturenum[i][3] =
  1226. GL_LoadTexture (name, pheader->skinwidth,
  1227. pheader->skinheight, (byte *)(pskintype + 1), true, false);
  1228. pskintype = (daliasskintype_t *)((byte *)(pskintype+1) + s);
  1229. } else {
  1230. // animating skin group. yuck.
  1231. pskintype++;
  1232. pinskingroup = (daliasskingroup_t *)pskintype;
  1233. groupskins = LittleLong (pinskingroup->numskins);
  1234. pinskinintervals = (daliasskininterval_t *)(pinskingroup + 1);
  1235. pskintype = (void *)(pinskinintervals + groupskins);
  1236. for (j=0 ; j<groupskins ; j++)
  1237. {
  1238. Mod_FloodFillSkin( skin, pheader->skinwidth, pheader->skinheight );
  1239. sprintf (name, "%s_%i_%i", loadmodel->name, i,j);
  1240. pheader->gl_texturenum[i][j&3] =
  1241. GL_LoadTexture (name, pheader->skinwidth,
  1242. pheader->skinheight, (byte *)(pskintype), true, false);
  1243. pskintype = (daliasskintype_t *)((byte *)(pskintype) + s);
  1244. }
  1245. k = j;
  1246. for (/* */; j < 4; j++)
  1247. pheader->gl_texturenum[i][j&3] =
  1248. pheader->gl_texturenum[i][j - k];
  1249. }
  1250. }
  1251. return (void *)pskintype;
  1252. }
  1253. //=========================================================================
  1254. /*
  1255. =================
  1256. Mod_LoadAliasModel
  1257. =================
  1258. */
  1259. void Mod_LoadAliasModel (model_t *mod, void *buffer)
  1260. {
  1261. int i, j;
  1262. mdl_t *pinmodel;
  1263. stvert_t *pinstverts;
  1264. dtriangle_t *pintriangles;
  1265. int version, numframes;
  1266. int size;
  1267. daliasframetype_t *pframetype;
  1268. daliasskintype_t *pskintype;
  1269. int start, end, total;
  1270. if (!strcmp(loadmodel->name, "progs/player.mdl") ||
  1271. !strcmp(loadmodel->name, "progs/eyes.mdl")) {
  1272. unsigned short crc;
  1273. byte *p;
  1274. int len;
  1275. char st[40];
  1276. CRC_Init(&crc);
  1277. for (len = com_filesize, p = buffer; len; len--, p++)
  1278. CRC_ProcessByte(&crc, *p);
  1279. sprintf(st, "%d", (int) crc);
  1280. Info_SetValueForKey (cls.userinfo,
  1281. !strcmp(loadmodel->name, "progs/player.mdl") ? pmodel_name : emodel_name,
  1282. st, MAX_INFO_STRING);
  1283. if (cls.state >= ca_connected) {
  1284. MSG_WriteByte (&cls.netchan.message, clc_stringcmd);
  1285. sprintf(st, "setinfo %s %d",
  1286. !strcmp(loadmodel->name, "progs/player.mdl") ? pmodel_name : emodel_name,
  1287. (int)crc);
  1288. SZ_Print (&cls.netchan.message, st);
  1289. }
  1290. }
  1291. start = Hunk_LowMark ();
  1292. pinmodel = (mdl_t *)buffer;
  1293. version = LittleLong (pinmodel->version);
  1294. if (version != ALIAS_VERSION)
  1295. Sys_Error ("%s has wrong version number (%i should be %i)",
  1296. mod->name, version, ALIAS_VERSION);
  1297. //
  1298. // allocate space for a working header, plus all the data except the frames,
  1299. // skin and group info
  1300. //
  1301. size = sizeof (aliashdr_t)
  1302. + (LittleLong (pinmodel->numframes) - 1) *
  1303. sizeof (pheader->frames[0]);
  1304. pheader = Hunk_AllocName (size, loadname);
  1305. mod->flags = LittleLong (pinmodel->flags);
  1306. //
  1307. // endian-adjust and copy the data, starting with the alias model header
  1308. //
  1309. pheader->boundingradius = LittleFloat (pinmodel->boundingradius);
  1310. pheader->numskins = LittleLong (pinmodel->numskins);
  1311. pheader->skinwidth = LittleLong (pinmodel->skinwidth);
  1312. pheader->skinheight = LittleLong (pinmodel->skinheight);
  1313. if (pheader->skinheight > MAX_LBM_HEIGHT)
  1314. Sys_Error ("model %s has a skin taller than %d", mod->name,
  1315. MAX_LBM_HEIGHT);
  1316. pheader->numverts = LittleLong (pinmodel->numverts);
  1317. if (pheader->numverts <= 0)
  1318. Sys_Error ("model %s has no vertices", mod->name);
  1319. if (pheader->numverts > MAXALIASVERTS)
  1320. Sys_Error ("model %s has too many vertices", mod->name);
  1321. pheader->numtris = LittleLong (pinmodel->numtris);
  1322. if (pheader->numtris <= 0)
  1323. Sys_Error ("model %s has no triangles", mod->name);
  1324. pheader->numframes = LittleLong (pinmodel->numframes);
  1325. numframes = pheader->numframes;
  1326. if (numframes < 1)
  1327. Sys_Error ("Mod_LoadAliasModel: Invalid # of frames: %d\n", numframes);
  1328. pheader->size = LittleFloat (pinmodel->size) * ALIAS_BASE_SIZE_RATIO;
  1329. mod->synctype = LittleLong (pinmodel->synctype);
  1330. mod->numframes = pheader->numframes;
  1331. for (i=0 ; i<3 ; i++)
  1332. {
  1333. pheader->scale[i] = LittleFloat (pinmodel->scale[i]);
  1334. pheader->scale_origin[i] = LittleFloat (pinmodel->scale_origin[i]);
  1335. pheader->eyeposition[i] = LittleFloat (pinmodel->eyeposition[i]);
  1336. }
  1337. //
  1338. // load the skins
  1339. //
  1340. pskintype = (daliasskintype_t *)&pinmodel[1];
  1341. pskintype = Mod_LoadAllSkins (pheader->numskins, pskintype);
  1342. //
  1343. // load base s and t vertices
  1344. //
  1345. pinstverts = (stvert_t *)pskintype;
  1346. for (i=0 ; i<pheader->numverts ; i++)
  1347. {
  1348. stverts[i].onseam = LittleLong (pinstverts[i].onseam);
  1349. stverts[i].s = LittleLong (pinstverts[i].s);
  1350. stverts[i].t = LittleLong (pinstverts[i].t);
  1351. }
  1352. //
  1353. // load triangle lists
  1354. //
  1355. pintriangles = (dtriangle_t *)&pinstverts[pheader->numverts];
  1356. for (i=0 ; i<pheader->numtris ; i++)
  1357. {
  1358. triangles[i].facesfront = LittleLong (pintriangles[i].facesfront);
  1359. for (j=0 ; j<3 ; j++)
  1360. {
  1361. triangles[i].vertindex[j] =
  1362. LittleLong (pintriangles[i].vertindex[j]);
  1363. }
  1364. }
  1365. //
  1366. // load the frames
  1367. //
  1368. posenum = 0;
  1369. pframetype = (daliasframetype_t *)&pintriangles[pheader->numtris];
  1370. for (i=0 ; i<numframes ; i++)
  1371. {
  1372. aliasframetype_t frametype;
  1373. frametype = LittleLong (pframetype->type);
  1374. if (frametype == ALIAS_SINGLE)
  1375. {
  1376. pframetype = (daliasframetype_t *)
  1377. Mod_LoadAliasFrame (pframetype + 1, &pheader->frames[i]);
  1378. }
  1379. else
  1380. {
  1381. pframetype = (daliasframetype_t *)
  1382. Mod_LoadAliasGroup (pframetype + 1, &pheader->frames[i]);
  1383. }
  1384. }
  1385. pheader->numposes = posenum;
  1386. mod->type = mod_alias;
  1387. // FIXME: do this right
  1388. mod->mins[0] = mod->mins[1] = mod->mins[2] = -16;
  1389. mod->maxs[0] = mod->maxs[1] = mod->maxs[2] = 16;
  1390. //
  1391. // build the draw lists
  1392. //
  1393. GL_MakeAliasModelDisplayLists (mod, pheader);
  1394. //
  1395. // move the complete, relocatable alias model to the cache
  1396. //
  1397. end = Hunk_LowMark ();
  1398. total = end - start;
  1399. Cache_Alloc (&mod->cache, total, loadname);
  1400. if (!mod->cache.data)
  1401. return;
  1402. memcpy (mod->cache.data, pheader, total);
  1403. Hunk_FreeToLowMark (start);
  1404. }
  1405. //=============================================================================
  1406. /*
  1407. =================
  1408. Mod_LoadSpriteFrame
  1409. =================
  1410. */
  1411. void * Mod_LoadSpriteFrame (void * pin, mspriteframe_t **ppframe, int framenum)
  1412. {
  1413. dspriteframe_t *pinframe;
  1414. mspriteframe_t *pspriteframe;
  1415. int width, height, size, origin[2];
  1416. char name[64];
  1417. pinframe = (dspriteframe_t *)pin;
  1418. width = LittleLong (pinframe->width);
  1419. height = LittleLong (pinframe->height);
  1420. size = width * height;
  1421. pspriteframe = Hunk_AllocName (sizeof (mspriteframe_t),loadname);
  1422. Q_memset (pspriteframe, 0, sizeof (mspriteframe_t));
  1423. *ppframe = pspriteframe;
  1424. pspriteframe->width = width;
  1425. pspriteframe->height = height;
  1426. origin[0] = LittleLong (pinframe->origin[0]);
  1427. origin[1] = LittleLong (pinframe->origin[1]);
  1428. pspriteframe->up = origin[1];
  1429. pspriteframe->down = origin[1] - height;
  1430. pspriteframe->left = origin[0];
  1431. pspriteframe->right = width + origin[0];
  1432. sprintf (name, "%s_%i", loadmodel->name, framenum);
  1433. pspriteframe->gl_texturenum = GL_LoadTexture (name, width, height, (byte *)(pinframe + 1), true, true);
  1434. return (void *)((byte *)pinframe + sizeof (dspriteframe_t) + size);
  1435. }
  1436. /*
  1437. =================
  1438. Mod_LoadSpriteGroup
  1439. =================
  1440. */
  1441. void * Mod_LoadSpriteGroup (void * pin, mspriteframe_t **ppframe, int framenum)
  1442. {
  1443. dspritegroup_t *pingroup;
  1444. mspritegroup_t *pspritegroup;
  1445. int i, numframes;
  1446. dspriteinterval_t *pin_intervals;
  1447. float *poutintervals;
  1448. void *ptemp;
  1449. pingroup = (dspritegroup_t *)pin;
  1450. numframes = LittleLong (pingroup->numframes);
  1451. pspritegroup = Hunk_AllocName (sizeof (mspritegroup_t) +
  1452. (numframes - 1) * sizeof (pspritegroup->frames[0]), loadname);
  1453. pspritegroup->numframes = numframes;
  1454. *ppframe = (mspriteframe_t *)pspritegroup;
  1455. pin_intervals = (dspriteinterval_t *)(pingroup + 1);
  1456. poutintervals = Hunk_AllocName (numframes * sizeof (float), loadname);
  1457. pspritegroup->intervals = poutintervals;
  1458. for (i=0 ; i<numframes ; i++)
  1459. {
  1460. *poutintervals = LittleFloat (pin_intervals->interval);
  1461. if (*poutintervals <= 0.0)
  1462. Sys_Error ("Mod_LoadSpriteGroup: interval<=0");
  1463. poutintervals++;
  1464. pin_intervals++;
  1465. }
  1466. ptemp = (void *)pin_intervals;
  1467. for (i=0 ; i<numframes ; i++)
  1468. {
  1469. ptemp = Mod_LoadSpriteFrame (ptemp, &pspritegroup->frames[i], framenum * 100 + i);
  1470. }
  1471. return ptemp;
  1472. }
  1473. /*
  1474. =================
  1475. Mod_LoadSpriteModel
  1476. =================
  1477. */
  1478. void Mod_LoadSpriteModel (model_t *mod, void *buffer)
  1479. {
  1480. int i;
  1481. int version;
  1482. dsprite_t *pin;
  1483. msprite_t *psprite;
  1484. int numframes;
  1485. int size;
  1486. dspriteframetype_t *pframetype;
  1487. pin = (dsprite_t *)buffer;
  1488. version = LittleLong (pin->version);
  1489. if (version != SPRITE_VERSION)
  1490. Sys_Error ("%s has wrong version number "
  1491. "(%i should be %i)", mod->name, version, SPRITE_VERSION);
  1492. numframes = LittleLong (pin->numframes);
  1493. size = sizeof (msprite_t) + (numframes - 1) * sizeof (psprite->frames);
  1494. psprite = Hunk_AllocName (size, loadname);
  1495. mod->cache.data = psprite;
  1496. psprite->type = LittleLong (pin->type);
  1497. psprite->maxwidth = LittleLong (pin->width);
  1498. psprite->maxheight = LittleLong (pin->height);
  1499. psprite->beamlength = LittleFloat (pin->beamlength);
  1500. mod->synctype = LittleLong (pin->synctype);
  1501. psprite->numframes = numframes;
  1502. mod->mins[0] = mod->mins[1] = -psprite->maxwidth/2;
  1503. mod->maxs[0] = mod->maxs[1] = psprite->maxwidth/2;
  1504. mod->mins[2] = -psprite->maxheight/2;
  1505. mod->maxs[2] = psprite->maxheight/2;
  1506. //
  1507. // load the frames
  1508. //
  1509. if (numframes < 1)
  1510. Sys_Error ("Mod_LoadSpriteModel: Invalid # of frames: %d\n", numframes);
  1511. mod->numframes = numframes;
  1512. pframetype = (dspriteframetype_t *)(pin + 1);
  1513. for (i=0 ; i<numframes ; i++)
  1514. {
  1515. spriteframetype_t frametype;
  1516. frametype = LittleLong (pframetype->type);
  1517. psprite->frames[i].type = frametype;
  1518. if (frametype == SPR_SINGLE)
  1519. {
  1520. pframetype = (dspriteframetype_t *)
  1521. Mod_LoadSpriteFrame (pframetype + 1,
  1522. &psprite->frames[i].frameptr, i);
  1523. }
  1524. else
  1525. {
  1526. pframetype = (dspriteframetype_t *)
  1527. Mod_LoadSpriteGroup (pframetype + 1,
  1528. &psprite->frames[i].frameptr, i);
  1529. }
  1530. }
  1531. mod->type = mod_sprite;
  1532. }
  1533. //=============================================================================
  1534. /*
  1535. ================
  1536. Mod_Print
  1537. ================
  1538. */
  1539. void Mod_Print (void)
  1540. {
  1541. int i;
  1542. model_t *mod;
  1543. Con_Printf ("Cached models:\n");
  1544. for (i=0, mod=mod_known ; i < mod_numknown ; i++, mod++)
  1545. {
  1546. Con_Printf ("%8p : %s\n",mod->cache.data, mod->name);
  1547. }
  1548. }