def _example(): from gdshelpers.geometry.chip import Cell from gdshelpers.parts.waveguide import Waveguide from gdshelpers.parts.resonator import RingResonator # ==== create some sample structures (straight line with ring resonator) wg = Waveguide(origin=(0, 0), angle=np.deg2rad(-90), width=1) wg.add_straight_segment(length=5) wg.add_bend(np.pi / 2, 5) wg2 = Waveguide.make_at_port(wg.current_port) wg2.add_straight_segment(15) reso = RingResonator.make_at_port(port=wg2.current_port, gap=0.2, radius=5) wg2.add_straight_segment(length=15) coupler2 = GratingCoupler.make_traditional_coupler_from_database_at_port( wg2.current_port, db_id='si220', wavelength=1550) underetching_parts = geometric_union([wg2, reso, coupler2]) structure = geometric_union([underetching_parts, wg]) # create the holes with a radius of 0.5 microns, a distance of 2 microns to the structure borders and # a distance of 2 microns between the holes holes = create_holes_for_under_etching(underetch_parts=underetching_parts, complete_structure=structure, hole_radius=0.5, hole_distance=2, hole_spacing=3, hole_length=3) # create a cell with the structures in layer 1 and the holes in layer 2 cell = Cell('CELL') cell.add_to_layer(1, structure) cell.add_to_layer(2, holes) # Show the cell cell.show()
def test_waveguide_construction(self): wg = Waveguide([0, 0], 0, 1) self.assertAlmostEqual(wg.length, 0) # Add straight waveguide wg.add_straight_segment(10) self.assertAlmostEqual(wg.x, 10) self.assertAlmostEqual(wg.y, 0) self.assertAlmostEqual(wg.angle, 0) self.assertAlmostEqual(wg.length, 10) # Add upwards 90 degree bend wg.add_bend(math.pi / 2, 5) self.assertAlmostEqual(wg.current_port.origin[0], 15) self.assertAlmostEqual(wg.current_port.origin[1], 5) self.assertAlmostEqual(wg.current_port.angle, math.pi / 2) self.assertAlmostEqual(wg.length_last_segment, math.pi / 2 * 5, delta=10e-5) # Add another arc, so that we are finally pointing 180 degree backwards wg.add_arc(math.pi, 5) self.assertAlmostEqual(wg.current_port.origin[0], 10) self.assertAlmostEqual(wg.current_port.origin[1], 10) self.assertAlmostEqual(abs(wg.current_port.angle), math.pi)
def test_export_import(self): waveguide = Waveguide([0, 0], 0, 1) for i_bend in range(9): waveguide.add_bend(angle=np.pi, radius=60 + i_bend * 40) offset = (10, 10) angle = np.pi cell = Cell('test') cell.add_to_layer(1, waveguide) sub_cell = Cell('sub_cell') sub_cell.add_to_layer(2, waveguide) cell.add_cell(sub_cell, origin=(0, 0), angle=0) sub_cell2 = Cell('sub_cell2') sub_cell2.add_to_layer(3, waveguide) cell.add_cell(sub_cell2, origin=offset, angle=angle) cell.save(grid_steps_per_micron=10000) def assert_almost_equal_shapely(a, b, tolerance=2e-4): self.assertTrue(a.buffer(tolerance).contains(b)) self.assertTrue(b.buffer(tolerance).contains(a)) assert_almost_equal_shapely( waveguide.get_shapely_object(), GDSIIImport('test.gds', 'test', 1).get_shapely_object()) assert_almost_equal_shapely( waveguide.get_shapely_object(), GDSIIImport('test.gds', 'test', 2).get_shapely_object()) assert_almost_equal_shapely( translate(rotate(waveguide.get_shapely_object(), angle, use_radians=True, origin=(0, 0)), *offset), GDSIIImport('test.gds', 'test', 3).get_shapely_object()) self.assertTrue(GDSIIImport('test.gds', 'test', 1, 2).get_shapely_object().is_empty)
def test_parallel_export(self): waveguide = Waveguide([0, 0], 0, 1) for i_bend in range(9): waveguide.add_bend(angle=np.pi, radius=60 + i_bend * 40) cells = [Cell('main')] for i in range(10): cell = Cell('sub_cell_' + str(i)) cell.add_to_layer(waveguide) cells[-1].add_cell(cell, (10, 10)) cells[0].save('serial.gds', library='gdshelpers', parallel=False) cells[0].save('parallel.gds', library='gdshelpers', parallel=True) self.assertTrue(filecmp.cmp('serial.gds', 'parallel.gds'))
def test_positive_resist(self): distance = 1e-3 waveguide = Waveguide([0, 0], 0, 1) for i_bend in range(9): waveguide.add_bend(angle=np.pi, radius=60 + i_bend * 40) waveguide_positive = convert_to_positive_resist(waveguide, 1) self.assertFalse(waveguide.get_shapely_object().buffer( -distance).intersects(waveguide_positive)) self.assertTrue(waveguide.get_shapely_object().buffer( distance).intersects(waveguide_positive)) self.assertTrue( waveguide_positive.convex_hull.contains( waveguide.get_shapely_object()))
def test_export_import(self): waveguide = Waveguide([0, 0], 0, 1) for i_bend in range(9): waveguide.add_bend(angle=np.pi, radius=60 + i_bend * 40) offset = (10, 10) angle = np.pi cell = Cell('test') cell.add_to_layer(1, waveguide) sub_cell = Cell('sub_cell') sub_cell.add_to_layer(2, waveguide) cell.add_cell(sub_cell, origin=(0, 0), angle=0) sub_cell2 = Cell('sub_cell2') sub_cell2.add_to_layer(3, waveguide) cell.add_cell(sub_cell2, origin=offset, angle=angle) cell.save(library='gdshelpers', grid_steps_per_micron=10000) self.assertTrue(waveguide.get_shapely_object().almost_equals( GDSIIImport('test.gds', 'test', 1).get_shapely_object(), decimal=3)) self.assertTrue(waveguide.get_shapely_object().almost_equals( GDSIIImport('test.gds', 'test', 2).get_shapely_object(), decimal=3)) self.assertTrue( translate( rotate(waveguide.get_shapely_object(), angle, use_radians=True, origin=(0, 0)), *offset).almost_equals(GDSIIImport('test.gds', 'test', 3).get_shapely_object(), decimal=3)) self.assertTrue( GDSIIImport('test.gds', 'test', 1, 2).get_shapely_object().is_empty)
def example_bend(): from gdshelpers.parts.waveguide import Waveguide bend = Waveguide((0, 0), 0, width=1) bend.add_bend(angle=np.pi / 2, radius=20, n_points=30) wgs = [Waveguide.make_at_port(port).add_straight_segment(4) for port in [bend.in_port, bend.current_port]] sim = Simulation(resolution=25, reduce_to_2d=True, padding=2, pml_thickness=.5) sim.add_structure([bend], wgs, mp.Medium(index=1.666), z_min=0, z_max=.33) # GaussianSource or ContinousSource source = sim.add_eigenmode_source(mp.GaussianSource(wavelength=1.55, width=2), bend.in_port.longitudinal_offset(1), z=0.33 / 2, height=1, eig_band=2) sim.init_sim(subpixel_maxeval=0) # subpixel_maxeval=0 for quick testing monitor_out = sim.add_eigenmode_monitor(bend.current_port.longitudinal_offset(1), 1.55, 2, 1, z=0.33 / 2, height=1) # sim.plot(mp.Hz) sim.run(until=150) sim.plot(mp.Hz) transmission = np.abs(sim.get_eigenmode_coefficients(monitor_out, [2]).alpha[0, 0, 0]) ** 2 / source.eig_power( 1 / 1.55) print('transmission to monitor 1: {:.3f}'.format(transmission))
diff = np.array(center_coordinates.interpolate(pos + padding / 2)) - np.array( center_coordinates.interpolate(pos - padding / 2)) d1 = np.array((-diff[1], diff[0])) / np.linalg.norm(diff) for direction in [-1, 1]: point = Point(xy + direction * (offset + spacing / 2 * (i % 2)) * d1) if outline.contains(point): new_circles = True if area_for_holes.contains(point): circles.append(point.buffer(hole_radius)) offset += spacing return unary_union(circles) if __name__ == '__main__': from gdshelpers.geometry.chip import Cell from gdshelpers.parts.waveguide import Waveguide wg = Waveguide((0, 0), 0, [3, 3, 3, 3, 3]) wg.add_straight_segment(5) wg.add_bend(np.pi / 2, 20) wg.width = 15 wg.add_straight_segment(4) wg.add_bend(-np.pi / 2, 20) cell = Cell('vortex_traps') cell.add_to_layer(1, wg) cell.add_to_layer(2, fill_waveguide_with_holes_in_honeycomb_lattice(wg, 1, .1, .15)) cell.add_to_layer(2, surround_with_holes(wg.get_shapely_outline(), 3, 1, 1, 15)) cell.show() cell.save()
if not no_hole_zone.contains(pos): holes.append(pos.buffer(hole_radius)) return geometric_union(holes) if __name__ == '__main__': import gdsCAD.core from gdshelpers.parts.waveguide import Waveguide from gdshelpers.parts.resonator import RingResonator from gdshelpers.geometry import convert_to_gdscad # ==== create some sample structures (straight line with ring resonator) wg = Waveguide(origin=(0, 0), angle=np.deg2rad(-90), width=1) wg.add_straight_segment(length=5) wg.add_bend(np.pi / 2, 5) wg2 = Waveguide.make_at_port(wg.current_port) wg2.add_straight_segment(15) reso = RingResonator.make_at_port(port=wg2.current_port, gap=0.2, radius=5) wg2.add_straight_segment(length=15) coupler2 = GratingCoupler.make_traditional_coupler_from_database_at_port( wg2.current_port, db_id='si220', wavelength=1550) underetching_parts = geometric_union([wg2, reso, coupler2]) structure = geometric_union([underetching_parts, wg]) # create the holes with a radius of 0.5 microns, a distance of 2 microns to the structure borders and # a distance of 2 microns between the holes holes = create_holes_for_under_etching(underetch_parts=underetching_parts, complete_structure=structure, hole_radius=0.5, hole_distance=2,