Unity3D的角色控制逻辑总结

Posted by Kriz on 2017-05-23

MonoBehaviour类各方法的调用顺序

  1. 场景启动时调用所有脚本的Awake()
  2. 调用所有脚本的Start()
  3. 调用Update()
  4. 调用FixedUpdate()(调用频率和帧数有关,由系统自动确定。一般用在力学更新效果中)
  5. 调用LateUpdate()(Update和LateUpdate都是一帧调用一次,先Update再LateUpdate。eg:用Update更新人物位置后,使用LateUpdate让摄像机跟随人物移动)

更详细的内容参考这个:

process

对象销毁

调用Destroy销毁GameObject

1
2
Destroy(gameObject);
Destroy(gameObject, 3); //等待3秒销毁

销毁对象时调用OnDestroy

(On开头的方法,是由其他事件触发调用的。如:OnDestory:物体被删除时调用;OnEnable:物体启用时被调用;OnDisable:物体被禁用时调用。)

脚本间通信

通过GetComponent来找到其他脚本

通过GameObject.Find来找到其他物体

控制角色前进

在Update函数中调用

1
2
3
void WalkForward() {
transform.position = transform.position + walkSpeed * transform.forward * Time.deltaTime;
}

这里要注意:在Update/LateUpdate中打印Time.deltaTime时间是不固定的,是一个动态变化值,是前两帧之间时间的差值;而在FixedUpdate中打印Time.deltaTime时间是固定的。

初始化跟踪摄像机

在player的Start中调用

1
GameObject.Find("Main Camera").GetComponent<SceneCamera>().player = this.gameObject;

再切到SceneCamera.cs,在LateUpdate中调用

1
2
if (player != null)
camera.transform.LookAt(player.transform.position);

设置游戏输入

Edit->Project Settings->Input。

在脚本中利用Input类来检测输入状态。Input.GetAxis返回的值在-1到1之间,0表示没有输入。

如果要通过键盘输入控制player移动,在设置好Input的Horizontal和Vertical属性后,修改Update

1
2
3
4
Debug.Log("Horizontal value: " + Input.GetAxis("Horizontal"));
// 在console中输出
Vector3 direction = Input.GetAxis("Horizontal") * transform.right + Input.GetAxis("Vertical") * transform.forward;
transform.position = transform.position + walkSpeed * direction * Time.deltaTime;

如果使用鼠标点击事件控制player移动:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
void Update() {
...
if(Input.GetMouseButtonUp(0)){
ClickOn(input.mousePosition);
}
}
void ClickOn(Vector2 pos) {
if(player == null)
return;
Ray ray = this.camera.ScreenPointToRay(pos);
RaycastHit[] hits = Physics.RaycastAll(ray);
foreach(RaycastHit hit in hits) {
BoxCollider bc = hit.collider as BoxCollider;
if (bc != null && bc.name.Contains("floor") && player != null) {
player.GetComponent<Player>().WalkTo(hit.point);
break;
}
}
}
//WalkTo函数好像有bug就不写了【逃