BeamFiberMaterial.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.4 $
00022 // $Date: 2003/02/14 23:01:24 $
00023 // $Source: /usr/local/cvs/OpenSees/SRC/material/nD/BeamFiberMaterial.cpp,v $
00024 
00025 // Written: MHS
00026 // Created: Aug 2001
00027 //
00028 // Description: This file contains the class definition of BeamFiberMaterial.
00029 // The BeamFiberMaterial class is a wrapper class that performs static
00030 // condensation on a three-dimensional material model to give the 11, 12, and 13
00031 // stress components which can then be integrated over an area to model a
00032 // shear flexible 3D beam.
00033 
00034 #include <BeamFiberMaterial.h>
00035 #include <Channel.h>
00036 #include <FEM_ObjectBroker.h>
00037 
00038 Vector BeamFiberMaterial::stress(3);
00039 Matrix BeamFiberMaterial::tangent(3,3);
00040 
00041 BeamFiberMaterial::BeamFiberMaterial(void)
00042 : NDMaterial(0, ND_TAG_BeamFiberMaterial),
00043 Tstrain22(0.0), Tstrain33(0.0), Tgamma23(0.0),
00044 Cstrain22(0.0), Cstrain33(0.0), Cgamma23(0.0),
00045 theMaterial(0), strain(3)
00046 {
00047         // Nothing to do
00048 }
00049 
00050 BeamFiberMaterial::BeamFiberMaterial(int tag, NDMaterial &theMat)
00051 : NDMaterial(tag, ND_TAG_BeamFiberMaterial),
00052 Tstrain22(0.0), Tstrain33(0.0), Tgamma23(0.0),
00053 Cstrain22(0.0), Cstrain33(0.0), Cgamma23(0.0),
00054 theMaterial(0), strain(3)
00055 
00056 {
00057   // Get a copy of the material
00058   theMaterial = theMat.getCopy("ThreeDimensional");
00059   
00060   if (theMaterial == 0) {
00061     opserr << "BeamFiberMaterial::BeamFiberMaterial -- failed to get copy of material\n";
00062     exit(-1);
00063   }
00064 }
00065 
00066 BeamFiberMaterial::~BeamFiberMaterial(void) 
00067 { 
00068         if (theMaterial != 0)
00069                 delete theMaterial;
00070 } 
00071 
00072 NDMaterial*
00073 BeamFiberMaterial::getCopy(void) 
00074 {
00075         BeamFiberMaterial *theCopy =
00076                 new BeamFiberMaterial(this->getTag(), *theMaterial);
00077 
00078         theCopy->Tstrain22 = this->Tstrain22;
00079         theCopy->Tstrain33 = this->Tstrain33;
00080         theCopy->Tgamma23  = this->Tgamma23;
00081         theCopy->Cstrain22 = this->Cstrain22;
00082         theCopy->Cstrain33 = this->Cstrain33;
00083         theCopy->Cgamma23  = this->Cgamma23;
00084 
00085         return theCopy;
00086 }
00087 
00088 NDMaterial* 
00089 BeamFiberMaterial::getCopy(const char *type)
00090 {
00091         if (strcmp(type, "BeamFiber") == 0)
00092                 return this->getCopy();
00093         else
00094                 return 0;
00095 }
00096 
00097 int 
00098 BeamFiberMaterial::getOrder(void) const
00099 {
00100         return 3;
00101 }
00102 
00103 const char*
00104 BeamFiberMaterial::getType(void) const 
00105 {
00106         return "BeamFiber";
00107 }
00108 
00109 int 
00110 BeamFiberMaterial::commitState(void)
00111 {
00112   Cstrain22 = Tstrain22;
00113   Cstrain33 = Tstrain33;
00114   Cgamma23 = Tgamma23;
00115 
00116   return theMaterial->commitState();
00117 }
00118 
00119 int 
00120 BeamFiberMaterial::revertToLastCommit(void)
00121 {
00122   Tstrain22 = Cstrain22;
00123   Tstrain33 = Cstrain33;
00124   Tgamma23 = Cgamma23;
00125   
00126   return theMaterial->revertToLastCommit();
00127 }
00128 
00129 int
00130 BeamFiberMaterial::revertToStart()
00131 {
00132   this->Tstrain22 = 0.0;
00133   this->Tstrain33 = 0.0;
00134   this->Tgamma23  = 0.0;
00135   this->Cstrain22 = 0.0;
00136   this->Cstrain33 = 0.0;
00137   this->Cgamma23  = 0.0;
00138 
00139   return theMaterial->revertToStart();
00140 }
00141 
00142 double
00143 BeamFiberMaterial::getRho(void)
00144 {
00145   return theMaterial->getRho();
00146 }
00147 
00148 
00149 //receive the strain
00150 //NDmaterial strain order        = 11, 22, 33, 12, 23, 31  
00151 //BeamFiberMaterial strain order = 11, 12, 31, 22, 33, 23
00152 int 
00153 BeamFiberMaterial::setTrialStrain(const Vector &strainFromElement)
00154 {
00155   static const double tolerance = 1.0e-08;
00156 
00157   this->strain(0) = strainFromElement(0);
00158   this->strain(1) = strainFromElement(1);
00159   this->strain(2) = strainFromElement(2);
00160 
00161   //newton loop to solve for out-of-plane strains
00162 
00163   double norm;
00164   static Vector condensedStress(3);
00165   static Vector strainIncrement(3);
00166   static Vector threeDstress(6);
00167   static Vector threeDstrain(6);
00168   static Matrix threeDtangent(6,6);
00169   static Vector threeDstressCopy(6); 
00170   static Matrix threeDtangentCopy(6,6);
00171   static Matrix dd22(3,3);
00172 
00173   int i, j;
00174   int ii, jj;
00175 
00176   do {
00177     //set three dimensional strain
00178     threeDstrain(0) = this->strain(0);
00179     threeDstrain(1) = this->Tstrain22;
00180     threeDstrain(2) = this->Tstrain33;
00181     threeDstrain(3) = this->strain(1); 
00182     threeDstrain(4) = this->Tgamma23;
00183     threeDstrain(5) = this->strain(2);
00184 
00185     if (theMaterial->setTrialStrain(threeDstrain) < 0) {
00186       opserr << "BeamFiberMaterial::setTrialStrain - setStrain failed in material with strain " << threeDstrain;
00187       return -1;   
00188     }
00189 
00190     //three dimensional stress
00191     threeDstress = theMaterial->getStress();
00192 
00193     //three dimensional tangent 
00194     threeDtangent = theMaterial->getTangent();
00195 
00196     //NDmaterial strain order        = 11, 22, 33, 12, 23, 31  
00197     //BeamFiberMaterial strain order = 11, 12, 31, 22, 33, 23
00198 
00199     //swap matrix indices to sort out-of-plane components 
00200     for (i=0; i<6; i++) {
00201 
00202       ii = this->indexMap(i);
00203 
00204       threeDstressCopy(ii) = threeDstress(i);
00205 
00206       for (j=0; j<6; j++) {
00207 
00208         jj = this->indexMap(j);
00209         
00210         threeDtangentCopy(ii,jj) = threeDtangent(i,j);
00211 
00212       }//end for j
00213        
00214     }//end for i
00215 
00216 
00217     //out of plane stress and tangents
00218     for (i=0; i<3; i++) {
00219 
00220       condensedStress(i) = threeDstressCopy(i+3);
00221 
00222       for (j=0; j<3; j++) 
00223         dd22(i,j) = threeDtangentCopy(i+3,j+3);
00224 
00225     }//end for i
00226 
00227     //set norm
00228     norm = condensedStress.Norm();
00229 
00230     //condensation 
00231     dd22.Solve(condensedStress, strainIncrement);
00232 
00233     //update out of plane strains
00234     this->Tstrain22 -= strainIncrement(0);
00235     this->Tstrain33 -= strainIncrement(1);
00236     this->Tgamma23  -= strainIncrement(2);
00237 
00238   } while (norm > tolerance);
00239 
00240   return 0;
00241 }
00242 
00243 const Vector& 
00244 BeamFiberMaterial::getStrain(void)
00245 {
00246   return this->strain;
00247 }
00248 
00249 const Vector&  
00250 BeamFiberMaterial::getStress()
00251 {
00252   const Vector &threeDstress = theMaterial->getStress();
00253   static Vector threeDstressCopy(6);
00254 
00255   int i, ii;
00256   //swap matrix indices to sort out-of-plane components 
00257   for (i=0; i<6; i++) {
00258 
00259     ii = this->indexMap(i);
00260 
00261     threeDstressCopy(ii) = threeDstress(i);
00262   }
00263 
00264   for (i=0; i<3; i++) 
00265     this->stress(i)     = threeDstressCopy(i);
00266 
00267   return this->stress;
00268 }
00269 
00270 const Matrix&  
00271 BeamFiberMaterial::getTangent()
00272 {
00273   static Matrix dd11(3,3);
00274   static Matrix dd12(3,3);
00275   static Matrix dd21(3,3);
00276   static Matrix dd22(3,3);
00277   static Matrix dd22invdd21(3,3);
00278   static Matrix threeDtangentCopy(6,6);
00279 
00280   const Matrix &threeDtangent = theMaterial->getTangent();
00281 
00282   //swap matrix indices to sort out-of-plane components 
00283   int i, j , ii, jj;
00284   for (i=0; i<6; i++) {
00285 
00286     ii = this->indexMap(i);
00287 
00288     for (j=0; j<6; j++) {
00289       
00290       jj = this->indexMap(j);
00291       
00292       threeDtangentCopy(ii,jj) = threeDtangent(i,j);
00293       
00294     }//end for j
00295        
00296   }//end for i
00297 
00298 
00299   for (i=0; i<3; i++) {
00300     for (j=0; j<3; j++) {
00301       dd11(i,j) = threeDtangentCopy(i,  j );
00302       dd12(i,j) = threeDtangentCopy(i,  j+3);
00303       dd21(i,j) = threeDtangentCopy(i+3,j );
00304       dd22(i,j) = threeDtangentCopy(i+3,j+3);
00305       
00306     }
00307   }
00308 
00309   //int Solve(const Vector &V, Vector &res) const;
00310   //int Solve(const Matrix &M, Matrix &res) const;
00311   //condensation 
00312   dd22.Solve(dd21, dd22invdd21);
00313   this->tangent   = dd11; 
00314   this->tangent  -= (dd12*dd22invdd21);
00315 
00316   return this->tangent;
00317 }
00318 
00319 const Matrix&  
00320 BeamFiberMaterial::getInitialTangent()
00321 {
00322   static Matrix dd11(3,3);
00323   static Matrix dd12(3,3);
00324   static Matrix dd21(3,3);
00325   static Matrix dd22(3,3);
00326   static Matrix dd22invdd21(3,3);
00327   static Matrix threeDtangentCopy(6,6);
00328 
00329   const Matrix &threeDtangent = theMaterial->getInitialTangent();
00330 
00331   //swap matrix indices to sort out-of-plane components 
00332   int i, j , ii, jj;
00333   for (i=0; i<6; i++) {
00334 
00335     ii = this->indexMap(i);
00336 
00337     for (j=0; j<6; j++) {
00338       
00339       jj = this->indexMap(j);
00340       
00341       threeDtangentCopy(ii,jj) = threeDtangent(i,j);
00342       
00343     }//end for j
00344        
00345   }//end for i
00346 
00347 
00348   for (i=0; i<3; i++) {
00349     for (j=0; j<3; j++) {
00350       dd11(i,j) = threeDtangentCopy(i,  j );
00351       dd12(i,j) = threeDtangentCopy(i,  j+3);
00352       dd21(i,j) = threeDtangentCopy(i+3,j );
00353       dd22(i,j) = threeDtangentCopy(i+3,j+3);
00354       
00355     }
00356   }
00357 
00358   //int Solve(const Vector &V, Vector &res) const;
00359   //int Solve(const Matrix &M, Matrix &res) const;
00360   //condensation 
00361   dd22.Solve(dd21, dd22invdd21);
00362   this->tangent   = dd11; 
00363   this->tangent  -= (dd12*dd22invdd21);
00364 
00365   return this->tangent;
00366 }
00367 
00368 //NDmaterial strain order        = 11, 22, 33, 12, 23, 31 
00369 //BeamFiberMaterial strain order = 11, 12, 31, 22, 33, 23
00370 int 
00371 BeamFiberMaterial::indexMap(int i)
00372 {
00373   int ii;
00374 
00375   if (i == 3) 
00376           ii = 1;
00377   else if (i == 5)
00378           ii = 2;
00379   else if (i == 1)
00380           ii = 3;
00381   else if (i == 2)
00382           ii = 4;
00383   else if (i == 4)
00384           ii = 5;
00385   else 
00386           ii = i;
00387 
00388   return ii;
00389 }
00390 
00391 void  
00392 BeamFiberMaterial::Print(OPS_Stream &s, int flag)
00393 {
00394         s << "BeamFiberMaterial, tag: " << this->getTag() << endln;
00395         s << "\tWrapped material: "<< theMaterial->getTag() << endln;
00396 
00397         theMaterial->Print(s, flag);
00398 }
00399 
00400 int 
00401 BeamFiberMaterial::sendSelf(int commitTag, Channel &theChannel) 
00402 {
00403   int res = 0;
00404 
00405   // put tag and assocaited materials class and database tags into an id and send it
00406   static ID idData(3);
00407   idData(0) = this->getTag();
00408   idData(1) = theMaterial->getClassTag();
00409   int matDbTag = theMaterial->getDbTag();
00410   if (matDbTag == 0) {
00411     matDbTag = theChannel.getDbTag();
00412     theMaterial->setDbTag(matDbTag);
00413   }
00414   idData(2) = matDbTag;
00415 
00416   res = theChannel.sendID(this->getDbTag(), commitTag, idData);
00417   if (res < 0) {
00418     opserr << "BeamFiberMaterial::sendSelf() - failed to send id data\n";
00419     return res;
00420   }
00421 
00422   // put the strains in a vector and send it
00423   static Vector vecData(3);
00424   vecData(0) = Cstrain22;
00425   vecData(1) = Cstrain33;
00426   vecData(2) = Cgamma23;
00427 
00428   res = theChannel.sendVector(this->getDbTag(), commitTag, vecData);
00429   if (res < 0) {
00430     opserr << "BeamFiberMaterial::sendSelf() - failed to send vector data\n";
00431     return res;
00432   }
00433 
00434   // now send the materials data
00435   res = theMaterial->sendSelf(commitTag, theChannel);
00436   if (res < 0) 
00437     opserr << "BeamFiberMaterial::sendSelf() - failed to send vector material\n";
00438 
00439   return res;
00440 }
00441 
00442 int 
00443 BeamFiberMaterial::recvSelf(int commitTag, Channel &theChannel, FEM_ObjectBroker &theBroker)
00444 {
00445   int res = 0;
00446 
00447   // recv an id containg the tag and associated materials class and db tags
00448   static ID idData(3);
00449   res = theChannel.sendID(this->getDbTag(), commitTag, idData);
00450   if (res < 0) {
00451     opserr << "BeamFiberMaterial::sendSelf() - failed to send id data\n";
00452     return res;
00453   }
00454 
00455   this->setTag(idData(0));
00456   int matClassTag = idData(1);
00457   
00458   // if the associated material has not yet been created or is of the wrong type
00459   // create a new material for recvSelf later
00460   if (theMaterial == 0 || theMaterial->getClassTag() != matClassTag) {
00461     if (theMaterial != 0)
00462       delete theMaterial;
00463     theMaterial = theBroker.getNewNDMaterial(matClassTag);
00464     if (theMaterial == 0) {
00465       opserr << "BeamFiberMaterial::recvSelf() - failed to get a material of type: " << matClassTag << endln;
00466       return -1;
00467     }
00468   }
00469   theMaterial->setDbTag(idData(2));
00470 
00471   // recv a vector containing strains and set the strains
00472   static Vector vecData(3);
00473   res = theChannel.recvVector(this->getDbTag(), commitTag, vecData);
00474   if (res < 0) {
00475     opserr << "BeamFiberMaterial::sendSelf() - failed to send vector data\n";
00476     return res;
00477   }
00478 
00479   Cstrain22 = vecData(0);
00480   Cstrain33 = vecData(1);
00481   Cgamma23  = vecData(2);
00482 
00483   Tstrain22 = Cstrain22;
00484   Tstrain33 = Cstrain33;
00485   Tgamma23  = Cgamma23;
00486 
00487   // now receive the materials data
00488   res = theMaterial->recvSelf(commitTag, theChannel, theBroker);
00489   if (res < 0) 
00490     opserr << "BeamFiberMaterial::sendSelf() - failed to send vector material\n";
00491   
00492   return res;
00493 }

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