Standalone openEMS FDTD Model#

This tutorial tells you how to simulate an openEMS model that you have already. You do not have to build the geometry again. All the simpleEMS tools apply to the results.

Model structure#

The model must contain the FDTD simulation settings and the CSXCAD properties and primitives. The openEMS Write2XML method writes a model of this type. Its root element is <openEMS>.

The model must also contain a mesh and a minimum of one port.

Important

simpleEMS finds the ports by their names. The names must agree with the names that openEMS.ports.LumpedPort gives them:

  • port_resist_<N> — the lumped element

  • port_excite_<N> — the excitation

  • port_ut_<N> — the voltage probe

  • port_it_<N> — the current probe

<N> is the port number. simpleEMS ignores a port with different names, and then stops with a RuntimeError because it found no ports.

A supported model looks like this:

<?xml version="1.0" encoding="UTF-8" standalone="yes" ?>
<openEMS>
    <FDTD NumberOfTimesteps="90000000" endCriteria="0.0001" OverSampling="4" TimeStepMethod="3">
        <Excitation Type="0" f0="1.5e+09" fc="5e+08" />
        <BoundaryCond xmin="PML_8" xmax="PML_8" ymin="PML_8" ymax="PML_8" zmin="PML_8" zmax="PML_8" />
    </FDTD>
    <ContinuousStructure CoordSystem="0">
        <RectilinearGrid DeltaUnit="0.001" CoordSystem="0">
            <XLines Qty="63">-127.625,-119.498166666667,-111.371333333333,-103.2445,-95.1176666666667,-86.9908333333333,-84.7750845310792,-82.3671923877018,-79.6088933514799,-76.4491946938185,-72.8296830034176,-68.6834442963866,-63.9338269761073,-58.4930247736574,-52.2604534715882,-45.120891401516,-37.3031435708078,-30.7691019057279,-25.3079766039755,-20.7435904108436,-16.9286950973505,-13.7402211959067,-11.0753077488116,-8.84798398828371,-6.98639589820163,-5.43048818574849,-4.13006688279287,-3.04318007604617,-2.13476452795024,-1.26541666666667,-0.632708333333333,0,0.632708333333333,1.26541666666667,2.13476452795024,3.04318007604617,4.13006688279287,5.43048818574849,6.98639589820163,8.84798398828371,11.0753077488116,13.7402211959067,16.9286950973505,20.7435904108436,25.3079766039755,30.7691019057279,37.3031435708078,45.120891401516,52.2604534715882,58.4930247736574,63.9338269761073,68.6834442963866,72.8296830034176,76.4491946938185,79.6088933514799,82.3671923877018,84.7750845310792,86.9908333333333,95.1176666666667,103.2445,111.371333333333,119.498166666667,127.625</XLines>
            <YLines Qty="61">-138.153,-130.026166666667,-121.899333333333,-113.7725,-105.645666666667,-97.5188333333333,-95.3059879400733,-92.8754104955498,-90.0648935051471,-86.8150461196463,-83.0571937155825,-78.7119266874351,-73.68742239198,-67.8775047847275,-61.1594007453708,-53.3911456797082,-45.6016360838628,-38.9014349368455,-33.1382100690777,-28.1809318997136,-23.9168944185642,-20.2491527628687,-17.0943191310363,-14.3806669224394,-12.0465,-10.03875,-8.031,-6.02325,-4.0155,-2.00775,0,2.00775,4.0155,6.02325,8.031,10.03875,12.0465,14.3806669224394,17.0943191310363,20.2491527628687,23.9168944185642,28.1809318997136,33.1382100690777,38.9014349368455,45.6016360838628,53.3911456797082,61.1594007453708,67.8775047847275,73.68742239198,78.7119266874351,83.0571937155825,86.8150461196463,90.0648935051471,92.8754104955498,95.3059879400733,97.5188333333333,105.645666666667,113.7725,121.899333333333,130.026166666667,138.153</YLines>
            <ZLines Qty="27">-42.0705000000015,-33.7947658350225,-26.8620629420291,-21.054436881986,-16.1893040508389,-12.1137115075184,-8.6995283483602,-5.83941745150834,-3.44346094860422,-1.43633333333333,-0.0175,0.266666666666667,0.533333333333333,0.8,1.0666666666652,1.33333333333186,1.61749999999853,3.03633333333186,5.04346094860275,7.43941745150687,10.2995283483587,13.7137115075169,17.7893040508374,22.6544368819845,28.4620629420276,35.3947658350211,43.6705</ZLines>
        </RectilinearGrid>
        <BackgroundMaterial Epsilon="1" Mue="1" Kappa="0" Sigma="0" />
        <ParameterSet />
        <Properties>
            <Material ID="0" Name="substrate" Isotropy="1">
                <FillColor R="15" G="138" B="0" a="100" />
                <EdgeColor R="15" G="138" B="0" a="100" />
                <Primitives>
                    <Box Priority="0">

The full file is examples/structure.xml.

if the model is missing these information or you want to modify it refer to the section below on how to do it.

Models with geometry only#

The CSXCAD Write2XML method writes a different model. The root element of that model is <ContinuousStructure>. It contains the mesh, the materials, the metals, the ports, and the probes, but no simulation settings. The excitation, the boundary conditions, and the run limits are all absent.

You cannot simulate such a model. simulate_model stops and shows a ValueError that tells you to add the settings first.

Use simpleEMS.fdtd_standalone_model.add_fdtd_setup() to add the simulation settings and write a complete model:

from simpleEMS import add_fdtd_setup, simulate_model

xml = add_fdtd_setup(
    "structure.xml",                       # root <ContinuousStructure>
    freq_range=(1e9, 2e9),                 # Hz
    FDTD_boundary=["MUR"] * 4 + ["PML_8"] * 2,
    overwrite=True,                        # replace an earlier result
)
sim_data, sim, charac_imp, nf2ff_box = simulate_model(xml)

add_fdtd_setup writes the result to structure_fdtd.xml, in the Sim_Path directory of the current directory. Give output_xml_path to write it somewhere else.

Caution

add_fdtd_setup does not replace a file that exists already. It stops with a FileExistsError. Give overwrite=True to replace the file, as above.

add_fdtd_setup also accepts a complete model and replaces its simulation settings. Use this to change the frequency band or the boundary conditions of a model. It does not change the geometry.

The default excitation is a Gaussian pulse, which sets a frequency band in the model. Give excitation="sinus", "dirac", or "step" for a different one. These three set no band, so you must then give freqs to simulate_model.

Simulate the model#

Use simpleEMS.fdtd_standalone_model.simulate_model() to load the model and simulate it.

Note

simulate_model shows the geometry in AppCSXCAD before the solver runs. Close the AppCSXCAD window to continue.

These arguments control the function:

  • output_path — the directory for the results. The default is the Sim_Path directory of the current directory.

  • num_points — the number of frequency points in the results. The default value is 1000.

  • freqs — the frequency points to report the results at. The default is the band of the model’s own excitation. Give this argument to use a smaller band, or when the excitation sets no band.

  • run — whether to run the solver. The default value is True. Set it to False to examine the results of an earlier run again.

The function returns three items:

  • sim_data — the S-parameters, the impedance, the VSWR, and the port power

  • sim — the CSXCAD geometry and the FDTD solver

  • charac_imp — the characteristic impedance, read from the model’s own port

Use all three to examine and export the results.

Show the results#

Use the SimTools class to plot and to export the results. The same tools apply to a model that you build with simpleEMS.

Example code#

The example below loads structure.xml, simulates it, shows the results, and writes them to different formats.

#!/usr/bin/env python3
from pathlib import Path
from simpleEMS import simulate_model, SimTools

# PATH
output_path = Path(__file__).with_suffix("")
output_path.mkdir(parents=True, exist_ok=True)

field_dump = output_path / "field_dump"
field_dump.mkdir(parents=True, exist_ok=True)
# PATH

# SIMULATE
sim_data, sim, charac_imp, nf2ff = simulate_model(
    "structure.xml",
    output_path,
)
# SIMULATE

# PPROCESS
SimTools.plot_s_param(
    sim_data.freqs,
    sim_data.s11,
    sim_data.s21,
)
SimTools.plot_2d_directivity(nf2ff, sim_data.freqs[0], output_path)
SimTools.plot_impedance(sim_data.freqs, sim_data.z11)
SimTools.plot_smith_chart(sim_data.freqs, sim_data.s11)
SimTools.plot_vswr(sim_data.freqs, sim_data.vswr)
SimTools.show_plots()
SimTools.save_plots(output_path)
# PPROCESS

# EXPORT
SimTools.export_stl(sim, output_path)
SimTools.export_touchstone(
    sim_data.freqs,
    sim_data.s11,
    output_path=output_path,
    charac_imp=charac_imp,
)
SimTools.export_gerber(sim, output_path)
# EXPORT