antenna-cad
Compile antenna and phased-array design intent into simulation-ready KiCad PCB layouts.
antenna-cad is a Python design compiler for printed antennas. You describe requirements
(frequency, substrate, polarization, gain); it synthesizes geometry, writes a
DRC-checkable .kicad_pcb, simulates the layout with openEMS, and reports predicted
performance against the requirements. Every step is deterministic and runs headlessly,
with no KiCad GUI and no LLM in the loop. Agents can drive the same typed API, but
nothing depends on one.
A 4×4 corporate-fed patch array at 10 GHz: synthesized, routed, DRC-checked, and full-wave simulated from a 15-line spec file. No human drew any copper.
From spec to verified board
design:
name: array_2x2_10ghz
requirements:
center_frequency: 10 GHz
impedance: 50 ohm
substrate: RO4350B
substrate_height: 0.508 mm
element:
type: rectangular_patch
array:
nx: 2
ny: 2
spacing: 0.6 lambda
pip install antenna-cad
antenna-cad report spec.yaml -o build/ --tune
That one command synthesizes the patches and the corporate feed (quarter-wave transformers, phase-compensated mirrored rows), emits a KiCad board, runs real KiCad DRC, simulates the exact layout in openEMS FDTD, iterates a simulate-and-correct tuning loop, and writes a verification report:
| Board (KiCad render) | Return loss | Radiation pattern |
|---|---|---|
Measured for this 2×2 (openEMS, tuned): resonance 10.12 GHz against the 10 GHz target, S11 −14.8 dB, directivity 12.8 dBi, gain 11.7 dBi, single broadside beam.
flowchart LR
S[spec.yaml] --> SYN[analytic synthesis]
SYN --> IR[typed design IR]
IR --> K[KiCad board + DRC]
IR --> EM[openEMS FDTD]
EM --> R[report + metrics]
R -->|simulate-and-correct| SYN
K --> FAB[Gerbers / STEP]
Verified examples
| Example | Result (openEMS) | |
|---|---|---|
| Single patch, 10 GHz | f_res 9.84 GHz, S11 −11.5 dB, D 6.8 dBi | |
| 2×2 corporate-fed array | tuned: f_res 10.12 GHz, S11 −14.8 dB, D 12.8 dBi, gain 11.7 dBi | |
| 4×4 corporate-fed array | D 16.8 dBi, gain 15.4 dBi, −13 dB E-plane sidelobes; match limited to −8 dB (why) |
Every number above is a real openEMS result from the committed example specs; the
figures rebuild from checked-in run data with uv run python figures/make_figures.py.
Design principles
- Compiler, not file generator. The source of truth is a typed internal representation of the design — geometry, stackup, nets, ports, constraints, units. KiCad, Gerber, and solver files are build artifacts compiled from it.
- Deterministic core. The same spec produces the same board, byte for byte.
Verification runs through real engines: KiCad DRC (
kicad-cli) and full-wave FDTD (openEMS). - Physical quantities carry units (via pint).
10 GHzand8.42 mmare values in the API; bare floats cross into backends only at explicit conversion boundaries. - Narrow scope by design. This targets the structures printed antennas need (patches, microstrip lines, impedance transformers, feed trees, ground pours, via fences) rather than general PCB autorouting or schematic capture.
Install
pip install antenna-cad # core: synthesis, IR, KiCad emission
pip install "antenna-cad[pam]" # + phased-array-modeling lattice interop
pip install "antenna-cad[mcp]" # + MCP server for agents
pip install "antenna-cad[dxf]" # + DXF export
KiCad 8+ provides DRC, rendering, and manufacturing export (brew install --cask kicad on macOS; distribution package kicad on Linux). openEMS runs natively where
its Python bindings are installed, or reproducibly in Docker:
docker build -t antenna-cad-openems docker/
For agents (MCP)
The same pipeline is exposed as typed MCP tools — synthesize, layout, DRC, simulate, report, export — so an agent can iterate designs against real DRC and full-wave feedback instead of hallucinating copper:
pip install "antenna-cad[mcp]"
antenna-cad mcp serve
{
"mcpServers": {
"antenna-cad": {"command": "antenna-cad", "args": ["mcp", "serve"]}
}
}
Citing
If antenna-cad contributes to academic work, please cite it (GitHub's "Cite this repository" button uses CITATION.cff; an archival DOI is planned):
@software{hodge2026antennacad,
author = {Hodge, John},
title = {antenna-cad: a design compiler for antenna and phased-array {PCBs}},
year = {2026},
version = {0.1.1},
url = {https://github.com/jman4162/antenna-cad},
license = {MIT}
}
License
MIT
Download files
Download the file for your platform. If you're not sure which to choose, learn more about installing packages.
Source Distribution
Built Distribution
Filter files by name, interpreter, ABI, and platform.
If you're not sure about the file name format, learn more about wheel file names.
Copy a direct link to the current filters
File details
Details for the file antenna_cad-0.1.1.tar.gz.
File metadata
- Download URL: antenna_cad-0.1.1.tar.gz
- Upload date:
- Size: 593.4 kB
- Tags: Source
- Uploaded using Trusted Publishing? Yes
- Uploaded via: twine/7.0.0 CPython/3.13.14
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
1641cb42d3e4709344257a9ea47149ecb1b49539f62b29dcaf9ade5aa4e62ede
|
|
| MD5 |
9f57f9403ef0f0661267192177f5f6a9
|
|
| BLAKE2b-256 |
6c8afcc78b09ef0779700041798dd54d99f7db2f50ecfec4efe69d85b422d18c
|
Provenance
The following attestation bundles were made for antenna_cad-0.1.1.tar.gz:
Publisher:
release.yml on jman4162/antenna-cad
-
Statement:
-
Statement type:
https://in-toto.io/Statement/v1 -
Predicate type:
https://docs.pypi.org/attestations/publish/v1 -
Subject name:
antenna_cad-0.1.1.tar.gz -
Subject digest:
1641cb42d3e4709344257a9ea47149ecb1b49539f62b29dcaf9ade5aa4e62ede - Sigstore transparency entry: 2422736941
- Sigstore integration time:
-
Permalink:
jman4162/antenna-cad@5644e397d34e50de25dcec8b75fa8e2cdaed6e2e -
Branch / Tag:
refs/tags/v0.1.1 - Owner: https://github.com/jman4162
-
Access:
public
-
Token Issuer:
https://token.actions.githubusercontent.com -
Runner Environment:
github-hosted -
Publication workflow:
release.yml@5644e397d34e50de25dcec8b75fa8e2cdaed6e2e -
Trigger Event:
push
-
Statement type:
File details
Details for the file antenna_cad-0.1.1-py3-none-any.whl.
File metadata
- Download URL: antenna_cad-0.1.1-py3-none-any.whl
- Upload date:
- Size: 66.9 kB
- Tags: Python 3
- Uploaded using Trusted Publishing? Yes
- Uploaded via: twine/7.0.0 CPython/3.13.14
File hashes
| Algorithm | Hash digest | |
|---|---|---|
| SHA256 |
a909c982e358022b531f5b9997eaee5c8b6e666fed0225c6e73a052eae82c526
|
|
| MD5 |
60f4f1f1d8ce089e5c515f5dd4fea891
|
|
| BLAKE2b-256 |
0c0dc62f7211aad67a9cdbafebc936c5bb62ccbfdd39d531a23e7486a55b59a1
|
Provenance
The following attestation bundles were made for antenna_cad-0.1.1-py3-none-any.whl:
Publisher:
release.yml on jman4162/antenna-cad
-
Statement:
-
Statement type:
https://in-toto.io/Statement/v1 -
Predicate type:
https://docs.pypi.org/attestations/publish/v1 -
Subject name:
antenna_cad-0.1.1-py3-none-any.whl -
Subject digest:
a909c982e358022b531f5b9997eaee5c8b6e666fed0225c6e73a052eae82c526 - Sigstore transparency entry: 2422737406
- Sigstore integration time:
-
Permalink:
jman4162/antenna-cad@5644e397d34e50de25dcec8b75fa8e2cdaed6e2e -
Branch / Tag:
refs/tags/v0.1.1 - Owner: https://github.com/jman4162
-
Access:
public
-
Token Issuer:
https://token.actions.githubusercontent.com -
Runner Environment:
github-hosted -
Publication workflow:
release.yml@5644e397d34e50de25dcec8b75fa8e2cdaed6e2e -
Trigger Event:
push
-
Statement type: