|
Lines 35-40
a/Source/WebCore/Modules/webxr/WebXRRigidTransform.cpp_sec1
|
| 35 |
|
35 |
|
| 36 |
namespace WebCore { |
36 |
namespace WebCore { |
| 37 |
|
37 |
|
|
|
38 |
static bool normalizeQuaternion(DOMPointInit& q) |
| 39 |
{ |
| 40 |
const double length = std::sqrt(q.x * q.x + q.y * q.y + q.z * q.z + q.w * q.w); |
| 41 |
if (WTF::areEssentiallyEqual<double>(length, 0)) |
| 42 |
return false; |
| 43 |
q.x /= length; |
| 44 |
q.y /= length; |
| 45 |
q.z /= length; |
| 46 |
q.w /= length; |
| 47 |
return true; |
| 48 |
} |
| 49 |
|
| 38 |
WTF_MAKE_ISO_ALLOCATED_IMPL(WebXRRigidTransform); |
50 |
WTF_MAKE_ISO_ALLOCATED_IMPL(WebXRRigidTransform); |
| 39 |
|
51 |
|
| 40 |
Ref<WebXRRigidTransform> WebXRRigidTransform::create() |
52 |
Ref<WebXRRigidTransform> WebXRRigidTransform::create() |
|
Lines 42-47
Ref<WebXRRigidTransform> WebXRRigidTransform::create()
a/Source/WebCore/Modules/webxr/WebXRRigidTransform.cpp_sec2
|
| 42 |
return adoptRef(*new WebXRRigidTransform({ }, { })); |
54 |
return adoptRef(*new WebXRRigidTransform({ }, { })); |
| 43 |
} |
55 |
} |
| 44 |
|
56 |
|
|
|
57 |
Ref<WebXRRigidTransform> WebXRRigidTransform::create(const TransformationMatrix& transform) |
| 58 |
{ |
| 59 |
return adoptRef(*new WebXRRigidTransform(transform)); |
| 60 |
} |
| 61 |
|
| 62 |
|
| 45 |
ExceptionOr<Ref<WebXRRigidTransform>> WebXRRigidTransform::create(const DOMPointInit& position, const DOMPointInit& orientation) |
63 |
ExceptionOr<Ref<WebXRRigidTransform>> WebXRRigidTransform::create(const DOMPointInit& position, const DOMPointInit& orientation) |
| 46 |
{ |
64 |
{ |
| 47 |
// The XRRigidTransform(position, orientation) constructor MUST perform the following steps when invoked: |
65 |
// The XRRigidTransform(position, orientation) constructor MUST perform the following steps when invoked: |
|
Lines 58-74
ExceptionOr<Ref<WebXRRigidTransform>> WebXRRigidTransform::create(const DOMPoint
a/Source/WebCore/Modules/webxr/WebXRRigidTransform.cpp_sec3
|
| 58 |
// 6. Else initialize transform’s orientation’s x value to orientation’s x dictionary member, y value to orientation’s y dictionary member, z value to orientation’s z dictionary member and w value to orientation’s w dictionary member. |
76 |
// 6. Else initialize transform’s orientation’s x value to orientation’s x dictionary member, y value to orientation’s y dictionary member, z value to orientation’s z dictionary member and w value to orientation’s w dictionary member. |
| 59 |
// 7. Normalize x, y, z, and w components of transform’s orientation. |
77 |
// 7. Normalize x, y, z, and w components of transform’s orientation. |
| 60 |
DOMPointInit orientationInit { orientation.x, orientation.y, orientation.z, orientation.w }; |
78 |
DOMPointInit orientationInit { orientation.x, orientation.y, orientation.z, orientation.w }; |
| 61 |
{ |
79 |
if (!normalizeQuaternion(orientationInit)) |
| 62 |
double length = std::sqrt(orientationInit.x * orientationInit.x + orientationInit.y * orientationInit.y |
80 |
return Exception { InvalidStateError }; |
| 63 |
+ orientationInit.z * orientationInit.z + orientationInit.w * orientationInit.w); |
|
|
| 64 |
if (WTF::areEssentiallyEqual<double>(length, 0)) |
| 65 |
return Exception { InvalidStateError }; |
| 66 |
|
| 67 |
orientationInit= { |
| 68 |
orientationInit.x / length, orientationInit.y / length, |
| 69 |
orientationInit.z / length, orientationInit.w / length, |
| 70 |
}; |
| 71 |
} |
| 72 |
|
81 |
|
| 73 |
// 8. Return transform. |
82 |
// 8. Return transform. |
| 74 |
return adoptRef(*new WebXRRigidTransform(positionInit, orientationInit)); |
83 |
return adoptRef(*new WebXRRigidTransform(positionInit, orientationInit)); |
|
Lines 78-87
WebXRRigidTransform::WebXRRigidTransform(const DOMPointInit& position, const DOM
a/Source/WebCore/Modules/webxr/WebXRRigidTransform.cpp_sec4
|
| 78 |
: m_position(DOMPointReadOnly::create(position)) |
87 |
: m_position(DOMPointReadOnly::create(position)) |
| 79 |
, m_orientation(DOMPointReadOnly::create(orientation)) |
88 |
, m_orientation(DOMPointReadOnly::create(orientation)) |
| 80 |
{ |
89 |
{ |
| 81 |
// FIXME: implement properly, per spec. |
90 |
TransformationMatrix translation; |
| 82 |
TransformationMatrix matrix; |
91 |
translation.translate3d(position.x, position.y, position.z); |
| 83 |
auto matrixData = matrix.toColumnMajorFloatArray(); |
92 |
auto rotation = TransformationMatrix::fromQuaternion(orientation.x, orientation.y, orientation.z, orientation.w); |
| 84 |
m_matrix = Float32Array::create(matrixData.data(), matrixData.size()); |
93 |
m_rawTransform = translation * rotation; |
|
|
94 |
} |
| 95 |
|
| 96 |
WebXRRigidTransform::WebXRRigidTransform(const TransformationMatrix& transform) |
| 97 |
: m_position(DOMPointReadOnly::create({ })) |
| 98 |
, m_orientation(DOMPointReadOnly::create({ })) |
| 99 |
, m_rawTransform(transform) |
| 100 |
{ |
| 101 |
if (transform.isIdentity()) { |
| 102 |
// TransformationMatrix::decompose returns a empty quaternion instead of unit quaternion for Identity. |
| 103 |
// WebXR tests expect a unit quaternion for this case. |
| 104 |
return; |
| 105 |
} |
| 106 |
|
| 107 |
TransformationMatrix::Decomposed4Type decomp = { }; |
| 108 |
transform.decompose4(decomp); |
| 109 |
|
| 110 |
m_position = DOMPointReadOnly::create(decomp.translateX, decomp.translateY, decomp.translateZ, 1.0f); |
| 111 |
|
| 112 |
DOMPointInit orientationInit { -decomp.quaternionX, -decomp.quaternionY, -decomp.quaternionZ, decomp.quaternionW }; |
| 113 |
normalizeQuaternion(orientationInit); |
| 114 |
m_orientation = DOMPointReadOnly::create(orientationInit); |
| 85 |
} |
115 |
} |
| 86 |
|
116 |
|
| 87 |
WebXRRigidTransform::~WebXRRigidTransform() = default; |
117 |
WebXRRigidTransform::~WebXRRigidTransform() = default; |
|
Lines 96-112
const DOMPointReadOnly& WebXRRigidTransform::orientation() const
a/Source/WebCore/Modules/webxr/WebXRRigidTransform.cpp_sec5
|
| 96 |
return m_orientation; |
126 |
return m_orientation; |
| 97 |
} |
127 |
} |
| 98 |
|
128 |
|
| 99 |
Ref<Float32Array> WebXRRigidTransform::matrix() const |
129 |
const Float32Array& WebXRRigidTransform::matrix() |
|
|
130 |
{ |
| 131 |
if (m_matrix && !m_matrix->isDetached()) |
| 132 |
return *m_matrix; |
| 133 |
|
| 134 |
// Lazily create matrix Float32Array. |
| 135 |
auto matrixData = m_rawTransform.toColumnMajorFloatArray(); |
| 136 |
m_matrix = Float32Array::create(matrixData.data(), matrixData.size()); |
| 137 |
|
| 138 |
return *m_matrix; |
| 139 |
} |
| 140 |
|
| 141 |
const WebXRRigidTransform& WebXRRigidTransform::inverse() |
| 100 |
{ |
142 |
{ |
| 101 |
auto matrix = Float32Array::create(16); |
143 |
// The inverse of a inverse object should return the original object. |
| 102 |
matrix->zeroFill(); |
144 |
if (m_parentInverse) |
| 103 |
return matrix; |
145 |
return *m_parentInverse; |
|
|
146 |
|
| 147 |
// Inverse should always return the same object. |
| 148 |
if (m_inverse) |
| 149 |
return *m_inverse; |
| 150 |
|
| 151 |
auto inverseTransform = m_rawTransform.inverse(); |
| 152 |
ASSERT(!!inverseTransform); |
| 153 |
|
| 154 |
m_inverse = WebXRRigidTransform::create(*inverseTransform); |
| 155 |
// The inverse of a inverse object should return the original object. |
| 156 |
m_inverse->m_parentInverse = makeWeakPtr(this); |
| 157 |
|
| 158 |
return *m_inverse; |
| 104 |
} |
159 |
} |
| 105 |
|
160 |
|
| 106 |
Ref<WebXRRigidTransform> WebXRRigidTransform::inverse() const |
161 |
const TransformationMatrix& WebXRRigidTransform::rawTransform() const |
| 107 |
{ |
162 |
{ |
| 108 |
// FIXME: implement properly. |
163 |
return m_rawTransform; |
| 109 |
return WebXRRigidTransform::create(); |
|
|
| 110 |
} |
164 |
} |
| 111 |
|
165 |
|
| 112 |
} // namespace WebCore |
166 |
} // namespace WebCore |