一、数学计算工具Mathf
1.math与mathf的区别
| 特性 | Mathf (Unity) | Math (C#) |
|---|---|---|
| 命名空间 | UnityEngine | System |
| 功能范围 | 包含Math方法+游戏开发专用方法 | 基础数学计算方法 |
| 适用场景 | Unity游戏开发 | 通用C#应用程序 |
结论:在Unity开发中,优先使用Mathf!
2.Mathf常用方法详解
(1)基础常数
print(Mathf.PI); // 输出圆周率π
(2)取绝对值
print(Mathf.Abs(-10)); // 输出:10
print(Mathf.Abs(-20)); // 输出:20
print(Mathf.Abs(1)); // 输出:1
(3)取整运算
// 向上取整
float f = 1.3f;
print((int)f); // 输出:1(直接截断)
print(Mathf.CeilToInt(f)); // 输出:2(向上取整)
print(Mathf.CeilToInt(1.00001f)); // 输出:2
// 向下取整
print(Mathf.FloorToInt(9.6f)); // 输出:9
(4)数值限制
// 钳制函数 - 将数值限制在指定范围内
print(Mathf.Clamp(10, 11, 20)); // 输出:11(小于最小值)
print(Mathf.Clamp(21, 11, 20)); // 输出:20(大于最大值)
print(Mathf.Clamp(15, 11, 20)); // 输出:15(在范围内)
(5)极值计算
// 最大值
print(Mathf.Max(1, 2, 3, 4, 5, 6, 7, 8)); // 输出:8
print(Mathf.Max(1, 2)); // 输出:2
// 最小值
print(Mathf.Min(1, 2, 3, 4, 545, 6, 1123, 123)); // 输出:1
print(Mathf.Min(1.1f, 0.4f)); // 输出:0.4
(6)幂运算与平方根
// 幂运算
print("一个数的n次方" + Mathf.Pow(4, 2)); // 输出:16
print("一个数的n次方" + Mathf.Pow(2, 3)); // 输出:8
// 平方根
print("返回一个数的平方根" + Mathf.Sqrt(4)); // 输出:2
print("返回一个数的平方根" + Mathf.Sqrt(16)); // 输出:4
print("返回一个数的平方根" + Mathf.Sqrt(64)); // 输出:8
(7)四舍五入
print("四舍五入" + Mathf.RoundToInt(1.3f)); // 输出:1
print("四舍五入" + Mathf.RoundToInt(1.5f)); // 输出:2
(8)特殊判断函数
// 判断是否为2的n次方
print("判断一个数是否是2的n次方" + Mathf.IsPowerOfTwo(4)); // 输出:True
print("判断一个数是否是2的n次方" + Mathf.IsPowerOfTwo(8)); // 输出:True
print("判断一个数是否是2的n次方" + Mathf.IsPowerOfTwo(3)); // 输出:False
print("判断一个数是否是2的n次方" + Mathf.IsPowerOfTwo(1)); // 输出:True
// 判断正负数
print("判断正负数" + Mathf.Sign(0)); // 输出:0
print("判断正负数" + Mathf.Sign(10)); // 输出:1
print("判断正负数" + Mathf.Sign(-10)); // 输出:-1
3.插值运算
(1)Lerp函数原理
语法:result = Mathf.Lerp(start, end, t)
等价公式:result = start + (end - start) * t
参数说明:
start:起始值 end:目标值 t:插值系数(0~1)
返回值:两个值之间按比例得到的过渡值
(2)两种常用用法
【1】每帧改变start值
void Update()
{
// 变化速度先快后慢,无限接近目标值但不会完全到达
start = Mathf.Lerp(start, 10, Time.deltaTime);
}
特点:减速运动,永远达不到精确终点

【2】每帧改变t值
float time = 0;
float result = 0;
void Update()
{
time += Time.deltaTime;
// 匀速变化,当t≥1时到达终点
result = Mathf.Lerp(start, 10, time);
}
特点:匀速运动,可以精确到达终点
4.Unity——Lerp练习题
(1)题目
使用Lerp在Unity实现一个物体向另外一个物体移动
(2)实现逻辑
方法一:减速运动
【1】首先创建两个物体:两个球体。创建一个脚本,并把脚本挂在在一个物体上

【2】实现代码逻辑
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class testmove : MonoBehaviour
{
public Transform BlueObject;//代表蓝球
public float movespeed;//为了方便调节速度,我添加一个可以随时改变的量
//脚本挂在红球上 this:指代红球
private void Update()
{
Mathf.Lerp(this.transform.position.x, BlueObject.position.x, Time.deltaTime * movespeed);
Mathf.Lerp(this.transform.position.y, BlueObject.position.y, Time.deltaTime * movespeed);
Mathf.Lerp(this.transform.position.z, BlueObject.position.z, Time.deltaTime * movespeed);
}
}
(3)效果展示
lerp移动减速
方法二:匀速运动
【1】同上
【2】实现代码逻辑
public class testmove : MonoBehaviour
{
public Transform BlueObject;//代表蓝球
public float movespeed=1;//为了方便调节速度,我添加一个可以随时改变的量
public Vector3 Temppos;//用于动态接受改变之后的红球坐标
public float TimeCount = 0f;
//脚本挂在红球上 this:指代红球
private void FixedUpdate()//这里我函数名修改了(为了保证没有外界干扰而已,不影响结论)
{
TimeCount += Time.deltaTime;
Temppos.x = Mathf.Lerp(this.transform.position.x, BlueObject.position.x, TimeCount * movespeed);
Temppos.y = Mathf.Lerp(this.transform.position.y, BlueObject.position.y, TimeCount * movespeed);
Temppos.z = Mathf.Lerp(this.transform.position.z, BlueObject.position.z, TimeCount * movespeed);
this.transform.position = Temppos;
}
}
【3】效果图
lerp匀速
二、三角函数
1.弧度与角度的相互转化
// 弧度转角度
float rad = 1;
float anger = rad * Mathf.Rad2Deg;
print(anger);
// 角度转弧度
anger = 1;
rad = anger * Mathf.Deg2Rad;
print(rad);
(1)Unity 中 Mathf.Rad2Deg 是一个常量(约等于 57.2958),用于将弧度转换为角度
(2)Mathf.Deg2Rad 是其倒数(约等于 0.01745),用于将角度转换为弧度
(3)转换公式:角度 = 弧度 × Mathf.Rad2Deg,弧度 = 角度 × Mathf.Deg2Rad
2.三角函数的使用
(1)正弦函数(sin)
(2)余弦函数(cos)
【2】常用正弦余弦值

// 注意:Mathf中的三角函数相关函数,传入的参数需要是弧度值
print(Mathf.Sin(30 * Mathf.Deg2Rad));// 输出约0.5
print(Mathf.Cos(60 * Mathf.Deg2Rad));// 输出约0.5
(1)Unity 中的 Mathf.Sin() 和 Mathf.Cos() 函数必须传入弧度值,而不是角度值
3.反三角函数的使用
// 反三角函数得到的结果是正弦或者余弦值对应的弧度
rad = Mathf.Asin(0.5f);
print(rad * Mathf.Rad2Deg); // 输出30
rad = Mathf.Acos(0.5f);
print(rad * Mathf.Rad2Deg); // 输出60
(1)反三角函数是三角函数的逆运算:Asin(x) 求的是正弦值为 x 的角度(弧度形式)
(2)反三角函数的返回值是弧度,需要转换为角度才能得到我们直观理解的度数
(3)输入值范围限制:Asin 和 Acos 的参数必须在 [-1, 1] 范围内,否则会返回 NaN( Not a Number(非数字)的缩写)
4.Unity——三角函数练习题
1.题目
实现一个物体按曲线移动(正弦或者余弦曲线)
2.实现逻辑
(1)首先实现一个物体水平方向匀速直线运动
(2)然后实现这个物体垂直方向做上下运动(sinx的-1~1之间变化)的运动
(3)代码实现
using System.Collections;
using System.Collections.Generic;
using Unity.VisualScripting;
using UnityEngine;
public class test2TriFun : MonoBehaviour
{
public float zSpeed=2;//直线速度
public float ySpeed=1;//竖直方向的速度
public float yLength = 1;//三角函数的幅度大小
public float TimeCount = 0;
//3.两个运动和起来就是曲线运动
private void Update()
{
TimeCount += Time.deltaTime;
//1.首先得让物体沿着一个轴方向(这里我选Z轴)做匀速直线运动
this.transform.Translate(Vector3.forward*zSpeed*Time.deltaTime);
//2.然后沿着竖直(Y轴)或者另外一个轴(X轴)【这里我选Y轴】做上下运动
this.transform.Translate(Vector3.up * yLength *Time.deltaTime* Mathf.Sin(TimeCount* ySpeed));
}
}
3.效果展示
三角函数曲线运动
三、坐标系
1.世界坐标系(World Coordinate System)
//目前学习的和世界坐标系相关的
this.transform.position;
this.transform.rotation;
this.transform.eulerAngles;
this.transform.lossyScale;
// 修改他们 会是相对世界坐标系的变化
(1)transform.position:物体在世界坐标系中的三维坐标(x,y,z),表示物体相对于世界原点的位置。
(2)transform.rotation:物体在世界坐标系中的旋转(四元数形式),描述物体的朝向。
(3)transform.eulerAngles:物体在世界坐标系中的旋转(欧拉角形式,单位:度),更直观(如 x 轴旋转 90° 表示绕世界 x 轴翻转)。
(4)transform.lossyScale:物体的 “损失缩放”,本质是物体在世界坐标系中的最终缩放比例(考虑了父物体的缩放叠加)。例如:一个子物体的 localScale 是 (2,2,2),而它的父物体 localScale 是 (0.5,0.5,0.5),那么子物体的 lossyScale 就是 (1,1,1)
2.物体坐标系(Local Coordinate System)
核心:物体坐标系是相对于父物体的局部坐标系。当一个物体成为另一个物体的子物体时,它的位置、旋转、缩放都会以父物体的坐标系为基准。
// 相对父对象的物体坐标系的位置 本地坐标 相对坐标
this.transform.localPosition;
this.transform.localEulerAngles;
this.transform.localRotation;
this.transform.localScale;
// 修改他们 会是相对父对象物体坐标系的变化
(1)transform.localPosition:物体相对于父物体原点的位置。若没有父物体,则等同于 position。
(2)transform.localEulerAngles:物体相对于父物体的旋转(欧拉角)。例如,父物体旋转 90° 后,子物体的 localEulerAngles 为(0,0,0)表示与父物体朝向一致。
(3)transform.localRotation:物体相对于父物体的旋转(四元数形式)。
(4)transform.localScale:物体相对于父物体的缩放比例。例如,父物体缩放为(2,2,2),子物体 localScale 为(0.5,0.5,0.5),则子物体在世界坐标系中的实际缩放为(1,1,1)。
Tips:子物体的变换会跟随父物体
3.屏幕坐标系(Screen Coordinate System)
(1)概念
屏幕坐标系是 2D 坐标系,以屏幕左下角为原点(0,0),右上角为(Screen.width, Screen.height),单位是像素。主要用于处理鼠标、触摸等屏幕交互。
Input.mousePosition
Screen.width;
Screen.height;
【1】Input.mousePosition:鼠标在屏幕坐标系中的位置(x 为水平像素,y 为垂直像素,z 无意义)。
【2】Screen.width / Screen.height:屏幕的宽度和高度(像素),例如 1920x1080 屏幕中,width=1920,height=1080。
4.视口坐标系(Viewport Coordinate System)
(1)概念
视口坐标系是标准化的 2D 坐标系,以摄像机的左下角为原点(0,0),右上角为(1,1),与屏幕分辨率无关。用于描述物体在摄像机可视范围内的相对位置。
摄像机上的 视口范围
【1】坐标值始终在 [0,1] 范围内(超出则表示在摄像机视野外)。
【2】x=0.5、y=0.5 表示摄像机视野的中心。
5.坐标系转换方法
| 转换方向 | 核心方法 | 用途说明 |
|---|---|---|
| 世界坐标系 → 物体坐标系 | InverseTransformPoint / InverseTransformDirection | 将世界坐标的点 / 方向转换为相对于当前物体的本地坐标(如判断目标在自身的前方还是后方)。 |
| 物体坐标系 → 世界坐标系 | TransformPoint / TransformDirection | 将本地坐标的点 / 方向转换为世界坐标(如子物体发射子弹时,计算子弹在世界中的初始位置)。 |
| 世界坐标系 → 屏幕坐标系 | Camera.main.WorldToScreenPoint | 将 3D 世界中的点转换为屏幕上的 2D 像素位置(如显示物体头顶的血条)。 |
| 屏幕坐标系 → 世界坐标系 | Camera.main.ScreenToWorldPoint | 将屏幕上的点(如鼠标位置)转换为 3D 世界坐标(如点击屏幕生成物体)。 |
| 世界坐标系 → 视口坐标系 | Camera.main.WorldToViewportPoint | 判断物体在摄像机视野中的相对位置(如检测物体是否移出屏幕)。 |
| 视口坐标系 → 世界坐标系 | Camera.main.ViewportToWorldPoint | 将视口坐标转换为世界坐标(如在摄像机视野右上角生成特效)。 |
| 视口 ↔ 屏幕坐标系 | ViewportToScreenPoint / ScreenToViewportPoint | 视口与屏幕坐标的相互转换(如将 UI 位置从像素单位转为标准化单位)。 |
1089

被折叠的 条评论
为什么被折叠?



