forked from kscience/visionforge
minor fix to Root rotations
This commit is contained in:
parent
6a801f9999
commit
92bfb173d8
@ -5,12 +5,17 @@ import space.kscience.dataforge.names.Name
|
|||||||
import space.kscience.dataforge.names.parseAsName
|
import space.kscience.dataforge.names.parseAsName
|
||||||
import space.kscience.dataforge.names.plus
|
import space.kscience.dataforge.names.plus
|
||||||
import space.kscience.dataforge.names.withIndex
|
import space.kscience.dataforge.names.withIndex
|
||||||
|
import space.kscience.kmath.complex.Quaternion
|
||||||
|
import space.kscience.kmath.geometry.fromRotationMatrix
|
||||||
|
import space.kscience.kmath.linear.VirtualMatrix
|
||||||
import space.kscience.visionforge.MutableVisionContainer
|
import space.kscience.visionforge.MutableVisionContainer
|
||||||
import space.kscience.visionforge.isEmpty
|
import space.kscience.visionforge.isEmpty
|
||||||
import space.kscience.visionforge.set
|
import space.kscience.visionforge.set
|
||||||
import space.kscience.visionforge.solid.*
|
import space.kscience.visionforge.solid.*
|
||||||
import space.kscience.visionforge.solid.SolidMaterial.Companion.MATERIAL_COLOR_KEY
|
import space.kscience.visionforge.solid.SolidMaterial.Companion.MATERIAL_COLOR_KEY
|
||||||
import kotlin.math.*
|
import kotlin.math.PI
|
||||||
|
import kotlin.math.cos
|
||||||
|
import kotlin.math.sin
|
||||||
|
|
||||||
private val volumesName = Name.EMPTY //"volumes".asName()
|
private val volumesName = Name.EMPTY //"volumes".asName()
|
||||||
|
|
||||||
@ -28,12 +33,10 @@ private data class RootToSolidContext(
|
|||||||
val colorCache: MutableMap<Meta, String> = mutableMapOf(),
|
val colorCache: MutableMap<Meta, String> = mutableMapOf(),
|
||||||
)
|
)
|
||||||
|
|
||||||
// converting to XYZ to Tait–Bryan angles according to https://en.wikipedia.org/wiki/Euler_angles#Rotation_matrix
|
// apply rotation from a matrix
|
||||||
private fun Solid.rotate(rot: DoubleArray) {
|
private fun Solid.rotate(rot: DoubleArray) {
|
||||||
val xAngle = atan2(-rot[5], rot[8])
|
val matrix = VirtualMatrix(3, 3) { i, j -> rot[i * 3 + j] }
|
||||||
val yAngle = atan2(rot[2], sqrt(1.0 - rot[2].pow(2)))
|
quaternion = Quaternion.fromRotationMatrix(matrix)
|
||||||
val zAngle = atan2(-rot[1], rot[0])
|
|
||||||
rotation = Float32Vector3D(xAngle, yAngle, zAngle)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private fun Solid.translate(trans: DoubleArray) {
|
private fun Solid.translate(trans: DoubleArray) {
|
||||||
|
@ -15,13 +15,13 @@ import kotlin.math.sin
|
|||||||
|
|
||||||
fun main() = serve {
|
fun main() = serve {
|
||||||
|
|
||||||
val azimuth = 60.degrees
|
// val azimuth = 60.degrees
|
||||||
val inclination = 15.degrees
|
// val inclination = 15.degrees
|
||||||
|
|
||||||
val direction = with(QuaternionField) {
|
// val direction = with(QuaternionField) {
|
||||||
Quaternion.fromRotation(-azimuth, Euclidean3DSpace.zAxis) *
|
// Quaternion.fromRotation(-azimuth, Euclidean3DSpace.zAxis) *
|
||||||
Quaternion.fromRotation(Angle.piDiv2 - inclination, Euclidean3DSpace.yAxis)
|
// Quaternion.fromRotation(Angle.piDiv2 - inclination, Euclidean3DSpace.yAxis)
|
||||||
}
|
// }
|
||||||
|
|
||||||
//val direction2 = Quaternion.fromEuler(Angle.zero, Angle.piDiv2 - inclination, -azimuth, RotationOrder.ZYX)
|
//val direction2 = Quaternion.fromEuler(Angle.zero, Angle.piDiv2 - inclination, -azimuth, RotationOrder.ZYX)
|
||||||
|
|
||||||
@ -43,7 +43,7 @@ fun main() = serve {
|
|||||||
solidGroup("frame") {
|
solidGroup("frame") {
|
||||||
z = 60
|
z = 60
|
||||||
|
|
||||||
val antenna = solidGroup("antenna") {
|
solidGroup("antenna") {
|
||||||
axes(200)
|
axes(200)
|
||||||
tube(40, 10, 30)
|
tube(40, 10, 30)
|
||||||
sphereLayer(100, 95, theta = PI / 6) {
|
sphereLayer(100, 95, theta = PI / 6) {
|
||||||
|
@ -206,7 +206,7 @@ public var Solid.rotationZ: Number by float(Z_ROTATION_KEY, 0f)
|
|||||||
/**
|
/**
|
||||||
* Raw quaternion value defined in properties
|
* Raw quaternion value defined in properties
|
||||||
*/
|
*/
|
||||||
public var Solid.quaternionValue: Quaternion?
|
public var Solid.quaternionOrNull: Quaternion?
|
||||||
get() = properties.getValue(ROTATION_KEY)?.list?.let {
|
get() = properties.getValue(ROTATION_KEY)?.list?.let {
|
||||||
require(it.size == 4) { "Quaternion must be a number array of 4 elements" }
|
require(it.size == 4) { "Quaternion must be a number array of 4 elements" }
|
||||||
Quaternion(it[0].float, it[1].float, it[2].float, it[3].float)
|
Quaternion(it[0].float, it[1].float, it[2].float, it[3].float)
|
||||||
@ -229,14 +229,14 @@ public var Solid.quaternionValue: Quaternion?
|
|||||||
* Quaternion value including information from euler angles
|
* Quaternion value including information from euler angles
|
||||||
*/
|
*/
|
||||||
public var Solid.quaternion: Quaternion
|
public var Solid.quaternion: Quaternion
|
||||||
get() = quaternionValue ?: Quaternion.fromEuler(
|
get() = quaternionOrNull ?: Quaternion.fromEuler(
|
||||||
rotationX.radians,
|
rotationX.radians,
|
||||||
rotationY.radians,
|
rotationY.radians,
|
||||||
rotationZ.radians,
|
rotationZ.radians,
|
||||||
rotationOrder
|
rotationOrder
|
||||||
)
|
)
|
||||||
set(value) {
|
set(value) {
|
||||||
quaternionValue = value
|
quaternionOrNull = value
|
||||||
}
|
}
|
||||||
|
|
||||||
public var Solid.scaleX: Number by float(X_SCALE_KEY, 1f)
|
public var Solid.scaleX: Number by float(X_SCALE_KEY, 1f)
|
||||||
|
@ -41,7 +41,7 @@ public fun Object3D.updatePosition(vision: Vision) {
|
|||||||
if (vision is Solid) {
|
if (vision is Solid) {
|
||||||
position.set(vision.x, vision.y, vision.z)
|
position.set(vision.x, vision.y, vision.z)
|
||||||
|
|
||||||
val quaternion = vision.quaternionValue
|
val quaternion = vision.quaternionOrNull
|
||||||
|
|
||||||
if (quaternion != null) {
|
if (quaternion != null) {
|
||||||
setRotationFromQuaternion(
|
setRotationFromQuaternion(
|
||||||
|
Loading…
Reference in New Issue
Block a user