Unity初学1——角色移动控制(2d)
Posted 林浮生
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Unity初学1——角色移动控制(2d)相关的知识,希望对你有一定的参考价值。
该文来自学习chutianbo老师的笔记,链接b站
在unity中移动角色一般采用控制角色transtion属性中的position其依据的坐标轴,一般就为二元一次方程的xy轴
最简单的移动
public class RubyController : MonoBehaviour
// 每帧调用一次 Update
// 让游戏对象每帧右移 0.1
void Update()
// 创建一个 Vector2 对象 position,用来获取当前对象的位置
Vector2 position = transform.position;
// 更改 position 的 x 坐标值,让其 加上 0.05
position.x = position.x + 0.05f;
// 更新当前对象的位置到新位置
transform.position = position;
那么这样每一帧我们的角色都会向x的正方向轴移动0.05距离(帧数越高,移动越快)。
用控制来移动
public class RubyController : MonoBehaviour
// 每帧调用一次 Update
// 让游戏对象每帧右移 0.1
void Update()
// 获取水平输入,按向左,会获得 -1.0 f ; 按向右,会获得 1.0 f
float horizontal = Input.GetAxis("Horizontal");
// 获取垂直输入,按向下,会获得 -1.0 f ; 按向上,会获得 1.0 f
float vertical = Input.GetAxis("Vertical");
// 获取对象当前位置
Vector2 position = transform.position;
// 更改位置
position.x = position.x + 0.1f * horizontal;
position.y = position.y + 0.1f * vertical;
// 新位置给游戏对象
transform.position = position;
这似乎是使用unity自带的组件进行移动,通过获取默认的垂直按键和水平案件,即直接对应wasd和方向键。
第二种控制移动方式
public class RubyController : MonoBehaviour
// Start is called before the first frame update
void Start()
// Update is called once per frame
void Update()
Vector2 position = transform.position;
if (Input.GetKey("w"))
position.y = position.y + 0.05f;
else if (Input.GetKey("a"))
position.x = position.x - 0.05f;
else if (Input.GetKey("s"))
position.y = position.y - 0.05f;
else if(Input.GetKey("d"))
position.x = position.x +0.05f;
transform.position = position;
使用getkey自定义控制方式
但是第一种和第二种中使用的GetKey和GetAxis两个方法的区别在于。GetKey只有0和1的区别,不会存在0.5或者0.05。但是getAxis是一种平滑曲线(移动控制推荐)。
直接使用update移动的弊端
由于update的调用时直接和游戏帧数挂钩的,即一帧调用一次update,所以你帧数越高,角色移动越快
假设游戏30帧,那么0.1f在一秒钟移动就是0.1*30为3个单位。如果是60帧,一秒钟就是6个单位。
解决帧数影响移动速率的方法一:锁帧
void Start()
//开垂直同步//
QualitySettings.vSyncCount = 0;
//帧率设置为50//
Application.targetFrameRate = 50;
但是锁帧会降低游戏画面质量,所以我们使用单位秒来控制Ruby的行动
暂时的最终解决办法
public class RubyController : MonoBehaviour
public float speed = 0.1f;
// Start is called before the first frame update
void Start()
// Update is called once per frame
void Update()
float horizontal = Input.GetAxis("Horizontal");
float vertical = Input.GetAxis("Vertical");
Vector2 position = transform.position;
position.x = position.x + speed * horizontal * Time.deltaTime;
position.y = position.y + speed * vertical * Time.deltaTime;
transform.position = position;
这样子的话,我们会发现speed=5时才能堪堪获得原本使用帧控制时0.1的速度;
解决碰撞时的bug
如果按照上方最后一份代码控制移动,那么我们会发现在两个刚体碰撞时,我们的角色会出现鬼畜,即我们的位置先进入了碰撞体所占据的位置,然后又被弹了出来,所以这里我们需要引入物体的刚体组件来解决
void Start()
//获得当前游戏对象的刚体组件
rigidbody2d = GetComponent<Rigidbody2D>();
void Update()
horizontal = Input.GetAxis("Horizontal");
vertical = Input.GetAxis("Vertical");
//固定时间间隔刷新方法
private void FixedUpdate()
Vector2 position = transform.position;
position.x = position.x + speed * horizontal * Time.deltaTime;
position.y = position.y + speed * vertical * Time.deltaTime;
rigidbody2d.position = position;
这里我们需要将获取移动放在update中,因为这样是一帧一调用,会更加平滑,放在FixedUpdate则是约是20ms一调用。
好,常规的bug时间
在上面这套使用物理系统的移动之后,我们在后续加入敌人移动之后,在与其他有力的作用的物体碰撞之后,我们的主角也会获得一个另一个物体移动方向的力(约莫就是机器人向下走,主角在机器人下方被碰撞,主角会一直向下直到碰到其他的碰撞体)
按照解答是刚体移动不能直接使用位置赋值
所以 rigidbody2d.position = position;这一句我们要改成 rigidbody2d.MovePosition(position);
本文仅是个人初步学习unity所用
链接: Ruby’s Adventure:2D 初学者
链接:垂直同步是什么
链接:Time.deltaTime的官方文档
Unity中,3D角色的移动(斜面上)、跳跃、冲刺
参考技术A 可控制角色在xoz平面内移动。当处于斜面上时,可沿斜面移动。可控制角色从地面上跳起、向前冲刺、向下冲刺。
角色移动:PlayerMoveCtr
角色移动控制(当前使用键盘):PlayerMoveKeyboardInput
相机跟随:CamCtr
以上是关于Unity初学1——角色移动控制(2d)的主要内容,如果未能解决你的问题,请参考以下文章