# Physics Simulation- Angular Velocity Applications

1. Oct 30, 2008

### Requerent

Hi, I have a little problem. I recently got the nerve to try and teach myself all of the physical properties necessary to program a physics engine (the insomnia is a DIFFERENT problem). It's going much better than I could've hoped (considering I started a few days ago). My knowledge of physics is quite limited, but I'll do the best I can to explain my problem. I have presented the main question at the bottom of the post, but just to try and make sure I'm clear on the issue I've provided how I came upon the problem, seeing as I don't really know too much about physics.

My objective (and a HUGE issue in computer theory) is to handle collision detection between two rigid bodies. My algorithm works fine and I'm not having problems with it at all, but just so I can explain my problem I'm going to try and not leave anything out.

Essentially, for a physics simulation to function realistically, you must make calculations using discrete timesteps, usually equal to one frame that could be displayed (so, 1/60th of a second is a common discrete timestep), as you'll only ever need to know where an object WILL be at the end of a timestep, and not necessarily where it IS exactly.

Next Position = Position + Velocity * DiscreteTimeStep.

All points in between current position (Position) and next position (Position + Velocity * TimeStep) can be determined with an alpha variable (that is, a variable which represents all possible values between 0 and 1).

Position + Velocity * (TimeStep * Alpha). Will give us all instances of position in time at the beggining and end of the timestep (again, imagine that being 1/60th of a second).

We need to compare the distance over Alpha between two objects. When the Distance is 0 we can find a contact point (point of collision). If the resulting Alpha is larger than 1 or less than 0, then we know there won't be a collision within the discrete time step (as alpha is more like a Percentage variable).

for ( Alpha >= 0 and Alpha < 1)
Distance = (A.Position + A.Velocity * (TimeStep * Alpha)) -
(B.Position + B.Velocity * (TimeStep * Alpha))

I then set the distance to 0 and solve alpha for all possible combinations of all points on the surface of each object (it's a LOT of planar intersection tests- that's not a problem though). The Velocity for each point is the same as the center of mass (it is a rigid body after all). So this conceptually works.

Distance = (A.Position + A.Velocity * (TimeStep * Alpha)) -
(B.Position + B.Velocity * (TimeStep * Alpha))

Distance is 0 for a contact point...
(A.Position + A.Velocity * (TimeStep * Alpha)) = (B.Position +
B.Velocity * (TimeStep * Alpha))

Isolate Alpha...
Alpha = (A.Position + B.Position)/(TimeStep * (A.Velocity + B.Velocity))

Now, EVERY point between the two objects gets compared and The smallest alpha between 1 and 0 is our contact point if a contact has occurred (we only want to find ONE contact point, because after a contact point has been found, forces are applied and the projected location of the object changes, at which point we need to run all the tests over again). Alpha is most likely going to be some insane irrational floating point value, which means a computer automatically rounds it off, which means there will be a small amount of rounding error for every collision. So somewhere the Permittivity of Free Space constant needs to go... (epsilon: 8.854 187 817... x10^-12). That's certainly not my main concern at this point (but if anyone has a clue on that one it'd be helpful, though that's more of a computer science question).

If the center of mass is rotating, then the position of any given point relative to that center of mass will also move as a function of time. That means my distance formula needs to compensate for the angular rotation of the center of mass as applied to every point in the rigid body.

In other words, I have Angular velocity, the Position of all points on a Rigid body, and the center of mass.

Point Position
AngularVelocity*DiscreteTimeStep
Velocity*DiscreteTimeStep
Center of Mass

AngularVelocity and Velocity are determined by an RK4 integration method (for all values of alpha within the timestep). So my angularVelocity and Velocity are NOT constant, but with 'good guessing' I think I get them close enough (And I can already handle the velocity change from acceleration relative to alpha- or however that works :P, I just mean to say that all of these values are different at any given point in time).

Problem:
How do I apply the AngularVelocity and Velocity to a Point on a rigid body, as a function of time?

For linear velocity, it's really simple- the x,y,z values of velocity just get added to the x,y,z values of the current position of a point, and that's the next position. I use a scalar to bring it down into the desired time range and test to see, at which scaling (alpha), two given points will collide given their current velocities. I guess it's just like

When Angular Velocity is considered, I'm clueless, even though I know what the value of Angular Velocity will be.

I just need to fit AngularVelocity into the following expression somewhere--
Position + Velocity*DiscreteTimeStep*Alpha

...And I need to know exactly how to do it.

Thanks!

2. Oct 31, 2008

### schroder

If you are considering the bodies as center of masses, or as ideal points, then their angular velocity around those points should have no effect on collisions. That should hold true even if you treat the bodies as perfect spheres, The angular velocity would only have an effect on collisions if you treat each body as an extended body, and you also define the geometric definition and the starting orientation for each body. That would greatly complicate your algorithm!

3. Oct 31, 2008

### Requerent

The only way to 'truly' determine when an object collides is by plotting every point on it's surface as a function of time between an arbitrarily small amount of time, and comparing the same with another object.

If an object is spinning, any given point on the surface of a rigid body will change due to angular velocity. I'm not concerned about collisions, but collision DETECTION.

I need to be able to plot the path of any given point on the surface of the object. I know the point's position, the center of mass, Velocity, and AngularVelocity- I need to know how they can all be used to determine where a point will be after a given amount of time.

vpoint = vlinear + vangular cross (p - x)

I just ran into this equation recently, and I think it's the one I need, but I'm not sure what it means (or what the 'cross' actually means). And I'm not sure how to 'add' a linear velocity with an angularvelocity to determine the new location. Again, I'm working with a point on the surface of an irregular rigid body, so its position is HIGHLY effected by rotation and angular velocity.

4. Oct 31, 2008

### cjmdjm

So, first of all, if our object has angular velocity W, then the angle which the object will rotate during the timeStep will be:

theta = W * timeStep

Now, lets say that the object's center of mass is at 0,0. And, lets say that a point on the edge of the object is at X1,Y1. Lets call this point A. Then, after a rotation of angle theta, the new coordinates of point A will be:

X2 = X1*cos(theta) + Y1*sin(theta)
Y2 = Y1*cos(theta) - X1*sin(theta)

These formulas assume that the center of mass hasn't moved. Ill explain in a second how to handle it if the center of mass is moving. Note that these formulas can be put in matrix or vector form as well.

Now, what if the center of mass (CM) is not at 0,0? Then we just replace X1 and Y1 in the formulas above with

Xtranslated = (X1- Xcm)
Ytranslated = (Y1 - Ycm)

where Xcm and Ycm are the coordinates of the center of mass. Then we have to add Xcm and Ycm to the answer. That is, the new coordinates will be (X2 + Xcm) and (Y2 + Ycm). So, just in case this is not clear, the formulas above become:

NewX = [(OldX-Xcm)*cos(theta) + (OldY-Ycm)*sin(theta)] + Xcm
NewY = [(OldY-Ycm)*cos(theta) - (OldX-Xcm)*sin(theta)] + Ycm

Where theta = angular velocity * timeStep. Now, if the center of mass is moving, you just have to add the change in Xcm to the end of the first formula and the change in Ycm to the end of the second formula. And you can of course get the change in Xcm and Ycm from the linear velocity of the CM.

Note: these only work for 2D of course. If your sim is full 3D then, well first off Im impressed, secondly, you will need another formula for Z.

Does that help?

Heres a detailed explanation:
http://www.kwon3d.com/theory/transform/rot.html

Last edited: Oct 31, 2008
5. Oct 31, 2008

### Requerent

Heheh- yes, it's full 3D, and I'm working with irregular polyhedrons (genuses, concavity, everything, except soft bodies and inertia tensors, I dont want to break my brain yet).

Apparently there is some trick to it, I had someone explain it to me, but my angular velocity is being scaled by a variable that I need to isolate (ouch).

AngularVelocity Cross Producted with the difference of Position - Center of Mass, then added to LinearVelocity.

That finally makes sense to me (the proof does not though...). If I'm applying a scalar to angular velocity, do I need to scale it before I cross it? If so, I might just start crying (The variable I'm solving for is a part of the scalar, pulling it OUT of a cross product will be a pain...).

6. Oct 31, 2008

### cjmdjm

Yeah, what you are doing is beyond my knowledge. I have done lots of physics simulations for fun, but most of them were 2D. Some had collision detection, but not with irregular polygons/polyhedrals.

I have wanted to try writing a simulation similar to yours, but I won't have enough free time until summer. If you get yours working, I would be very curious to see it. Maybe you could post it on here for others to download/play with.

7. Nov 1, 2008

### edguy99

Consider

procedure Tmemoryform.rotatepoint(r0: real; pcx, pcy: int64; var pnewx, pnewy: int64);
var r1, r2: real;
begin
r1:=0;
if pnewy-pcy=0 then if (pnewx-pcx) >0 then r1:=r0-pi/2;
if pnewy-pcy=0 then if (pnewx-pcx) <0 then r1:=r0+pi/2;
if pnewy-pcy<0 then r1:=r0+arctan((pnewx-pcx)/(pnewy-pcy));
if pnewy-pcy>0 then r1:=r0+arctan((pnewx-pcx)/(pnewy-pcy))+pi;
r2:=sqrt(sqr(pcx*1.0-pnewx)+sqr(pcy*1.0-pnewy));
pnewx:=pcx-round(sin(r1)*r2);
pnewy:=pcy-round(cos(r1)*r2);
end;

For each timeslice you will have to calculate something along the above that repositions the 2d point (pnewx,pnewy) based on the angle r0 that it would rotate in the timeslice around center (pcx,pcy). You must apply a new r0 each timeslice as things continue to rotate unless outside forces apply.

In 3d you must do the above for the each 3d plane (xy/xz/yz). Good luck, its fun.

8. Nov 3, 2008

### Requerent

ah, I've figured it out by now. I just derive the Tangential Velocity from Angular Velocity and add it to the Linear Velocity- which makes up an Aggregate Velocity. That Velocity * Time + Position of a point = Position of that point at Time.

Thanks.