diff --git a/AUTHORS b/AUTHORS index a5b88cd..0dde9e7 100644 --- a/AUTHORS +++ b/AUTHORS @@ -12,6 +12,7 @@ QW/Q1 tree merging: Jeff Teunissen Zephaniah E. Hull Marcus Sundberg + Bill Currie Autoconf support: Loring Holden diff --git a/uquake/gl_rmain.c b/common/gl_rmain.c similarity index 92% rename from uquake/gl_rmain.c rename to common/gl_rmain.c index c5ee392..4d4bf0c 100644 --- a/uquake/gl_rmain.c +++ b/common/gl_rmain.c @@ -84,7 +84,11 @@ cvar_t r_mirroralpha = {"r_mirroralpha","1"}; cvar_t r_wateralpha = {"r_wateralpha","1"}; cvar_t r_dynamic = {"r_dynamic","1"}; cvar_t r_novis = {"r_novis","0"}; +#ifdef QUAKEWORLD +cvar_t r_netgraph = {"r_netgraph","0"}; +#else cvar_t r_fog = {"r_fog", "0"}; +#endif cvar_t gl_finish = {"gl_finish","0"}; cvar_t gl_clear = {"gl_clear","0"}; @@ -96,12 +100,18 @@ cvar_t gl_polyblend = {"gl_polyblend","1"}; cvar_t gl_flashblend = {"gl_flashblend","1"}; cvar_t gl_playermip = {"gl_playermip","0"}; cvar_t gl_nocolors = {"gl_nocolors","0"}; -cvar_t gl_keeptjunctions = {"gl_keeptjunctions","0"}; +#ifdef QUAKEWORLD +cvar_t gl_keeptjunctions = {"gl_keeptjunctions","1"}; cvar_t gl_reporttjunctions = {"gl_reporttjunctions","0"}; +#else +cvar_t gl_keeptjunctions = {"gl_keeptjunctions","0"}; cvar_t gl_doubleeyes = {"gl_doubleeys", "1"}; +#endif extern cvar_t gl_ztrick; - +#ifdef QUAKEWORLD +extern cvar_t scr_fov; +#endif /* ================= R_CullBox @@ -126,6 +136,7 @@ void R_RotateForEntity (entity_t *e) glRotatef (e->angles[1], 0, 0, 1); glRotatef (-e->angles[0], 0, 1, 0); + //ZOID: fixed z angle glRotatef (e->angles[2], 1, 0, 0); } @@ -229,6 +240,11 @@ void R_DrawSpriteModel (entity_t *e) glEnable (GL_ALPHA_TEST); glBegin (GL_QUADS); +#ifdef QUAKEWORLD + glEnable (GL_ALPHA_TEST); + glBegin (GL_QUADS); +#endif + glTexCoord2f (0, 1); VectorMA (e->origin, frame->down, up, point); VectorMA (point, frame->left, right, point); @@ -491,14 +507,18 @@ void R_DrawAliasModel (entity_t *e) shadelight = 192 - ambientlight; // ZOID: never allow players to go totally black +#ifdef QUAKEWORLD + if (!strcmp(clmodel->name, "progs/player.mdl")) { +#else i = currententity - cl_entities; if (i >= 1 && i<=cl.maxclients /* && !strcmp (currententity->model->name, "progs/player.mdl") */) +#endif if (ambientlight < 8) ambientlight = shadelight = 8; - // HACK HACK HACK -- no fullbright colors, so make torches full light - if (!strcmp (clmodel->name, "progs/flame2.mdl") + } else if (!strcmp (clmodel->name, "progs/flame2.mdl") || !strcmp (clmodel->name, "progs/flame.mdl") ) + // HACK HACK HACK -- no fullbright colors, so make torches full light ambientlight = shadelight = 256; shadedots = r_avertexnormal_dots[((int)(e->angles[1] * (SHADEDOT_QUANT / 360.0))) & (SHADEDOT_QUANT - 1)]; @@ -526,9 +546,13 @@ void R_DrawAliasModel (entity_t *e) glPushMatrix (); R_RotateForEntity (e); - if (!strcmp (clmodel->name, "progs/eyes.mdl") && gl_doubleeyes.value) { +#ifdef QUAKEWORLD + if (!strcmp (clmodel->name, "progs/eyes.mdl") ) { +#else + if (!strcmp (clmodel->name, "progs/eyes.mdl" && gl_doubleeyes.value) ) { +#endif glTranslatef (paliashdr->scale_origin[0], paliashdr->scale_origin[1], paliashdr->scale_origin[2] - (22 + 8)); -// double size of eyes, since they are really hard to see in gl + // double size of eyes, since they are really hard to see in gl glScalef (paliashdr->scale[0]*2, paliashdr->scale[1]*2, paliashdr->scale[2]*2); } else { glTranslatef (paliashdr->scale_origin[0], paliashdr->scale_origin[1], paliashdr->scale_origin[2]); @@ -540,12 +564,25 @@ void R_DrawAliasModel (entity_t *e) // we can't dynamically colormap textures, so they are cached // seperately for the players. Heads are just uncolored. +#ifdef QUAKEWORLD + if (currententity->scoreboard && !gl_nocolors.value) + { + i = currententity->scoreboard - cl.players; + if (!currententity->scoreboard->skin) { + Skin_Find(currententity->scoreboard); + R_TranslatePlayerSkin(i); + } + if (i >= 0 && icolormap != vid.colormap && !gl_nocolors.value) { i = currententity - cl_entities; if (i >= 1 && i<=cl.maxclients /* && !strcmp (currententity->model->name, "progs/player.mdl") */) GL_Bind(playertextures - 1 + i); } +#endif if (gl_smoothmodels.value) glShadeModel (GL_SMOOTH); @@ -597,7 +634,11 @@ void R_DrawEntitiesOnList (void) // draw sprites seperately, because of alpha blending for (i=0 ; imodel->type) { @@ -616,13 +657,20 @@ void R_DrawEntitiesOnList (void) for (i=0 ; imodel->type) { case mod_sprite: R_DrawSpriteModel (currententity); break; + + default : + break; } } } @@ -642,20 +690,29 @@ void R_DrawViewModel (void) dlight_t *dl; int ambientlight, shadelight; +#ifdef QUAKEWORLD + if (!r_drawviewmodel.value || !Cam_DrawViewModel()) + return; +#else if (!r_drawviewmodel.value) return; if (chase_active.value) return; +#endif if (envmap) return; if (!r_drawentities.value) return; - +#ifdef QUAKEWORLD + if (cl.stats[STAT_ITEMS] & IT_INVISIBILITY) + return; +#else if (cl.items & IT_INVISIBILITY) return; +#endif if (cl.stats[STAT_HEALTH] <= 0) return; @@ -798,8 +855,15 @@ R_SetupFrame void R_SetupFrame (void) { // don't allow cheats in multiplayer +#ifdef QUAKEWORLD + r_fullbright.value = 0; + r_lightmap.value = 0; + if (!atoi(Info_ValueForKey(cl.serverinfo, "watervis"))) + r_wateralpha.value = 1; +#else if (cl.maxclients > 1) Cvar_Set ("r_fullbright", "0"); +#endif R_AnimateLight (); @@ -884,6 +948,9 @@ void R_SetupGL (void) glViewport (glx + x, gly + y2, w, h); screenaspect = (float)r_refdef.vrect.width/r_refdef.vrect.height; // yfov = 2*atan((float)r_refdef.vrect.height/r_refdef.vrect.width)*180/M_PI; +// yfov = (2.0 * tan (scr_fov.value/360*M_PI)) / screenaspect; +// yfov = 2*atan((float)r_refdef.vrect.height/r_refdef.vrect.width)*(scr_fov.value*2)/M_PI; +// MYgluPerspective (yfov, screenaspect, 4, 4096); MYgluPerspective (r_refdef.fov_y, screenaspect, 4, 4096); if (mirror) @@ -1010,6 +1077,7 @@ void R_Clear (void) glDepthRange (gldepthmin, gldepthmax); } +#ifndef QUAKEWORLD //!!! FIXME, Zoid, mirror is disabled for now /* ============= R_Mirror @@ -1076,6 +1144,7 @@ void R_Mirror (void) glDisable (GL_BLEND); glColor4f (1,1,1,1); } +#endif /* ================ @@ -1087,9 +1156,10 @@ r_refdef must be set before the first call void R_RenderView (void) { double time1 = 0, time2 = 0; - +#ifndef QUAKEWORLD // Fixme: the last argument should be a cvar... r_fog_gamma GLfloat colors[4] = {(GLfloat) 0.0, (GLfloat) 0.0, (GLfloat) 1, (GLfloat) 0.15}; +#endif if (r_norefresh.value) return; @@ -1113,6 +1183,8 @@ void R_RenderView (void) R_Clear (); // render normal view +#ifndef QUAKEWORLD + // XXX /***** Experimental silly looking fog ****** ****** Use r_fullbright if you enable ****** @@ -1136,18 +1208,19 @@ if(r_fog.value) { glFogf (GL_FOG_DENSITY, .0005); glEnable(GL_FOG); } - +#endif R_RenderScene (); R_DrawViewModel (); R_DrawWaterSurfaces (); +#ifndef QUAKEWORLD // More fog right here :) glDisable(GL_FOG); // End of all fog code... // render mirror view R_Mirror (); - +#endif R_PolyBlend (); if (r_speeds.value) diff --git a/qw_client/gl_rmain.c b/qw_client/gl_rmain.c deleted file mode 100644 index 48a5a54..0000000 --- a/qw_client/gl_rmain.c +++ /dev/null @@ -1,1144 +0,0 @@ -/* -Copyright (C) 1996-1997 Id Software, Inc. - -This program is free software; you can redistribute it and/or -modify it under the terms of the GNU General Public License -as published by the Free Software Foundation; either version 2 -of the License, or (at your option) any later version. - -This program is distributed in the hope that it will be useful, -but WITHOUT ANY WARRANTY; without even the implied warranty of -MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. - -See the GNU General Public License for more details. - -You should have received a copy of the GNU General Public License -along with this program; if not, write to the Free Software -Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. - -*/ -// r_main.c - -#include "quakedef.h" - -entity_t r_worldentity; - -qboolean r_cache_thrash; // compatability - -vec3_t modelorg, r_entorigin; -entity_t *currententity; - -int r_visframecount; // bumped when going to a new PVS -int r_framecount; // used for dlight push checking - -mplane_t frustum[4]; - -int c_brush_polys, c_alias_polys; - -qboolean envmap; // true during envmap command capture - -int currenttexture = -1; // to avoid unnecessary texture sets - -int cnttextures[2] = {-1, -1}; // cached - -int particletexture; // little dot for particles -int playertextures; // up to 16 color translated skins - -int mirrortexturenum; // quake texturenum, not gltexturenum -qboolean mirror; -mplane_t *mirror_plane; - -// -// view origin -// -vec3_t vup; -vec3_t vpn; -vec3_t vright; -vec3_t r_origin; - -float r_world_matrix[16]; -float r_base_world_matrix[16]; - -// -// screen size info -// -refdef_t r_refdef; - -mleaf_t *r_viewleaf, *r_oldviewleaf; - -texture_t *r_notexture_mip; - -int d_lightstylevalue[256]; // 8.8 fraction of base light value - - -void R_MarkLeaves (void); - -cvar_t r_norefresh = {"r_norefresh","0"}; -cvar_t r_drawentities = {"r_drawentities","1"}; -cvar_t r_drawviewmodel = {"r_drawviewmodel","1"}; -cvar_t r_speeds = {"r_speeds","0"}; -cvar_t r_fullbright = {"r_fullbright","0"}; -cvar_t r_lightmap = {"r_lightmap","0"}; -cvar_t r_shadows = {"r_shadows","0"}; -cvar_t r_mirroralpha = {"r_mirroralpha","1"}; -cvar_t r_wateralpha = {"r_wateralpha","1"}; -cvar_t r_dynamic = {"r_dynamic","1"}; -cvar_t r_novis = {"r_novis","0"}; -cvar_t r_netgraph = {"r_netgraph","0"}; - -cvar_t gl_clear = {"gl_clear","0"}; -cvar_t gl_cull = {"gl_cull","1"}; -cvar_t gl_texsort = {"gl_texsort","1"}; -cvar_t gl_smoothmodels = {"gl_smoothmodels","1"}; -cvar_t gl_affinemodels = {"gl_affinemodels","0"}; -cvar_t gl_polyblend = {"gl_polyblend","1"}; -cvar_t gl_flashblend = {"gl_flashblend","1"}; -cvar_t gl_playermip = {"gl_playermip","0"}; -cvar_t gl_nocolors = {"gl_nocolors","0"}; -cvar_t gl_keeptjunctions = {"gl_keeptjunctions","1"}; -cvar_t gl_reporttjunctions = {"gl_reporttjunctions","0"}; -cvar_t gl_finish = {"gl_finish","0"}; - -extern cvar_t gl_ztrick; -extern cvar_t scr_fov; -/* -================= -R_CullBox - -Returns true if the box is completely outside the frustom -================= -*/ -qboolean R_CullBox (vec3_t mins, vec3_t maxs) -{ - int i; - - for (i=0 ; i<4 ; i++) - if (BoxOnPlaneSide (mins, maxs, &frustum[i]) == 2) - return true; - return false; -} - - -void R_RotateForEntity (entity_t *e) -{ - glTranslatef (e->origin[0], e->origin[1], e->origin[2]); - - glRotatef (e->angles[1], 0, 0, 1); - glRotatef (-e->angles[0], 0, 1, 0); - //ZOID: fixed z angle - glRotatef (e->angles[2], 1, 0, 0); -} - -/* -============================================================= - - SPRITE MODELS - -============================================================= -*/ - -/* -================ -R_GetSpriteFrame -================ -*/ -mspriteframe_t *R_GetSpriteFrame (entity_t *currententity) -{ - msprite_t *psprite; - mspritegroup_t *pspritegroup; - mspriteframe_t *pspriteframe; - int i, numframes, frame; - float *pintervals, fullinterval, targettime, time; - - psprite = currententity->model->cache.data; - frame = currententity->frame; - - if ((frame >= psprite->numframes) || (frame < 0)) - { - Con_Printf ("R_DrawSprite: no such frame %d\n", frame); - frame = 0; - } - - if (psprite->frames[frame].type == SPR_SINGLE) - { - pspriteframe = psprite->frames[frame].frameptr; - } - else - { - pspritegroup = (mspritegroup_t *)psprite->frames[frame].frameptr; - pintervals = pspritegroup->intervals; - numframes = pspritegroup->numframes; - fullinterval = pintervals[numframes-1]; - - time = cl.time + currententity->syncbase; - - // when loading in Mod_LoadSpriteGroup, we guaranteed all interval values - // are positive, so we don't have to worry about division by 0 - targettime = time - ((int)(time / fullinterval)) * fullinterval; - - for (i=0 ; i<(numframes-1) ; i++) - { - if (pintervals[i] > targettime) - break; - } - - pspriteframe = pspritegroup->frames[i]; - } - - return pspriteframe; -} - - -/* -================= -R_DrawSpriteModel - -================= -*/ -void R_DrawSpriteModel (entity_t *e) -{ - vec3_t point; - mspriteframe_t *frame; - float *up, *right; - vec3_t v_forward, v_right, v_up; - msprite_t *psprite; - - // don't even bother culling, because it's just a single - // polygon without a surface cache - frame = R_GetSpriteFrame (e); - psprite = currententity->model->cache.data; - - if (psprite->type == SPR_ORIENTED) - { // bullet marks on walls - AngleVectors (currententity->angles, v_forward, v_right, v_up); - up = v_up; - right = v_right; - } - else - { // normal sprite - up = vup; - right = vright; - } - - glColor3f (1,1,1); - - GL_DisableMultitexture(); - - GL_Bind(frame->gl_texturenum); - - glEnable (GL_ALPHA_TEST); - glBegin (GL_QUADS); - - glEnable (GL_ALPHA_TEST); - glBegin (GL_QUADS); - - glTexCoord2f (0, 1); - VectorMA (e->origin, frame->down, up, point); - VectorMA (point, frame->left, right, point); - glVertex3fv (point); - - glTexCoord2f (0, 0); - VectorMA (e->origin, frame->up, up, point); - VectorMA (point, frame->left, right, point); - glVertex3fv (point); - - glTexCoord2f (1, 0); - VectorMA (e->origin, frame->up, up, point); - VectorMA (point, frame->right, right, point); - glVertex3fv (point); - - glTexCoord2f (1, 1); - VectorMA (e->origin, frame->down, up, point); - VectorMA (point, frame->right, right, point); - glVertex3fv (point); - - glEnd (); - - glDisable (GL_ALPHA_TEST); -} - -/* -============================================================= - - ALIAS MODELS - -============================================================= -*/ - - -#define NUMVERTEXNORMALS 162 - -float r_avertexnormals[NUMVERTEXNORMALS][3] = { -#include "anorms.h" -}; - -vec3_t shadevector; -float shadelight, ambientlight; - -// precalculated dot products for quantized angles -#define SHADEDOT_QUANT 16 -float r_avertexnormal_dots[SHADEDOT_QUANT][256] = -#include "anorm_dots.h" -; - -float *shadedots = r_avertexnormal_dots[0]; - -int lastposenum; - -/* -============= -GL_DrawAliasFrame -============= -*/ -void GL_DrawAliasFrame (aliashdr_t *paliashdr, int posenum) -{ - float l; - trivertx_t *verts; - int *order; - int count; - -lastposenum = posenum; - - verts = (trivertx_t *)((byte *)paliashdr + paliashdr->posedata); - verts += posenum * paliashdr->poseverts; - order = (int *)((byte *)paliashdr + paliashdr->commands); - - while (1) - { - // get the vertex count and primitive type - count = *order++; - if (!count) - break; // done - if (count < 0) - { - count = -count; - glBegin (GL_TRIANGLE_FAN); - } - else - glBegin (GL_TRIANGLE_STRIP); - - do - { - // texture coordinates come from the draw list - glTexCoord2f (((float *)order)[0], ((float *)order)[1]); - order += 2; - - // normals and vertexes come from the frame list - l = shadedots[verts->lightnormalindex] * shadelight; - glColor3f (l, l, l); - glVertex3f (verts->v[0], verts->v[1], verts->v[2]); - verts++; - } while (--count); - - glEnd (); - } -} - - -/* -============= -GL_DrawAliasShadow -============= -*/ -extern vec3_t lightspot; - -void GL_DrawAliasShadow (aliashdr_t *paliashdr, int posenum) -{ - trivertx_t *verts; - int *order; - vec3_t point; - float height, lheight; - int count; - - lheight = currententity->origin[2] - lightspot[2]; - - height = 0; - verts = (trivertx_t *)((byte *)paliashdr + paliashdr->posedata); - verts += posenum * paliashdr->poseverts; - order = (int *)((byte *)paliashdr + paliashdr->commands); - - height = -lheight + 1.0; - - while (1) - { - // get the vertex count and primitive type - count = *order++; - if (!count) - break; // done - if (count < 0) - { - count = -count; - glBegin (GL_TRIANGLE_FAN); - } - else - glBegin (GL_TRIANGLE_STRIP); - - do - { - // texture coordinates come from the draw list - // (skipped for shadows) glTexCoord2fv ((float *)order); - order += 2; - - // normals and vertexes come from the frame list - point[0] = verts->v[0] * paliashdr->scale[0] + paliashdr->scale_origin[0]; - point[1] = verts->v[1] * paliashdr->scale[1] + paliashdr->scale_origin[1]; - point[2] = verts->v[2] * paliashdr->scale[2] + paliashdr->scale_origin[2]; - - point[0] -= shadevector[0]*(point[2]+lheight); - point[1] -= shadevector[1]*(point[2]+lheight); - point[2] = height; -// height -= 0.001; - glVertex3fv (point); - - verts++; - } while (--count); - - glEnd (); - } -} - - - -/* -================= -R_SetupAliasFrame - -================= -*/ -void R_SetupAliasFrame (int frame, aliashdr_t *paliashdr) -{ - int pose, numposes; - float interval; - - if ((frame >= paliashdr->numframes) || (frame < 0)) - { - Con_DPrintf ("R_AliasSetupFrame: no such frame %d\n", frame); - frame = 0; - } - - pose = paliashdr->frames[frame].firstpose; - numposes = paliashdr->frames[frame].numposes; - - if (numposes > 1) - { - interval = paliashdr->frames[frame].interval; - pose += (int)(cl.time / interval) % numposes; - } - - GL_DrawAliasFrame (paliashdr, pose); -} - - - -/* -================= -R_DrawAliasModel - -================= -*/ -void R_DrawAliasModel (entity_t *e) -{ - int i; - int lnum; - vec3_t dist; - float add; - model_t *clmodel; - vec3_t mins, maxs; - aliashdr_t *paliashdr; - float an; - int anim; - - clmodel = currententity->model; - - VectorAdd (currententity->origin, clmodel->mins, mins); - VectorAdd (currententity->origin, clmodel->maxs, maxs); - - if (R_CullBox (mins, maxs)) - return; - - - VectorCopy (currententity->origin, r_entorigin); - VectorSubtract (r_origin, r_entorigin, modelorg); - - // - // get lighting information - // - - ambientlight = shadelight = R_LightPoint (currententity->origin); - - // allways give the gun some light - if (e == &cl.viewent && ambientlight < 24) - ambientlight = shadelight = 24; - - for (lnum=0 ; lnum= cl.time) - { - VectorSubtract (currententity->origin, - cl_dlights[lnum].origin, - dist); - add = cl_dlights[lnum].radius - Length(dist); - - if (add > 0) { - ambientlight += add; - //ZOID models should be affected by dlights as well - shadelight += add; - } - } - } - - // clamp lighting so it doesn't overbright as much - if (ambientlight > 128) - ambientlight = 128; - if (ambientlight + shadelight > 192) - shadelight = 192 - ambientlight; - - // ZOID: never allow players to go totally black - if (!strcmp(clmodel->name, "progs/player.mdl")) { - if (ambientlight < 8) - ambientlight = shadelight = 8; - - } else if (!strcmp (clmodel->name, "progs/flame2.mdl") - || !strcmp (clmodel->name, "progs/flame.mdl") ) - // HACK HACK HACK -- no fullbright colors, so make torches full light - ambientlight = shadelight = 256; - - shadedots = r_avertexnormal_dots[((int)(e->angles[1] * (SHADEDOT_QUANT / 360.0))) & (SHADEDOT_QUANT - 1)]; - shadelight = shadelight / 200.0; - - an = e->angles[1]/180*M_PI; - shadevector[0] = cos(-an); - shadevector[1] = sin(-an); - shadevector[2] = 1; - VectorNormalize (shadevector); - - // - // locate the proper data - // - paliashdr = (aliashdr_t *)Mod_Extradata (currententity->model); - - c_alias_polys += paliashdr->numtris; - - // - // draw all the triangles - // - - GL_DisableMultitexture(); - - glPushMatrix (); - R_RotateForEntity (e); - - if (!strcmp (clmodel->name, "progs/eyes.mdl") ) { - glTranslatef (paliashdr->scale_origin[0], paliashdr->scale_origin[1], paliashdr->scale_origin[2] - (22 + 8)); - // double size of eyes, since they are really hard to see in gl - glScalef (paliashdr->scale[0]*2, paliashdr->scale[1]*2, paliashdr->scale[2]*2); - } else { - glTranslatef (paliashdr->scale_origin[0], paliashdr->scale_origin[1], paliashdr->scale_origin[2]); - glScalef (paliashdr->scale[0], paliashdr->scale[1], paliashdr->scale[2]); - } - - anim = (int)(cl.time*10) & 3; - GL_Bind(paliashdr->gl_texturenum[currententity->skinnum][anim]); - - // we can't dynamically colormap textures, so they are cached - // seperately for the players. Heads are just uncolored. - if (currententity->scoreboard && !gl_nocolors.value) - { - i = currententity->scoreboard - cl.players; - if (!currententity->scoreboard->skin) { - Skin_Find(currententity->scoreboard); - R_TranslatePlayerSkin(i); - } - if (i >= 0 && iframe, paliashdr); - - glTexEnvf(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE); - - glShadeModel (GL_FLAT); - if (gl_affinemodels.value) - glHint (GL_PERSPECTIVE_CORRECTION_HINT, GL_NICEST); - - glPopMatrix (); - - if (r_shadows.value) - { - glPushMatrix (); - R_RotateForEntity (e); - glDisable (GL_TEXTURE_2D); - glEnable (GL_BLEND); - glColor4f (0,0,0,0.5); - GL_DrawAliasShadow (paliashdr, lastposenum); - glEnable (GL_TEXTURE_2D); - glDisable (GL_BLEND); - glColor4f (1,1,1,1); - glPopMatrix (); - } - -} - -//================================================================================== - -/* -============= -R_DrawEntitiesOnList -============= -*/ -void R_DrawEntitiesOnList (void) -{ - int i; - - if (!r_drawentities.value) - return; - - // draw sprites seperately, because of alpha blending - for (i=0 ; imodel->type) - { - case mod_alias: - R_DrawAliasModel (currententity); - break; - - case mod_brush: - R_DrawBrushModel (currententity); - break; - - default: - break; - } - } - - for (i=0 ; imodel->type) - { - case mod_sprite: - R_DrawSpriteModel (currententity); - break; - - default : - break; - } - } -} - -/* -============= -R_DrawViewModel -============= -*/ -void R_DrawViewModel (void) -{ - float ambient[4], diffuse[4]; - int j; - int lnum; - vec3_t dist; - float add; - dlight_t *dl; - int ambientlight, shadelight; - - if (!r_drawviewmodel.value || !Cam_DrawViewModel()) - return; - - if (envmap) - return; - - if (!r_drawentities.value) - return; - - if (cl.stats[STAT_ITEMS] & IT_INVISIBILITY) - return; - - if (cl.stats[STAT_HEALTH] <= 0) - return; - - currententity = &cl.viewent; - if (!currententity->model) - return; - - j = R_LightPoint (currententity->origin); - - if (j < 24) - j = 24; // allways give some light on gun - ambientlight = j; - shadelight = j; - -// add dynamic lights - for (lnum=0 ; lnumradius) - continue; - if (!dl->radius) - continue; - if (dl->die < cl.time) - continue; - - VectorSubtract (currententity->origin, dl->origin, dist); - add = dl->radius - Length(dist); - if (add > 0) - ambientlight += add; - } - - ambient[0] = ambient[1] = ambient[2] = ambient[3] = (float)ambientlight / 128; - diffuse[0] = diffuse[1] = diffuse[2] = diffuse[3] = (float)shadelight / 128; - - // hack the depth range to prevent view model from poking into walls - glDepthRange (gldepthmin, gldepthmin + 0.3*(gldepthmax-gldepthmin)); - R_DrawAliasModel (currententity); - glDepthRange (gldepthmin, gldepthmax); -} - - -/* -============ -R_PolyBlend -============ -*/ -void R_PolyBlend (void) -{ - if (!gl_polyblend.value) - return; - if (!v_blend[3]) - return; - -//Con_Printf("R_PolyBlend(): %4.2f %4.2f %4.2f %4.2f\n",v_blend[0], v_blend[1], v_blend[2], v_blend[3]); - - GL_DisableMultitexture(); - - glDisable (GL_ALPHA_TEST); - glEnable (GL_BLEND); - glDisable (GL_DEPTH_TEST); - glDisable (GL_TEXTURE_2D); - - glLoadIdentity (); - - glRotatef (-90, 1, 0, 0); // put Z going up - glRotatef (90, 0, 0, 1); // put Z going up - - glColor4fv (v_blend); - - glBegin (GL_QUADS); - - glVertex3f (10, 100, 100); - glVertex3f (10, -100, 100); - glVertex3f (10, -100, -100); - glVertex3f (10, 100, -100); - glEnd (); - - glDisable (GL_BLEND); - glEnable (GL_TEXTURE_2D); - glEnable (GL_ALPHA_TEST); -} - - -int SignbitsForPlane (mplane_t *out) -{ - int bits, j; - - // for fast box on planeside test - - bits = 0; - for (j=0 ; j<3 ; j++) - { - if (out->normal[j] < 0) - bits |= 1<contents); - V_CalcBlend (); - - r_cache_thrash = false; - - c_brush_polys = 0; - c_alias_polys = 0; - -} - - -void MYgluPerspective( GLdouble fovy, GLdouble aspect, - GLdouble zNear, GLdouble zFar ) -{ - GLdouble xmin, xmax, ymin, ymax; - - ymax = zNear * tan( fovy * M_PI / 360.0 ); - ymin = -ymax; - - xmin = ymin * aspect; - xmax = ymax * aspect; - - glFrustum( xmin, xmax, ymin, ymax, zNear, zFar ); -} - - -/* -============= -R_SetupGL -============= -*/ -void R_SetupGL (void) -{ - float screenaspect; - extern int glwidth, glheight; - int x, x2, y2, y, w, h; - - // - // set up viewpoint - // - glMatrixMode(GL_PROJECTION); - glLoadIdentity (); - x = r_refdef.vrect.x * glwidth/vid.width; - x2 = (r_refdef.vrect.x + r_refdef.vrect.width) * glwidth/vid.width; - y = (vid.height-r_refdef.vrect.y) * glheight/vid.height; - y2 = (vid.height - (r_refdef.vrect.y + r_refdef.vrect.height)) * glheight/vid.height; - - // fudge around because of frac screen scale - if (x > 0) - x--; - if (x2 < glwidth) - x2++; - if (y2 < 0) - y2--; - if (y < glheight) - y++; - - w = x2 - x; - h = y - y2; - - if (envmap) - { - x = y2 = 0; - w = h = 256; - } - - glViewport (glx + x, gly + y2, w, h); - screenaspect = (float)r_refdef.vrect.width/r_refdef.vrect.height; -// yfov = 2*atan((float)r_refdef.vrect.height/r_refdef.vrect.width)*180/M_PI; -// yfov = (2.0 * tan (scr_fov.value/360*M_PI)) / screenaspect; -// yfov = 2*atan((float)r_refdef.vrect.height/r_refdef.vrect.width)*(scr_fov.value*2)/M_PI; -// MYgluPerspective (yfov, screenaspect, 4, 4096); - MYgluPerspective (r_refdef.fov_y, screenaspect, 4, 4096); - - if (mirror) - { - if (mirror_plane->normal[2]) - glScalef (1, -1, 1); - else - glScalef (-1, 1, 1); - glCullFace(GL_BACK); - } - else - glCullFace(GL_FRONT); - - glMatrixMode(GL_MODELVIEW); - glLoadIdentity (); - - glRotatef (-90, 1, 0, 0); // put Z going up - glRotatef (90, 0, 0, 1); // put Z going up - glRotatef (-r_refdef.viewangles[2], 1, 0, 0); - glRotatef (-r_refdef.viewangles[0], 0, 1, 0); - glRotatef (-r_refdef.viewangles[1], 0, 0, 1); - glTranslatef (-r_refdef.vieworg[0], -r_refdef.vieworg[1], -r_refdef.vieworg[2]); - - glGetFloatv (GL_MODELVIEW_MATRIX, r_world_matrix); - - // - // set drawing parms - // - if (gl_cull.value) - glEnable(GL_CULL_FACE); - else - glDisable(GL_CULL_FACE); - - glDisable(GL_BLEND); - glDisable(GL_ALPHA_TEST); - glEnable(GL_DEPTH_TEST); -} - -/* -================ -R_RenderScene - -r_refdef must be set before the first call -================ -*/ -void R_RenderScene (void) -{ - R_SetupFrame (); - - R_SetFrustum (); - - R_SetupGL (); - - R_MarkLeaves (); // done here so we know if we're in water - - R_DrawWorld (); // adds static entities to the list - - S_ExtraUpdate (); // don't let sound get messed up if going slow - - R_DrawEntitiesOnList (); - - GL_DisableMultitexture(); - - R_RenderDlights (); - - R_DrawParticles (); - -#ifdef GLTEST - Test_Draw (); -#endif - -} - - -/* -============= -R_Clear -============= -*/ -void R_Clear (void) -{ - if (r_mirroralpha.value != 1.0) - { - if (gl_clear.value) - glClear (GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); - else - glClear (GL_DEPTH_BUFFER_BIT); - gldepthmin = 0; - gldepthmax = 0.5; - glDepthFunc (GL_LEQUAL); - } - else if (gl_ztrick.value) - { - static int trickframe; - - if (gl_clear.value) - glClear (GL_COLOR_BUFFER_BIT); - - trickframe++; - if (trickframe & 1) - { - gldepthmin = 0; - gldepthmax = 0.49999; - glDepthFunc (GL_LEQUAL); - } - else - { - gldepthmin = 1; - gldepthmax = 0.5; - glDepthFunc (GL_GEQUAL); - } - } - else - { - if (gl_clear.value) - glClear (GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); - else - glClear (GL_DEPTH_BUFFER_BIT); - gldepthmin = 0; - gldepthmax = 1; - glDepthFunc (GL_LEQUAL); - } - - glDepthRange (gldepthmin, gldepthmax); -} - -#if 0 //!!! FIXME, Zoid, mirror is disabled for now -/* -============= -R_Mirror -============= -*/ -void R_Mirror (void) -{ - float d; - msurface_t *s; - entity_t *ent; - - if (!mirror) - return; - - memcpy (r_base_world_matrix, r_world_matrix, sizeof(r_base_world_matrix)); - - d = DotProduct (r_refdef.vieworg, mirror_plane->normal) - mirror_plane->dist; - VectorMA (r_refdef.vieworg, -2*d, mirror_plane->normal, r_refdef.vieworg); - - d = DotProduct (vpn, mirror_plane->normal); - VectorMA (vpn, -2*d, mirror_plane->normal, vpn); - - r_refdef.viewangles[0] = -asin (vpn[2])/M_PI*180; - r_refdef.viewangles[1] = atan2 (vpn[1], vpn[0])/M_PI*180; - r_refdef.viewangles[2] = -r_refdef.viewangles[2]; - - ent = &cl_entities[cl.viewentity]; - if (cl_numvisedicts < MAX_VISEDICTS) - { - cl_visedicts[cl_numvisedicts] = ent; - cl_numvisedicts++; - } - - gldepthmin = 0.5; - gldepthmax = 1; - glDepthRange (gldepthmin, gldepthmax); - glDepthFunc (GL_LEQUAL); - - R_RenderScene (); - R_DrawWaterSurfaces (); - - - gldepthmin = 0; - gldepthmax = 0.5; - glDepthRange (gldepthmin, gldepthmax); - glDepthFunc (GL_LEQUAL); - - // blend on top - glEnable (GL_BLEND); - glMatrixMode(GL_PROJECTION); - if (mirror_plane->normal[2]) - glScalef (1,-1,1); - else - glScalef (-1,1,1); - glCullFace(GL_FRONT); - glMatrixMode(GL_MODELVIEW); - - glLoadMatrixf (r_base_world_matrix); - - glColor4f (1,1,1,r_mirroralpha.value); - s = cl.worldmodel->textures[mirrortexturenum]->texturechain; - for ( ; s ; s=s->texturechain) - R_RenderBrushPoly (s); - cl.worldmodel->textures[mirrortexturenum]->texturechain = NULL; - glDisable (GL_BLEND); - glColor4f (1,1,1,1); -} -#endif - -/* -================ -R_RenderView - -r_refdef must be set before the first call -================ -*/ -void R_RenderView (void) -{ - double time1 = 0, time2; - - if (r_norefresh.value) - return; - - if (!r_worldentity.model || !cl.worldmodel) - Sys_Error ("R_RenderView: NULL worldmodel"); - - if (r_speeds.value) - { - glFinish (); - time1 = Sys_DoubleTime (); - c_brush_polys = 0; - c_alias_polys = 0; - } - - mirror = false; - - if (gl_finish.value) - glFinish (); - - R_Clear (); - - // render normal view - R_RenderScene (); - R_DrawViewModel (); - R_DrawWaterSurfaces (); - - // render mirror view -// R_Mirror (); - - R_PolyBlend (); - - if (r_speeds.value) - { -// glFinish (); - time2 = Sys_DoubleTime (); - Con_Printf ("%3i ms %4i wpoly %4i epoly\n", (int)((time2-time1)*1000), c_brush_polys, c_alias_polys); - } -}