69 lines
1.9 KiB
C#
69 lines
1.9 KiB
C#
using System.Runtime.InteropServices;
|
|
using OpenTK.Mathematics;
|
|
|
|
namespace Dashboard.Drawing.OpenGL
|
|
{
|
|
public class GradientUniformBuffer
|
|
{
|
|
private int _top = 0;
|
|
private readonly MappableBuffer<GradientUniformStruct> _buffer = new MappableBuffer<GradientUniformStruct>();
|
|
private readonly Dictionary<Gradient, Entry> _entries = new Dictionary<Gradient, Entry>();
|
|
|
|
public void Initialize()
|
|
{
|
|
_buffer.Initialize();
|
|
}
|
|
|
|
public Entry InternGradient(Gradient gradient)
|
|
{
|
|
if (_entries.TryGetValue(gradient, out Entry entry))
|
|
return entry;
|
|
|
|
int count = gradient.Count;
|
|
int offset = _top;
|
|
_top += count;
|
|
|
|
_buffer.EnsureCapacity(_top);
|
|
_buffer.Map();
|
|
Span<GradientUniformStruct> span = _buffer.AsSpan()[offset.._top];
|
|
|
|
for (int i = 0; i < count; i++)
|
|
{
|
|
GradientStop stop = gradient[i];
|
|
span[i] = new GradientUniformStruct()
|
|
{
|
|
Position = stop.Position,
|
|
Color = new Vector4(
|
|
stop.Color.R / 255f,
|
|
stop.Color.G / 255f,
|
|
stop.Color.B / 255f,
|
|
stop.Color.A / 255f),
|
|
};
|
|
}
|
|
|
|
entry = new Entry(offset, count);
|
|
_entries.Add(gradient, entry);
|
|
|
|
return entry;
|
|
}
|
|
|
|
public void Clear()
|
|
{
|
|
_entries.Clear();
|
|
_top = 0;
|
|
}
|
|
|
|
public record struct Entry(int Offset, int Count);
|
|
}
|
|
|
|
[StructLayout(LayoutKind.Explicit, Size = 8 * sizeof(float))]
|
|
public struct GradientUniformStruct
|
|
{
|
|
[FieldOffset(0 * sizeof(float))]
|
|
public float Position;
|
|
|
|
[FieldOffset(4 * sizeof(float))]
|
|
public Vector4 Color;
|
|
}
|
|
}
|