Thanks to visit codestin.com
Credit goes to github.com

Skip to content

Commit efdda38

Browse files
author
Frank Schultz
committed
introduce new wfs 2.5D point source time domain driving function
1 parent 21bd666 commit efdda38

File tree

1 file changed

+109
-8
lines changed

1 file changed

+109
-8
lines changed

sfs/td/wfs.py

Lines changed: 109 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -39,7 +39,8 @@ def plot(d, selection, secondary_source, t=0):
3939
p = sfs.td.synthesize(d, selection, array, secondary_source, grid=grid,
4040
observation_time=t)
4141
sfs.plot2d.level(p, grid)
42-
sfs.plot2d.loudspeakers(array.x, array.n, selection * array.a, size=0.15)
42+
sfs.plot2d.loudspeakers(array.x, array.n,
43+
selection * array.a, size=0.15)
4344
4445
"""
4546
import numpy as _np
@@ -92,9 +93,9 @@ def plane_25d(x0, n0, n=[0, 1, 0], xref=[0, 0, 0], c=None):
9293
9394
.. math::
9495
95-
d_{2.5D}(x_0,t) = h(t)
96+
d_{2.5D}(x_0,t) =
9697
2 g_0 \scalarprod{n}{n_0}
97-
\dirac{t - \frac{1}{c} \scalarprod{n}{x_0}}
98+
\dirac{t - \frac{1}{c} \scalarprod{n}{x_0}} \ast_t h(t)
9899
99100
with wfs(2.5D) prefilter h(t), which is not implemented yet.
100101
@@ -125,7 +126,101 @@ def plane_25d(x0, n0, n=[0, 1, 0], xref=[0, 0, 0], c=None):
125126

126127

127128
def point_25d(x0, n0, xs, xref=[0, 0, 0], c=None):
128-
r"""Point source by 2.5-dimensional WFS.
129+
r"""Driving function for 2.5-dimensional WFS of a virtual point source.
130+
131+
.. versionchanged:: 0.61
132+
see notes, old handling of `point_25d()` is now `point_25d_legacy()`
133+
134+
Parameters
135+
----------
136+
x0 : (N, 3) array_like
137+
Sequence of secondary source positions.
138+
n0 : (N, 3) array_like
139+
Sequence of secondary source orientations.
140+
xs : (3,) array_like
141+
Virtual source position.
142+
xref : (N, 3) array_like or (3,) array_like
143+
Reference curve of correct amplitude xref(x0)
144+
c : float, optional
145+
Speed of sound
146+
147+
Returns
148+
-------
149+
delays : (N,) numpy.ndarray
150+
Delays of secondary sources in seconds.
151+
weights: (N,) numpy.ndarray
152+
Weights of secondary sources.
153+
selection : (N,) numpy.ndarray
154+
Boolean array containing ``True`` or ``False`` depending on
155+
whether the corresponding secondary source is "active" or not.
156+
secondary_source_function : callable
157+
A function that can be used to create the sound field of a
158+
single secondary source. See `sfs.td.synthesize()`.
159+
160+
Notes
161+
-----
162+
163+
Eq. (2.138) in :cite:`Schultz2016`:
164+
165+
.. math::
166+
167+
d_{2.5D}(x_0, x_{ref}, t) =
168+
\sqrt{8\pi}
169+
\frac{\scalarprod{(x_0 - x_s)}{n_0}}{|x_0 - x_s|}
170+
\sqrt{\frac{|x_0 - x_s||x_0 - x_{ref}|}{|x_0 - x_s|+|x_0 - x_{ref}|}}
171+
\cdot
172+
\frac{\dirac{t - \frac{|x_0 - x_s|}{c}}}{4\pi |x_0 - x_s|} \ast_t h(t)
173+
174+
.. math::
175+
176+
h(t) = F^{-1}(\sqrt{\frac{j \omega}{c}})
177+
178+
with wfs(2.5D) prefilter h(t), which is not implemented yet.
179+
180+
`point_25d()` derives WFS from 3D to 2.5D via the stationary phase
181+
approximation approach (i.e. the Delft approach).
182+
The theoretical link of `point_25d()` and `point_25d_legacy()` was
183+
introduced as *unified WFS framework* in :cite:`Firtha2017`.
184+
185+
Examples
186+
--------
187+
.. plot::
188+
:context: close-figs
189+
190+
delays, weights, selection, secondary_source = \
191+
sfs.td.wfs.point_25d(array.x, array.n, xs)
192+
d = sfs.td.wfs.driving_signals(delays, weights, signal)
193+
plot(d, selection, secondary_source, t=ts)
194+
195+
"""
196+
if c is None:
197+
c = _default.c
198+
x0 = _util.asarray_of_rows(x0)
199+
n0 = _util.asarray_of_rows(n0)
200+
xs = _util.asarray_1d(xs)
201+
xref = _util.asarray_of_rows(xref)
202+
203+
x0xs = x0 - xs
204+
x0xref = x0 - xref
205+
x0xs_n = _np.linalg.norm(x0xs, axis=1)
206+
x0xref_n = _np.linalg.norm(x0xref, axis=1)
207+
208+
g0 = 1/(_np.sqrt(2*_np.pi)*x0xs_n**2)
209+
g0 *= _np.sqrt((x0xs_n*x0xref_n)/(x0xs_n+x0xref_n))
210+
211+
delays = x0xs_n/c
212+
weights = g0*_inner1d(x0xs, n0)
213+
selection = _util.source_selection_point(n0, x0, xs)
214+
return delays, weights, selection, _secondary_source_point(c)
215+
216+
217+
def point_25d_legacy(x0, n0, xs, xref=[0, 0, 0], c=None):
218+
r"""Driving function for 2.5-dimensional WFS of a virtual point source.
219+
220+
.. versionadded:: 0.61
221+
`point_25d()` was renamed to `point_25d_legacy()` (and a new
222+
function with the name `point_25d()` was introduced). See notes below
223+
for further details.
129224
130225
Parameters
131226
----------
@@ -166,15 +261,21 @@ def point_25d(x0, n0, xs, xref=[0, 0, 0], c=None):
166261
167262
.. math::
168263
169-
d_{2.5D}(x_0,t) = h(t)
264+
d_{2.5D}(x_0,t) =
170265
\frac{g_0 \scalarprod{(x_0 - x_s)}{n_0}}
171266
{2\pi |x_0 - x_s|^{3/2}}
172-
\dirac{t - \frac{|x_0 - x_s|}{c}}
267+
\dirac{t - \frac{|x_0 - x_s|}{c}} \ast_t h(t)
173268
174269
with wfs(2.5D) prefilter h(t), which is not implemented yet.
175270
176271
See :sfs:`d_wfs/#equation-td-wfs-point-25d`
177272
273+
`point_25d_legacy()` derives 2.5D WFS from the 2D
274+
Neumann-Rayleigh integral (i.e. the approach by Rabenstein & Spors), cf.
275+
:cite:`Spors2008`.
276+
The theoretical link of `point_25d()` and `point_25d_legacy()` was
277+
introduced as *unified WFS framework* in :cite:`Firtha2017`.
278+
178279
Examples
179280
--------
180281
.. plot::
@@ -248,10 +349,10 @@ def focused_25d(x0, n0, xs, ns, xref=[0, 0, 0], c=None):
248349
249350
.. math::
250351
251-
d_{2.5D}(x_0,t) = h(t)
352+
d_{2.5D}(x_0,t) =
252353
\frac{g_0 \scalarprod{(x_0 - x_s)}{n_0}}
253354
{|x_0 - x_s|^{3/2}}
254-
\dirac{t + \frac{|x_0 - x_s|}{c}}
355+
\dirac{t + \frac{|x_0 - x_s|}{c}} \ast_t h(t)
255356
256357
with wfs(2.5D) prefilter h(t), which is not implemented yet.
257358

0 commit comments

Comments
 (0)