⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 character.cpp

📁 《光线引擎演示程序》执行程序+源代码,《光线引擎演示程序》执行程序+源代码
💻 CPP
字号:


#include "character.h"


extern LightSolid *foot, *body;
// 摄像机参数
extern vec3_t eye, center;

// 渲染角色
void Character::Render()
{
	float angle;

	// 显示骨骼动画
	player.md3->SetPos( player.pos[0], player.pos[1]-16, player.pos[2] );
	angle = 360 - (player.rotate[0] * (( float)180 / G_PI )) + 90;
	player.md3->SetRotate( angle, 0, 1.0f, 0 );
	player.md3->Render();
}

// 渲染角色阴影
void Character::RenderShadow()
{
	float angle;

	// 显示骨骼动画
	player.md3->SetPos( player.pos[0], player.pos[1]-16, player.pos[2] );
	angle = 360 - (player.rotate[0] * (( float)180 / G_PI )) + 90;
	player.md3->SetRotate( angle, 0, 1.0f, 0 );
	player.md3->RenderShadow();
}

// 读取角色资源
int Character::Load()
{
	player.pos[0] = -100;
	player.pos[1] = 50;
	player.pos[2] = -200;

	player.rotate[0] = 0;
	player.rotate[1] = 0;
	player.rotate[2] = 0;
	player.mouse_speed = 500;
	player.viewline = 150;	
	player.forward = 0;
	player.right = 0;
	player.lastforward = 0;
	player.lastright = 0;
	player.move = 0;
	player.velocity = 200.0f;
	player.lower = 1;
	player.upper = 0;
	player.shoot = 0;
	player.jump = 0;
	player.jumptime = 0;
	//////////////////////
	// 防止地面摩擦
	//player.pos[2] +=5;
	//////////////////////

	// 读入声音文件
	player.sjump = engine->NewSound();
	player.step[0] = engine->NewSound();
	player.step[1] = engine->NewSound();
	player.step[2] = engine->NewSound();
	player.step[3] = engine->NewSound();
	player.m4a1[0] = engine->NewSound();
	player.m4a1[1] = engine->NewSound();
	player.m4a1[2] = engine->NewSound();
	player.m4a1[3] = engine->NewSound();
	player.hit = engine->NewSound();
	player.biggun = engine->NewSound();
	player.sjump->Load( "jump.wav" );	
	player.step[0]->Load( "step.wav" );	
	player.m4a1[0]->Load( "m4a1_unsil.wav" );
	player.hit->Load( "hit.wav" );
	player.step[0]->SetMinDistance( 50 );
	player.m4a1[0]->SetMinDistance( 100 );

	// 通过指定该人物所有模型的前缀来读取模型文件
	player.md3 = engine->NewModelMD3();
	player.md3->LoadModel( "lara" );
	player.md3->LoadWeapon( "Railgun" );
	player.md3->SetUpperState("TORSO_STAND");	
	player.md3->SetLowerState("LEGS_IDLE");

	player.md3->Adjust( 0, -7, 0 );
	player.md3->SetBoundBox( 26, 60, 26 );

	g_vVelocity.x = 0;
	g_vVelocity.y = 0;
	g_vVelocity.z = 0;
	g_FrameInterval = 0.0f;

	rotate[0] = 0;
	rotate[1] = 0;
	rotate[2] = 0;

	return 0;
}

// 更新角色状态
int Character::Update()
{
	POINT point;
	int x, y, cx, cy;
	vec3_t upright;
	RECT rect;
	int time;

	time = engine->GetTickCount();

	// 保存玩家原来坐标
	CVector3 vOldPosition;
	CVector3 vCurrentPosition;
	CVector3 vNewPosition;

	///////////////////////////////////
	player.md3->GetPos( player.pos );
	///////////////////////////////////

	vOldPosition.x = player.pos[0];
	vOldPosition.y = player.pos[1];
	vOldPosition.z = player.pos[2];

	// 处理跳的动作
	if( player.jump )
	{
		if( player.md3->IsOnGround() )
		{
			// 跳起
			if( player.jumptime == 0  )
			{
				g_vVelocity.y = kJumpAcceleration;
				player.md3->SetLowerState("LEGS_JUMP");				
				player.sjump->SetPosition( player.pos[0], player.pos[1], player.pos[2] );
				player.sjump->Play();
				player.jumptime = time;
				player.lower = 5;
			}
			// 落下
			else
			if( time - player.jumptime > 700 )
			{
				g_vVelocity.y = 0;
				player.jump = 0;
				player.jumptime = 0;
			} 
		}
	}

	// 重力加速度
	g_FrameInterval = ( double )( time - player.lasttime ) * 0.001f;
	g_vVelocity.y -= (float)(kGravity * g_FrameInterval);

	// 计算摄像机参数
	vec3_t move;
	float s1 = (float)player.velocity * ( time - player.lasttime ) * 0.001f;
	move[1] = s1 * player.forward;
	move[0] = s1 * 0.4 * player.right;
	move[2] = g_vVelocity.y;
	camera->Rotate( player.pos, rotate, 150, move, FALSE, player.direction, player.eyes, player.up );

	if( player.forward || player.right )
	{
		// 设置模型动作
		if ( player.lower != 4 )
		{
			player.lower = 4;
			player.md3->SetLowerState("LEGS_RUN");
		}
		// 播放脚步声
		if( time - player.steptime > 300 )
		{
			player.step[0]->SetPosition( player.pos[0], player.pos[1], player.pos[2] );
			player.step[0]->Play();
			player.steptime = time;
		}
	}
	else
	{
		// 设置模型动作
		if ( player.lower == 4 || (player.lower == 5 && player.jump == 0) )
		{
			player.lower = 1;			
			player.md3->SetLowerState("LEGS_IDLE");			
		}
	}


	// 进行碰撞检测,并计算碰撞后坐标
	/*vCurrentPosition.x = player.pos[0] + player.direction[0];
	vCurrentPosition.y = player.pos[1] + player.direction[1];
	vCurrentPosition.z = player.pos[2] + player.direction[2];

	// Check for collision with AABB's and grab the new position
	vNewPosition = g_Level->TraceBox(vOldPosition, vCurrentPosition,
		                             CVector3(-20, -40, -20), CVector3(20, 40, 20));
	// 检测每个模型是否发生碰撞
	vec3_t p1, p2, cross;
	vec3_t min = { -20-400, -40+50, -20+750 };
	vec3_t max = { 20-400, 40+50, 20+750 };

	p1[0] = vOldPosition.x;
	p1[1] = vOldPosition.y;
	p1[2] = vOldPosition.z;
	p2[0] = vNewPosition.x;
	p2[1] = vNewPosition.y;
	p2[2] = vNewPosition.z;
	if( !player.md3->CrossBox( p1, p2, min, max, cross ) )
	{
		player.pos[0] = vNewPosition.x;
		player.pos[1] = vNewPosition.y;
		player.pos[2] = vNewPosition.z;
	}*/
	
	// 对几何体物理施加速度
	/*if( player.forward != player.lastforward || player.right != player.lastright )
	{
		float v = 20;
		if( player.forward || player.right )
			//foot->AddForce( player.direction[0]*v, player.direction[1]*v, player.direction[2]*v );
			//foot->SetLinearVel( player.direction[0]*v, player.direction[1]*v, player.direction[2]*v );
			foot->SetAngularVel( 5, 5, 0 );
		else
		{
			foot->SetLinearVel( 0, 0, 0 );
			foot->SetAngularVel( 0, 0, 0 );
		}
		player.lastforward = player.forward;
		player.lastright = player.right;
	}*/

	// 进行碰撞检测,并计算碰撞后坐标
	vCurrentPosition.x = player.pos[0] + player.direction[0];
	vCurrentPosition.y = player.pos[1] + player.direction[1];
	vCurrentPosition.z = player.pos[2] + player.direction[2];
	player.md3->Goto( vCurrentPosition.x, vCurrentPosition.y, vCurrentPosition.z );

	if( player.md3->IsOnGround())
		if( g_vVelocity.y < 0.0f )
			g_vVelocity.y = 0.0f;

	// 射击处理
	if( player.shoot == 1 )
	{
		if( time - player.shoottime > 100 )
		{
			player.upper = 1;
			player.m4a1[0]->SetPosition( player.pos[0], player.pos[1], player.pos[2] );
			player.m4a1[0]->Play();
			player.shoottime = time;
			player.md3->SetUpperState( "TORSO_ATTACK" );
			player.shoot = 0;
			// 检测 boss 是否被打中
			vec3_t cross;
			if( player.boss->CrossRay( eye, center, cross ) )
			{
				player.boss->SetUpperState( "TORSO_GESTURE" );
				player.boss->SetLowerState( "LEGS_LANDB" );
			}
		}
	}
	else
	if( player.shoot == 2 )
	{
		if( ((player.upper == 1) && (time - player.shoottime > 100) ) ||
			((player.upper == 2) && (time - player.shoottime > 500) ) ||
			  player.upper == 0 )
		{
			player.upper = 2;
			player.hit->SetPosition( player.pos[0], player.pos[1], player.pos[2] );
			player.hit->Play();
			player.shoottime = time;
			player.md3->SetUpperState( "TORSO_ATTACK2" );
			player.shoot = 0;
		}
	}
	else
	// 站立状态
	if( ((player.upper == 1) && (time - player.shoottime > 100) ) ||
		((player.upper == 2) && (time - player.shoottime > 500) ) )	
	{
		player.upper = 0;
		player.md3->SetUpperState( "TORSO_STAND" );
	    player.shoot = 0;
	}
	else
	if( player.upper == 0 )
		player.shoottime = time;

	player.lasttime = time;

	// 将摄像机局部坐标转换成全局坐标	
	player.eyes[0] += player.pos[0];
	player.eyes[1] += player.pos[1];
	player.eyes[2] += player.pos[2];

	player.up[0] += player.eyes[0];
	player.up[1] += player.eyes[1];
	player.up[2] += player.eyes[2];

	// 保存摄像机旋转角度
	player.rotate[0] = rotate[0];
	player.rotate[1] = rotate[1];

	return 0;
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -