Note
Go to the end to download the full example code.
Biased droplet dynamics
Demonstrates how droplet dynamics can be biased using an external field, which is here read from an image.

0%| | 0/10.0 [00:00<?, ?it/s]
Initializing: 0%| | 0/10.0 [00:00<?, ?it/s]
0%| | 0/10.0 [00:05<?, ?it/s]
1%| | 0.1/10.0 [00:07<12:17, 74.52s/it]
2%|▏ | 0.2/10.0 [00:07<06:05, 37.26s/it]
3%|▎ | 0.3/10.0 [00:07<04:00, 24.84s/it]
3%|▎ | 0.3/10.0 [00:07<04:00, 24.84s/it]
100%|██████████| 10.0/10.0 [00:07<00:00, 1.34it/s]
100%|██████████| 10.0/10.0 [00:07<00:00, 1.34it/s]
from numba import jit
from droplets import SphericalDroplet
from pde import CartesianGrid, ScalarField, UnitGrid, get_backend
import emulsim
# set up state
grid = UnitGrid([32, 32], periodic=True)
background = emulsim.ScalarFieldElement.from_field(ScalarField(grid, 0.1))
droplet_data = [SphericalDroplet(grid.get_random_point(), 1) for _ in range(3)]
droplets = emulsim.SphericalDropletsElement.from_droplets(droplet_data)
state = emulsim.State({"background": background, "droplets": droplets})
# define how the equilibrium concentration is calculated
class cEqOutField:
"""Class calculating equilibrium concentrations based on a field."""
def __init__(self, image: ScalarField):
self.image = image
def __call__(self, position, radius, droplet_id):
"""Return equilibrium concentration for a position."""
return 1e-2 * self.image.interpolate(position)
def get_function(self, backend):
"""Return compiled function for calculating c_eq for a position."""
interpolate = get_backend("numba").make_interpolator(self.image)
image_data = self.image.data
@jit
def c_eq(position, radius, droplet_id):
return 1e-2 * interpolate(position, image_data)
return c_eq
# set up random field used as the defining image
image_grid = CartesianGrid(grid.axes_bounds, 16, periodic=grid.periodic)
image = ScalarField.random_uniform(image_grid)
# set up simulation
simulation = emulsim.Simulation(state)
simulation.add_actor("background", emulsim.DiffusionActor())
parameters = {"equilibrium_concentration": cEqOutField(image)}
simulation.add_actor(
("droplets", "background"), emulsim.SphericalDropletActor(parameters)
)
# run simulation
result = simulation.run(t_range=10)
result.plot()
Total running time of the script: (0 minutes 7.553 seconds)