Skip to content

Commit 0c386ae

Browse files
committed
Fix: Divide IPC contact gradients by dt^2 to get actual force
- IPC contact gradients are force * dt^2, not force - Divide by dt^2 when accumulating contact forces - Use self.options.dt (IPC dt) instead of sim dt
1 parent f41c0f2 commit 0c386ae

File tree

1 file changed

+5
-1
lines changed

1 file changed

+5
-1
lines changed

genesis/engine/couplers/ipc_coupler.py

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2053,6 +2053,9 @@ def _record_ipc_contact_forces(self):
20532053
prim_types = contact_feature.contact_primitive_types()
20542054

20552055
# Accumulate contact gradients (forces) for all vertices
2056+
# NOTE: IPC gradients are actually force * dt^2, so we need to divide by dt^2
2057+
dt = self.options.dt
2058+
dt2 = dt * dt
20562059
total_force_dict = {} # {vertex_index: force_vector}
20572060

20582061
for prim_type in prim_types:
@@ -2070,11 +2073,12 @@ def _record_ipc_contact_forces(self):
20702073
gradients = view(grad_attr)
20712074

20722075
# Accumulate gradients for each vertex
2076+
# Gradients from IPC are force * dt^2, so divide by dt^2 to get actual force
20732077
for idx, grad in zip(indices, gradients):
20742078
grad_vec = np.array(grad).flatten()
20752079
if idx not in total_force_dict:
20762080
total_force_dict[idx] = np.zeros(3)
2077-
total_force_dict[idx] += grad_vec[:3] # Take first 3 components
2081+
total_force_dict[idx] += grad_vec[:3] / dt2 # Convert gradient to force
20782082

20792083
if not total_force_dict:
20802084
return # No contact forces to process

0 commit comments

Comments
 (0)