You cannot select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

57 lines
2.5 KiB
Kotlin

package me.eater.threedom.gl.vertex
import me.eater.threedom.gl.vertex.VertexDataPoint.*
import org.joml.*
import java.nio.ByteBuffer
import kotlin.reflect.KProperty
import kotlin.reflect.KProperty1
abstract class VertexData() {
private val items = linkedMapOf<String, Pair<Int, VertexDataPoint<*>>>()
private var offset = 0
val length
get() = items.map { (_, v) -> v.component2().length }.sum()
class VertexDataRegister<T>(private val default: T, val provider: (default: T) -> VertexDataPoint<T>) {
operator fun provideDelegate(thisRef: VertexData, prop: KProperty<*>): VertexDataPoint<T> {
val delegate = provider(default)
thisRef.items[prop.name] = thisRef.offset to delegate
thisRef.offset += delegate.length
return delegate
}
}
fun int(value: Int = 0): VertexDataRegister<Int> = VertexDataRegister(value, ::SingleInt)
fun double(value: Double = 0.0): VertexDataRegister<Double> = VertexDataRegister(value, ::SingleDouble)
fun float(value: Float = 0f): VertexDataRegister<Float> = VertexDataRegister(value, ::SingleFloat)
fun bool(value: Boolean = false): VertexDataRegister<Boolean> = VertexDataRegister(value, ::SingleBoolean)
fun vec2(value: Vector2fc = Vector2f()): VertexDataRegister<Vector2fc> = VertexDataRegister(value, ::Vec2)
fun vec3(value: Vector3fc = Vector3f()): VertexDataRegister<Vector3fc> = VertexDataRegister(value, ::Vec3)
fun vec4(value: Vector4fc = Vector4f()): VertexDataRegister<Vector4fc> = VertexDataRegister(value, ::Vec4)
fun mat3(value: Matrix3fc = Matrix3f()): VertexDataRegister<Matrix3fc> = VertexDataRegister(value, ::Mat3)
fun mat4(value: Matrix4fc = Matrix4f()): VertexDataRegister<Matrix4fc> = VertexDataRegister(value, ::Mat4)
fun getDataPoint(prop: KProperty1<out VertexData, *>): VertexDataPoint<*>? = items[prop.name]?.component2()
fun getOffset(prop: KProperty1<out VertexData, *>): Int? = items[prop.name]?.component1()
fun writeNonInterleaved(position: Int, size: Int, byteBuffer: ByteBuffer) {
var offset = 0;
for ((_, pair) in items) {
val (_, item) = pair
item.write(offset + (position * item.length), byteBuffer)
offset += item.length * size
}
}
fun write(position: Int, byteBuffer: ByteBuffer) {
var pos = position
for ((_, pair) in items) {
val (_, item) = pair
item.write(pos, byteBuffer)
pos += item.length
}
}
}