Files
OldThink/Content.Client/_White/Trail/SplineRenderer/TrailSplineRendererContinuous.cs

91 lines
3.2 KiB
C#

using System.Linq;
using System.Numerics;
using Content.Shared._White.Spline;
using Content.Shared._White.Trail;
using Robust.Client.Graphics;
using Vector4 = Robust.Shared.Maths.Vector4;
namespace Content.Client._White.Trail.SplineRenderer;
public sealed class TrailSplineRendererContinuous : ITrailSplineRenderer
{
public void Render(
DrawingHandleWorld handle,
Texture? texture,
ISpline<Vector2> splineIterator,
ISpline<Vector4> gradientIterator,
ITrailSettings settings,
Vector2[] paPositions,
float[] paLifetimes
)
{
float[] splinePointParams;
if (settings.LengthStep == 0f)
{
splinePointParams = Enumerable.Range(0, paPositions.Length - 1).Select(x => (float) x).ToArray();
}
else
{
splinePointParams = splineIterator
.IteratePointParamsByLength(paPositions, Math.Max(settings.LengthStep, 0.1f)).ToArray();
}
var gradientControlGroups = gradientIterator.GetControlGroupAmount(settings.Gradient.Length);
var colorToPointMul = 0f;
if (gradientControlGroups > 0)
colorToPointMul = gradientControlGroups / splineIterator.GetControlGroupAmount(paPositions.Length);
(Vector2, Vector2)? prevPoints = null;
foreach (var u in splinePointParams)
{
var (position, velocity) = splineIterator.SamplePositionVelocity(paPositions, u);
var offset = new Vector2(-velocity.Y, velocity.X).Normalized() *
settings.Scale.X; // 90-degree anticlockwise rotation
var curPoints = (position - offset, position + offset);
if (prevPoints.HasValue)
{
var colorVec = Vector4.One;
if (settings.Gradient != null && settings.Gradient.Length > 0)
{
if (gradientControlGroups > 0)
colorVec = gradientIterator.SamplePosition(settings.Gradient, u * colorToPointMul);
else
colorVec = settings.Gradient[0];
}
if (texture != null)
{
var verts = new DrawVertexUV2D[]
{
new(curPoints.Item1, Vector2.Zero),
new(curPoints.Item2, Vector2.UnitY),
new(prevPoints.Value.Item2, Vector2.One),
new(prevPoints.Value.Item1, Vector2.UnitX),
};
handle.DrawPrimitives(DrawPrimitiveTopology.TriangleFan, texture, verts,
new Color(colorVec.X, colorVec.Y, colorVec.Z, colorVec.W));
}
else
{
var verts = new[]
{
curPoints.Item1,
curPoints.Item2,
prevPoints.Value.Item2,
prevPoints.Value.Item1,
};
handle.DrawPrimitives(DrawPrimitiveTopology.TriangleFan, verts,
new Color(colorVec.X, colorVec.Y, colorVec.Z, colorVec.W));
}
}
prevPoints = curPoints;
}
}
}