Line data Source code
1 : //* This file is part of the MOOSE framework 2 : //* https://mooseframework.inl.gov 3 : //* 4 : //* All rights reserved, see COPYRIGHT for full restrictions 5 : //* https://github.com/idaholab/moose/blob/master/COPYRIGHT 6 : //* 7 : //* Licensed under LGPL 2.1, please see LICENSE for details 8 : //* https://www.gnu.org/licenses/lgpl-2.1.html 9 : 10 : #include "libmesh/ignore_warnings.h" 11 : #include "EulerAngles.h" 12 : #include "MooseRandom.h" 13 : 14 0 : EulerAngles::EulerAngles() 15 : { 16 0 : phi1 = 0.0; 17 0 : Phi = 0.0; 18 0 : phi2 = 0.0; 19 0 : } 20 : 21 223184 : EulerAngles::EulerAngles(const Eigen::Quaternion<Real> & q) 22 : { 23 223184 : phi1 = std::atan2((q.x() * q.z() + q.w() * q.y()), -(-q.w() * q.x() + q.y() * q.z())) * 24 : (180.0 / libMesh::pi); 25 223184 : Phi = std::atan2( 26 : std::sqrt(1 - 27 223184 : std::pow(q.w() * q.w() - q.x() * q.x() - q.y() * q.y() + q.z() * q.z(), 2.0)), 28 223184 : q.w() * q.w() - q.x() * q.x() - q.y() * q.y() + q.z() * q.z()) * 29 : (180.0 / libMesh::pi); 30 223184 : phi2 = std::atan2((q.x() * q.z() - q.w() * q.y()), (q.w() * q.x() + q.y() * q.z())) * 31 : (180.0 / libMesh::pi); 32 : 33 : // Following checks and updates are done only to comply with bunge euler angle definitions, 0.0 34 : // <= phi1/phi2 <= 360.0 35 223184 : if (phi1 < 0.0) 36 49514 : phi1 += 360.0; 37 223184 : if (phi2 < 0.0) 38 0 : phi2 += 360.0; 39 223184 : if (Phi < 0.0) 40 0 : mooseError("Euler angle out of range."); 41 223184 : } 42 : 43 : Eigen::Quaternion<Real> 44 0 : EulerAngles::toQuaternion() 45 : { 46 : Eigen::Quaternion<Real> q; 47 : 48 : Real cPhi1PlusPhi2, cphi, cPhi1MinusPhi2; 49 : Real sPhi1PlusPhi2, sphi, sPhi1MinusPhi2; 50 : 51 : /** 52 : * "NASA Mission Planning and Analysis Division. 53 : * "Euler Angles, Quaternions, and Transformation Matrices". NASA. 54 : */ 55 : 56 0 : cPhi1PlusPhi2 = std::cos((phi1 * libMesh::pi / 180.0 + phi2 * libMesh::pi / 180.0) / 2.0); 57 0 : cphi = std::cos(Phi * libMesh::pi / 360.0); 58 0 : cPhi1MinusPhi2 = std::cos((phi1 * libMesh::pi / 180.0 - phi2 * libMesh::pi / 180.0) / 2.0); 59 : 60 0 : sPhi1PlusPhi2 = std::sin((phi1 * libMesh::pi / 180.0 + phi2 * libMesh::pi / 180.0) / 2.0); 61 0 : sphi = std::sin(Phi * libMesh::pi / 360.0); 62 0 : sPhi1MinusPhi2 = std::sin((phi1 * libMesh::pi / 180.0 - phi2 * libMesh::pi / 180.0) / 2.0); 63 : 64 0 : q.w() = cphi * cPhi1PlusPhi2; 65 0 : q.x() = sphi * cPhi1MinusPhi2; 66 0 : q.y() = sphi * sPhi1MinusPhi2; 67 0 : q.z() = cphi * sPhi1PlusPhi2; 68 : 69 0 : return q; 70 : } 71 : 72 : void 73 0 : EulerAngles::random() 74 : { 75 0 : phi1 = MooseRandom::rand() * 360.0; 76 0 : Phi = std::acos(1.0 - 2.0 * MooseRandom::rand()) / libMesh::pi * 180.0; 77 0 : phi2 = MooseRandom::rand() * 360; 78 0 : } 79 : 80 : void 81 0 : EulerAngles::random(MooseRandom & random) 82 : { 83 0 : phi1 = random.rand(0) * 360.0; 84 0 : Phi = std::acos(1.0 - 2.0 * random.rand(0)) / libMesh::pi * 180.0; 85 0 : phi2 = random.rand(0) * 360; 86 0 : } 87 : #include "libmesh/restore_warnings.h"