diff --git a/Quake/cl_main.c b/Quake/cl_main.c index 01118419..109f4af8 100644 --- a/Quake/cl_main.c +++ b/Quake/cl_main.c @@ -497,7 +497,7 @@ static qboolean CL_LerpEntity(entity_t *ent, vec3_t org, vec3_t ang, float frac) vec3_t delta; qboolean teleported = false; - if (ent->netstate.pmovetype && ent-cl.entities==cl.viewentity && qcvm->worldmodel && !cl_nopred.value) + if (ent->netstate.pmovetype && ent-cl.entities==cl.viewentity && qcvm->worldmodel && !cl_nopred.value && cls.signon == SIGNONS) { //note: V_CalcRefdef will copy from cl.entities[viewent] to get its origin, so doing it here is the proper place anyway. static struct { @@ -1107,6 +1107,8 @@ qboolean CL_CheckDownload(const char *filename) return true; //block while we're already downloading something if (!cl.protocol_dpdownload) return false; //can't download anyway + if (cl.wronggamedir) + return false; //don't download them into the wrong place. this may be awkward for id1 content though (if such a thing logically exists... like custom maps). if (*cls.download.current && !strcmp(cls.download.current, filename)) return false; //if the previous download failed, don't endlessly retry. if (COM_FileExists(filename, NULL)) diff --git a/Quake/cl_parse.c b/Quake/cl_parse.c index 79bcf209..00654b9d 100644 --- a/Quake/cl_parse.c +++ b/Quake/cl_parse.c @@ -1407,7 +1407,7 @@ static void CL_ParseServerInfo (void) q_strlcpy(gamedir, MSG_ReadString(), sizeof(gamedir)); if (!COM_GameDirMatches(gamedir)) { - gamedirswitchwarning = true; + cl.wronggamedir = true; } } @@ -1467,8 +1467,9 @@ static void CL_ParseServerInfo (void) q_snprintf(protname, sizeof(protname), "fte%i", cl.protocol); else q_snprintf(protname, sizeof(protname), "%i", cl.protocol); - Con_Printf ("Using protocol %s", protname); - Con_Printf ("\n"); + if (con_x) //some servers try to save spam by skipping the \n. don't make it ugly. + Con_Printf ("\n"); + Con_Printf ("Using protocol %s\n", protname); // seperate the printfs so the server message can have a color Con_Printf ("\n%s\n", Con_Quakebar(40)); //johnfitz @@ -1546,10 +1547,13 @@ static void CL_ParseServerInfo (void) cl.ackframes[cl.ackframes_count++] = -1; //this is here, to try to make sure its a little more obvious that its there. - if (gamedirswitchwarning) + if (cl.wronggamedir) { + const char *curgame = COM_GetGameNames(false); + if (!*curgame) + curgame = COM_GetGameNames(true); Con_Warning("Server is using a different gamedir.\n"); - Con_Warning("Current: %s\n", COM_GetGameNames(false)); + Con_Warning("Current: %s\n", curgame); Con_Warning("Server: %s\n", gamedir); Con_Warning("You will probably want to switch gamedir to match the server.\n"); } @@ -2079,6 +2083,8 @@ static void CL_ParsePrecache(void) case 0: //models if (index < MAX_MODELS) { + if (cl.model_count == index) + cl.model_count = index+1; q_strlcpy (cl.model_name[index], name, MAX_QPATH); Mod_TouchModel (name); if (!cl.sendprespawn) @@ -2109,7 +2115,12 @@ static void CL_ParsePrecache(void) #endif case 2: //sounds if (index < MAX_SOUNDS) + { + if (cl.sound_count == index) + cl.sound_count = index+1; + q_strlcpy (cl.sound_name[index], name, MAX_QPATH); cl.sound_precache[index] = S_PrecacheSound (name); + } break; // case 3: //unused default: diff --git a/Quake/client.h b/Quake/client.h index e1642093..18ede58c 100644 --- a/Quake/client.h +++ b/Quake/client.h @@ -269,6 +269,7 @@ typedef struct unsigned protocol_pext1; //spike -- flag of fte protocol extensions unsigned protocol_pext2; //spike -- flag of fte protocol extensions qboolean protocol_dpdownload; + qboolean wronggamedir; //blocks downloads #ifdef PSET_SCRIPT qboolean protocol_particles; diff --git a/Quake/console.h b/Quake/console.h index df56a280..b9952c69 100644 --- a/Quake/console.h +++ b/Quake/console.h @@ -28,6 +28,7 @@ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. // extern int con_totallines; extern int con_backscroll; +extern int con_x; //for testing if there's trailing junk that needs an \n extern qboolean con_forcedup; // because no entities to refresh extern qboolean con_initialized; extern byte *con_chars; diff --git a/Quake/gl_rmain.c b/Quake/gl_rmain.c index b8e21e76..b1295fc3 100644 --- a/Quake/gl_rmain.c +++ b/Quake/gl_rmain.c @@ -1271,10 +1271,11 @@ void R_RenderView (void) //Spike: flag whether the skyroom was actually visible, so we don't needlessly draw it when its not (1 frame's lag, hopefully not too noticable) if (r_refdef.drawworld) { - if (r_viewleaf->contents == CONTENTS_SOLID || r_drawflat_cheatsafe || r_lightmap_cheatsafe) + extern cvar_t r_fastsky; + if (r_viewleaf->contents == CONTENTS_SOLID || r_drawflat_cheatsafe || r_lightmap_cheatsafe || r_fastsky.value) skyroom_visible = false; //don't do skyrooms when the view is in the void, for framerate reasons while debugging. else - skyroom_visible = R_SkyroomWasVisible(); + skyroom_visible = RSceneCache_HasSky() || R_SkyroomWasVisible(); skyroom_drawn = false; } //skyroom end diff --git a/Quake/gl_sky.c b/Quake/gl_sky.c index 63bf9c76..f7cbd8ca 100644 --- a/Quake/gl_sky.c +++ b/Quake/gl_sky.c @@ -29,10 +29,6 @@ Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. float Fog_GetDensity(void); float *Fog_GetColor(void); -#ifndef SDL_THREADS_DISABLED -qboolean RSceneCache_DrawSkySurfDepth(void); //Draws sky surfaces. -#endif - extern int rs_skypolys; // for r_speeds readout extern int rs_skypasses; // for r_speeds readout diff --git a/Quake/glquake.h b/Quake/glquake.h index 92ec62b5..aad0967a 100644 --- a/Quake/glquake.h +++ b/Quake/glquake.h @@ -464,8 +464,12 @@ void R_ClearTextureChains (qmodel_t *mod, texchain_t chain); void R_ChainSurface (msurface_t *surf, texchain_t chain); void R_DrawTextureChains (qmodel_t *model, entity_t *ent, texchain_t chain); void R_DrawWorld_Water (void); +#ifndef SDL_THREADS_DISABLED void RSceneCache_Cleanup(qmodel_t *mod); void RSceneCache_Shutdown(void); +qboolean RSceneCache_DrawSkySurfDepth(void); //Draws sky surfaces. +qboolean RSceneCache_HasSky(void); +#endif extern byte *skipsubmodels; void GL_BindBuffer (GLenum target, GLuint buffer); diff --git a/Quake/pr_cmds.c b/Quake/pr_cmds.c index 7753fc1d..9bd7370d 100644 --- a/Quake/pr_cmds.c +++ b/Quake/pr_cmds.c @@ -1796,6 +1796,7 @@ void PR_spawnfunc_misc_model(edict_t *self) //make sure the model is precached, to avoid errors. G_INT(OFS_PARM0) = self->v.model; PF_sv_precache_model(); + self->v.modelindex = SV_ModelIndex(PR_GetString(self->v.model)); //and lets just call makestatic instead of worrying if it'll interfere with the rest of the qc. G_INT(OFS_PARM0) = EDICT_TO_PROG(self); diff --git a/Quake/pr_edict.c b/Quake/pr_edict.c index e4a383d6..45c05c95 100644 --- a/Quake/pr_edict.c +++ b/Quake/pr_edict.c @@ -1020,7 +1020,9 @@ const char *ED_ParseEdict (const char *data, edict_t *ent) //johnfitz -- HACK -- suppress error becuase fog/sky/alpha fields might not be mentioned in defs.qc else #endif - if (strncmp(keyname, "sky", 3) && strcmp(keyname, "fog") && strcmp(keyname, "alpha")) + if (!strcmp(keyname, "skyroom") && ent == sv.qcvm.edicts) + SV_SetupSkyRoom(com_token); //*barf* mapper should have used a leading underscore. hack around their bugs. + else if (strncmp(keyname, "sky", 3) && strcmp(keyname, "fog") && strcmp(keyname, "alpha")) Con_DPrintf ("\"%s\" is not a field\n", keyname); //johnfitz -- was Con_Printf continue; } diff --git a/Quake/r_world.c b/Quake/r_world.c index 6ea6bff7..b1e04910 100644 --- a/Quake/r_world.c +++ b/Quake/r_world.c @@ -2116,6 +2116,15 @@ static void RSceneCache_Draw(qboolean water) RSceneCache_Finish(cache); skipsubmodels = cache->cachedsubmodels; + glDepthMask(GL_TRUE); + glDisable (GL_BLEND); + if (skyroom_drawn) + { //draw skies first, so we don't end up drawing overlapping non-skies behind + glColorMask(GL_FALSE,GL_FALSE,GL_FALSE,GL_FALSE); + RSceneCache_DrawSkySurfDepth(); + glColorMask(GL_TRUE,GL_TRUE,GL_TRUE,GL_TRUE); + } + GL_BindBuffer (GL_ARRAY_BUFFER, gl_bmodel_vbo); GL_BindBuffer (GL_ELEMENT_ARRAY_BUFFER, cache->ebo); // indices come from client memory! @@ -2127,10 +2136,7 @@ static void RSceneCache_Draw(qboolean water) GL_VertexAttribPointerFunc (texCoordsAttrIndex, 2, GL_FLOAT, GL_FALSE, VERTEXSIZE * sizeof(float), ((float *)0) + 3); GL_VertexAttribPointerFunc (LMCoordsAttrIndex, 2, GL_FLOAT, GL_FALSE, VERTEXSIZE * sizeof(float), ((float *)0) + 5); - rs_brushpolys += cache->brushpolys; //for r_speeds. - - glDepthMask (GL_TRUE); - glDisable (GL_BLEND); + rs_brushpolys += cache->brushpolys; //for r_speeds.; for (i = 0; i < cache->numtextures; i++) { @@ -2208,7 +2214,9 @@ static void RSceneCache_Draw(qboolean water) GL_SelectTexture (GL_TEXTURE2); GL_Bind(tex->fullbright); - if (lastprog != r_water[mode].program) + if (skyroom_drawn) + continue; //already drew them + else if (lastprog != r_water[mode].program) { lastprog = r_water[mode].program; GL_UseProgramFunc (r_water[mode].program); @@ -2271,6 +2279,24 @@ static void RSceneCache_Draw(qboolean water) GL_BindBuffer (GL_ARRAY_BUFFER, 0); GL_BindBuffer (GL_ELEMENT_ARRAY_BUFFER, 0); } +qboolean RSceneCache_HasSky(void) +{ + struct rscenecache_s *cache = rscenecache.drawing; + int i; + texture_t *tex; + + if (cache) + { + for (i = 0; i < cache->numtextures; i++) + { + tex = cache->worldmodel->textures[i]; + if (!tex || !(tex->name[0]=='s'&&tex->name[1]=='k'&&tex->name[2]=='y')) + continue; //we only want sky textures. + return true; + } + } + return false; +} qboolean RSceneCache_DrawSkySurfDepth(void) { //legacy skyboxes are a serious pain, but oh well... //if we draw anything here then its JUST depth values. we don't need glsl nor even textures for this.