如何通过三角形重心坐标在网格内随机生成任意一点?

摘要:1.重心坐标 三角形重心坐标(Barycentric Coordinates)可以通过alpha、beta、gamma三个权重总和为1的插值系数得到 三角形内任意一点,可以用此求出某点的重心坐标系数,或是给出系数得到一点: public c
1.重心坐标 三角形重心坐标(Barycentric Coordinates)可以通过alpha、beta、gamma三个权重总和为1的插值系数得到 三角形内任意一点,可以用此求出某点的重心坐标系数,或是给出系数得到一点: public class Test : MonoBehaviour { public Transform p0; public Transform p1; public Transform p2; [Range(0f, 1f)] public float w1; [Range(0f, 1f)] public float w2; [Range(0f, 1f)] public float w3; private void OnDrawGizmos() { float sum = w1 + w2 + w3; w1 /= sum; w2 /= sum; w3 /= sum; Gizmos.DrawLine(p0.position, p1.position); Gizmos.DrawLine(p1.position, p2.position); Gizmos.DrawLine(p2.position, p0.position); var target = w1 * p0.position + w2 * p1.position + w3 * p2.position; Gizmos.DrawWireSphere(target, 0.1f); } } 2.绘制 使用三角形重心坐标生成Mesh内任意一点时,需要将三角形面积纳入考量,进行加权随机选取三角形, 选取三角形后,再通过重心坐标选取随机点即可: using System.Collections.Generic; using UnityEngine; public class Scatters : MonoBehaviour { public struct WeightItem { public float weight; public int value; } private int WeightRandom(WeightItem[] weightItems) { const float kEps = 0.00001f; float sumWeight = 0; for (int i = 0; i < weightItems.Length; i++) sumWeight += weightItems[i].weight; float randomValue = Random.Range(0f, sumWeight); float atte = 0f; for (int i = 0; i < weightItems.Length; i++) { float min = atte; atte += weightItems[i].weight; float max = atte; if (randomValue > min && randomValue < max + kEps) { return weightItems[i].value; } } throw new System.Exception(); } public MeshFilter meshFilter; private Vector3 Exec() { float Area(Vector3 a, Vector3 b, Vector3 c) { return Vector3.Cross(b - a, c - a).magnitude * 0.5f; } var triangles = meshFilter.sharedMesh.triangles; var v
阅读全文