WIP Combining DES and PhysX to create a visualization of Physical effects
This Tutorial Requires at least Prespective build version 2021.1.1244 - a download can be found here
(see the Prespective About window)
Not all parts of your material handling may require the continous (64-bits) precision that DES enforces. Moreover, sometimes you simply want to create a quick visualization containing slow-moving free- or constrained physical bodies. This short Application Guide shows you:
(1) How you can combine DES and PhysX (Unity Physics) in a proper controlled fashion.
(2) How you can detect the two systems are not working together properly.
(3) What to expect when tweaking PhysX to resolve unexpected results
Be aware, objects controlled by DES are simulated in a continuous fashion - the objects controlled by PhysX however are not, and depend on a sufficiently small Fixed TimeStep/ Delta Time to be properly calculated - Note that the Fixed Delta Time you need to set for your setup is primarily dependant on 2 facets:
The Relative Velocity of your PhysX Rigidbodies - Fast moving objects have a tendency to ‘miss/jump over collisions'. If 2 Objects move exceedingly fast in comparison to each other (!) you’ll notice they don’t detect interacting at all (see further in this article)
The Size of your colliders - Simular to fast moving objects, if your colliders are too small (<0.01 unity units) you’ll notice collisions are not allways detected (regardless of relative velocity)
As mentioned a bit further in this article, the default fix for missed collisions is reducing the Fixed Timestep duration, but that may come at a price.
1. Overview of Prespective Features used in this Setup
Feature | Used For |
---|---|
D(ouble) Spline | Scene Path to describe the Transformation ‘plan’ of the DES Actor |
DES Controller | Controlling the DES Material Handling and simulation time multiplication Can be used to pause the simulation at a fixed point. |
DES Actor | Transforming a GameObject within the DES Material Handling Simulation |
DES MotionTensor Activity | Transformation Activity added to the DES Actor in order to move it accross the DSpline |
DES MotionTensorView | DES Actor Inspector field to ease the setup of the Motion Tensor Activity |
Baseclass of the DES Actor, allows you to switch between transforming in single (32-bits floating point) or double (64-bits) precision. In this case, also allowing you to target a (PhysX) Rigidbody | |
Double Transform | Counterpart to the Unity3D ‘Transform’ component - it makes sure that double transformations are properly enacted, and continuous double-precision simulation does not lose precision in Unitys' floating-point precision world |
1. Scene Setup
A package containing the scene can be downloaded here
(requires a project with Prespective >= v2021.1.1244 included)
Fig. 1 - Hierarchical overview of the scene
The scene contains 2 (relevant) root elements ‘DESController’ and ‘PhysxObjects’
The ‘DESController’ contains a closed square ‘Spline’ path, and a ‘MovingActor’ gameobject with a actor script that starts transforming this actor over the spline when you press play. the content of this script is explained in a different tutorial ‘1 | Setting up an actor for motion’ - and so is the use of the contained ‘MotionTensorView’ field.
Note that the ‘MovingActor’ has been fitted with a Rigidbody component set to ‘Is Kinematic’ - just adding this component to any actor will allready allow it to interact with Unity Physics (PhysX) (but not necassarily correctly!)
Fig. 2 - Settings of the Rigidbody component on the ‘MovingActor’
The ‘PhysXObjects’ contains both a constrained body (Hinge Joint) and Free bodies (non-jointed) rigidbodies to demo DES interaction. Note that ‘Pushable Lever’ uses the ‘Pushable Lever Hinge’ as its (Kinematic) Connected Body (origin to rotate around).
Fig. 3 - Hinge Joint settings on the ‘Pushable Lever’ GameObject
Fig. 4 - Rigidbody settings on the ‘PushableLeverHinge’ Gameobject
Explaining how to setup PhysX joints in unity3D is outside of this guides’ scope - however there are many great tutorials you can find online (like this one on hinges)
Furthermore, that the ‘FreeBodySphere' Gameobjects are held in place by the 'KinematicBodyFloor’ - which is a simple fixed body.
Fig. 5 - Rigidbody settings on the ‘FreeBodySphere’ Free Body GameObjects'
Fig. 6 - Simple fixed body to hold up the free bodies
2. Faulty transformation resolution Setup
Recognizing faulty motion transfer in Physx can be quite tricky, so lets start with a setup that (1) will transfer motion/force, but (2) not do it in a correct magnitude and vector.
To get this effect, start with disabling the ‘Use Rigidbody’ setting in the inspector of the ‘MovingActor’ GameObject.
Fig. 7 - Try disabling use Rigidbody first
If you enter playmode now, you’ll see the response of the Physx objects is at best ‘wobbly’ - this is caused by the lack of synchronization between the 2 Transformation Systems; DES and PhysX. The following image attempts to explain what happens:
Fig. 8 - side-view of the intersection between the Actor (Dark-red Cube) and the Lever (Green)
The dark-red outline in Fig.8 shows a side-view of the scene when the Actor hits the lever. In this particular simulation (fixed-update) frame the Actor moves from the Dark-red outline position to the yellow outline position; as it does so it actually hits the collider/rigidbody of the Lever (green) and a physical interaction is to be expected.
If we have ‘Use Rigidbody’ set to disabled/false the DES Simulation will set the transform of the actor directly to the frame end position after its done calculating.
The update of the PhysX simulation however happens in the fixed update AFTER the DES simulation is complete, as such it doesn’t know about the original (dark-red) position of the Actor, and thus also cannot predict how it got to the yellow position. It does however detect an intrusion (red fill) with the Lever body (Green), and thus (only) attempts to rectify it (so you will see movement in the rigidbodies, but it will not be correct!)
in rigidbody simulation any two rigidbodies that occupy the same space experience a so-called ‘Restitution Error’ and must thus be ‘pulled apart'
Even if you use PhysX without DES this can happen to you in Unity3D - arguably stay away from setting the transform directly when using PhysX, rather set your transform on the rigidbody:
Dont use:
transform.position = [someVector3];
Rather use:
rigidbody.movePosition([someVector3]);
2. Correct(-ish) transformation resolution Setup
To get correct(-ish) behavior, start with enabling the ‘Use Rigidbody’ setting in the inspector of the ‘MovingActor’ GameObject. If you enter playmode now the behavior will appear to be correct - and in many cases this behavior may be sufficient for visualizing an effect - but please take into account that a little bit of ‘restitution error’ will remain due to the sizable Fixed Timestep unity uses by default:
Fig. 9 - Enabling ‘Use Rigidbody’ will make your simulation look more realistic
Lets first however explain why this setting fixes the transformation conflict between DES and PhysX:
Fig. 10 - Transformation conflict resolution resolution between DES and PhysX
When ‘Use Rigidbody’ is active DES does not actually set the Transform after completing the simulation, but rather it indicates to the Rigidbody where it wants to go (light-pink outline). When Unity Physics now starts simulating it notices a difference in the starting position of the rigidbody (dark-pink outline) and our request, and thus can solve the difference - leading to a ‘proper’ physical behavior.
3. Tweaking PhysX to deal with unexpected results
PhysX uses discrete simulation frames rather than a continuous system (like with DES) to get correct physical (transformation) behavior. this automatically means 2 things:
A shorter Fixed Timestep (arguably) results in more accurate rigidbody simulation.
A different Fixed Timestep results in different transformation behaviour
What we’ll show you here - PhysX simulations are notoriously hard to get deterministic, and may thus differ in precise behaviour on differing systems, or under differing operating conditions (e.g. youtube running in the background)
In the provided scene we can sometimes easily* spot ‘an unexpected situation’ under normal timestep conditions (0.02s/ fixed update) you will notice that the collision between the ‘Moving Actor’ and ‘Pushable Hinge’ is actually missed on DES (controller) frame #249 - to be fair the actor is moving quite fast (10m/s)
*As a testament to the unpredictable behavior - sometimes the collision at frame #249 is handled properly, but in that case another one at DES frame #490 may be missed (just to complicate it further, it may only happen if you don’t pause the simulation)
If you want you can automatically pause the simulation in frame #248 by setting ‘Pause at Frame’ to 248 in the DES Controller.
Fig. 11 - DES frame #248 on Fixed Timeframe 0.02s and Actor Velocity 10m/s
Fig. 12 - DES Frame #249 on Fixed Timeframe 0.02s and Actor Velocity 10m/s - as you can seen the collision between the Actor and the Hinge was totally missed regardless of using the Rigidbody.
If you encounter such a discrepancy you can generally change the Fixed Time Step to a lower value to resolve the issue - try setting it to 0.002s (default/10); however….
Changing the Fixed Time Step affects ALL operations running on it - so expect reduced performance all around
DES also does its calculations on the Fixed Time Step, that means that you will see greatly diminished performance (fps) if you perform more complex DES transformations - even more so - you can easily GAIN performance (fps) in DES by increasing the Fixed Time Step!
There’s a limit to what you can fix - if you want to detect interactions downwards of 0.01m3 in physX, expect that they may fail in any future run, on any system or any conditions different from your current (so implement a backup detection or fall-back if a transformation goes wrong)
However, Each new version of Unity extends the settings you can change in the ‘Physics’ submenu in your project settings - at the time of reading there may well be a setting that directly solves this particular missed interaction so don’t hesitate to test them - more on what these settings are you can find on the Unity Website
Fig 13. - Changing the fixed timestep can be done in Edit > Project Settings > Time > Fixed TimeStep; by default its set to 0.02
Now lets see if this change of the fixed timestep to 0.002s has fixed our problem - DES frames scale equal to the the timestep, so we should now expect the error to occur around frame #2480, however - your frame will probably look like this:
Fig. 14 - the simulation state on DES frame #2480 at fixed timestep 0.002s
Note that the Moving Actor is on the right spot, however the lever is now following a totally different transformation.
So what happened? Arguably, the first push interaction on frame #93 now exerts force for multiple frames on the lever which will either (1) leave it (apparently) with a lot more force potential in comparison to the 0.02s, Fixed interval or (2) the easing that occurs when the leaver approaches its azimuth is calculated differently resulting in much less drag
Please also see the lever rigid body figures below, the resulting velocity at least does not explain much. Either way, a relatively small change (changing the timestep) had widescale effects on the simulation result.
Fig. 15 - Frame #13 at Fixed Interval 0.02s
Fig. 16 - Frame #135 at Fixed Interval 0.002s
So what can you take away from this exercise? lowering the Fixed Delta time may resolve missed contacts, but it may also greatly impact the flow, at unexpected points in your simulation - so, feel free to combine DES and PhysX to enrich your simulations - but when working with PhysX, (at least for now) expect the unexpected!
Prespective Documentation