Процедурное выдавливание проблем сетки
Я пробую какое-то процедурное выдавливание сетки, но у меня сейчас две проблемы. Код, который выполняет выдавливание, является частью примера пакета Unity и доступен здесь (MeshExtrusion.cs)
Первая проблема заключается в том, что обновление сетки отображается только в том случае, если к сетке добавлена дополнительная точка, в GIF ниже это должно быть выделено.
Вторая проблема заключается в том, что меш скручивается. Я предполагаю, что это связано с выдавливанием неправильных вершин, но я не уверен на 100%. Вот мой код, который реализует экструзию сетки:
using System.Collections;
using System.Collections.Generic;
using UnityEngine;
public class ExtrudeTest : MonoBehaviour {
private Vector3 currentMousePosition;
private float currentMouseDistance;
MeshExtrusion.Edge[] preComputedEdges;
private Mesh srcMesh;
private List<Matrix4x4> extrusionPoints = new List<Matrix4x4>();
private Matrix4x4 currentTransformMatrix;
GameObject lineObject;
LineRenderer drawLine;
private bool invertFaces = false;
// Use this for initialization
void Start () {
srcMesh = GetComponent<MeshFilter>().sharedMesh;
preComputedEdges = MeshExtrusion.BuildManifoldEdges(srcMesh);
extrusionPoints.Add(transform.worldToLocalMatrix * Matrix4x4.TRS(transform.position, Quaternion.identity, Vector3.one));
lineObject = new GameObject("lineRenderer");
drawLine = lineObject.AddComponent<LineRenderer>();
}
//Store the current world mouse position.
public void storeMouseLocation()
{
Ray ray = Camera.main.ScreenPointToRay(UnityEngine.Input.mousePosition);
RaycastHit hit;
if (Physics.Raycast(ray, out hit, Mathf.Infinity))
{
currentMousePosition = hit.point;
currentMouseDistance = hit.distance;
currentTransformMatrix = hit.transform.localToWorldMatrix;
}
}
private void adjustMesh()
{
Matrix4x4 worldToLocal = transform.worldToLocalMatrix;
Matrix4x4[] finalSections = new Matrix4x4[extrusionPoints.Count];
Quaternion rotation;
Quaternion previousRotation = Quaternion.identity;
Vector3 direction;
for (int i=0; i < extrusionPoints.Count; i++)
{
if (i == 0)
{
direction = extrusionPoints[0].GetColumn(3) - extrusionPoints[1].GetColumn(3);
rotation = Quaternion.LookRotation(direction, Vector3.up);
previousRotation = rotation;
finalSections[i] = worldToLocal * Matrix4x4.TRS(transform.position, rotation, Vector3.one);
}
else if (i != extrusionPoints.Count - 1)
{
direction = extrusionPoints[i].GetColumn(3) - extrusionPoints[i + 1].GetColumn(3);
rotation = Quaternion.LookRotation(direction, Vector3.up);
// When the angle of the rotation compared to the last segment is too high
// smooth the rotation a little bit. Optimally we would smooth the entire sections array.
if (Quaternion.Angle(previousRotation, rotation) > 20)
{
rotation = Quaternion.Slerp(previousRotation, rotation, 0.5f);
}
previousRotation = rotation;
finalSections[i] = worldToLocal * Matrix4x4.TRS(extrusionPoints[i].GetColumn(3), rotation, Vector3.one);
}
else
{
finalSections[i] = finalSections[i - 1];
}
}
extrudeMesh(finalSections);
}
private void extrudeMesh(Matrix4x4[] sections)
{
Debug.Log("Extruding mesh");
MeshExtrusion.ExtrudeMesh(srcMesh, GetComponent<MeshFilter>().mesh, sections, preComputedEdges, invertFaces);
}
// Update is called once per frame
void Update () {
storeMouseLocation();
drawLine.SetPosition(0, extrusionPoints[extrusionPoints.Count-1].GetColumn(3));
drawLine.SetPosition(1, currentMousePosition);
if (Input.GetMouseButtonDown(0))
{
extrusionPoints.Add(transform.worldToLocalMatrix * Matrix4x4.TRS(transform.position + new Vector3(currentMousePosition.x, currentMousePosition.y, currentMousePosition.z),
Quaternion.identity,
Vector3.one));
}
if (extrusionPoints.Count >=2)
{
adjustMesh();
}
}
}
Вот GIF, который показывает, как он работает в настоящее время:
https://puu.sh/xeS7e/bfc3d71fba.gif
Я не совсем уверен, что вызывает эти проблемы, поэтому, если кто-то может предложить какой-либо совет или вклад, я был бы очень признателен. Спасибо