Unity学习笔记 03 —— 三维数学

Unity更多API

射线

Ray ray - new Ray();    // 新建射线
ray.origin = transform.position;    // 射线起点设置为当前游戏对象的位置
ray.direction = transform.forward;  // 射线方向设置为当前游戏对象前方
Debug.DrawRay(ray.origin, ray.direction);    // 使用Debug查看射线,仅在场景模式下可见
// 发射一条射线
// 将射线碰到的第一个对象的相关信息以RaycastHit的类型传递到hit中(注意out关键字)
if (Physics.Raycast(ray, out RaycastHit hit, 100, layerMask))
{
    Debug.Log(hit.collider.gameObject.name);
}

三维数学运算

向量

基础
Vector3 position = transform.position;    // 获取世界原点到物体A的向量
Vector3 cubePosition = cube.transform.position;
Vector3 diff = position - cubePosition; // 向量减法,减数指向被减数
cubePosition.Translate(diff);    // 使cube移动到物体A的位置
Vector3 normalizedPosition = position.normalized;    // 获取向量方向上的单位向量,不会改变当前向量
position.Nomalize(); // 单位化向量,会改变当前向量
简单应用
Vector3 curVec = transform.forward;
Vector3 cubeVec = cube.transform.forward;
Vector3.Dot(curVec, cubeVec);    // 点乘
Vector3.Cross(curVec, cubeVec);  // 叉乘


// 计算向量夹角
// 以°为单位,获取180°以内的角度
float angle = Mathf.Acos(Vector3.Dot(curVec, cubeVec)) * Mathf.Rad2Deg;
// 可以使用叉乘判断某一方向上的
Vector3 corss = Vector3.Cross(curVec, cubeVec);
// 进而求出大于360°以内的角
if (cross.y < 0)
{
    angle = 360 - angle;
}

欧拉角

使用三个浮点数描述方位,其中X轴和Z轴以自身坐标为准,Y轴以世界坐标系为准。欧拉角没有方向概念也没有大小概念,知识表达绕着各个轴转动的角度。

以欧拉角获取物体的方位 Vector3 eulerAngle = transform.euleerAngles;

理论上可以以任何数字作为欧拉角取值,但是这样可能出现同样的方位却有多种表达方式的问题。为解决这一问题,Unity中将Y和Z限制在[-180, 180],X限制在[-90, 90]。

万向节死锁

欧拉角收到万向锁的影响,当依次施加三个旋转时,第一个或第二个旋转可能导致第三个轴的方向与先前两个轴之一相同,这就意为这物体失去自由度而不能围绕这一轴应用第三个旋转值。

因此,使用四元数表示方向是必要的。

四元数

四元数可用于表示游戏对象的方向或旋转。此方法在内部用是个数字表示,通常不需要知道四元数的详细原理,也不会直接访问这四个数字。

四元数不受万向锁影响,但是不能表示任何方向超过180度的旋转,而且在直观上难以理解。

以四元数获取物体的旋转 Quaternion quaternion = transform.rotation;

欧拉角转换为四元数 Quaternion qua = Quaternion.Euler(Vector3 eulerAngle);

坐标系统

世界坐标系(WorldSpace)

整个场景的绝对坐标,表示场景内每个物体的固定位置和方向

相关变量和函数

transform.forward在世界坐标系中表示物体的正前方,一般为z轴正方向

transform.right在世界坐标系中表示物体的正右方,一般为x轴正方向

transform.up在世界坐标系中表示物体的正上方,一般为y轴正方向

transform.TransformPoint 物体坐标系 -> 世界坐标系 转换点

transform.TransformDirection物体坐标系 -> 世界坐标系 转换方向

transform.TransformVector物体坐标系 -> 世界坐标系 ~~~~转换变量

物体坐标系(LocalSpace)

每个物体独立的坐标系,以模型轴心为原点,表示物体间相对位置

相关函数

transform.InverseTransformPoint 世界坐标系 -> 物体坐标系 转换点

transform.InverseTransformDirection世界坐标系 -> 物体坐标系 转换方向

transform.InverseTransformVector世界坐标系 -> 物体坐标系转换变量

屏幕坐标系(ScreenSpace)

以像素为单位,左下角对于X=0,Y=0即(0,0)点,右上角则为最大值,其中X=屏幕宽度,Y=屏幕高度,Z表示物体到相机的位置。

视口坐标系(ViewportSpace)

以屏幕左下角为原点,右上角为(1,1),Z表示到相机的位置。

其他函数

Camera.main.WordToScreenPoint世界坐标系 -> 屏幕坐标系 转换点

Camera.main.ScreenToWorldPoint屏幕坐标系 -> 世界坐标系 转换点

Camera.main.WorldToViewportPoint世界坐标系 -> 视口坐标系 转换点

Camera.main.ViewportToWorldPoint视口坐标系 -> 世界坐标系 转换点

应用 —— 物体始终保持在镜头内

仅给出关键部分,控制部分略

        var local = mainCamera.WorldToViewportPoint(transform.position);
        float localX = local.x;
        float localY = local.y;
        if (localX < 0) // 超出镜头左沿
        {
            local.x = 1;    // 回到镜头右沿
        }

        if (localX > 1) // 超出镜头右沿
        {
            local.x = 0;    // 回到镜头左沿
        }

        if (localY < 0) // 超出镜头上沿
        {
            local.y = 1;    // 回到镜头下沿
        }

        if (localY > 1) // 超出镜头上沿
        {
            local.y = 0;    // 回到镜头下沿
        }

        transform.position = mainCamera.ViewportToWorldPoint(local);
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值