FiberSectionGJ.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.6 $
00022 // $Date: 2006/09/05 23:29:17 $
00023 // $Source: /usr/local/cvs/OpenSees/SRC/material/section/FiberSectionGJ.cpp,v $
00024                                                                         
00025 // Written: fmk
00026 // Created: 04/04
00027 //
00028 // Description: This file contains the class implementation of FiberSection2d.
00029 
00030 #include <stdlib.h>
00031 
00032 #include <Channel.h>
00033 #include <Vector.h>
00034 #include <Matrix.h>
00035 #include <MatrixUtil.h>
00036 #include <Fiber.h>
00037 #include <classTags.h>
00038 #include <FiberSectionGJ.h>
00039 #include <ID.h>
00040 #include <FEM_ObjectBroker.h>
00041 #include <Information.h>
00042 #include <MaterialResponse.h>
00043 #include <UniaxialMaterial.h>
00044 
00045 ID FiberSectionGJ::code(4);
00046 Vector FiberSectionGJ::s(4);
00047 Matrix FiberSectionGJ::ks(4,4);
00048 
00049 // constructors:
00050 FiberSectionGJ::FiberSectionGJ(int tag, int num, Fiber **fibers, double gj): 
00051   SectionForceDeformation(tag, SEC_TAG_FiberSectionGJ),
00052   numFibers(num), theMaterials(0), matData(0),
00053   yBar(0.0), zBar(0.0), e(4), eCommit(4), GJ(gj)
00054 {
00055   if (numFibers != 0) {
00056     theMaterials = new UniaxialMaterial *[numFibers];
00057 
00058     if (theMaterials == 0) {
00059       opserr << "FiberSectionGJ::FiberSectionGJ -- failed to allocate Material pointers\n";
00060       exit(-1);
00061     }
00062 
00063     matData = new double [numFibers*3];
00064 
00065     if (matData == 0) {
00066       opserr << "FiberSectionGJ::FiberSectionGJ -- failed to allocate double array for material data\n";
00067       exit(-1);
00068     }
00069     double Qz = 0.0;
00070     double Qy = 0.0;
00071     double A  = 0.0;
00072     
00073     for (int i = 0; i < numFibers; i++) {
00074       Fiber *theFiber = fibers[i];
00075       double yLoc, zLoc, Area;
00076       theFiber->getFiberLocation(yLoc, zLoc);
00077       Area = theFiber->getArea();
00078 
00079       Qz += yLoc*Area;
00080       Qy += zLoc*Area;
00081       A  += Area;
00082 
00083       matData[i*3] = -yLoc;
00084       matData[i*3+1] = zLoc;
00085       matData[i*3+2] = Area;
00086       UniaxialMaterial *theMat = theFiber->getMaterial();
00087       theMaterials[i] = theMat->getCopy();
00088 
00089       if (theMaterials[i] == 0) {
00090         opserr << "FiberSectionGJ::FiberSectionGJ -- failed to get copy of a Material\n";
00091         exit(-1);
00092       }
00093     }
00094 
00095     yBar = -Qz/A;
00096     zBar = Qy/A;
00097   }
00098 
00099   sData[0] = 0.0;
00100   sData[1] = 0.0;
00101   sData[2] = 0.0;
00102 
00103   for (int i=0; i<6; i++)
00104     kData[i] = 0.0;
00105 
00106   code(0) = SECTION_RESPONSE_P;
00107   code(1) = SECTION_RESPONSE_MZ;
00108   code(2) = SECTION_RESPONSE_MY;
00109   code(3) = SECTION_RESPONSE_T;
00110 }
00111 
00112 // constructor for blank object that recvSelf needs to be invoked upon
00113 FiberSectionGJ::FiberSectionGJ():
00114   SectionForceDeformation(0, SEC_TAG_FiberSectionGJ),
00115   numFibers(0), theMaterials(0), matData(0),
00116   yBar(0.0), zBar(0.0), e(4), eCommit(4), GJ(1.0)
00117 {
00118   sData[0] = 0.0;
00119   sData[1] = 0.0;
00120   sData[2] = 0.0;
00121 
00122   for (int i=0; i<6; i++)
00123     kData[i] = 0.0;
00124 
00125   code(0) = SECTION_RESPONSE_P;
00126   code(1) = SECTION_RESPONSE_MZ;
00127   code(2) = SECTION_RESPONSE_MY;
00128   code(3) = SECTION_RESPONSE_T;
00129 }
00130 
00131 int
00132 FiberSectionGJ::addFiber(Fiber &newFiber)
00133 {
00134   // need to create a larger array
00135   int newSize = numFibers+1;
00136 
00137   UniaxialMaterial **newArray = new UniaxialMaterial *[newSize]; 
00138   double *newMatData = new double [3 * newSize];
00139   
00140   if (newArray == 0 || newMatData == 0) {
00141     opserr << "FiberSectionGJ::addFiber -- failed to allocate Fiber pointers\n";
00142     return -1;
00143   }
00144 
00145   // copy the old pointers
00146   int i;
00147   for (i = 0; i < numFibers; i++) {
00148     newArray[i] = theMaterials[i];
00149     newMatData[3*i] = matData[3*i];
00150     newMatData[3*i+1] = matData[3*i+1];
00151     newMatData[3*i+2] = matData[3*i+2];
00152   }
00153   // set the new pointers
00154   double yLoc, zLoc, Area;
00155   newFiber.getFiberLocation(yLoc, zLoc);
00156   Area = newFiber.getArea();
00157   newMatData[numFibers*3] = -yLoc;
00158   newMatData[numFibers*3+1] = zLoc;
00159   newMatData[numFibers*3+2] = Area;
00160   UniaxialMaterial *theMat = newFiber.getMaterial();
00161   newArray[numFibers] = theMat->getCopy();
00162 
00163   if (newArray[numFibers] == 0) {
00164     opserr << "FiberSectionGJ::addFiber -- failed to get copy of a Material\n";
00165                           
00166 
00167     delete [] newArray;
00168     delete [] newMatData;
00169     return -1;
00170   }
00171 
00172   numFibers++;
00173   
00174   if (theMaterials != 0) {
00175     delete [] theMaterials;
00176     delete [] matData;
00177   }
00178 
00179   theMaterials = newArray;
00180   matData = newMatData;
00181 
00182   double Qz = 0.0;
00183   double Qy = 0.0;
00184   double A  = 0.0;
00185 
00186   // Recompute centroid
00187   for (i = 0; i < numFibers; i++) {
00188     yLoc = -matData[2*i];
00189     zLoc = matData[2*i+1];
00190     Area = matData[2*i+2];
00191     A  += Area;
00192     Qz += yLoc*Area;
00193     Qy += zLoc*Area;
00194   }
00195 
00196   yBar = -Qz/A;
00197   zBar = Qy/A;
00198 
00199   return 0;
00200 }
00201 
00202 
00203 
00204 // destructor:
00205 FiberSectionGJ::~FiberSectionGJ()
00206 {
00207   if (theMaterials != 0) {
00208     for (int i = 0; i < numFibers; i++)
00209       if (theMaterials[i] != 0)
00210         delete theMaterials[i];
00211       
00212     delete [] theMaterials;
00213   }
00214 
00215   if (matData != 0)
00216     delete [] matData;
00217 }
00218 
00219 int
00220 FiberSectionGJ::setTrialSectionDeformation (const Vector &deforms)
00221 {
00222   int res = 0;
00223   e = deforms;
00224 
00225   kData[0] = 0.0; kData[1] = 0.0; kData[2] = 0.0;
00226   kData[3] = 0.0; kData[4] = 0.0; kData[5] = 0.0; 
00227 
00228   sData[0] = 0.0; sData[1] = 0.0; sData[2] = 0.0; 
00229 
00230   int loc = 0;
00231 
00232   double d0 = deforms(0);
00233   double d1 = deforms(1);
00234   double d2 = deforms(2);
00235 
00236   for (int i = 0; i < numFibers; i++) {
00237     UniaxialMaterial *theMat = theMaterials[i];
00238     double y = matData[loc++] - yBar;
00239     double z = matData[loc++] - zBar;
00240     double A = matData[loc++];
00241 
00242     // determine material strain and set it
00243     double strain = d0 + y*d1 + z*d2;
00244     double tangent, stress;
00245     res = theMat->setTrial(strain, stress, tangent);
00246 
00247     double value = tangent * A;
00248     double vas1 = y*value;
00249     double vas2 = z*value;
00250     double vas1as2 = vas1*z;
00251 
00252     kData[0] += value;
00253     kData[1] += vas1;
00254     kData[2] += vas2;
00255     
00256     kData[3] += vas1 * y;
00257     kData[4] += vas1as2;
00258     
00259     kData[5] += vas2 * z; 
00260 
00261     double fs0 = stress * A;
00262     sData[0] += fs0;
00263     sData[1] += fs0 * y;
00264     sData[2] += fs0 * z;
00265   }
00266 
00267   return res;
00268 }
00269 
00270 const Matrix&
00271 FiberSectionGJ::getInitialTangent(void)
00272 {
00273   kData[0] = 0.0; kData[1] = 0.0; kData[2] = 0.0;
00274   kData[3] = 0.0; kData[4] = 0.0; kData[5] = 0.0;
00275 
00276   int loc = 0;
00277 
00278   for (int i = 0; i < numFibers; i++) {
00279     UniaxialMaterial *theMat = theMaterials[i];
00280     double y = matData[loc++] - yBar;
00281     double z = matData[loc++] - zBar;
00282     double A = matData[loc++];
00283 
00284     double tangent = theMat->getInitialTangent();
00285 
00286     double value = tangent * A;
00287     double vas1 = y*value;
00288     double vas2 = z*value;
00289     double vas1as2 = vas1*z;
00290 
00291     kData[0] += value;
00292     kData[1] += vas1;
00293     kData[2] += vas2;
00294     
00295     kData[3] += vas1 * y;
00296     kData[4] += vas1as2;
00297     
00298     kData[5] += vas2 * z; 
00299   }
00300 
00301   ks(0,0) = kData[0];
00302   ks(0,1) = ks(1,0) = kData[1];
00303   ks(0,2) = ks(2,0) = kData[2];
00304   ks(1,1) = kData[3];
00305   ks(1,2) = ks(2,1) = kData[4];
00306   ks(2,2) = kData[5];
00307 
00308   ks(3,3) = GJ;
00309 
00310   return ks;
00311 }
00312 
00313 const Vector&
00314 FiberSectionGJ::getSectionDeformation(void)
00315 {
00316   return e;
00317 }
00318 
00319 const Matrix&
00320 FiberSectionGJ::getSectionTangent(void)
00321 {
00322   ks(0,0) = kData[0];
00323   ks(0,1) = ks(1,0) = kData[1];
00324   ks(0,2) = ks(2,0) = kData[2];
00325   ks(1,1) = kData[3];
00326   ks(1,2) = ks(2,1) = kData[4];
00327   ks(2,2) = kData[5];
00328 
00329   ks(3,3) = GJ;
00330 
00331   return ks;
00332 }
00333 
00334 const Vector&
00335 FiberSectionGJ::getStressResultant(void)
00336 {
00337   s(0) = sData[0];
00338   s(1) = sData[1];
00339   s(2) = sData[2];
00340 
00341   s(3) = GJ*e(3);
00342 
00343   return s;
00344 }
00345 
00346 SectionForceDeformation*
00347 FiberSectionGJ::getCopy(void)
00348 {
00349   FiberSectionGJ *theCopy = new FiberSectionGJ();
00350   theCopy->setTag(this->getTag());
00351 
00352   theCopy->numFibers = numFibers;
00353 
00354   if (numFibers != 0) {
00355     theCopy->theMaterials = new UniaxialMaterial *[numFibers];
00356 
00357     if (theCopy->theMaterials == 0) {
00358       opserr << "FiberSectionGJ::FiberSectionGJ -- failed to allocate Material pointers\n";
00359       exit(-1);
00360     }
00361 
00362     theCopy->matData = new double [numFibers*3];
00363 
00364     if (theCopy->matData == 0) {
00365       opserr << "FiberSectionGJ::FiberSectionGJ -- failed to allocate double array for material data\n";
00366       exit(-1);
00367     }    
00368     for (int i = 0; i < numFibers; i++) {
00369       theCopy->matData[i*3] = matData[i*3];
00370       theCopy->matData[i*3+1] = matData[i*3+1];
00371       theCopy->matData[i*3+2] = matData[i*3+2];
00372       theCopy->theMaterials[i] = theMaterials[i]->getCopy();
00373 
00374       if (theCopy->theMaterials[i] == 0) {
00375         opserr << "FiberSectionGJ::getCopy -- failed to get copy of a Material\n";
00376         exit(-1);
00377       }
00378     }    
00379   }
00380 
00381   theCopy->eCommit = eCommit;
00382   theCopy->e = e;
00383   theCopy->yBar = yBar;
00384   theCopy->zBar = zBar;
00385 
00386   for (int i=0; i<6; i++)
00387     theCopy->kData[i] = kData[i];
00388 
00389   theCopy->sData[0] = sData[0];
00390   theCopy->sData[1] = sData[1];
00391   theCopy->sData[2] = sData[2];
00392 
00393   theCopy->GJ = GJ;
00394 
00395   return theCopy;
00396 }
00397 
00398 const ID&
00399 FiberSectionGJ::getType ()
00400 {
00401   return code;
00402 }
00403 
00404 int
00405 FiberSectionGJ::getOrder () const
00406 {
00407   return 4;
00408 }
00409 
00410 int
00411 FiberSectionGJ::commitState(void)
00412 {
00413   int err = 0;
00414 
00415   for (int i = 0; i < numFibers; i++)
00416     err += theMaterials[i]->commitState();
00417 
00418   eCommit = e;
00419 
00420   return err;
00421 }
00422 
00423 int
00424 FiberSectionGJ::revertToLastCommit(void)
00425 {
00426   int err = 0;
00427 
00428   // Last committed section deformations
00429   e = eCommit;
00430 
00431   kData[0] = 0.0; kData[1] = 0.0; kData[2] = 0.0;
00432   kData[3] = 0.0; kData[4] = 0.0; kData[5] = 0.0;
00433 
00434   sData[0] = 0.0; sData[1] = 0.0; sData[2] = 0.0; 
00435 
00436   int loc = 0;
00437 
00438   for (int i = 0; i < numFibers; i++) {
00439     UniaxialMaterial *theMat = theMaterials[i];
00440     double y = matData[loc++] - yBar;
00441     double z = matData[loc++] - zBar;
00442     double A = matData[loc++];
00443 
00444     // invoke revertToLast on the material
00445     err += theMat->revertToLastCommit();
00446 
00447     double tangent = theMat->getTangent();
00448     double stress = theMat->getStress();
00449 
00450     double value = tangent * A;
00451     double vas1 = y*value;
00452     double vas2 = z*value;
00453     double vas1as2 = vas1*z;
00454 
00455     kData[0] += value;
00456     kData[1] += vas1;
00457     kData[2] += vas2;
00458     
00459     kData[3] += vas1 * y;
00460     kData[4] += vas1as2;
00461     
00462     kData[5] += vas2 * z; 
00463 
00464     double fs0 = stress * A;
00465     sData[0] += fs0;
00466     sData[1] += fs0 * y;
00467     sData[2] += fs0 * z;
00468   }
00469 
00470   return err;
00471 }
00472 
00473 int
00474 FiberSectionGJ::revertToStart(void)
00475 {
00476   // revert the fibers to start    
00477   int err = 0;
00478 
00479   kData[0] = 0.0; kData[1] = 0.0; kData[2] = 0.0;
00480   kData[3] = 0.0; kData[4] = 0.0; kData[5] = 0.0;
00481 
00482   sData[0] = 0.0; sData[1] = 0.0; sData[2] = 0.0; 
00483 
00484   int loc = 0;
00485 
00486   for (int i = 0; i < numFibers; i++) {
00487     UniaxialMaterial *theMat = theMaterials[i];
00488     double y = matData[loc++] - yBar;
00489     double z = matData[loc++] - zBar;
00490     double A = matData[loc++];
00491 
00492     // invoke revertToStart on the material
00493     err += theMat->revertToStart();
00494 
00495     double tangent = theMat->getTangent();
00496     double stress = theMat->getStress();
00497 
00498     double value = tangent * A;
00499     double vas1 = y*value;
00500     double vas2 = z*value;
00501     double vas1as2 = vas1*z;
00502 
00503     kData[0] += value;
00504     kData[1] += vas1;
00505     kData[2] += vas2;
00506     
00507     kData[3] += vas1 * y;
00508     kData[4] += vas1as2;
00509     
00510     kData[5] += vas2 * z; 
00511 
00512     double fs0 = stress * A;
00513     sData[0] += fs0;
00514     sData[1] += fs0 * y;
00515     sData[2] += fs0 * z;
00516   }
00517 
00518   return err;
00519 }
00520 
00521 int
00522 FiberSectionGJ::sendSelf(int commitTag, Channel &theChannel)
00523 {
00524   int res = 0;
00525 
00526   // create an id to send objects tag and numFibers, 
00527   //     size 4 so no conflict with fiberData below if just 1 fiber
00528   static Vector data(4);
00529   data(0) = this->getTag();
00530   data(1) = numFibers;
00531   data(2) = GJ;
00532   int dbTag = this->getDbTag();
00533   res += theChannel.sendVector(dbTag, commitTag, data);
00534   if (res < 0) {
00535     opserr << "FiberSection2d::sendSelf - failed to send ID data\n";
00536     return res;
00537   }    
00538 
00539   if (numFibers != 0) {
00540     
00541     // create an id containingg classTag and dbTag for each material & send it
00542     ID materialData(2*numFibers);
00543     for (int i=0; i<numFibers; i++) {
00544       UniaxialMaterial *theMat = theMaterials[i];
00545       materialData(2*i) = theMat->getClassTag();
00546       int matDbTag = theMat->getDbTag();
00547       if (matDbTag == 0) {
00548         matDbTag = theChannel.getDbTag();
00549         if (matDbTag != 0)
00550           theMat->setDbTag(matDbTag);
00551       }
00552       materialData(2*i+1) = matDbTag;
00553     }    
00554     
00555     res += theChannel.sendID(dbTag, commitTag, materialData);
00556     if (res < 0) {
00557       opserr << "FiberSection2d::sendSelf- failed to send material data\n";
00558       return res;
00559     }    
00560 
00561     // send the fiber data, i.e. area and loc
00562     Vector fiberData(matData, 3*numFibers);
00563     res += theChannel.sendVector(dbTag, commitTag, fiberData);
00564     if (res < 0) {
00565       opserr << "FiberSection2d::sendSelf - failed to send material data\n";
00566       return res;
00567     }    
00568 
00569     // now invoke send(0 on all the materials
00570     for (int j=0; j<numFibers; j++)
00571       theMaterials[j]->sendSelf(commitTag, theChannel);
00572   }
00573 
00574   return res;
00575 }
00576 
00577 int
00578 FiberSectionGJ::recvSelf(int commitTag, Channel &theChannel,
00579                          FEM_ObjectBroker &theBroker)
00580 {
00581   int res = 0;
00582 
00583   static Vector data(4);
00584   
00585   int dbTag = this->getDbTag();
00586   res += theChannel.recvVector(dbTag, commitTag, data);
00587   if (res < 0) {
00588     opserr << "FiberSection2d::recvSelf - failed to recv ID data\n";
00589     return res;
00590   }    
00591   this->setTag((int)data(0));
00592   GJ = data(2);
00593 
00594   // recv data about materials objects, classTag and dbTag
00595   numFibers = (int)data(1);
00596   if (numFibers != 0) {
00597     ID materialData(2*numFibers);
00598     res += theChannel.recvID(dbTag, commitTag, materialData);
00599     if (res < 0) {
00600       opserr << "FiberSection2d::recvSelf - failed to send material data\n";
00601       return res;
00602     }    
00603 
00604     // if current arrays not of correct size, release old and resize
00605     if (theMaterials == 0 || numFibers != data(1)) {
00606       // delete old stuff if outa date
00607       if (theMaterials != 0) {
00608         for (int i=0; i<numFibers; i++)
00609           delete theMaterials[i];
00610         delete [] theMaterials;
00611         if (matData != 0)
00612           delete [] matData;
00613         matData = 0;
00614         theMaterials = 0;
00615       }
00616 
00617       // create memory to hold material pointers and fiber data
00618       if (numFibers != 0) {
00619 
00620         theMaterials = new UniaxialMaterial *[numFibers];
00621         
00622         if (theMaterials == 0) {
00623           opserr << "FiberSection2d::recvSelf -- failed to allocate Material pointers\n";
00624           exit(-1);
00625         }
00626                                 
00627         
00628         for (int j=0; j<numFibers; j++)
00629           theMaterials[j] = 0;
00630 
00631         matData = new double [numFibers*3];
00632 
00633         if (matData == 0) {
00634           opserr << "FiberSection2d::recvSelf -- failed to allocate double array for material data\n";
00635           exit(-1);
00636         }
00637       }
00638     }
00639 
00640     Vector fiberData(matData, 3*numFibers);
00641     res += theChannel.recvVector(dbTag, commitTag, fiberData);
00642     if (res < 0) {
00643       opserr << "FiberSection2d::recvSelf - failed to send material data\n";
00644 
00645       return res;
00646     }    
00647 
00648     int i;
00649     for (i=0; i<numFibers; i++) {
00650       int classTag = materialData(2*i);
00651       int dbTag = materialData(2*i+1);
00652 
00653       // if material pointed to is blank or not of corrcet type, 
00654       // release old and create a new one
00655       if (theMaterials[i] == 0)
00656         theMaterials[i] = theBroker.getNewUniaxialMaterial(classTag);
00657       else if (theMaterials[i]->getClassTag() != classTag) {
00658         delete theMaterials[i];
00659         theMaterials[i] = theBroker.getNewUniaxialMaterial(classTag);      
00660       }
00661 
00662       if (theMaterials[i] == 0) {
00663         opserr << "FiberSection2d::recvSelf -- failed to allocate double array for material data\n";
00664         exit(-1);
00665       }
00666                               
00667       theMaterials[i]->setDbTag(dbTag);
00668       res += theMaterials[i]->recvSelf(commitTag, theChannel, theBroker);
00669     }
00670 
00671     double Qz = 0.0;
00672     double Qy = 0.0;
00673     double A  = 0.0;
00674     double yLoc, zLoc, Area;
00675 
00676     // Recompute centroid
00677     for (i = 0; i < numFibers; i++) {
00678       yLoc = -matData[2*i];
00679       zLoc = matData[2*i+1];
00680       Area = matData[2*i+2];
00681       A  += Area;
00682       Qz += yLoc*Area;
00683       Qy += zLoc*Area;
00684     }
00685     
00686     yBar = -Qz/A;
00687     zBar = Qy/A;
00688   }    
00689 
00690   return res;
00691 }
00692 
00693 void
00694 FiberSectionGJ::Print(OPS_Stream &s, int flag)
00695 {
00696   s << "\nFiberSectionGJ, tag: " << this->getTag() << endln;
00697   s << "\tSection code: " << code;
00698   s << "\tNumber of Fibers: " << numFibers << endln;
00699   s << "\tCentroid: (" << -yBar << ", " << zBar << ')' << endln;
00700   s << "\tTorsional Stiffness: " << GJ << endln;
00701 
00702   if (flag == 1) {
00703     int loc = 0;
00704     for (int i = 0; i < numFibers; i++) {
00705       s << "\nLocation (y, z) = (" << -matData[loc++] << ", " << matData[loc++] << ")";
00706       s << "\nArea = " << matData[loc++] << endln;
00707       theMaterials[i]->Print(s, flag);
00708     }
00709   }
00710 }
00711 
00712 Response*
00713 FiberSectionGJ::setResponse(const char **argv, int argc, Information &sectInfo, OPS_Stream &output)
00714 {
00715 
00716   // See if the response is one of the defaults
00717   Response *theResponse = SectionForceDeformation::setResponse(argv, argc, sectInfo, output);
00718   if (theResponse != 0)
00719     return theResponse;
00720 
00721 
00722   if (argc <=2 || strcmp(argv[0],"fiber") != 0)
00723     return 0;
00724 
00725   int key = numFibers;
00726   int passarg = 2;
00727   
00728   
00729   if (argc <= 3)        {  // fiber number was input directly
00730 
00731     key = atoi(argv[1]);
00732 
00733   } else if (argc > 4) {         // find fiber closest to coord. with mat tag
00734     int matTag = atoi(argv[3]);
00735     double yCoord = atof(argv[1]);
00736     double zCoord = atof(argv[2]);
00737     double closestDist;
00738     double ySearch, zSearch, dy, dz;
00739     double distance;
00740     int j;
00741 
00742     // Find first fiber with specified material tag
00743     for (j = 0; j < numFibers; j++) {
00744       if (matTag == theMaterials[j]->getTag()) {
00745         ySearch = -matData[3*j];
00746         zSearch =  matData[3*j+1];
00747         dy = ySearch-yCoord;
00748         dz = zSearch-zCoord;
00749         closestDist = sqrt(dy*dy + dz*dz);
00750         key = j;
00751         break;
00752       }
00753     }
00754 
00755     // Search the remaining fibers
00756     for ( ; j < numFibers; j++) {
00757       if (matTag == theMaterials[j]->getTag()) {
00758         ySearch = -matData[3*j];
00759         zSearch =  matData[3*j+1];
00760         dy = ySearch-yCoord;
00761         dz = zSearch-zCoord;
00762         distance = sqrt(dy*dy + dz*dz);
00763         if (distance < closestDist) {
00764           closestDist = distance;
00765           key = j;
00766         }
00767       }
00768     }
00769     passarg = 4;
00770   }
00771   
00772   else {                  // fiber near-to coordinate specified
00773     double yCoord = atof(argv[1]);
00774     double zCoord = atof(argv[2]);
00775     double closestDist;
00776     double ySearch, zSearch, dy, dz;
00777     double distance;
00778     ySearch = -matData[0];
00779     zSearch =  matData[1];
00780     dy = ySearch-yCoord;
00781     dz = zSearch-zCoord;
00782     closestDist = sqrt(dy*dy + dz*dz);
00783     key = 0;
00784     for (int j = 1; j < numFibers; j++) {
00785       ySearch = -matData[3*j];
00786       zSearch =  matData[3*j+1];
00787       dy = ySearch-yCoord;
00788       dz = zSearch-zCoord;
00789       distance = sqrt(dy*dy + dz*dz);
00790       if (distance < closestDist) {
00791         closestDist = distance;
00792         key = j;
00793       }
00794     }
00795     passarg = 3;
00796   }
00797 
00798   if (key < numFibers && key >= 0) {
00799     output.tag("FiberOutput");
00800     output.attr("yLoc",-matData[2*key]);
00801     output.attr("zLoc",matData[2*key+1]);
00802     output.attr("area",matData[2*key+2]);
00803     
00804     theResponse =  theMaterials[key]->setResponse(&argv[passarg], argc-passarg, sectInfo, output);
00805 
00806     output.endTag();
00807   }
00808   
00809   return theResponse;
00810 }
00811 
00812 
00813 int 
00814 FiberSectionGJ::getResponse(int responseID, Information &sectInfo)
00815 {
00816   // Just call the base class method ... don't need to define
00817   // this function, but keeping it here just for clarity
00818   return SectionForceDeformation::getResponse(responseID, sectInfo);
00819 }
00820 
00821 int
00822 FiberSectionGJ::setParameter (const char **argv, int argc, Parameter &param)
00823 {
00824   if (argc < 3)
00825     return 0;
00826 
00827   // A material parameter
00828   if (strstr(argv[0],"material") != 0) {
00829 
00830     // Get the tag of the material
00831     int paramMatTag = atoi(argv[1]);
00832 
00833     // Loop over fibers to find the right material(s)
00834     int ok = 0;
00835     for (int i = 0; i < numFibers; i++) 
00836       if (paramMatTag == theMaterials[i]->getTag())
00837         ok += theMaterials[i]->setParameter(&argv[2], argc-2, param);
00838 
00839     return ok;
00840   }
00841 
00842   else
00843     return -1;
00844 }

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