00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018 #ifndef __itkFEMImageMetricLoadImplementation_h
00019 #define __itkFEMImageMetricLoadImplementation_h
00020
00021 #include "itkFEMImageMetricLoad.h"
00022
00023 #include "itkFEMElement2DC0LinearLineStress.h"
00024 #include "itkFEMElement2DC1Beam.h"
00025 #include "itkFEMElement2DC0LinearTriangularStress.h"
00026 #include "itkFEMElement2DC0LinearQuadrilateralMembrane.h"
00027 #include "itkFEMElement2DC0LinearQuadrilateralMembrane.h"
00028 #include "itkFEMElement3DC0LinearTetrahedronStrain.h"
00029 #include "itkFEMElement3DC0LinearHexahedronStrain.h"
00030
00031 namespace itk {
00032 namespace fem {
00033
00034
00035
00036
00053 template<class TLoadClass>
00054 class ImageMetricLoadImplementation
00055 {
00056 public:
00057
00058 template<class TElementClassConstPointer>
00059 static void ImplementImageMetricLoad(TElementClassConstPointer element, Element::LoadPointer load, Element::VectorType& Fe )
00060 {
00061
00062
00063
00064 typename TLoadClass::Pointer l0=dynamic_cast<TLoadClass*>(&*load);
00065 if ( !l0 ) throw FEMException(__FILE__, __LINE__, "FEM error");
00066
00067 Implementation(static_cast<Element::ConstPointer>(element),l0,Fe);
00068 }
00069
00070 private:
00071
00072 static const bool registered;
00073
00074 static void Implementation(typename Element::ConstPointer element, typename TLoadClass::Pointer l0, typename Element::VectorType& Fe)
00075 {
00076 const unsigned int TotalSolutionIndex=1;
00077 typename Solution::ConstPointer S=l0->GetSolution();
00078
00079
00080
00081
00082 unsigned int order=l0->GetNumberOfIntegrationPoints();
00083
00084 const unsigned int Nip=element->GetNumberOfIntegrationPoints(order);
00085 const unsigned int Ndofs=element->GetNumberOfDegreesOfFreedomPerNode();
00086 const unsigned int Nnodes=element->GetNumberOfNodes();
00087 unsigned int ImageDimension=Ndofs;
00088
00089 Element::VectorType force(Ndofs,0.0),
00090 ip,gip,gsol,force_tmp,shapef;
00091 Element::Float w,detJ;
00092
00093 Fe.set_size(element->GetNumberOfDegreesOfFreedom());
00094 Fe.fill(0.0);
00095 shapef.set_size(Nnodes);
00096 gsol.set_size(Ndofs);
00097 gip.set_size(Ndofs);
00098
00099 for(unsigned int i=0; i<Nip; i++)
00100 {
00101 element->GetIntegrationPointAndWeight(i,ip,w,order);
00102
00103
00104
00105
00106
00107
00108 if (ImageDimension == 3){
00109 #define FASTHEX
00110 #ifdef FASTHEX
00111 float r=ip[0]; float s=ip[1]; float t=ip[2];
00112
00113 shapef[0] = (1 - r) * (1 - s) * (1 - t) * 0.125;
00114 shapef[1] = (1 + r) * (1 - s) * (1 - t) * 0.125;
00115 shapef[2] = (1 + r) * (1 + s) * (1 - t) * 0.125;
00116 shapef[3] = (1 - r) * (1 + s) * (1 - t) * 0.125;
00117 shapef[4] = (1 - r) * (1 - s) * (1 + t) * 0.125;
00118 shapef[5] = (1 + r) * (1 - s) * (1 + t) * 0.125;
00119 shapef[6] = (1 + r) * (1 + s) * (1 + t) * 0.125;
00120 shapef[7] = (1 - r) * (1 + s) * (1 + t) * 0.125;
00121 #else
00122 shapef = element->ShapeFunctions(ip);
00123 #endif
00124 }else if (ImageDimension==2) shapef = element->ShapeFunctions(ip);
00125
00126 float solval,posval;
00127 detJ=element->JacobianDeterminant(ip);
00128
00129 for(unsigned int f=0; f<ImageDimension; f++)
00130 {
00131 solval=0.0;
00132 posval=0.0;
00133 for(unsigned int n=0; n<Nnodes; n++)
00134 {
00135 posval+=shapef[n]*((element->GetNodeCoordinates(n))[f]);
00136 solval+=shapef[n] * S->GetSolutionValue( element->GetNode(n)->GetDegreeOfFreedom(f) , TotalSolutionIndex);
00137 }
00138 gsol[f]=solval;
00139 gip[f]=posval;
00140 }
00141
00142
00143
00144
00145
00146 force.fill(0.0);
00147
00148 force=l0->Fe(gip,gsol);
00149
00150 for(unsigned int n=0; n<Nnodes; n++)
00151 {
00152 for(unsigned int d=0; d<Ndofs; d++)
00153 {
00154 itk::fem::Element::Float temp=shapef[n]*force[d]*w*detJ;
00155 Fe[n*Ndofs+d]+=temp;
00156 }
00157 }
00158
00159 }
00160
00161 }
00162
00163 };
00164
00165
00166 template<class TLoadClass>
00167 const bool ImageMetricLoadImplementation<TLoadClass>::registered = false;
00168
00169
00170
00171
00172
00173
00174
00175
00176
00177
00178
00179
00180
00181
00182
00183 }}
00184
00185 #endif // #ifndef __itkFEMImageMetricLoadImplementation_h