Skip to content

Commit

Permalink
Update to v0.5.1
Browse files Browse the repository at this point in the history
  • Loading branch information
hochunlin committed Jun 21, 2024
1 parent fcb2a20 commit 6dfe8f2
Show file tree
Hide file tree
Showing 24 changed files with 344 additions and 338 deletions.
2 changes: 1 addition & 1 deletion Project.toml
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ name = "MESTI"
uuid = "8d7f31fa-9986-4e1d-8c81-72752476e54d"
license = "GPL-3.0"
authors = ["Ho-Chun Lin<hochunlin0508@gmail.com>, Shiyu Li<lishiyu@usc.edu>, Zeyu Wang<wangzeyu@usc.edu>, and Chia Wei Hsu<cwhsu@usc.edu>"]
version = "0.5.0"
version = "0.5.1"

[deps]
GeometryPrimitives = "17051e67-205e-509e-8301-03b320b998e6"
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -74,9 +74,9 @@ N_prop_low = channels_low.N_prop # number of propagating channels on the low sid
Cx = Source_struct()
ny_Ex = Int(W/dx)
Cx.pos = [[1,pml_npixels+1,ny_Ex,1]]
# sqrt(nu)*conj(u_Ex(m)) serves as a projection profile for a propagating channel, where nu = sin(kzdx)
# sqrt(nu)*conj(f_x(m)) serves as a projection profile for a propagating channel, where nu = sin(kzdx)
# here we project the result onto all propagating channels as a output basis
C_low = (conj(channels_low.u_x_m(channels_low.kydx_prop))).*reshape(channels_low.sqrt_nu_prop,1,:).*reshape(exp.((-1im*0.5)*channels_low.kzdx_prop),1,:) # 0.5 pixel backpropagation indicates that the projection(detect) region is half a pixel away from z = 0
C_low = (conj(channels_low.f_x_m(channels_low.kydx_prop))).*reshape(channels_low.sqrt_nu_prop,1,:).*reshape(exp.((-1im*0.5)*channels_low.kzdx_prop),1,:) # 0.5 pixel backpropagation indicates that the projection(detect) region is half a pixel away from z = 0
Cx.data = [C_low]

# Calculate output channel amplitude coefficients (w) for the propagating channels from the point source through APF
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -118,9 +118,9 @@
"Cx = Source_struct()\n",
"ny_Ex = Int(W/dx)\n",
"Cx.pos = [[1,pml_npixels+1,ny_Ex,1]]\n",
"# sqrt(nu)*conj(u_Ex(m)) serves as a projection profile for a propagating channel, where nu = sin(kzdx)\n",
"# sqrt(nu)*conj(f_x(m)) serves as a projection profile for a propagating channel, where nu = sin(kzdx)\n",
"# here we project the result onto all propagating channels as a output basis \n",
"C_low = (conj(channels_low.u_x_m(channels_low.kydx_prop))).*reshape(channels_low.sqrt_nu_prop,1,:).*reshape(exp.((-1im*0.5)*channels_low.kzdx_prop),1,:) # 0.5 pixel backpropagation indicates that the projection(detect) region is half a pixel away from z = 0\n",
"C_low = (conj(channels_low.f_x_m(channels_low.kydx_prop))).*reshape(channels_low.sqrt_nu_prop,1,:).*reshape(exp.((-1im*0.5)*channels_low.kzdx_prop),1,:) # 0.5 pixel backpropagation indicates that the projection(detect) region is half a pixel away from z = 0\n",
"Cx.data = [C_low]\n",
"\n",
"# Calculate output channel amplitude coefficients (w) for the propagating channels from the point source through APF\n",
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -72,9 +72,9 @@ N_prop_low = channels_low.N_prop # number of propagating channels on the low sid
Cx = Source_struct()
ny_Ex = Int(W/dx)
Cx.pos = [[1,pml_npixels+1,ny_Ex,1]]
# sqrt(nu)*conj(u_Ex(m)) serves as a projection profile for a propagating channel, where nu = sin(kzdx)
# sqrt(nu)*conj(f_x(m)) serves as a projection profile for a propagating channel, where nu = sin(kzdx)
# here we project the result onto all propagating channels as a output basis
C_low = (conj(channels_low.u_x_m(channels_low.kydx_prop))).*reshape(channels_low.sqrt_nu_prop,1,:).*reshape(exp.((-1im*0.5)*channels_low.kzdx_prop),1,:) # 0.5 pixel backpropagation indicates that the projection(detect) region is half a pixel away from z = 0
C_low = (conj(channels_low.f_x_m(channels_low.kydx_prop))).*reshape(channels_low.sqrt_nu_prop,1,:).*reshape(exp.((-1im*0.5)*channels_low.kzdx_prop),1,:) # 0.5 pixel backpropagation indicates that the projection(detect) region is half a pixel away from z = 0
Cx.data = [C_low]

# Calculate output channel amplitude coefficients (w) for the propagating channels from the point source through APF
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -79,14 +79,14 @@ kxdx_FOV = sqrt.((k0dx)^2 .- (kydx_FOV).^2) # kxdx within the FOV
N_L = length(kydx_FOV) # Number of incident angles of interest

# Build the propagating channels on the left of metalens
B_basis = channels_L.u_x_m(channels_L.kydx_prop)
B_basis = channels_L.f_x_m(channels_L.kydx_prop)

# Multiply the flux-normalized prefactor sqrt(nu)
sqrt_nu_L_basis = reshape(channels_L.sqrt_nu_prop,1,:) # row vector

# Build the truncated incident plane waves at various angles
ind_source_out = findall(x-> (abs(x) > D_in/2), (collect(0.5:1:ny) .- ny/2)*dx) # y coordinates outside of the input aperture
B_trunc = channels_L.u_x_m(kydx_FOV)*sqrt(ny/ny_L)
B_trunc = channels_L.f_x_m(kydx_FOV)*sqrt(ny/ny_L)
B_trunc[ind_source_out,:] .= 0 # Block light outside of the input aperture

# We project each truncated input plane wave, with |y|<=D_in/2, onto propagating channels at the metalens input side,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -38,7 +38,7 @@ ASP use angular spectrum propagation (ASP) to propagate a scalar field
different distance x (if x is a row vector).
"""

function asp(f0::Union{Matrix{Int64}, Matrix{Float64}, Matrix{ComplexF64}, Vector{Int64}, Vector{Float64}, Vector{ComplexF64}}, x::Union{Int64, Float64, Matrix{Int64}, Matrix{Float64}}, kx_prop::Union{Vector{Int64}, Vector{Float64}, Vector{ComplexF64}}, ny_tot::Union{Int64, Nothing}, ny_pad_low::Union{Int64, Nothing})
function asp(f0::Union{Matrix{Int32}, Matrix{Int64}, Matrix{Float32}, Matrix{Float64}, Matrix{ComplexF32}, Matrix{ComplexF64}, Vector{Int32}, Vector{Int64}, Vector{Float32}, Vector{Float64}, Vector{ComplexF32}, Vector{ComplexF64}}, x::Union{Int64, Float64, Matrix{Int64}, Matrix{Float64}}, kx_prop::Union{Vector{Int64}, Vector{Float64}, Vector{ComplexF64}}, ny_tot::Union{Int64, Nothing}, ny_pad_low::Union{Int64, Nothing})

# Check if f0 has more than one column and enforce x to be a scalar
if size(f0, 2) > 1 && !(isa(x, Int64) || isa(x, Float64))
Expand Down Expand Up @@ -95,10 +95,10 @@ end
# The following are asp functions to take different number of input arguments, but all of them will
# call the asp main function.

function asp(f0::Union{Matrix{Int64}, Matrix{Float64}, Matrix{ComplexF64}, Vector{Int64}, Vector{Float64}, Vector{ComplexF64}}, x::Union{Int64, Float64, Matrix{Int64}, Matrix{Float64}}, kx_prop::Union{Vector{Int64}, Vector{Float64}, Vector{ComplexF64}})
function asp(f0::Union{Matrix{Int32}, Matrix{Int64}, Matrix{Float32}, Matrix{Float64}, Matrix{ComplexF32}, Matrix{ComplexF64}, Vector{Int32}, Vector{Int64}, Vector{Float32}, Vector{Float64}, Vector{ComplexF32}, Vector{ComplexF64}}, x::Union{Int64, Float64, Matrix{Int64}, Matrix{Float64}}, kx_prop::Union{Vector{Int64}, Vector{Float64}, Vector{ComplexF64}})
return asp(f0, x, kx_prop, nothing, nothing)
end

function asp(f0::Union{Matrix{Int64}, Matrix{Float64}, Matrix{ComplexF64}, Vector{Int64}, Vector{Float64}, Vector{ComplexF64}}, x::Union{Int64, Float64, Matrix{Int64}, Matrix{Float64}}, kx_prop::Union{Vector{Int64}, Vector{Float64}, Vector{ComplexF64}}, ny_tot::Union{Int64, Nothing})
function asp(f0::Union{Matrix{Int32}, Matrix{Int64}, Matrix{Float32}, Matrix{Float64}, Matrix{ComplexF32}, Matrix{ComplexF64}, Vector{Int32}, Vector{Int64}, Vector{Float32}, Vector{Float64}, Vector{ComplexF32}, Vector{ComplexF64}}, x::Union{Int64, Float64, Matrix{Int64}, Matrix{Float64}}, kx_prop::Union{Vector{Int64}, Vector{Float64}, Vector{ComplexF64}}, ny_tot::Union{Int64, Nothing})
return asp(f0, x, kx_prop, ny_tot, nothing)
end
end
Original file line number Diff line number Diff line change
Expand Up @@ -107,14 +107,14 @@
"N_L = length(kydx_FOV) # Number of incident angles of interest\n",
"\n",
"# Build the propagating channels on the left of metalens\n",
"B_basis = channels_L.u_x_m(channels_L.kydx_prop) \n",
"B_basis = channels_L.f_x_m(channels_L.kydx_prop) \n",
"\n",
"# Multiply the flux-normalized prefactor sqrt(nu)\n",
"sqrt_nu_L_basis = reshape(channels_L.sqrt_nu_prop,1,:) # row vector\n",
"\n",
"# Build the truncated incident plane waves at various angles\n",
"ind_source_out = findall(x-> (abs(x) > D_in/2), (collect(0.5:1:ny) .- ny/2)*dx) # y coordinates outside of the input aperture\n",
"B_trunc = channels_L.u_x_m(kydx_FOV)*sqrt(ny/ny_L)\n",
"B_trunc = channels_L.f_x_m(kydx_FOV)*sqrt(ny/ny_L)\n",
"B_trunc[ind_source_out,:] .= 0 # Block light outside of the input aperture\n",
"\n",
"# We project each truncated input plane wave, with |y|<=D_in/2, onto propagating channels at the metalens input side,\n",
Expand Down Expand Up @@ -308,7 +308,7 @@
"id": "5443bd6a",
"metadata": {},
"source": [
"# Calculate the field on the left side, inside and after the metalens"
"## Calculate the field on the left side, inside and after the metalens"
]
},
{
Expand All @@ -318,7 +318,6 @@
"metadata": {},
"outputs": [],
"source": [
"# Calculate the field on the left side, inside and after the metalens\n",
"else\n",
" # Use mesti() to compute the field inside the metalens.\n",
" field_inside_metalens, _ = mesti(syst, [B_struct], opts)\n",
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -77,14 +77,14 @@ kxdx_FOV = sqrt.((k0dx)^2 .- (kydx_FOV).^2) # kxdx within the FOV
N_L = length(kydx_FOV) # Number of incident angles of interest

# Build the propagating channels on the left of metalens
B_basis = channels_L.u_x_m(channels_L.kydx_prop)
B_basis = channels_L.f_x_m(channels_L.kydx_prop)

# Multiply the flux-normalized prefactor sqrt(nu)
sqrt_nu_L_basis = reshape(channels_L.sqrt_nu_prop,1,:) # row vector

# Build the truncated incident plane waves at various angles
ind_source_out = findall(x-> (abs(x) > D_in/2), (collect(0.5:1:ny) .- ny/2)*dx) # y coordinates outside of the input aperture
B_trunc = channels_L.u_x_m(kydx_FOV)*sqrt(ny/ny_L)
B_trunc = channels_L.f_x_m(kydx_FOV)*sqrt(ny/ny_L)
B_trunc[ind_source_out,:] .= 0 # Block light outside of the input aperture

# We project each truncated input plane wave, with |y|<=D_in/2, onto propagating channels at the metalens input side,
Expand Down
Binary file not shown.
10 changes: 6 additions & 4 deletions examples/2d_open_channel_through_disorder/README.md
Original file line number Diff line number Diff line change
Expand Up @@ -139,6 +139,7 @@ nz_low = round(Int,(L_tot-L)/2/dx)
nz_high = nz_low
opts.nz_low = nz_low
opts.nz_high = nz_high
opts.use_L0_threads = false

# for field-profile computations
Ex, _, _ = mesti2s(syst, input, opts)
Expand Down Expand Up @@ -187,14 +188,14 @@ syst.PML = [pml]
# syst.zPML = [pml] (and do not need to specify pml.direction = "z")

Bx = Source_struct()
u_prop_low_Ex = channels.u_x_m(channels.low.kydx_prop) # the transverse profiles, u_Ex, for the propagating ones
f_prop_low_Ex = channels.f_x_m(channels.low.kydx_prop) # the transverse profiles, f_Ex, for the propagating ones

# If it is a single propagating channel, a line source of -2i*sqrt(nu)*u_Ex(m) at l=0 will generate an z-flux-normalized incident field of exp(i*kzdx*|l|)*u_Ex(l)/sqrt(nu), where nu = sin(kzdx)
# If it is a single propagating channel, a line source of -2i*sqrt(nu)*f_Ex(m) at l=0 will generate an z-flux-normalized incident field of exp(i*kzdx*|l|)*f_Ex(l)/sqrt(nu), where nu = sin(kzdx)
# here, we want input wavefront fields on the low side, which is a superposition of propagating channels
# these input wavefront fields on the low side are specified by v_low, and we take superpositions of the propagating channels using the v coefficients, with the sqrt(nu)*exp(-i*kzdx*0.5) prefactors included.
# we will multiply the -2i prefactor at the end.
# the source B_Ex would generate the input wavefront fields
B_Ex_low = u_prop_low_Ex*(channels.low.sqrt_nu_prop.*exp.((-1im*0.5)*channels.low.kzdx_prop).*v_low) # 0.5 pixel backpropagation indicates that the source is half a pixel away from z = 0
B_Ex_low = f_prop_low_Ex*(channels.low.sqrt_nu_prop.*exp.((-1im*0.5)*channels.low.kzdx_prop).*v_low) # 0.5 pixel backpropagation indicates that the source is half a pixel away from z = 0
Bx.data = [B_Ex_low] # the value of the source

# the position of the source specify by a rectangle.
Expand All @@ -208,6 +209,7 @@ Bx.pos = [[1,pml_npixels+1,ny_Ex,1]]
opts = Opts()
# the -2i prefactor would be multiplied by.
opts.prefactor = -2im
opts.use_L0_threads = false

Ex_prime, _ = mesti(syst, [Bx], opts)
```
Expand Down Expand Up @@ -243,7 +245,7 @@ Ex = Ex/maximum(abs.(Ex[:,:,1]))
nframes_per_period = 10

# extend the x coordinate to include free spaces on the two sides
z_Ex = vcat(z_Ex[1] .- (opts.nz_low:-1:1)*dx, z_Ex, z_Ex[end] .+ (1:opts.nz_high)*dx)
z_Ex = vcat(z_Ex[1] .- (nz_low:-1:1)*dx, z_Ex, z_Ex[end] .+ (1:nz_high)*dx)

# animate the field profile with plane-wave input
anim_pw = @animate for ii 0:(nframes_per_period-1)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -186,6 +186,7 @@
"nz_high = nz_low\n",
"opts.nz_low = nz_low\n",
"opts.nz_high = nz_high\n",
"opts.use_L0_threads = false\n",
"\n",
"# for field-profile computations\n",
"Ex, _, _ = mesti2s(syst, input, opts);"
Expand Down Expand Up @@ -228,14 +229,14 @@
"# syst.zPML = [pml] (and do not need to specify pml.direction = \"z\")\n",
"\n",
"Bx = Source_struct()\n",
"u_prop_low_Ex = channels.u_x_m(channels.low.kydx_prop) # the transverse profiles, u_Ex, for the propagating ones\n",
"f_prop_low_Ex = channels.f_x_m(channels.low.kydx_prop) # the transverse profiles, f_Ex, for the propagating ones\n",
"\n",
"# If it is a single propagating channel, a line source of -2i*sqrt(nu)*u_Ex(m) at l=0 will generate an z-flux-normalized incident field of exp(i*kzdx*|l|)*u_Ex(l)/sqrt(nu), where nu = sin(kzdx)\n",
"# If it is a single propagating channel, a line source of -2i*sqrt(nu)*f_Ex(m) at l=0 will generate an z-flux-normalized incident field of exp(i*kzdx*|l|)*f_Ex(l)/sqrt(nu), where nu = sin(kzdx)\n",
"# here, we want input wavefront fields on the low side, which is a superposition of propagating channels\n",
"# these input wavefront fields on the low side are specified by v_low, and we take superpositions of the propagating channels using the v coefficients, with the sqrt(nu)*exp(-i*kzdx*0.5) prefactors included.\n",
"# we will multiply the -2i prefactor at the end.\n",
"# the source B_Ex would generate the input wavefront fields\n",
"B_Ex_low = u_prop_low_Ex*(channels.low.sqrt_nu_prop.*exp.((-1im*0.5)*channels.low.kzdx_prop).*v_low) # 0.5 pixel backpropagation indicates that the source is half a pixel away from z = 0\n",
"B_Ex_low = f_prop_low_Ex*(channels.low.sqrt_nu_prop.*exp.((-1im*0.5)*channels.low.kzdx_prop).*v_low) # 0.5 pixel backpropagation indicates that the source is half a pixel away from z = 0\n",
"Bx.data = [B_Ex_low] # the value of the source\n",
"\n",
"# the position of the source specify by a rectangle.\n",
Expand All @@ -249,6 +250,7 @@
"opts = Opts()\n",
"# the -2i prefactor would be multiplied by.\n",
"opts.prefactor = -2im\n",
"opts.use_L0_threads = false\n",
"\n",
"Ex_prime, _ = mesti(syst, [Bx], opts)"
]
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -108,6 +108,7 @@ nz_low = round(Int,(L_tot-L)/2/dx)
nz_high = nz_low
opts.nz_low = nz_low
opts.nz_high = nz_high
opts.use_L0_threads = false

# compute the field-profiles through mesti()
Ex, _, _ = mesti2s(syst, input, opts)
Expand Down Expand Up @@ -137,14 +138,14 @@ syst.PML = [pml]
# syst.zPML = [pml] (and do not need to specify pml.direction = "z")

Bx = Source_struct()
u_prop_low_Ex = channels.u_x_m(channels.low.kydx_prop) # the transverse profiles, u_Ex, for the propagating ones
f_prop_low_Ex = channels.f_x_m(channels.low.kydx_prop) # the transverse profiles, f_Ex, for the propagating ones

# If it is a single propagating channel, a line source of -2i*sqrt(nu)*u_Ex(m) at l=0 will generate an z-flux-normalized incident field of exp(i*kzdx*|l|)*u_Ex(l)/sqrt(nu), where nu = sin(kzdx)
# If it is a single propagating channel, a line source of -2i*sqrt(nu)*f_Ex(m) at l=0 will generate an z-flux-normalized incident field of exp(i*kzdx*|l|)*f_Ex(l)/sqrt(nu), where nu = sin(kzdx)
# here, we want input wavefront fields on the low side, which is a superposition of propagating channels
# these input wavefront fields on the low side are specified by v_low, and we take superpositions of the propagating channels using the v coefficients, with the sqrt(nu)*exp(-i*kzdx*0.5) prefactors included.
# we will multiply the -2i prefactor at the end.
# the source B_Ex would generate the input wavefront fields
B_Ex_low = u_prop_low_Ex*(channels.low.sqrt_nu_prop.*exp.((-1im*0.5)*channels.low.kzdx_prop).*v_low) # 0.5 pixel backpropagation indicates that the source is half a pixel away from z = 0
B_Ex_low = f_prop_low_Ex*(channels.low.sqrt_nu_prop.*exp.((-1im*0.5)*channels.low.kzdx_prop).*v_low) # 0.5 pixel backpropagation indicates that the source is half a pixel away from z = 0
Bx.data = [B_Ex_low] # the value of the source

# the position of the source specify by a rectangle.
Expand All @@ -158,6 +159,7 @@ Bx.pos = [[1,pml_npixels+1,ny_Ex,1]]
opts = Opts()
# the -2i prefactor would be multiplied by.
opts.prefactor = -2im
opts.use_L0_threads = false

Ex_prime, _ = mesti(syst, [Bx], opts)

Expand All @@ -172,7 +174,7 @@ Ex = Ex/maximum(abs.(Ex[:,:,1]))
nframes_per_period = 10

# extend the x coordinate to include free spaces on the two sides
z_Ex = vcat(z_Ex[1] .- (opts.nz_low:-1:1)*dx, z_Ex, z_Ex[end] .+ (1:opts.nz_high)*dx)
z_Ex = vcat(z_Ex[1] .- (nz_low:-1:1)*dx, z_Ex, z_Ex[end] .+ (1:nz_high)*dx)

# animate the field profile with plane-wave input
anim_pw = @animate for ii 0:(nframes_per_period-1)
Expand Down
Loading

2 comments on commit 6dfe8f2

@hochunlin
Copy link
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@JuliaRegistrator
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Registration pull request created: JuliaRegistries/General/109509

Tip: Release Notes

Did you know you can add release notes too? Just add markdown formatted text underneath the comment after the text
"Release notes:" and it will be added to the registry PR, and if TagBot is installed it will also be added to the
release that TagBot creates. i.e.

@JuliaRegistrator register

Release notes:

## Breaking changes

- blah

To add them here just re-invoke and the PR will be updated.

Tagging

After the above pull request is merged, it is recommended that a tag is created on this repository for the registered package version.

This will be done automatically if the Julia TagBot GitHub Action is installed, or can be done manually through the github interface, or via:

git tag -a v0.5.1 -m "<description of version>" 6dfe8f23acceb47a5929c7fdba19198ce8af98ce
git push origin v0.5.1

Please sign in to comment.