Why does my water explode?

434 views Asked by At

I am trying to implement the Clavet method for simulating fluids in JavaScript, so debugging is a nightmare, which is why I'm asking here, hoping that someone who has gone through the same thing will tell me what I'm doing wrong.

I have it working OKAY so far:

particles basically work

But I have two problems:

1) Since in this method everything is sort of "offset" by half a step, I'm not sure how to bounce the particles off the walls correctly. Right now I take the particle's position and previous position and flip them around the crossed wall, then scale around the crossing point by a bounce factor.

my reflection method

My logic tells me that this should work. The next step in the algorithm is to update particle velocities, so I reflect the previous position also. But in practice this gives me a result which I don't understand:

too much reflected force

This shows the "forces" on the particles. The walls reflect way too much force, which keeps everything in perpetual motion.

Formula 4.58 in this paper apparently shows a way to prevent this, but I haven't been able to get it to work.

Also there's stuff in the paper I don't get, like what "we only want to reflect the velocity that was omitted in the collision" means. Why? Could someone ELI5 this stuff to me please?

2) Even when walls aren't involved, the simulation "explodes" periodically. This happens more with higher pressure:

exploding sim

This is JavaScript, so there's that, but I've gone over the code and there are no divisions by zero or situations where I can imagine a NaN happening.

I've seen some talk in the papers about sim instability, and I wonder if this is it. Most of what's in this literature is beyond me.

From what I did understand (I think), one of the ways to eliminate instability is viscosity, but I added it and it didn't help with the explosions:

viscosity doesn't prevent explosions

I can post code, but at the get-it-to-work-first stage it's kind of hard to read right now.

One final question: how do I figure out how to convert from the pseudo constants in this method to physical units?

Edit: I've discovered that the sim freezes occasionally, it seems it does produce a NaN somewhere, but Chrome catches it way too late.

2

There are 2 answers

7
Massimiliano Janes On BEST ANSWER

assuming this is a cg project without rigorous physical significance...

first of all, you should really consider using a fixed time step for your simulation code, otherwise you'll get erratic (and visually disturbing) behaviour as dt ( and error ) jitters around. If you cannot get a consistent framerate as per your final requirements, positions should be interpolated rather than simulated at non fixed time points.

regarding your wall calculations, it clearly depends on the effect you want to ultimately achieve; so, if you apply a more or less momentum preserving mirror condition ( as you're doing now ) particles will continue 'circulating' around even if a damping is applied. If you want the fluid to 'stick' to the walls somehow, you need to introduce wall forces or some other stronger dissipative effect.

I ran your code, and after setting a consistent dt and tuning viscosity and simplifying the wall calculation to simpler "if (p.px < left) p.px = left + (left - p.px)*canvas.wallBounce; else if()..." conditions I get a nice 'relaxation' behaviour ( if this is what you're looking for ). Updating also the previous position is counterproductive as it will increase wall 'reflectiveness' so to speak.

0
Davis Herring On

Obviously there's a lot here. I'm sure I can't answer it all, but here are some hopefully significant points:

About the walls: what you've implemented is called a momentum mirror. In a fluid under pressure, the momentum mirror serves to attract particles with a sort of negative surface tension (because there are no particles beyond it to repel those near the boundary). The more tightly packed particles there will generate larger forces and be more likely to cause numerical problems (especially because their teleportation tends to grant them potential energy).

About the coefficient of restitution: the simple linear scaling around the collision produces a tangential force on impact which is not typical for momentum mirrors but does tend to produce a physically realistic no-slip condition.

About the second paper you linked: I think they're trying to do something intelligent based on their point projection. However, I don't know why they merely project back to the surface (rather than computing a time of collision and then a new position based on the (reduced) new velocity thereafter).