thunder4d.lensframe

Beam-following (“lens-frame”) propagation: the grid expands with the cell eigenmode, so it only has to hold the beam at the waist scale. See The lens frame for the theory.

LensFrameSimulation

class thunder4d.lensframe.LensFrameSimulation(pulse, cell, *, phi_max=0.02, gouy_step=0.05, self_steepening=True, kernels='auto', **kw)[source]

MPCSimulation running on a LensFrameSolver. It accepts every keyword argument of MPCSimulation (record_every, near_field, max_order, mode_reference, save_fields, record_mirror, slit, profile_wavelengths, profile_bandwidth, profile_axis) and has the same methods (run, checkpoint, resume, save), history keys (Recorded history) and saved file.

Parameters:
  • pulse – input Pulse on a lens-frame grid (suggest_lens_grid()), defined at the cell centre

  • cell – MPC

  • phi_max (float) – maximum peak nonlinear phase per step [rad]

  • gouy_step (float) – maximum Gouy phase per step [rad] (step in \(\zeta\) at most gouy_step × \(z_R\))

  • kernels (str) – "auto" | "numba" | "numpy", see UPPESolver

mirror_scale

\(s_m = \sqrt{1 + (d/2z_R)^2}\): scale of the grid at the mirror. Records at the cell centre are physical; mirror records (fluence_mirror, prof_mirror) are in frame coordinates: physical position = mirror_scale × frame position, physical fluence = frame fluence / mirror_scale².

LensFrameSolver

class thunder4d.lensframe.LensFrameSolver(grid, cell, *, phi_max=0.02, gouy_step=0.05, self_steepening=True, absorber_frac=0.9, absorber_order=16, kernels='auto')[source]

Split-step solver in \(\zeta\): diffraction + dispersion (half steps, merged), harmonic potential, Kerr (RK4). Subclass of UPPESolver, from which it inherits nonlinear, peak_intensity and absorb; the 3D linear operator of the standard solver is not built.

State: B (accumulated on-axis peak B-integral [rad]), nsteps, z (physical distance propagated [m]), zR, zeta_m (\(\zeta\) at the mirror), s_m, h_max (= gouy_step × zR), k0, k1, n2, kernels.

propagate_zeta(Bw, zeta_a, zeta_b)[source]

Nonlinear propagation from \(\zeta_a\) to \(\zeta_b\) within one pass (\(|\zeta| \le \zeta_m\)), adaptive step. Returns the new field.

propagate_linear_zeta(Bw, zeta_a, zeta_b)[source]

Linear propagation (no Kerr), forwards or backwards.

mirror(Bw)[source]

Bounce in the frame: spectral response of the mirror (reflectivity, GDD, TOD, measured phase) and clear aperture at the physical radius \(s_m\rho\). The curvature cancels.

z_of_zeta(zeta)[source]

\(z = z_R \tan(\zeta/z_R)\).

propagate(Aw, L) is not available (it raises): use propagate_zeta.

Functions

thunder4d.lensframe.suggest_lens_grid(cell, lambda0, lambda_min, lambda_max, pulse_fwhm, *, box_factor=6.0, points_per_waist=8.0, time_window_factor=8.0, **grid_kw)[source]

Grid for the lens frame: box = box_factor × linear waist at lambda_max, \(dx\) = waist at lambda_min / points_per_waist, time step from the spectral window, time window = time_window_factor × pulse_fwhm. Other keywords go to Grid (device, dtype, …).

Use box_factor ≈ 6 for matched Gaussians and 10–14 for top-hats, hard edges or a strong mismatch (their higher-order content is larger than the fundamental).

thunder4d.lensframe.imaged_near_field_lens(grid, E, beam, energy, cell, image_z=None, verbose=True)[source]

Lens-frame version of Pulse.imaged_near_field: near field imaged (same size for every colour) onto the plane at distance image_z from the centre (default: the mirror, \(d/2\)) with the wavefront of the cell eigenmode, then propagated back to the centre in the frame. beam is given in physical coordinates at the image plane, e.g. Beam(top_hat(1.12 * w_mirror)). Returns a Pulse.

thunder4d.lensframe.lens_frame_scale(cell)[source]

Returns (zR, zeta_m, s_m): Rayleigh range of the cell eigenmode, \(\zeta\) at the mirror and the mirror scale factor.