rabidus-test/Assets/Dreamteck/Splines/Components/SplineRenderer.cs

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++;
}
}
}
}
}