Пример #1
0
def rms_janss(variables, *args):
    """calculate the rms value of the Janssen method with variables:
    variables[0] = piston,
    variables[1] = radius of circle on sh sensor[px],
    Z_mat is used to calculate the Zernike polynomial on a grid, to compare with original interferogram.
    arguments should be in order"""
    if args:
        x_pos_zero, y_pos_zero, x_pos_flat, y_pos_flat, x_pos_dist, y_pos_dist, px_size_sh, f_sh, j_max, wavelength, xx, yy, N, orig, mask, Z_mat, box_len, centre = args
    else:
        print("put the arguments!")
        return
    #x_pos_flat_f, y_pos_flat_f = Hm.centroid_positions(x_pos_zero, y_pos_zero, image_control, xx, yy, spot_size = box_len)

    r_sh_m = px_size_sh * variables[1]

    x_pos_norm = (x_pos_flat - centre[0]) / variables[1]
    y_pos_norm = (y_pos_flat - centre[1]) / variables[1]

    ### check if all is within circle
    ### not implemented due to constraints
    inside = np.sqrt(x_pos_norm**2 +
                     y_pos_norm**2) <= (1 + (box_len / variables[1]))
    x_pos_norm_it, y_pos_norm_it, x_pos_flat_it, y_pos_flat_it, x_pos_dist_it, y_pos_dist_it = mc.filter_positions(
        inside, x_pos_norm, y_pos_norm, x_pos_flat, y_pos_flat, x_pos_dist,
        y_pos_dist)

    ## calculate slopes
    #x_pos_dist, y_pos_dist = Hm.centroid_positions(x_pos_flat_f, y_pos_flat_f, dist_image, xx, yy, spot_size = box_len)
    dWdx, dWdy = Hm.centroid2slope(x_pos_dist_it, y_pos_dist_it, x_pos_flat_it,
                                   y_pos_flat_it, px_size_sh, f_sh, r_sh_m,
                                   wavelength)

    ## make zernike matrix
    kmax = np.power(np.ceil(np.sqrt(j_max)),
                    2)  #estimation of maximum fringe number
    n, m = Zn.Zernike_j_2_nm(np.array(range(
        1,
        int(kmax) + 1)))  #find n and m pairs for maximum fringe number
    Kmax = np.max(Zn.Zernike_nm_2_j(
        n + 1,
        np.abs(m) + 1))  #find highest order of j for which beta is needed
    Z_mat_complex = janssen.avg_complex_zernike(x_pos_norm_it,
                                                y_pos_norm_it,
                                                Kmax,
                                                variables[1],
                                                spot_size=box_len)

    #Invert and solve for beta
    dW_plus = dWdx + 1j * dWdy
    dW_min = dWdx - 1j * dWdy
    beta_plus = np.linalg.lstsq(Z_mat_complex, dW_plus)[0]
    beta_min = np.linalg.lstsq(Z_mat_complex, dW_min)[0]

    kmax = int(kmax)
    a = np.zeros(kmax, dtype=np.complex_)
    a_check = np.zeros(j_max, dtype=np.complex_)
    #a_avg = np.zeros(j_max, dtype = np.complex_)
    for jj in range(2, kmax + 1):
        n, m = Zn.Zernike_j_2_nm(jj)
        index1 = int(Zn.Zernike_nm_2_j(n - 1.0, m + 1.0) - 1)
        index2 = int(Zn.Zernike_nm_2_j(n - 1.0, m - 1.0) - 1)
        index3 = int(Zn.Zernike_nm_2_j(n + 1.0, m + 1.0) - 1)
        index4 = int(Zn.Zernike_nm_2_j(n + 1.0, m - 1.0) - 1)
        fact1 = 1.0 / (2 * n * (1 + (n != abs(m))))
        fact2 = 1.0 / (2 * (n + 2) * (1 + (((n + 2) != abs(m)))))
        if m + 1.0 > n - 1.0:
            a[jj -
              1] = fact1 * (beta_min[index2]) - fact2 * (beta_plus[index3] +
                                                         beta_min[index4])
        elif np.abs(m - 1.0) > np.abs(n - 1.0):
            a[jj -
              1] = fact1 * (beta_plus[index1]) - fact2 * (beta_plus[index3] +
                                                          beta_min[index4])
        else:
            a[jj -
              1] = fact1 * (beta_plus[index1] + beta_min[index2]) - fact2 * (
                  beta_plus[index3] + beta_min[index4])

    for jj in range(2, j_max + 2):
        n, m = Zn.Zernike_j_2_nm(jj)
        if m > 0:
            j_min = int(Zn.Zernike_nm_2_j(n, -m))
            a_check[jj - 2] = (1.0 / np.sqrt(2 * n + 2)) * (a[jj - 1] +
                                                            a[j_min - 1])
        elif m < 0:
            j_plus = int(Zn.Zernike_nm_2_j(n, np.abs(m)))
            a_check[jj - 2] = (1.0 / np.sqrt(2 * n + 2)) * (a[j_plus - 1] -
                                                            a[jj - 1]) * 1j
        else:
            a_check[jj - 2] = (1.0 / np.sqrt(n + 1)) * a[jj - 1]
    a_janss = np.real(a_check)

    orig = np.ma.array(orig, mask=mask)
    inter = np.ma.array(Zn.int_for_comp(j_max,
                                        a_janss,
                                        N,
                                        variables[0],
                                        Z_mat,
                                        fliplr=False),
                        mask=mask)
    rms = np.sqrt(np.sum((inter - orig)**2) / N**2)
    return rms
x_pos_zero, y_pos_zero = Hm.zero_positions(zero_image_zeros)
x_pos_flat, y_pos_flat = Hm.centroid_positions(x_pos_zero, y_pos_zero, image_control, xx, yy)
centre = Hm.centroid_centre(x_pos_flat, y_pos_flat)
x_pos_norm = ((x_pos_flat - centre[0]))/r_sh_px
y_pos_norm = ((y_pos_flat - centre[1]))/r_sh_px
inside = np.where(np.sqrt(x_pos_norm**2 + y_pos_norm**2) <= (1 + (box_len/r_sh_px))) #35 is the half the width of the pixel box aroudn a centroid and r_sh_px is the scaling factor
x_pos_zero_f, y_pos_zero_f, x_pos_flat_f, y_pos_flat_f, x_pos_norm_f, y_pos_norm_f = mc.filter_positions(inside, x_pos_zero, y_pos_zero, x_pos_flat, y_pos_flat, x_pos_norm, y_pos_norm)
integrate = False
inside_without_outsides = np.where(np.sqrt(x_pos_norm**2 + y_pos_norm**2) <= 1 - (box_len/r_sh_px))
x_pos_norm_f_wth, y_pos_norm_f_wth = mc.filter_positions(inside_without_outsides, x_pos_norm, y_pos_norm)

janss_args = (x_pos_zero_f, y_pos_zero_f, image_control, dist_image, px_size_sh, f_sh, j_max, wavelength, xx, yy, N, orig, mask, Z_mat, box_len, integrate)

x_norm_mat, y_norm_mat = np.meshgrid(x_pos_norm_f, y_pos_norm_f)

Z_mat_com_int = janssen.avg_complex_zernike(x_pos_norm_f, y_pos_norm_f, 200, 310)
Z_mat_com_non = Zn.complex_zernike(200, x_pos_norm_f, y_pos_norm_f)
Z_mat_int_wth, Z_mat_non_wth = janssen.avg_complex_zernike(x_pos_norm_f_wth, y_pos_norm_f_wth, 200, 310), Zn.complex_zernike(200, x_pos_norm_f_wth, y_pos_norm_f_wth)

rms_mat = np.sqrt((Z_mat_com_int - Z_mat_com_non)**2)/len(x_pos_norm_f)
rms = np.sum(rms_mat, axis = 0)
rms_mat_wth = np.sqrt((Z_mat_int_wth - Z_mat_non_wth)**2)/len(x_pos_norm_f_wth)
rms_wth = np.sum(rms_mat_wth, axis = 0)
#plot_z = Z_mat_com[:, 98].reshape(x_norm_mat)

fig = plt.figure()
ax = fig.add_subplot(121, projection='3d')
ax.scatter(x_pos_norm_f, y_pos_norm_f, rms_mat[:,189])
ax.set_zlim(bottom= 0)
ax.set_xlabel(r'x')
ax.set_ylabel(r'y')
def a_from_vars_int(variables, *args):
    if args:
       x_pos_zero_f, y_pos_zero_f, image_control, dist_image, px_size_sh, f_sh, j_max, wavelength, xx, yy, N, orig, mask, Z_mat, box_len, integrate = args
    else:
        print("put the arguments!")
        return
    x_pos_flat_f, y_pos_flat_f = Hm.centroid_positions(x_pos_zero, y_pos_zero, image_control, xx, yy)

    r_sh_m = px_size_sh * variables[3]

    x_pos_norm = (x_pos_flat_f - variables[1])/variables[3]
    y_pos_norm = (y_pos_flat_f - variables[2])/variables[3]

    ### check if all is within circle
    inside = np.sqrt(x_pos_norm ** 2 + y_pos_norm**2) <= (1+ (box_len/variables[3]))
    x_pos_norm, y_pos_norm, x_pos_flat_f,y_pos_flat_f = mc.filter_positions(inside, x_pos_norm, y_pos_norm, x_pos_flat_f, y_pos_flat_f)

    ## calculate slopes
    x_pos_dist, y_pos_dist = Hm.centroid_positions(x_pos_flat_f, y_pos_flat_f, dist_image, xx, yy)
    dWdx, dWdy = Hm.centroid2slope(x_pos_dist, y_pos_dist, x_pos_flat_f, y_pos_flat_f, px_size_sh, f_sh, r_sh_m, wavelength)

    ## make zernike matrix
    kmax = np.power(np.ceil(np.sqrt(j_max)),2) #estimation of maximum fringe number
    n, m = Zn.Zernike_j_2_nm(np.array(range(1, int(kmax)+1))) #find n and m pairs for maximum fringe number
    Kmax = np.max(Zn.Zernike_nm_2_j(n+1, np.abs(m)+1)) #find highest order of j for which beta is needed
    if integrate == True:
        Z_mat_complex = janssen.avg_complex_zernike(x_pos_norm, y_pos_norm, Kmax, r_sh_px, spot_size = 35)
    else:
        Z_mat_complex = Zn.complex_zernike(Kmax, x_pos_norm, y_pos_norm)
        
    #Invert and solve for beta
    dW_plus = dWdx + 1j * dWdy
    dW_min = dWdx - 1j * dWdy
    beta_plus = np.linalg.lstsq(Z_mat_complex, dW_plus)[0]
    beta_min = np.linalg.lstsq(Z_mat_complex, dW_min)[0]

    kmax = int(kmax)
    a = np.zeros(kmax, dtype = np.complex_)
    a_check = np.zeros(j_max, dtype = np.complex_)
    #a_avg = np.zeros(j_max, dtype = np.complex_)
    for jj in range(2, kmax+1):
        n, m = Zn.Zernike_j_2_nm(jj)
        index1 = int(Zn.Zernike_nm_2_j(n - 1.0, m + 1.0) - 1)
        index2 = int(Zn.Zernike_nm_2_j(n - 1.0, m - 1.0) - 1)
        index3 = int(Zn.Zernike_nm_2_j(n + 1.0, m + 1.0) - 1)
        index4 = int(Zn.Zernike_nm_2_j(n + 1.0, m - 1.0) - 1)
        fact1 = 1.0 / ( 2 * n * ( 1 + (n != abs(m))))
        fact2 = 1.0 / (2 * (n+2) * ( 1 + (((n+2) != abs(m)))))
        if m + 1.0 > n - 1.0:
            a[jj-1] = fact1 * (beta_min[index2]) - fact2 * (beta_plus[index3] + beta_min[index4])
        elif np.abs(m - 1.0) > np.abs(n - 1.0):
            a[jj-1] = fact1 * (beta_plus[index1]) - fact2 * (beta_plus[index3] + beta_min[index4])
        else:
            a[jj-1] = fact1 * (beta_plus[index1] + beta_min[index2]) - fact2 * (beta_plus[index3] + beta_min[index4])

    for jj in range(2, j_max+2):
        n, m = Zn.Zernike_j_2_nm(jj)
        if m > 0:
            j_min = int(Zn.Zernike_nm_2_j(n, -m))
            a_check[jj-2] = (1.0/np.sqrt(2*n+2))*(a[jj-1] + a[j_min-1])
        elif m < 0:
            j_plus = int(Zn.Zernike_nm_2_j(n, np.abs(m)))
            a_check[jj-2] = (1.0/np.sqrt(2*n+2)) * (a[j_plus - 1] - a[jj-1]) * 1j
        else:
            a_check[jj-2] = (1.0/np.sqrt(n+1)) * a[jj-1]
    a_janss = np.real(a_check)

    return a_janss
Пример #4
0
def rms_phi_janssen(variables, *args):
    """Calculate the 2-norm distance from the intended phase to the measured phase using Janssen's method,
    variables[0] = x0
    variables[1] = y0
    variables[2] = radius
    Z_mat is used to calculate Zernike polynomials on a grid, to compare with original phase, 3rd dimension should be length j_max"""

    if args:
       x_pos_zero, y_pos_zero, x_pos_flat, y_pos_flat, x_pos_dist, y_pos_dist, px_size_sh, f_sh, j_max, wavelength, xx, yy, N, mask, Z_mat, box_len, phi_ref = args
    else:
        print("put the arguments!")
        return
    r_sh_m = px_size_sh * variables[2]

    x_pos_norm = (x_pos_flat - variables[0])/variables[2]
    y_pos_norm = (y_pos_flat - variables[1])/variables[2]

    ### check if all is within circle
    ### not implemented due to constraints
    inside = np.sqrt(x_pos_norm ** 2 + y_pos_norm**2) <= (1+ (box_len/variables[2]))
    x_pos_norm_it, y_pos_norm_it, x_pos_flat_it, y_pos_flat_it, x_pos_dist_it, y_pos_dist_it = mc.filter_positions(inside, x_pos_norm, y_pos_norm, x_pos_flat, y_pos_flat, x_pos_dist, y_pos_dist)

    ## calculate slopes
    #x_pos_dist, y_pos_dist = Hm.centroid_positions(x_pos_flat_f, y_pos_flat_f, dist_image, xx, yy, spot_size = box_len)
    dWdx, dWdy = Hm.centroid2slope(x_pos_dist_it, y_pos_dist_it, x_pos_flat_it, y_pos_flat_it, px_size_sh, f_sh, r_sh_m, wavelength)

    ## make zernike matrix
    kmax = np.power(np.ceil(np.sqrt(j_max+1)),2) #estimation of maximum fringe number
    n, m = Zn.Zernike_j_2_nm(np.array(range(1, int(kmax)+1))) #find n and m pairs for maximum fringe number
    Kmax = np.max(Zn.Zernike_nm_2_j(n+1, np.abs(m)+1)) #find highest order of j for which beta is needed
    Z_mat_complex = janssen.avg_complex_zernike(x_pos_norm_it, y_pos_norm_it, Kmax, variables[2], spot_size = box_len)

    #Invert and solve for beta
    dW_plus = dWdx + 1j * dWdy
    dW_min = dWdx - 1j * dWdy
    beta_plus = np.linalg.lstsq(Z_mat_complex, dW_plus)[0]
    beta_min = np.linalg.lstsq(Z_mat_complex, dW_min)[0]

    kmax = int(kmax)
    a = np.zeros(kmax, dtype = np.complex_)
    a_check = np.zeros(j_max, dtype = np.complex_)
    #a_avg = np.zeros(j_max, dtype = np.complex_)
    for jj in range(2, kmax+1):
        n, m = Zn.Zernike_j_2_nm(jj)
        index1 = int(Zn.Zernike_nm_2_j(n - 1.0, m + 1.0) - 1)
        index2 = int(Zn.Zernike_nm_2_j(n - 1.0, m - 1.0) - 1)
        index3 = int(Zn.Zernike_nm_2_j(n + 1.0, m + 1.0) - 1)
        index4 = int(Zn.Zernike_nm_2_j(n + 1.0, m - 1.0) - 1)

        fact1 = 1.0 / ( 2 * n * ( 1 + (n != abs(m))))
        fact2 = 1.0 / (2 * (n+2) * ( 1 + (((n+2) != abs(m)))))
        if m + 1.0 > n - 1.0:
            a[jj-1] = fact1 * (beta_min[index2]) - fact2 * (beta_plus[index3] + beta_min[index4])
        elif np.abs(m - 1.0) > np.abs(n - 1.0):
            a[jj-1] = fact1 * (beta_plus[index1]) - fact2 * (beta_plus[index3] + beta_min[index4])
        else:
            a[jj-1] = fact1 * (beta_plus[index1] + beta_min[index2]) - fact2 * (beta_plus[index3] + beta_min[index4])

    for jj in range(2, j_max+2):
        n, m = Zn.Zernike_j_2_nm(jj)
        if m > 0:
            j_min = int(Zn.Zernike_nm_2_j(n, -m))
            a_check[jj-2] = (1.0/np.sqrt(2*n+2))*(a[jj-1] + a[j_min-1])
        elif m < 0:
            j_plus = int(Zn.Zernike_nm_2_j(n, np.abs(m)))
            a_check[jj-2] = (1.0/np.sqrt(2*n+2)) * (a[j_plus - 1] - a[jj-1]) * 1j
        else:
            a_check[jj-2] = (1.0/np.sqrt(n+1)) * a[jj-1]
    a_janss = np.real(a_check)

    phi_janss = np.ma.array(np.dot(Z_mat, a_janss), mask = mask)
    phi_diff = np.ma.array(phi_ref - phi_janss, mask = mask)
    rms = np.sqrt((phi_diff**2).sum())/N
    return rms