25 :m_softBodySolver(0),m_worldInfo(worldInfo)
40 for(
int i=0,ni=node_count;i<ni;++i)
56 :m_worldInfo(worldInfo)
139 const Node* n[]={node0,node1};
143 if( (l.
m_n[0]==n[0]&&l.
m_n[1]==n[1])||
144 (l.
m_n[0]==n[1]&&l.
m_n[1]==n[0]))
164 if( (f.
m_n[j]==n[0])||
166 (f.
m_n[j]==n[2])) c|=1<<j;
else break;
168 if(c==7)
return(
true);
285 if((!bcheckexist)||(!
checkLink(node0,node1)))
364 appendAnchor(node,body,local,disableCollisionBetweenLinkedBodies,influence);
370 if (disableCollisionBetweenLinkedBodies)
465 const bool as_lift = kLF>0;
466 const bool as_drag = kDG>0;
467 const bool as_aero = as_lift || as_drag;
499 btScalar tri_area = 0.5f * n.m_area;
501 fDrag = 0.5f * kDG * medium.
m_density * rel_v2 * tri_area * n_dot_v * (-rel_v_nrm);
505 if ( 0 < n_dot_v && n_dot_v < 0.98480f)
506 fLift = 0.5f * kLF * medium.
m_density * rel_v_len * tri_area *
btSqrt(1.0f-n_dot_v*n_dot_v) * (nrm.
cross(rel_v_nrm).
cross(rel_v_nrm));
510 btScalar del_v_by_fDrag_len2 = del_v_by_fDrag.length2();
513 if (del_v_by_fDrag_len2 >= v_len2 && del_v_by_fDrag_len2 > 0)
515 btScalar del_v_by_fDrag_len = del_v_by_fDrag.length();
517 fDrag *=
btScalar(0.8)*(v_len / del_v_by_fDrag_len);
533 const btScalar c0 = n.m_area * dvn * rel_v2/2;
535 force += nrm*(-c1*kLF);
552 const bool as_lift = kLF>0;
553 const bool as_drag = kDG>0;
554 const bool as_aero = as_lift || as_drag;
587 fDrag = 0.5f * kDG * medium.
m_density * rel_v2 * tri_area * n_dot_v * (-rel_v_nrm);
591 if ( 0 < n_dot_v && n_dot_v < 0.98480f)
592 fLift = 0.5f * kLF * medium.
m_density * rel_v_len * tri_area *
btSqrt(1.0f-n_dot_v*n_dot_v) * (nrm.
cross(rel_v_nrm).
cross(rel_v_nrm));
606 if (del_v_by_fDrag_len2 >= v_len2 && del_v_by_fDrag_len2 > 0)
610 fDrag *=
btScalar(0.8)*(v_len / del_v_by_fDrag_len);
630 force += nrm*(-c1*kLF);
674 m_nodes[node].m_im=mass>0?1/mass:0;
878 if(
m_nodes[i].m_im<=0) tmass+=kmass;
954 for(
int i=0,ni=cluster->
m_nodes.size();i<ni;++i)
1046 const unsigned inf=(~(unsigned)0)>>1;
1047 unsigned* adj=
new unsigned[n*n];
1050 #define IDX(_x_,_y_) ((_y_)*n+(_x_))
1057 adj[
IDX(i,j)]=adj[
IDX(j,i)]=inf;
1061 adj[
IDX(i,j)]=adj[
IDX(j,i)]=0;
1094 for (
int ii=0;ii<nodeLinks.
size();ii++)
1098 for (
int jj=0;jj<nodeLinks[ii].m_links.
size();jj++)
1100 int k = nodeLinks[ii].m_links[jj];
1101 for (
int kk=0;kk<nodeLinks[k].m_links.
size();kk++)
1103 int j = nodeLinks[k].m_links[kk];
1106 const unsigned sum=adj[
IDX(i,k)]+adj[
IDX(k,j)];
1108 if(adj[
IDX(i,j)]>sum)
1120 for(
int k=0;k<n;++k)
1126 const unsigned sum=adj[
IDX(i,k)]+adj[
IDX(k,j)];
1127 if(adj[
IDX(i,j)]>sum)
1143 if(adj[
IDX(i,j)]==(
unsigned)distance)
1160 unsigned long seed=243703;
1161 #define NEXTRAND (seed=(1664525L*seed+1013904223L)&0xffffffff)
1221 const btScalar w=2-btMin<btScalar>(1,iterations/slope);
1236 c = centers[i]+(c-centers[i])*w;
1247 for(
int j=1;j<k;++j)
1258 }
while(changed&&(iterations<maxiterations));
1274 for(
int j=0;j<3;++j)
1276 const int cid=cids[idx[j]];
1277 for(
int q=1;q<3;++q)
1279 const int kid=idx[(j+q)%3];
1321 for (
int j=0;j<4;j++)
1338 for(
int j=0;j<3;++j)
1361 bool connected=
false;
1364 for (
int i=0;!connected&&i<cla->
m_nodes.size();i++)
1366 for (
int j=0;j<clb->
m_nodes.size();j++)
1410 edges(
int(l.
m_n[0]-nbase),
int(l.
m_n[1]-nbase))=-1;
1415 edges(
int(f.
m_n[0]-nbase),
int(f.
m_n[1]-nbase))=-1;
1416 edges(
int(f.
m_n[1]-nbase),
int(f.
m_n[2]-nbase))=-1;
1417 edges(
int(f.
m_n[2]-nbase),
int(f.
m_n[0]-nbase))=-1;
1420 for(i=0;i<ncount;++i)
1422 for(j=i+1;j<ncount;++j)
1441 const btScalar f=(ma+mb)/(ma+mb+mc);
1469 const int idx[]={ int(feat.
m_n[0]-nbase),
1470 int(feat.
m_n[1]-nbase)};
1471 if((idx[0]<ncount)&&(idx[1]<ncount))
1473 const int ni=edges(idx[0],idx[1]);
1490 const int idx[]={ int(feat.
m_n[0]-nbase),
1491 int(feat.
m_n[1]-nbase),
1492 int(feat.
m_n[2]-nbase)};
1493 for(j=2,k=0;k<3;j=k++)
1495 if((idx[j]<ncount)&&(idx[k]<ncount))
1497 const int ni=edges(idx[j],idx[k]);
1501 const int l=(k+1)%3;
1520 const int pcount=ncount;
1525 for(i=0;i<ncount;++i)
1528 if((i>=pcount)||(
btFabs(ifn->
Eval(x))<accurary))
1532 if(m>0) { m*=0.5f;
m_nodes[i].m_im/=0.5f; }
1542 const int id[]={ int(
m_links[i].m_n[0]-nbase),
1543 int(
m_links[i].m_n[1]-nbase)};
1545 if(cnodes[
id[0]]&&cnodes[
id[1]])
1559 for(
int j=0;j<2;++j)
1561 int cn=cnodes[int(l.
m_n[j]-nbase)];
1570 if( (ifn->
Eval(n[0]->
m_x)<accurary)&&
1571 (ifn->
Eval(n[1]->
m_x)<accurary)&&
1572 (ifn->
Eval(n[2]->
m_x)<accurary))
1574 for(
int j=0;j<3;++j)
1576 int cn=cnodes[int(n[j]-nbase)];
1588 for(
int j=0;j<2;++j) ranks[
int(
m_links[i].m_n[j]-nbase)]++;
1592 for(
int j=0;j<3;++j) ranks[
int(
m_faces[i].m_n[j]-nbase)]++;
1596 const int id[]={ int(
m_links[i].m_n[0]-nbase),
1597 int(
m_links[i].m_n[1]-nbase)};
1598 const bool sg[]={ ranks[
id[0]]==1,
1609 for(i=nnodes-1;i>=0;--i)
1616 for(
int i=0;i<nnodes;++i) map[i]=i;
1617 PointersToIndices(
this);
1618 for(
int i=0,ni=todelete.
size();i<ni;++i)
1622 int& b=map[--nnodes];
1627 IndicesToPointers(
this,&map[0]);
1665 pft[0]->
m_n[1]=pn[mtch];
1666 pft[1]->
m_n[0]=pn[1-mtch];
1672 for(
int k=2,l=0;l<3;k=l++)
1679 pft[0]->
m_n[l]=pn[mtch];
1680 pft[1]->
m_n[k]=pn[1-mtch];
1681 appendLink(pn[0],pft[0]->m_n[(l+1)%3],pft[0]->m_material,
true);
1682 appendLink(pn[1],pft[0]->m_n[(l+1)%3],pft[0]->m_material,
true);
1704 results.
body =
this;
1774 for (
int c=0;c<3;c++)
1776 if (deltaV[c]>clampDeltaV)
1778 deltaV[c] = clampDeltaV;
1780 if (deltaV[c]<-clampDeltaV)
1782 deltaV[c]=-clampDeltaV;
1943 for(
int isolve=0;isolve<iterations;++isolve)
1961 const int nb=bodies.
size();
1971 bodies[i]->prepareClusters(iterations);
1973 for(i=0;i<iterations;++i)
1976 for(
int j=0;j<nb;++j)
1978 bodies[j]->solveClusters(sor);
1983 bodies[i]->cleanupClusters();
2009 const btScalar t=rayFromToTriangle( m_rayFrom,m_rayTo,m_rayNormalizedDirection,
2014 if((t>0)&&(t<m_mint))
2024 const btVector3& rayNormalizedDirection,
2040 if((t>teps)&&(t<maxt))
2042 const btVector3 hit=rayFrom+rayNormalizedDirection*t;
2057 #define PTR2IDX(_p_,_b_) reinterpret_cast<btSoftBody::Node*>((_p_)-(_b_))
2065 m_nodes[i].m_leaf->data=*(
void**)&i;
2080 m_faces[i].m_leaf->data=*(
void**)&i;
2089 for(
int j=0;j<
m_notes[i].m_rank;++j)
2100 #define IDX2PTR(_p_,_b_) map?(&(_b_)[map[(((char*)_p_)-(char*)0)]]): \
2101 (&(_b_)[(((char*)_p_)-(char*)0)])
2133 for(
int j=0;j<
m_notes[i].m_rank;++j)
2190 int tetfaces[4][3] = {{0,1,2},{0,1,3},{1,2,3},{0,2,3}};
2191 for (
int f=0;f<4;f++)
2194 int index0=tetfaces[f][0];
2195 int index1=tetfaces[f][1];
2196 int index2=tetfaces[f][2];
2358 Apq[0].setX(eps);Apq[1].setY(eps*2);Apq[2].setZ(eps*3);
2406 for(
int j=0;j<3;++j)
2433 for(
int j=0;j<3;++j)
2441 m_nodes[i].m_area *= 0.3333333f;
2479 for(
int j=0;j<c.
m_nodes.size();++j)
2502 for(i=0,ni=c.
m_nodes.size();i<ni;++i)
2507 ii[0][0] += m*(q[1]+q[2]);
2508 ii[1][1] += m*(q[0]+q[2]);
2509 ii[2][2] += m*(q[0]+q[1]);
2510 ii[0][1] -= m*k[0]*k[1];
2511 ii[0][2] -= m*k[0]*k[2];
2512 ii[1][2] -= m*k[1]*k[2];
2556 for(
int i=0;i<c.
m_nodes.size();++i)
2560 m[0]+=a[0]*b;m[1]+=a[1]*b;m[2]+=a[2]*b;
2576 c.
m_invwi=c.m_xform.getBasis().scaled(iin)*c.m_xform.getBasis().transpose();
2579 for(
int i=0;i<n;++i)
2584 c.
m_invwi[0][0] += m*(q[1]+q[2]);
2585 c.
m_invwi[1][1] += m*(q[0]+q[2]);
2586 c.
m_invwi[2][2] += m*(q[0]+q[1]);
2587 c.
m_invwi[0][1] -= m*k[0]*k[1];
2588 c.
m_invwi[0][2] -= m*k[0]*k[2];
2589 c.
m_invwi[1][2] -= m*k[1]*k[2];
2621 for(
int j=0;j<c.
m_nodes.size();++j)
2633 for(
int j=1;j<n;++j)
2718 for(
int j=0;j<c.
m_nodes.size();++j)
2728 for(i=0;i<deltas.
size();++i)
2732 m_nodes[i].m_x+=deltas[i]/weights[i];
2747 for(
int j=0;j<c.
m_nodes.size();++j)
2766 m_bodies[0].activate();
2767 m_bodies[1].activate();
2775 m_rpos[0] = m_bodies[0].xform()*m_refs[0];
2776 m_rpos[1] = m_bodies[1].xform()*m_refs[1];
2777 m_drift =
Clamp(m_rpos[0]-m_rpos[1],maxdrift)*m_erp/dt;
2778 m_rpos[0] -= m_bodies[0].xform().getOrigin();
2779 m_rpos[1] -= m_bodies[1].xform().getOrigin();
2780 m_massmatrix =
ImpulseMatrix( m_bodies[0].invMass(),m_bodies[0].invWorldInertia(),m_rpos[0],
2781 m_bodies[1].invMass(),m_bodies[1].invWorldInertia(),m_rpos[1]);
2784 m_sdrift = m_massmatrix*(m_drift*m_split);
2785 m_drift *= 1-m_split;
2793 const btVector3 va=m_bodies[0].velocity(m_rpos[0]);
2794 const btVector3 vb=m_bodies[1].velocity(m_rpos[1]);
2798 impulse.
m_velocity = m_massmatrix*(m_drift+vr*m_cfm)*sor;
2799 m_bodies[0].applyImpulse(-impulse,m_rpos[0]);
2800 m_bodies[1].applyImpulse( impulse,m_rpos[1]);
2808 m_bodies[0].applyDImpulse(-m_sdrift,m_rpos[0]);
2809 m_bodies[1].applyDImpulse( m_sdrift,m_rpos[1]);
2817 m_icontrol->Prepare(
this);
2819 m_axis[0] = m_bodies[0].xform().getBasis()*m_refs[0];
2820 m_axis[1] = m_bodies[1].xform().getBasis()*m_refs[1];
2822 m_drift *=
btMin(maxdrift,
btAcos(Clamp<btScalar>(
btDot(m_axis[0],m_axis[1]),-1,+1)));
2823 m_drift *= m_erp/dt;
2824 m_massmatrix=
AngularImpulseMatrix(m_bodies[0].invWorldInertia(),m_bodies[1].invWorldInertia());
2827 m_sdrift = m_massmatrix*(m_drift*m_split);
2828 m_drift *= 1-m_split;
2836 const btVector3 va=m_bodies[0].angularVelocity();
2837 const btVector3 vb=m_bodies[1].angularVelocity();
2840 const btVector3 vc=vr-m_axis[0]*m_icontrol->Speed(
this,sp);
2843 impulse.
m_velocity = m_massmatrix*(m_drift+vc*m_cfm)*sor;
2844 m_bodies[0].applyAImpulse(-impulse);
2845 m_bodies[1].applyAImpulse( impulse);
2853 m_bodies[0].applyDAImpulse(-m_sdrift);
2854 m_bodies[1].applyDAImpulse( m_sdrift);
2862 const bool dodrift=(m_life==0);
2863 m_delete=(++m_life)>m_maxlife;
2866 m_drift=m_drift*m_erp/dt;
2869 m_sdrift = m_massmatrix*(m_drift*m_split);
2870 m_drift *= 1-m_split;
2883 const btVector3 va=m_bodies[0].velocity(m_rpos[0]);
2884 const btVector3 vb=m_bodies[1].velocity(m_rpos[1]);
2898 if (m_bodies[0].m_soft==m_bodies[1].m_soft)
2905 if (impulse.
m_velocity.
length() <m_bodies[0].m_soft->m_maxSelfCollisionImpulse)
2910 m_bodies[0].applyImpulse(-impulse*m_bodies[0].m_soft->m_selfCollisionImpulseFactor,m_rpos[0]);
2911 m_bodies[1].applyImpulse( impulse*m_bodies[0].m_soft->m_selfCollisionImpulseFactor,m_rpos[1]);
2917 m_bodies[0].applyImpulse(-impulse,m_rpos[0]);
2918 m_bodies[1].applyImpulse( impulse,m_rpos[1]);
2927 m_bodies[0].applyDImpulse(-m_sdrift,m_rpos[0]);
2928 m_bodies[1].applyDImpulse( m_sdrift,m_rpos[1]);
2942 const bool as_lift = kLF>0;
2943 const bool as_drag = kDG>0;
2944 const bool as_pressure = kPR!=0;
2945 const bool as_volume = kVC>0;
2946 const bool as_aero = as_lift ||
2952 const bool use_medium = as_aero;
2953 const bool use_volume = as_pressure ||
2962 ivolumetp = 1/
btFabs(volume)*kPR;
3172 volume.Expand(
btVector3(basemargin,basemargin,basemargin));
3173 docollide.
psb =
this;
3177 docollide.
dynmargin = basemargin+timemargin;
3219 docollide.
psb[0]=
this;
3220 docollide.
psb[1]=psb;
3225 docollide.
psb[0]=psb;
3226 docollide.
psb[1]=
this;
3273 if (sbd->m_materials)
3276 int numElem = sbd->m_numMaterials;
3280 for (
int i=0;i<numElem;i++,memPtr++)
3307 int numElem = sbd->m_numNodes;
3310 for (
int i=0;i<numElem;i++,memPtr++)
3331 int numElem = sbd->m_numLinks;
3334 for (
int i=0;i<numElem;i++,memPtr++)
3354 int numElem = sbd->m_numFaces;
3357 for (
int i=0;i<numElem;i++,memPtr++)
3361 for (
int j=0;j<3;j++)
3373 if (sbd->m_tetrahedra)
3376 int numElem = sbd->m_numTetrahedra;
3379 for (
int i=0;i<numElem;i++,memPtr++)
3381 for (
int j=0;j<4;j++)
3399 int numElem = sbd->m_numAnchors;
3402 for (
int i=0;i<numElem;i++,memPtr++)
3417 sbd->m_config.m_dynamicFriction =
m_cfg.
kDF;
3419 sbd->m_config.m_pressure =
m_cfg.
kPR;
3428 sbd->m_config.m_damping =
m_cfg.
kDP;
3429 sbd->m_config.m_poseMatch =
m_cfg.
kMT;
3431 sbd->m_config.m_volume =
m_cfg.
kVC;
3432 sbd->m_config.m_rigidContactHardness =
m_cfg.
kCHR;
3433 sbd->m_config.m_kineticContactHardness =
m_cfg.
kKHR;
3434 sbd->m_config.m_softContactHardness =
m_cfg.
kSHR;
3435 sbd->m_config.m_anchorHardness =
m_cfg.
kAHR;
3439 sbd->m_config.m_softKineticClusterHardness =
m_cfg.
kSKHR_CL;
3466 for (
int i=0;i<numElem;i++,memPtr++)
3482 int sz =
sizeof(float);
3484 float* memPtr = (
float*) chunk->
m_oldPtr;
3485 for (
int i=0;i<numElem;i++,memPtr++)
3499 if (sbd->m_numClusters)
3501 int numElem = sbd->m_numClusters;
3505 for (
int i=0;i<numElem;i++,memPtr++)
3547 for (
int j=0;j<numElem;j++,memPtr++)
3549 m_clusters[i]->m_framerefs[j].serializeFloat(*memPtr);
3558 int sz =
sizeof(float);
3560 float* memPtr = (
float*) chunk->
m_oldPtr;
3561 for (
int j=0;j<numElem;j++,memPtr++)
3572 int sz =
sizeof(int);
3574 int* memPtr = (
int*) chunk->
m_oldPtr;
3575 for (
int j=0;j<numElem;j++,memPtr++)
3579 *memPtr = *indexPtr;
3600 for (
int i=0;i<numElem;i++,memPtr++)
3610 for (
int j=0;j<4;j++)
3617 if (
m_joints[i]->m_bodies[0].m_soft)
3622 if (
m_joints[i]->m_bodies[0].m_collisionObject)
3627 if (
m_joints[i]->m_bodies[0].m_rigid)
3633 if (
m_joints[i]->m_bodies[1].m_soft)
3638 if (
m_joints[i]->m_bodies[1].m_collisionObject)
3643 if (
m_joints[i]->m_bodies[1].m_rigid)
btMatrix3x3 inverse() const
Return the inverse of the matrix.
static void PSolve_RContacts(btSoftBody *psb, btScalar kst, btScalar ti)
btScalar getInvMass() const
RayFromToCaster(const btVector3 &rayFrom, const btVector3 &rayTo, btScalar mxt)
static T sum(const btAlignedObjectArray< T > &items)
const btCollisionObject * m_colObj
static const btRigidBody * upcast(const btCollisionObject *colObj)
to keep collision detection and dynamics separate we don't store a rigidbody pointer but a rigidbody ...
int generateBendingConstraints(int distance, Material *mat=0)
static void solveClusters(const btAlignedObjectArray< btSoftBody * > &bodies)
btScalar length(const btQuaternion &q)
Return the length of a quaternion.
eFeature::_ feature
soft body
void push_back(const T &_Val)
void Process(const btDbvtNode *leaf)
void(* vsolver_t)(btSoftBody *, btScalar)
Vertex normals are oriented toward velocity.
SoftBodyMaterialData * m_material
btScalar m_maxDisplacement
void Prepare(btScalar dt, int iterations)
static void ZeroInitialize(T &value)
void defaultCollisionHandler(const btCollisionObjectWrapper *pcoWrap)
btSoftBody implementation by Nathanael Presson
static btMatrix3x3 ImpulseMatrix(btScalar dt, btScalar ima, btScalar imb, const btMatrix3x3 &iwi, const btVector3 &r)
bool cutLink(int node0, int node1, btScalar position)
btVector3FloatData m_relPosition[2]
Vertex normals are flipped to match velocity.
btScalar m_restLengthScale
tVector3Array m_framerefs
void setSolver(eSolverPresets::_ preset)
static btVector3 clusterVelocity(const Cluster *cluster, const btVector3 &rpos)
const btCollisionObjectWrapper * m_colObj1Wrap
btVector3FloatData m_previousPosition
btVector3FloatData m_localFrame
btAlignedObjectArray< bool > m_clusterConnectivity
virtual void * getUniquePointer(void *oldPtr)=0
Material * appendMaterial()
virtual void Prepare(btScalar dt, int iterations)
btScalar btSqrt(btScalar y)
static btScalar rayFromToTriangle(const btVector3 &rayFrom, const btVector3 &rayTo, const btVector3 &rayNormalizedDirection, const btVector3 &a, const btVector3 &b, const btVector3 &c, btScalar maxt=SIMD_INFINITY)
void Prepare(btScalar dt, int iterations)
Cluster vs convex rigid vs soft.
btAlignedObjectArray< Node * > m_nodes
static void clusterVImpulse(Cluster *cluster, const btVector3 &rpos, const btVector3 &impulse)
btDispatcher * m_dispatcher
The btCollisionShape class provides an interface for collision shapes that can be shared among btColl...
btScalar fraction
feature index
void setVelocity(const btVector3 &velocity)
static btMatrix3x3 Mul(const btMatrix3x3 &a, btScalar b)
btDbvtNode * insert(const btDbvtVolume &box, void *data)
btVector3FloatData m_vimpulses[2]
void Solve(btScalar dt, btScalar sor)
static btScalar AreaOf(const btVector3 &x0, const btVector3 &x1, const btVector3 &x2)
tSContactArray m_scontacts
void appendAnchor(int node, btRigidBody *body, bool disableCollisionBetweenLinkedBodies=false, btScalar influence=1)
static void clusterImpulse(Cluster *cluster, const btVector3 &rpos, const Impulse &impulse)
static bool SameSign(const T &x, const T &y)
const btTransform & xform() const
static btVector3 clusterCom(const Cluster *cluster)
static int PolarDecompose(const btMatrix3x3 &m, btMatrix3x3 &q, btMatrix3x3 &s)
btVector3FloatData m_dimpulses[2]
static DBVT_PREFIX void rayTest(const btDbvtNode *root, const btVector3 &rayFrom, const btVector3 &rayTo, DBVT_IPOLICY)
rayTest is a re-entrant ray test, and can be called in parallel as long as the btAlignedAlloc is thre...
Vertex normals are taken as it is.
void addForce(const btVector3 &force)
static void EvaluateMedium(const btSoftBodyWorldInfo *wfi, const btVector3 &x, btSoftBody::sMedium &medium)
btVector3FloatData m_accumulatedForce
void setWindVelocity(const btVector3 &velocity)
Set a wind velocity for interaction with the air.
void ProcessColObj(btSoftBody *ps, const btCollisionObjectWrapper *colObWrap)
Cluster vs cluster soft vs soft handling.
btTransform m_initialWorldTransform
btTransform m_worldTransform
btSoftBody(btSoftBodyWorldInfo *worldInfo, int node_count, const btVector3 *x, const btScalar *m)
btSoftBody implementation by Nathanael Presson
void appendLink(int model=-1, Material *mat=0)
void Terminate(btScalar dt)
bool rayTest(const btVector3 &rayFrom, const btVector3 &rayTo, sRayCast &results)
Ray casting using rayFrom and rayTo in worldspace, (not direction!)
btCollisionShape * m_collisionShape
virtual void getAabb(const btTransform &t, btVector3 &aabbMin, btVector3 &aabbMax) const =0
getAabb returns the axis aligned bounding box in the coordinate frame of the given transform t...
btScalar dot(const btVector3 &v) const
Return the dot product.
void appendAngularJoint(const AJoint::Specs &specs, Cluster *body0, Body body1)
The btHashMap template class implements a generic and lightweight hashmap.
btVector3FloatData m_normal
const btScalar & x() const
Return the x value.
void appendFace(int model=-1, Material *mat=0)
btSoftBodyWorldInfo * m_worldInfo
btVector3 getVelocityInLocalPoint(const btVector3 &rel_pos) const
const btScalar & getZ() const
Return the z value.
btVector3FloatData m_normal
Cluster soft body self collision.
btScalar getTotalMass() const
static btDbvtVolume VolumeOf(const btSoftBody::Face &f, btScalar margin)
void clear()
clear the array, deallocated memory. Generally it is better to use array.resize(0), to reduce performance overhead of run-time memory (de)allocations.
btSparseSdf< 3 > m_sparsesdf
static btVector3 ProjectOnPlane(const btVector3 &v, const btVector3 &a)
int generateClusters(int k, int maxiterations=8192)
generateClusters with k=0 will create a convex cluster for each tetrahedron or triangle otherwise an ...
#define IDX2PTR(_p_, _b_)
void addVelocity(const btVector3 &velocity)
void addAeroForceToNode(const btVector3 &windVelocity, int nodeIndex)
btVector3 btCross(const btVector3 &v1, const btVector3 &v2)
Return the cross product of two vectors.
void appendLinearJoint(const LJoint::Specs &specs, Cluster *body0, Body body1)
virtual const char * serialize(void *dataBuffer, class btSerializer *serializer) const
fills the dataBuffer and returns the struct name (and 0 on failure)
void update(btDbvtNode *leaf, int lookahead=-1)
btScalar getRestLengthScale()
btTransform & getWorldTransform()
btVector3FloatData m_refs[2]
btMatrix3x3FloatData m_c0
int m_internalType
m_internalType is reserved to distinguish Bullet's btCollisionObject, btRigidBody, btSoftBody, btGhostObject etc.
btMatrix3x3FloatData m_rot
void indicesToPointers(const int *map=0)
int size() const
return the number of elements in the array
void optimizeIncremental(int passes)
btBroadphaseProxy * getBroadphaseHandle()
void setVolumeMass(btScalar mass)
static void ApplyClampedForce(btSoftBody::Node &n, const btVector3 &f, btScalar dt)
void randomizeConstraints()
Vertex normals are flipped to match velocity and lift and drag forces are applied.
void Prepare(btScalar dt, int iterations)
void updateLinkConstants()
const btVector3 & getWindVelocity()
Return the wind velocity for interaction with the air.
const btScalar & w() const
Return the w value.
tMaterialArray m_materials
static void clusterDImpulse(Cluster *cluster, const btVector3 &rpos, const btVector3 &impulse)
SoftBodyMaterialData * m_material
void refine(ImplicitFn *ifn, btScalar accurary, bool cut)
static void PSolve_SContacts(btSoftBody *psb, btScalar, btScalar ti)
static btDbvtAabbMm FromMM(const btVector3 &mi, const btVector3 &mx)
static btScalar ClusterMetric(const btVector3 &x, const btVector3 &y)
void staticSolve(int iterations)
RayFromToCaster takes a ray from, ray to (instead of direction!)
static psolver_t getSolver(ePSolver::_ solver)
#define btSoftBodyDataName
void releaseCluster(int index)
btVector3 cross(const btVector3 &v) const
Return the cross product between this and another vector.
const btScalar & getY() const
Return the y value.
const btTransform & getWorldTransform() const
btScalar getMass(int node) const
void appendTetra(int model, Material *mat)
#define btAlignedFree(ptr)
void predictMotion(btScalar dt)
const btScalar & getX() const
Return the x value.
void insert(const Key &key, const Value &value)
static btVector3 Clamp(const btVector3 &v, btScalar maxlength)
btMatrix3x3FloatData m_invwi
static void clusterVAImpulse(Cluster *cluster, const btVector3 &impulse)
void appendNode(const btVector3 &x, btScalar m)
void appendNote(const char *text, const btVector3 &o, const btVector4 &c=btVector4(1, 0, 0, 0), Node *n0=0, Node *n1=0, Node *n2=0, Node *n3=0)
btVector3FloatData m_velocity
The btRigidBody is the main class for rigid body objects.
btScalar length() const
Return the length of the vector.
static void VSolve_Links(btSoftBody *psb, btScalar kst)
virtual void setMargin(btScalar margin)=0
void setTotalMass(btScalar mass, bool fromfaces=false)
void initializeClusters()
static int MatchEdge(const btSoftBody::Node *a, const btSoftBody::Node *b, const btSoftBody::Node *ma, const btSoftBody::Node *mb)
tPSolverArray m_dsequence
static btDbvtAabbMm FromCR(const btVector3 &c, btScalar r)
void initializeFaceTree()
void rotate(const btQuaternion &rot)
btMatrix3x3FloatData m_scale
static T BaryEval(const T &a, const T &b, const T &c, const btVector3 &coord)
btRigidBodyData * m_rigidBody
void serializeFloat(struct btVector3FloatData &dataOut) const
void setTotalDensity(btScalar density)
const btScalar & y() const
Return the y value.
btAlignedObjectArray< int > m_links
const btCollisionShape * getCollisionShape() const
int capacity() const
return the pre-allocated (reserved) elements, this is at least as large as the total number of elemen...
static btMatrix3x3 AngularImpulseMatrix(const btMatrix3x3 &iia, const btMatrix3x3 &iib)
virtual int calculateSerializeBufferSize() const
void activate(bool forceActivation=false) const
btVector3 can be used to represent 3D points and vectors.
#define ATTRIBUTE_ALIGNED16(a)
const Value * find(const Key &key) const
btScalar length2() const
Return the length of the vector squared.
btScalar btAcos(btScalar x)
virtual btScalar Eval(const btVector3 &x)=0
DBVT_INLINE const btVector3 & Maxs() const
void serializeFloat(struct btMatrix3x3FloatData &dataOut) const
virtual void finalizeChunk(btChunk *chunk, const char *structType, int chunkCode, void *oldPtr)=0
btMatrix3x3FloatData m_aqq
static btScalar ImplicitSolve(btSoftBody::ImplicitFn *fn, const btVector3 &a, const btVector3 &b, const btScalar accuracy, const int maxiterations=256)
btVector3FloatData m_position
void Solve(btScalar dt, btScalar sor)
float m_maxSelfCollisionImpulse
btVector3 normalized() const
Return a normalized version of this vector.
void Solve(btScalar dt, btScalar sor)
#define btSoftBodyData
btSoftBody implementation by Nathanael Presson
void(* psolver_t)(btSoftBody *, btScalar, btScalar)
void remove(const T &key)
void applyClusters(bool drift)
static T Lerp(const T &a, const T &b, btScalar t)
Face normals are flipped to match velocity.
void transform(const btTransform &trs)
void resize(int newsize, const T &fillData=T())
#define BT_SBMATERIAL_CODE
bool btFuzzyZero(btScalar x)
void ProcessSoftSoft(btSoftBody *psa, btSoftBody *psb)
int findLinearSearch(const T &key) const
btScalar Evaluate(const btVector3 &x, const btCollisionShape *shape, btVector3 &normal, btScalar margin)
void Terminate(btScalar dt)
btMatrix3x3 transpose() const
Return the transpose of the matrix.
Face normals are flipped to match velocity and lift and drag forces are applied.
SoftBodyMaterialData * m_material
btRigidBody * m_rigidBody
#define PTR2IDX(_p_, _b_)
bool checkContact(const btCollisionObjectWrapper *colObjWrap, const btVector3 &x, btScalar margin, btSoftBody::sCti &cti) const
virtual btScalar getMargin() const =0
static void clusterAImpulse(Cluster *cluster, const Impulse &impulse)
void scale(const btVector3 &scl)
const T & btMax(const T &a, const T &b)
const btMatrix3x3 & getInvInertiaTensorWorld() const
tVSolverArray m_vsequence
btVector3FloatData * m_framerefs
virtual void setAabb(btBroadphaseProxy *proxy, const btVector3 &aabbMin, const btVector3 &aabbMax, btDispatcher *dispatcher)=0
#define btAlignedAlloc(size, alignment)
tPSolverArray m_psequence
The btMatrix3x3 class implements a 3x3 rotation matrix, to perform linear algebra in combination with...
static btVector3 NormalizeAny(const btVector3 &v)
btScalar dot(const btQuaternion &q1, const btQuaternion &q2)
Calculate the dot product between two quaternions.
btVector3FloatData m_c0[4]
SoftBodyMaterialData * m_material
btBroadphaseInterface * m_broadphase
void translate(const btVector3 &trs)
DBVT_PREFIX void collideTT(const btDbvtNode *root0, const btDbvtNode *root1, DBVT_IPOLICY)
void applyImpulse(const btVector3 &impulse, const btVector3 &rel_pos)
The btQuaternion implements quaternion to perform linear algebra rotations in combination with btMatr...
void setRestLengthScale(btScalar restLength)
btScalar btDot(const btVector3 &v1, const btVector3 &v2)
Return the dot product between two vectors.
btAlignedObjectArray< const class btCollisionObject * > m_collisionDisabledObjects
virtual const char * serialize(void *dataBuffer, class btSerializer *serializer) const
fills the dataBuffer and returns the struct name (and 0 on failure)
void setMax(const btVector3 &other)
Set each element to the max of the current values and the values of another btVector3.
virtual void * findPointer(void *oldPtr)=0
void prepareClusters(int iterations)
static void solveCommonConstraints(btSoftBody **bodies, int count, int iterations)
DBVT_INLINE const btVector3 & Mins() const
The btSoftBody is an class to simulate cloth and volumetric soft bodies.
static void clusterDCImpulse(Cluster *cluster, const btVector3 &impulse)
const T & btMin(const T &a, const T &b)
btTransformFloatData m_framexform
const btCollisionShape * getCollisionShape() const
void setPose(bool bvolume, bool bframe)
static void PSolve_Anchors(btSoftBody *psb, btScalar kst, btScalar ti)
void setMass(int node, btScalar mass)
void setVolumeDensity(btScalar density)
bool checkFace(int node0, int node1, int node2) const
DBVT_PREFIX void collideTV(const btDbvtNode *root, const btDbvtVolume &volume, DBVT_IPOLICY) const
int getActivationState() const
tRContactArray m_rcontacts
btScalar determinant() const
Return the determinant of the matrix.
btVector3 evaluateCom() const
float m_selfCollisionImpulseFactor
static void PSolve_Links(btSoftBody *psb, btScalar kst, btScalar ti)
btVector3 m_rayNormalizedDirection
void remove(btDbvtNode *leaf)
void addAeroForceToFace(const btVector3 &windVelocity, int faceIndex)
void setIdentity()
Set the matrix to the identity.
static void clusterDAImpulse(Cluster *cluster, const btVector3 &impulse)
virtual btChunk * allocate(size_t size, int numElements)=0
btVector3FloatData * m_positions
Vertex vs face soft vs soft handling.
btScalar getVolume() const
void updateArea(bool averageArea=true)
void setMin(const btVector3 &other)
Set each element to the min of the current values and the values of another btVector3.
float btScalar
The btScalar type abstracts floating point numbers, to easily switch between double and single floati...
bool checkLink(int node0, int node1) const
void Terminate(btScalar dt)
btMatrix3x3FloatData m_locii
static btDbvtVolume bounds(const tNodeArray &leaves)
const btCollisionObject * getCollisionObject() const
btScalar btFabs(btScalar x)
void resetLinkRestLengths()
const btScalar & z() const
Return the z value.