added curves
This commit is contained in:
@@ -155,4 +155,24 @@ fun transformOffsetByScale(offset: Vector3f, scale: Vector3f): Vector3f {
|
|||||||
|
|
||||||
fun lerp(x: Float, y: Float, t: Float) : Float {
|
fun lerp(x: Float, y: Float, t: Float) : Float {
|
||||||
return x + (y - x) * t
|
return x + (y - x) * t
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
fun interpolateCurve(curve: Array<Vector3f>, t: Float): Vector3f {
|
||||||
|
if (curve.size < 2) { return curve[0] }
|
||||||
|
|
||||||
|
val clampedT = t.coerceIn(0.0f, 1.0f)
|
||||||
|
|
||||||
|
val scaledT = clampedT * (curve.size - 1)
|
||||||
|
val segmentIndex = scaledT.toInt()
|
||||||
|
val segmentT = scaledT - segmentIndex
|
||||||
|
|
||||||
|
val start = curve[segmentIndex]
|
||||||
|
val end = curve[(segmentIndex + 1).coerceAtMost(curve.size - 1)] // Ensure bounds
|
||||||
|
|
||||||
|
return Vector3f(
|
||||||
|
start.x + (end.x - start.x) * segmentT,
|
||||||
|
start.y + (end.y - start.y) * segmentT,
|
||||||
|
start.z + (end.z - start.z) * segmentT
|
||||||
|
)
|
||||||
}
|
}
|
||||||
@@ -18,8 +18,8 @@ class Particle(private val particleParams: ParticleParams) {
|
|||||||
|
|
||||||
private var rot = randomBetweenVector3f(particleParams.rotRandom.first, particleParams.rotRandom.second)
|
private var rot = randomBetweenVector3f(particleParams.rotRandom.first, particleParams.rotRandom.second)
|
||||||
private val rotVel = randomBetweenVector3f(particleParams.rotVelRandom.first, particleParams.rotVelRandom.second)
|
private val rotVel = randomBetweenVector3f(particleParams.rotVelRandom.first, particleParams.rotVelRandom.second)
|
||||||
private val scale = randomBetweenVector3f(particleParams.sizeRandom.first, particleParams.sizeRandom.second)
|
|
||||||
private var vel = randomBetweenVector3f(particleParams.velRandom.first, particleParams.velRandom.second)
|
private var vel = randomBetweenVector3f(particleParams.velRandom.first, particleParams.velRandom.second)
|
||||||
|
private var scale = randomBetweenVector3f(particleParams.sizeRandom.first, particleParams.sizeRandom.second)
|
||||||
|
|
||||||
private var blockDisplay: DisplayEntity? = null
|
private var blockDisplay: DisplayEntity? = null
|
||||||
|
|
||||||
@@ -32,6 +32,13 @@ class Particle(private val particleParams: ParticleParams) {
|
|||||||
fun init(pos: Vec3d) {
|
fun init(pos: Vec3d) {
|
||||||
this.pos = pos
|
this.pos = pos
|
||||||
|
|
||||||
|
if ( particleParams.uniformSize ) {
|
||||||
|
val randomUniform = randomFloatBetween(particleParams.sizeRandom.first.x, particleParams.sizeRandom.second.x)
|
||||||
|
scale.x = randomUniform
|
||||||
|
scale.y = randomUniform
|
||||||
|
scale.z = randomUniform
|
||||||
|
}
|
||||||
|
|
||||||
val (quatRot, newOffset) = calcTransformOffset(rot, initOffset, scale)
|
val (quatRot, newOffset) = calcTransformOffset(rot, initOffset, scale)
|
||||||
|
|
||||||
val properties = DisplayEntityProperties(
|
val properties = DisplayEntityProperties(
|
||||||
@@ -81,23 +88,20 @@ class Particle(private val particleParams: ParticleParams) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
// TODO: rotVelRandom, rotVelCurve, sizeCurve, forceFields
|
// TODO: forceFields, shape
|
||||||
private fun calcNewProperties() : DisplayEntityProperties {
|
private fun calcNewProperties() : DisplayEntityProperties {
|
||||||
fun calcBlockCurve() : String {
|
|
||||||
val newBlockIdx = round(
|
|
||||||
lerp(
|
|
||||||
0.0f,
|
|
||||||
particleParams.blockCurve.lastIndex.toFloat(),
|
|
||||||
(timeAlive.toFloat() / particleParams.lifeTime.toFloat()).coerceIn(0.0f, 1.0f)
|
|
||||||
)
|
|
||||||
).toInt()
|
|
||||||
|
|
||||||
|
fun calcBlockCurve(timeAliveClamped: Float) : String {
|
||||||
|
val newBlockIdx = round(lerp(0.0f, particleParams.blockCurve.lastIndex.toFloat(), timeAliveClamped)).toInt()
|
||||||
return particleParams.blockCurve[newBlockIdx]
|
return particleParams.blockCurve[newBlockIdx]
|
||||||
}
|
}
|
||||||
|
|
||||||
fun calcRot() : Vector3f {
|
fun calcRot(timeAliveClamped: Float) : Vector3f {
|
||||||
val newRot = Vector3f(rot)
|
val newRot = Vector3f(rot)
|
||||||
newRot.add(rotVel)
|
val newVel = Vector3f(rotVel)
|
||||||
|
|
||||||
|
newVel.mul(interpolateCurve(particleParams.sizeCurve, timeAliveClamped))
|
||||||
|
newRot.add(newVel)
|
||||||
return newRot
|
return newRot
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -115,17 +119,24 @@ class Particle(private val particleParams: ParticleParams) {
|
|||||||
return Pair(vel, newOffset)
|
return Pair(vel, newOffset)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
fun calcSize(timeAliveClamped: Float) : Vector3f {
|
||||||
|
val scale = Vector3f(scale)
|
||||||
|
scale.mul(interpolateCurve(particleParams.sizeCurve, timeAliveClamped))
|
||||||
|
return scale
|
||||||
|
}
|
||||||
|
|
||||||
|
val timeAliveClamped = (timeAlive.toFloat() / particleParams.lifeTime.toFloat()).coerceIn(0.0f, 1.0f)
|
||||||
|
|
||||||
val newBlock = calcBlockCurve()
|
val newBlock = calcBlockCurve(timeAliveClamped)
|
||||||
val (newVel, newOffset) = calcOffset()
|
val (newVel, newOffset) = calcOffset()
|
||||||
val newRot = calcRot()
|
val newRot = calcRot(timeAliveClamped)
|
||||||
|
val newScale = calcSize(timeAliveClamped)
|
||||||
|
|
||||||
vel = newVel
|
vel = newVel
|
||||||
offset = newOffset
|
offset = newOffset
|
||||||
rot = newRot
|
rot = newRot
|
||||||
|
|
||||||
val (quatRot, transformOffset) = calcTransformOffset(newRot, initOffset, scale /* newScale */)
|
val (quatRot, transformOffset) = calcTransformOffset(newRot, initOffset, newScale)
|
||||||
val combinedOffset = transformOffset.add(newOffset)
|
val combinedOffset = transformOffset.add(newOffset)
|
||||||
|
|
||||||
val newProperties = DisplayEntityProperties(
|
val newProperties = DisplayEntityProperties(
|
||||||
@@ -133,7 +144,7 @@ class Particle(private val particleParams: ParticleParams) {
|
|||||||
blockType = newBlock,
|
blockType = newBlock,
|
||||||
translation = combinedOffset,
|
translation = combinedOffset,
|
||||||
leftRotation = quatRot,
|
leftRotation = quatRot,
|
||||||
scale = scale, //fix
|
scale = newScale,
|
||||||
tags = arrayOf("BPS_Particle")
|
tags = arrayOf("BPS_Particle")
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|||||||
@@ -2,21 +2,24 @@ package com.bytedice.bde_particles.particle
|
|||||||
|
|
||||||
import org.joml.Vector3f
|
import org.joml.Vector3f
|
||||||
|
|
||||||
// sizeRandom: set y and z on both vectors to -1 for uniform scale // not implemented
|
// TODO: order these correctly, explain all
|
||||||
|
// sizeRandom: if uniformSize is true then sizeRandom will be uniform (cubic) and the values are taken from X
|
||||||
// lifeTime: any value below 1 will result in a particle not spawning
|
// lifeTime: any value below 1 will result in a particle not spawning
|
||||||
// minVel values 0 or less mean the particle can travel however slow it wants
|
// minVel: values 0 or less mean the particle can travel however slow it wants
|
||||||
|
// gravity: Y being -0.025 is close to regular gravity
|
||||||
data class ParticleParams (
|
data class ParticleParams (
|
||||||
//val shape: Shape, // add later, start with single point
|
//val shape: Shape, // add later, start with single point
|
||||||
val blockCurve: Array<String> = arrayOf("minecraft:purple_concrete", "minecraft:purple_stained_glass"),
|
val blockCurve: Array<String> = arrayOf("minecraft:shroomlight", "minecraft:orange_concrete", "minecraft:orange_stained_glass", "minecraft:gray_stained_glass", "minecraft:light_gray_stained_glass"),
|
||||||
val rotRandom: Pair<Vector3f, Vector3f> = Pair(Vector3f(0.0f, 0.0f, 0.0f), Vector3f(360.0f, 360.0f, 360.0f)),
|
val rotRandom: Pair<Vector3f, Vector3f> = Pair(Vector3f(0.0f, 0.0f, 0.0f), Vector3f(360.0f, 360.0f, 360.0f)),
|
||||||
val rotVelRandom: Pair<Vector3f, Vector3f> = Pair(Vector3f(-0.2f, -0.2f, -0.2f), Vector3f(0.2f, 0.2f, 0.2f)),
|
val rotVelRandom: Pair<Vector3f, Vector3f> = Pair(Vector3f(-0.2f, -0.2f, -0.2f), Vector3f(0.2f, 0.2f, 0.2f)),
|
||||||
val rotVelCurve: Array<Vector3f> = arrayOf(Vector3f(1.0f, 1.0f, 1.0f), Vector3f(0.0f, 0.0f, 0.0f)),
|
val rotVelCurve: Array<Vector3f> = arrayOf(Vector3f(1.0f, 1.0f, 1.0f), Vector3f(0.0f, 0.0f, 0.0f)),
|
||||||
val sizeRandom: Pair<Vector3f, Vector3f> = Pair(Vector3f(0.5f, 0.5f, 0.5f), Vector3f(1.0f, 1.0f, 1.0f)),
|
val sizeRandom: Pair<Vector3f, Vector3f> = Pair(Vector3f(0.5f, 0.5f, 0.5f), Vector3f(1.0f, 1.0f, 1.0f)),
|
||||||
val sizeCurve: Array<Vector3f> = arrayOf(Vector3f(1.0f, 1.0f, 1.0f), Vector3f(0.0f, 0.0f, 0.0f)),
|
val uniformSize: Boolean = true,
|
||||||
val velRandom: Pair<Vector3f, Vector3f> = Pair(Vector3f(-0.3f, 0.3f, -0.3f), Vector3f(0.3f, 0.6f, 0.3f)),
|
val sizeCurve: Array<Vector3f> = arrayOf(Vector3f(1.0f, 1.0f, 1.0f), Vector3f(0.5f, 0.5f, 0.5f)),
|
||||||
|
val velRandom: Pair<Vector3f, Vector3f> = Pair(Vector3f(-0.1f, 0.4f, -0.1f), Vector3f(0.1f, 0.8f, 0.1f)),
|
||||||
val forceFields: ForceField = ForceField(),
|
val forceFields: ForceField = ForceField(),
|
||||||
val gravity: Vector3f = Vector3f(0.0f, -0.025f, 0.0f),
|
val gravity: Vector3f = Vector3f(0.0f, -0.01f, 0.0f),
|
||||||
val drag: Float = 0.075f,
|
val drag: Float = 0.075f,
|
||||||
val minVel: Float = 0.0f,
|
val minVel: Float = 0.0f,
|
||||||
val lifeTime: Int = 20
|
val lifeTime: Int = 30
|
||||||
)
|
)
|
||||||
Reference in New Issue
Block a user