CMS 3D CMS Logo

/data/refman/pasoursint/CMSSW_4_1_8_patch12/src/Alignment/CommonAlignment/src/AlignableModifier.cc

Go to the documentation of this file.
00001 #include "CLHEP/Random/DRand48Engine.h"
00002 #include "CLHEP/Random/RandGauss.h"
00003 #include "CLHEP/Random/Randomize.h"
00004 
00005 #include "DataFormats/TrackingRecHit/interface/AlignmentPositionError.h"
00006 #include "FWCore/ServiceRegistry/interface/Service.h"
00007 #include "FWCore/Utilities/interface/RandomNumberGenerator.h"
00008 #include "FWCore/MessageLogger/interface/MessageLogger.h"
00009 #include "FWCore/ParameterSet/interface/ParameterSet.h"
00010 
00011 #include "Alignment/CommonAlignment/interface/AlignableComposite.h"
00012 #include "Alignment/CommonAlignment/interface/AlignableModifier.h"
00013 
00014 
00015 //__________________________________________________________________________________________________
00016 AlignableModifier::AlignableModifier( void )
00017 {
00018 
00019   theDRand48Engine = new CLHEP::DRand48Engine();
00020 
00021 }
00022 
00023 
00024 //__________________________________________________________________________________________________
00025 AlignableModifier::~AlignableModifier()
00026 {
00027 
00028   delete theDRand48Engine;
00029 
00030 }
00031 
00032 //__________________________________________________________________________________________________
00033 void AlignableModifier::init_( void )
00034 {
00035 
00036   // Initialize all known parameters (according to ORCA's MisalignmentScenario.cc)
00037   distribution_ = "";        // Switch for distributions ("fixed","flat","gaussian")
00038   setError_     = false;     // Apply alignment errors
00039   setRotations_ = true;      // Apply rotations
00040   setTranslations_ = true;   // Apply translations
00041   scale_        = 1.;        // Scale to apply to all movements
00042   scaleError_   = 1.;        // Scale to apply to alignment errors
00043   phiX_         = 0.;        // Rotation angle around X [rad]
00044   phiY_         = 0.;        // Rotation angle around Y [rad]
00045   phiZ_         = 0.;        // Rotation angle around Z [rad]
00046   phiXlocal_    = 0.;        // Local rotation angle around X [rad]
00047   phiYlocal_    = 0.;        // Local rotation angle around Y [rad]
00048   phiZlocal_    = 0.;        // Local rotation angle around Z [rad]
00049   dX_           = 0.;        // X displacement [cm]
00050   dY_           = 0.;        // Y displacement [cm]
00051   dZ_           = 0.;        // Z displacement [cm]
00052   dXlocal_      = 0.;        // Local X displacement [cm]
00053   dYlocal_      = 0.;        // Local Y displacement [cm]
00054   dZlocal_      = 0.;        // Local Z displacement [cm]
00055   twist_        = 0.;        // Twist angle [rad]
00056   shear_        = 0.;        // Shear angle [rad]
00057 
00058   // These are set through 'distribution'
00059   random_       = true;      // Use random distributions
00060   gaussian_     = true;      // Use gaussian distribution (otherwise flat)
00061 
00062 }
00063 
00064 //__________________________________________________________________________________________________
00065 // Return true if given parameter name should be propagated down
00066 const bool AlignableModifier::isPropagated( const std::string& parameterName ) const
00067 {
00068 
00069   if ( parameterName == "distribution"    || 
00070        parameterName == "setError"        ||
00071        parameterName == "scaleError"      ||
00072        parameterName == "setRotations"    ||
00073        parameterName == "setTranslations" ||
00074        parameterName == "scale" 
00075        ) return true;
00076   
00077   return false;
00078 
00079 }
00080 
00081 
00082 //__________________________________________________________________________________________________
00084 bool AlignableModifier::modify( Alignable* alignable, const edm::ParameterSet& pSet )
00085 {
00086 
00087   // Initialize parameters
00088   this->init_();
00089   int rotX_=0, rotY_=0, rotZ_=0; // To check correct backward compatibility
00090 
00091 
00092   // Reset counter
00093   m_modified = 0;
00094   
00095   // Retrieve parameters
00096   std::ostringstream error;
00097   std::vector<std::string> parameterNames = pSet.getParameterNames();
00098   for ( std::vector<std::string>::iterator iParam = parameterNames.begin(); 
00099         iParam != parameterNames.end(); iParam++ ) {
00100     if  ( (*iParam) == "distribution" ) distribution_ = pSet.getParameter<std::string>( *iParam );
00101     else if ( (*iParam) == "setError" ) setError_ = pSet.getParameter<bool>( *iParam );
00102     else if ( (*iParam) == "setRotations") setRotations_ = pSet.getParameter<bool>( *iParam );
00103     else if ( (*iParam) == "setTranslations") setTranslations_ = pSet.getParameter<bool>( *iParam );
00104     else if ( (*iParam) == "scale" )    scale_ = pSet.getParameter<double>( *iParam );
00105     else if ( (*iParam) == "scaleError" ) scaleError_ = pSet.getParameter<double>( *iParam );
00106     else if ( (*iParam) == "phiX" )    phiX_     = pSet.getParameter<double>( *iParam );
00107     else if ( (*iParam) == "phiY" )    phiY_     = pSet.getParameter<double>( *iParam );
00108     else if ( (*iParam) == "phiZ" )    phiZ_     = pSet.getParameter<double>( *iParam );
00109     else if ( (*iParam) == "dX" )      dX_       = pSet.getParameter<double>( *iParam );
00110     else if ( (*iParam) == "dY" )      dY_       = pSet.getParameter<double>( *iParam );
00111     else if ( (*iParam) == "dZ" )      dZ_       = pSet.getParameter<double>( *iParam );
00112     else if ( (*iParam) == "dXlocal" ) dXlocal_  = pSet.getParameter<double>( *iParam );
00113     else if ( (*iParam) == "dYlocal" ) dYlocal_  = pSet.getParameter<double>( *iParam );
00114     else if ( (*iParam) == "dZlocal" ) dZlocal_  = pSet.getParameter<double>( *iParam );
00115     else if ( (*iParam) == "twist" )   twist_    = pSet.getParameter<double>( *iParam );
00116     else if ( (*iParam) == "shear" )   shear_    = pSet.getParameter<double>( *iParam );
00117     else if ( (*iParam) == "localX" ) { phiXlocal_=pSet.getParameter<double>( *iParam ); rotX_++; }
00118     else if ( (*iParam) == "localY" ) { phiYlocal_=pSet.getParameter<double>( *iParam ); rotY_++; }
00119     else if ( (*iParam) == "localZ" ) { phiZlocal_=pSet.getParameter<double>( *iParam ); rotZ_++; }
00120     else if ( (*iParam) == "phiXlocal" ) { phiXlocal_=pSet.getParameter<double>( *iParam ); rotX_++; }
00121     else if ( (*iParam) == "phiYlocal" ) { phiYlocal_=pSet.getParameter<double>( *iParam ); rotY_++; }
00122     else if ( (*iParam) == "phiZlocal" ) { phiZlocal_=pSet.getParameter<double>( *iParam ); rotZ_++; }
00123     else if ( !pSet.existsAs<edm::ParameterSet>(*iParam) ) { // PSets are OK to ignore
00124       if ( !error.str().length() ) error << "Unknown parameter name(s): ";
00125       error << " " << *iParam;
00126     }
00127   }
00128 
00129   // Check if both 'localN' and 'phiNlocal' have been used
00130   if ( rotX_==2 ) throw cms::Exception("BadConfig") << "Found both localX and phiXlocal";
00131   if ( rotY_==2 ) throw cms::Exception("BadConfig") << "Found both localY and phiYlocal";
00132   if ( rotZ_==2 ) throw cms::Exception("BadConfig") << "Found both localZ and phiZlocal";
00133 
00134   // Check error
00135   if ( error.str().length() )
00136     throw cms::Exception("BadConfig") << error.str();
00137 
00138   // Decode distribution
00139   this->setDistribution( distribution_ );
00140 
00141   //if (scale_) { NO! Different random sequence if only parts scale to zero!
00142 
00143   // Apply displacements
00144   if ( std::abs(dX_) + std::abs(dY_) + std::abs(dZ_) > 0 && setTranslations_ )
00145     this->moveAlignable( alignable, random_, gaussian_, scale_*dX_, scale_*dY_, scale_*dZ_ );
00146   
00147   // Apply local displacements
00148   if ( std::abs(dXlocal_) + std::abs(dYlocal_) + std::abs(dZlocal_) > 0 && setTranslations_ )
00149     this->moveAlignableLocal( alignable, random_, gaussian_, 
00150                               scale_*dXlocal_, scale_*dYlocal_, scale_*dZlocal_ );
00151   
00152   // Apply rotations
00153   if ( std::abs(phiX_) + std::abs(phiY_) + std::abs(phiZ_) > 0 && setRotations_ )
00154     this->rotateAlignable( alignable, random_, gaussian_,
00155                            scale_*phiX_, scale_*phiY_, scale_*phiZ_ );
00156   
00157   // Apply local rotations
00158   if ( std::abs(phiXlocal_) + std::abs(phiYlocal_) + std::abs(phiZlocal_) > 0 && setRotations_ )
00159     this->rotateAlignableLocal( alignable, random_, gaussian_, 
00160                                 scale_*phiXlocal_, scale_*phiYlocal_, scale_*phiZlocal_ );
00161   
00162   // Apply twist
00163   if ( std::abs(twist_) > 0 )
00164     edm::LogError("NotImplemented") << "Twist is not implemented yet";
00165   
00166   // Apply shear
00167   if ( std::abs(shear_) > 0 )
00168     edm::LogError("NotImplemented") << "Shear is not implemented yet";
00169   
00170   // Apply error - first add scale_ to error
00171   scaleError_ *= scale_;
00172   if ( setError_ && scaleError_ ) {
00173     // Alignment Position Error for flat distribution: 1 sigma
00174     if ( !gaussian_ ) scaleError_ *= 0.68;
00175     
00176     
00177     // Error on displacement
00178     if ( std::abs(dX_) + std::abs(dY_) + std::abs(dZ_) > 0 && setTranslations_ )
00179       this->addAlignmentPositionError( alignable, 
00180                                        scaleError_*dX_, scaleError_*dY_, scaleError_*dZ_ );
00181     
00182     // Error on local displacements
00183     if ( std::abs(dXlocal_) + std::abs(dYlocal_) + std::abs(dZlocal_) > 0 && setTranslations_ )
00184       this->addAlignmentPositionErrorLocal( alignable,
00185                                             scaleError_*dXlocal_, scaleError_*dYlocal_, 
00186                                             scaleError_*dZlocal_ );
00187     
00188     // Error on rotations
00189     if ( std::abs(phiX_) + std::abs(phiY_) + std::abs(phiZ_) > 0 && setRotations_ )
00190       this->addAlignmentPositionErrorFromRotation( alignable, 
00191                                                    scaleError_*phiX_, scaleError_*phiY_, 
00192                                                    scaleError_*phiZ_ );
00193     
00194     // Error on local rotations
00195     if ( std::abs(phiXlocal_) + std::abs(phiYlocal_) + std::abs(phiZlocal_) > 0
00196          && setRotations_ )
00197       this->addAlignmentPositionErrorFromLocalRotation( alignable, 
00198                                                         scaleError_*phiXlocal_, 
00199                                                         scaleError_*phiYlocal_, 
00200                                                         scaleError_*phiZlocal_ );
00201   }
00202   // } // end if (scale_)
00203 
00204   return ( m_modified > 0 );
00205   
00206 }
00207 
00208 
00209 //__________________________________________________________________________________________________
00210 void AlignableModifier::setDistribution( const std::string& distr )
00211 {
00212 
00213   if ( distr == "fixed" ) random_ = false;
00214   else if ( distr == "flat" ) {
00215     random_   = true;
00216     gaussian_ = false;
00217   } else if ( distr == "gaussian" ) {
00218     random_   = true;
00219     gaussian_ = true;
00220   }
00221   
00222 }
00223 
00224 
00225 //__________________________________________________________________________________________________
00227 void AlignableModifier::setSeed( const long seed )
00228 {
00229 
00230   long m_seed;
00231 
00232   if ( seed > 0 ) m_seed = seed;
00233   else {
00234     edm::Service<edm::RandomNumberGenerator> rng;
00235     m_seed = rng->mySeed();
00236   }
00237 
00238   LogDebug("PrintArgs") << "Setting generator seed to " << m_seed;
00239 
00240   theDRand48Engine->setSeed( m_seed );
00241 
00242 }
00243 
00244 //__________________________________________________________________________________________________
00247 void AlignableModifier::moveAlignable( Alignable* alignable, bool random, bool gaussian,
00248                                        float sigmaX, float sigmaY, float sigmaZ )
00249 {
00250 
00251   
00252   std::ostringstream message;
00253  
00254   // Get movement vector according to arguments
00255   GlobalVector moveV( sigmaX, sigmaY, sigmaZ ); // Default: fixed
00256   if ( random ) {
00257     std::vector<float> randomNumbers;
00258     message << "random ";
00259     if (gaussian)       {
00260       randomNumbers = this->gaussianRandomVector( sigmaX, sigmaY, sigmaZ );
00261       message << "gaussian ";
00262     } else      {
00263       randomNumbers = this->flatRandomVector( sigmaX, sigmaY, sigmaZ );
00264       message << "flat ";
00265     }
00266     moveV = GlobalVector( randomNumbers[0], randomNumbers[1], randomNumbers[2] );
00267   }
00268   
00269   message << " move with sigma " << sigmaX << " " << sigmaY << " " << sigmaZ;
00270 
00271   LogDebug("PrintArgs") << message.str(); // Arguments
00272 
00273   LogDebug("PrintMovement") << "applied displacement: " << moveV; // Actual movements
00274   alignable->move(moveV);
00275   m_modified++;
00276 
00277 
00278 }
00279 
00280 //__________________________________________________________________________________________________
00283 void AlignableModifier::moveAlignableLocal( Alignable* alignable, bool random, bool gaussian,
00284                                             float sigmaX, float sigmaY, float sigmaZ )
00285 {
00286 
00287   
00288   std::ostringstream message;
00289  
00290   // Get movement vector according to arguments
00291   align::LocalVector moveV( sigmaX, sigmaY, sigmaZ ); // Default: fixed
00292   if ( random ) {
00293     std::vector<float> randomNumbers;
00294     message << "random ";
00295     if (gaussian) {
00296       randomNumbers = this->gaussianRandomVector( sigmaX, sigmaY, sigmaZ );
00297       message << "gaussian ";
00298     } else {
00299       randomNumbers = this->flatRandomVector( sigmaX, sigmaY, sigmaZ );
00300       message << "flat ";
00301     }
00302     moveV = align::LocalVector( randomNumbers[0], randomNumbers[1], randomNumbers[2] );
00303   }
00304   
00305   message << " move with sigma " << sigmaX << " " << sigmaY << " " << sigmaZ;
00306 
00307   LogDebug("PrintArgs") << message.str(); // Arguments
00308 
00309   LogDebug("PrintMovement") << "applied local displacement: " << moveV; // Actual movements
00310   alignable->move( alignable->surface().toGlobal(moveV) );
00311   m_modified++;
00312 
00313 
00314 }
00315 
00316 
00317 //__________________________________________________________________________________________________
00320 void AlignableModifier::rotateAlignable( Alignable* alignable, bool random, bool gaussian,
00321                                          float sigmaPhiX, float sigmaPhiY, float sigmaPhiZ )
00322 {
00323 
00324   
00325   std::ostringstream message;
00326 
00327   // Get rotation vector according to arguments
00328   GlobalVector rotV( sigmaPhiX, sigmaPhiY, sigmaPhiZ ); // Default: fixed
00329   if ( random ) {
00330     std::vector<float> randomNumbers;
00331     message << "random ";
00332     if (gaussian) {
00333       randomNumbers = this->gaussianRandomVector( sigmaPhiX, sigmaPhiY, sigmaPhiZ );
00334       message << "gaussian ";
00335     } else {
00336       randomNumbers = flatRandomVector( sigmaPhiX, sigmaPhiY, sigmaPhiZ );
00337       message << "flat ";
00338     }
00339     rotV = GlobalVector( randomNumbers[0], randomNumbers[1], randomNumbers[2] );
00340   }
00341   
00342   message << "global rotation by angles " << sigmaPhiX << " " << sigmaPhiY << " " << sigmaPhiZ;
00343 
00344   LogDebug("PrintArgs") << message.str(); // Arguments
00345 
00346   LogDebug("PrintMovement") << "applied rotation angles: " << rotV; // Actual movements
00347   if ( std::abs(sigmaPhiX) ) alignable->rotateAroundGlobalX( rotV.x() );
00348   if ( std::abs(sigmaPhiY) ) alignable->rotateAroundGlobalY( rotV.y() );
00349   if ( std::abs(sigmaPhiZ) ) alignable->rotateAroundGlobalZ( rotV.z() );
00350   m_modified++;
00351 
00352 
00353 }
00354 
00355 //__________________________________________________________________________________________________
00358 void 
00359 AlignableModifier::rotateAlignableLocal( Alignable* alignable, bool random, bool gaussian,
00360                                          float sigmaPhiX, float sigmaPhiY, float sigmaPhiZ )
00361 {
00362 
00363   
00364   std::ostringstream message;
00365 
00366   // Get rotation vector according to arguments
00367   align::LocalVector rotV( sigmaPhiX, sigmaPhiY, sigmaPhiZ ); // Default: fixed
00368   if ( random ) {
00369     std::vector<float> randomNumbers;
00370     message << "random ";
00371     if (gaussian) {
00372       randomNumbers = this->gaussianRandomVector( sigmaPhiX, sigmaPhiY, sigmaPhiZ );
00373       message << "gaussian ";
00374     } else {
00375       randomNumbers = flatRandomVector( sigmaPhiX, sigmaPhiY, sigmaPhiZ );
00376       message << "flat ";
00377     }
00378     rotV = align::LocalVector( randomNumbers[0], randomNumbers[1], randomNumbers[2] );
00379   }
00380   
00381   message << "local rotation by angles " << sigmaPhiX << " " << sigmaPhiY << " " << sigmaPhiZ;
00382   
00383   LogDebug("PrintArgs") << message.str(); // Arguments
00384   
00385   LogDebug("PrintMovement") << "applied local rotation angles: " << rotV; // Actual movements
00386   if ( std::abs(sigmaPhiX) ) alignable->rotateAroundLocalX( rotV.x() );
00387   if ( std::abs(sigmaPhiY) ) alignable->rotateAroundLocalY( rotV.y() );
00388   if ( std::abs(sigmaPhiZ) ) alignable->rotateAroundLocalZ( rotV.z() );
00389   m_modified++;
00390 
00391 
00392 }
00393 
00394 
00395 //__________________________________________________________________________________________________
00396 const std::vector<float> 
00397 AlignableModifier::gaussianRandomVector( float sigmaX, float sigmaY, float sigmaZ ) const
00398 {
00399 
00400   // Get absolute value if negative arguments
00401   if ( sigmaX < 0 ) {
00402     edm::LogWarning("BadConfig") << " taking absolute value for gaussian sigma_x";
00403     sigmaX = std::abs(sigmaX);
00404   }
00405   if ( sigmaY < 0 ) {
00406     edm::LogWarning("BadConfig") << " taking absolute value for gaussian sigma_y";
00407     sigmaY = std::abs(sigmaY);
00408   }
00409   if ( sigmaZ < 0 ) {
00410     edm::LogWarning("BadConfig") << " taking absolute value for gaussian sigma_z";
00411     sigmaZ = std::abs(sigmaZ);
00412   }
00413 
00414   // Pass by reference, otherwise pointer is deleted!
00415   CLHEP::RandGauss aGaussObjX( *theDRand48Engine, 0., sigmaX );
00416   CLHEP::RandGauss aGaussObjY( *theDRand48Engine, 0., sigmaY );
00417   CLHEP::RandGauss aGaussObjZ( *theDRand48Engine, 0., sigmaZ );
00418 
00419   std::vector<float> randomVector;
00420   randomVector.push_back( aGaussObjX.fire() );
00421   randomVector.push_back( aGaussObjY.fire() );
00422   randomVector.push_back( aGaussObjZ.fire() );
00423 
00424   return randomVector;
00425 
00426 }
00427 
00428 
00429 //__________________________________________________________________________________________________
00430 const  std::vector<float> 
00431 AlignableModifier::flatRandomVector( float sigmaX,float sigmaY, float sigmaZ ) const
00432 {
00433 
00434   // Get absolute value if negative arguments
00435   if ( sigmaX < 0 ) {
00436     edm::LogWarning("BadConfig") << " taking absolute value for flat sigma_x";
00437     sigmaX = std::abs(sigmaX);
00438   }
00439   if ( sigmaY < 0 ) {
00440     edm::LogWarning("BadConfig") << " taking absolute value for flat sigma_y";
00441     sigmaY = std::abs(sigmaY);
00442   }
00443   if ( sigmaZ < 0 ) {
00444     edm::LogWarning("BadConfig") << " taking absolute value for flat sigma_z";
00445     sigmaZ = std::abs(sigmaZ);
00446   }
00447 
00448   CLHEP::RandFlat aFlatObjX( *theDRand48Engine, -sigmaX, sigmaX );
00449   CLHEP::RandFlat aFlatObjY( *theDRand48Engine, -sigmaY, sigmaY );
00450   CLHEP::RandFlat aFlatObjZ( *theDRand48Engine, -sigmaZ, sigmaZ );
00451 
00452   std::vector<float> randomVector;
00453   randomVector.push_back( aFlatObjX.fire() );
00454   randomVector.push_back( aFlatObjY.fire() );
00455   randomVector.push_back( aFlatObjZ.fire() );
00456 
00457   return randomVector;
00458 
00459 }
00460 
00461 
00462 
00463 //__________________________________________________________________________________________________
00464 void AlignableModifier::addAlignmentPositionError( Alignable* alignable, 
00465                                                    float dx, float dy, float dz )
00466 {
00467 
00468   LogDebug("PrintArgs") << "Adding an AlignmentPositionError of size " 
00469                         << dx << " "  << dy << " "  << dz;
00470 
00471   AlignmentPositionError ape(dx,dy,dz);
00472   alignable->addAlignmentPositionError( ape, true );
00473 
00474 }
00475 
00476 
00477 //__________________________________________________________________________________________________
00478 void AlignableModifier::addAlignmentPositionErrorLocal( Alignable* alignable, 
00479                                                         float dx, float dy, float dz )
00480 {
00481 
00482   LogDebug("PrintArgs") << "Adding a local AlignmentPositionError of size " 
00483                         << dx << " "  << dy << " "  << dz;
00484 
00485   AlgebraicSymMatrix as(3,0); //3x3, zeroed
00486   as[0][0] = dx*dx; as[1][1] = dy*dy; as[2][2] = dz*dz; //diagonals
00487   align::RotationType rt = alignable->globalRotation(); //get rotation
00488   AlgebraicMatrix am(3,3);
00489   am[0][0]=rt.xx(); am[0][1]=rt.xy(); am[0][2]=rt.xz();
00490   am[1][0]=rt.yx(); am[1][1]=rt.yy(); am[1][2]=rt.yz();
00491   am[2][0]=rt.zx(); am[2][1]=rt.zy(); am[2][2]=rt.zz();
00492   as=as.similarityT(am); //rotate error matrix
00493 
00494   GlobalError ge( as );
00495   AlignmentPositionError ape( ge );
00496 
00497   alignable->addAlignmentPositionError( ape, true ); // propagate down to components
00498 
00499 }
00500 
00501 
00502 
00503 //__________________________________________________________________________________________________
00504 void AlignableModifier::addAlignmentPositionErrorFromRotation( Alignable* alignable, 
00505                                                                float phiX, float phiY, 
00506                                                                float phiZ )
00507 {
00508 
00509   align::RotationType rotx( Basic3DVector<float>(1.0, 0.0, 0.0), phiX );
00510   align::RotationType roty( Basic3DVector<float>(0.0, 1.0, 0.0), phiY );
00511   align::RotationType rotz( Basic3DVector<float>(0.0, 0.0, 1.0), phiZ );
00512   align::RotationType rot = rotz * roty * rotx;
00513   
00514   this->addAlignmentPositionErrorFromRotation( alignable, rot );
00515 
00516 }
00517 
00518 
00519 //__________________________________________________________________________________________________
00520 void AlignableModifier::addAlignmentPositionErrorFromLocalRotation( Alignable* alignable, 
00521                                                                     float phiX, float phiY, 
00522                                                                     float phiZ )
00523 {
00524 
00525   align::RotationType rotx( Basic3DVector<float>(1.0, 0.0, 0.0), phiX );
00526   align::RotationType roty( Basic3DVector<float>(0.0, 1.0, 0.0), phiY );
00527   align::RotationType rotz( Basic3DVector<float>(0.0, 0.0, 1.0), phiZ );
00528   align::RotationType rot = rotz * roty * rotx;
00529   
00530   this->addAlignmentPositionErrorFromLocalRotation( alignable, rot );
00531 
00532 }
00533 
00534 
00535 //__________________________________________________________________________________________________
00536 void AlignableModifier::addAlignmentPositionErrorFromRotation( Alignable* alignable, 
00537                                                                align::RotationType& rotation )
00538 { 
00539 
00540   LogDebug("PrintArgs") << "Adding an AlignmentPositionError from Rotation" << std::endl 
00541                         << rotation;
00542 
00543   alignable->addAlignmentPositionErrorFromRotation(rotation, true); // propagate down to components
00544 
00545 }
00546 
00547 
00548 //__________________________________________________________________________________________________
00549 void AlignableModifier::addAlignmentPositionErrorFromLocalRotation( Alignable* alignable, 
00550                                                                     align::RotationType& rotation )
00551 { 
00552   
00553   LogDebug("PrintArgs") << "Adding an AlignmentPositionError from Local Rotation" << std::endl 
00554                         << rotation;
00555   
00556   // true: propagate down to components
00557   alignable->addAlignmentPositionErrorFromLocalRotation(rotation, true);
00558   
00559 }
00560