Bounds 叫作外包围盒、边界框、外扩矩形.是struct 结构体。
而我们获得Bounds的主要途径有三种:Render,Collider,Mesh。
Render.bounds 世界坐标
Collider.bounds 世界坐标
Mesh.bounds 本地坐标
var m= GetComponent().bounds;var c = GetComponent().bounds;var r = GetComponent().bounds;
//把本地坐标换算成世界坐标var centerPoint = transform.TransformPoint(bounds.center);Bounds newBounds = new Bounds(centerPoint, bounds.size);
Bounds和碰撞器的绿方框(绿色线)的区别
碰撞器的方框始终跟着模型旋转移动,缩放跟着模型的,只要模型不缩放它也不缩放
Bounds 跟随模型移动,
而不会跟模型着旋转,而是随着模型旋转而缩放变大变小,始终包裹模型.
下面红色方框就是 Bounds 方框
只读属性
我们不能直接修改 Bounds 结构体里头的 center 和 size 属性都不能直接设置,而且 BoxCollider 的 bounds 属性也不能.
.bounds.center; //中心点坐标
.bounds.size; //盒子的总尺寸,xyz长度
.bounds.min; //最小点的位置:左下角
.bounds.max; //最大点的位置:右上角
.bounds.center.x; //中心点的X
.bounds.center.y; //中心点的Y
// 点point是否在这个包围盒内部
public bool Contains(Vector3 point);// bounds会自动扩充大小(改变center和extens),来包含这个point
public void Encapsulate(Vector3 point);// bounds会自动扩充大小(改变center和extens),把原本的bounds和传入的bounds都包含进来
public void Encapsulate(Bounds bounds);// 这条射线是否与这个包围盒相交
public bool IntersectRay(Ray ray);//包围盒最近的点
public Vector3 ClosestPoint(Vector3 point);//设置边界框的最小最大值
public void SetMinMax(Vector3 min, Vector3 max);
计算多物体Bounds,则要遍历所有子物体,然后调用Encapsulate方法来计算。
Bounds bounds;
Renderer[] renderers = model.GetComponentsInChildren();
for (int i = 0; i < renderers.Length; i++)
{bounds.Encapsulate(renderers[i].bounds);
}
center = bounds.center;
ext = bounds.extents;float deltaX = Mathf.Abs(ext.x);
float deltaY = Mathf.Abs(ext.y);
float deltaZ = Mathf.Abs(ext.z);#region 获取AABB包围盒顶点
points = new Vector3[8];
points[0] = center + new Vector3(-deltaX, deltaY, -deltaZ); // 上前左(相对于中心点)
points[1] = center + new Vector3(deltaX, deltaY, -deltaZ); // 上前右
points[2] = center + new Vector3(deltaX, deltaY, deltaZ); // 上后右
points[3] = center + new Vector3(-deltaX, deltaY, deltaZ); // 上后左points[4] = center + new Vector3(-deltaX, -deltaY, -deltaZ); // 下前左
points[5] = center + new Vector3(deltaX, -deltaY, -deltaZ); // 下前右
points[6] = center + new Vector3(deltaX, -deltaY, deltaZ); // 下后右
points[7] = center + new Vector3(-deltaX, -deltaY, deltaZ); // 下后左
#endregion
/// /// 绘制Bounds方框/// /// /// /// /// public static void DrawBoundBoxLine(Bounds bounds, Color color = default(Color), float offsetSize = 1f, float duration = 0.1f){//先计算出包围盒8个点Vector3[] points = new Vector3[8];var width_x = bounds.size.x * offsetSize;var hight_y = bounds.size.y * offsetSize;var length_z = bounds.size.z * offsetSize;var LeftBottomPoint = bounds.min;var rightUpPoint = bounds.max;var centerPoint = bounds.center;var topPoint = new Vector3(centerPoint.x, centerPoint.y + hight_y / 2, centerPoint.z);var bottomPoint = new Vector3(centerPoint.x, centerPoint.y - hight_y * 0.5f, centerPoint.z);points[0] = LeftBottomPoint + Vector3.right * width_x;points[1] = LeftBottomPoint + Vector3.up * hight_y;points[2] = LeftBottomPoint + Vector3.forward * length_z;points[3] = rightUpPoint - Vector3.right * width_x;points[4] = rightUpPoint - Vector3.up * hight_y;points[5] = rightUpPoint - Vector3.forward * length_z;points[6] = LeftBottomPoint;points[7] = rightUpPoint;Debug.DrawLine(LeftBottomPoint, points[0], color, duration);Debug.DrawLine(LeftBottomPoint, points[1], color, duration);Debug.DrawLine(LeftBottomPoint, points[2], color, duration);Debug.DrawLine(rightUpPoint, points[3], color, duration);Debug.DrawLine(rightUpPoint, points[4], color, duration);Debug.DrawLine(rightUpPoint, points[5], color, duration);Debug.DrawLine(points[1], points[3], color, duration);Debug.DrawLine(points[2], points[4], color, duration);Debug.DrawLine(points[0], points[5], color, duration);Debug.DrawLine(points[2], points[3], color, duration);Debug.DrawLine(points[0], points[4], color, duration);Debug.DrawLine(points[1], points[5], color, duration);}
/// /// 绘制boxCollider的绿色方框/// /// void DrawGizmosOnRunTime(Color color){var boxCollider = GetComponent();Gizmos.color = color;Matrix4x4 rotationMatrix = Matrix4x4.TRS(boxCollider.transform.position, boxCollider.transform.rotation, boxCollider.transform.lossyScale);Gizmos.matrix = rotationMatrix;Gizmos.DrawWireCube(boxCollider.center, boxCollider.size);}void OnDrawGizmos(){DrawGizmosOnRunTime(Color.red);}
/// /// 绘制boxCollider的绿色方框/// /// /// /// public static void DrawOnGameViewRuntime(BoxCollider boxCollider, Color color = default(Color), float offsetSize = 1f){float width = 0.1f;Vector3 rightDir = boxCollider.transform.right.normalized;Vector3 forwardDir = boxCollider.transform.forward.normalized;Vector3 upDir = boxCollider.transform.up.normalized;Vector3 center = boxCollider.transform.position + boxCollider.center;Vector3 size = boxCollider.size * offsetSize;size.x *= boxCollider.transform.lossyScale.x;size.y *= boxCollider.transform.lossyScale.y;size.z *= boxCollider.transform.lossyScale.z;Debug.DrawLine(center + upDir * size.y / 2f + rightDir * size.x / 2f + forwardDir * size.z / 2f, center + upDir * size.y / 2f - rightDir * size.x / 2f + forwardDir * size.z / 2f, color);Debug.DrawLine(center - upDir * size.y / 2f + rightDir * size.x / 2f + forwardDir * size.z / 2f, center - upDir * size.y / 2f - rightDir * size.x / 2f + forwardDir * size.z / 2f, color);Debug.DrawLine(center + upDir * size.y / 2f + rightDir * size.x / 2f + forwardDir * size.z / 2f, center - upDir * size.y / 2f + rightDir * size.x / 2f + forwardDir * size.z / 2f, color);Debug.DrawLine(center + upDir * size.y / 2f - rightDir * size.x / 2f + forwardDir * size.z / 2f, center - upDir * size.y / 2f - rightDir * size.x / 2f + forwardDir * size.z / 2f, color);Debug.DrawLine(center + upDir * size.y / 2f + rightDir * size.x / 2f - forwardDir * size.z / 2f, center + upDir * size.y / 2f - rightDir * size.x / 2f - forwardDir * size.z / 2f, color);Debug.DrawLine(center - upDir * size.y / 2f + rightDir * size.x / 2f - forwardDir * size.z / 2f, center - upDir * size.y / 2f - rightDir * size.x / 2f - forwardDir * size.z / 2f, color);Debug.DrawLine(center + upDir * size.y / 2f + rightDir * size.x / 2f - forwardDir * size.z / 2f, center - upDir * size.y / 2f + rightDir * size.x / 2f - forwardDir * size.z / 2f, color);Debug.DrawLine(center + upDir * size.y / 2f - rightDir * size.x / 2f - forwardDir * size.z / 2f, center - upDir * size.y / 2f - rightDir * size.x / 2f - forwardDir * size.z / 2f, color);Debug.DrawLine(center + upDir * size.y / 2f + rightDir * size.x / 2f + forwardDir * size.z / 2f, center + upDir * size.y / 2f + rightDir * size.x / 2f - forwardDir * size.z / 2f, color);Debug.DrawLine(center - upDir * size.y / 2f + rightDir * size.x / 2f + forwardDir * size.z / 2f, center - upDir * size.y / 2f + rightDir * size.x / 2f - forwardDir * size.z / 2f, color);Debug.DrawLine(center + upDir * size.y / 2f - rightDir * size.x / 2f + forwardDir * size.z / 2f, center + upDir * size.y / 2f - rightDir * size.x / 2f - forwardDir * size.z / 2f, color);Debug.DrawLine(center - upDir * size.y / 2f - rightDir * size.x / 2f + forwardDir * size.z / 2f, center - upDir * size.y / 2f - rightDir * size.x / 2f - forwardDir * size.z / 2f, color);}
// Distance between two ClosestPointOnBounds// this is needed in cases where entites are really big. in those cases,// we can't just move to entity.transform.position, because it will be// unreachable. instead we have to go the closest point on the boundary.//// Vector3.Distance(a.transform.position, b.transform.position):// _____ _____// | | | |// | x==|======|==x |// |_____| |_____|////// Utils.ClosestDistance(a.collider, b.collider):// _____ _____// | | | |// | |x====x| |// |_____| |_____|//public static float ClosestDistance(Collider a, Collider b){return Vector3.Distance(a.ClosestPointOnBounds(b.transform.position),b.ClosestPointOnBounds(a.transform.position));}
计算出多个Bounds的中心点
[MenuItem ("MyMenu/Do Test")]static void Test () {Transform parent = Selection.activeGameObject.transform;Vector3 postion = parent.position;Quaternion rotation = parent.rotation;Vector3 scale = parent.localScale;parent.position = Vector3.zero;parent.rotation = Quaternion.Euler(Vector3.zero);parent.localScale = Vector3.one;Vector3 center = Vector3.zero;Renderer[] renders = parent.GetComponentsInChildren();foreach (Renderer child in renders){center += child.bounds.center; }center /= parent.GetComponentsInChildren().Length; Bounds bounds = new Bounds(center,Vector3.zero);foreach (Renderer child in renders){bounds.Encapsulate(child.bounds); }parent.position = postion;parent.rotation = rotation;parent.localScale = scale;foreach(Transform t in parent){t.position = t.position - bounds.center;}parent.transform.position = bounds.center + parent.position;}
参考
https://blog.csdn.net/sinat_25415095/article/details/104588989
https://www.5axxw.com/questions/content/imitu9
上一篇:网站变灰白css
下一篇: 不要放开我的手优美散文