Unity 2D Movement 物體移動案例


Unity 2D Movement 物體移動案例

導入工程

可通過Unity Asset Store導入或者自行下載導入Sunny Land

繪制地圖

  1. 制作Tile Palette

    通過Window > 2D > Tile Palette調整面板
    新建Palette

  2. 導入素材:將Sunnyland/artwork/Environment/titleset-sliced拖入Tile Palette面板

    最后導入效果如圖,如其他畫板功能類似,左鍵單擊(長按)選取,然后繪制。

    注:如果導入素材后繪制像素過小,請檢查素材Pixels Per Unit值的大小(本工程為16)

  3. 開始繪制

    在場景中添加TileMap(右鍵2D Object > Tilemap),即可利用Tile palette中的功能在場景中進行繪制。

    注:如果有多個Tilemap,可以通過在Tile palette中激活需要操作的TileMap。

    在繪制完后我們可通過組件Tilemap Collider 2D快速地添加碰撞盒

    前景:草、植物等

    ground層:地面等

    背景:牆、柱子等(通過改變Transform.Position.Z的值來改變前后關系)

    ground層

人物制作

首先簡單地導入Sunnyland\artwork\Sprites\player\idle\player-idle-1.png到場景中

為Player添加剛體及碰撞盒

Character Controller

包含Object受力、速度、狀態判斷的變量

函數:

  1. Move(float move, bool crouch, bool jump)

    move:橫向移動量

  2. Flip() —— 人物轉向

using UnityEngine;

public class CharacterController2D : MonoBehaviour {
	[SerializeField] private float m_JumpForce = 400f;                          // Amount of force added when the player jumps.
	[Range(0, 1)] [SerializeField] private float m_CrouchSpeed = .36f;          // Amount of maxSpeed applied to crouching movement. 1 = 100%
	[Range(0, .3f)] [SerializeField] private float m_MovementSmoothing = .05f;  // How much to smooth out the movement
	[SerializeField] private bool m_AirControl = false;                         // Whether or not a player can steer while jumping;
	[SerializeField] private LayerMask m_WhatIsGround;                          // A mask determining what is ground to the character
	[SerializeField] private Transform m_GroundCheck;                           // A position marking where to check if the player is grounded.
	[SerializeField] private Transform m_CeilingCheck;                          // A position marking where to check for ceilings
	[SerializeField] private Collider2D m_CrouchDisableCollider;                // A collider that will be disabled when crouching

	const float k_GroundedRadius = .2f; // Radius of the overlap circle to determine if grounded
	private bool m_Grounded;            // Whether or not the player is grounded.
	const float k_CeilingRadius = .2f; // Radius of the overlap circle to determine if the player can stand up
	private Rigidbody2D m_Rigidbody2D;
	private bool m_FacingRight = true;  // For determining which way the player is currently facing.
	private Vector3 velocity = Vector3.zero;

	private void Awake() {
		m_Rigidbody2D = GetComponent<Rigidbody2D>();
	}


	private void FixedUpdate() {
		m_Grounded = false;

		// The player is grounded if a circlecast to the groundcheck position hits anything designated as ground
		// This can be done using layers instead but Sample Assets will not overwrite your project settings.
		Collider2D[] colliders = Physics2D.OverlapCircleAll(m_GroundCheck.position, k_GroundedRadius, m_WhatIsGround);
		for (int i = 0; i < colliders.Length; i++) {
			if (colliders[i].gameObject != gameObject)
				m_Grounded = true;
		}
	}

	public void Move(float move, bool crouch, bool jump) {
		// If crouching, check to see if the character can stand up
		if (!crouch) {
			// If the character has a ceiling preventing them from standing up, keep them crouching
			if (Physics2D.OverlapCircle(m_CeilingCheck.position, k_CeilingRadius, m_WhatIsGround)) {
				crouch = true;
			}
		}

		//only control the player if grounded or airControl is turned on
		if (m_Grounded || m_AirControl) {

			// If crouching
			if (crouch) {
				// Reduce the speed by the crouchSpeed multiplier
				move *= m_CrouchSpeed;

				// Disable one of the colliders when crouching
				if (m_CrouchDisableCollider != null)
					m_CrouchDisableCollider.enabled = false;
			} else {
				// Enable the collider when not crouching
				if (m_CrouchDisableCollider != null)
					m_CrouchDisableCollider.enabled = true;
			}

			// Move the character by finding the target velocity
			Vector3 targetVelocity = new Vector2(move * 10f, m_Rigidbody2D.velocity.y);
			// And then smoothing it out and applying it to the character
			m_Rigidbody2D.velocity = Vector3.SmoothDamp(m_Rigidbody2D.velocity, targetVelocity, ref velocity, m_MovementSmoothing);

			// If the input is moving the player right and the player is facing left...
			if (move > 0 && !m_FacingRight) {
				// ... flip the player.
				Flip();
			}
			// Otherwise if the input is moving the player left and the player is facing right...
			else if (move < 0 && m_FacingRight) {
				// ... flip the player.
				Flip();
			}
		}
		// If the player should jump...
		if (m_Grounded && jump) {
			// Add a vertical force to the player.
			m_Grounded = false;
			m_Rigidbody2D.AddForce(new Vector2(0f, m_JumpForce));
		}
	}


	private void Flip() {
		// Switch the way the player is labelled as facing.
		m_FacingRight = !m_FacingRight;

		// Multiply the player's x local scale by -1.
		Vector3 theScale = transform.localScale;
		theScale.x *= -1;
		transform.localScale = theScale;
	}
}

Player Move Controller

Input.GetAxisRaw("Horizontal") —— 獲取橫向移動量,x的正方向移動為1,x的負方向移動-1,站立不動為0

Input.GetButtonDown("Jump") —— 判斷按下"Jump"的指令

Edit > Project Settings > Input Manager設定Input系統

例如:Jump通過space鍵觸發

我們需要添加Crouch判定,觸發爬行行為

using UnityEngine;

public class PlayerMoveController : MonoBehaviour {

	private CharacterController2D cc;

	private float move = 0f;
	private bool jump = false;
	private bool crouch = false;

	private void Awake() {
		cc = GetComponent<CharacterController2D>();
	}

	// Update is called once per frame
	void Update() {

		move = Input.GetAxisRaw("Horizontal");

		if (Input.GetButtonDown("Jump"))
			jump = true;
		
		if (Input.GetButtonDown("Crouch"))
			crouch = true;
		else if (Input.GetButtonUp("Crouch"))
			crouch = false;
	
	}

	private void FixedUpdate() {

		cc.Move(move, crouch, jump);
		jump = false;

	}

}

其他設置

  1. Player腳本相關設置

​ 也可以通過Rigidbody調整物體的重力因素等,如Gravity Scale()、Collision Detection(剛體的碰撞檢測模式)。

  1. 設置ColliderMaterial(減少摩擦)

    在project面板中右鍵 > Create > Physics Material 2D,將Friction參數設置為0。

    拖動該material到collider上。

演示


按住"Crouch"鍵,進入爬行狀態,隱藏頭部碰撞盒

補充

Gitee工程源碼


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM