///Diagonalizes a symmetric matrix (M = M^T) void Diagonalize(Mat3Ptr matrix) { if (matrix == NULL) ErrorIf(matrix == NULL, "Matrix3 - Null pointer passed for matrix."); Matrix3 quatMatrix = ToMatrix3(CreateDiagonalizer(*matrix)); *matrix = Concat(Concat(quatMatrix, *matrix), quatMatrix.Transposed()); }
void Matrix3x4::Decompose(Vector3& translation, Quaternion& rotation, Vector3& scale) const { translation.x_ = m03_; translation.y_ = m13_; translation.z_ = m23_; scale.x_ = sqrtf(m00_ * m00_ + m10_ * m10_ + m20_ * m20_); scale.y_ = sqrtf(m01_ * m01_ + m11_ * m11_ + m21_ * m21_); scale.z_ = sqrtf(m02_ * m02_ + m12_ * m12_ + m22_ * m22_); Vector3 invScale(1.0f / scale.x_, 1.0f / scale.y_, 1.0f / scale.z_); rotation = Quaternion(ToMatrix3().Scaled(invScale)); }
Matrix3 XMLElement::GetMatrix3(const ea::string& name) const { return ToMatrix3(GetAttribute(name)); }
Quaternion CreateDiagonalizer(Mat3Param matrix) { const unsigned cMaxSteps = 50; const float cThetaLimit = 1.0e6f; Quaternion quat(0.0f, 0.0f, 0.0f, 1.0f); Matrix3 quatMatrix; Matrix3 diagMatrix; for(unsigned i = 0; i < cMaxSteps; ++i) { ToMatrix3(quat, &quatMatrix); diagMatrix = Concat(Concat(quatMatrix, matrix), quatMatrix.Transposed()); //Elements not on the diagonal Vector3 offDiag(diagMatrix(1, 2), diagMatrix(0, 2), diagMatrix(0, 1)); //Magnitude of the off-diagonal elements Vector3 magDiag = Abs(offDiag); //Index of the largest element unsigned k = ((magDiag.x > magDiag.y) && (magDiag.x > magDiag.z)) ? 0 : ((magDiag.y > magDiag.z) ? 1 : 2); unsigned k1 = (k + 1) % 3; unsigned k2 = (k + 2) % 3; //Diagonal already if(offDiag[k] == 0.0f) { break; } float theta = (diagMatrix(k2, k2) - diagMatrix(k1, k1)) / (2.0f * offDiag[k]); float sign = Math::GetSign(theta); //Make theta positive theta *= sign; //Large term in T float thetaTerm = theta < 1e6f ? Math::Sqrt(Math::Sq(theta) + 1.0f) : theta; //Sign(T) / (|T| + sqrt(T^2 + 1)) float t = sign / (theta + thetaTerm); //c = 1 / (t^2 + 1) t = s / c float c = 1.0f / Math::Sqrt(Math::Sq(t) + 1.0f); //No room for improvement - reached machine precision. if(c == 1.0f) { break; } //Jacobi rotation for this iteration Quaternion jacobi(0.0f, 0.0f, 0.0f, 0.0f); //Using 1/2 angle identity sin(a/2) = sqrt((1-cos(a))/2) jacobi[k] = sign * Math::Sqrt((1.0f - c) / 2.0f); //Since our quat-to-matrix convention was for v*M instead of M*v jacobi.w = Math::Sqrt(1.0f - Math::Sq(jacobi[k])); //Reached limits of floating point precision if(jacobi.w == 1.0f) { break; } quat *= jacobi; Normalize(&quat); } return quat; }
Matrix3 ToMatrix3(const String& source) { return ToMatrix3(source.CString()); }
void Variant::FromString(VariantType type, const char* value) { switch (type) { case VAR_INT: *this = ToInt(value); break; case VAR_INT64: *this = ToInt64(value); break; case VAR_BOOL: *this = ToBool(value); break; case VAR_FLOAT: *this = ToFloat(value); break; case VAR_VECTOR2: *this = ToVector2(value); break; case VAR_VECTOR3: *this = ToVector3(value); break; case VAR_VECTOR4: *this = ToVector4(value); break; case VAR_QUATERNION: *this = ToQuaternion(value); break; case VAR_COLOR: *this = ToColor(value); break; case VAR_STRING: *this = value; break; case VAR_BUFFER: { SetType(VAR_BUFFER); PODVector<unsigned char>& buffer = *(reinterpret_cast<PODVector<unsigned char>*>(&value_)); StringToBuffer(buffer, value); } break; case VAR_VOIDPTR: // From string to void pointer not supported, set to null *this = (void*)0; break; case VAR_RESOURCEREF: { StringVector values = String::Split(value, ';'); if (values.Size() == 2) { SetType(VAR_RESOURCEREF); ResourceRef& ref = *(reinterpret_cast<ResourceRef*>(&value_)); ref.type_ = values[0]; ref.name_ = values[1]; } } break; case VAR_RESOURCEREFLIST: { StringVector values = String::Split(value, ';', true); if (values.Size() >= 1) { SetType(VAR_RESOURCEREFLIST); ResourceRefList& refList = *(reinterpret_cast<ResourceRefList*>(&value_)); refList.type_ = values[0]; refList.names_.Resize(values.Size() - 1); for (unsigned i = 1; i < values.Size(); ++i) refList.names_[i - 1] = values[i]; } } break; case VAR_INTRECT: *this = ToIntRect(value); break; case VAR_INTVECTOR2: *this = ToIntVector2(value); break; case VAR_INTVECTOR3: *this = ToIntVector3(value); break; case VAR_PTR: // From string to RefCounted pointer not supported, set to null *this = (RefCounted*)0; break; case VAR_MATRIX3: *this = ToMatrix3(value); break; case VAR_MATRIX3X4: *this = ToMatrix3x4(value); break; case VAR_MATRIX4: *this = ToMatrix4(value); break; case VAR_DOUBLE: *this = ToDouble(value); break; case VAR_RECT: *this = ToRect(value); break; default: SetType(VAR_NONE); } }
Mat3Ref Matrix3::Orthonormalize(void) { //return Quat().SetFromMatrix(*this).Normalize().ToMatrix(*this); return ToMatrix3(ToQuaternion(*this).Normalized()); }
Matrix3 JSONValue::GetMatrix3(unsigned index) const { return ToMatrix3(GetCString(index)); }
Matrix3 JSONValue::GetMatrix3(const String& name) const { return ToMatrix3(GetCString(name)); }
void QtPropertyDataDavaVariant::SetValueInternal(const QVariant &value) { switch(curVariantValue.type) { case DAVA::VariantType::TYPE_BOOLEAN: curVariantValue.SetBool(value.toBool()); break; case DAVA::VariantType::TYPE_FLOAT: curVariantValue.SetFloat(value.toFloat()); break; case DAVA::VariantType::TYPE_INT32: curVariantValue.SetInt32(value.toInt()); break; case DAVA::VariantType::TYPE_INT64: curVariantValue.SetInt64(value.toLongLong()); break; case DAVA::VariantType::TYPE_UINT32: curVariantValue.SetUInt32(value.toUInt()); break; case DAVA::VariantType::TYPE_UINT64: curVariantValue.SetUInt64(value.toULongLong()); break; case DAVA::VariantType::TYPE_KEYED_ARCHIVE: ToKeyedArchive(value); break; case DAVA::VariantType::TYPE_STRING: curVariantValue.SetString(value.toString().toStdString()); break; case DAVA::VariantType::TYPE_MATRIX2: ToMatrix2(value); break; case DAVA::VariantType::TYPE_MATRIX3: ToMatrix3(value); break; case DAVA::VariantType::TYPE_MATRIX4: ToMatrix4(value); break; case DAVA::VariantType::TYPE_VECTOR2: ToVector2(value); break; case DAVA::VariantType::TYPE_VECTOR3: ToVector3(value); break; case DAVA::VariantType::TYPE_VECTOR4: ToVector4(value); break; case DAVA::VariantType::TYPE_COLOR: ToColor(value); break; case DAVA::VariantType::TYPE_FASTNAME: curVariantValue.SetFastName(DAVA::FastName(value.toString().toStdString().c_str())); break; case DAVA::VariantType::TYPE_AABBOX3: ToAABBox3(value); break; case DAVA::VariantType::TYPE_BYTE_ARRAY: default: break; } }