home *** CD-ROM | disk | FTP | other *** search
/ Enigma Amiga Life 113 / EnigmaAmiga113CD.iso / software / sviluppo / quake_src / gl_rmisc.c < prev    next >
Encoding:
C/C++ Source or Header  |  2000-06-17  |  11.6 KB  |  456 lines

  1. /*
  2. Copyright (C) 1996-1997 Id Software, Inc.
  3.  
  4. This program is free software; you can redistribute it and/or
  5. modify it under the terms of the GNU General Public License
  6. as published by the Free Software Foundation; either version 2
  7. of the License, or (at your option) any later version.
  8.  
  9. This program is distributed in the hope that it will be useful,
  10. but WITHOUT ANY WARRANTY; without even the implied warranty of
  11. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  
  12.  
  13. See the GNU General Public License for more details.
  14.  
  15. You should have received a copy of the GNU General Public License
  16. along with this program; if not, write to the Free Software
  17. Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
  18.  
  19. */
  20. // r_misc.c
  21.  
  22. #include "quakedef.h"
  23.  
  24.  
  25.  
  26. /*
  27. ==================
  28. R_InitTextures
  29. ==================
  30. */
  31. void  R_InitTextures (void)
  32. {
  33.   int   x,y, m;
  34.   byte  *dest;
  35.  
  36. // create a simple checkerboard texture for the default
  37.   r_notexture_mip = Hunk_AllocName (sizeof(texture_t) + 16*16+8*8+4*4+2*2, "notexture");
  38.   
  39.   r_notexture_mip->width = r_notexture_mip->height = 16;
  40.   r_notexture_mip->offsets[0] = sizeof(texture_t);
  41.   r_notexture_mip->offsets[1] = r_notexture_mip->offsets[0] + 16*16;
  42.   r_notexture_mip->offsets[2] = r_notexture_mip->offsets[1] + 8*8;
  43.   r_notexture_mip->offsets[3] = r_notexture_mip->offsets[2] + 4*4;
  44.   
  45.   for (m=0 ; m<4 ; m++)
  46.   {
  47.     dest = (byte *)r_notexture_mip + r_notexture_mip->offsets[m];
  48.     for (y=0 ; y< (16>>m) ; y++)
  49.       for (x=0 ; x< (16>>m) ; x++)
  50.       {
  51.         if (  (y< (8>>m) ) ^ (x< (8>>m) ) )
  52.           *dest++ = 0;
  53.         else
  54.           *dest++ = 0xff;
  55.       }
  56.   } 
  57. }
  58.  
  59. byte  dottexture[8][8] =
  60. {
  61.   {0,1,1,0,0,0,0,0},
  62.   {1,1,1,1,0,0,0,0},
  63.   {1,1,1,1,0,0,0,0},
  64.   {0,1,1,0,0,0,0,0},
  65.   {0,0,0,0,0,0,0,0},
  66.   {0,0,0,0,0,0,0,0},
  67.   {0,0,0,0,0,0,0,0},
  68.   {0,0,0,0,0,0,0,0},
  69. };
  70. void R_InitParticleTexture (void)
  71. {
  72.   int   x,y;
  73.   byte  data[8][8][4];
  74.  
  75.   //
  76.   // particle texture
  77.   //
  78.   particletexture = texture_extension_number++;
  79.     GL_Bind(particletexture);
  80.  
  81.   for (x=0 ; x<8 ; x++)
  82.   {
  83.     for (y=0 ; y<8 ; y++)
  84.     {
  85.       data[y][x][0] = 255;
  86.       data[y][x][1] = 255;
  87.       data[y][x][2] = 255;
  88.       data[y][x][3] = dottexture[x][y]*255;
  89.     }
  90.   }
  91.   glTexImage2D (GL_TEXTURE_2D, 0, gl_alpha_format, 8, 8, 0, GL_RGBA, GL_UNSIGNED_BYTE, data);
  92.  
  93.   glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE);
  94.  
  95.   glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
  96.   glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
  97. }
  98.  
  99. /*
  100. ===============
  101. R_Envmap_f
  102.  
  103. Grab six views for environment mapping tests
  104. ===============
  105. */
  106. void R_Envmap_f (void)
  107. {
  108.   byte  buffer[256*256*4];
  109.   char  name[1024];
  110.  
  111.   glDrawBuffer  (GL_FRONT);
  112.   glReadBuffer  (GL_FRONT);
  113.   envmap = true;
  114.  
  115.   r_refdef.vrect.x = 0;
  116.   r_refdef.vrect.y = 0;
  117.   r_refdef.vrect.width = 256;
  118.   r_refdef.vrect.height = 256;
  119.  
  120.   r_refdef.viewangles[0] = 0;
  121.   r_refdef.viewangles[1] = 0;
  122.   r_refdef.viewangles[2] = 0;
  123.   GL_BeginRendering (&glx, &gly, &glwidth, &glheight);
  124.   R_RenderView ();
  125.   glReadPixels (0, 0, 256, 256, GL_RGBA, GL_UNSIGNED_BYTE, buffer);
  126.   COM_WriteFile ("env0.rgb", buffer, sizeof(buffer));   
  127.  
  128.   r_refdef.viewangles[1] = 90;
  129.   GL_BeginRendering (&glx, &gly, &glwidth, &glheight);
  130.   R_RenderView ();
  131.   glReadPixels (0, 0, 256, 256, GL_RGBA, GL_UNSIGNED_BYTE, buffer);
  132.   COM_WriteFile ("env1.rgb", buffer, sizeof(buffer));   
  133.  
  134.   r_refdef.viewangles[1] = 180;
  135.   GL_BeginRendering (&glx, &gly, &glwidth, &glheight);
  136.   R_RenderView ();
  137.   glReadPixels (0, 0, 256, 256, GL_RGBA, GL_UNSIGNED_BYTE, buffer);
  138.   COM_WriteFile ("env2.rgb", buffer, sizeof(buffer));   
  139.  
  140.   r_refdef.viewangles[1] = 270;
  141.   GL_BeginRendering (&glx, &gly, &glwidth, &glheight);
  142.   R_RenderView ();
  143.   glReadPixels (0, 0, 256, 256, GL_RGBA, GL_UNSIGNED_BYTE, buffer);
  144.   COM_WriteFile ("env3.rgb", buffer, sizeof(buffer));   
  145.  
  146.   r_refdef.viewangles[0] = -90;
  147.   r_refdef.viewangles[1] = 0;
  148.   GL_BeginRendering (&glx, &gly, &glwidth, &glheight);
  149.   R_RenderView ();
  150.   glReadPixels (0, 0, 256, 256, GL_RGBA, GL_UNSIGNED_BYTE, buffer);
  151.   COM_WriteFile ("env4.rgb", buffer, sizeof(buffer));   
  152.  
  153.   r_refdef.viewangles[0] = 90;
  154.   r_refdef.viewangles[1] = 0;
  155.   GL_BeginRendering (&glx, &gly, &glwidth, &glheight);
  156.   R_RenderView ();
  157.   glReadPixels (0, 0, 256, 256, GL_RGBA, GL_UNSIGNED_BYTE, buffer);
  158.   COM_WriteFile ("env5.rgb", buffer, sizeof(buffer));   
  159.  
  160.   envmap = false;
  161.   glDrawBuffer  (GL_BACK);
  162.   glReadBuffer  (GL_BACK);
  163.   GL_EndRendering ();
  164. }
  165.  
  166. /*
  167. ===============
  168. R_Init
  169. ===============
  170. */
  171. void R_Init (void)
  172.   extern byte *hunk_base;
  173.   extern cvar_t gl_finish;
  174.  
  175.   Cmd_AddCommand ("timerefresh", R_TimeRefresh_f);  
  176.   Cmd_AddCommand ("envmap", R_Envmap_f);  
  177.   Cmd_AddCommand ("pointfile", R_ReadPointFile_f);  
  178.  
  179.   Cvar_RegisterVariable (&r_norefresh);
  180.   Cvar_RegisterVariable (&r_lightmap);
  181.   Cvar_RegisterVariable (&r_fullbright);
  182.   Cvar_RegisterVariable (&r_drawentities);
  183.   Cvar_RegisterVariable (&r_drawviewmodel);
  184.   Cvar_RegisterVariable (&r_shadows);
  185.   Cvar_RegisterVariable (&r_mirroralpha);
  186.   Cvar_RegisterVariable (&r_wateralpha);
  187.   Cvar_RegisterVariable (&r_dynamic);
  188.   Cvar_RegisterVariable (&r_novis);
  189.   Cvar_RegisterVariable (&r_speeds);
  190.  
  191.   Cvar_RegisterVariable (&gl_finish);
  192.   Cvar_RegisterVariable (&gl_clear);
  193.   Cvar_RegisterVariable (&gl_texsort);
  194.  
  195.   if (gl_mtexable)
  196.     Cvar_SetValue ("gl_texsort", 0.0);
  197.  
  198.   Cvar_RegisterVariable (&gl_cull);
  199.   Cvar_RegisterVariable (&gl_smoothmodels);
  200.   Cvar_RegisterVariable (&gl_affinemodels);
  201.   Cvar_RegisterVariable (&gl_polyblend);
  202.   Cvar_RegisterVariable (&gl_flashblend);
  203.   Cvar_RegisterVariable (&gl_playermip);
  204.   Cvar_RegisterVariable (&gl_nocolors);
  205.  
  206.   Cvar_RegisterVariable (&gl_keeptjunctions);
  207.   Cvar_RegisterVariable (&gl_reporttjunctions);
  208.  
  209.   Cvar_RegisterVariable (&gl_doubleeyes);
  210.  
  211.   R_InitParticles ();
  212.   R_InitParticleTexture ();
  213.  
  214. #ifdef GLTEST
  215.   Test_Init ();
  216. #endif
  217.  
  218.   playertextures = texture_extension_number;
  219.   texture_extension_number += 16;
  220. }
  221.  
  222. /*
  223. ===============
  224. R_TranslatePlayerSkin
  225.  
  226. Translates a skin texture by the per-player color lookup
  227. ===============
  228. */
  229. void R_TranslatePlayerSkin (int playernum)
  230. {
  231.   int   top, bottom;
  232.   byte  translate[256];
  233.   unsigned  translate32[256];
  234.   int   i, j, s;
  235.   model_t *model;
  236.   aliashdr_t *paliashdr;
  237.   byte  *original;
  238.   unsigned  pixels[512*256], *out;
  239.   unsigned  scaled_width, scaled_height;
  240.   int     inwidth, inheight;
  241.   byte    *inrow;
  242.   unsigned  frac, fracstep;
  243.   extern  byte    **player_8bit_texels_tbl;
  244.  
  245.   GL_DisableMultitexture();
  246.  
  247.   top = cl.scores[playernum].colors & 0xf0;
  248.   bottom = (cl.scores[playernum].colors &15)<<4;
  249.  
  250.   for (i=0 ; i<256 ; i++)
  251.     translate[i] = i;
  252.  
  253.   for (i=0 ; i<16 ; i++)
  254.   {
  255.     if (top < 128)  // the artists made some backwards ranges.  sigh.
  256.       translate[TOP_RANGE+i] = top+i;
  257.     else
  258.       translate[TOP_RANGE+i] = top+15-i;
  259.         
  260.     if (bottom < 128)
  261.       translate[BOTTOM_RANGE+i] = bottom+i;
  262.     else
  263.       translate[BOTTOM_RANGE+i] = bottom+15-i;
  264.   }
  265.  
  266.   //
  267.   // locate the original skin pixels
  268.   //
  269.   currententity = &cl_entities[1+playernum];
  270.   model = currententity->model;
  271.   if (!model)
  272.     return;   // player doesn't have a model yet
  273.   if (model->type != mod_alias)
  274.     return; // only translate skins on alias models
  275.  
  276.   paliashdr = (aliashdr_t *)Mod_Extradata (model);
  277.   s = paliashdr->skinwidth * paliashdr->skinheight;
  278.   if (currententity->skinnum < 0 || currententity->skinnum >= paliashdr->numskins) {
  279.     Con_Printf("(%d): Invalid player skin #%d\n", playernum, currententity->skinnum);
  280.     original = (byte *)paliashdr + paliashdr->texels[0];
  281.   } else
  282.     original = (byte *)paliashdr + paliashdr->texels[currententity->skinnum];
  283.   if (s & 3)
  284.     Sys_Error ("R_TranslateSkin: s&3");
  285.  
  286.   inwidth = paliashdr->skinwidth;
  287.   inheight = paliashdr->skinheight;
  288.  
  289.   // because this happens during gameplay, do it fast
  290.   // instead of sending it through gl_upload 8
  291.     GL_Bind(playertextures + playernum);
  292.  
  293. #if 0
  294.   byte  translated[320*200];
  295.  
  296.   for (i=0 ; i<s ; i+=4)
  297.   {
  298.     translated[i] = translate[original[i]];
  299.     translated[i+1] = translate[original[i+1]];
  300.     translated[i+2] = translate[original[i+2]];
  301.     translated[i+3] = translate[original[i+3]];
  302.   }
  303.  
  304.  
  305.   // don't mipmap these, because it takes too long
  306.   GL_Upload8 (translated, paliashdr->skinwidth, paliashdr->skinheight, false, false, true);
  307. #else
  308.   scaled_width = gl_max_size.value < 512 ? gl_max_size.value : 512;
  309.   scaled_height = gl_max_size.value < 256 ? gl_max_size.value : 256;
  310.  
  311.   // allow users to crunch sizes down even more if they want
  312.   scaled_width >>= (int)gl_playermip.value;
  313.   scaled_height >>= (int)gl_playermip.value;
  314.  
  315.   if (VID_Is8bit()) { // 8bit texture upload
  316.     byte *out2;
  317.  
  318.     out2 = (byte *)pixels;
  319.     memset(pixels, 0, sizeof(pixels));
  320.     fracstep = inwidth*0x10000/scaled_width;
  321.     for (i=0 ; i<scaled_height ; i++, out2 += scaled_width)
  322.     {
  323.       inrow = original + inwidth*(i*inheight/scaled_height);
  324.       frac = fracstep >> 1;
  325.       for (j=0 ; j<scaled_width ; j+=4)
  326.       {
  327.         out2[j] = translate[inrow[frac>>16]];
  328.         frac += fracstep;
  329.         out2[j+1] = translate[inrow[frac>>16]];
  330.         frac += fracstep;
  331.         out2[j+2] = translate[inrow[frac>>16]];
  332.         frac += fracstep;
  333.         out2[j+3] = translate[inrow[frac>>16]];
  334.         frac += fracstep;
  335.       }
  336.     }
  337.  
  338.     GL_Upload8_EXT ((byte *)pixels, scaled_width, scaled_height, false, false);
  339.     return;
  340.   }
  341.  
  342.   for (i=0 ; i<256 ; i++)
  343.     translate32[i] = d_8to24table[translate[i]];
  344.  
  345.   out = pixels;
  346.   fracstep = inwidth*0x10000/scaled_width;
  347.   for (i=0 ; i<scaled_height ; i++, out += scaled_width)
  348.   {
  349.     inrow = original + inwidth*(i*inheight/scaled_height);
  350.     frac = fracstep >> 1;
  351.     for (j=0 ; j<scaled_width ; j+=4)
  352.     {
  353.       out[j] = translate32[inrow[frac>>16]];
  354.       frac += fracstep;
  355.       out[j+1] = translate32[inrow[frac>>16]];
  356.       frac += fracstep;
  357.       out[j+2] = translate32[inrow[frac>>16]];
  358.       frac += fracstep;
  359.       out[j+3] = translate32[inrow[frac>>16]];
  360.       frac += fracstep;
  361.     }
  362.   }
  363.   glTexImage2D (GL_TEXTURE_2D, 0, gl_solid_format, scaled_width, scaled_height, 0, GL_RGBA, GL_UNSIGNED_BYTE, pixels);
  364.  
  365.   glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_MODULATE);
  366.   glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
  367.   glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
  368. #endif
  369.  
  370. }
  371.  
  372.  
  373. /*
  374. ===============
  375. R_NewMap
  376. ===============
  377. */
  378. void R_NewMap (void)
  379. {
  380.   int   i;
  381.   
  382.   for (i=0 ; i<256 ; i++)
  383.     d_lightstylevalue[i] = 264;   // normal light value
  384.  
  385.   memset (&r_worldentity, 0, sizeof(r_worldentity));
  386.   r_worldentity.model = cl.worldmodel;
  387.  
  388. // clear out efrags in case the level hasn't been reloaded
  389. // FIXME: is this one short?
  390.   for (i=0 ; i<cl.worldmodel->numleafs ; i++)
  391.     cl.worldmodel->leafs[i].efrags = NULL;
  392.       
  393.   r_viewleaf = NULL;
  394.   R_ClearParticles ();
  395.  
  396.   GL_BuildLightmaps ();
  397.  
  398.   // identify sky texture
  399.   skytexturenum = -1;
  400.   mirrortexturenum = -1;
  401.   for (i=0 ; i<cl.worldmodel->numtextures ; i++)
  402.   {
  403.     if (!cl.worldmodel->textures[i])
  404.       continue;
  405.     if (!Q_strncmp(cl.worldmodel->textures[i]->name,"sky",3) )
  406.       skytexturenum = i;
  407.     if (!Q_strncmp(cl.worldmodel->textures[i]->name,"window02_1",10) )
  408.       mirrortexturenum = i;
  409.     cl.worldmodel->textures[i]->texturechain = NULL;
  410.   }
  411. #ifdef QUAKE2
  412.   R_LoadSkys ();
  413. #endif
  414. }
  415.  
  416.  
  417. /*
  418. ====================
  419. R_TimeRefresh_f
  420.  
  421. For program optimization
  422. ====================
  423. */
  424. void R_TimeRefresh_f (void)
  425. {
  426.   int     i;
  427.   float   start, stop, time;
  428.   int     startangle;
  429.   vrect_t   vr;
  430.  
  431.   glDrawBuffer  (GL_FRONT);
  432.   glFinish ();
  433.  
  434.   start = Sys_FloatTime ();
  435.   for (i=0 ; i<128 ; i++)
  436.   {
  437.     r_refdef.viewangles[1] = i/128.0*360.0;
  438.     R_RenderView ();
  439.   }
  440.  
  441.   glFinish ();
  442.   stop = Sys_FloatTime ();
  443.   time = stop-start;
  444.   Con_Printf ("%f seconds (%f fps)\n", time, 128/time);
  445.  
  446.   glDrawBuffer  (GL_BACK);
  447.   GL_EndRendering ();
  448. }
  449.  
  450. void D_FlushCaches (void)
  451. {
  452. }
  453.  
  454.  
  455.