7 #include "imstkPbdAngularConstraint.h" 31 const Quatd& q = bodies.getOrientation(
m_particles[i]);
32 const Mat3d& invInteria = bodies.getInvInertia(
m_particles[i]);
33 const Vec3d l = q.inverse()._transformVector(
m_dcdx[i]);
34 w += l[0] * l[0] * invInteria(0, 0) +
35 l[1] * l[1] * invInteria(1, 1) +
36 l[2] * l[2] * invInteria(2, 2);
39 if (w < IMSTK_DOUBLE_EPS)
48 case (SolverType::PBD):
51 case (SolverType::xPBD):
54 dlambda = -(c + alpha *
m_lambda) / (w + alpha);
62 const Mat3d& invInteria = bodies.getInvInertia(
m_particles[i]);
65 const Vec3d p = dlambda *
m_dcdx[i];
67 rot = q.inverse()._transformVector(rot);
68 rot = invInteria * rot;
69 rot = q._transformVector(rot);
72 const double phi = rot.norm();
78 const Quatd dq_quat = Quatd(0.0,
82 q.coeffs() += dq_quat.coeffs() * 0.5;
88 PbdAngularHingeConstraint::initConstraint(
90 const Vec3d& hingeAxes,
91 const double compliance)
94 m_hingeAxes = hingeAxes;
95 setCompliance(compliance);
100 double& c, std::vector<Vec3d>& dcdx)
103 const Vec3d localY = bodies.getOrientation(
m_particles[0]).toRotationMatrix().col(1);
106 Vec3d dir = m_hingeAxes.cross(localY);
107 dcdx[0] = dir.normalized();
117 const double compliance)
121 setCompliance(compliance);
129 const double compliance)
134 const Quatd& q0 = bodies.getOrientation(
m_particles[0]);
135 const Quatd& q1 = bodies.getOrientation(
m_particles[1]);
137 m_offset = q0.inverse() * q1;
139 setCompliance(compliance);
146 const Quatd rotationalOffset,
147 const double compliance)
149 initConstraint(p0, p1, compliance);
150 m_offset = rotationalOffset;
155 double& c, std::vector<Vec3d>& dcdx)
157 const Quatd& q0 = bodies.getOrientation(
m_particles[0]);
158 const Quatd& q1 = bodies.getOrientation(
m_particles[1]);
161 const Quatd dq = q1 * (q0 * m_offset).inverse();
162 Eigen::AngleAxisd angleAxes(dq);
163 dcdx[0] = angleAxes.axis();
165 c = -angleAxes.angle();
std::vector< Vec3d > m_dcdx
Normalized constraint gradients (per particle)
void projectConstraint(PbdState &bodies, const double dt, const SolverType &type) override
Update positions by projecting constraints.
std::pair< int, int > PbdParticleId
Index pair that refers to a particle in a PbdState. Index 0 is the body id, Index 1 is the particle i...
double m_lambda
Lagrange multiplier.
std::vector< PbdParticleId > m_particles
body, particle index
bool computeValueAndGradient(PbdState &bodies, double &c, std::vector< Vec3d > &dcdx) override
Compute value and gradient of constraint function.
double m_compliance
used in xPBD, inverse of Stiffness
void initConstraintOffset(const PbdState &bodies, const PbdParticleId &p0, const PbdParticleId &p1, const double compliance)
Constrain p0 to match p1's orientation according to the the current rotational offset between them...
virtual bool computeValueAndGradient(PbdState &bodies, double &c, std::vector< Vec3d > &dcdx)=0
Compute value and gradient of the constraint.
double m_stiffness
used in PBD, [0, 1]
SolverType
Type of solvers.
Provides interface for accessing particles from a 2d array of PbdBody,Particles.
bool computeValueAndGradient(PbdState &bodies, double &c, std::vector< Vec3d > &dcdx) override
Compute value and gradient of constraint function.
void initConstraint(const PbdParticleId &p0, const PbdParticleId &p1, const double compliance)
Constraint p0 to match p1, zero rotational offset.