Smoke¶

Google Collab Book

This example simulates a rising plume of hot smoke. It demonstrates how to advect and couple other quantities with the fluid.

In [1]:
%pip install phiflow
from phi.jax.flow import *
from tqdm.notebook import trange
# from phi.flow import *  # If JAX is not installed. You can use phi.torch or phi.tf as well.

We begin by defining our simulation size and smoke inflow.

In [2]:
domain = Box(x=100, y=100)
inflow = Sphere(x=50, y=9.5, radius=5)
inflow_rate = 0.2

Our simulation advects the velocity and smoke fields, computes the buoyancy force proportional to the smoke density, and enforces incompressibility. We sample the velocities on a $64\times 64$ staggered grid, and the smoke density on a $200\times 200$ grid.

In [16]:
@jit_compile
def step(v, s, p, dt):
    s = advect.mac_cormack(s, v, dt) + inflow_rate * resample(inflow, to=s, soft=True)
    buoyancy = resample(s * (0, 0.1), to=v)
    v = advect.semi_lagrangian(v, v, dt) + buoyancy * dt
    v, p = fluid.make_incompressible(v, (), Solve('CG', 1e-3, x0=p))
    return v, s, p

v0 = StaggeredGrid(0, 0, domain, x=64, y=64)
smoke0 = CenteredGrid(0, ZERO_GRADIENT, domain, x=200, y=200)
In [17]:
v_trj, s_trj, p_trj = iterate(step, batch(time=300), v0, smoke0, None, dt=.5, range=trange, substeps=3)
  0%|          | 0/300 [00:00<?, ?it/s]
In [20]:
plot(s_trj, animate='time', frame_time=80)
Out[20]:
Your browser does not support the video tag.