commonMain.ru.casperix.math.curve.float32.Bezier2f.kt Maven / Gradle / Ivy
package ru.casperix.math.curve.float32
import ru.casperix.math.curve.CurveHelper
import ru.casperix.math.interpolation.float32.InterpolationFloat
import ru.casperix.math.vector.float32.Vector2f
import ru.casperix.misc.clamp
import kotlinx.serialization.Serializable
import kotlin.math.roundToInt
@Serializable
class Bezier2f(val points: List) : ParametricCurve2f {
init {
if (points.isEmpty()) throw Error("Curve must contains points")
}
override fun divide(t: Float): Pair {
TODO("Not yet implemented")
}
override fun getPosition(t: Float): Vector2f {
val segments = points.size - 1
if (segments == 0) {
return points[0]
}
if (segments == 1) {
return InterpolationFloat.vector2(points[0], points[1], t)
}
val factor = segments * t.clamp(0f, 1f)
val index = factor.roundToInt()
val fract = factor - index.toFloat() + 0.5f
val main = points[index]
var last = points.getOrNull(index - 1)
var next = points.getOrNull(index + 1)
if (last == null) {
val dir = next!! - main
last = main - dir
}
if (next == null) {
val dir = last!! - main
next = main - dir
}
val a = (last + main) / 2f
val b = main
val c = (next + main) / 2f
return BezierQuadratic2f(a, b, c).getPosition(fract)
}
override fun length(): Float {
return CurveHelper.calculateLength(this, 10)
}
}