node-native-win-utils 1.4.0 → 2.1.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +29 -82
- package/binding.gyp +2 -0
- package/dist/dirnameLocal.cjs +4 -0
- package/dist/dirnameLocal.d.cts +1 -0
- package/dist/dirnameLocal.d.mts +1 -0
- package/dist/dirnameLocal.mjs +2 -0
- package/dist/{index.js → index.cjs} +83 -16
- package/dist/{index.d.ts → index.d.cts} +68 -17
- package/dist/index.d.mts +230 -0
- package/dist/index.mjs +212 -0
- package/dist/keyCodes.d.mts +101 -0
- package/dist/keyCodes.mjs +201 -0
- package/node22.json +16 -0
- package/package.json +19 -9
- package/prebuilds/win32-x64/node-native-win-utils.node +0 -0
- package/src/cpp/keyboard.cpp +141 -140
- package/src/cpp/main.cpp +9 -3
- package/src/cpp/{capturewindow.cpp → screenshot.cpp} +174 -2
- package/src/dirnameLocal.mts +3 -0
- package/src/index.mts +455 -0
- package/src/keyCodes.mts +203 -0
- package/dllCopy.js +0 -14
- package/include/opencv2/core/affine.hpp +0 -678
- package/include/opencv2/core/async.hpp +0 -105
- package/include/opencv2/core/base.hpp +0 -664
- package/include/opencv2/core/bindings_utils.hpp +0 -325
- package/include/opencv2/core/bufferpool.hpp +0 -40
- package/include/opencv2/core/check.hpp +0 -170
- package/include/opencv2/core/core.hpp +0 -48
- package/include/opencv2/core/core_c.h +0 -3128
- package/include/opencv2/core/cuda/block.hpp +0 -211
- package/include/opencv2/core/cuda/border_interpolate.hpp +0 -722
- package/include/opencv2/core/cuda/color.hpp +0 -309
- package/include/opencv2/core/cuda/common.hpp +0 -131
- package/include/opencv2/core/cuda/datamov_utils.hpp +0 -113
- package/include/opencv2/core/cuda/detail/color_detail.hpp +0 -2018
- package/include/opencv2/core/cuda/detail/reduce.hpp +0 -365
- package/include/opencv2/core/cuda/detail/reduce_key_val.hpp +0 -502
- package/include/opencv2/core/cuda/detail/transform_detail.hpp +0 -392
- package/include/opencv2/core/cuda/detail/type_traits_detail.hpp +0 -191
- package/include/opencv2/core/cuda/detail/vec_distance_detail.hpp +0 -121
- package/include/opencv2/core/cuda/dynamic_smem.hpp +0 -88
- package/include/opencv2/core/cuda/emulation.hpp +0 -269
- package/include/opencv2/core/cuda/filters.hpp +0 -293
- package/include/opencv2/core/cuda/funcattrib.hpp +0 -79
- package/include/opencv2/core/cuda/functional.hpp +0 -805
- package/include/opencv2/core/cuda/limits.hpp +0 -128
- package/include/opencv2/core/cuda/reduce.hpp +0 -209
- package/include/opencv2/core/cuda/saturate_cast.hpp +0 -292
- package/include/opencv2/core/cuda/scan.hpp +0 -258
- package/include/opencv2/core/cuda/simd_functions.hpp +0 -869
- package/include/opencv2/core/cuda/transform.hpp +0 -75
- package/include/opencv2/core/cuda/type_traits.hpp +0 -90
- package/include/opencv2/core/cuda/utility.hpp +0 -230
- package/include/opencv2/core/cuda/vec_distance.hpp +0 -232
- package/include/opencv2/core/cuda/vec_math.hpp +0 -923
- package/include/opencv2/core/cuda/vec_traits.hpp +0 -288
- package/include/opencv2/core/cuda/warp.hpp +0 -139
- package/include/opencv2/core/cuda/warp_reduce.hpp +0 -76
- package/include/opencv2/core/cuda/warp_shuffle.hpp +0 -162
- package/include/opencv2/core/cuda.hpp +0 -1279
- package/include/opencv2/core/cuda.inl.hpp +0 -763
- package/include/opencv2/core/cuda_stream_accessor.hpp +0 -86
- package/include/opencv2/core/cuda_types.hpp +0 -144
- package/include/opencv2/core/cv_cpu_dispatch.h +0 -381
- package/include/opencv2/core/cv_cpu_helper.h +0 -550
- package/include/opencv2/core/cvdef.h +0 -973
- package/include/opencv2/core/cvstd.hpp +0 -190
- package/include/opencv2/core/cvstd.inl.hpp +0 -197
- package/include/opencv2/core/cvstd_wrapper.hpp +0 -154
- package/include/opencv2/core/detail/async_promise.hpp +0 -71
- package/include/opencv2/core/detail/dispatch_helper.impl.hpp +0 -49
- package/include/opencv2/core/detail/exception_ptr.hpp +0 -27
- package/include/opencv2/core/directx.hpp +0 -184
- package/include/opencv2/core/dualquaternion.hpp +0 -979
- package/include/opencv2/core/dualquaternion.inl.hpp +0 -487
- package/include/opencv2/core/eigen.hpp +0 -402
- package/include/opencv2/core/fast_math.hpp +0 -433
- package/include/opencv2/core/hal/hal.hpp +0 -256
- package/include/opencv2/core/hal/interface.h +0 -190
- package/include/opencv2/core/hal/intrin.hpp +0 -939
- package/include/opencv2/core/hal/intrin_avx.hpp +0 -3177
- package/include/opencv2/core/hal/intrin_avx512.hpp +0 -3090
- package/include/opencv2/core/hal/intrin_cpp.hpp +0 -3321
- package/include/opencv2/core/hal/intrin_forward.hpp +0 -191
- package/include/opencv2/core/hal/intrin_lasx.hpp +0 -3236
- package/include/opencv2/core/hal/intrin_msa.hpp +0 -1887
- package/include/opencv2/core/hal/intrin_neon.hpp +0 -2610
- package/include/opencv2/core/hal/intrin_rvv.hpp +0 -3320
- package/include/opencv2/core/hal/intrin_rvv071.hpp +0 -2545
- package/include/opencv2/core/hal/intrin_rvv_scalable.hpp +0 -2080
- package/include/opencv2/core/hal/intrin_sse.hpp +0 -3467
- package/include/opencv2/core/hal/intrin_sse_em.hpp +0 -180
- package/include/opencv2/core/hal/intrin_vsx.hpp +0 -1608
- package/include/opencv2/core/hal/intrin_wasm.hpp +0 -2782
- package/include/opencv2/core/hal/msa_macros.h +0 -1558
- package/include/opencv2/core/hal/simd_utils.impl.hpp +0 -186
- package/include/opencv2/core/llapi/llapi.h +0 -102
- package/include/opencv2/core/mat.hpp +0 -3775
- package/include/opencv2/core/mat.inl.hpp +0 -3422
- package/include/opencv2/core/matx.hpp +0 -1536
- package/include/opencv2/core/neon_utils.hpp +0 -128
- package/include/opencv2/core/ocl.hpp +0 -917
- package/include/opencv2/core/ocl_genbase.hpp +0 -69
- package/include/opencv2/core/opencl/ocl_defs.hpp +0 -82
- package/include/opencv2/core/opencl/opencl_info.hpp +0 -212
- package/include/opencv2/core/opencl/opencl_svm.hpp +0 -81
- package/include/opencv2/core/opencl/runtime/autogenerated/opencl_clblas.hpp +0 -602
- package/include/opencv2/core/opencl/runtime/autogenerated/opencl_clfft.hpp +0 -146
- package/include/opencv2/core/opencl/runtime/autogenerated/opencl_core.hpp +0 -371
- package/include/opencv2/core/opencl/runtime/autogenerated/opencl_core_wrappers.hpp +0 -272
- package/include/opencv2/core/opencl/runtime/autogenerated/opencl_gl.hpp +0 -62
- package/include/opencv2/core/opencl/runtime/autogenerated/opencl_gl_wrappers.hpp +0 -42
- package/include/opencv2/core/opencl/runtime/opencl_clblas.hpp +0 -53
- package/include/opencv2/core/opencl/runtime/opencl_clfft.hpp +0 -53
- package/include/opencv2/core/opencl/runtime/opencl_core.hpp +0 -84
- package/include/opencv2/core/opencl/runtime/opencl_core_wrappers.hpp +0 -47
- package/include/opencv2/core/opencl/runtime/opencl_gl.hpp +0 -53
- package/include/opencv2/core/opencl/runtime/opencl_gl_wrappers.hpp +0 -47
- package/include/opencv2/core/opencl/runtime/opencl_svm_20.hpp +0 -48
- package/include/opencv2/core/opencl/runtime/opencl_svm_definitions.hpp +0 -42
- package/include/opencv2/core/opencl/runtime/opencl_svm_hsa_extension.hpp +0 -166
- package/include/opencv2/core/opengl.hpp +0 -733
- package/include/opencv2/core/openvx/ovx_defs.hpp +0 -48
- package/include/opencv2/core/operations.hpp +0 -610
- package/include/opencv2/core/optim.hpp +0 -302
- package/include/opencv2/core/ovx.hpp +0 -28
- package/include/opencv2/core/parallel/backend/parallel_for.openmp.hpp +0 -72
- package/include/opencv2/core/parallel/backend/parallel_for.tbb.hpp +0 -153
- package/include/opencv2/core/parallel/parallel_backend.hpp +0 -90
- package/include/opencv2/core/persistence.hpp +0 -1350
- package/include/opencv2/core/private/cv_cpu_include_simd_declarations.hpp +0 -30
- package/include/opencv2/core/private.cuda.hpp +0 -169
- package/include/opencv2/core/private.hpp +0 -896
- package/include/opencv2/core/quaternion.hpp +0 -1696
- package/include/opencv2/core/quaternion.inl.hpp +0 -1063
- package/include/opencv2/core/saturate.hpp +0 -180
- package/include/opencv2/core/simd_intrinsics.hpp +0 -87
- package/include/opencv2/core/softfloat.hpp +0 -514
- package/include/opencv2/core/sse_utils.hpp +0 -652
- package/include/opencv2/core/traits.hpp +0 -417
- package/include/opencv2/core/types.hpp +0 -2457
- package/include/opencv2/core/types_c.h +0 -2126
- package/include/opencv2/core/utility.hpp +0 -1229
- package/include/opencv2/core/utils/allocator_stats.hpp +0 -29
- package/include/opencv2/core/utils/allocator_stats.impl.hpp +0 -158
- package/include/opencv2/core/utils/buffer_area.private.hpp +0 -136
- package/include/opencv2/core/utils/configuration.private.hpp +0 -22
- package/include/opencv2/core/utils/filesystem.hpp +0 -82
- package/include/opencv2/core/utils/filesystem.private.hpp +0 -66
- package/include/opencv2/core/utils/fp_control.private.hpp +0 -29
- package/include/opencv2/core/utils/fp_control_utils.hpp +0 -69
- package/include/opencv2/core/utils/instrumentation.hpp +0 -125
- package/include/opencv2/core/utils/lock.private.hpp +0 -119
- package/include/opencv2/core/utils/logger.defines.hpp +0 -42
- package/include/opencv2/core/utils/logger.hpp +0 -218
- package/include/opencv2/core/utils/logtag.hpp +0 -28
- package/include/opencv2/core/utils/plugin_loader.private.hpp +0 -165
- package/include/opencv2/core/utils/tls.hpp +0 -235
- package/include/opencv2/core/utils/trace.hpp +0 -252
- package/include/opencv2/core/utils/trace.private.hpp +0 -421
- package/include/opencv2/core/va_intel.hpp +0 -75
- package/include/opencv2/core/version.hpp +0 -26
- package/include/opencv2/core/vsx_utils.hpp +0 -1047
- package/include/opencv2/core.hpp +0 -3365
- package/include/opencv2/imgcodecs/imgcodecs.hpp +0 -48
- package/include/opencv2/imgcodecs/imgcodecs_c.h +0 -1
- package/include/opencv2/imgcodecs/ios.h +0 -59
- package/include/opencv2/imgcodecs/legacy/constants_c.h +0 -54
- package/include/opencv2/imgcodecs/macosx.h +0 -20
- package/include/opencv2/imgcodecs.hpp +0 -407
- package/include/opencv2/imgproc/bindings.hpp +0 -34
- package/include/opencv2/imgproc/detail/gcgraph.hpp +0 -395
- package/include/opencv2/imgproc/hal/hal.hpp +0 -246
- package/include/opencv2/imgproc/hal/interface.h +0 -46
- package/include/opencv2/imgproc/imgproc.hpp +0 -48
- package/include/opencv2/imgproc/imgproc_c.h +0 -1177
- package/include/opencv2/imgproc/segmentation.hpp +0 -141
- package/include/opencv2/imgproc/types_c.h +0 -659
- package/include/opencv2/imgproc.hpp +0 -5035
- package/include/opencv2/opencv_modules.hpp +0 -17
- package/include/tesseract/baseapi.h +0 -820
- package/include/tesseract/capi.h +0 -485
- package/include/tesseract/export.h +0 -37
- package/include/tesseract/ltrresultiterator.h +0 -235
- package/include/tesseract/ocrclass.h +0 -158
- package/include/tesseract/osdetect.h +0 -139
- package/include/tesseract/pageiterator.h +0 -364
- package/include/tesseract/publictypes.h +0 -281
- package/include/tesseract/renderer.h +0 -334
- package/include/tesseract/resultiterator.h +0 -250
- package/include/tesseract/tesseract.h +0 -40
- package/include/tesseract/unichar.h +0 -174
- package/include/tesseract/version.h +0 -34
- package/include/tesseract/version.h.in +0 -34
- package/libs/libjpeg-turbo.lib +0 -0
- package/libs/libpng.lib +0 -0
- package/libs/opencv_core470.lib +0 -0
- package/libs/opencv_imgcodecs470.lib +0 -0
- package/libs/opencv_imgproc470.lib +0 -0
- package/libs/tesseract.lib +0 -0
- package/libs/zlib.lib +0 -0
- /package/dist/{keyCodes.js → keyCodes.cjs} +0 -0
- /package/dist/{keyCodes.d.ts → keyCodes.d.cts} +0 -0
|
@@ -1,1063 +0,0 @@
|
|
|
1
|
-
// This file is part of OpenCV project.
|
|
2
|
-
// It is subject to the license terms in the LICENSE file found in the top-level directory
|
|
3
|
-
// of this distribution and at http://opencv.org/license.html.
|
|
4
|
-
//
|
|
5
|
-
//
|
|
6
|
-
// License Agreement
|
|
7
|
-
// For Open Source Computer Vision Library
|
|
8
|
-
//
|
|
9
|
-
// Copyright (C) 2020, Huawei Technologies Co., Ltd. All rights reserved.
|
|
10
|
-
// Third party copyrights are property of their respective owners.
|
|
11
|
-
//
|
|
12
|
-
// Licensed under the Apache License, Version 2.0 (the "License");
|
|
13
|
-
// you may not use this file except in compliance with the License.
|
|
14
|
-
// You may obtain a copy of the License at
|
|
15
|
-
//
|
|
16
|
-
// http://www.apache.org/licenses/LICENSE-2.0
|
|
17
|
-
//
|
|
18
|
-
// Unless required by applicable law or agreed to in writing, software
|
|
19
|
-
// distributed under the License is distributed on an "AS IS" BASIS,
|
|
20
|
-
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
|
21
|
-
// See the License for the specific language governing permissions and
|
|
22
|
-
// limitations under the License.
|
|
23
|
-
//
|
|
24
|
-
// Author: Liangqian Kong <chargerKong@126.com>
|
|
25
|
-
// Longbu Wang <riskiest@gmail.com>
|
|
26
|
-
|
|
27
|
-
#ifndef OPENCV_CORE_QUATERNION_INL_HPP
|
|
28
|
-
#define OPENCV_CORE_QUATERNION_INL_HPP
|
|
29
|
-
|
|
30
|
-
#ifndef OPENCV_CORE_QUATERNION_HPP
|
|
31
|
-
#erorr This is not a standalone header. Include quaternion.hpp instead.
|
|
32
|
-
#endif
|
|
33
|
-
|
|
34
|
-
//@cond IGNORE
|
|
35
|
-
///////////////////////////////////////////////////////////////////////////////////////
|
|
36
|
-
//Implementation
|
|
37
|
-
namespace cv {
|
|
38
|
-
|
|
39
|
-
template <typename T>
|
|
40
|
-
Quat<T>::Quat() : w(0), x(0), y(0), z(0) {}
|
|
41
|
-
|
|
42
|
-
template <typename T>
|
|
43
|
-
Quat<T>::Quat(const Vec<T, 4> &coeff):w(coeff[0]), x(coeff[1]), y(coeff[2]), z(coeff[3]){}
|
|
44
|
-
|
|
45
|
-
template <typename T>
|
|
46
|
-
Quat<T>::Quat(const T qw, const T qx, const T qy, const T qz):w(qw), x(qx), y(qy), z(qz){}
|
|
47
|
-
|
|
48
|
-
template <typename T>
|
|
49
|
-
Quat<T> Quat<T>::createFromAngleAxis(const T angle, const Vec<T, 3> &axis)
|
|
50
|
-
{
|
|
51
|
-
T w, x, y, z;
|
|
52
|
-
T vNorm = std::sqrt(axis.dot(axis));
|
|
53
|
-
if (vNorm < CV_QUAT_EPS)
|
|
54
|
-
{
|
|
55
|
-
CV_Error(Error::StsBadArg, "this quaternion does not represent a rotation");
|
|
56
|
-
}
|
|
57
|
-
const T angle_half = angle * T(0.5);
|
|
58
|
-
w = std::cos(angle_half);
|
|
59
|
-
const T sin_v = std::sin(angle_half);
|
|
60
|
-
const T sin_norm = sin_v / vNorm;
|
|
61
|
-
x = sin_norm * axis[0];
|
|
62
|
-
y = sin_norm * axis[1];
|
|
63
|
-
z = sin_norm * axis[2];
|
|
64
|
-
return Quat<T>(w, x, y, z);
|
|
65
|
-
}
|
|
66
|
-
|
|
67
|
-
template <typename T>
|
|
68
|
-
Quat<T> Quat<T>::createFromRotMat(InputArray _R)
|
|
69
|
-
{
|
|
70
|
-
CV_CheckTypeEQ(_R.type(), cv::traits::Type<T>::value, "");
|
|
71
|
-
if (_R.rows() != 3 || _R.cols() != 3)
|
|
72
|
-
{
|
|
73
|
-
CV_Error(Error::StsBadArg, "Cannot convert matrix to quaternion: rotation matrix should be a 3x3 matrix");
|
|
74
|
-
}
|
|
75
|
-
Matx<T, 3, 3> R;
|
|
76
|
-
_R.copyTo(R);
|
|
77
|
-
|
|
78
|
-
T S, w, x, y, z;
|
|
79
|
-
T trace = R(0, 0) + R(1, 1) + R(2, 2);
|
|
80
|
-
if (trace > 0)
|
|
81
|
-
{
|
|
82
|
-
S = std::sqrt(trace + 1) * T(2);
|
|
83
|
-
x = (R(1, 2) - R(2, 1)) / S;
|
|
84
|
-
y = (R(2, 0) - R(0, 2)) / S;
|
|
85
|
-
z = (R(0, 1) - R(1, 0)) / S;
|
|
86
|
-
w = -T(0.25) * S;
|
|
87
|
-
}
|
|
88
|
-
else if (R(0, 0) > R(1, 1) && R(0, 0) > R(2, 2))
|
|
89
|
-
{
|
|
90
|
-
|
|
91
|
-
S = std::sqrt(T(1.0) + R(0, 0) - R(1, 1) - R(2, 2)) * T(2);
|
|
92
|
-
x = -T(0.25) * S;
|
|
93
|
-
y = -(R(1, 0) + R(0, 1)) / S;
|
|
94
|
-
z = -(R(0, 2) + R(2, 0)) / S;
|
|
95
|
-
w = (R(1, 2) - R(2, 1)) / S;
|
|
96
|
-
}
|
|
97
|
-
else if (R(1, 1) > R(2, 2))
|
|
98
|
-
{
|
|
99
|
-
S = std::sqrt(T(1.0) - R(0, 0) + R(1, 1) - R(2, 2)) * T(2);
|
|
100
|
-
x = (R(0, 1) + R(1, 0)) / S;
|
|
101
|
-
y = T(0.25) * S;
|
|
102
|
-
z = (R(1, 2) + R(2, 1)) / S;
|
|
103
|
-
w = (R(0, 2) - R(2, 0)) / S;
|
|
104
|
-
}
|
|
105
|
-
else
|
|
106
|
-
{
|
|
107
|
-
S = std::sqrt(T(1.0) - R(0, 0) - R(1, 1) + R(2, 2)) * T(2);
|
|
108
|
-
x = (R(0, 2) + R(2, 0)) / S;
|
|
109
|
-
y = (R(1, 2) + R(2, 1)) / S;
|
|
110
|
-
z = T(0.25) * S;
|
|
111
|
-
w = -(R(0, 1) - R(1, 0)) / S;
|
|
112
|
-
}
|
|
113
|
-
return Quat<T> (w, x, y, z);
|
|
114
|
-
}
|
|
115
|
-
|
|
116
|
-
template <typename T>
|
|
117
|
-
Quat<T> Quat<T>::createFromRvec(InputArray _rvec)
|
|
118
|
-
{
|
|
119
|
-
if (!((_rvec.cols() == 1 && _rvec.rows() == 3) || (_rvec.cols() == 3 && _rvec.rows() == 1))) {
|
|
120
|
-
CV_Error(Error::StsBadArg, "Cannot convert rotation vector to quaternion: The length of rotation vector should be 3");
|
|
121
|
-
}
|
|
122
|
-
Vec<T, 3> rvec;
|
|
123
|
-
_rvec.copyTo(rvec);
|
|
124
|
-
T psi = std::sqrt(rvec.dot(rvec));
|
|
125
|
-
if (abs(psi) < CV_QUAT_EPS) {
|
|
126
|
-
return Quat<T> (1, 0, 0, 0);
|
|
127
|
-
}
|
|
128
|
-
Vec<T, 3> axis = rvec / psi;
|
|
129
|
-
return createFromAngleAxis(psi, axis);
|
|
130
|
-
}
|
|
131
|
-
|
|
132
|
-
template <typename T>
|
|
133
|
-
inline Quat<T> Quat<T>::operator-() const
|
|
134
|
-
{
|
|
135
|
-
return Quat<T>(-w, -x, -y, -z);
|
|
136
|
-
}
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
template <typename T>
|
|
140
|
-
inline bool Quat<T>::operator==(const Quat<T> &q) const
|
|
141
|
-
{
|
|
142
|
-
return (abs(w - q.w) < CV_QUAT_EPS && abs(x - q.x) < CV_QUAT_EPS && abs(y - q.y) < CV_QUAT_EPS && abs(z - q.z) < CV_QUAT_EPS);
|
|
143
|
-
}
|
|
144
|
-
|
|
145
|
-
template <typename T>
|
|
146
|
-
inline Quat<T> Quat<T>::operator+(const Quat<T> &q1) const
|
|
147
|
-
{
|
|
148
|
-
return Quat<T>(w + q1.w, x + q1.x, y + q1.y, z + q1.z);
|
|
149
|
-
}
|
|
150
|
-
|
|
151
|
-
template <typename T>
|
|
152
|
-
inline Quat<T> operator+(const T a, const Quat<T>& q)
|
|
153
|
-
{
|
|
154
|
-
return Quat<T>(q.w + a, q.x, q.y, q.z);
|
|
155
|
-
}
|
|
156
|
-
|
|
157
|
-
template <typename T>
|
|
158
|
-
inline Quat<T> operator+(const Quat<T>& q, const T a)
|
|
159
|
-
{
|
|
160
|
-
return Quat<T>(q.w + a, q.x, q.y, q.z);
|
|
161
|
-
}
|
|
162
|
-
|
|
163
|
-
template <typename T>
|
|
164
|
-
inline Quat<T> operator-(const T a, const Quat<T>& q)
|
|
165
|
-
{
|
|
166
|
-
return Quat<T>(a - q.w, -q.x, -q.y, -q.z);
|
|
167
|
-
}
|
|
168
|
-
|
|
169
|
-
template <typename T>
|
|
170
|
-
inline Quat<T> operator-(const Quat<T>& q, const T a)
|
|
171
|
-
{
|
|
172
|
-
return Quat<T>(q.w - a, q.x, q.y, q.z);
|
|
173
|
-
}
|
|
174
|
-
|
|
175
|
-
template <typename T>
|
|
176
|
-
inline Quat<T> Quat<T>::operator-(const Quat<T> &q1) const
|
|
177
|
-
{
|
|
178
|
-
return Quat<T>(w - q1.w, x - q1.x, y - q1.y, z - q1.z);
|
|
179
|
-
}
|
|
180
|
-
|
|
181
|
-
template <typename T>
|
|
182
|
-
inline Quat<T>& Quat<T>::operator+=(const Quat<T> &q1)
|
|
183
|
-
{
|
|
184
|
-
w += q1.w;
|
|
185
|
-
x += q1.x;
|
|
186
|
-
y += q1.y;
|
|
187
|
-
z += q1.z;
|
|
188
|
-
return *this;
|
|
189
|
-
}
|
|
190
|
-
|
|
191
|
-
template <typename T>
|
|
192
|
-
inline Quat<T>& Quat<T>::operator-=(const Quat<T> &q1)
|
|
193
|
-
{
|
|
194
|
-
w -= q1.w;
|
|
195
|
-
x -= q1.x;
|
|
196
|
-
y -= q1.y;
|
|
197
|
-
z -= q1.z;
|
|
198
|
-
return *this;
|
|
199
|
-
}
|
|
200
|
-
|
|
201
|
-
template <typename T>
|
|
202
|
-
inline Quat<T> Quat<T>::operator*(const Quat<T> &q1) const
|
|
203
|
-
{
|
|
204
|
-
Vec<T, 4> q{w, x, y, z};
|
|
205
|
-
Vec<T, 4> q2{q1.w, q1.x, q1.y, q1.z};
|
|
206
|
-
return Quat<T>(q * q2);
|
|
207
|
-
}
|
|
208
|
-
|
|
209
|
-
|
|
210
|
-
template <typename T>
|
|
211
|
-
Quat<T> operator*(const Quat<T> &q1, const T a)
|
|
212
|
-
{
|
|
213
|
-
return Quat<T>(a * q1.w, a * q1.x, a * q1.y, a * q1.z);
|
|
214
|
-
}
|
|
215
|
-
|
|
216
|
-
template <typename T>
|
|
217
|
-
Quat<T> operator*(const T a, const Quat<T> &q1)
|
|
218
|
-
{
|
|
219
|
-
return Quat<T>(a * q1.w, a * q1.x, a * q1.y, a * q1.z);
|
|
220
|
-
}
|
|
221
|
-
|
|
222
|
-
template <typename T>
|
|
223
|
-
inline Quat<T>& Quat<T>::operator*=(const Quat<T> &q1)
|
|
224
|
-
{
|
|
225
|
-
T qw, qx, qy, qz;
|
|
226
|
-
qw = w * q1.w - x * q1.x - y * q1.y - z * q1.z;
|
|
227
|
-
qx = x * q1.w + w * q1.x + y * q1.z - z * q1.y;
|
|
228
|
-
qy = y * q1.w + w * q1.y + z * q1.x - x * q1.z;
|
|
229
|
-
qz = z * q1.w + w * q1.z + x * q1.y - y * q1.x;
|
|
230
|
-
w = qw;
|
|
231
|
-
x = qx;
|
|
232
|
-
y = qy;
|
|
233
|
-
z = qz;
|
|
234
|
-
return *this;
|
|
235
|
-
}
|
|
236
|
-
|
|
237
|
-
template <typename T>
|
|
238
|
-
inline Quat<T>& Quat<T>::operator/=(const Quat<T> &q1)
|
|
239
|
-
{
|
|
240
|
-
Quat<T> q(*this * q1.inv());
|
|
241
|
-
w = q.w;
|
|
242
|
-
x = q.x;
|
|
243
|
-
y = q.y;
|
|
244
|
-
z = q.z;
|
|
245
|
-
return *this;
|
|
246
|
-
}
|
|
247
|
-
template <typename T>
|
|
248
|
-
Quat<T>& Quat<T>::operator*=(const T q1)
|
|
249
|
-
{
|
|
250
|
-
w *= q1;
|
|
251
|
-
x *= q1;
|
|
252
|
-
y *= q1;
|
|
253
|
-
z *= q1;
|
|
254
|
-
return *this;
|
|
255
|
-
}
|
|
256
|
-
|
|
257
|
-
template <typename T>
|
|
258
|
-
inline Quat<T>& Quat<T>::operator/=(const T a)
|
|
259
|
-
{
|
|
260
|
-
const T a_inv = 1.0 / a;
|
|
261
|
-
w *= a_inv;
|
|
262
|
-
x *= a_inv;
|
|
263
|
-
y *= a_inv;
|
|
264
|
-
z *= a_inv;
|
|
265
|
-
return *this;
|
|
266
|
-
}
|
|
267
|
-
|
|
268
|
-
template <typename T>
|
|
269
|
-
inline Quat<T> Quat<T>::operator/(const T a) const
|
|
270
|
-
{
|
|
271
|
-
const T a_inv = T(1.0) / a;
|
|
272
|
-
return Quat<T>(w * a_inv, x * a_inv, y * a_inv, z * a_inv);
|
|
273
|
-
}
|
|
274
|
-
|
|
275
|
-
template <typename T>
|
|
276
|
-
inline Quat<T> Quat<T>::operator/(const Quat<T> &q) const
|
|
277
|
-
{
|
|
278
|
-
return *this * q.inv();
|
|
279
|
-
}
|
|
280
|
-
|
|
281
|
-
template <typename T>
|
|
282
|
-
inline const T& Quat<T>::operator[](std::size_t n) const
|
|
283
|
-
{
|
|
284
|
-
switch (n) {
|
|
285
|
-
case 0:
|
|
286
|
-
return w;
|
|
287
|
-
case 1:
|
|
288
|
-
return x;
|
|
289
|
-
case 2:
|
|
290
|
-
return y;
|
|
291
|
-
case 3:
|
|
292
|
-
return z;
|
|
293
|
-
default:
|
|
294
|
-
CV_Error(Error::StsOutOfRange, "subscript exceeds the index range");
|
|
295
|
-
}
|
|
296
|
-
}
|
|
297
|
-
|
|
298
|
-
template <typename T>
|
|
299
|
-
inline T& Quat<T>::operator[](std::size_t n)
|
|
300
|
-
{
|
|
301
|
-
switch (n) {
|
|
302
|
-
case 0:
|
|
303
|
-
return w;
|
|
304
|
-
case 1:
|
|
305
|
-
return x;
|
|
306
|
-
case 2:
|
|
307
|
-
return y;
|
|
308
|
-
case 3:
|
|
309
|
-
return z;
|
|
310
|
-
default:
|
|
311
|
-
CV_Error(Error::StsOutOfRange, "subscript exceeds the index range");
|
|
312
|
-
}
|
|
313
|
-
}
|
|
314
|
-
|
|
315
|
-
template <typename T>
|
|
316
|
-
std::ostream & operator<<(std::ostream &os, const Quat<T> &q)
|
|
317
|
-
{
|
|
318
|
-
os << "Quat " << Vec<T, 4>{q.w, q.x, q.y, q.z};
|
|
319
|
-
return os;
|
|
320
|
-
}
|
|
321
|
-
|
|
322
|
-
template <typename T>
|
|
323
|
-
inline T Quat<T>::at(size_t index) const
|
|
324
|
-
{
|
|
325
|
-
return (*this)[index];
|
|
326
|
-
}
|
|
327
|
-
|
|
328
|
-
template <typename T>
|
|
329
|
-
inline Quat<T> Quat<T>::conjugate() const
|
|
330
|
-
{
|
|
331
|
-
return Quat<T>(w, -x, -y, -z);
|
|
332
|
-
}
|
|
333
|
-
|
|
334
|
-
template <typename T>
|
|
335
|
-
inline T Quat<T>::norm() const
|
|
336
|
-
{
|
|
337
|
-
return std::sqrt(dot(*this));
|
|
338
|
-
}
|
|
339
|
-
|
|
340
|
-
template <typename T>
|
|
341
|
-
Quat<T> exp(const Quat<T> &q)
|
|
342
|
-
{
|
|
343
|
-
return q.exp();
|
|
344
|
-
}
|
|
345
|
-
|
|
346
|
-
template <typename T>
|
|
347
|
-
Quat<T> Quat<T>::exp() const
|
|
348
|
-
{
|
|
349
|
-
Vec<T, 3> v{x, y, z};
|
|
350
|
-
T normV = std::sqrt(v.dot(v));
|
|
351
|
-
T k = normV < CV_QUAT_EPS ? 1 : std::sin(normV) / normV;
|
|
352
|
-
return std::exp(w) * Quat<T>(std::cos(normV), v[0] * k, v[1] * k, v[2] * k);
|
|
353
|
-
}
|
|
354
|
-
|
|
355
|
-
template <typename T>
|
|
356
|
-
Quat<T> log(const Quat<T> &q, QuatAssumeType assumeUnit)
|
|
357
|
-
{
|
|
358
|
-
return q.log(assumeUnit);
|
|
359
|
-
}
|
|
360
|
-
|
|
361
|
-
template <typename T>
|
|
362
|
-
Quat<T> Quat<T>::log(QuatAssumeType assumeUnit) const
|
|
363
|
-
{
|
|
364
|
-
Vec<T, 3> v{x, y, z};
|
|
365
|
-
T vNorm = std::sqrt(v.dot(v));
|
|
366
|
-
if (assumeUnit)
|
|
367
|
-
{
|
|
368
|
-
T k = vNorm < CV_QUAT_EPS ? 1 : std::acos(w) / vNorm;
|
|
369
|
-
return Quat<T>(0, v[0] * k, v[1] * k, v[2] * k);
|
|
370
|
-
}
|
|
371
|
-
T qNorm = norm();
|
|
372
|
-
if (qNorm < CV_QUAT_EPS)
|
|
373
|
-
{
|
|
374
|
-
CV_Error(Error::StsBadArg, "Cannot apply this quaternion to log function: undefined");
|
|
375
|
-
}
|
|
376
|
-
T k = vNorm < CV_QUAT_EPS ? 1 : std::acos(w / qNorm) / vNorm;
|
|
377
|
-
return Quat<T>(std::log(qNorm), v[0] * k, v[1] * k, v[2] *k);
|
|
378
|
-
}
|
|
379
|
-
|
|
380
|
-
template <typename T>
|
|
381
|
-
inline Quat<T> power(const Quat<T> &q1, const T alpha, QuatAssumeType assumeUnit)
|
|
382
|
-
{
|
|
383
|
-
return q1.power(alpha, assumeUnit);
|
|
384
|
-
}
|
|
385
|
-
|
|
386
|
-
template <typename T>
|
|
387
|
-
inline Quat<T> Quat<T>::power(const T alpha, QuatAssumeType assumeUnit) const
|
|
388
|
-
{
|
|
389
|
-
if (x * x + y * y + z * z > CV_QUAT_EPS)
|
|
390
|
-
{
|
|
391
|
-
T angle = getAngle(assumeUnit);
|
|
392
|
-
Vec<T, 3> axis = getAxis(assumeUnit);
|
|
393
|
-
if (assumeUnit)
|
|
394
|
-
{
|
|
395
|
-
return createFromAngleAxis(alpha * angle, axis);
|
|
396
|
-
}
|
|
397
|
-
return std::pow(norm(), alpha) * createFromAngleAxis(alpha * angle, axis);
|
|
398
|
-
}
|
|
399
|
-
else
|
|
400
|
-
{
|
|
401
|
-
return std::pow(norm(), alpha) * Quat<T>(w, x, y, z);
|
|
402
|
-
}
|
|
403
|
-
}
|
|
404
|
-
|
|
405
|
-
|
|
406
|
-
template <typename T>
|
|
407
|
-
inline Quat<T> sqrt(const Quat<T> &q, QuatAssumeType assumeUnit)
|
|
408
|
-
{
|
|
409
|
-
return q.sqrt(assumeUnit);
|
|
410
|
-
}
|
|
411
|
-
|
|
412
|
-
template <typename T>
|
|
413
|
-
inline Quat<T> Quat<T>::sqrt(QuatAssumeType assumeUnit) const
|
|
414
|
-
{
|
|
415
|
-
return power(0.5, assumeUnit);
|
|
416
|
-
}
|
|
417
|
-
|
|
418
|
-
|
|
419
|
-
template <typename T>
|
|
420
|
-
inline Quat<T> power(const Quat<T> &p, const Quat<T> &q, QuatAssumeType assumeUnit)
|
|
421
|
-
{
|
|
422
|
-
return p.power(q, assumeUnit);
|
|
423
|
-
}
|
|
424
|
-
|
|
425
|
-
|
|
426
|
-
template <typename T>
|
|
427
|
-
inline Quat<T> Quat<T>::power(const Quat<T> &q, QuatAssumeType assumeUnit) const
|
|
428
|
-
{
|
|
429
|
-
return cv::exp(q * log(assumeUnit));
|
|
430
|
-
}
|
|
431
|
-
|
|
432
|
-
template <typename T>
|
|
433
|
-
inline T Quat<T>::dot(Quat<T> q1) const
|
|
434
|
-
{
|
|
435
|
-
return w * q1.w + x * q1.x + y * q1.y + z * q1.z;
|
|
436
|
-
}
|
|
437
|
-
|
|
438
|
-
|
|
439
|
-
template <typename T>
|
|
440
|
-
inline Quat<T> crossProduct(const Quat<T> &p, const Quat<T> &q)
|
|
441
|
-
{
|
|
442
|
-
return p.crossProduct(q);
|
|
443
|
-
}
|
|
444
|
-
|
|
445
|
-
|
|
446
|
-
template <typename T>
|
|
447
|
-
inline Quat<T> Quat<T>::crossProduct(const Quat<T> &q) const
|
|
448
|
-
{
|
|
449
|
-
return Quat<T> (0, y * q.z - z * q.y, z * q.x - x * q.z, x * q.y - q.x * y);
|
|
450
|
-
}
|
|
451
|
-
|
|
452
|
-
template <typename T>
|
|
453
|
-
inline Quat<T> Quat<T>::normalize() const
|
|
454
|
-
{
|
|
455
|
-
T normVal = norm();
|
|
456
|
-
if (normVal < CV_QUAT_EPS)
|
|
457
|
-
{
|
|
458
|
-
CV_Error(Error::StsBadArg, "Cannot normalize this quaternion: the norm is too small.");
|
|
459
|
-
}
|
|
460
|
-
return Quat<T>(w / normVal, x / normVal, y / normVal, z / normVal) ;
|
|
461
|
-
}
|
|
462
|
-
|
|
463
|
-
template <typename T>
|
|
464
|
-
inline Quat<T> inv(const Quat<T> &q, QuatAssumeType assumeUnit)
|
|
465
|
-
{
|
|
466
|
-
return q.inv(assumeUnit);
|
|
467
|
-
}
|
|
468
|
-
|
|
469
|
-
|
|
470
|
-
template <typename T>
|
|
471
|
-
inline Quat<T> Quat<T>::inv(QuatAssumeType assumeUnit) const
|
|
472
|
-
{
|
|
473
|
-
if (assumeUnit)
|
|
474
|
-
{
|
|
475
|
-
return conjugate();
|
|
476
|
-
}
|
|
477
|
-
T norm2 = dot(*this);
|
|
478
|
-
if (norm2 < CV_QUAT_EPS)
|
|
479
|
-
{
|
|
480
|
-
CV_Error(Error::StsBadArg, "This quaternion do not have inverse quaternion");
|
|
481
|
-
}
|
|
482
|
-
return conjugate() / norm2;
|
|
483
|
-
}
|
|
484
|
-
|
|
485
|
-
template <typename T>
|
|
486
|
-
inline Quat<T> sinh(const Quat<T> &q)
|
|
487
|
-
{
|
|
488
|
-
return q.sinh();
|
|
489
|
-
}
|
|
490
|
-
|
|
491
|
-
|
|
492
|
-
template <typename T>
|
|
493
|
-
inline Quat<T> Quat<T>::sinh() const
|
|
494
|
-
{
|
|
495
|
-
Vec<T, 3> v{x, y ,z};
|
|
496
|
-
T vNorm = std::sqrt(v.dot(v));
|
|
497
|
-
T k = vNorm < CV_QUAT_EPS ? 1 : std::cosh(w) * std::sin(vNorm) / vNorm;
|
|
498
|
-
return Quat<T>(std::sinh(w) * std::cos(vNorm), v[0] * k, v[1] * k, v[2] * k);
|
|
499
|
-
}
|
|
500
|
-
|
|
501
|
-
|
|
502
|
-
template <typename T>
|
|
503
|
-
inline Quat<T> cosh(const Quat<T> &q)
|
|
504
|
-
{
|
|
505
|
-
return q.cosh();
|
|
506
|
-
}
|
|
507
|
-
|
|
508
|
-
|
|
509
|
-
template <typename T>
|
|
510
|
-
inline Quat<T> Quat<T>::cosh() const
|
|
511
|
-
{
|
|
512
|
-
Vec<T, 3> v{x, y ,z};
|
|
513
|
-
T vNorm = std::sqrt(v.dot(v));
|
|
514
|
-
T k = vNorm < CV_QUAT_EPS ? 1 : std::sinh(w) * std::sin(vNorm) / vNorm;
|
|
515
|
-
return Quat<T>(std::cosh(w) * std::cos(vNorm), v[0] * k, v[1] * k, v[2] * k);
|
|
516
|
-
}
|
|
517
|
-
|
|
518
|
-
template <typename T>
|
|
519
|
-
inline Quat<T> tanh(const Quat<T> &q)
|
|
520
|
-
{
|
|
521
|
-
return q.tanh();
|
|
522
|
-
}
|
|
523
|
-
|
|
524
|
-
template <typename T>
|
|
525
|
-
inline Quat<T> Quat<T>::tanh() const
|
|
526
|
-
{
|
|
527
|
-
return sinh() * cosh().inv();
|
|
528
|
-
}
|
|
529
|
-
|
|
530
|
-
|
|
531
|
-
template <typename T>
|
|
532
|
-
inline Quat<T> sin(const Quat<T> &q)
|
|
533
|
-
{
|
|
534
|
-
return q.sin();
|
|
535
|
-
}
|
|
536
|
-
|
|
537
|
-
|
|
538
|
-
template <typename T>
|
|
539
|
-
inline Quat<T> Quat<T>::sin() const
|
|
540
|
-
{
|
|
541
|
-
Vec<T, 3> v{x, y ,z};
|
|
542
|
-
T vNorm = std::sqrt(v.dot(v));
|
|
543
|
-
T k = vNorm < CV_QUAT_EPS ? 1 : std::cos(w) * std::sinh(vNorm) / vNorm;
|
|
544
|
-
return Quat<T>(std::sin(w) * std::cosh(vNorm), v[0] * k, v[1] * k, v[2] * k);
|
|
545
|
-
}
|
|
546
|
-
|
|
547
|
-
template <typename T>
|
|
548
|
-
inline Quat<T> cos(const Quat<T> &q)
|
|
549
|
-
{
|
|
550
|
-
return q.cos();
|
|
551
|
-
}
|
|
552
|
-
|
|
553
|
-
template <typename T>
|
|
554
|
-
inline Quat<T> Quat<T>::cos() const
|
|
555
|
-
{
|
|
556
|
-
Vec<T, 3> v{x, y ,z};
|
|
557
|
-
T vNorm = std::sqrt(v.dot(v));
|
|
558
|
-
T k = vNorm < CV_QUAT_EPS ? 1 : std::sin(w) * std::sinh(vNorm) / vNorm;
|
|
559
|
-
return Quat<T>(std::cos(w) * std::cosh(vNorm), -v[0] * k, -v[1] * k, -v[2] * k);
|
|
560
|
-
}
|
|
561
|
-
|
|
562
|
-
template <typename T>
|
|
563
|
-
inline Quat<T> tan(const Quat<T> &q)
|
|
564
|
-
{
|
|
565
|
-
return q.tan();
|
|
566
|
-
}
|
|
567
|
-
|
|
568
|
-
template <typename T>
|
|
569
|
-
inline Quat<T> Quat<T>::tan() const
|
|
570
|
-
{
|
|
571
|
-
return sin() * cos().inv();
|
|
572
|
-
}
|
|
573
|
-
|
|
574
|
-
template <typename T>
|
|
575
|
-
inline Quat<T> asinh(const Quat<T> &q)
|
|
576
|
-
{
|
|
577
|
-
return q.asinh();
|
|
578
|
-
}
|
|
579
|
-
|
|
580
|
-
template <typename T>
|
|
581
|
-
inline Quat<T> Quat<T>::asinh() const
|
|
582
|
-
{
|
|
583
|
-
return cv::log(*this + cv::power(*this * *this + Quat<T>(1, 0, 0, 0), 0.5));
|
|
584
|
-
}
|
|
585
|
-
|
|
586
|
-
template <typename T>
|
|
587
|
-
inline Quat<T> acosh(const Quat<T> &q)
|
|
588
|
-
{
|
|
589
|
-
return q.acosh();
|
|
590
|
-
}
|
|
591
|
-
|
|
592
|
-
template <typename T>
|
|
593
|
-
inline Quat<T> Quat<T>::acosh() const
|
|
594
|
-
{
|
|
595
|
-
return cv::log(*this + cv::power(*this * *this - Quat<T>(1,0,0,0), 0.5));
|
|
596
|
-
}
|
|
597
|
-
|
|
598
|
-
template <typename T>
|
|
599
|
-
inline Quat<T> atanh(const Quat<T> &q)
|
|
600
|
-
{
|
|
601
|
-
return q.atanh();
|
|
602
|
-
}
|
|
603
|
-
|
|
604
|
-
template <typename T>
|
|
605
|
-
inline Quat<T> Quat<T>::atanh() const
|
|
606
|
-
{
|
|
607
|
-
Quat<T> ident(1, 0, 0, 0);
|
|
608
|
-
Quat<T> c1 = (ident + *this).log();
|
|
609
|
-
Quat<T> c2 = (ident - *this).log();
|
|
610
|
-
return 0.5 * (c1 - c2);
|
|
611
|
-
}
|
|
612
|
-
|
|
613
|
-
template <typename T>
|
|
614
|
-
inline Quat<T> asin(const Quat<T> &q)
|
|
615
|
-
{
|
|
616
|
-
return q.asin();
|
|
617
|
-
}
|
|
618
|
-
|
|
619
|
-
template <typename T>
|
|
620
|
-
inline Quat<T> Quat<T>::asin() const
|
|
621
|
-
{
|
|
622
|
-
Quat<T> v(0, x, y, z);
|
|
623
|
-
T vNorm = v.norm();
|
|
624
|
-
T k = vNorm < CV_QUAT_EPS ? 1 : vNorm;
|
|
625
|
-
return -v / k * (*this * v / k).asinh();
|
|
626
|
-
}
|
|
627
|
-
|
|
628
|
-
template <typename T>
|
|
629
|
-
inline Quat<T> acos(const Quat<T> &q)
|
|
630
|
-
{
|
|
631
|
-
return q.acos();
|
|
632
|
-
}
|
|
633
|
-
|
|
634
|
-
template <typename T>
|
|
635
|
-
inline Quat<T> Quat<T>::acos() const
|
|
636
|
-
{
|
|
637
|
-
Quat<T> v(0, x, y, z);
|
|
638
|
-
T vNorm = v.norm();
|
|
639
|
-
T k = vNorm < CV_QUAT_EPS ? 1 : vNorm;
|
|
640
|
-
return -v / k * acosh();
|
|
641
|
-
}
|
|
642
|
-
|
|
643
|
-
template <typename T>
|
|
644
|
-
inline Quat<T> atan(const Quat<T> &q)
|
|
645
|
-
{
|
|
646
|
-
return q.atan();
|
|
647
|
-
}
|
|
648
|
-
|
|
649
|
-
template <typename T>
|
|
650
|
-
inline Quat<T> Quat<T>::atan() const
|
|
651
|
-
{
|
|
652
|
-
Quat<T> v(0, x, y, z);
|
|
653
|
-
T vNorm = v.norm();
|
|
654
|
-
T k = vNorm < CV_QUAT_EPS ? 1 : vNorm;
|
|
655
|
-
return -v / k * (*this * v / k).atanh();
|
|
656
|
-
}
|
|
657
|
-
|
|
658
|
-
template <typename T>
|
|
659
|
-
inline T Quat<T>::getAngle(QuatAssumeType assumeUnit) const
|
|
660
|
-
{
|
|
661
|
-
if (assumeUnit)
|
|
662
|
-
{
|
|
663
|
-
return 2 * std::acos(w);
|
|
664
|
-
}
|
|
665
|
-
if (norm() < CV_QUAT_EPS)
|
|
666
|
-
{
|
|
667
|
-
CV_Error(Error::StsBadArg, "This quaternion does not represent a rotation");
|
|
668
|
-
}
|
|
669
|
-
return 2 * std::acos(w / norm());
|
|
670
|
-
}
|
|
671
|
-
|
|
672
|
-
template <typename T>
|
|
673
|
-
inline Vec<T, 3> Quat<T>::getAxis(QuatAssumeType assumeUnit) const
|
|
674
|
-
{
|
|
675
|
-
T angle = getAngle(assumeUnit);
|
|
676
|
-
const T sin_v = std::sin(angle * 0.5);
|
|
677
|
-
if (assumeUnit)
|
|
678
|
-
{
|
|
679
|
-
return Vec<T, 3>{x, y, z} / sin_v;
|
|
680
|
-
}
|
|
681
|
-
return Vec<T, 3> {x, y, z} / (norm() * sin_v);
|
|
682
|
-
}
|
|
683
|
-
|
|
684
|
-
template <typename T>
|
|
685
|
-
Matx<T, 4, 4> Quat<T>::toRotMat4x4(QuatAssumeType assumeUnit) const
|
|
686
|
-
{
|
|
687
|
-
T a = w, b = x, c = y, d = z;
|
|
688
|
-
if (!assumeUnit)
|
|
689
|
-
{
|
|
690
|
-
Quat<T> qTemp = normalize();
|
|
691
|
-
a = qTemp.w;
|
|
692
|
-
b = qTemp.x;
|
|
693
|
-
c = qTemp.y;
|
|
694
|
-
d = qTemp.z;
|
|
695
|
-
}
|
|
696
|
-
Matx<T, 4, 4> R{
|
|
697
|
-
1 - 2 * (c * c + d * d), 2 * (b * c - a * d) , 2 * (b * d + a * c) , 0,
|
|
698
|
-
2 * (b * c + a * d) , 1 - 2 * (b * b + d * d), 2 * (c * d - a * b) , 0,
|
|
699
|
-
2 * (b * d - a * c) , 2 * (c * d + a * b) , 1 - 2 * (b * b + c * c), 0,
|
|
700
|
-
0 , 0 , 0 , 1,
|
|
701
|
-
};
|
|
702
|
-
return R;
|
|
703
|
-
}
|
|
704
|
-
|
|
705
|
-
template <typename T>
|
|
706
|
-
Matx<T, 3, 3> Quat<T>::toRotMat3x3(QuatAssumeType assumeUnit) const
|
|
707
|
-
{
|
|
708
|
-
T a = w, b = x, c = y, d = z;
|
|
709
|
-
if (!assumeUnit)
|
|
710
|
-
{
|
|
711
|
-
Quat<T> qTemp = normalize();
|
|
712
|
-
a = qTemp.w;
|
|
713
|
-
b = qTemp.x;
|
|
714
|
-
c = qTemp.y;
|
|
715
|
-
d = qTemp.z;
|
|
716
|
-
}
|
|
717
|
-
Matx<T, 3, 3> R{
|
|
718
|
-
1 - 2 * (c * c + d * d), 2 * (b * c - a * d) , 2 * (b * d + a * c),
|
|
719
|
-
2 * (b * c + a * d) , 1 - 2 * (b * b + d * d), 2 * (c * d - a * b),
|
|
720
|
-
2 * (b * d - a * c) , 2 * (c * d + a * b) , 1 - 2 * (b * b + c * c)
|
|
721
|
-
};
|
|
722
|
-
return R;
|
|
723
|
-
}
|
|
724
|
-
|
|
725
|
-
template <typename T>
|
|
726
|
-
Vec<T, 3> Quat<T>::toRotVec(QuatAssumeType assumeUnit) const
|
|
727
|
-
{
|
|
728
|
-
T angle = getAngle(assumeUnit);
|
|
729
|
-
Vec<T, 3> axis = getAxis(assumeUnit);
|
|
730
|
-
return angle * axis;
|
|
731
|
-
}
|
|
732
|
-
|
|
733
|
-
template <typename T>
|
|
734
|
-
Vec<T, 4> Quat<T>::toVec() const
|
|
735
|
-
{
|
|
736
|
-
return Vec<T, 4>{w, x, y, z};
|
|
737
|
-
}
|
|
738
|
-
|
|
739
|
-
template <typename T>
|
|
740
|
-
Quat<T> Quat<T>::lerp(const Quat<T> &q0, const Quat<T> &q1, const T t)
|
|
741
|
-
{
|
|
742
|
-
return (1 - t) * q0 + t * q1;
|
|
743
|
-
}
|
|
744
|
-
|
|
745
|
-
template <typename T>
|
|
746
|
-
Quat<T> Quat<T>::slerp(const Quat<T> &q0, const Quat<T> &q1, const T t, QuatAssumeType assumeUnit, bool directChange)
|
|
747
|
-
{
|
|
748
|
-
Quatd v0(q0);
|
|
749
|
-
Quatd v1(q1);
|
|
750
|
-
if (!assumeUnit)
|
|
751
|
-
{
|
|
752
|
-
v0 = v0.normalize();
|
|
753
|
-
v1 = v1.normalize();
|
|
754
|
-
}
|
|
755
|
-
T cosTheta = v0.dot(v1);
|
|
756
|
-
constexpr T DOT_THRESHOLD = 0.995;
|
|
757
|
-
if (cosTheta > DOT_THRESHOLD)
|
|
758
|
-
{
|
|
759
|
-
return nlerp(v0, v1, t, QUAT_ASSUME_UNIT);
|
|
760
|
-
}
|
|
761
|
-
|
|
762
|
-
if (directChange && cosTheta < 0)
|
|
763
|
-
{
|
|
764
|
-
v0 = -v0;
|
|
765
|
-
cosTheta = -cosTheta;
|
|
766
|
-
}
|
|
767
|
-
T sinTheta = std::sqrt(1 - cosTheta * cosTheta);
|
|
768
|
-
T angle = atan2(sinTheta, cosTheta);
|
|
769
|
-
return (std::sin((1 - t) * angle) / (sinTheta) * v0 + std::sin(t * angle) / (sinTheta) * v1).normalize();
|
|
770
|
-
}
|
|
771
|
-
|
|
772
|
-
|
|
773
|
-
template <typename T>
|
|
774
|
-
inline Quat<T> Quat<T>::nlerp(const Quat<T> &q0, const Quat<T> &q1, const T t, QuatAssumeType assumeUnit)
|
|
775
|
-
{
|
|
776
|
-
Quat<T> v0(q0), v1(q1);
|
|
777
|
-
if (v1.dot(v0) < 0)
|
|
778
|
-
{
|
|
779
|
-
v0 = -v0;
|
|
780
|
-
}
|
|
781
|
-
if (assumeUnit)
|
|
782
|
-
{
|
|
783
|
-
return ((1 - t) * v0 + t * v1).normalize();
|
|
784
|
-
}
|
|
785
|
-
v0 = v0.normalize();
|
|
786
|
-
v1 = v1.normalize();
|
|
787
|
-
return ((1 - t) * v0 + t * v1).normalize();
|
|
788
|
-
}
|
|
789
|
-
|
|
790
|
-
|
|
791
|
-
template <typename T>
|
|
792
|
-
inline bool Quat<T>::isNormal(T eps) const
|
|
793
|
-
{
|
|
794
|
-
|
|
795
|
-
double normVar = norm();
|
|
796
|
-
if ((normVar > 1 - eps) && (normVar < 1 + eps))
|
|
797
|
-
return true;
|
|
798
|
-
return false;
|
|
799
|
-
}
|
|
800
|
-
|
|
801
|
-
template <typename T>
|
|
802
|
-
inline void Quat<T>::assertNormal(T eps) const
|
|
803
|
-
{
|
|
804
|
-
if (!isNormal(eps))
|
|
805
|
-
CV_Error(Error::StsBadArg, "Quaternion should be normalized");
|
|
806
|
-
}
|
|
807
|
-
|
|
808
|
-
|
|
809
|
-
template <typename T>
|
|
810
|
-
inline Quat<T> Quat<T>::squad(const Quat<T> &q0, const Quat<T> &q1,
|
|
811
|
-
const Quat<T> &q2, const Quat<T> &q3,
|
|
812
|
-
const T t, QuatAssumeType assumeUnit,
|
|
813
|
-
bool directChange)
|
|
814
|
-
{
|
|
815
|
-
Quat<T> v0(q0), v1(q1), v2(q2), v3(q3);
|
|
816
|
-
if (!assumeUnit)
|
|
817
|
-
{
|
|
818
|
-
v0 = v0.normalize();
|
|
819
|
-
v1 = v1.normalize();
|
|
820
|
-
v2 = v2.normalize();
|
|
821
|
-
v3 = v3.normalize();
|
|
822
|
-
}
|
|
823
|
-
|
|
824
|
-
Quat<T> c0 = slerp(v0, v3, t, assumeUnit, directChange);
|
|
825
|
-
Quat<T> c1 = slerp(v1, v2, t, assumeUnit, directChange);
|
|
826
|
-
return slerp(c0, c1, 2 * t * (1 - t), assumeUnit, directChange);
|
|
827
|
-
}
|
|
828
|
-
|
|
829
|
-
template <typename T>
|
|
830
|
-
Quat<T> Quat<T>::interPoint(const Quat<T> &q0, const Quat<T> &q1,
|
|
831
|
-
const Quat<T> &q2, QuatAssumeType assumeUnit)
|
|
832
|
-
{
|
|
833
|
-
Quat<T> v0(q0), v1(q1), v2(q2);
|
|
834
|
-
if (!assumeUnit)
|
|
835
|
-
{
|
|
836
|
-
v0 = v0.normalize();
|
|
837
|
-
v1 = v1.normalize();
|
|
838
|
-
v2 = v2.normalize();
|
|
839
|
-
}
|
|
840
|
-
return v1 * cv::exp(-(cv::log(v1.conjugate() * v0, assumeUnit) + (cv::log(v1.conjugate() * v2, assumeUnit))) / 4);
|
|
841
|
-
}
|
|
842
|
-
|
|
843
|
-
template <typename T>
|
|
844
|
-
Quat<T> Quat<T>::spline(const Quat<T> &q0, const Quat<T> &q1, const Quat<T> &q2, const Quat<T> &q3, const T t, QuatAssumeType assumeUnit)
|
|
845
|
-
{
|
|
846
|
-
Quatd v0(q0), v1(q1), v2(q2), v3(q3);
|
|
847
|
-
if (!assumeUnit)
|
|
848
|
-
{
|
|
849
|
-
v0 = v0.normalize();
|
|
850
|
-
v1 = v1.normalize();
|
|
851
|
-
v2 = v2.normalize();
|
|
852
|
-
v3 = v3.normalize();
|
|
853
|
-
}
|
|
854
|
-
T cosTheta;
|
|
855
|
-
std::vector<Quat<T>> vec{v0, v1, v2, v3};
|
|
856
|
-
for (size_t i = 0; i < 3; ++i)
|
|
857
|
-
{
|
|
858
|
-
cosTheta = vec[i].dot(vec[i + 1]);
|
|
859
|
-
if (cosTheta < 0)
|
|
860
|
-
{
|
|
861
|
-
vec[i + 1] = -vec[i + 1];
|
|
862
|
-
}
|
|
863
|
-
}
|
|
864
|
-
Quat<T> s1 = interPoint(vec[0], vec[1], vec[2], QUAT_ASSUME_UNIT);
|
|
865
|
-
Quat<T> s2 = interPoint(vec[1], vec[2], vec[3], QUAT_ASSUME_UNIT);
|
|
866
|
-
return squad(vec[1], s1, s2, vec[2], t, assumeUnit, QUAT_ASSUME_NOT_UNIT);
|
|
867
|
-
}
|
|
868
|
-
|
|
869
|
-
namespace detail {
|
|
870
|
-
|
|
871
|
-
template <typename T> static
|
|
872
|
-
Quat<T> createFromAxisRot(int axis, const T theta)
|
|
873
|
-
{
|
|
874
|
-
if (axis == 0)
|
|
875
|
-
return Quat<T>::createFromXRot(theta);
|
|
876
|
-
if (axis == 1)
|
|
877
|
-
return Quat<T>::createFromYRot(theta);
|
|
878
|
-
if (axis == 2)
|
|
879
|
-
return Quat<T>::createFromZRot(theta);
|
|
880
|
-
CV_Assert(0);
|
|
881
|
-
}
|
|
882
|
-
|
|
883
|
-
inline bool isIntAngleType(QuatEnum::EulerAnglesType eulerAnglesType)
|
|
884
|
-
{
|
|
885
|
-
return eulerAnglesType < QuatEnum::EXT_XYZ;
|
|
886
|
-
}
|
|
887
|
-
|
|
888
|
-
inline bool isTaitBryan(QuatEnum::EulerAnglesType eulerAnglesType)
|
|
889
|
-
{
|
|
890
|
-
return eulerAnglesType/6 == 1 || eulerAnglesType/6 == 3;
|
|
891
|
-
}
|
|
892
|
-
} // namespace detail
|
|
893
|
-
|
|
894
|
-
template <typename T>
|
|
895
|
-
Quat<T> Quat<T>::createFromYRot(const T theta)
|
|
896
|
-
{
|
|
897
|
-
return Quat<T>{std::cos(theta * 0.5f), 0, std::sin(theta * 0.5f), 0};
|
|
898
|
-
}
|
|
899
|
-
|
|
900
|
-
template <typename T>
|
|
901
|
-
Quat<T> Quat<T>::createFromXRot(const T theta){
|
|
902
|
-
return Quat<T>{std::cos(theta * 0.5f), std::sin(theta * 0.5f), 0, 0};
|
|
903
|
-
}
|
|
904
|
-
|
|
905
|
-
template <typename T>
|
|
906
|
-
Quat<T> Quat<T>::createFromZRot(const T theta){
|
|
907
|
-
return Quat<T>{std::cos(theta * 0.5f), 0, 0, std::sin(theta * 0.5f)};
|
|
908
|
-
}
|
|
909
|
-
|
|
910
|
-
|
|
911
|
-
template <typename T>
|
|
912
|
-
Quat<T> Quat<T>::createFromEulerAngles(const Vec<T, 3> &angles, QuatEnum::EulerAnglesType eulerAnglesType) {
|
|
913
|
-
CV_Assert(eulerAnglesType < QuatEnum::EulerAnglesType::EULER_ANGLES_MAX_VALUE);
|
|
914
|
-
static const int rotationAxis[24][3] = {
|
|
915
|
-
{0, 1, 2}, ///< Intrinsic rotations with the Euler angles type X-Y-Z
|
|
916
|
-
{0, 2, 1}, ///< Intrinsic rotations with the Euler angles type X-Z-Y
|
|
917
|
-
{1, 0, 2}, ///< Intrinsic rotations with the Euler angles type Y-X-Z
|
|
918
|
-
{1, 2, 0}, ///< Intrinsic rotations with the Euler angles type Y-Z-X
|
|
919
|
-
{2, 0, 1}, ///< Intrinsic rotations with the Euler angles type Z-X-Y
|
|
920
|
-
{2, 1, 0}, ///< Intrinsic rotations with the Euler angles type Z-Y-X
|
|
921
|
-
{0, 1, 0}, ///< Intrinsic rotations with the Euler angles type X-Y-X
|
|
922
|
-
{0, 2, 0}, ///< Intrinsic rotations with the Euler angles type X-Z-X
|
|
923
|
-
{1, 0, 1}, ///< Intrinsic rotations with the Euler angles type Y-X-Y
|
|
924
|
-
{1, 2, 1}, ///< Intrinsic rotations with the Euler angles type Y-Z-Y
|
|
925
|
-
{2, 0, 2}, ///< Intrinsic rotations with the Euler angles type Z-X-Z
|
|
926
|
-
{2, 1, 2}, ///< Intrinsic rotations with the Euler angles type Z-Y-Z
|
|
927
|
-
{0, 1, 2}, ///< Extrinsic rotations with the Euler angles type X-Y-Z
|
|
928
|
-
{0, 2, 1}, ///< Extrinsic rotations with the Euler angles type X-Z-Y
|
|
929
|
-
{1, 0, 2}, ///< Extrinsic rotations with the Euler angles type Y-X-Z
|
|
930
|
-
{1, 2, 0}, ///< Extrinsic rotations with the Euler angles type Y-Z-X
|
|
931
|
-
{2, 0, 1}, ///< Extrinsic rotations with the Euler angles type Z-X-Y
|
|
932
|
-
{2, 1, 0}, ///< Extrinsic rotations with the Euler angles type Z-Y-X
|
|
933
|
-
{0, 1, 0}, ///< Extrinsic rotations with the Euler angles type X-Y-X
|
|
934
|
-
{0, 2, 0}, ///< Extrinsic rotations with the Euler angles type X-Z-X
|
|
935
|
-
{1, 0, 1}, ///< Extrinsic rotations with the Euler angles type Y-X-Y
|
|
936
|
-
{1, 2, 1}, ///< Extrinsic rotations with the Euler angles type Y-Z-Y
|
|
937
|
-
{2, 0, 2}, ///< Extrinsic rotations with the Euler angles type Z-X-Z
|
|
938
|
-
{2, 1, 2} ///< Extrinsic rotations with the Euler angles type Z-Y-Z
|
|
939
|
-
};
|
|
940
|
-
Quat<T> q1 = detail::createFromAxisRot(rotationAxis[eulerAnglesType][0], angles(0));
|
|
941
|
-
Quat<T> q2 = detail::createFromAxisRot(rotationAxis[eulerAnglesType][1], angles(1));
|
|
942
|
-
Quat<T> q3 = detail::createFromAxisRot(rotationAxis[eulerAnglesType][2], angles(2));
|
|
943
|
-
if (detail::isIntAngleType(eulerAnglesType))
|
|
944
|
-
{
|
|
945
|
-
return q1 * q2 * q3;
|
|
946
|
-
}
|
|
947
|
-
else // (!detail::isIntAngleType<T>(eulerAnglesType))
|
|
948
|
-
{
|
|
949
|
-
return q3 * q2 * q1;
|
|
950
|
-
}
|
|
951
|
-
}
|
|
952
|
-
|
|
953
|
-
template <typename T>
|
|
954
|
-
Vec<T, 3> Quat<T>::toEulerAngles(QuatEnum::EulerAnglesType eulerAnglesType){
|
|
955
|
-
CV_Assert(eulerAnglesType < QuatEnum::EulerAnglesType::EULER_ANGLES_MAX_VALUE);
|
|
956
|
-
Matx33d R = toRotMat3x3();
|
|
957
|
-
enum {
|
|
958
|
-
C_ZERO,
|
|
959
|
-
C_PI,
|
|
960
|
-
C_PI_2,
|
|
961
|
-
N_CONSTANTS,
|
|
962
|
-
R_0_0 = N_CONSTANTS, R_0_1, R_0_2,
|
|
963
|
-
R_1_0, R_1_1, R_1_2,
|
|
964
|
-
R_2_0, R_2_1, R_2_2
|
|
965
|
-
};
|
|
966
|
-
static const T constants_[N_CONSTANTS] = {
|
|
967
|
-
0, // C_ZERO
|
|
968
|
-
(T)CV_PI, // C_PI
|
|
969
|
-
(T)(CV_PI * 0.5) // C_PI_2, -C_PI_2
|
|
970
|
-
};
|
|
971
|
-
static const int rotationR_[24][12] = {
|
|
972
|
-
{+R_0_2, +R_1_0, +R_1_1, C_PI_2, +R_2_1, +R_1_1, -C_PI_2, -R_1_2, +R_2_2, +R_0_2, -R_0_1, +R_0_0}, // INT_XYZ
|
|
973
|
-
{+R_0_1, -R_1_2, +R_2_2, -C_PI_2, +R_2_0, +R_2_2, C_PI_2, +R_2_1, +R_1_1, -R_0_1, +R_0_2, +R_0_0}, // INT_XZY
|
|
974
|
-
{+R_1_2, -R_0_1, +R_0_0, -C_PI_2, +R_0_1, +R_0_0, C_PI_2, +R_0_2, +R_2_2, -R_1_2, +R_1_0, +R_1_1}, // INT_YXZ
|
|
975
|
-
{+R_1_0, +R_0_2, +R_2_2, C_PI_2, +R_0_2, +R_0_1, -C_PI_2, -R_2_0, +R_0_0, +R_1_0, -R_1_2, +R_1_1}, // INT_YZX
|
|
976
|
-
{+R_2_1, +R_1_0, +R_0_0, C_PI_2, +R_1_0, +R_0_0, -C_PI_2, -R_0_1, +R_1_1, +R_2_1, -R_2_0, +R_2_2}, // INT_ZXY
|
|
977
|
-
{+R_2_0, -R_0_1, +R_1_1, -C_PI_2, +R_1_2, +R_1_1, C_PI_2, +R_1_0, +R_0_0, -R_2_0, +R_2_1, +R_2_2}, // INT_ZYX
|
|
978
|
-
{+R_0_0, +R_2_1, +R_2_2, C_ZERO, +R_1_2, +R_1_1, C_PI, +R_1_0, -R_2_0, +R_0_0, +R_0_1, +R_0_2}, // INT_XYX
|
|
979
|
-
{+R_0_0, +R_2_1, +R_2_2, C_ZERO, -R_2_1, +R_2_2, C_PI, +R_2_0, +R_1_0, +R_0_0, +R_0_2, -R_0_1}, // INT_XZX
|
|
980
|
-
{+R_1_1, +R_0_2, +R_0_0, C_ZERO, -R_2_0, +R_0_0, C_PI, +R_0_1, +R_2_1, +R_1_1, +R_1_0, -R_1_2}, // INT_YXY
|
|
981
|
-
{+R_1_1, +R_0_2, +R_0_0, C_ZERO, +R_0_2, -R_0_0, C_PI, +R_2_1, -R_0_1, +R_1_1, +R_1_2, +R_1_0}, // INT_YZY
|
|
982
|
-
{+R_2_2, +R_1_0, +R_1_1, C_ZERO, +R_1_0, +R_0_0, C_PI, +R_0_2, -R_1_2, +R_2_2, +R_2_0, +R_2_1}, // INT_ZXZ
|
|
983
|
-
{+R_2_2, +R_1_0, +R_0_0, C_ZERO, +R_1_0, +R_0_0, C_PI, +R_1_2, +R_0_2, +R_2_2, +R_2_1, -R_2_0}, // INT_ZYZ
|
|
984
|
-
|
|
985
|
-
{+R_2_0, -C_PI_2, -R_0_1, +R_1_1, C_PI_2, +R_1_2, +R_1_1, +R_2_1, +R_2_2, -R_2_0, +R_1_0, +R_0_0}, // EXT_XYZ
|
|
986
|
-
{+R_1_0, C_PI_2, +R_0_2, +R_2_2, -C_PI_2, +R_0_2, +R_0_1, -R_1_2, +R_1_1, +R_1_0, -R_2_0, +R_0_0}, // EXT_XZY
|
|
987
|
-
{+R_2_1, C_PI_2, +R_1_0, +R_0_0, -C_PI_2, +R_1_0, +R_0_0, -R_2_0, +R_2_2, +R_2_1, -R_0_1, +R_1_1}, // EXT_YXZ
|
|
988
|
-
{+R_0_2, -C_PI_2, -R_1_2, +R_2_2, C_PI_2, +R_2_0, +R_2_2, +R_0_2, +R_0_0, -R_0_1, +R_2_1, +R_1_1}, // EXT_YZX
|
|
989
|
-
{+R_1_2, -C_PI_2, -R_0_1, +R_0_0, C_PI_2, +R_0_1, +R_0_0, +R_1_0, +R_1_1, -R_1_2, +R_0_2, +R_2_2}, // EXT_ZXY
|
|
990
|
-
{+R_0_2, C_PI_2, +R_1_0, +R_1_1, -C_PI_2, +R_2_1, +R_1_1, -R_0_1, +R_0_0, +R_0_2, -R_1_2, +R_2_2}, // EXT_ZYX
|
|
991
|
-
{+R_0_0, C_ZERO, +R_2_1, +R_2_2, C_PI, +R_1_2, +R_1_1, +R_0_1, +R_0_2, +R_0_0, +R_1_0, -R_2_0}, // EXT_XYX
|
|
992
|
-
{+R_0_0, C_ZERO, +R_2_1, +R_2_2, C_PI, +R_2_1, +R_2_2, +R_0_2, -R_0_1, +R_0_0, +R_2_0, +R_1_0}, // EXT_XZX
|
|
993
|
-
{+R_1_1, C_ZERO, +R_0_2, +R_0_0, C_PI, -R_2_0, +R_0_0, +R_1_0, -R_1_2, +R_1_1, +R_0_1, +R_2_1}, // EXT_YXY
|
|
994
|
-
{+R_1_1, C_ZERO, +R_0_2, +R_0_0, C_PI, +R_0_2, -R_0_0, +R_1_2, +R_1_0, +R_1_1, +R_2_1, -R_0_1}, // EXT_YZY
|
|
995
|
-
{+R_2_2, C_ZERO, +R_1_0, +R_1_1, C_PI, +R_1_0, +R_0_0, +R_2_0, +R_2_1, +R_2_2, +R_0_2, -R_1_2}, // EXT_ZXZ
|
|
996
|
-
{+R_2_2, C_ZERO, +R_1_0, +R_0_0, C_PI, +R_1_0, +R_0_0, +R_2_1, -R_2_0, +R_2_2, +R_1_2, +R_0_2}, // EXT_ZYZ
|
|
997
|
-
};
|
|
998
|
-
T rotationR[12];
|
|
999
|
-
for (int i = 0; i < 12; i++)
|
|
1000
|
-
{
|
|
1001
|
-
int id = rotationR_[eulerAnglesType][i];
|
|
1002
|
-
unsigned idx = std::abs(id);
|
|
1003
|
-
T value = 0.0f;
|
|
1004
|
-
if (idx < N_CONSTANTS)
|
|
1005
|
-
{
|
|
1006
|
-
value = constants_[idx];
|
|
1007
|
-
}
|
|
1008
|
-
else
|
|
1009
|
-
{
|
|
1010
|
-
unsigned r_idx = idx - N_CONSTANTS;
|
|
1011
|
-
CV_DbgAssert(r_idx < 9);
|
|
1012
|
-
value = R.val[r_idx];
|
|
1013
|
-
}
|
|
1014
|
-
bool isNegative = id < 0;
|
|
1015
|
-
if (isNegative)
|
|
1016
|
-
value = -value;
|
|
1017
|
-
rotationR[i] = value;
|
|
1018
|
-
}
|
|
1019
|
-
Vec<T, 3> angles;
|
|
1020
|
-
if (detail::isIntAngleType(eulerAnglesType))
|
|
1021
|
-
{
|
|
1022
|
-
if (abs(rotationR[0] - 1) < CV_QUAT_CONVERT_THRESHOLD)
|
|
1023
|
-
{
|
|
1024
|
-
CV_LOG_WARNING(NULL,"Gimbal Lock occurs. Euler angles are non-unique, we set the third angle to 0");
|
|
1025
|
-
angles = {std::atan2(rotationR[1], rotationR[2]), rotationR[3], 0};
|
|
1026
|
-
return angles;
|
|
1027
|
-
}
|
|
1028
|
-
else if(abs(rotationR[0] + 1) < CV_QUAT_CONVERT_THRESHOLD)
|
|
1029
|
-
{
|
|
1030
|
-
CV_LOG_WARNING(NULL,"Gimbal Lock occurs. Euler angles are non-unique, we set the third angle to 0");
|
|
1031
|
-
angles = {std::atan2(rotationR[4], rotationR[5]), rotationR[6], 0};
|
|
1032
|
-
return angles;
|
|
1033
|
-
}
|
|
1034
|
-
}
|
|
1035
|
-
else // (!detail::isIntAngleType<T>(eulerAnglesType))
|
|
1036
|
-
{
|
|
1037
|
-
if (abs(rotationR[0] - 1) < CV_QUAT_CONVERT_THRESHOLD)
|
|
1038
|
-
{
|
|
1039
|
-
CV_LOG_WARNING(NULL,"Gimbal Lock occurs. Euler angles are non-unique, we set the first angle to 0");
|
|
1040
|
-
angles = {0, rotationR[1], std::atan2(rotationR[2], rotationR[3])};
|
|
1041
|
-
return angles;
|
|
1042
|
-
}
|
|
1043
|
-
else if (abs(rotationR[0] + 1) < CV_QUAT_CONVERT_THRESHOLD)
|
|
1044
|
-
{
|
|
1045
|
-
CV_LOG_WARNING(NULL,"Gimbal Lock occurs. Euler angles are non-unique, we set the first angle to 0");
|
|
1046
|
-
angles = {0, rotationR[4], std::atan2(rotationR[5], rotationR[6])};
|
|
1047
|
-
return angles;
|
|
1048
|
-
}
|
|
1049
|
-
}
|
|
1050
|
-
|
|
1051
|
-
angles(0) = std::atan2(rotationR[7], rotationR[8]);
|
|
1052
|
-
if (detail::isTaitBryan(eulerAnglesType))
|
|
1053
|
-
angles(1) = std::acos(rotationR[9]);
|
|
1054
|
-
else
|
|
1055
|
-
angles(1) = std::asin(rotationR[9]);
|
|
1056
|
-
angles(2) = std::atan2(rotationR[10], rotationR[11]);
|
|
1057
|
-
return angles;
|
|
1058
|
-
}
|
|
1059
|
-
|
|
1060
|
-
} // namepsace
|
|
1061
|
-
//! @endcond
|
|
1062
|
-
|
|
1063
|
-
#endif /*OPENCV_CORE_QUATERNION_INL_HPP*/
|