/*	A moving object that doesn't obey physics
*/
void Physics_NoClip(edict_t *eEntity)
{
	// Regular thinking
	if(!Server_RunThink(eEntity))
		return;

	Math_VectorMA(eEntity->v.angles,host_frametime,eEntity->v.avelocity,eEntity->v.angles);
	Math_VectorMA(eEntity->v.origin,host_frametime,eEntity->v.velocity,eEntity->v.origin);

	SV_LinkEdict(eEntity,false);
}
示例#2
0
/*	The mouse click did not hit the brush, so grab one or more side
	planes for dragging
*/
void Brush_SideSelect(brush_t *b,vec3_t origin,vec3_t dir,bool shear)
{
	face_t	*f, *f2;
	vec3_t	p1, p2;

	for(f = b->brush_faces; f; f = f->next)
	{
		Math_VectorCopy(origin,p1);
		Math_VectorMA(origin,16384,dir,p2);

		for (f2=b->brush_faces ; f2 ; f2=f2->next)
		{
			if (f2 == f)
				continue;
			Brush_ClipLineToFace(p1,p2,f2);
		}

		if(f2)
			continue;

		if(Math_VectorCompare(p1,origin))
			continue;
		if(Brush_ClipLineToFace(p1,p2,f))
			continue;

		Brush_SelectFaceForDragging (b, f, shear);
	}
}
// TODO: stay at least 8 units away from all walls in this leaf
void Chase_UpdateForDrawing (void)
{
	int		i;
	vec3_t	forward, up, right;
	vec3_t	ideal, crosshair, temp;

	Math_AngleVectors(cl.viewangles, forward, right, up);

	// calc ideal camera location before checking for walls
	for (i=0 ; i<3 ; i++)
		ideal[i] = cl.viewent.origin[i]
		- forward[i]*chase_back.value
		+ right[i]*chase_right.value;
		//+ up[i]*chase_up.value;
	ideal[2] = cl.viewent.origin[2] + chase_up.value;

	// make sure camera is not in or behind a wall
	TraceLine(r_refdef.vieworg, ideal, temp);
	if(Math_Length(temp) != 0)
		Math_VectorCopy(temp, ideal);

	// place camera
	Math_VectorCopy(ideal, r_refdef.vieworg);

	// find the spot the player is looking at
	Math_VectorMA(cl.viewent.origin, 4096, forward, temp);
	TraceLine(cl.viewent.origin, temp, crosshair);

	// calculate camera angles to look at the same spot
	Math_VectorSubtract(crosshair,r_refdef.vieworg,temp);
	Math_VectorAngles (temp, r_refdef.viewangles);
	if (r_refdef.viewangles[PITCH] == 90 || r_refdef.viewangles[PITCH] == -90)
		r_refdef.viewangles[YAW] = cl.viewangles[YAW];
}
/*	Player character actions
*/
void SV_Physics_Client (edict_t	*ent, int num)
{
	if(!svs.clients[num-1].active)
		return;		// unconnected slot

	// call standard client pre-think
	pr_global_struct.self = EDICT_TO_PROG(ent);

	Game->Game_Init(SERVER_PLAYERPRETHINK,ent,sv.time);

	Game->Physics_CheckVelocity(ent);

	// decide which move function to call
	switch(ent->v.movetype)
	{
	case MOVETYPE_NONE:
		if (!Server_RunThink(ent))
			return;
		break;
	case MOVETYPE_WALK:
		if(!Server_RunThink(ent))
			return;

		if(!Physics_CheckWater(ent) && !(ent->v.flags & FL_WATERJUMP))
			Game->Physics_SetGravity(ent);

		SV_CheckStuck (ent);
		SV_WalkMove (ent);
		break;
	case MOVETYPE_TOSS:
	case MOVETYPE_BOUNCE:
	case MOVETYPE_FLYBOUNCE:
		Physics_Toss(ent);
		break;
	case MOVETYPE_FLY:
		if(!Server_RunThink(ent))
			return;

		SV_FlyMove(ent,host_frametime,NULL);
		break;
	case MOVETYPE_NOCLIP:
		if(!Server_RunThink(ent))
			return;
		Math_VectorMA (ent->v.origin, host_frametime, ent->v.velocity, ent->v.origin);
		break;
	default:
		Sys_Error ("SV_Physics_client: bad movetype %i", (int)ent->v.movetype);
	}

	// Call standard player post-think
	SV_LinkEdict(ent,true);

	pr_global_struct.self = EDICT_TO_PROG(ent);

	Game->Game_Init(SERVER_CLIENTPOSTTHINK,ent,sv.time);
}
/*	Toss, bounce, and fly movement.  When onground, do nothing.
*/
void Physics_Toss(edict_t *ent)
{
	trace_t	trace;
	vec3_t	move;
	float	backoff;

	// Regular thinking
	if(!Server_RunThink(ent) || (ent->v.flags & FL_ONGROUND))
		return;

	Game->Physics_CheckVelocity(ent);

	// Add gravity
	if(ent->v.movetype != MOVETYPE_FLY
	&& ent->v.movetype != MOVETYPE_FLYMISSILE
	&& ent->v.movetype != MOVETYPE_FLYBOUNCE)
		Game->Physics_SetGravity(ent);

	// Move angles
	Math_VectorMA(ent->v.angles,host_frametime,ent->v.avelocity,ent->v.angles);

	// Move origin
	Math_VectorScale(ent->v.velocity,host_frametime,move);
	trace = SV_PushEntity(ent, move);
	if(trace.fraction == 1.0f || ent->free)
		return;

	if(ent->v.movetype == MOVETYPE_FLYBOUNCE)
		backoff = 2.0f;
	else if (ent->v.movetype == MOVETYPE_BOUNCE)
		backoff = 1.5f;
	else
		backoff = 1.0f;

	ClipVelocity (ent->v.velocity, trace.plane.normal, ent->v.velocity, backoff);

	// Stop if on ground
	if(trace.plane.normal[2] > 0.7 || (ent->v.movetype != MOVETYPE_BOUNCE && ent->v.movetype != MOVETYPE_FLYBOUNCE))
		if(ent->v.velocity[2] < 60.0f)
		{
			ent->v.flags		= ent->v.flags | FL_ONGROUND;
			ent->v.groundentity = trace.ent;

			Math_VectorCopy(mv3Origin,ent->v.velocity);
			Math_VectorCopy(mv3Origin,ent->v.avelocity);
		}

	Game->Physics_CheckWaterTransition(ent);
}
示例#6
0
winding_t *BasePolyForPlane (plane_t *p)
{
	int			i, x;
	vec_t		max, v;
	vec3_t		org, vright, vup;
	winding_t	*w;

	// find the major axis
	max = -BOGUS_RANGE;
	x = -1;
	for (i=0 ; i<3; i++)
	{
		v = fabs(p->normal[i]);
		if (v > max)
		{
			x = i;
			max = v;
		}
	}

	if (x==-1)
		Error("BasePolyForPlane: no axis found");

	Math_VectorCopy(vec3_origin,vup);
	switch (x)
	{
	case 0:
	case 1:
		vup[2] = 1;
		break;
	case 2:
		vup[0] = 1;
		break;
	}


	v = Math_DotProduct(vup,p->normal);
	Math_VectorMA(vup,-v,p->normal,vup);
	Math_VectorNormalize(vup);

	Math_VectorScale(p->normal,p->dist,org);

	Math_CrossProduct(vup,p->normal,vright);

	Math_VectorScale(vup,8192,vup);
	Math_VectorScale(vright,8192,vright);

// project a really big	axis aligned box onto the plane
	w = NewWinding (4);

	Math_VectorSubtract(org,vright,w->points[0]);
	Math_VectorAdd(w->points[0],vup,w->points[0]);

	Math_VectorAdd(org,vright,w->points[1]);
	Math_VectorAdd(w->points[1],vup,w->points[1]);

	Math_VectorAdd(org,vright,w->points[2]);
	Math_VectorSubtract(w->points[2],vup,w->points[2]);

	Math_VectorSubtract(org,vright,w->points[3]);
	Math_VectorSubtract(w->points[3],vup,w->points[3]);

	w->numpoints = 4;

	return w;
}
void R_RenderView (void)
{
	double	time1 = 0,
			time2;

	if (r_norefresh.value)
		return;

	if (!cl.worldmodel)
		Sys_Error ("R_RenderView: NULL worldmodel");

	if(r_speeds.value)
	{
		glFinish ();
		time1 = System_DoubleTime();

		//johnfitz -- rendering statistics
		rs_brushpolys = rs_aliaspolys = rs_skypolys = rs_particles = rs_fogpolys = rs_megatexels =
		rs_dynamiclightmaps = rs_aliaspasses = rs_skypasses = rs_brushpasses = 0;
	}

	R_SetupView (); //johnfitz -- this does everything that should be done once per frame

	Video_ClearBuffer();

	//johnfitz -- stereo rendering -- full of hacky goodness
	if (r_stereo.value)
	{
		float	eyesep = Math_Clamp(-8.0f, r_stereo.value, 8.0f),
			fdepth = Math_Clamp(32.0f, r_stereodepth.value, 1024.0f);

		Math_AngleVectors(r_refdef.viewangles, vpn, vright, vup);

		// Render left eye (red)
		glColorMask(true,false,false,true);
		Math_VectorMA (r_refdef.vieworg, -0.5f * eyesep, vright, r_refdef.vieworg);
		frustum_skew = 0.5f*eyesep*NEARCLIP/fdepth;
		srand((int) (cl.time * 1000)); //sync random stuff between eyes

		R_RenderScene();

		// Render right eye (cyan)
		glClear (GL_DEPTH_BUFFER_BIT);
		glColorMask(0, 1, 1, 1);
		Math_VectorMA (r_refdef.vieworg, 1.0f * eyesep, vright, r_refdef.vieworg);
		frustum_skew = -frustum_skew;
		srand((int) (cl.time * 1000)); //sync random stuff between eyes

		R_RenderScene();

		// Restore
		glColorMask(true,true,true,true);
		Math_VectorMA (r_refdef.vieworg, -0.5f * eyesep, vright, r_refdef.vieworg);
		frustum_skew = 0.0f;
	}
	else
		R_RenderScene();
	//johnfitz

	//johnfitz -- modified r_speeds output
	time2 = System_DoubleTime();
	if(r_speeds.value == 2)
		Con_Printf(	"%3i ms  %4i/%4i wpoly %4i/%4i epoly %3i lmap %4i/%4i sky %1.1f mtex\n",
					(int)((time2-time1)*1000),
					rs_brushpolys,
					rs_brushpasses,
					rs_aliaspolys,
					rs_aliaspasses,
					rs_dynamiclightmaps,
					rs_skypolys,
					rs_skypasses,
					TexMgr_FrameUsage ());
	else if(r_speeds.value)
		Con_Printf ("%3i ms  %4i wpoly %4i epoly %3i lmap\n",
					(int)((time2-time1)*1000),
					rs_brushpolys,
					rs_aliaspolys,
					rs_dynamiclightmaps);
	//johnfitz
}