Unity基础练习与总结

向量和四元数练习

void Start()
    {
        Vector3 A = new Vector3(1, 2, 3);
        Vector3 B = new Vector3(4, 5, 6);
        //1.向量的模长 就是 两个点之间的距离
        Vector3 AB = B - A;//终点 - 起点
        //通过向量得到长度
        print(AB.magnitude);
        //通过API得到长度
        print(Vector3.Distance(A,B));

        //2.单位向量 就是 只需要方向 不需要模长
        print(AB.normalized);

        //3.向量模长的计算 根号下每个数的平方相加
        //4.单位向量的计算 先计算出模长 在分别除以向量

        //摄像机跟随
        //写在LateUpdate中 
        //void LateUpdate()
        //{
        //    //摄像机的位置 =  目标位置 + 偏移
        //    this.transform.position = cubeTrans.position + cubeTrans.forward * 5 + cubeTrans.up * 10;
        //    this.transform.LookAt(cubeTrans);
        //}
        
        //向量点乘
        //1.假设有一个物体 不确定他在我的前面还是后面 就可以通过向量点乘的方式来判断
        //通过正前方的向量 * 向量(目标位置 - 我的位置 得到向量)判断这个角度是否大于等于90°就在前面 小于就在后面 
        float f =  Vector3.Dot(this.transform.forward, trans.position - this.transform.position);
        //2.通过公式推导计算出夹角
        //*****************************
        //使用API
        float f1 =  Vector3.Angle(this.trans.forward, trans.position - this.transform.position);

	/*void Update()
    {
        //画一条射线
        //第一个参数是起始位置
        //第二个参数是方向
        Debug.DrawRay(this.transform.position,trans.position - this.transform.position,Color.blue);

        //小练习
        float f1 = Vector3.Angle(this.trans.forward, trans.position - this.transform.position);
        if (f1 <= 22.5f && Vector3.Distance(this.trans.position,this.transform.position) <= 5)
        {
            Debug.Log("123");
        }
    }
    */
    
    	//向量叉乘
    	//传入的值都代表向量
    	Vector3 v = Vector3.Cross(A.position, B.position);
        if(v.y > 0)
        {
            Debug.Log("B在A的右侧");
        }
        else
        {
            Debug.Log("B在A的左侧");
        }
        //叉乘的几何意义
        //点乘只能判断一个物体在某个角度范围内 但不能确定左右
        //叉乘会根据Y值判断出一个物体的左右
    	}
    	
    	//小练习 判断一个物体在哪里
    	Debug.DrawRay(this.A.position, this.B.position - this.A.position, Color.green);
        //点乘 前方向量 * 向量
        float f1 = Vector3.Dot(A.forward, B.position - A.position);
        //叉乘 法向量
        Vector3 v1 = Vector3.Cross(A.forward, B.position - A.position);
        //后面的 判断前面的
        //点乘大于0 说明在前面
        if (f1 >= 0)
        {
            //叉乘的y大于0 说明在右边
            if (v1.y >= 0)
            {
                Debug.Log("B在A的右前");
            }
            //小于0 在左边
            else
            {
                Debug.Log("B在A的左前");
            }
        }
        //叉乘小于0 说明在后面
        else
        {
            //叉乘的y大于0 说明在右边
            if (v1.y >= 0)
            {
                Debug.Log("B在A的右后");
            }
            else
            {
                Debug.Log("B在A的左后");
            }
        }
        //计算角度
        float f2 = Vector3.Angle(A.forward, B.position - A.position);
        //可以根据角度判断物体小于or大于多少度


		//向量插值运算
		//插值
		//start是起始位置 end是终止位置 time是0-1取值
		//计算公式 = start + (end - start)* t
		//先快后慢 无限趋近于end 但不会等于end
        float start =  Vector3.Lerp(start,end,Time.deltatime);
		//匀速
		//start是恒定不动的 所以是匀速的
		time += Time.deltatime;
		float result = Vector3.Lerp(start,end,nowTime);
        //球形插值
        Vector3.Slerp(start, end, time);


		//四元数
		//轴 角对
        Quaternion q = Quaternion.AngleAxis(1, Vector3.up);
        //四元数解决欧拉角1.同一角度表示不唯一 2.万向节死锁问题
        //四元数只会表示180 - 负180 
        //四元数相乘表示旋转

        //单位四元数
        this.transform.rotation = Quaternion.identity;
        //LookRotation(传入一个方向向量)
        Quaternion.LookRotation(target.postion - this.transform.position);

		//小练习 假设Transform没有LookAt方法 利用四元数的LookRotation方法实现该方法
public static class 基础 
{
	//C#拓展方法的练习 首先类是静态的 函数也是静态的
	//第一个参数就是调用者本身 第二个参数是目标值
    public static void MyLookAt(this Transform obj,Transform target)
    {
        Quaternion q =  Quaternion.LookRotation(target.position - obj.position);
        obj.transform.rotation = q;
    }
}

四元数小练习

//飞机四种发射子弹的方式 分别是单发 双发 扇形 四周发射
public enum E_TypeFire
{
    One,
    Two,
    Three,
    Four
}
public class 基础 : MonoBehaviour
{
    public E_TypeFire type = E_TypeFire.One;
    public GameObject bullet;
    public int num = 4;
    void Start()
    {
        
    }

    // Update is called once per frame
    void Update()
    {
        if (Input.GetKeyDown(KeyCode.Alpha0))
        {
            type = E_TypeFire.One;
        }
        else if (Input.GetKeyDown(KeyCode.Alpha1))
        {
            type = E_TypeFire.Two;
        }
        else if (Input.GetKeyDown(KeyCode.Alpha2))
        {
            type = E_TypeFire.Three;
        }
        else if (Input.GetKeyDown(KeyCode.Alpha3))
        {
            type = E_TypeFire.Four;
        }
        if(Input.GetKeyDown(KeyCode.Space))
        {
            Fire();
        }
    }

    public void Fire()
    {
        switch(type)
        {
            case E_TypeFire.One:
                Instantiate(bullet, this.transform.position, this.transform.rotation);
                break;
            case E_TypeFire.Two:
                Instantiate(bullet,this.transform.position + this.transform.right * 0.5f , this.transform.rotation);
                Instantiate(bullet,this.transform.position - this.transform.right * 0.5f , this.transform.rotation);
                break;
            case E_TypeFire.Three:
                Instantiate(bullet, this.transform.position, this.transform.rotation);
                //四元数相乘 = 新四元数 相当于旋转量的叠加
                //四元数:转多少度 绕哪个轴
                Instantiate(bullet, this.transform.position, this.transform.rotation * Quaternion.AngleAxis(-20,Vector3.up));
                Instantiate(bullet, this.transform.position, this.transform.rotation * Quaternion.AngleAxis(20, Vector3.up));
                break;
            case E_TypeFire.Four:
                float angle = 360 / num;
                for(int i = 0; i < num; i++)
                {
                    //0 90 180 270
                    Instantiate(bullet, this.transform.position, this.transform.rotation * Quaternion.AngleAxis(i * angle,Vector3.up));
                }
                break;
        }
    }
}

四元数计算练习2

public class CameraMove : MonoBehaviour
{
    //目标对象
    public Transform cube;
    //头顶偏移
    public int headOffset;
    //倾斜角度
    public int rotaAngle;
    //观测距离
    public float distance;

    Vector3 nowPos;
    void Start()
    {
        
    }

    // Update is called once per frame
    void Update()
    {
        distance += Input.GetAxis("Mouse ScrollWheel");
        distance = Mathf.Clamp(distance, 2, 10);

        //头顶偏移
        this.nowPos = cube.position + cube.up * headOffset;
        //后方偏移
        this.nowPos = cube.position +Quaternion.AngleAxis(rotaAngle,cube.right) * -cube.forward * distance;

        this.transform.position = nowPos;

        Quaternion q = Quaternion.LookRotation(-(Quaternion.AngleAxis(rotaAngle, cube.right) * -cube.forward));
        this.transform.rotation = Quaternion.Slerp(this.transform.rotation,q,Time.deltaTime * 5f);
    }
}

范围检测练习

//范围检测分为三种 盒 胶囊 圆
//盒参数 中心点 大小 旋转角度 层级 是否忽略触发器
//胶囊参数 起点 终点 大小 层级 是否忽略触发器
//圆参数 中心点 半径 层级 是否忽略触发器
void Update()
    {
        this.transform.Translate(Vector3.forward * moveSpeed * Time.deltaTime * Input.GetAxis("Vertical"));
        this.transform.Rotate(Vector3.up, rotaSpeed * Time.deltaTime * Input.GetAxis("Horizontal"));

        if(Input.GetKeyDown(KeyCode.J))
        {
            Collider[] colliders = Physics.OverlapBox(this.transform.position + this.transform.forward, 
                                                      Vector3.one,
                                                      this.transform.rotation,
                                                      1 << LayerMask.NameToLayer("Monster"),
                                                      QueryTriggerInteraction.UseGlobal);
            for(int i = 0; i < colliders.Length; i++)
            {
                print(colliders[i].name);
            }
        }
        if (Input.GetKeyDown(KeyCode.K))
        {
            Collider[] colliders2 = Physics.OverlapCapsule(this.transform.position, this.transform.position + this.transform.forward * 5,
                                   0.5f,
                                   1 << LayerMask.NameToLayer("Monster"));
            for (int i = 0; i < colliders2.Length; i++)
            {
                print(colliders2[i].name);
            }
        }
        if (Input.GetKeyDown(KeyCode.L))
        {
            Collider[] colliders3 = Physics.OverlapSphere(this.transform.position,10,
                                   1 << LayerMask.NameToLayer("Monster"));
            for (int i = 0; i < colliders3.Length; i++)
            {
                print(colliders3[i].name);
            }
        }

射线检测练习

//射线检测 
//实例化一条射线 第一个参数是起点 第二个参数是方向向量
//射线检测RayCast的参数 射线 最大距离 层级 是否忽略触发器(只能判断是否碰撞 获取不到碰撞的对象)
//所以使用另一个重载 就是射线改为 起点 和 方向

//获取相交物体单个的信息
//RaycastHit的参数 射线 out(返回数据)距离 层级 是否忽略触发器
//获取相交物体多个的信息
//RaycastHitAll的参数 射线 距离 层级 是否忽略触发器

//使用的时候注意看重载 容易记混乱 写错
void Update()
    {
        #region
        //子弹射击练习
        this.transform.Translate(Vector3.forward * moveSpeed * Time.deltaTime * Input.GetAxis("Vertical"));
        this.transform.Rotate(Vector3.up, rotaSpeed * Time.deltaTime * Input.GetAxis("Horizontal"));

        Ray y = Camera.main.ScreenPointToRay(Input.mousePosition);
        Debug.DrawLine(y.origin,y.direction);
        if (Input.GetMouseButtonDown(0))
        {
            if(Physics.Raycast(Camera.main.ScreenPointToRay(Input.mousePosition),out hit,1000,1 << LayerMask.NameToLayer("Monster")))
            {
                //创建打击特效
                GameObject eff = Instantiate(Resources.Load<GameObject>("eff"));
                //设置特效点位置
                //位置有重合 让特效在外面一点
                eff.transform.position = hit.point + hit.normal * 0.5f;
                //设置角度朝向自己
                //四元数API中写入法向量 得到一个朝向自己的四元数 赋值给旋转
                eff.transform.rotation = Quaternion.LookRotation(hit.normal);
            }
        }
        #endregion


        //game窗口随意拖动立方体练习
        if(Input.GetMouseButtonDown(0))
        {
            if(Physics.Raycast(Camera.main.ScreenPointToRay(Input.mousePosition),out hit, 1000,1 << LayerMask.NameToLayer("Cube")))
            {
            	//设置cube的transform 就是 碰撞物
                cube = hit.transform;
            }
        }
        //长按移动
        if(Input.GetMouseButton(0) && cube != null)
        {
        	//射线检测 地板
        	//根据地板点击碰撞点的位置 设置cube的位置
            if (Physics.Raycast(Camera.main.ScreenPointToRay(Input.mousePosition), out hit, 1000, 1 << LayerMask.NameToLayer("Floor")))
            {
                //设置立方体等于地板上的点
                //偏移一定高度 让cube在地板上 而不是和地板重合或者在下面
                cube.position = hit.point + Vector3.up * 0.55f;
            }
        }
        if(Input.GetMouseButtonDown(1))
        {
            cube = null;
        }
    }
  • 3
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值