Replies: 2 comments 3 replies
-
|
Assuming that the monopole is lambda/4 in length, your distance to the simulation boundaries is too small. You need to have at least lambda/4 air margin. around the antenna on all sides. At zmax, that is measured from the upper end of the monopole. |
Beta Was this translation helpful? Give feedback.
-
|
Hello @VolkerMuehlhaus, Thanks for your response and feedback. I have added more space to the simulation box, I pointed the antenna along the Z-axis and added a finer mesh around the radiating element and the groundplane to prevent staircasing. Currently I am having these results:
Which is a lot better than before, but still not as good as I expected. I am expecting a result similar to that of my initial post (-40db, exactly around 2.4GHz). If the airbox was the problem, why does the old simulation show a more 'expected' result instead of nonsense? Updated codeimport os, tempfile
from pylab import *
from CSXCAD import ContinuousStructure
from CSXCAD import AppCSXCAD_BIN
from openEMS import openEMS
from openEMS.physical_constants import *
# Constants
NAME = 'monopole_fix'
F0 = 2e9 # center frequency
FC = 2e9 # 20 dB corner frequency
UNIT = 1e-3 # Millimeters
CPW = 40 # Cells per wavelength
RES = C0/(F0+FC) / UNIT / CPW # Resolution
METAL_RES = 32
IMPEDANCE = 50
RATIO = 1.4
DEBUG = 1
### Create folder if not exists in current folder
current_directory = os.getcwd()
Sim_Path = os.path.join(current_directory, r'simulation_output')
if not os.path.exists(Sim_Path):
os.makedirs(Sim_Path)
# size of the simulation box
xmin = -80
xmax = 80
ymin = -60
ymax = 60
zmin = -80
zmax = 80
# Method to mesh materials
def mesh_primitives(obj, axis='xyz', center_line='', fine_mesh=''):
for primitive in obj.GetAllPrimitives():
box = primitive.GetBoundBox()
mesh_primitive(box[0], box[1], axis, center_line, fine_mesh)
# Method to mesh a single primitive
def mesh_primitive(start, stop, axis='xyz', center_line='', fine_mesh=''):
# Get drawing direction
dirs = get_directions(start, stop)
# Draw edge lines for specified axis
for a in axis:
if a in 'xyz':
index = 'xyz'.index(a)
mesh.AddLine(a, start[index])
mesh.AddLine(a, stop[index])
# Draw centerline for specified axis
for a in center_line:
if a in 'xyz':
index = 'xyz'.index(a)
center = (abs((start[index] + stop[index])) / 2) * dirs[index]
mesh.AddLine(a, center)
if 'x' in fine_mesh:
mesh.AddLine('x', linspace(start[0], stop[0], METAL_RES))
if 'y' in fine_mesh:
mesh.AddLine('y', linspace(start[1], stop[1], METAL_RES))
if 'z' in fine_mesh:
mesh.AddLine('z', linspace(start[2], stop[2], METAL_RES))
# Method to mesh port
def mesh_port(port):
mesh_primitive(port.start, port.stop, center_line='xyz') # Mesh port with centerline on all axis
# Method to get drawing direction
def get_directions(start, stop):
dir_x = 1 if start[0] - stop[1] < 0 else -1
dir_y = 1 if start[1] - stop[1] < 0 else -1
dir_z = 1 if start[2] - stop[2] < 0 else -1
return [dir_x, dir_y, dir_z]
### FDTD setup
FDTD = openEMS(NrTS=30000, EndCriteria=1e-4)
FDTD.SetGaussExcite(F0, FC)
FDTD.SetBoundaryCond(['MUR', 'MUR', 'MUR', 'MUR', 'MUR', 'MUR'])
# Mesh Setup
CSX = ContinuousStructure()
FDTD.SetCSX(CSX)
mesh = CSX.GetGrid()
mesh.SetDeltaUnit(UNIT)
# Initialize the mesh with the "air-box" dimensions
mesh.AddLine('x', [xmin, xmax])
mesh.AddLine('y', [ymin, ymax])
mesh.AddLine('z', [zmin, zmax])
# Create ground
gnd = CSX.AddMetal('gnd') # create a perfect electric conductor (PEC)
gnd.AddCylinder(priority=1, start=[0, 0, -0.125], stop=[0, 0, 0], radius=31/2)
mesh_primitives(gnd, fine_mesh='xy')
# Create monopole antenna
ant = CSX.AddMetal('ant')
start = [-0.125, -0.125, 0.125]
stop = [0.125, 0.125, 31.25]
ant.AddBox(priority=1, start=start, stop=stop)
mesh_primitives(ant)
# Extra meshing for antenna
mesh.AddLine('x', linspace(start[0]-0.25, stop[0]+0.25, 10))
mesh.AddLine('y', linspace(start[1]-0.25, stop[1]+0.25, 10))
mesh.AddLine('z', linspace(start[2]-0.25, stop[2]+0.25, 50))
# Smooth mesh line with resolution
mesh.SmoothMeshLines('all', RES, RATIO)
# Excitation
start = [0.125, 0.125, 0]
stop = [-0.125, -0.125, 0.125]
port = FDTD.AddLumpedPort(1, IMPEDANCE, start, stop, 'z', 1.0, priority=5)
mesh_port(port)
# Write model
CSX_file = os.path.join(Sim_Path, '{}.xml'.format(NAME))
if not os.path.exists(Sim_Path):
os.mkdir(Sim_Path)
CSX.Write2XML(CSX_file)
# Show model
if DEBUG:
os.system(AppCSXCAD_BIN + ' "{}"'.format(CSX_file))
# Run simulation
FDTD.Run(Sim_Path, verbose=3, cleanup=True)
# Post-processing and plotting
f = np.linspace(max(1e8,F0-FC),F0+FC,401)
port.CalcPort(Sim_Path, f)
s11 = port.uf_ref/port.uf_inc
s11_dB = 20.0*np.log10(np.abs(s11))
figure()
axvline(x = 2.45, color = 'b', label = '2.45GHz', linestyle='--')
axis([0.5, 3, -50, 10])
plot(f/1e9, s11_dB, 'k-', linewidth=2, label='$S_{11}$')
grid()
legend()
ylabel('S-Parameter (dB)')
xlabel('Frequency (GHz)')
show()
Cheers |
Beta Was this translation helpful? Give feedback.



Uh oh!
There was an error while loading. Please reload this page.
Uh oh!
There was an error while loading. Please reload this page.
-
Hello,
I am having trouble with the simulation of a simple 2.4GHz monopole antenna. The result of the simulation seems to vary when changing the simulation box. Whenever i use a box of dimensions [50, 70, 20], I get a beautiful 2.4GHz resonance.
However, when i use a box of dimensions [50, 70, 40], I get a very different result.
I do not understand why this happens, as the resolution stays the same, it is just more cells in the simulation. I am not using automeshing, but also with automeshing i get the same result. The code is available in the spoiler below.
So I have 3 questions
I am probably lacking some crucial knowledge in FDTD simulations
Thanks in advance!
Bart
See code
Beta Was this translation helpful? Give feedback.
All reactions