PeriDyno 1.0.0
Loading...
Searching...
No Matches
PJSNJSConstraintSolver.cu
Go to the documentation of this file.
1#include "PJSNJSConstraintSolver.h"
2#include "SharedFuncsForRigidBody.h"
3
4namespace dyno
5{
6 IMPLEMENT_TCLASS(PJSNJSConstraintSolver, TDataType)
7
8 template<typename TDataType>
9 PJSNJSConstraintSolver<TDataType>::PJSNJSConstraintSolver()
10 :ConstraintModule()
11 {
12 this->inContacts()->tagOptional(true);
13 }
14
15 template<typename TDataType>
16 PJSNJSConstraintSolver<TDataType>::~PJSNJSConstraintSolver()
17 {}
18
19 template<typename TDataType>
20 void PJSNJSConstraintSolver<TDataType>::initializeJacobian(Real dt)
21 {
22 int constraint_size = 0;
23 int contact_size = this->inContacts()->size();
24
25 auto topo = this->inDiscreteElements()->constDataPtr();
26
27 int ballAndSocketJoint_size = topo->ballAndSocketJoints().size();
28 int sliderJoint_size = topo->sliderJoints().size();
29 int hingeJoint_size = topo->hingeJoints().size();
30 int fixedJoint_size = topo->fixedJoints().size();
31 int pointJoint_size = topo->pointJoints().size();
32
33 if (this->varFrictionEnabled()->getData())
34 {
35 constraint_size += 3 * contact_size;
36 }
37 else
38 {
39 constraint_size = contact_size;
40 }
41
42 if (ballAndSocketJoint_size != 0)
43 {
44 constraint_size += 3 * ballAndSocketJoint_size;
45 }
46
47 if (sliderJoint_size != 0)
48 {
49 constraint_size += 8 * sliderJoint_size;
50 }
51
52 if (hingeJoint_size != 0)
53 {
54 constraint_size += 8 * hingeJoint_size;
55 }
56
57 if (fixedJoint_size != 0)
58 {
59 constraint_size += 6 * fixedJoint_size;
60 }
61
62 if (pointJoint_size != 0)
63 {
64 constraint_size += 3 * pointJoint_size;
65 }
66
67 if (constraint_size == 0)
68 {
69 return;
70 }
71
72 mVelocityConstraints.resize(constraint_size);
73
74 if (contact_size != 0)
75 {
76 auto& contacts = this->inContacts()->getData();
77 setUpContactAndFrictionConstraints(
78 mVelocityConstraints,
79 mContactsInLocalFrame,
80 this->inCenter()->getData(),
81 this->inRotationMatrix()->getData(),
82 this->varFrictionEnabled()->getData()
83 );
84 }
85
86 if (ballAndSocketJoint_size != 0)
87 {
88 auto& joints = topo->ballAndSocketJoints();
89 int begin_index = contact_size;
90
91 if (this->varFrictionEnabled()->getData())
92 {
93 begin_index += 2 * contact_size;
94 }
95
96 setUpBallAndSocketJointConstraints(
97 mVelocityConstraints,
98 joints,
99 this->inCenter()->getData(),
100 this->inRotationMatrix()->getData(),
101 begin_index
102 );
103 }
104
105 if (sliderJoint_size != 0)
106 {
107 auto& joints = topo->sliderJoints();
108 int begin_index = contact_size;
109
110 if (this->varFrictionEnabled()->getData())
111 {
112 begin_index += 2 * contact_size;
113 }
114 begin_index += 3 * ballAndSocketJoint_size;
115 setUpSliderJointConstraints(
116 mVelocityConstraints,
117 joints,
118 this->inCenter()->getData(),
119 this->inRotationMatrix()->getData(),
120 this->inQuaternion()->getData(),
121 begin_index
122 );
123 }
124
125 if (hingeJoint_size != 0)
126 {
127 auto& joints = topo->hingeJoints();
128 int begin_index = contact_size + 3 * ballAndSocketJoint_size + 8 * sliderJoint_size;
129 if (this->varFrictionEnabled()->getData())
130 {
131 begin_index += 2 * contact_size;
132 }
133 setUpHingeJointConstraints(
134 mVelocityConstraints,
135 joints,
136 this->inCenter()->getData(),
137 this->inRotationMatrix()->getData(),
138 this->inQuaternion()->getData(),
139 begin_index
140 );
141 }
142
143 if (fixedJoint_size != 0)
144 {
145 auto& joints = topo->fixedJoints();
146 int begin_index = contact_size + 3 * ballAndSocketJoint_size + 8 * sliderJoint_size + 8 * hingeJoint_size;
147 if (this->varFrictionEnabled()->getData())
148 {
149 begin_index += 2 * contact_size;
150 }
151 setUpFixedJointConstraints(
152 mVelocityConstraints,
153 joints,
154 this->inRotationMatrix()->getData(),
155 this->inQuaternion()->getData(),
156 begin_index
157 );;
158 }
159
160 if (pointJoint_size != 0)
161 {
162 auto& joints = topo->pointJoints();
163 int begin_index = contact_size + 3 * ballAndSocketJoint_size + 8 * sliderJoint_size + 8 * hingeJoint_size + 6 * fixedJoint_size;
164 if (this->varFrictionEnabled()->getData())
165 {
166 begin_index += 2 * contact_size;
167 }
168 setUpPointJointConstraints(
169 mVelocityConstraints,
170 joints,
171 this->inCenter()->getData(),
172 begin_index
173 );
174 }
175
176 auto sizeOfRigids = this->inCenter()->size();
177 mContactNumber.resize(sizeOfRigids);
178
179 mJ.resize(4 * constraint_size);
180 mB.resize(4 * constraint_size);
181 mK_1.resize(constraint_size);
182 mK_2.resize(constraint_size);
183 mK_3.resize(constraint_size);
184 mEta.resize(constraint_size);
185 mLambda.resize(constraint_size);
186
187 mJ.reset();
188 mB.reset();
189 mK_1.reset();
190 mK_2.reset();
191 mK_3.reset();
192 mEta.reset();
193 mLambda.reset();
194
195 mContactNumber.reset();
196
197 calculateJacobianMatrix(
198 mJ,
199 mB,
200 this->inCenter()->getData(),
201 this->inInertia()->getData(),
202 this->inMass()->getData(),
203 this->inRotationMatrix()->getData(),
204 mVelocityConstraints
205 );
206
207 calculateK(
208 mVelocityConstraints,
209 mJ,
210 mB,
211 this->inCenter()->getData(),
212 this->inInertia()->getData(),
213 this->inMass()->getData(),
214 mK_1,
215 mK_2,
216 mK_3
217 );
218
219 calculateEtaVectorForPJS(
220 mEta,
221 mJ,
222 this->inVelocity()->getData(),
223 this->inAngularVelocity()->getData(),
224 mVelocityConstraints
225 );
226
227 if (contact_size != 0)
228 {
229 calculateContactPoints(
230 this->inContacts()->getData(),
231 mContactNumber);
232 }
233 }
234
235 template<typename TDataType>
236 void PJSNJSConstraintSolver<TDataType>::initializeJacobianForNJS()
237 {
238 int constraint_size = 0;
239 int contact_size = this->inContacts()->size();
240
241 auto topo = this->inDiscreteElements()->constDataPtr();
242
243 int ballAndSocketJoint_size = topo->ballAndSocketJoints().size();
244 int sliderJoint_size = topo->sliderJoints().size();
245 int hingeJoint_size = topo->hingeJoints().size();
246 int fixedJoint_size = topo->fixedJoints().size();
247 int pointJoint_size = topo->pointJoints().size();
248
249 constraint_size += contact_size;
250
251 if (ballAndSocketJoint_size != 0)
252 {
253 constraint_size += 3 * ballAndSocketJoint_size;
254 }
255
256 if (sliderJoint_size != 0)
257 {
258 constraint_size += 8 * sliderJoint_size;
259 }
260
261 if (hingeJoint_size != 0)
262 {
263 constraint_size += 8 * hingeJoint_size;
264 }
265
266 if (fixedJoint_size != 0)
267 {
268 constraint_size += 6 * fixedJoint_size;
269 }
270
271 if (pointJoint_size != 0)
272 {
273 constraint_size += 3 * pointJoint_size;
274 }
275
276 if (constraint_size == 0)
277 {
278 return;
279 }
280
281 mPositionConstraints.resize(constraint_size);
282
283 if (contact_size != 0)
284 {
285 auto& contacts = this->inContacts()->getData();
286 setUpContactConstraints(
287 mPositionConstraints,
288 mContactsInLocalFrame,
289 this->inCenter()->getData(),
290 this->inRotationMatrix()->getData()
291 );
292 }
293
294 if (ballAndSocketJoint_size != 0)
295 {
296 auto& joints = topo->ballAndSocketJoints();
297 int begin_index = contact_size;
298
299 setUpBallAndSocketJointConstraints(
300 mPositionConstraints,
301 joints,
302 this->inCenter()->getData(),
303 this->inRotationMatrix()->getData(),
304 begin_index
305 );
306 }
307
308 if (sliderJoint_size != 0)
309 {
310 auto& joints = topo->sliderJoints();
311 int begin_index = contact_size;
312
313 begin_index += 3 * ballAndSocketJoint_size;
314 setUpSliderJointConstraints(
315 mVelocityConstraints,
316 joints,
317 this->inCenter()->getData(),
318 this->inRotationMatrix()->getData(),
319 this->inQuaternion()->getData(),
320 begin_index
321 );
322 }
323
324 if (hingeJoint_size != 0)
325 {
326 auto& joints = topo->hingeJoints();
327 int begin_index = contact_size + 3 * ballAndSocketJoint_size + 8 * sliderJoint_size;
328
329 setUpHingeJointConstraints(
330 mPositionConstraints,
331 joints,
332 this->inCenter()->getData(),
333 this->inRotationMatrix()->getData(),
334 this->inQuaternion()->getData(),
335 begin_index
336 );
337 }
338
339 if (fixedJoint_size != 0)
340 {
341 auto& joints = topo->fixedJoints();
342 int begin_index = contact_size + 3 * ballAndSocketJoint_size + 8 * sliderJoint_size + 8 * hingeJoint_size;
343
344 setUpFixedJointConstraints(
345 mVelocityConstraints,
346 joints,
347 this->inRotationMatrix()->getData(),
348 this->inQuaternion()->getData(),
349 begin_index
350 );;
351 }
352
353 if (pointJoint_size != 0)
354 {
355 auto& joints = topo->pointJoints();
356 int begin_index = contact_size + 3 * ballAndSocketJoint_size + 8 * sliderJoint_size + 8 * hingeJoint_size + 6 * fixedJoint_size;
357
358 setUpPointJointConstraints(
359 mPositionConstraints,
360 joints,
361 this->inCenter()->getData(),
362 begin_index
363 );
364 }
365
366 auto sizeOfRigids = this->inCenter()->size();
367 mJ_p.resize(4 * constraint_size);
368 mB_p.resize(4 * constraint_size);
369 mK_1.resize(constraint_size);
370 mK_2.resize(constraint_size);
371 mK_3.resize(constraint_size);
372 mEta_p.resize(constraint_size);
373 mLambda.resize(constraint_size);
374
375 mJ_p.reset();
376 mB_p.reset();
377 mK_1.reset();
378 mK_2.reset();
379 mK_3.reset();
380 mEta_p.reset();
381 mLambda.reset();
382
383 calculateJacobianMatrixForNJS(
384 mJ_p,
385 mB_p,
386 this->inCenter()->getData(),
387 this->inInertia()->getData(),
388 this->inMass()->getData(),
389 this->inRotationMatrix()->getData(),
390 mPositionConstraints
391 );
392
393 calculateK(
394 mPositionConstraints,
395 mJ_p,
396 mB_p,
397 this->inCenter()->getData(),
398 this->inInertia()->getData(),
399 this->inMass()->getData(),
400 mK_1,
401 mK_2,
402 mK_3
403 );
404
405 calculateEtaVectorForNJS(
406 mEta_p,
407 mJ_p,
408 this->inCenter()->getData(),
409 this->inQuaternion()->getData(),
410 mPositionConstraints,
411 this->varSlop()->getValue(),
412 this->varBaumgarteBias()->getValue()
413 );
414 }
415
416 template<typename TDataType>
417 void PJSNJSConstraintSolver<TDataType>::constrain()
418 {
419 uint bodyNum = this->inCenter()->size();
420
421 auto topo = this->inDiscreteElements()->constDataPtr();
422
423 mImpulseC.resize(bodyNum * 2);
424 mImpulseExt.resize(bodyNum * 2);
425 mImpulseC.reset();
426 mImpulseExt.reset();
427
428 Real dt = this->inTimeStep()->getData();
429
430 if (this->varGravityEnabled()->getValue())
431 {
432 setUpGravity(
433 mImpulseExt,
434 this->varGravityValue()->getValue(),
435 dt
436 );
437 }
438
439 updateVelocity(
440 this->inAttribute()->getData(),
441 this->inVelocity()->getData(),
442 this->inAngularVelocity()->getData(),
443 mImpulseExt,
444 this->varLinearDamping()->getValue(),
445 this->varAngularDamping()->getValue(),
446 dt
447 );
448 if (!this->inContacts()->isEmpty())
449 {
450 if (mContactsInLocalFrame.size() != this->inContacts()->size()) {
451 mContactsInLocalFrame.resize(this->inContacts()->size());
452 }
453
454 setUpContactsInLocalFrame(
455 mContactsInLocalFrame,
456 this->inContacts()->getData(),
457 this->inCenter()->getData(),
458 this->inRotationMatrix()->getData()
459 );
460 }
461
462 //Velocity Solver
463 if (!this->inContacts()->isEmpty() || topo->totalJointSize() > 0)
464 {
465 initializeJacobian(dt);
466 int constraint_size = mVelocityConstraints.size();
467 for (int i = 0; i < this->varIterationNumberForVelocitySolver()->getValue(); i++)
468 {
469 JacobiIteration(
470 mLambda,
471 mImpulseC,
472 mJ,
473 mB,
474 mEta,
475 mVelocityConstraints,
476 mContactNumber,
477 mK_1,
478 mK_2,
479 mK_3,
480 this->inMass()->getData(),
481 this->inFrictionCoefficients()->getData(),
482 this->varFrictionCoefficient()->getData(),
483 this->varGravityValue()->getData(),
484 dt
485 );
486 }
487 }
488
489 updateVelocity(
490 this->inAttribute()->getData(),
491 this->inVelocity()->getData(),
492 this->inAngularVelocity()->getData(),
493 mImpulseC,
494 this->varLinearDamping()->getValue(),
495 this->varAngularDamping()->getValue(),
496 dt
497 );
498
499 updateGesture(
500 this->inAttribute()->getData(),
501 this->inCenter()->getData(),
502 this->inQuaternion()->getData(),
503 this->inRotationMatrix()->getData(),
504 this->inInertia()->getData(),
505 this->inVelocity()->getData(),
506 this->inAngularVelocity()->getData(),
507 this->inInitialInertia()->getData(),
508 dt
509 );
510
511 // Position Solver
512 if (!this->inContacts()->isEmpty() || topo->totalJointSize() > 0)
513 {
514 for (int i = 0; i < this->varIterationNumberForPositionSolver()->getValue(); i++)
515 {
516 mImpulseC.reset();
517 mLambda.reset();
518 initializeJacobianForNJS();
519 int constraint_size = mPositionConstraints.size();
520 for (int j = 0; j < 1; j++)
521 {
522 JacobiIterationForNJS(
523 mLambda,
524 mImpulseC,
525 mJ_p,
526 mB_p,
527 mEta_p,
528 mPositionConstraints,
529 mContactNumber,
530 mK_1,
531 mK_2,
532 mK_3
533 );
534 }
535
536 updatePositionAndRotation(
537 this->inCenter()->getData(),
538 this->inQuaternion()->getData(),
539 this->inRotationMatrix()->getData(),
540 this->inInertia()->getData(),
541 this->inInitialInertia()->getData(),
542 mImpulseC
543 );
544 }
545 }
546 }
547 DEFINE_CLASS(PJSNJSConstraintSolver);
548}