Skip to content

Commit b2961c5

Browse files
committed
add example for rigid circular array
1 parent c6d5936 commit b2961c5

File tree

1 file changed

+55
-0
lines changed

1 file changed

+55
-0
lines changed
Lines changed: 55 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,55 @@
1+
"""
2+
Compute the plane wave decomposition for an incident broadband plane wave
3+
on an open circular array using a modal beamformer of finite order.
4+
"""
5+
6+
import numpy as np
7+
import matplotlib.pyplot as plt
8+
import micarray
9+
10+
Nsf = 50 # order of the incident sound field
11+
N = 30 # order of modal beamformer/microphone array
12+
pw_angle = 1 * np.pi # incidence angle of plane wave
13+
pol_pwd = np.linspace(0, 2*np.pi, 180, endpoint=False) # angles for plane wave decomposition
14+
k = np.linspace(0.1, 20, 100) # wavenumber vector
15+
r = 1 # radius of array
16+
M = 61 # number of microphones
17+
18+
# get uniform grid (microphone positions) of number M
19+
pol, weights = micarray.modal.angular.grid_equal_polar_angle(M)
20+
21+
# get circular harmonics matrix for sensors
22+
bn = micarray.modal.radial.circular_pw(Nsf, k, r, setup='rigid')
23+
D = micarray.modal.radial.circ_diagonal_mode_mat(bn)
24+
Psi_p = micarray.modal.angular.cht_matrix(Nsf, pol, weights)
25+
Psi_pw = micarray.modal.angular.cht_matrix(Nsf, pw_angle)
26+
p = np.matmul(np.matmul(np.conj(Psi_pw.T), D), Psi_p)
27+
p = np.squeeze(p)
28+
29+
# get circular harmonics matrix for a source ensemble of azimuthal plane wave
30+
Psi_p = micarray.modal.angular.cht_matrix(N, pol)
31+
Psi_q = micarray.modal.angular.cht_matrix(N, pol_pwd)
32+
# get radial filters
33+
Bn = micarray.modal.radial.circular_pw(N, k, r, setup='rigid')
34+
Dn, _ = micarray.modal.radial.regularize(1/Bn, 100, 'softclip')
35+
D = micarray.modal.radial.circ_diagonal_mode_mat(Dn)
36+
# compute plane wave decomposition
37+
A_pwd = np.matmul(np.matmul(np.conj(Psi_q.T), D), Psi_p)
38+
q_pwd = np.squeeze(np.matmul(A_pwd, np.expand_dims(p, 2)))
39+
q_pwd_t = np.fft.fftshift(np.fft.irfft(q_pwd, axis=0), axes=0)
40+
41+
# visualize plane wave decomposition (aka beampattern)
42+
plt.figure()
43+
plt.pcolormesh(k, pol_pwd/np.pi, micarray.util.db(q_pwd.T), vmin=-40)
44+
plt.colorbar()
45+
plt.xlabel(r'$kr$')
46+
plt.ylabel(r'$\phi / \pi$')
47+
plt.title('Plane wave docomposition by modal beamformer (frequency domain)')
48+
plt.savefig('modal_open_beamformer_pwd_fd.png')
49+
50+
plt.figure()
51+
plt.pcolormesh(range(2*len(k)-2), pol_pwd/np.pi, micarray.util.db(q_pwd_t.T), vmin=-40)
52+
plt.colorbar()
53+
plt.ylabel(r'$\phi / \pi$')
54+
plt.title('Plane wave docomposition by modal beamformer (time domain)')
55+
plt.savefig('modal_open_beamformer_pwd_td.png')

0 commit comments

Comments
 (0)