|
| 1 | +namespace AssetRipper.TextureDecoder; |
| 2 | + |
| 3 | +public readonly ref struct Span2D<T> |
| 4 | +{ |
| 5 | + public int Width { get; } |
| 6 | + public int Height { get; } |
| 7 | + public Span<T> Data { get; } |
| 8 | + |
| 9 | + public Span2D(Span<T> data, int width, int height) |
| 10 | + { |
| 11 | + Validate(data, width, height); |
| 12 | + Data = data; |
| 13 | + Width = width; |
| 14 | + Height = height; |
| 15 | + |
| 16 | + static void Validate(Span<T> data, int width, int height) |
| 17 | + { |
| 18 | + ArgumentOutOfRangeException.ThrowIfNegative(width); |
| 19 | + ArgumentOutOfRangeException.ThrowIfNegative(height); |
| 20 | + if (data.Length != width * height) |
| 21 | + { |
| 22 | + throw new ArgumentException("Data length does not match width and height.", nameof(data)); |
| 23 | + } |
| 24 | + } |
| 25 | + } |
| 26 | + |
| 27 | + //public Span<T> this[int y] => Data.Slice(y * Width, Width); |
| 28 | + |
| 29 | + public T this[int x, int y] |
| 30 | + { |
| 31 | + get => Data[y * Width + x]; |
| 32 | + set => Data[y * Width + x] = value; |
| 33 | + } |
| 34 | + |
| 35 | + public static implicit operator ReadOnlySpan2D<T>(Span2D<T> span) => new(span.Data, span.Width, span.Height); |
| 36 | + |
| 37 | + public static explicit operator Span2D<T>(T[] array) => new(array, array.Length, 1); |
| 38 | + |
| 39 | + public static explicit operator Span2D<T>(Span<T> span) => new(span, span.Length, 1); |
| 40 | +} |
0 commit comments