Unity3D 的LookAt() 与 LookRotation()方法的比较

LookAt(),定义: 其定义在UnityEngine.Transform类中,

public void LookAt(Vector3 worldPosition);

public void LookAt(Transform target);

用法: 一:transform.LookAt(new Vector3(1,1,1));

使游戏对象看向该坐标点(游戏对象的z轴指向(1,1,1));

二:transform.LookAt(gameobject.transform)

使游戏对象看向gameobject的transform的position;

在场景中创建cube与Sphere两个游戏对象,将脚本挂载到Cube上;

using UnityEngine;

public class Test : MonoBehaviour {

    private Transform other;//Sphere游戏对象

    void Awake()
    {
        //找到Sphere游戏对象
        other = transform.Find("/Sphere").GetComponent<Transform>();
    }

	void Start()
    {
        //Cube的z轴指向(1,1,1)点
//        transform.LookAt(new Vector3(1, 1, 1));
    }

    void Update()
    {
        //画线调试,由Cube的postion指向Sphere的postion
        Debug.DrawLine(transform.position,other.position,Color.cyan);
        //Cube的z轴指向Sphere,(指向了Sphere游戏对象的Transform组件的position值,也是一个Vector3类型的值) 
        transform.LookAt(other);
    }
}

运行结果:

Cube(蓝色箭头为Cube的z轴)指向了Sphere的中心;

#运行过程中的有趣发现#

为Cube添加了Rigidbody组件后,运行时Cube在不停摆动,且z轴一直指向Sphere的中心。其原因应为将LookAt()方法放于Update()方法中,使其每一帧都指向Sphere,并且Cube并没有贴合地面,在重力作用下往下掉的同时由于LookAt每一帧都在修复其指向,从而出现这种情况;


LookRotation() 定义: 其为定义在UnityEngine.Quaternion中的静态方法,

public static Quaternion LookRotation(Vector3 forward);

用法: Quaternion.LookRotation(new Vector3(1,1,1));

获取一个向量所表示的方向(将一个向量转为该向量所对应的方向);

使游戏对象面向(1,1,1)这个向量

在场景中创建一个cube_1与Sphere,将脚本挂在cube_1上

using UnityEngine;

public class LookRotation : MonoBehaviour {

    private Transform other;//Sphere游戏对象

    void Awake()
    {
        //找到Sphere游戏对象
        other = transform.Find("/Sphere").GetComponent<Transform>();
    }

    void Start()
    {
        //将Cube_1的z轴指向坐标原点(Vector.zero)到 Vector3(2,2,2)所对应的向量方向
        transform.rotation = Quaternion.LookRotation(new Vector3(2, 2, 2));
        //将Cube_1的z轴指向原点到other.position对应向量的方向
        transform.rotation =  Quaternion.LookRotation(other.position);
    }

    void Update()
    {
        //画线调试,画出从Cube_1到Sphere的线段
        Debug.DrawLine(transform.position, other.position,Color.blue);
        //画线调试,画出坐标原点到Sphere的射线在cube_1上的表现,即画出向量方向
        Debug.DrawRay(transform.position, other.position,Color.red);
        Move();
    }

    void Move()
    {
        float horizontal = Input.GetAxis("Horizontal");//获取水平偏移量(x轴)
        float vertical = Input.GetAxis("Vertical");    //获取垂直偏移量(z轴)
        //将水平偏移量与垂直偏移量组合为一个方向向量
        Vector3 direction = new Vector3(horizontal, 0, vertical);
        //判断是否有水平偏移量与垂直偏移量产生
        if (direction != Vector3.zero)
        {
            //将游戏对象的z轴转向对应的方向向量
//            transform.rotation = Quaternion.LookRotation(direction);
            //对上一行代码进行插值运算则可以将转向表现得较平滑
            transform.rotation = Quaternion.Lerp(transform.rotation, Quaternion.LookRotation(direction), 0.3f);
            //将游戏对象进行移动变换方法则可以实现简单的物体移动
            transform.Translate(Vector3.forward * 5 * Time.deltaTime);
        }
    }
}
运行结果:


cube_1的z轴与红色这条射线重合,而并非指向sphere(并未与蓝色射线重合);

用LookRotation()可以实现游戏对象转向;参考上面的Move()方法;

小结:

LookAt()与LookRotation()的参数都相似,但前者是将游戏对象的z轴指向参数所表示的那个点,而后者是将游戏对象的z轴指向参数所表示的向量的方向;

OpenGL中的`lookAt()`函数主要用于设置观察点、目标点以及视点方向,它是一个非常重要的三维变换函数,常用于创建相机视角。通过指定这三个关键点,可以生成一组矩阵(通常是正交投影矩阵和平行投影矩阵),进而控制摄像机的位置、角度及视野范围。 **基本语法**: ```cpp gluLookAt(eyeX, eyeY, eyeZ, centerX, centerY, centerZ, upX, upY, upZ); ``` 这里的参数分别代表: - `eyeX`, `eyeY`, `eyeZ`: 观察点 (camera) 的位置坐标; - `centerX`, `centerY`, `centerZ`: 目标点的位置坐标; - `upX`, `upY`, `upZ`: 表示向上向量,即垂直于观察者视线的一个单位向量,默认值为 (0, 1, 0),通常用于确定垂直于屏幕的方向。 `lookAt()` 函数通过这些参数构建出一个透视或正交视图矩阵,这个矩阵随后会被传递给其他渲染函数如`glMultMatrix()`,用于将场景数据转换到当前视图空间内进行绘制。通过调整观察点、目标点以及向上向量,用户可以动态地改变视角,实现三维图形的全方位展示。 **使用示例**: ```cpp // 创建 OpenGL 环境并初始化上下文... glMatrixMode(GL_MODELVIEW); // 设置模型视图模式 glLoadIdentity(); // 初始化视图矩阵为单位矩阵 // 设置观察点为中心,目标点为正前方,向上向量为默认值 gluLookAt(0, 0, 5, 0, 0, 0, 0, 1, 0); // 绘制场景... glutSwapBuffers(); ``` 在这个例子中,摄像头位于坐标轴原点上方5单位的地方,朝向原点,并且垂直向量默认指向屏幕顶部。 --- ## 相关问题 - OpenGL lookAt 1. **如何自定义向上向量?** - 可以直接在`lookAt()`函数中修改第三个参数组`upX`, `upY`, `upZ`的值来自定义向上向量,这会影响到相机视角在水平面内的定向。 2. **如何仅更改观察点而不移动目标点?** - 修改`eyeX`, `eyeY`, `eyeZ`即可实现观察点的移动,而保持`centerX`, `centerY`, `centerZ`不变,则目标点不会跟着动。 3. **`lookAt()`函数和`perspective()`函数有何区别?** - `lookAt()`主要用于设定相机的位置、目标点以及视野的方向,它是构建视图矩阵的一部分;`perspective()`则用于创建透视投影矩阵,结合视图矩阵一同完成从世界坐标系到屏幕坐标系的转换过程。两者共同作用决定了最终图像的呈现效果。
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值