【Unity基础练习--运动1 小球的平面运动】

今天继续来总结做的Unity基础练习
我觉得以后直接把我做练习过程中感觉困难的点或者是一些可以优化的点,以及教程的一些思路写出来。就不转述整体框架了。
今天的教程来自于:
Unity基础练习,运动1
这次练习1完成的是一个可运动的小球,在不使用物理引擎的情况下实现控制小球运动范围,速度控制以及加速度还有碰撞回弹效果。
完整脚本代码如下,附带了详细的注释:

using System.Collections;
using System.Collections.Generic;
using UnityEngine;

public class MovingSphere : MonoBehaviour
{
    //下方SerializeField对Unity字段序列化,这意味着它已保存在Unity编译器中公开
    //该字段仍然不受该类之外的代码影响
    [SerializeField,Range(0f,100f)]
    float maxSpeed = 10f;//调整速度

    [SerializeField,Range(0f,100f)]
    float maxAcceleration = 10f;//调整加速度

    [SerializeField]
    Rect allowedArea = new Rect(-5f,-5f,10f,10f);//新建了一个矩形结构体

    [SerializeField,Range(0f,1f)]
    float bounciness = 0.5f;//碰撞反弹量

    Vector3 velocity;//跟踪速度
    void Update(){
        Vector2 playerInput;//用一个Vector2来存储玩家的二维移动指令
        playerInput.x = Input.GetAxis("Horizontal");//让小球水平移动
        playerInput.y = Input.GetAxis("Vertical");//让小球垂直移动
        //上面这种方法控制移动是一种默认绑定
        //你可以从Edit——Project Setting——input中查看相关的设置
        playerInput = Vector2.ClampMagnitude(playerInput,1f);
        // playerInput.Normalize(); //该函数确保矢量不大于1,或者是使用上方ClampMagnitude方法
        //确保矢量不大于1可以让斜着走和其它方向的移动保持相同速度

        Vector3 desiredVelocity = new Vector3(playerInput.x,0f,playerInput.y)*maxSpeed;
        float maxSpeedChange = maxAcceleration * Time.deltaTime;//更新速度的幅度
        // if(velocity.x < desiredVelocity.x)
        // {
        //     velocity.x = Mathf.Min(velocity.x+maxSpeedChange,desiredVelocity.x);//选取最小值消除过冲
        // }
        // else if(velocity.x>desiredVelocity.x){
        //     velocity.x = Mathf.Max(velocity.x-maxSpeedChange,desiredVelocity.x);//选取最大值消除过冲效应
        // }
        //上方判定代码的简化:
        //该函数返回值为    1+3<2? 1+3:2
        velocity.x = Mathf.MoveTowards(velocity.x,desiredVelocity.x,maxSpeedChange);
        velocity.z = Mathf.MoveTowards(velocity.z,desiredVelocity.z,maxSpeedChange);
        Vector3 displacement = velocity*Time.deltaTime;//使用Time消除帧速率对速度的影响
        Vector3 newPosition = transform.localPosition + displacement;//通过约束新位置来约束球体
        if(!allowedArea.Contains(new Vector2(newPosition.x,newPosition.z)))//检查新位置是不是被包含允许区域之内,同时保证维度相同
        {
            // Mathf.Clamp(float value,float min,float max)
            // 在 Mathf.Clamp 中传入三个参数:value,min,max         
            // 限制 value的值在min,max之间,如果value大于max,则返回max,如果value小于min,则返回min,否者返回value;
            // newPosition.x = 
            //     Mathf.Clamp(newPosition.x,allowedArea.xMin,allowedArea.xMax);//让碰撞不要那么生硬
            // newPosition.z = 
            //     Mathf.Clamp(newPosition.z,allowedArea.yMin,allowedArea.yMax); 

            //以下代码是在不使用刚体和碰撞组件的情况下模拟碰撞,让小球可以快速离开墙面,而不受本来速度的影响
            if(newPosition.x<allowedArea.xMin){
                newPosition.x = allowedArea.xMin;
                velocity.x = -velocity.x+bounciness;//模拟弹回
            }
            else if(newPosition.x>allowedArea.xMax){
                newPosition.x = allowedArea.xMax;
                velocity.x = -velocity.x+bounciness;//模拟弹回
            }
            if(newPosition.z<allowedArea.yMin){
                newPosition.z = allowedArea.yMin;
                velocity.z = -velocity.z+bounciness;//模拟弹回
            }
            else if(newPosition.z>allowedArea.yMax){
                newPosition.z = allowedArea.yMax;
                velocity.z = -velocity.z+bounciness;//模拟弹回
            }
        }
        transform.localPosition = newPosition;
    }
}

一些注意事项:

1.Trail Renderer(轨迹组件)需求的材质在Unity2020中需要设置成Particles/Standard Unit

2.Input.GetAxis()函数控制移动,该方法的移动使用的键位是默认值。
你可以从Edit——Project Setting——input中查看相关的设置
在这里插入图片描述

3.【SerializeField,Range(x,y)】对Unity字段序列化,等于向编译器公开该序列。但是该字段仍然不会受除了定义类以外的别的类影响

4.ClampManitude(vector,x)可以限制向量的最大长度为x。
当x=1f时,该方法可以控制斜着走的速度(一般来说是根号二倍)与其它方向的速度相同。

5.使用Time清除帧速率对速度的影响。(主要是针对Update帧率不固定的更新方法)

6.使用Mathf.Clamp()使小球和边缘的碰撞更平滑

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值