Source code for gwadama.detectors

import bilby
import numpy as np
import scipy as sp

from . import tat


[docs] def project(h_plus: np.ndarray, h_cros: np.ndarray, *, parameters: dict, sf: int, nfft: int, detector: str) -> np.ndarray: """Project strain modes in a GW detector. Project the input GW modes in the sky as detected by the specified detector using Bilby. PARAMETERS ---------- h_plus, h_cros : NDArray GW polarizations. parameters : dict Sky position and time of the event, as requested by Bilby's method: ``` { ra: 0, dec: 0, geocent_time: 0, # In GPS. psi: 0 # Binary polarization angle } ``` REF: https://lscsoft.docs.ligo.org/bilby/api/bilby.gw.detector.interferometer.Interferometer.html#bilby.gw.detector.interferometer.Interferometer.get_detector_response sf : int Sample rate of the waveform. nfft : int Length of the FFT window. detector : str GW detector into which the modes will be projected. Must exist in Bilby's InterferometerList(). RETURNS ------- strains_projected: NDArray Strain(s) projected. If only one detector specified, it is a 1d-array. Otherwise, a 2d-array with shape (3, strain). NOTES ----- - Strains are converted to frequency domain in order to project them, and hence must be windowed. - Before the FFT, a Tukey window is used with `alpha=0.04`, therefore the initial length of the strains has to be taken into account since around 2% of the beginning and the end of the signal will be damped. """ ifo = bilby.gw.detector.InterferometerList([detector])[0] l_input = len(h_plus) assert l_input <= nfft # Pad signal and apply window (first) pad_l = (nfft - l_input)//2 pad_r = pad_l + (nfft - l_input)%2 window = sp.signal.windows.tukey(l_input, 0.04) h_plus_padded = np.pad(h_plus*window, (pad_l,pad_r)) h_cros_padded = np.pad(h_cros*window, (pad_l,pad_r)) i_merger_pad = tat.find_merger(h_plus_padded - 1j*h_cros_padded) # Bilby works in frequencies. frequencies = np.fft.rfftfreq(nfft, d=1/sf) waveform_polarizations = { 'plus': np.fft.rfft(h_plus_padded), 'cross': np.fft.rfft(h_cros_padded) } # Project the GW strains_projected = ifo.get_detector_response( waveform_polarizations, parameters, frequencies=frequencies ) strains_projected = np.fft.irfft(strains_projected) # Get back the original length and position of the GW. i_merger = tat.find_merger(strains_projected) i0 = i_merger - i_merger_pad + pad_l i1 = i0 + l_input strains_projected = strains_projected[i0:i1] return strains_projected