@@ -242,10 +242,8 @@ def _flex_vertices(
242242def _flex_edges (
243243 # Model:
244244 nflex : int ,
245- body_parentid : wp .array (dtype = int ),
246245 body_rootid : wp .array (dtype = int ),
247246 body_dofadr : wp .array (dtype = int ),
248- dof_bodyid : wp .array (dtype = int ),
249247 flex_vertadr : wp .array (dtype = int ),
250248 flex_edgeadr : wp .array (dtype = int ),
251249 flex_edgenum : wp .array (dtype = int ),
@@ -286,64 +284,32 @@ def _flex_edges(
286284
287285 dofi = body_dofadr [b1 ]
288286 dofj = body_dofadr [b2 ]
289- dofi0 = dofi + 0
290- dofi1 = dofi + 1
291- dofi2 = dofi + 2
292- dofj0 = dofj + 0
293- dofj1 = dofj + 1
294- dofj2 = dofj + 2
295-
296- vel1 = wp .vec3 (qvel_in [worldid , dofi0 ], qvel_in [worldid , dofi1 ], qvel_in [worldid , dofi2 ])
297- vel2 = wp .vec3 (qvel_in [worldid , dofj0 ], qvel_in [worldid , dofj1 ], qvel_in [worldid , dofj2 ])
287+
288+ vel1 = wp .vec3 (qvel_in [worldid , dofi ], qvel_in [worldid , dofi + 1 ], qvel_in [worldid , dofi + 2 ])
289+ vel2 = wp .vec3 (qvel_in [worldid , dofj ], qvel_in [worldid , dofj + 1 ], qvel_in [worldid , dofj + 2 ])
298290 flexedge_velocity_out [worldid , edgeid ] = wp .dot (vel2 - vel1 , edge )
299291
300292 rowadr = flexedge_J_rowadr [edgeid ]
301293
302- sparseid0 = rowadr + 0
303- sparseid1 = rowadr + 1
304- sparseid2 = rowadr + 2
305- sparseid3 = rowadr + 3
306- sparseid4 = rowadr + 4
307- sparseid5 = rowadr + 5
308-
309- # TODO(team): jacdif
310-
311- jacp1 , _ = support .jac_dof (body_parentid , body_rootid , dof_bodyid , subtree_com_in , cdof_in , pos1 , b1 , dofi0 , worldid )
312- jacp2 , _ = support .jac_dof (body_parentid , body_rootid , dof_bodyid , subtree_com_in , cdof_in , pos2 , b2 , dofi0 , worldid )
313- jacdif = jacp2 - jacp1
314- Ji0 = wp .dot (jacdif , edge )
315-
316- jacp1 , _ = support .jac_dof (body_parentid , body_rootid , dof_bodyid , subtree_com_in , cdof_in , pos1 , b1 , dofi1 , worldid )
317- jacp2 , _ = support .jac_dof (body_parentid , body_rootid , dof_bodyid , subtree_com_in , cdof_in , pos2 , b2 , dofi1 , worldid )
318- jacdif = jacp2 - jacp1
319- Ji1 = wp .dot (jacdif , edge )
320-
321- jacp1 , _ = support .jac_dof (body_parentid , body_rootid , dof_bodyid , subtree_com_in , cdof_in , pos1 , b1 , dofi2 , worldid )
322- jacp2 , _ = support .jac_dof (body_parentid , body_rootid , dof_bodyid , subtree_com_in , cdof_in , pos2 , b2 , dofi2 , worldid )
323- jacdif = jacp2 - jacp1
324- Ji2 = wp .dot (jacdif , edge )
325-
326- jacp1 , _ = support .jac_dof (body_parentid , body_rootid , dof_bodyid , subtree_com_in , cdof_in , pos1 , b1 , dofj0 , worldid )
327- jacp2 , _ = support .jac_dof (body_parentid , body_rootid , dof_bodyid , subtree_com_in , cdof_in , pos2 , b2 , dofj0 , worldid )
328- jacdif = jacp2 - jacp1
329- Jj0 = wp .dot (jacdif , edge )
330-
331- jacp1 , _ = support .jac_dof (body_parentid , body_rootid , dof_bodyid , subtree_com_in , cdof_in , pos1 , b1 , dofj1 , worldid )
332- jacp2 , _ = support .jac_dof (body_parentid , body_rootid , dof_bodyid , subtree_com_in , cdof_in , pos2 , b2 , dofj1 , worldid )
333- jacdif = jacp2 - jacp1
334- Jj1 = wp .dot (jacdif , edge )
335-
336- jacp1 , _ = support .jac_dof (body_parentid , body_rootid , dof_bodyid , subtree_com_in , cdof_in , pos1 , b1 , dofj2 , worldid )
337- jacp2 , _ = support .jac_dof (body_parentid , body_rootid , dof_bodyid , subtree_com_in , cdof_in , pos2 , b2 , dofj2 , worldid )
338- jacdif = jacp2 - jacp1
339- Jj2 = wp .dot (jacdif , edge )
340-
341- flexedge_J_out [worldid , sparseid0 ] = Ji0
342- flexedge_J_out [worldid , sparseid1 ] = Ji1
343- flexedge_J_out [worldid , sparseid2 ] = Ji2
344- flexedge_J_out [worldid , sparseid3 ] = Jj0
345- flexedge_J_out [worldid , sparseid4 ] = Jj1
346- flexedge_J_out [worldid , sparseid5 ] = Jj2
294+ # compute offsets once per body (avoids 12 redundant tree-ancestry walks in jac_dof)
295+ offset1 = pos1 - wp .vec3 (subtree_com_in [worldid , body_rootid [b1 ]])
296+ offset2 = pos2 - wp .vec3 (subtree_com_in [worldid , body_rootid [b2 ]])
297+
298+ # body1 DOFs: b1 is in subtree, b2 is not -> jacdif = 0 - jacp1 = -jacp1
299+ for k in range (3 ):
300+ cdof = cdof_in [worldid , dofi + k ]
301+ cdof_ang = wp .spatial_top (cdof )
302+ cdof_lin = wp .spatial_bottom (cdof )
303+ jacp1 = cdof_lin + wp .cross (cdof_ang , offset1 )
304+ flexedge_J_out [worldid , rowadr + k ] = wp .dot (- jacp1 , edge )
305+
306+ # body2 DOFs: b2 is in subtree, b1 is not -> jacdif = jacp2 - 0 = jacp2
307+ for k in range (3 ):
308+ cdof = cdof_in [worldid , dofj + k ]
309+ cdof_ang = wp .spatial_top (cdof )
310+ cdof_lin = wp .spatial_bottom (cdof )
311+ jacp2 = cdof_lin + wp .cross (cdof_ang , offset2 )
312+ flexedge_J_out [worldid , rowadr + 3 + k ] = wp .dot (jacp2 , edge )
347313
348314
349315@event_scope
@@ -415,10 +381,8 @@ def flex(m: Model, d: Data):
415381 dim = (d .nworld , m .nflexedge ),
416382 inputs = [
417383 m .nflex ,
418- m .body_parentid ,
419384 m .body_rootid ,
420385 m .body_dofadr ,
421- m .dof_bodyid ,
422386 m .flex_vertadr ,
423387 m .flex_edgeadr ,
424388 m .flex_edgenum ,
0 commit comments