PLaSK library

Loading...
Searching...
No Matches
wire2d.py
Go to the documentation of this file.
1#!/usr/bin/env python3
2# This file is part of PLaSK (https://plask.app) by Photonics Group at TUL
3# Copyright (c) 2022 Lodz University of Technology
4#
5# This program is free software: you can redistribute it and/or modify
6# it under the terms of the GNU General Public License as published by
7# the Free Software Foundation, version 3.
8#
9# This program is distributed in the hope that it will be useful,
10# but WITHOUT ANY WARRANTY; without even the implied warranty of
11# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12# GNU General Public License for more details.
13
14 import unittest
15
16 from numpy import *
17
18 from plask import *
19 from plask import material, geometry, mesh
20 from optical import modal
21
22 config.axes = 'zxy'
23
24@material.simple()
25 class Glass(material.Material):
26 def Nr(self, wl, T=300., n=0.): return 1.30
27
28
29@material.simple()
30 class Cladding(material.Material):
31 def Nr(self, wl, T=300., n=0.): return 1.28
32
33
34 class Wire(unittest.TestCase):
35
36 def setUp(self):
37 self.solver = modal.Fourier2D("fourier")
38 wire_stack = geometry.Stack2D()
39 wire_stack.append(geometry.Rectangle(0.75, 0.125, Glass()))
40 rect = geometry.Rectangle(0.75, 0.375, Glass())
41 rect.role = 'interface'
42 wire_stack.append(rect)
43 space = geometry.Cartesian2D(wire_stack, left="mirror")
44 self.solver.geometry = space
45 self.solver.lam = 1000.
46
47 def testComputations(self):
48 self.solver.symmetry = 'Etran'
49 # self.solver.polarization = "Etran"
50 self.assertAlmostEqual(self.solver.modes[self.solver.find_mode(neff=1.15)].neff, 1.147, 3)
51 self.solver.symmetry = 'Htran'
52 # self.solver.polarization = "Htran"
53 self.assertAlmostEqual( self.solver.modes[self.solver.find_mode(neff=1.05)].neff, 1.054, 3)
54
55 def testFullDeterminant(self):
56 self.solver.determinant_type = 'full'
57 self.solver.symmetry = 'Etran'
58 # self.solver.polarization = "Etran"
59 self.assertAlmostEqual(self.solver.modes[self.solver.find_mode(neff=1.15)].neff, 1.147, 3)
60 self.solver.symmetry = 'Htran'
61 # self.solver.polarization = "Htran"
62 self.assertAlmostEqual( self.solver.modes[self.solver.find_mode(neff=1.05)].neff, 1.054, 3)
63
64
65# class WireLaser(unittest.TestCase):
66#
67# def setUp(self):
68# plask.config.axes = 'xy'
69# rect1 = geometry.Rectangle(0.75, 0.24, Glass())
70# self.rect2 = geometry.Rectangle(0.75, 0.02, Glass())
71# self.rect2.role = 'gain'
72# stack = geometry.Stack2D()
73# stack.prepend(rect1)
74# stack.prepend(self.rect2)
75# stack.prepend(rect1)
76# space = geometry.Cartesian2D(stack, left="mirror", length=1000)
77# self.solver = modal.Fourier2D("fourier")
78# self.solver.geometry = space
79# self.solver.mirrors = 0.7, 1.0
80# self.profile = StepProfile(space)
81# self.solver.inGain = self.profile.outGain
82#
83# def testThreshold(self):
84# try:
85# from scipy.optimize import brentq
86# except ImportError:
87# pass
88# else:
89# self.solver.stripe_root.method = 'muller'
90# def fun(g):
91# self.profile[self.rect2] = g
92# m = self.solver.find_mode(1.15)
93# return self.solver.modes[m].neff.imag
94# gain = brentq(fun, 0., 100.)
95# self.assertAlmostEqual(gain, 81.648, 2)
96#
97# def testAbsorptionIntegral(self):
98# self.profile[self.rect2] = 81.649513489
99# m = self.solver.find_mode(1.15)
100# self.solver.modes[m].power = 1.4
101# self.assertAlmostEqual(self.solver.get_total_absorption(m), -2.0, 1)
102#
103# def testAbsorbedHeat(self):
104# self.profile[self.rect2] = 81.649513489
105# m = self.solver.find_mode(1.15)
106# self.solver.modes[m].power = 0.7
107# box = self.solver.geometry.item.bbox
108# msh = mesh.Rectangular2D(mesh.Regular(box.lower.x, box.upper.x, 1000), mesh.Regular(box.lower.y, box.upper.y, 1000))
109# heat = self.solver.outHeat(msh)
110# # 1e-15: µm³->m³ W->mW
111# integral = 2e-15 * sum(heat) * (msh.axis0[1] - msh.axis0[0]) * (msh.axis1[1] - msh.axis1[0]) * self.solver.geometry.extrusion.length
112# self.assertAlmostEqual(integral, self.solver.get_total_absorption(m), 2)
113
114
115 if __name__ == '__main__':
116 wire = Wire()
117 wire.setUp()
118 neffs = linspace(1.0, 1.3, 301)
119 wire.solver.symmetry = 'Etran'
120 det1 = wire.solver.get_determinant(neff=neffs)
121 wire.solver.determinant_type = 'full'
122 det2 = wire.solver.get_determinant(neff=neffs)
123 plot(neffs, abs(det1))
124 plot(neffs, abs(det2))
125 xlabel("$n_\\mathrm{eff}$")
126 ylabel("Determinant")
127 yscale('log')
128 show()