Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add field information to dft_flux from frequency domain solver #490

Closed
smartalecH opened this issue Sep 4, 2018 · 6 comments
Closed

Add field information to dft_flux from frequency domain solver #490

smartalecH opened this issue Sep 4, 2018 · 6 comments

Comments

@smartalecH
Copy link
Collaborator

Is there already an easy way to add the field information calculated from the frequency domain solver to a dft_flux object (preferably in python)? That way, we can use the existing get_eigenmode routines by passing the modified flux object with the frequency domain solver.

@smartalecH
Copy link
Collaborator Author

I have a proposed routine, but am stuck on step 4:

1.) Define a volume and a mode region to be at the same location. Add the mode monitor:

vol = mp.Volume(center=mp.Vector3(x,y),size=mp.Vector3(0,3,0))
modeReg = mp.ModeRegion(center=mp.Vector3(x,y),size=mp.Vector3(0,3,0))
modeMon = sim.add_mode_monitor(fcen,0,1,modeReg)

2.) Run the frequency solver:

sim.solve_cw(1e-10, 10000, 10)

3.) Pull all of the relevant frequency domain fields:

Ex = sim.get_array(vol=vol,component=mp.Ex)
Ey = sim.get_array(vol=vol,component=mp.Ey)
Ez = sim.get_array(vol=vol,component=mp.Ez)
Hx = sim.get_array(vol=vol,component=mp.Hx)
Hy = sim.get_array(vol=vol,component=mp.Hy)
Hz = sim.get_array(vol=vol,component=mp.Hz)

4.) Organize them into single numpy arrays:

Etot = ?
Htot = ?

5.) Add the arrays to the flux object:

FluxData = namedtuple('FluxData', ['E', 'H'])
FluxData.E = Etot
FluxData.H = Htot
sim.load_flux_data(modeMon, FluxData)

6.) Run the mode decomposition routine:

incident_coeffs, vgrp, kpoints = sim.get_eigenmode_coefficients(modeMon, [1],eig_parity=mp.ODD_Z+mp.EVEN_Y)

I'm not quite sure how to consolidate the fields (step 4). The dft chunking scheme is a little confusing to me. It looks like the are 4 groups of each field (i.e Ex, Ey, Ez, E?) but I could be wrong.

If I could get any insight, I could submit a pull request for a new function.

@stevengj
Copy link
Collaborator

It seems like it should work (up to some overall scale factor) if you simply add the dft_flux objects etc. as usual, call sim.solve_cw, and call fields::update_dfts to update the dft_flux objects with the computed fields, and then call get_eigenmode_coefficients.

A little more care is required if we care about the overall normalization of the resulting coefficients, e.g. update_dfts() includes a dt factor that we may not want.

@smartalecH
Copy link
Collaborator Author

smartalecH commented Sep 19, 2018

Hmm it seems that even with the call to fields::update_dfts, the monitors detect zero field. At least I assume they don't detect any field because the resulting forward and backward coefficients are zero as well.

I attached a script that tries this method:

simpleFDFDExample.py.zip

@stevengj
Copy link
Collaborator

Weird. Maybe add a printf in dft_chunk::update_dft (in dft.cpp) to make sure it is being called? I'm sure we're missing something simple…

@stevengj
Copy link
Collaborator

stevengj commented Oct 16, 2018

Ah, just add sim._evaluate_dft_objects() to the line after solve_cw.

@stevengj
Copy link
Collaborator

To do:

  • In update_dfts(), we should do nothing if doing_solve_cw is true: we don't want to update dfts during the CW solver.

  • In Python, we should automatically _evaluate_dft_objects when doing solve_cw.

  • The solve_cw function in C++ should call update_dfts() when it is done. We might also adjust the scaling to remove the dt factor.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants