using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;
using Unity.Burst;
using Unity.Collections;
using Unity.Jobs;
using UnityEngine;
///
/// 三角形合并网格
///
public class UnitAlgorithmMergeTriangle : UnitAlgorithm {
/// 三角形合并网格
public UnitAlgorithmMergeTriangle() { }
public void Compute(DataPlate data) {
List polygons = data.triangles;
//三角形合并
List vertices = vertices = MergeVertices(polygons);
List triangles = JobFindTriangleIndex(polygons, vertices);
//展开uv (顶点去掉z坐标就是未缩放的平面UV)
List uv = new List();
for (int i = 0; i < vertices.Count; i++) { uv.Add(vertices[i]); }
//附加数据
data.designMesh = new Mesh();
data.designMesh.vertices = vertices.ToArray();
data.designMesh.uv = uv.ToArray();
data.designMesh.triangles = triangles.ToArray();
data.designMesh.RecalculateBounds();
data.designMesh.RecalculateNormals();
}
/// 合并顶点
private List MergeVertices(List polygons) {
List vertices = new List();
for (int i = 0; i < polygons.Count; i++) {
vertices.Add(polygons[i].a);
vertices.Add(polygons[i].b);
vertices.Add(polygons[i].c);
}
return vertices.Distinct().ToList();
}
#region Jobs
/// 三角形顶点索引查找作业
private List JobFindTriangleIndex(List polygons, List vertices) {
NativeArray dataArray = new NativeArray(polygons.ToArray(), Allocator.TempJob);
NativeArray verticeArray = new NativeArray(vertices.ToArray(), Allocator.TempJob);
NativeArray trianglesArray = new NativeArray(polygons.Count, Allocator.TempJob);
TriangleIndex triangleIndex = new TriangleIndex();
triangleIndex.dataArray = dataArray;
triangleIndex.vertices = verticeArray;
triangleIndex.triangles = trianglesArray;
JobHandle dependency = new JobHandle();
JobHandle handle = triangleIndex.ScheduleParallel(polygons.Count, 2048, dependency);
handle.Complete();
List triangles = new List();
for (int i = 0; i < trianglesArray.Length; i++) {
triangles.Add(trianglesArray[i].a);
triangles.Add(trianglesArray[i].b);
triangles.Add(trianglesArray[i].c);
}
dataArray.Dispose();
verticeArray.Dispose();
trianglesArray.Dispose();
return triangles;
}
/// 三角形顶点索引查找作业
[BurstCompile]
public struct TriangleIndex : IJobFor {
[ReadOnly] public NativeArray dataArray;
[ReadOnly] public NativeArray vertices;
public NativeArray triangles;
public void Execute(int index) {
DataTriangle dataTriangle = dataArray[index];
Triangle triangle = new Triangle();
bool a = false, b = false, c = false;
for (int i = 0; i < vertices.Length; i++) {
Vector3 vector = vertices[i];
if (dataTriangle.a == vector) { triangle.a = i; a = true; }
if (dataTriangle.b == vector) { triangle.b = i; b = true; }
if (dataTriangle.c == vector) { triangle.c = i; c = true; }
if (a && b && c) { break; }
}
triangles[index] = triangle;
}
}
/// 三角形顶点索引
public struct Triangle { public int a, b, c; }
#endregion
/// 是否启用计时器
private readonly bool isEnableTimer = true;
/// 计时器
private void Chronoscope(string content, Action action) {
if (!isEnableTimer) { action?.Invoke(); return; }
float time = Time.realtimeSinceStartup;
action?.Invoke();
float consumed = Time.realtimeSinceStartup - time;
Debug.Log($"{content}{consumed * 1000}");
}
}