Skip to content

Commit

Permalink
Zero thickness for volumetric equivalence of 2D material
Browse files Browse the repository at this point in the history
Different subclass for volumeric equivalence of Medium2D

Filter out zero coefficient poles in volumetric equivalent with zero size 2d materials: there is no need to perform intersections with previously added 2d materials in _volumetric_structures_grid
  • Loading branch information
weiliangjin2021 committed Apr 23, 2024
1 parent 95919b8 commit 9c2631d
Show file tree
Hide file tree
Showing 4 changed files with 16 additions and 21 deletions.
4 changes: 1 addition & 3 deletions tests/test_components/test_grid_spec.py
Original file line number Diff line number Diff line change
Expand Up @@ -116,9 +116,7 @@ def test_autogrid_2dmaterials():
)
assert np.isclose(sim.volumetric_structures[0].geometry.bounding_box.center[2], 1, rtol=RTOL)
grid_dl = sim.discretize(box.geometry).sizes.z[0]
assert np.isclose(
sim.volumetric_structures[0].geometry.bounding_box.size[2], grid_dl, rtol=RTOL
)
assert np.isclose(sim.volumetric_structures[0].geometry.bounding_box.size[2], 0, rtol=RTOL)

# now if we increase conductivity, the in-plane grid size should decrease
sigma2 = 4.5
Expand Down
4 changes: 2 additions & 2 deletions tests/test_components/test_simulation.py
Original file line number Diff line number Diff line change
Expand Up @@ -2003,10 +2003,10 @@ def test_sim_volumetric_structures(log_capture, tmp_path): # noqa F811
)
if isinstance(struct.geometry, td.Box):
assert np.isclose(
sim.volumetric_structures[0].geometry.bounding_box.size[2], grid_dl, rtol=RTOL
sim.volumetric_structures[0].geometry.bounding_box.size[2], 0, rtol=RTOL
)
else:
assert np.isclose(sim.volumetric_structures[0].geometry.length_axis, grid_dl, rtol=RTOL)
assert np.isclose(sim.volumetric_structures[0].geometry.length_axis, 0, rtol=RTOL)
assert np.isclose(
sim.volumetric_structures[0].medium.xx.to_medium().conductivity,
sigma * thickness / grid_dl,
Expand Down
14 changes: 11 additions & 3 deletions tidy3d/components/medium.py
Original file line number Diff line number Diff line change
Expand Up @@ -4477,6 +4477,12 @@ def sel_inside(self, bounds: Bound):
return self.updated_copy(**dict(zip(["xx", "yy", "zz"], new_comps)))


class AnisotropicMediumFromMedium2D(AnisotropicMedium):
"""The same as ``AnisotropoicMeidum``, but converted from Medium2D.
(This class is for internal use only)
"""


class FullyAnisotropicMedium(AbstractMedium):
"""Fully anisotropic medium including all 9 components of the permittivity and conductivity
tensors.
Expand Down Expand Up @@ -5358,7 +5364,7 @@ def _weighted_avg(
return med
else:
raise ValidationError("Invalid medium type for the components of 'Medium2D'.")
poles += [(a, weight * c) for (a, c) in pole_res.poles]
poles += [(a, weight * c) for (a, c) in pole_res.poles if c != 0.0]
return PoleResidue(eps_inf=np.real(eps_inf), poles=poles)

def volumetric_equivalent(
Expand Down Expand Up @@ -5430,7 +5436,9 @@ def get_background(comp: Axis) -> PoleResidue:
ax_coord=media_bg[axis], plane_coords=media_fg_weighted, axis=axis
)
media_3d_kwargs = {dim + dim: medium for dim, medium in zip("xyz", media_3d)}
return AnisotropicMedium(**media_3d_kwargs, frequency_range=self.frequency_range)
return AnisotropicMediumFromMedium2D(
**media_3d_kwargs, frequency_range=self.frequency_range
)

def to_anisotropic_medium(self, axis: Axis, thickness: float) -> AnisotropicMedium:
"""Generate a 3D :class:`.AnisotropicMedium` equivalent of a given thickness.
Expand Down Expand Up @@ -5667,7 +5675,7 @@ def is_comp_pec_2d(self, comp: Axis, axis: Axis):

# types of mediums that can be used in Simulation and Structures

MediumType = Union[MediumType3D, Medium2D]
MediumType = Union[MediumType3D, Medium2D, AnisotropicMediumFromMedium2D]


# Utility function
Expand Down
15 changes: 2 additions & 13 deletions tidy3d/components/simulation.py
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@
from .geometry.base import Geometry, Box
from .geometry.mesh import TriangleMesh
from .geometry.utils import flatten_groups, traverse_geometries
from .geometry.utils_2d import get_bounds, increment_float, set_bounds, get_thickened_geom
from .geometry.utils_2d import get_bounds, set_bounds, get_thickened_geom
from .geometry.utils_2d import subdivide, snap_coordinate_to_grid
from .types import Ax, FreqBound, Axis, annotate_type, InterpMethod, Symmetry
from .types import Literal, TYPE_TAG_STR
Expand Down Expand Up @@ -1245,7 +1245,6 @@ def snap_to_grid(geom: Geometry, axis: Axis) -> Geometry:
avg_axis_dl = get_dls(geometry, axis, 1)[0]
subdivided_geometries = subdivide(geometry, axis, avg_axis_dl, background_structures)
# Create and add volumetric equivalents
background_structures_temp = []
for subdivided_geometry in subdivided_geometries:
# Snap to the grid and create volumetric equivalent
snapped_geometry = snap_to_grid(subdivided_geometry[0], axis)
Expand All @@ -1258,21 +1257,11 @@ def snap_to_grid(geom: Geometry, axis: Axis) -> Geometry:
axis=axis, adjacent_media=adjacent_media, adjacent_dls=dls
)

new_bounds = (snapped_center - dls[0] / 2, snapped_center + dls[1] / 2)
temp_geometry = set_bounds(snapped_geometry, bounds=new_bounds, axis=axis)
temp_structure = structure.updated_copy(geometry=temp_geometry, medium=new_medium)

if structure.medium.is_pec:
pec_plus = increment_float(snapped_center, 1.0)
pec_minus = increment_float(snapped_center, -1.0)
new_bounds = (pec_minus, pec_plus)
new_bounds = (snapped_center, snapped_center)
new_geometry = set_bounds(snapped_geometry, bounds=new_bounds, axis=axis)
new_structure = structure.updated_copy(geometry=new_geometry, medium=new_medium)

new_structures.append(new_structure)
background_structures_temp.append(temp_structure)

background_structures += background_structures_temp

return tuple(new_structures)

Expand Down

0 comments on commit 9c2631d

Please sign in to comment.