diff --git a/engine/client/cl_ents.c b/engine/client/cl_ents.c index 08a3949bc..1fdbb311c 100644 --- a/engine/client/cl_ents.c +++ b/engine/client/cl_ents.c @@ -1742,7 +1742,8 @@ void CL_LinkPacketEntities (void) } VectorCopy(angles, ent->angles); - angles[0]*=-1; + if (model && model->type == mod_alias) + angles[0]*=-1; //carmack screwed up when he added alias models - they pitch the wrong way. AngleVectors(angles, ent->axis[0], ent->axis[1], ent->axis[2]); VectorInverse(ent->axis[1]); diff --git a/engine/client/pr_menu.c b/engine/client/pr_menu.c index 997508b67..58c93b50b 100644 --- a/engine/client/pr_menu.c +++ b/engine/client/pr_menu.c @@ -544,6 +544,9 @@ void PF_CL_drawgetimagesize (progfuncs_t *prinst, struct globalvars_s *pr_global float *ret = G_VECTOR(OFS_RETURN); + if (!p) + p = Draw_SafeCachePic(va("%s.tga", picname)); + if (p) { ret[0] = p->width; diff --git a/engine/common/cvar.c b/engine/common/cvar.c index 75a833f17..17406d7a8 100644 --- a/engine/common/cvar.c +++ b/engine/common/cvar.c @@ -686,7 +686,7 @@ cvar_t *Cvar_SetCore (cvar_t *var, const char *value, qboolean force) } #endif - latch = var->string; + latch = var->string;//save off the old value (so cvar_set(var, var->string) works) var->string = (char*)Z_Malloc (Q_strlen(value)+1); Q_strcpy (var->string, value); @@ -920,13 +920,19 @@ void Cvar_RegisterVariable (cvar_t *variable) cvar_t *Cvar_Get(const char *name, const char *defaultvalue, int flags, const char *group) { cvar_t *var; + int old; var = Cvar_FindVar(name); if (var) { //allow this to change all < cvar_latch values. //this allows q2 dlls to apply different flags to a cvar without destroying our important ones (like cheat). + old = var->flags; var->flags = (var->flags & ~(CVAR_NOSET)) | (flags & (CVAR_NOSET|CVAR_SERVERINFO|CVAR_USERINFO|CVAR_ARCHIVE)); + if (old != var->flags) + { + Cvar_Set(var, var->string); + } return var; } diff --git a/engine/common/net_wins.c b/engine/common/net_wins.c index d8d2316d1..459320a7b 100644 --- a/engine/common/net_wins.c +++ b/engine/common/net_wins.c @@ -1765,24 +1765,26 @@ vfsfile_t *FS_OpenTCP(char *name) { tcpfile_t *newf; int sock; - netadr_t adr; - if (!NET_StringToAdr(name, &adr)) + netadr_t adr = {0}; + if (NET_StringToAdr(name, &adr)) + { + sock = TCP_OpenStream(adr); + if (sock == INVALID_SOCKET) + return NULL; + + newf = Z_Malloc(sizeof(*newf)); + newf->sock = sock; + newf->funcs.Close = VFSTCP_Close; + newf->funcs.Flush = NULL; + newf->funcs.GetLen = VFSTCP_GetLen; + newf->funcs.ReadBytes = VFSTCP_ReadBytes; + newf->funcs.Seek = VFSTCP_Seek; + newf->funcs.Tell = VFSTCP_Tell; + newf->funcs.WriteBytes = VFSTCP_WriteBytes; + newf->funcs.seekingisabadplan = true; + + return &newf->funcs; + } + else return NULL; - - sock = TCP_OpenStream(adr); - if (sock == INVALID_SOCKET) - return NULL; - - newf = Z_Malloc(sizeof(*newf)); - newf->sock = sock; - newf->funcs.Close = VFSTCP_Close; - newf->funcs.Flush = NULL; - newf->funcs.GetLen = VFSTCP_GetLen; - newf->funcs.ReadBytes = VFSTCP_ReadBytes; - newf->funcs.Seek = VFSTCP_Seek; - newf->funcs.Tell = VFSTCP_Tell; - newf->funcs.WriteBytes = VFSTCP_WriteBytes; - newf->funcs.seekingisabadplan = true; - - return &newf->funcs; } diff --git a/engine/common/pmovetst.c b/engine/common/pmovetst.c index 3b9b4878b..869cbf964 100644 --- a/engine/common/pmovetst.c +++ b/engine/common/pmovetst.c @@ -199,9 +199,9 @@ qboolean PM_TransformedHullCheck (model_t *model, vec3_t start, vec3_t end, trac if (trace->fraction != 1.0) { - a[0] = angles[0]; - a[1] = angles[1]; - a[2] = angles[2]; + a[0] = -angles[0]; + a[1] = -angles[1]; + a[2] = -angles[2]; AngleVectors (a, forward, right, up); VectorCopy (trace->plane.normal, temp); diff --git a/engine/ftequake/ftequake.dsp b/engine/ftequake/ftequake.dsp index 7e2561f63..85ae63635 100644 --- a/engine/ftequake/ftequake.dsp +++ b/engine/ftequake/ftequake.dsp @@ -3064,6 +3064,8 @@ SOURCE=..\gl\gl_bloom.c !ELSEIF "$(CFG)" == "ftequake - Win32 Debug Dedicated Server" +# PROP Exclude_From_Build 1 + !ELSEIF "$(CFG)" == "ftequake - Win32 Release Dedicated Server" # PROP Exclude_From_Build 1 diff --git a/engine/gl/gl_model.c b/engine/gl/gl_model.c index 30d6165a5..391b5a73c 100644 --- a/engine/gl/gl_model.c +++ b/engine/gl/gl_model.c @@ -2194,7 +2194,7 @@ qboolean GLMod_LoadClipnodes (lump_t *l) hull->planes = loadmodel->planes; hull->clip_mins[0] = -48; hull->clip_mins[1] = -48; - hull->clip_mins[2] = -50; + hull->clip_mins[2] = -50 - 24; hull->clip_maxs[0] = 48; hull->clip_maxs[1] = 48; hull->clip_maxs[2] = 50; diff --git a/engine/gl/gl_ppl.c b/engine/gl/gl_ppl.c index d40c5b357..eb105efa1 100644 --- a/engine/gl/gl_ppl.c +++ b/engine/gl/gl_ppl.c @@ -1731,12 +1731,25 @@ void PPL_BaseBModelTextures(entity_t *e) currentmodel = model = e->model; s = model->surfaces+model->firstmodelsurface; - GL_TexEnv(GL_MODULATE); + if (currententity->drawflags & DRF_TRANSLUCENT) + currententity->shaderRGBAf[3]=0.5; + if ((currententity->drawflags & MLS_ABSLIGHT) == MLS_ABSLIGHT) + { + currententity->shaderRGBAf[0] = + currententity->shaderRGBAf[1] = + currententity->shaderRGBAf[2] = currententity->abslight/255.0f; + } if (currententity->shaderRGBAf[3]<1) + { + GL_TexEnv(GL_MODULATE); qglEnable(GL_BLEND); + } else + { + GL_TexEnv(GL_REPLACE); qglDisable(GL_BLEND); + } qglColor4fv(currententity->shaderRGBAf); diff --git a/engine/gl/gl_rlight.c b/engine/gl/gl_rlight.c index fe409933f..6dcc85c10 100644 --- a/engine/gl/gl_rlight.c +++ b/engine/gl/gl_rlight.c @@ -711,6 +711,13 @@ float *GLRecursiveLightPoint3C (mnode_t *node, vec3_t start, vec3_t end) float scale; int maps; + if (!cl.worldmodel->lightdata) + { + l[0]=255;l[1]=255;l[2]=255; + l[3]=0;l[4]=1;l[5]=1; + return l; + } + if (cl.worldmodel->fromgame == fg_quake2) { if (node->contents != -1) diff --git a/engine/gl/gl_rsurf.c b/engine/gl/gl_rsurf.c index fbf07d068..3efce90cd 100644 --- a/engine/gl/gl_rsurf.c +++ b/engine/gl/gl_rsurf.c @@ -259,6 +259,18 @@ void GLR_AddStain(vec3_t org, float red, float green, float blue, float radius) parms[1] = org[0] - pe->origin[0]; parms[2] = org[1] - pe->origin[1]; parms[3] = org[2] - pe->origin[2]; + + if (pe->angles[0] || pe->angles[1] || pe->angles[2]) + { + vec3_t f, r, u, temp; + AngleVectors(pe->angles, f, r, u); + VectorCopy((parms+1), temp); + parms[1] = DotProduct(temp, f); + parms[2] = -DotProduct(temp, r); + parms[3] = DotProduct(temp, u); + } + + pe->model->funcs.StainNode(pe->model->nodes+pe->model->hulls[0].firstclipnode, parms); } } diff --git a/engine/qclib/qcc_pr_comp.c b/engine/qclib/qcc_pr_comp.c index 116be824d..3f79e7702 100644 --- a/engine/qclib/qcc_pr_comp.c +++ b/engine/qclib/qcc_pr_comp.c @@ -2674,9 +2674,13 @@ QCC_def_t *QCC_PR_ParseFunctionCall (QCC_def_t *func) //warning, the func could e = QCC_PR_Statement(pr_opcodes+OP_CONV_FTOI, e, NULL, NULL); else if (p->type == ev_float && e->type->type == ev_integer) //convert float -> int... is this a constant? e = QCC_PR_Statement(pr_opcodes+OP_CONV_ITOF, e, NULL, NULL); + else if (p->type == ev_function && e->type->type == ev_integer && e->constant && !((int*)qcc_pr_globals)[e->ofs]) + { //you're allowed to use int 0 to pass a null function pointer + //this is basically because __NULL__ is defined as ~0 (int 0) + } else if (p->type != ev_variant) //can cast to variant whatever happens { - if (flag_laxcasts) + if (flag_laxcasts || (p->type == ev_function && e->type->type == ev_function)) { QCC_PR_ParseWarning(WARN_LAXCAST, "type mismatch on parm %i - (%s should be %s)", arg+1, TypeName(e->type), TypeName(p)); QCC_PR_ParsePrintDef(WARN_LAXCAST, func); diff --git a/engine/qclib/qcc_pr_lex.c b/engine/qclib/qcc_pr_lex.c index 7656334d7..decee9c6f 100644 --- a/engine/qclib/qcc_pr_lex.c +++ b/engine/qclib/qcc_pr_lex.c @@ -162,18 +162,34 @@ void QCC_FindBestInclude(char *newfile, char *currentfile, char *rootpath) { char fullname[10248]; char *stripfrom; + int doubledots; char *end = fullname; if (!*newfile) return; + doubledots = 0; + while(!strncmp(newfile, "../", 3) || !strncmp(newfile, "..\\", 3)) + { + newfile+=3; + doubledots++; + } + currentfile += strlen(rootpath); //could this be bad? for(stripfrom = currentfile+strlen(currentfile)-1; stripfrom>currentfile; stripfrom--) { if (*stripfrom == '/' || *stripfrom == '\\') - break; + { + if (doubledots>0) + doubledots--; + else + { + stripfrom++; + break; + } + } } strcpy(end, rootpath); end = end+strlen(end); if (*fullname && end[-1] != '/') diff --git a/engine/server/pr_cmds.c b/engine/server/pr_cmds.c index 4282dcd63..69d283e70 100644 --- a/engine/server/pr_cmds.c +++ b/engine/server/pr_cmds.c @@ -114,6 +114,7 @@ func_t pr_SV_ShouldPause; func_t SV_PlayerPhysicsQC; //DP's DP_SV_PLAYERPHYSICS extension func_t EndFrameQC; +func_t pr_ClassChangeWeapon; qboolean pr_items2; @@ -540,6 +541,7 @@ void PR_LoadGlabalStruct(void) pr_SV_PausedTic = PR_FindFunction(svprogfuncs, "SV_PausedTic", PR_ANY); pr_SV_ShouldPause = PR_FindFunction(svprogfuncs, "SV_ShouldPause", PR_ANY); + pr_ClassChangeWeapon = PR_FindFunction(svprogfuncs, "ClassChangeWeapon", PR_ANY); if (pr_no_playerphysics.value) SV_PlayerPhysicsQC = 0; @@ -1262,7 +1264,7 @@ void Q_InitProgs(void) if (f) { pr_globals = PR_globals(svprogfuncs, PR_CURRENT); - G_INT(OFS_PARM0) = (int)PR_SetString(svprogfuncs, as); + G_INT(OFS_PARM0) = (int)PR_SetString(svprogfuncs, sv_addon[i2].string); PR_ExecuteProgram (svprogfuncs, f); } else @@ -1328,7 +1330,7 @@ qboolean PR_ShouldTogglePause(client_t *initiator, qboolean newpaused) globalvars_t *pr_globals; if (!svprogfuncs || !pr_SV_ShouldPause) - return false; + return true; pr_globals = PR_globals(svprogfuncs, PR_CURRENT); @@ -7478,6 +7480,32 @@ void PF_advanceweaponframe (progfuncs_t *prinst, struct globalvars_s *pr_globals G_FLOAT(OFS_RETURN) = state; } +void PR_SetPlayerClass(client_t *cl, int classnum, qboolean fromqc) +{ + char temp[16]; + if (classnum < 1) + return; //reject it (it would crash the (standard hexen2) mod) + if (classnum > 5) + return; + if (cl->playerclass != classnum) + { + cl->edict->v->playerclass = classnum; + cl->playerclass = classnum; + + sprintf(temp,"%i",(int)classnum); + Info_SetValueForKey (cl->userinfo, "cl_playerclass", temp, sizeof(cl->userinfo)); + + if (!fromqc) + { + cl->sendinfo = true; + if (cl->state == cs_spawned && pr_ClassChangeWeapon) + { + pr_global_struct->self = EDICT_TO_PROG(svprogfuncs, cl->edict); + PR_ExecuteProgram (svprogfuncs, pr_ClassChangeWeapon); + } + } + } +} void PF_setclass (progfuncs_t *prinst, struct globalvars_s *pr_globals) { diff --git a/engine/server/q3g_public.h b/engine/server/q3g_public.h index 97d585ddd..2eefe82d8 100644 --- a/engine/server/q3g_public.h +++ b/engine/server/q3g_public.h @@ -129,7 +129,7 @@ typedef enum { // ClientCommand and ServerCommand parameter access G_ARGV, // ( int n, char *buffer, int bufferLength ); - +//10 G_FS_FOPEN_FILE, // ( const char *qpath, fileHandle_t *file, fsMode_t mode ); G_FS_READ, // ( void *buffer, int len, fileHandle_t f ); G_FS_WRITE, // ( const void *buffer, int len, fileHandle_t f ); @@ -162,7 +162,7 @@ typedef enum { // All confgstrings are cleared at each level start. G_GET_CONFIGSTRING, // ( int num, char *buffer, int bufferSize ); - +//20 G_GET_USERINFO, // ( int num, char *buffer, int bufferSize ); // userinfo strings are maintained by the server system, so they // are persistant across level loads, while all other game visible @@ -189,7 +189,7 @@ typedef enum { G_ADJUST_AREA_PORTAL_STATE, // ( gentity_t *ent, qboolean open ); G_AREAS_CONNECTED, // ( int area1, int area2 ); - +//30 G_LINKENTITY, // ( gentity_t *ent ); // an entity will never be sent to a client or used for collision // if it is not passed to linkentity. If the size, position, or @@ -219,6 +219,7 @@ typedef enum { G_FS_GETFILELIST, G_DEBUG_POLYGON_CREATE, +//40 G_DEBUG_POLYGON_DELETE, G_REAL_TIME, G_SNAPVECTOR, diff --git a/engine/server/sv_chat.c b/engine/server/sv_chat.c index 425442d51..116397b3a 100644 --- a/engine/server/sv_chat.c +++ b/engine/server/sv_chat.c @@ -119,7 +119,10 @@ void Chat_GetTag(char *filename, float tag, char **text, char **condition, char } } } - Sys_Error("Tag %f not found in file %s", tag, host_client->chat.filename); + *text = va("Chat Tag %f not found in file %s", tag, host_client->chat.filename); + *condition = ""; + *options = ""; + return; } chatvar_t *SV_ChatFindVariable(char *name) diff --git a/engine/server/sv_ents.c b/engine/server/sv_ents.c index 31e9e20d4..9ebbcb322 100644 --- a/engine/server/sv_ents.c +++ b/engine/server/sv_ents.c @@ -2546,8 +2546,6 @@ void SV_WriteEntitiesToClient (client_t *client, sizebuf_t *msg, qboolean ignore state->modelindex = SV_ModelIndex(modname); } } - if (/*progstype == PROG_H2 &&*/ ent->v->solid == SOLID_BSP) - state->angles[0]*=-1; if (state->effects & EF_FULLBRIGHT) { diff --git a/engine/server/sv_init.c b/engine/server/sv_init.c index 431fbe259..af544d92a 100644 --- a/engine/server/sv_init.c +++ b/engine/server/sv_init.c @@ -1022,6 +1022,7 @@ void SV_SpawnServer (char *server, char *startspot, qboolean noents, qboolean us if (progstype == PROG_H2) { + cvar_t *cv; if (coop.value) { eval = PR_FindGlobal(svprogfuncs, "coop", 0); @@ -1032,11 +1033,13 @@ void SV_SpawnServer (char *server, char *startspot, qboolean noents, qboolean us eval = PR_FindGlobal(svprogfuncs, "deathmatch", 0); if (eval) eval->_float = deathmatch.value; } + cv = Cvar_Get("randomclass", "0", CVAR_LATCH, "Hexen2"); eval = PR_FindGlobal(svprogfuncs, "randomclass", 0); - if (eval) eval->_float = Cvar_Get("randomclass", "1", CVAR_LATCH, "Hexen2 rules")->value; + if (eval && cv) eval->_float = cv->value; + cv = Cvar_Get("cl_playerclass", "1", CVAR_USERINFO|CVAR_ARCHIVE, "Hexen2"); eval = PR_FindGlobal(svprogfuncs, "cl_playerclass", 0); - if (eval) eval->_float = 1; + if (eval && cv) eval->_float = cv->value; } else { @@ -1078,6 +1081,8 @@ void SV_SpawnServer (char *server, char *startspot, qboolean noents, qboolean us spawnflagmask |= SPAWNFLAG_NOT_H2HARD; else spawnflagmask |= SPAWNFLAG_NOT_H2MEDIUM; + + //don't filter based on player class. we're lame and don't have any real concept of player classes. } else if (!deathmatch.value) //decide if we are to inhibit single player game ents instead { diff --git a/engine/server/sv_main.c b/engine/server/sv_main.c index 120a20984..ab0fa397c 100644 --- a/engine/server/sv_main.c +++ b/engine/server/sv_main.c @@ -3721,6 +3721,12 @@ void SV_ExtractFromUserinfo (client_t *cl) else cl->drate = 0; //0 disables the downloading check + val = Info_ValueForKey (cl->userinfo, "cl_playerclass"); + if (val) + { + PR_SetPlayerClass(cl, atoi(val), false); + } + // msg command val = Info_ValueForKey (cl->userinfo, "msg"); if (strlen(val)) diff --git a/engine/server/sv_move.c b/engine/server/sv_move.c index c80468915..ff37137da 100644 --- a/engine/server/sv_move.c +++ b/engine/server/sv_move.c @@ -72,7 +72,10 @@ realcheck: start[0] = stop[0] = (mins[0] + maxs[0])*0.5; start[1] = stop[1] = (mins[1] + maxs[1])*0.5; stop[2] = start[2] - 2*pm_stepheight; + savedhull = ent->v->hull; + ent->v->hull = 0; trace = SV_Move (start, vec3_origin, vec3_origin, stop, true, ent); + ent->v->hull = savedhull; if (trace.fraction == 1.0) return false; diff --git a/engine/server/sv_mvd.c b/engine/server/sv_mvd.c index 4bda693b0..06fd8e99f 100644 --- a/engine/server/sv_mvd.c +++ b/engine/server/sv_mvd.c @@ -114,13 +114,13 @@ void DestFlush(qboolean compleate) break; case DEST_STREAM: - if (d->cacheused) + if (d->cacheused && !d->error) { len = send(d->socket, d->cache, d->cacheused, 0); if (len == 0) //client died d->error = true; - else if (len > 0) //error of some kind - { + else if (len > 0) //we put some data through + { //move up the buffer d->cacheused -= len; memmove(d->cache, d->cache+len, d->cacheused); } diff --git a/engine/server/world.c b/engine/server/world.c index a6396b08e..a39e96933 100644 --- a/engine/server/world.c +++ b/engine/server/world.c @@ -389,26 +389,42 @@ void SV_LinkEdict (edict_t *ent, qboolean touch_triggers) if (ent->v->solid == SOLID_BSP && (ent->v->angles[0] || ent->v->angles[1] || ent->v->angles[2]) ) { // expand for rotation + +#if 1 + int i; + float v; + float max, min; + //q2 method + max = 0; + for (i=0 ; i<3 ; i++) + { + v =fabs( ent->v->mins[i]); + if (v > max) + max = v; + v =fabs( ent->v->maxs[i]); + if (v > max) + max = v; + } + for (i=0 ; i<3 ; i++) + { + ent->v->absmin[i] = ent->v->origin[i] - max; + ent->v->absmax[i] = ent->v->origin[i] + max; + } +#else + int i; vec3_t f, r, u; vec3_t mn, mx; - + //we need to link to the correct leaves - if (progstype == PROG_H2) - { - ent->v->angles[0]*=-1; - AngleVectors(ent->v->angles, f,r,u); - ent->v->angles[0]*=-1; - } - else - AngleVectors(ent->v->angles, f,r,u); + AngleVectors(ent->v->angles, f,r,u); mn[0] = DotProduct(ent->v->mins, f); mn[1] = -DotProduct(ent->v->mins, r); mn[2] = DotProduct(ent->v->mins, u); - + mx[0] = DotProduct(ent->v->maxs, f); mx[1] = -DotProduct(ent->v->maxs, r); mx[2] = DotProduct(ent->v->maxs, u); @@ -425,6 +441,7 @@ void SV_LinkEdict (edict_t *ent, qboolean touch_triggers) ent->v->absmax[i] = ent->v->origin[i]+mn[i]+0.1; } } +#endif } else { @@ -959,22 +976,29 @@ qboolean TransformedTrace (struct model_s *model, int hulloverride, int frame, v if (rotated) { // FIXME: figure out how to do this with existing angles - // VectorNegate (angles, a); - a[0] = -angles[0]; - a[1] = -angles[1]; - a[2] = -angles[2]; - AngleVectors (a, forward, right, up); - VectorCopy (trace->plane.normal, temp); - trace->plane.normal[0] = DotProduct (temp, forward); - trace->plane.normal[1] = -DotProduct (temp, right); - trace->plane.normal[2] = DotProduct (temp, up); + if (trace->fraction != 1) + { + VectorNegate (angles, a); + AngleVectors (a, forward, right, up); - trace->endpos[0] = start[0] + trace->fraction * (end[0] - start[0]); - trace->endpos[1] = start[1] + trace->fraction * (end[1] - start[1]); - trace->endpos[2] = start[2] + trace->fraction * (end[2] - start[2]); + VectorCopy (trace->plane.normal, temp); + trace->plane.normal[0] = DotProduct (temp, forward); + trace->plane.normal[1] = -DotProduct (temp, right); + trace->plane.normal[2] = DotProduct (temp, up); + + + trace->endpos[0] = start[0] + trace->fraction * (end[0] - start[0]); + trace->endpos[1] = start[1] + trace->fraction * (end[1] - start[1]); + trace->endpos[2] = start[2] + trace->fraction * (end[2] - start[2]); + } + else + { + VectorCopy (end, trace->endpos); + } } - VectorAdd (trace->endpos, origin, trace->endpos); + else + VectorAdd (trace->endpos, origin, trace->endpos); } else { @@ -1115,15 +1139,15 @@ trace_t SV_ClipMoveToEntity (edict_t *ent, vec3_t start, vec3_t mins, vec3_t max } // trace a line through the apropriate clipping hull - if (progstype == PROG_H2 && ent->v->solid == SOLID_BSP) + if (ent->v->solid != SOLID_BSP) { - ent->v->angles[0]*=-1; - TransformedTrace(model, 0, ent->v->frame, start, end, mins, maxs, &trace, ent->v->origin, ent->v->angles); + ent->v->angles[0]*=-1; //carmack made bsp models rotate wrongly. + TransformedTrace(model, hullnum, ent->v->frame, start, end, mins, maxs, &trace, ent->v->origin, ent->v->angles); ent->v->angles[0]*=-1; } else { - TransformedTrace(model, 0, ent->v->frame, start, end, mins, maxs, &trace, ent->v->origin, ent->v->angles); + TransformedTrace(model, hullnum, ent->v->frame, start, end, mins, maxs, &trace, ent->v->origin, ent->v->angles); } // fix trace up by the offset @@ -1146,7 +1170,7 @@ trace_t SV_ClipMoveToEntity (edict_t *ent, vec3_t start, vec3_t mins, vec3_t max if (model && model->funcs.Trace) { //do the second trace - TransformedTrace(model, 0, ent->v->frame, start, end, mins, maxs, &trace, ent->v->origin, ent->v->angles); + TransformedTrace(model, hullnum, ent->v->frame, start, end, mins, maxs, &trace, ent->v->origin, ent->v->angles); } }