MP_Joint3D.cpp

Go to the documentation of this file.
00001 /* ****************************************************************** **
00002 **    OpenSees - Open System for Earthquake Engineering Simulation    **
00003 **          Pacific Earthquake Engineering Research Center            **
00004 **                                                                    **
00005 **                                                                    **
00006 ** (C) Copyright 1999, The Regents of the University of California    **
00007 ** All Rights Reserved.                                               **
00008 **                                                                    **
00009 ** Commercial use of this program without express permission of the   **
00010 ** University of California, Berkeley, is strictly prohibited.  See   **
00011 ** file 'COPYRIGHT'  in main directory for information on usage and   **
00012 ** redistribution,  and for a DISCLAIMER OF ALL WARRANTIES.           **
00013 **                                                                    **
00014 ** Developed by:                                                      **
00015 **   Frank McKenna (fmckenna@ce.berkeley.edu)                         **
00016 **   Gregory L. Fenves (fenves@ce.berkeley.edu)                       **
00017 **   Filip C. Filippou (filippou@ce.berkeley.edu)                     **
00018 **                                                                    **
00019 ** ****************************************************************** */
00020                                                                         
00021 // $Revision: 1.2 $
00022 // $Date: 2004/09/01 04:01:27 $
00023 // $Source: /usr/local/cvs/OpenSees/SRC/element/joint/MP_Joint3D.cpp,v $
00024 
00025 // Written: Arash Altoontash, Gregory Deierlein
00026 // Created: 04/03
00027 // Revision: Arash
00028 
00029 // Purpose: This file contains the implementation of class MP_Joint3D.
00030 
00031 
00032 #include <MP_Joint3D.h>
00033 
00034 #include <stdlib.h>
00035 #include <Matrix.h>
00036 #include <ID.h>
00037 #include <Channel.h>
00038 #include <FEM_ObjectBroker.h>
00039 
00040 
00041 // constructor for FEM_ObjectBroker
00042 MP_Joint3D::MP_Joint3D()
00043 :MP_Constraint( 0 , CNSTRNT_TAG_MP_Joint3D ), thisDomain(0),
00044 nodeRetained(0), nodeConstrained(0), nodeRotation(0), RotDOF(0),
00045 nodeDisplacement(0), DispDOF(0), LargeDisplacement(0), Length0(0.0),
00046 constraint(0), constrDOF(0), retainDOF(0), RotNormVect(0), DspNormVect(0),
00047 dbTag1(0), dbTag2(0), dbTag3(0), RetainedNode(0), ConstrainedNode(0),
00048 RotationNode(0), DisplacementNode(0)
00049 {
00050     
00051 }
00052 
00053 
00054 // general constructor for ModelBuilder
00055 MP_Joint3D::MP_Joint3D( Domain *theDomain, int tag, int nodeRetain, int nodeConstr,
00056                 int nodeRot, int Rotdof, int nodeDisp, int Dispdof, int LrgDsp )
00057 :MP_Constraint( tag , CNSTRNT_TAG_MP_Joint3D ), thisDomain(theDomain),
00058 nodeRetained(nodeRetain), nodeConstrained(nodeConstr), nodeRotation(nodeRot),
00059 RotDOF(Rotdof), nodeDisplacement(nodeDisp), DispDOF(Dispdof), 
00060 LargeDisplacement(LrgDsp), Length0(0.0), constraint(0), constrDOF(0),
00061 retainDOF(0), RotNormVect(3), DspNormVect(3), 
00062 dbTag1(0), dbTag2(0), dbTag3(0), RetainedNode(0), ConstrainedNode(0),
00063 RotationNode(0), DisplacementNode(0)
00064 {
00065 
00066   if( thisDomain == NULL ) {
00067     opserr << "WARNING MP_Joint3D(): Specified domain does not exist";
00068     opserr << "Domain = 0\n";
00069     return;
00070   }
00071 
00072   this->setTag(tag);
00073 
00074   // get node pointers of constrainted, retained, rotation and displacement nodes
00075   ConstrainedNode = theDomain->getNode(nodeConstrained);
00076   if (ConstrainedNode == NULL) {
00077     
00078     opserr << "MP_Joint3D::MP_Joint3D: nodeConstrained: ";
00079     opserr << nodeConstrained << "does not exist in model\n";
00080     exit(0);
00081   }
00082   
00083   RetainedNode = theDomain->getNode(nodeRetained);
00084   if (RetainedNode == NULL) {
00085     
00086     opserr << "MP_Joint3D::MP_Joint3D: nodeRetained: ";
00087     opserr << nodeRetained << "does not exist in model\n";
00088     exit(0);
00089   }
00090   
00091   RotationNode = theDomain->getNode(nodeRotation);
00092   if (RotationNode == NULL) {
00093     
00094     opserr << "MP_Joint3D::MP_Joint3D: nodeRotation: ";
00095     opserr << nodeRotation << "does not exist in model\n";
00096     exit(0);
00097   }
00098   
00099   DisplacementNode = theDomain->getNode(nodeDisplacement);
00100   if (DisplacementNode == NULL)
00101     {
00102       opserr << "MP_Joint3D::MP_Joint3D: nodeDisplacement: ";
00103       opserr << nodeDisplacement << "does not exist in model\n";
00104       exit(0);
00105     }
00106   
00107   
00108   // check for proper degrees of freedom
00109   int RnumDOF = RetainedNode->getNumberDOF();
00110   int CnumDOF = ConstrainedNode->getNumberDOF();
00111   if (RnumDOF != 9 || CnumDOF != 6 ){
00112     opserr << "MP_Joint3D::MP_Joint3D - mismatch in numDOF\n DOF not supported by this type of constraint";
00113     return;
00114   }
00115   
00116   
00117   // check the main degree of freedom. Assign auxilary DOF 
00118   if ( RotDOF<6 || RotDOF>8 || DispDOF<6 || DispDOF>8 || RotDOF==DispDOF ) {
00119     opserr << "MP_Joint3D::MP_Joint3D - Wrong degrees of freedom" ;
00120     return;
00121   }
00122   
00123   // check for proper dimensions of coordinate space
00124   const Vector &crdRet = RetainedNode->getCrds();
00125   int dimRet = crdRet.Size();
00126   const Vector &crdCon = ConstrainedNode->getCrds();
00127   int dimCon = crdCon.Size();
00128   const Vector &crdRot = RotationNode->getCrds();
00129   int dimRot = crdRot.Size();
00130   const Vector &crdDsp = DisplacementNode->getCrds();
00131   int dimDsp = crdDsp.Size();
00132   
00133   if ( dimRet != 3 || dimCon != 3 || dimRot != 3 || dimDsp != 3 ){
00134     opserr << "MP_Joint3D::MP_Joint3D - mismatch in dimnesion\n dimension not supported by this type of constraint";
00135     return;
00136   }
00137   
00138   
00139   // calculate the initial length of the rigid link
00140   double deltaX = crdCon(0) - crdRet(0);
00141   double deltaY = crdCon(1) - crdRet(1);
00142   double deltaZ = crdCon(2) - crdRet(2);
00143   
00144   Length0 = sqrt( deltaX*deltaX + deltaY*deltaY + deltaY*deltaY );
00145   if ( Length0 <= 1.0e-12 ) {
00146     opserr << "MP_Joint3D::MP_Joint3D - The constraint length is zero\n";
00147   }
00148   
00149   // calculate the normal vectors for the rotation mode and displacement mode
00150   for (int i = 0 ; i<3 ; i++ ) {
00151     RotNormVect(i)= crdRot(i) - crdRet(i);
00152     DspNormVect(i)= crdDsp(i) - crdRet(i);      
00153   }
00154   
00155   if ( RotNormVect.Norm() <= 1.0e-12 || DspNormVect.Norm() <= 1.0e-12 ) {               
00156     opserr << "MP_Joint3D::MP_Joint3D - the normal vector for the rotation mode or the displacement mode is zero\n";
00157   }
00158   RotNormVect = RotNormVect / RotNormVect.Norm();
00159   DspNormVect = DspNormVect / DspNormVect.Norm();
00160   
00161   
00162   // allocate and set up the constranted and retained id's
00163   
00164   // the end is released
00165   constrDOF = new ID(6);
00166   retainDOF = new ID(8);
00167   for (int j = 0 ; j<6 ; j++ ) {
00168     (*constrDOF)(j) = j;
00169     (*retainDOF)(j) = j;        
00170   }
00171   (*retainDOF)(6) = RotDOF;
00172   (*retainDOF)(7) = DispDOF;
00173   
00174   
00175   if (constrDOF == NULL || retainDOF == NULL ) { 
00176     opserr << "MP_Joint3D::MP_Joint3D - ran out of memory \ncan not generate ID for nodes\n";
00177     exit(-1);
00178   }
00179   
00180   
00181   // allocate and set up the constraint matrix          
00182   constraint = new Matrix( constrDOF->Size() , retainDOF->Size() );
00183   
00184   (*constraint) (0,0) = 1.0 ;
00185   (*constraint) (1,1) = 1.0 ;
00186   (*constraint) (2,2) = 1.0 ;
00187   (*constraint) (1,3) = -deltaZ;
00188   (*constraint) (2,3) = deltaY;
00189   (*constraint) (3,3) = 1.0 ;
00190   (*constraint) (0,4) = deltaZ;
00191   (*constraint) (2,4) = -deltaX;
00192   (*constraint) (4,4) = 1.0 ;
00193   (*constraint) (0,5) = -deltaY;
00194   (*constraint) (1,5) = deltaX;
00195   (*constraint) (5,5) = 1.0 ;
00196   (*constraint) (3,6) = RotNormVect(0);
00197   (*constraint) (4,6) = RotNormVect(1);
00198   (*constraint) (5,6) = RotNormVect(2);
00199   (*constraint) (0,7) = deltaZ*DspNormVect(1) - deltaY*DspNormVect(2);
00200   (*constraint) (1,7) = deltaX*DspNormVect(2) - deltaZ*DspNormVect(0) ;
00201   (*constraint) (1,7) = deltaY*DspNormVect(0) - deltaX*DspNormVect(1) ;
00202   
00203   
00204   if (constraint == NULL ) {
00205     opserr << "MP_Joint3D::MP_Joint3D - ran out of memory \ncan not generate the constraint matrix";
00206     exit(-1);
00207   }
00208 }
00209 
00210 
00211 
00212 MP_Joint3D::~MP_Joint3D()
00213 {
00214   // invoke the destructor on the matrix and the two ID objects
00215   if (constraint != NULL)
00216     delete constraint;
00217   if (constrDOF != NULL)
00218     delete constrDOF;
00219   if (retainDOF != NULL)
00220     delete retainDOF;    
00221 }
00222 
00223 
00224 int
00225 MP_Joint3D::getNodeRetained(void) const
00226 {
00227     // return id of retained node
00228     return nodeRetained;
00229 }
00230 
00231 int
00232 MP_Joint3D::getNodeConstrained(void) const
00233 {
00234     // return id of constrained node    
00235     return nodeConstrained;
00236 }
00237 
00238 
00239 const ID &
00240 MP_Joint3D::getConstrainedDOFs(void) const
00241 {
00242   if (constrDOF == NULL) {
00243     opserr << "MP_Joint3D::getConstrainedDOF - no ID was set, ";
00244     opserr << "was recvSelf() ever called? or subclass incorrect?\n";   
00245     exit(-1);
00246   }
00247   
00248   // return the ID corresponding to constrained DOF of Ccr
00249   return (*constrDOF);    
00250 }
00251 
00252 
00253 const ID &
00254 MP_Joint3D::getRetainedDOFs(void) const
00255 {
00256   if (retainDOF == NULL) {
00257     opserr << "MP_Joint3D::getRetainedDOFs - no ID was set\n ";
00258     opserr << "was recvSelf() ever called? or subclass incorrect?\n";           
00259     exit(-1);
00260   }
00261   
00262   // return the ID corresponding to retained DOF of Ccr
00263   return (*retainDOF);    
00264 }
00265 
00266 
00267 int 
00268 MP_Joint3D::applyConstraint(double timeStamp)
00269 {
00270   if ( LargeDisplacement != 0 )
00271     {
00272       // calculate the constraint at this moment
00273       
00274       // get the coordinates of the two nodes - check dimensions are the same FOR THE MOMENT
00275       const Vector &crdRet = RetainedNode->getCrds();
00276       const Vector &crdCon = ConstrainedNode->getCrds();
00277       const Vector &crdRot = RotationNode->getCrds();
00278       const Vector &crdDsp = DisplacementNode->getCrds();
00279       
00280       // get commited displacements of nodes to get updated coordinates
00281       const Vector &dispRet = RetainedNode->getDisp();
00282       const Vector &dispCon = ConstrainedNode->getDisp();
00283       const Vector &dispRot = RotationNode->getDisp();
00284       const Vector &dispDsp = DisplacementNode->getDisp();
00285       
00286       double deltaX = dispCon(0) + crdCon(0) - dispRet(0) - crdRet(0);
00287       double deltaY = dispCon(1) + crdCon(1) - dispRet(1) - crdRet(1);
00288       double deltaZ = dispCon(2) + crdCon(2) - dispRet(2) - crdRet(2);
00289       
00290       for ( int i = 0 ; i<3 ; i++ )
00291         {
00292           RotNormVect(i)= dispRot(i) + crdRot(i) - dispRet(i) - crdRet(i);
00293           DspNormVect(i)= dispDsp(i) + crdDsp(i) - dispRet(i) - crdRet(i);      
00294         }
00295       
00296       RotNormVect = RotNormVect / RotNormVect.Norm();
00297       DspNormVect = DspNormVect / DspNormVect.Norm();
00298       
00299       
00300       constraint->Zero();
00301       
00302       (*constraint) (0,0) = 1.0 ;
00303       (*constraint) (1,1) = 1.0 ;
00304       (*constraint) (2,2) = 1.0 ;
00305       (*constraint) (1,3) = -deltaZ;
00306       (*constraint) (2,3) = deltaY;
00307       (*constraint) (3,3) = 1.0 ;
00308       (*constraint) (0,4) = deltaZ;
00309       (*constraint) (2,4) = -deltaX;
00310       (*constraint) (4,4) = 1.0 ;
00311       (*constraint) (0,5) = -deltaY;
00312       (*constraint) (1,5) = deltaX;
00313       (*constraint) (5,5) = 1.0 ;
00314       (*constraint) (3,6) = RotNormVect(0);
00315       (*constraint) (4,6) = RotNormVect(1);
00316       (*constraint) (5,6) = RotNormVect(2);
00317       (*constraint) (0,7) = deltaZ*DspNormVect(1) - deltaY*DspNormVect(2);
00318       (*constraint) (1,7) = deltaX*DspNormVect(2) - deltaZ*DspNormVect(0) ;
00319       (*constraint) (2,7) = deltaY*DspNormVect(0) - deltaX*DspNormVect(1) ;
00320     }
00321   return 0;
00322 }
00323 
00324 
00325 bool
00326 MP_Joint3D::isTimeVarying(void) const
00327 {
00328   if ( LargeDisplacement != 0 ) return true;
00329   
00330   return false;
00331 }
00332 
00333 
00334 int MP_Joint3D::sendSelf(int commitTag, Channel &theChannel)
00335 {
00336   return 0;
00337 }
00338 
00339 
00340 int MP_Joint3D::recvSelf(int commitTag, Channel &theChannel, 
00341                          FEM_ObjectBroker &theBroker)
00342 {
00343   return 0;
00344 }
00345 
00346 
00347 const Matrix &MP_Joint3D::getConstraint(void)
00348 {
00349     if (constraint == 0) {
00350       opserr << "MP_Joint3D::getConstraint - no Matrix was set\n";
00351       exit(-1);
00352     }    
00353     
00354     // Length correction
00355     // to correct the trial displacement
00356     if ( LargeDisplacement == 2 )
00357       {
00358         // get the coordinates of the two nodes - check dimensions are the same FOR THE MOMENT
00359         const Vector &crdR = RetainedNode->getCrds();
00360         const Vector &crdC = ConstrainedNode->getCrds();
00361         
00362         // get commited displacements of nodes to get updated coordinates
00363         const Vector &dispR = RetainedNode->getTrialDisp();
00364         const Vector &dispC = ConstrainedNode->getTrialDisp();
00365         
00366         double deltaX = dispC(0) + crdC(0) - dispR(0) - crdR(0);
00367         double deltaY = dispC(1) + crdC(1) - dispR(1) - crdR(1);
00368         double deltaZ = dispC(2) + crdC(2) - dispR(2) - crdR(2);
00369         
00370         
00371         Vector Direction(3);
00372         Direction(0) = deltaX;
00373         Direction(1) = deltaY;
00374         Direction(2) = deltaZ;
00375         double NewLength = Direction.Norm();
00376         if ( NewLength < 1e-12 ) opserr << "MP_Joint3D::applyConstraint : length of rigid link is too small or zero"; 
00377         Direction = Direction * (Length0/NewLength);            // correct the length
00378         // find new displacements of the constrainted node
00379         
00380         Vector NewLocation(6);
00381         NewLocation(0) = Direction(0) + dispR(0) + crdR(0) - crdC(0);
00382         NewLocation(1) = Direction(1) + dispR(1) + crdR(1) - crdC(1);
00383         NewLocation(2) = Direction(2) + dispR(2) + crdR(2) - crdC(2);
00384         NewLocation(3) = dispC(3);
00385         NewLocation(4) = dispC(4);
00386         NewLocation(5) = dispC(5);
00387         
00388         int dummy = ConstrainedNode->setTrialDisp( NewLocation );
00389       }
00390     // end of length correction procedure
00391     
00392     // return the constraint matrix Ccr
00393     return (*constraint);
00394 }
00395 
00396 void MP_Joint3D::Print(OPS_Stream &s, int flag )
00397 {
00398   s << "MP_Joint3D: " << this->getTag() << "\n";
00399   s << "\tConstrained Node: " << nodeConstrained;
00400   s << " Retained Node: " << nodeRetained ;
00401   s << " Large Disp: " << LargeDisplacement;
00402   if (constrDOF != 0)
00403     s << " constrained dof: " << *constrDOF;    
00404   if (retainDOF != 0)
00405     s << " retained dof: " << *retainDOF;        
00406   if (constraint != 0)
00407     s << " constraint matrix: " << *constraint << "\n";
00408   
00409 }
00410 
00411 
00412 void
00413 MP_Joint3D::setDomain(Domain *theDomain)
00414 {
00415   this->DomainComponent::setDomain(theDomain);
00416   thisDomain = theDomain;
00417   
00418   RetainedNode = thisDomain->getNode(nodeRetained);
00419   ConstrainedNode = thisDomain->getNode(nodeConstrained);
00420   RotationNode = thisDomain->getNode(nodeRotation);
00421   DisplacementNode = thisDomain->getNode(nodeDisplacement);
00422 }

Generated on Mon Oct 23 15:05:08 2006 for OpenSees by doxygen 1.5.0