I am trying out the serial chain manipulator example <https://docs.sympy.org/latest/modules/physics/mechanics/examples/multi_degree_freedom_holonomic_system.html> in the sympy mechanics docs but am finding out that the kinematics sympy computes in the backend are buggy. I am attaching the file I use to test it. In the example <https://docs.sympy.org/latest/modules/physics/mechanics/examples/multi_degree_freedom_holonomic_system.html>, the velocity of the center of mass of the simple pendulum *should be : u1(t)*N_frame.x + l*u2(t)*B_frame.x + l*(u2(t) + u3(t))*C_frame.x*. However, *sympy returns : u1(t)*N_frame.x + l*u3(t)/3*B_frame.x + l*u3(t)*C_frame.x*.
I tried to investigate this by looking at the definition of a PinJoint in sympy. It turns out every joint, when initialized calls the *_set_linear_velocity* function. In case of the PinJoint the *_set_linear_velocity* function calls *child.masscenter.v2pt_theory(parent.masscenter, parent.frame, child.frame)* to impose velocity constraints between the child and parent link mass centers. The v2pt_theory function operates under the assumption that child and parent mass centers are fixed in the child frame (frame attached to the center of mass of the child). This would hold true if the parent link has mass concentrated at one end (or at the joint i.e. COM and joint location coincide) but not if the joint location is anywhere other than the COM of the parent link. Is there a way to define a serial chain manipulator in sympy without making such assumptions about the mass distribution of the links? -- You received this message because you are subscribed to the Google Groups "sympy" group. To unsubscribe from this group and stop receiving emails from it, send an email to sympy+unsubscr...@googlegroups.com. To view this discussion on the web visit https://groups.google.com/d/msgid/sympy/c4d9c1aa-49b3-44b5-81a9-d794e26e2c86n%40googlegroups.com.
from sympy import zeros, symbols from sympy.physics.mechanics import Body, PinJoint, PrismaticJoint, JointsMethod, inertia from sympy.physics.mechanics import dynamicsymbols from ipdb import set_trace q1, q2, q3, u1, u2, u3 = dynamicsymbols('q1, q2, q3, u1, u2, u3') l, k, c, g, kT = symbols('l, k, c, g, kT') ma, mb, mc, IBzz= symbols('ma, mb, mc, IBzz') wall = Body('N') block = Body('A', mass=ma) IB = inertia(block.frame, 0, 0, IBzz) compound_pend = Body('B', mass=mb, central_inertia=IB) simple_pend = Body('C', mass=mc) bodies = (wall, block, compound_pend, simple_pend) slider = PrismaticJoint('J1', wall, block, coordinates=q1, speeds=u1) rev1 = PinJoint('J2', block, compound_pend, coordinates=q2, speeds=u2, child_axis=compound_pend.z, child_joint_pos=l*2/3*compound_pend.y, parent_axis=block.z) rev2 = PinJoint('J3', compound_pend, simple_pend, coordinates=q3, speeds=u3, child_axis=simple_pend.z, parent_joint_pos=-l/3*compound_pend.y, parent_axis=compound_pend.z, child_joint_pos=l*simple_pend.y) joints = (slider, rev1, rev2) print(simple_pend.masscenter.vel(wall.frame)) # set_trace()