程序性挤出网格问题

时间:2017-08-20 13:25:53

标签: c# unity3d procedural-generation

我正在尝试一些程序网格挤出,但我现在有两个问题。执行挤出的代码是Unity示例包的一部分,可用here(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

我不完全确定导致这些问题的原因,所以如果有人可以提供任何建议或意见,我会非常感激。感谢

0 个答案:

没有答案
相关问题