# torque

Hi All,

I want to get the torque of a body.

I use the following code to get the torque as well as the force.
#####################
def coon():

friction_force_cal0 = sum(O.forces.f(b)[0] for b in cylinderIDS)
friction_force_cal1 = sum(O.forces.f(b)[1] for b in cylinderIDS)
friction_force_cal2 = sum(O.forces.f(b)[2] for b in cylinderIDS)
#friction_force_cal = sum(O.forces.f(b) for b in cylinderIDS)

#torque_cal = sum(O.forces.t(b) for b in cylinderIDS)
torque_cal0 = sum(O.forces.t(b)[0] for b in cylinderIDS)
torque_cal1 = sum(O.forces.t(b)[1] for b in cylinderIDS)
torque_cal2 = sum(O.forces.t(b)[2] for b in cylinderIDS)

f_0=utils.sumForces(ids=cylinderIDS,direction =(1,0,0))
f_1=utils.sumForces(ids=cylinderIDS,direction =(0,1,0))
f_2=utils.sumForces(ids=cylinderIDS,direction =(0,0,1))
torque_0 = utils.sumTorques(ids=cylinderIDS,axis = (1,0,0),axisPt = (0.2,0,0))
torque_1 = utils.sumTorques(ids=cylinderIDS,axis = (0,1,0),axisPt = (0,0.2,0))
torque_2 = utils.sumTorques(ids=cylinderIDS,axis = (0,0,1),axisPt = (0,0,0.2))
plot.addData(f1 =f_0,f2 = f_1,f3 = f_2, friction1 = friction_force_cal0,
friction2 = friction_force_cal1, friction3 = friction_force_cal2,
torque1 = torque_cal0, torque2 = torque_cal1, torque3 = torque_cal2,
t1 = torque_0, t2 = torque_1,t3 = torque_2,unbalanced=unbalancedForce(),i=O.iter)

plot.saveDataTxt('alldata.txt')

#######################
the results show that f1 = friction1, f2 = friction2, f3 = friction3. this testify the above code for forces.
while the code for torque don't give me the expeted results. (I'm thinking the t1 should be equal to torque1.)

I found that t1 = -t2.

I don't know which one is correct for the torque.
or because of the axisPt so the torque is different.

## Question information

Language:
English Edit question
Status:
Solved
For:
Assignee:
No assignee Edit question
Solved by:
Jan Stránský
Solved:
2020-04-29
Last query:
2020-04-29
2020-04-28
 Jérôme Duriez (jduriez) said on 2020-04-22: #1

I'm not really familiar to sumTorques() (or your code), but it seems strange to me to compare torques that are computed in different points.

 Jan Stránský (honzik) said on 2020-04-22: #2

> friction_force_cal = sum(O.forces.f(b) for b in cylinderIDS)
> torque_cal = sum(O.forces.t(b) for b in cylinderIDS)

python sum takes an initial value (default is 0, but does not work with vectors), so you can do:
###
friction_force_cal = sum((O.forces.f(b) for b in cylinderIDS), Vector3.Zero)
torque_cal = sum((O.forces.t(b) for b in cylinderIDS), Vector3.Zero)
###

if you sum torques "manually", do not forget to take into account forces on bodies, otherwise it is different computation than utils.sumTorques [1]

cheers
Jan

 nobody (nobody01) said on 2020-04-24: #3

Hi Jérôme and Jan,

for the command used in my code.
for instance:
###########
(1)torque_cal0 = sum(O.forces.t(b)[0] for b in cylinderIDS)
(2)torque_0 = utils.sumTorques(ids=cylinderIDS,axis = (1,0,0),axisPt = (0.2,0,0))
#########
as we all know, torque = force*(cross dot) length. so for command(1) we can get the torque, but the definition didn't mention where is the action point------so what is the meaning of this command in YADE?
as for (2), my object is a cylinder, if I want to get the torque generated from the object, which is result from the contact force * the radius of the cylinder. so I can't use command (2) also?

best,
Yong

 Jan Stránský (honzik) said on 2020-04-24: #4

> as we all know, torque = force*(cross dot) length. so for command(1) we can get the torque, but the definition didn't mention where is the action point------so what is the meaning of this command in YADE?

for command (1), you get sum of "plain" torques applied to bodies. It is something different than utils.sumTorques, but may have some use case..

If you want to sum "total" torques "manually", do the same as utils.sumTorques [1]:
torque = sum(( O.forces.t(b) + (O.bodies[b].state.pos-actionPoint).cross(O.forces.f(b)) for b in cylinderIDS), Vector3.Zero)
of not one line:
###
ret = Vector3.Zero
for i in cylinderIDS:
b = O.bodies[i]
p = b.state.pos
r = p - actionPoint
t = O.forces.t(i)
f = O.forces.f(i)
ret += t + r.cross(f)
###

cheers
Jan

 nobody (nobody01) said on 2020-04-24: #5

Hi Jan,

why do we need to use this: ret += t + r.cross(f)?
why not we use ret += r.cross(f)?

thanks
Yong

 Jan Stránský (honzik) said on 2020-04-24: #6

> why do we need

well, you don't need :-)
you need to use it to get the same result as utils.sumTorques, which is physically the total torque with respect to a given point from individual torques and forces applied to the bodies.

> why not we use ret += r.cross(f)?

because (obviously) you would get different result. As sum(plain torques), discussed on previous answers, also sum(torques only from forces) probably may be useful, but it is not what you are asking.

Total torque has two contributions:
- torques directly applied to bodies, i.e. "t"
- forces applied to bodies and their "excentricity", i.e. "r.cross(f)"

To get correct results, you need both (even sometimes one of the contributions may be negligible compared to the other, it is not good idea to depend on that fact)

cheers
Jan

 Jérôme Duriez (jduriez) said on 2020-04-24: #7

Going back to #3, I see O.forces.t as referring to the (resultant) torque computed at state.pos (center of mass of the Body)

 nobody (nobody01) said on 2020-04-24: #8

hi Jan,

thank you very much!

I forgot the part that the torque directly applied to the bodies.

hi Jérôme,

if I remember correctly, for the object created by the facets it doesn't have the mass by default. but we can assign the mass to that object.
generally speaking, can we say centroid of the body instead of the center of mass of the body?

 Jan Stránský (honzik) said on 2020-04-26: #9

> generally speaking, can we say centroid of the body instead of the center of mass of the body?

not really in general. Especially in the case of facets, where b.state.pos "by default" is NOT a center of mass (or centroid), but center if inscribed circle [1]

cheers
Jan

 nobody (nobody01) said on 2020-04-28: #10

Hi Jan,

let me explain more clearly,
(1) for O.forces.t, the torque we get from this command, the action point is the center of the inscribed circle of that facet. which means the length in the torque equation (torque = force.cross*length) is the distance between the contact point where the contact force happens and the center of the inscribed circle of that facet.

(2) for this command: utils.sumTorques----- we can set the axis Point by ourselves at anywhere. (whether the action point is the center of the inscribed center of the facet or point at the center of the cylinder)

If I want to calculate the torque for a cylinder, it seems these two methods don't work. because in my opinion, the action point for each contact force isn't the same. the action length for each contact force is the radius of the cylinder.

I don't know whether my opinion is correct or not, you can correct me if I'm wrong.

thanks
Yong

 Jan Stránský (honzik) said on 2020-04-28: #11

(1) correct (more or less :-)
you need a vector for cross product, not just a length.
the branch vector = contactPoint - pos
torque = branch.cross(force), which is opposite to force.cross(branch)

(2)
TLTR: have a look at a basic materials for mechanics concerning forces, moments, sums, equlibrium...

I did not get the meaning correctly, but I think I got the confusion.

All this is about force and moment (non)equilibrium.
Consider a rigid body.

Consider a torque applied to the body. From the point of view of force and moment (non)equilibrium, it does not matter where it acts, you can shift it to any point with the same effect (the equilibrium / amount of non-equilibrium remains the same).

Consider a force applied to the body. From the point of view of force and moment (non)equilibrium, you can shift it only across its action line to have the same effect. You can shift it to any point, but then you have to adjust the torque at this point = branch.cross(force) to preserve the equilibrium / amount of non-equilibrium the same.

You can do this with multiple torques and forces, e.g. to get one sum force and torque with respect to a special point.
You can do this multiple times, i.e. shift the force and then shift the new force-torque couple again.

For the case of one single body, you have multiple interactions, at each contact point you may have torque and force.
For easier manipulation, all these forces and torques are expressed with one force and one torque with respect to b.state.pos.
(this is the value stored in O.forces)

For multiple bodies, you can:
- shift torques and forces w.r.t b.state.pos (from O.forces) to the special point
- shift torques and forces from individual interactions to the special point
the result is the same

I suggest to experiment with a few (e.g. 3) bodies to get some feeling about it.

cheers
Jan

 nobody (nobody01) said on 2020-04-29: #12

Hi Jan,

thanks!

 nobody (nobody01) said on 2020-04-29: #13

Thanks Jan Stránský, that solved my question.