EdgePressureForceField.h
Go to the documentation of this file.00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025 #ifndef SOFA_COMPONENT_FORCEFIELD_EDGEPRESSUREFORCEFIELD_H
00026 #define SOFA_COMPONENT_FORCEFIELD_EDGEPRESSUREFORCEFIELD_H
00027
00028
00029 #include <sofa/core/componentmodel/behavior/ForceField.h>
00030 #include <sofa/component/topology/EdgeSubsetData.h>
00031 #include <sofa/component/topology/EdgeSetGeometryAlgorithms.h>
00032
00033
00034 namespace sofa
00035 {
00036
00037 namespace component
00038 {
00039
00040 namespace forcefield
00041 {
00042
00043 using namespace sofa::defaulttype;
00044 using namespace sofa::component::topology;
00045
00046 template<class DataTypes>
00047 class EdgePressureForceField : public core::componentmodel::behavior::ForceField<DataTypes>, public virtual core::objectmodel::BaseObject
00048 {
00049 public:
00050 typedef typename DataTypes::VecCoord VecCoord;
00051 typedef typename DataTypes::VecDeriv VecDeriv;
00052 typedef typename DataTypes::Coord Coord ;
00053 typedef typename DataTypes::Deriv Deriv ;
00054 typedef typename Coord::value_type Real ;
00055
00056 protected:
00057
00058 class EdgePressureInformation
00059 {
00060 public:
00061 Real length;
00062 Deriv force;
00063
00064 EdgePressureInformation() {}
00065 EdgePressureInformation(const EdgePressureInformation &e)
00066 : length(e.length),force(e.force)
00067 { }
00068 };
00069
00070 EdgeSubsetData<EdgePressureInformation> edgePressureMap;
00071
00072 sofa::core::componentmodel::topology::BaseMeshTopology* _topology;
00073 sofa::component::topology::EdgeSetGeometryAlgorithms<DataTypes>* edgeGeo;
00074
00075 Data<Deriv> pressure;
00076
00077 Data<std::string> edgeList;
00078
00080 Data<Deriv> normal;
00081
00082 Data<Real> dmin;
00083 Data<Real> dmax;
00084
00085 public:
00086
00087 EdgePressureForceField():
00088 pressure(initData(&pressure, "pressure", "Pressure force per unit area"))
00089 , edgeList(initData(&edgeList,std::string(""),"edgeList", "Indices of edges separated with commas where a pressure is applied"))
00090 , normal(initData(&normal,"normal", "Normal direction for the plane selection of edges"))
00091 , dmin(initData(&dmin,(Real)0.0, "dmin", "Minimum distance from the origin along the normal direction"))
00092 , dmax(initData(&dmax,(Real)0.0, "dmax", "Maximum distance from the origin along the normal direction"))
00093 {
00094 }
00095
00096 virtual ~EdgePressureForceField();
00097
00098 virtual void init();
00099
00100 virtual void addForce (VecDeriv& f, const VecCoord& x, const VecDeriv& v);
00101 virtual void addDForce (VecDeriv& , const VecDeriv& ) {}
00102 virtual double getPotentialEnergy(const VecCoord& x);
00103
00104
00105 virtual void handleTopologyChange();
00106
00107 void draw();
00108
00109 void setDminAndDmax(const double _dmin, const double _dmax) {
00110 dmin.setValue((Real)_dmin);dmax.setValue((Real)_dmax);}
00111 void setNormal(const Coord n) { normal.setValue(n);}
00112 void setPressure(Deriv _pressure) { this->pressure = _pressure; updateEdgeInformation(); }
00113
00114 protected :
00115 void selectEdgesAlongPlane();
00116 void selectEdgesFromString();
00117 void updateEdgeInformation();
00118 void initEdgeInformation();
00119 bool isPointInPlane(Coord p) {
00120 Real d=dot(p,normal.getValue());
00121 if ((d>dmin.getValue())&& (d<dmax.getValue()))
00122 return true;
00123 else
00124 return false;
00125 }
00126 };
00127
00128
00129 }
00130
00131 }
00132
00133 }
00134
00135 #endif