Question: Simulating water

pico
Posts: 229
Joined: Sun Sep 30, 2007 7:58 am

Question: Simulating water

Post by pico »

Hello,

i know there is currently no support for water/buoyancy in Bullet.

Do you think there is a way to simulate this with the current API?

My water is made of a x*y sized triangle mesh.
A part of it gets updated each game frame.

I want to simulate the effects when bodies fall into the water and get lifted by the buoyancy.
I also want to have the height component of my triangle mesh to add a force to the bodies within.
A racing boats speed and waves height should cause to make it 'jump'.

Maybe someone already has experience in adding water support to Bullet?

I'm definitely don't look out for a physically correct simulation. It should just give a plesant and fast enough approximation that
can be used within a game environment.

Thanks for your help
Proctoid
Posts: 18
Joined: Fri Apr 21, 2006 3:04 pm
Location: uk

Re: Question: Simulating water

Post by Proctoid »

Scan through all your game objects, if the bodies pos is below the water pos then apply an impulse to the body
- this basic method of applying impulses is also useful for explosion/wind effects etc
pico
Posts: 229
Joined: Sun Sep 30, 2007 7:58 am

Re: Question: Simulating water

Post by pico »

Proctoid wrote:Scan through all your game objects, if the bodies pos is below the water pos then apply an impulse to the body
- this basic method of applying impulses is also useful for explosion/wind effects etc
Won't this make objects jump out of the water instead of floating?
Also how can this take into account wave height or center of buoyancy?
Dirk Gregorius
Posts: 875
Joined: Sun Jul 03, 2005 4:06 pm
Location: Kirkland, WA

Re: Question: Simulating water

Post by Dirk Gregorius »

GPG 6 has a good articles buoyancy . They used it in the latest Tomb Raider . I have no experience with this apporach though...
User avatar
Erwin Coumans
Site Admin
Posts: 4232
Joined: Sun Jun 26, 2005 6:43 pm
Location: California, USA
Contact:

Re: Question: Simulating water

Post by Erwin Coumans »

Bullet should have some basic buoyancy demo indeed. If anyone can help contributing such demo that would be great.
Otherwise I will put it on the ever growing todo list.

The heightfield based water & buoyancy technique was also used in the Playstation 3 Duck Demo, and earlier discussed in some papers like:
Rapid, Stable Fluid Dynamics for Computer Graphics by James O'Brien.
Matthias Muller did some nice presentation on fluid and buoyancy at SIGGRAPH 2007:
http://www.matthiasmueller.info/talks/g ... ds2007.pdf

From this paper you can see that you can get nice looking 2d water surface animation simply by using

Code: Select all

v[i,j] +=(u[i-1,j] + u[i+1,j] + u[i,j-1] + u[i,j+1])/4 – u[i,j]
v[i,j] *= 0.99
u[i,j] += v[i,j]
This surface animation effect could be applied to the ConcaveDemo, or using the btHeightfieldTerrainShape in the VehicleDemo.

Some other link to a student project: http://projects.gscept.com/dev/?cat=4

Applying buoyancy to the rigidbodies would be implemented by applying impulses, related to the water volume the body pushes away. The GPG6 article by Erin Catto (for TombRaider) that Dirk mentions only supports polyhedra. I would like to see a more general approach in Bullet, that also supports non-tesselated spheres, cylinders, cones etc.

Erwin
Erin Catto
Posts: 324
Joined: Fri Jul 01, 2005 5:29 am
Location: Irvine
Contact:

Re: Question: Simulating water

Post by Erin Catto »

I've posted my buoyancy code here: http://www.gphysics.com/files/Buoyancy.zip

Does Bullet have a general solution to computing inertia tensors? If so, that could be adapted to compute buoyancy forces.
User avatar
Erwin Coumans
Site Admin
Posts: 4232
Joined: Sun Jun 26, 2005 6:43 pm
Location: California, USA
Contact:

Re: Question: Simulating water

Post by Erwin Coumans »

Does Bullet have a general solution to computing inertia tensors? If so, that could be adapted to compute buoyancy forces.
I expect the inertia calculations and/or approximations for the collision shapes used in Bullet to work fine with buoyancy.

The main issue is to find the buoyancy forces/impulses to apply, for a more general approach that works for non-polyhedral objects. I am thinking of a method that samples the depth in several locations on the rigidbody, similar to Matthias Muller's presentation, page 21.
Water ?Object
–Each bar below the object applies force
f= -?u?h^2g to body at its location
– ?u is the height replaced by the body,
? is water density, g is gravity
The bars in Matthias approach determine the locations for the sampling. We already have the persistent contact manifold, with the deepest penetration vector/plane, so we could sample additional depth values as if we had bars.
Erwin
Erin Catto
Posts: 324
Joined: Fri Jul 01, 2005 5:29 am
Location: Irvine
Contact:

Re: Question: Simulating water

Post by Erin Catto »

Well, computing buoyancy forces requires computing the volume and centroid of the submerged portion. If you have a method for computing the mass and inertia tensor of arbitrary volumes, then you can can use that algorithm to compute the buoyancy force.

This article also discusses sampling methods for buoyancy:
Interactive Simulation of Water Surfaces, GPG1 by Miguel Gomez (2000).

I went for an exact polyhedral approach because sampling requires an additional authoring step and a lot of extra data. But perhaps Matthias found a way to avoid the extra data.
User avatar
Erwin Coumans
Site Admin
Posts: 4232
Joined: Sun Jun 26, 2005 6:43 pm
Location: California, USA
Contact:

Re: Question: Simulating water

Post by Erwin Coumans »

Erin Catto wrote:[...] sampling requires an additional authoring step and a lot of extra data. But perhaps Matthias found a way to avoid the extra data.
Have you checked slide 21 of Matthias' notes :)? I'm curious, why would sampling require 'additional authoring and a lot of extra data' for his approach?

Matthias Mullers buoyancy Object -> Water interaction
Matthias Mullers buoyancy Object -> Water interaction
MatthiasSlide21.png (117.76 KiB) Viewed 17036 times
Thanks,
Erwin
Erin Catto
Posts: 324
Joined: Fri Jul 01, 2005 5:29 am
Location: Irvine
Contact:

Re: Question: Simulating water

Post by Erin Catto »

That picture doesn't tell me how he actually implements the algorithm. Here's how you could do it for convex shapes without extra data.

1. Form an AABB of the shape parallel to the water plane.
2. If the AABB is above the water plane then return zero force.
3. Take a face of the AABB parallel to the water plane and break it up into a grid. Say 10x10. Each grid point has an associated cell area.
4. Fire rays from the top and bottom of the AABB along the grid points, pointing inwards.
5. For the grid cells with hits, clip the grid cell column against the water plane.
6. Compute the volume of the remaining water columns and apply a force at the centroid.

So how fast can you do 200 ray casts against a general convex object? There is no culling because the rays are inside the AABB. Wouldn't it be faster to use pre-processed data that consists of points sprinkled on the surface of the shape and give the points some area (like Gomez did)?

Based on Gomez's account, I don't think you can go much coarser than 10x10. YMMV. For me, I didn't want to deal with the extra data or trying to pick a good grid size, especially when an exact solution was at hand.

Maybe I'm missing something. Do you have a faster algorithm in mind?
User avatar
Erwin Coumans
Site Admin
Posts: 4232
Joined: Sun Jun 26, 2005 6:43 pm
Location: California, USA
Contact:

Re: Question: Simulating water

Post by Erwin Coumans »

The water/buoyancy approach that Matthias outlines fits better with Bullet because it automatically support the common case of shapes defined by their supporting vertex, including sphere, box, cylinder, cone, convex hull (= point cloud) and custom shapes defined by the supporting vertex mechanism. Still, your approach for polyhedral meshes is nice (and I might add it at some stage) would be a special case that need additional triangle mesh data support in the API, which is not available at the moment.
Erin Catto wrote:That picture doesn't tell me how he actually implements the algorithm.
The heightfield is used to simulate a 2D water front that can be used for 2-way object/water interaction, as well to support GPU/shader based rendering. Splashes could be done using SPH (smoothed particle hydrodynamics).
The object is pushes by the heightfield 'bars', so you would probably need 2 raycasts for each bar hitting the object. Note that the water that is pushes away is added next to the object, which gives a nice effect (rimpled surface).
So how fast can you do 200 ray casts against a general convex object? There is no culling because the rays are inside the AABB. Wouldn't it be faster to use pre-processed data that consists of points sprinkled on the surface of the shape and give the points some area (like Gomez did)?

Maybe I'm missing something. Do you have a faster algorithm in mind?
The raycasts are all in the same direction on the same object so it lends itself for many optimizations. I expect this to be no bottlebeck.

It would be straightforward to extend the currentusing the Bullet raycast with a batch raycast with special property that the ray directions are all the same. This would reduce the initial N 'getSupportingVertex' calls into a single one. Also there might be other optimizations based on incremental updates of the persistent contact manifold: the sampling of the heightfield bars could be optimized by using rules for updating/refreshing the contact points.

So in short, it would be great to implement such heightfield-based buoyancy in Bullet asap. Anyone volunteering?

Hope this helps,
Erwin
pico
Posts: 229
Joined: Sun Sep 30, 2007 7:58 am

Re: Question: Simulating water

Post by pico »

Erwin Coumans wrote:This surface animation effect could be applied to the ConcaveDemo, or using the btHeightfieldTerrainShape in the VehicleDemo.
Erwin
Thanks Erwin.

Does 'btHeightfieldTerrainShape' recognize when the initial flat mesh gets changed? Or is it needed to force somehow a recalculation of the AABB?

Another 'off topic' question: When creating a 'new btRigidBody'. Can the initial transform.basis contain a scale+rotation or only a rotational matrix?
User avatar
Erwin Coumans
Site Admin
Posts: 4232
Joined: Sun Jun 26, 2005 6:43 pm
Location: California, USA
Contact:

Re: Question: Simulating water

Post by Erwin Coumans »

pico wrote:Does 'btHeightfieldTerrainShape' recognize when the initial flat mesh gets changed? Or is it needed to force somehow a recalculation of the AABB?
Yes, it should automatically support deformation. You can pass in the maximum height for the terrain/heightfield in the constructor. Just make it big enough, so the AABB get initialized conservatively/large enough at the start.

Code: Select all

btHeightfieldTerrainShape(int width,int height,void* heightfieldData, btScalar maxHeight,int upAxis,bool useFloatData,bool flipQuadEdges);
The btBvhTriangleMeshShape has support for deformation, using the 'refit' or 'refitPartial' methods. You need to pass in the AABB that includes the maximum deformation:

Code: Select all

	///optionally pass in a larger bvh aabb, used for quantization. This allows for deformations within this aabb
	btBvhTriangleMeshShape(btStridingMeshInterface* meshInterface, bool useQuantizedAabbCompression,const btVector3& bvhAabbMin,const btVector3& bvhAabbMax, bool buildBvh = true);

You can run the ConcaveDemo and press 'g' to see the deformation.
Another 'off topic' question: When creating a 'new btRigidBody'. Can the initial transform.basis contain a scale+rotation or only a rotational matrix?
The rigidbody world transform should not have any scaling. If you want to use scaling, you have to scale the collision shape. Non-uniform (not the same in all directions) local scaling is supported for most collision shapes. Otherwise you can use uniform scaling of collision shapes. See also the btCollisionShape::setLocalScaling method. You can also re-use the child collision shape to reduce memory using the btUniformScalingShape.

Hope this helps,
Erwin
Eternl Knight
Posts: 58
Joined: Sun Jan 22, 2006 4:31 am

Re: Question: Simulating water

Post by Eternl Knight »

I've been looking at changing the height-field collision detection & resolution (as detailed in another thread) and this seems to have similar requirements and/or implementation details. Perhaps there is a way to have both bouyancy and "volumetric" height-fields catered for in the same fashion?

The way Erwin & I discussed the implementation of a volumetric height-field (i.e. one where penetration is detected even if the object falls completely under the surface of the terrain) is that instead of just dynamically creating triangles for the surface - the height-field would create prisms for each surface triangle.

As I understand the suggestion for implementing buoyancy above, the idea would be for "box columns" (very similar to the height-field prisms) to add an upward impulse with options for detecting the amount of "water displacement" by the depth the bars are "pushed down".

The similarity seems so distinct to me that it would be a natural fit to merge the two into one concept - or am I missing something?

--EK
User avatar
Erwin Coumans
Site Admin
Posts: 4232
Joined: Sun Jun 26, 2005 6:43 pm
Location: California, USA
Contact:

Re: Question: Simulating water

Post by Erwin Coumans »

Eternl Knight wrote:I've been looking at changing the height-field collision detection & resolution (as detailed in another thread) and this seems to have similar requirements and/or implementation details. Perhaps there is a way to have both bouyancy and "volumetric" height-fields catered for in the same fashion?

As I understand the suggestion for implementing buoyancy above, the idea would be for "box columns" (very similar to the height-field prisms) to add an upward impulse with options for detecting the amount of "water displacement" by the depth the bars are "pushed down".

The similarity seems so distinct to me that it would be a natural fit to merge the two into one concept - or am I missing something?
--EK
You are right, there are a lot of similarities, so it is a good idea to keep both requirements in mind.

The main differences in my view:
I expected the buoyancy to have much lower quality 'contact', using a single raycast to push things up. The standard heightfield collision detection still needs the current full contact manifold (up to 4 points, including the deepest point), even for a single heightfield element (bar/triangle/tetrahedron). Also, the buoyancy might have objects->water feedback, by moving parts of the 'bar' above the objects away.

EK, do you have some time to help with the heightfield collision issue?
Thanks,
Erwin
Post Reply