1:《地牢守卫者》代码解析PlayerController

Posted on 2012-02-23 18:02  neocsl  阅读(894)  评论(0编辑  收藏  举报

  UDK中有强大的Archetype机制,因此利用该机制spawn一个敌人template将与传统的方式有所不同。

比如以下的代码spawn一个template:

exec function SpawnEnemy()
{
local AntEnemy AntEnemyTemplate;

AntEnemyTemplate=AntEnemy(DynamicLoadObject(Archetype.AntEnemy,class'AntEnemy'));
//LoadObject 在主机平台不适用,iphone不知道
Spawn(class'AntEnemy',,,Pawn.Location+(vect(100,0,0)>>Pawn.Rotation),rot(0,0,0),AntEnemyTemplate,true);
//与传统的spawn不同之处是,后边得指定模板template
}


在控制台中可以建立一些杀死敌人或自己的调试函数

exec function killEnemy()
{
local AntEnemy KEnemy;

foreach DynamicActors(class'AntEnemy',KEnemy)
{
KEnemy.TakeDamage(1000,none,KEnemy.Location,vect(0,0,0),class'DamageType');
}
}

 

在我开发的上一个游戏中当时还没有办法让死掉的尸体掩藏掉,这里将会提及方法:

var pawn LastDiedPawn;


event Possess(pawn inpawn,bool bVehicleTransition)
{
if(LastDiedPawn!=none) //这里获取的是上一次死亡的pawn,下面的程序执行让其毁掉尸体
{
AntPlayer(LastDiedPawn).PlayDestroyEffect();
LastDiedPawn=none;
}
super.Possess(inpawn,bVehicleTransition);
  AntPlayer(inpawn).CreateInventoryFromTemplate(WeaponUpgrades[CurrentWeaponUpgradeLevel].WeaponTemplate);
}


function pawnDied(pawn inpawn)
{
LastDiedPawn=pawn; //这里将要死的pawn赋予LastDiedPawn
super.PawnDied(inpawn);
}

因为金币AntManaToken要加入到得分系统中,所以得要调用金币的函数销毁自己,同时给controller和HUD同时更新ManaPower的值

function ManaTokenCollected(ManaToken Token)
{
token.collected(AntPlayer(pawn)); //destroy self
AddManaPower(token.ManaPower); //point
}



function AddManaPower(float SignedManaPower)
{
ManaPower=Clamp(ManaPower+SignedManaPower,0,MaxManaPower);

if(myHUD!=none)
AntHUD(myHUD).NotifyUpdateManaPower();
}

Now the UDK theory about HUD calculation is that everything is supposed to be calculated in a function called PostRender.

function PostRender()

{

  //变量的一些运算,运算完结后送到DrawHUD()中进行渲染

DrawHUD(); //通常DrawHUD是在PostRender中调用的
}


升级武器中的算法

exec function UpgradeWeapon()

{

  if(Pawn==none)

  return;

  

  nextLevel = GetNextWeaponUpgradeLevel();

  if(Pawn.Physics!=Phys_Walking||nextLevel==Wu_MAx||ManaPower<WeaponUpgrades[nextLevel].ManaCost)

  {

    PlaySpellInvalidSound();

    return;
  }

  PlaySpellValidSound();

  PushState();
}

关键在if中的条件判断pawn.Physics!=PHYS_Walking||nextLevel==WU_Max||ManaPower<UpgradeWeapon[nextLevel].ManaCost

本章的精髓原本是复杂的放置塔的状态,在这里先略过,着重将player的元素完善。以后将会完善放置塔的程序。

 

state PlayerWalking状态中有两个重要的函数PlayerMove和ProcessMove,前者将调用后者对角色进行运动处理。

如果摄像机在PlayerController的GetPlayerViewPoint改良,使用ProcessMove将会简单

function ProcessMove(flaot DeltaTime,Vector newAccel,eDoubleClickDir DoubleClickMove, rotator DeltaRot)

{

  local vector X,Y,Z,AltAccel;

  GetAxes(CameraRotation,X,Y,Z);

  AltAccel=PlayerInput.AForward*Z+PlayerInput.AStrafe*Y;

  AltAccel.Z=0;

  AltAccel=Pawn.AccelRate*Normal(AltAccel);

  super.ProcessMove(DeltaTime,AltAccel,DoubleClickMove,DeltaRot);

  
}

前面提到了改良摄像机,这里着手改良摄像机

var vector PlayerViewOffset;
var rotator CurrentCameraRotation;

simulated event GetPlayerViewPoint(out vector out_location,out rotator out_rotation)
{
if(Pawn!=none)
{
out_location=location+(PlayerViewoffset);
out_rotation=location-PlayerViweoffset;
}


}

defaulrproperties中声明以下

InputClass=class'AntInput'

CameraClass=class'AntCamera'

到这里PlayerController先简单结束,以后再进行补全。