Field Simulation
Compute electric field distributions on a plane using the deterministic solver
Overview#
The solve_field() function computes the full electromagnetic field on an axis-aligned plane. Unlike the radiomap solvers which return signal strength over a grid, solve_field() returns the complex field broken down into components: line-of-sight, reflection, and diffraction.
Basic Example#
import witwin.channel as wc
scene = wc.Scene(
structures=[
wc.Structure(
name="wall",
geometry=wc.Box(
position=(0.0, 0.0, 1.5),
size=(0.25, 4.0, 3.0),
device="cuda",
),
material=wc.Material(eps_r=4.0, sigma_e=0.0),
),
],
transmitters=[
wc.Transmitter("tx", (-2.0, 0.0, 1.5)),
],
frequency=3.5e9,
device="cuda",
)
field_spec = wc.deterministic.FieldSpec(
axis="z",
position=1.5,
bounds=((-5.0, 5.0), (-5.0, 5.0)),
resolution=0.1,
ray_sampling="full_sphere",
)
result = wc.deterministic.solve_field(
scene=scene,
frequency=3.5e9,
tx_pos=(-2.0, 0.0, 1.5),
field=field_spec,
config=wc.deterministic.Config(
num_samples=512,
max_bounces=2,
max_diffraction_order=1,
),
)FieldSpec Parameters#
FieldSpec defines the receiver plane where the field is computed:
| Parameter | Default | Description |
|---|---|---|
axis | "z" | Normal axis of the measurement plane |
position | 0.0 | Position along the normal axis |
bounds | ((-8.0, 8.0), (-8.0, 8.0)) | Extent of the plane in the two tangential directions |
grid_shape | None | Fixed grid resolution as (nx, ny) |
resolution | None | Grid resolution in wavelengths. Use instead of grid_shape |
ray_sampling | "full_sphere" | Ray sampling strategy. One of "auto", "circle", "full_sphere", "hemisphere", "hemisphere_facing_monitor" |
max_diffractions | None | Override max_diffraction_order from Config for this plane |
Note
Either grid_shape or resolution must be provided. If both are given, grid_shape takes precedence.
Reading the Result#
FieldResult contains the field broken down by propagation mechanism:
total_field = result.field.total
los = result.field.los
reflection = result.field.reflection
diffraction = result.field.diffraction
total_power = result.total_power
x = result.coords.x
y = result.coords.yThe field attribute is a FieldComponents object with these components:
| Component | Description |
|---|---|
los | Line-of-sight field |
reflection | Reflected field |
diffraction | Total diffracted field |
diffraction_direct | Direct diffraction only |
diffraction_mixed | Mixed reflection-diffraction |
total | Sum of all components |
Config Parameters#
solve_field() uses the same Config as the deterministic radiomap solver:
| Parameter | Default | Description |
|---|---|---|
num_samples | 10000 | Number of rays |
max_bounces | 2 | Maximum reflection bounces |
max_diffraction_order | 1 | Maximum diffraction order |
edge_policy | None | Edge selection policy |
Next Steps#
- Solvers API — full solver reference
- Neural Networks — use field gradients for optimization