topical media & game development
lib-unity-example-procedural-Assets-Sources-ExtrudedMeshTrail.js / js
// Generates an extrusion trail from the attached mesh
// Uses the MeshExtrusion algorithm in MeshExtrusion.cs to generate and preprocess the mesh.
var time = 2.0;
var autoCalculateOrientation = true;
var minDistance = 0.1;
var invertFaces = false;
private var srcMesh : Mesh;
private var precomputedEdges : MeshExtrusion.Edge[];
class ExtrudedTrailSection
{
var point : Vector3;
var matrix : Matrix4x4;
var time : float;
}
function Start ()
{
srcMesh = GetComponent(MeshFilter).sharedMesh;
precomputedEdges = MeshExtrusion.BuildManifoldEdges(srcMesh);
}
private var sections = new Array();
function LateUpdate () {
var position = transform.position;
var now = Time.time;
// Remove old sections
while (sections.length > 0 && now > sections[sections.length - 1].time + time) {
sections.Pop();
}
// Add a new trail section to beginning of array
if (sections.length == 0 || (sections[0].point - position).sqrMagnitude > minDistance * minDistance)
{
var section = ExtrudedTrailSection ();
section.point = position;
section.matrix = transform.localToWorldMatrix;
section.time = now;
sections.Unshift(section);
}
// We need at least 2 sections to create the line
if (sections.length < 2)
return;
var worldToLocal = transform.worldToLocalMatrix;
var finalSections = new Matrix4x4[sections.length];
var previousRotation : Quaternion;
for (var i=0;i<sections.length;i++)
{
if (autoCalculateOrientation)
{
if (i == 0)
{
var direction = sections[0].point - sections[1].point;
var rotation = Quaternion.LookRotation(direction, Vector3.up);
previousRotation = rotation;
finalSections[i] = worldToLocal * Matrix4x4.TRS(position, rotation, Vector3.one);
}
// all elements get the direction by looking up the next section
else if (i != sections.length - 1)
{
direction = sections[i].point - sections[i+1].point;
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.5);
previousRotation = rotation;
finalSections[i] = worldToLocal * Matrix4x4.TRS(sections[i].point, rotation, Vector3.one);
}
// except the last one, which just copies the previous one
else
{
finalSections[i] = finalSections[i-1];
}
}
else
{
if (i == 0)
{
finalSections[i] = Matrix4x4.identity;
}
else
{
finalSections[i] = worldToLocal * sections[i].matrix;
}
}
}
// Rebuild the extrusion mesh
MeshExtrusion.ExtrudeMesh (srcMesh, GetComponent(MeshFilter).mesh, finalSections, precomputedEdges, invertFaces);
}
@script RequireComponent (MeshFilter)
(C) Æliens
04/09/2009
You may not copy or print any of this material without explicit permission of the author or the publisher.
In case of other copyright issues, contact the author.