146 lines
4.6 KiB
C#
146 lines
4.6 KiB
C#
using UnityEngine;
|
|
using System.Collections;
|
|
using System.Collections.Generic;
|
|
using System.Threading;
|
|
using Dreamteck.Splines;
|
|
|
|
namespace Dreamteck.Splines
|
|
{
|
|
[RequireComponent(typeof(MeshFilter))]
|
|
[RequireComponent(typeof(MeshRenderer))]
|
|
[AddComponentMenu("Dreamteck/Splines/Users/Spline Renderer")]
|
|
[ExecuteInEditMode]
|
|
public class SplineRenderer : MeshGenerator
|
|
{
|
|
public int slices
|
|
{
|
|
get { return _slices; }
|
|
set
|
|
{
|
|
if (value != _slices)
|
|
{
|
|
if (value < 1) value = 1;
|
|
_slices = value;
|
|
Rebuild();
|
|
}
|
|
}
|
|
}
|
|
[HideInInspector]
|
|
public bool autoOrient = true;
|
|
[HideInInspector]
|
|
public int updateFrameInterval = 0;
|
|
[SerializeField]
|
|
[HideInInspector]
|
|
private int _slices = 1;
|
|
|
|
private int _currentFrame = 0;
|
|
private Vector3 _vertexDirection = Vector3.up;
|
|
private bool _orthographic = false;
|
|
private bool _init = false;
|
|
|
|
void Start()
|
|
{
|
|
if (Camera.current != null)
|
|
{
|
|
_orthographic = Camera.current.orthographic;
|
|
}
|
|
else if (Camera.main != null)
|
|
{
|
|
_orthographic = Camera.main.orthographic;
|
|
}
|
|
|
|
CreateMesh();
|
|
}
|
|
|
|
protected override void LateRun()
|
|
{
|
|
if (updateFrameInterval > 0)
|
|
{
|
|
_currentFrame++;
|
|
if (_currentFrame > updateFrameInterval) _currentFrame = 0;
|
|
}
|
|
}
|
|
|
|
protected override void BuildMesh()
|
|
{
|
|
base.BuildMesh();
|
|
GenerateVertices(_vertexDirection, _orthographic);
|
|
MeshUtility.GeneratePlaneTriangles(ref _tsMesh.triangles, _slices, sampleCount, false, 0, 0);
|
|
}
|
|
|
|
public void RenderWithCamera(Camera cam)
|
|
{
|
|
_orthographic = cam.orthographic;
|
|
if (_orthographic)
|
|
{
|
|
_vertexDirection = -cam.transform.forward;
|
|
}
|
|
else
|
|
{
|
|
_vertexDirection = cam.transform.position;
|
|
}
|
|
BuildMesh();
|
|
WriteMesh();
|
|
}
|
|
|
|
void OnWillRenderObject()
|
|
{
|
|
if (!autoOrient) return;
|
|
if (updateFrameInterval > 0)
|
|
{
|
|
if (_currentFrame != 0) return;
|
|
}
|
|
|
|
if (!Application.isPlaying)
|
|
{
|
|
if (!_init)
|
|
{
|
|
Awake();
|
|
_init = true;
|
|
}
|
|
}
|
|
|
|
if (Camera.current != null)
|
|
{
|
|
RenderWithCamera(Camera.current);
|
|
}
|
|
else if(Camera.main)
|
|
{
|
|
RenderWithCamera(Camera.main);
|
|
}
|
|
}
|
|
|
|
public void GenerateVertices(Vector3 vertexDirection, bool orthoGraphic)
|
|
{
|
|
AllocateMesh((_slices + 1) * sampleCount, _slices * (sampleCount - 1) * 6);
|
|
int vertexIndex = 0;
|
|
ResetUVDistance();
|
|
bool hasOffset = offset != Vector3.zero;
|
|
for (int i = 0; i < sampleCount; i++)
|
|
{
|
|
GetSample(i, ref evalResult);
|
|
Vector3 center = evalResult.position;
|
|
if (hasOffset) center += offset.x * -Vector3.Cross(evalResult.forward, evalResult.up) + offset.y * evalResult.up + offset.z * evalResult.forward;
|
|
Vector3 vertexNormal;
|
|
if(orthoGraphic) vertexNormal = vertexDirection;
|
|
else vertexNormal = (vertexDirection - center).normalized;
|
|
Vector3 vertexRight = Vector3.Cross(evalResult.forward, vertexNormal).normalized;
|
|
if (uvMode == UVMode.UniformClamp || uvMode == UVMode.UniformClip) AddUVDistance(i);
|
|
Color vertexColor = evalResult.color * color;
|
|
for (int n = 0; n < _slices + 1; n++)
|
|
{
|
|
float slicePercent = ((float)n / _slices);
|
|
_tsMesh.vertices[vertexIndex] = center - vertexRight * evalResult.size * 0.5f * size + vertexRight * evalResult.size * slicePercent * size;
|
|
CalculateUVs(evalResult.percent, slicePercent);
|
|
_tsMesh.uv[vertexIndex] = Vector2.one * 0.5f + (Vector2)(Quaternion.AngleAxis(uvRotation + 180f, Vector3.forward) * (Vector2.one * 0.5f - __uvs));
|
|
_tsMesh.normals[vertexIndex] = vertexNormal;
|
|
_tsMesh.colors[vertexIndex] = vertexColor;
|
|
vertexIndex++;
|
|
}
|
|
}
|
|
}
|
|
|
|
|
|
}
|
|
}
|