Quick Start
This guide will get you running your first FDTD simulation in minutes.
Your First Simulation
Let’s create a simple 2D plane wave simulation using the TFSF (Total-Field/Scattered-Field) formulation:
from prismo import Simulation, TFSFSource, FieldMonitor
# Create a 2D simulation domain
sim = Simulation(
size=(2.0e-6, 2.0e-6, 0.0), # 2µm × 2µm (note: in meters!)
resolution=40e6, # 40 points per meter (40 ppµm)
boundary_conditions="pml", # Perfectly Matched Layer boundaries
pml_layers=10, # 10 grid points for PML
)
# Add a plane wave source
source = TFSFSource(
center=(1.0e-6, 1.0e-6, 0.0), # Center of domain
size=(1.0e-6, 1.0e-6, 0.0), # TFSF region size
direction="+x", # Propagate in +x direction
polarization="y", # E-field polarized in y
frequency=150e12, # 150 THz (2µm wavelength)
pulse=False, # Continuous wave
amplitude=1.0,
)
sim.add_source(source)
# Add a field monitor to record data
monitor = FieldMonitor(
center=(1.0e-6, 1.0e-6, 0.0),
size=(1.8e-6, 1.8e-6, 0.0), # Monitor region
components=["Ey"], # Record Ey component
time_domain=True,
)
sim.add_monitor(monitor)
# Run the simulation
sim_time = 50e-15 # 50 femtoseconds
sim.run(sim_time)
# Get and visualize results
time_points, ey_data = monitor.get_time_data("Ey")
print(f"Captured {len(time_points)} time steps")
print(f"Field shape: {ey_data.shape}")
Understanding the Output
The simulation will:
Create a computational grid with PML absorbing boundaries
Inject a plane wave using TFSF formulation (artifact-free)
Record the Ey field component at every time step
Return time-domain data as NumPy arrays
The ey_data array has shape (time_steps, ny, nx) where:
time_steps: Number of time steps recordedny, nx: Spatial grid dimensions
Basic Visualization
Add visualization to see the field evolution:
import matplotlib.pyplot as plt
import numpy as np
# Plot the final field distribution
plt.figure(figsize=(10, 8))
vmax = np.max(np.abs(ey_data)) * 0.8
plt.imshow(
ey_data[-1], # Last time step
cmap="RdBu_r",
vmin=-vmax,
vmax=vmax,
origin="lower",
extent=[0, 2.0, 0, 2.0], # Physical dimensions in µm
)
plt.colorbar(label="Ey (V/m)")
plt.xlabel("x (µm)")
plt.ylabel("y (µm)")
plt.title("Electric Field at Final Time")
plt.tight_layout()
plt.show()
Key Concepts
Units
Prismo uses SI units throughout:
Length: meters (m)
Time: seconds (s)
Frequency: Hertz (Hz)
Fields: V/m (electric), A/m (magnetic)
💡 Tip: For convenience, use scientific notation:
1e-6for micrometers (µm)1e-15for femtoseconds (fs)1e12for THz
Grid Resolution
The resolution parameter defines spatial discretization:
Higher resolution → better accuracy, longer computation
Rule of thumb: Use at least 20 points per wavelength
For λ = 2µm at 40 ppµm: 80 points per wavelength ✓
Boundary Conditions
PML (Perfectly Matched Layer): Absorbing boundaries (default)
Prevents reflections from domain edges
Typically use 8-12 PML layers
Time Step
The time step dt is automatically calculated based on the Courant stability condition:
print(f"Time step: {sim.dt:.3e} seconds")
Common Patterns
Adding Multiple Sources
# Add multiple dipole sources
from prismo import ElectricDipole
dipole1 = ElectricDipole(
position=(0.5e-6, 1.0e-6, 0.0),
polarization="y",
frequency=150e12,
pulse=True,
pulse_width=10e-15,
)
sim.add_source(dipole1)
dipole2 = ElectricDipole(
position=(1.5e-6, 1.0e-6, 0.0),
polarization="y",
frequency=150e12,
pulse=True,
pulse_width=10e-15,
)
sim.add_source(dipole2)
Frequency-Domain Monitoring
monitor = FieldMonitor(
center=(1.0e-6, 1.0e-6, 0.0),
size=(1.8e-6, 1.8e-6, 0.0),
components=["Ey", "Ez"],
time_domain=True,
frequencies=[150e12, 200e12], # Monitor at specific frequencies
)
sim.add_monitor(monitor)
# After simulation
freq_field = monitor.get_frequency_data("Ey", 150e12)
Progress Monitoring
def progress_callback(step, total_steps, sim_time, elapsed_time):
if step % 100 == 0:
print(f"Progress: {step}/{total_steps} ({step/total_steps*100:.1f}%)")
sim.run(sim_time, progress_callback=progress_callback)
Complete Example Scripts
Check out the example scripts in the examples/ directory:
tfsf_plane_wave.py: TFSF plane wave demonstrationbasic_waveguide.py: Gaussian beam in waveguideplane_wave_validation.py: Validation against analytical solutions
Run them with:
python examples/tfsf_plane_wave.py
Next Steps
Learn about Sources and Monitors in detail
Explore Simulation Setup for advanced options
Check out Examples for more complex simulations
Read about Validation to verify your results
Troubleshooting
Simulation Takes Too Long
Reduce grid resolution
Decrease simulation time
Use smaller computational domain
Instabilities or NaN Values
Check Courant condition (should be < 1.0)
Ensure sources aren’t too strong
Verify PML boundaries are thick enough
Memory Issues
Reduce grid size or resolution
Limit monitor regions
Use selective component monitoring
For more help, see the FAQ or open an issue.