mirror of
https://github.com/migatu/vtt_work.git
synced 2026-07-14 13:34:42 +00:00
94 lines
3.1 KiB
Python
94 lines
3.1 KiB
Python
import numpy as np
|
|
import soundfile as sf
|
|
from scipy.signal import lfilter, fftconvolve
|
|
|
|
# Global Parameters
|
|
sample_rate = 44100
|
|
duration_seconds = 30
|
|
samples = duration_seconds * sample_rate
|
|
t = np.linspace(0, duration_seconds, samples, endpoint=False)
|
|
|
|
# === 1. Aggressive White Noise + Reverb ===
|
|
def aggressive_white_noise():
|
|
noise = np.random.normal(0, 0.07, samples)
|
|
|
|
# High-pass filter
|
|
b = [0.95, -0.95]
|
|
a = [1, -0.85]
|
|
filtered_noise = lfilter(b, a, noise)
|
|
|
|
# Reverb via impulse response (short decaying tail)
|
|
impulse_response = np.exp(-np.linspace(0, 1.5, int(0.3 * sample_rate)))
|
|
impulse_response = impulse_response * np.random.uniform(0.8, 1.2, impulse_response.shape)
|
|
reverb_noise = fftconvolve(filtered_noise, impulse_response, mode='full')[:samples]
|
|
|
|
return reverb_noise
|
|
|
|
white_noise = aggressive_white_noise()
|
|
|
|
# === 3. Metallic Sonar Ping with Echo ===
|
|
def generate_sonar_ping(start_time, freq=5000, ping_duration=0.82):
|
|
ping_t = np.linspace(0, ping_duration, int(sample_rate * ping_duration), endpoint=False)
|
|
|
|
# FM modulation for metallic texture
|
|
mod_freq = 1000 # Modulating frequency
|
|
fm_wave = np.sin(2 * np.pi * freq * ping_t + 5 * np.sin(2 * np.pi * mod_freq * ping_t))
|
|
|
|
envelope = np.exp(-8 * ping_t)
|
|
ping = fm_wave * envelope * 0.6
|
|
|
|
mod_freq = 4000 # Modulating frequency
|
|
fm_wave = np.sin(2 * np.pi * freq * ping_t + 5 * np.sin(2 * np.pi * mod_freq * ping_t))
|
|
|
|
envelope = np.exp(-8 * ping_t)
|
|
ping = fm_wave * envelope * 0.9
|
|
|
|
mod_freq = 7000 # Modulating frequency
|
|
fm_wave = np.sin(2 * np.pi * freq * ping_t + 5 * np.sin(2 * np.pi * mod_freq * ping_t))
|
|
|
|
envelope = np.exp(-8 * ping_t)
|
|
ping = fm_wave * envelope * 0.5
|
|
|
|
# Add echo (delay)
|
|
echo_delay = int(0.01 * sample_rate)
|
|
echo = np.pad(ping * 0.1, (echo_delay, 0), 'constant')[:len(ping)]
|
|
ping = ping + echo
|
|
echo_delay = int(0.06 * sample_rate)
|
|
echo = np.pad(ping * 0.1, (echo_delay, 0), 'constant')[:len(ping)]
|
|
ping = ping + echo
|
|
echo_delay = int(0.06 * sample_rate)
|
|
echo = np.pad(ping * 0.1, (echo_delay, 0), 'constant')[:len(ping)]
|
|
ping = ping + echo
|
|
echo_delay = int(0.1 * sample_rate)
|
|
echo = np.pad(ping * 0.1, (echo_delay, 0), 'constant')[:len(ping)]
|
|
ping = ping + echo
|
|
echo_delay = int(0.2 * sample_rate)
|
|
echo = np.pad(ping * 0.1, (echo_delay, 0), 'constant')[:len(ping)]
|
|
ping = ping + echo
|
|
|
|
|
|
|
|
|
|
sonar = np.zeros(samples)
|
|
start_sample = int(start_time * sample_rate)
|
|
end_sample = start_sample + len(ping)
|
|
if end_sample <= samples:
|
|
sonar[start_sample:end_sample] = ping
|
|
return sonar
|
|
|
|
sonar_total = np.zeros(samples)
|
|
np.random.seed(42)
|
|
ping_times = np.cumsum(np.random.uniform(0.5, 3.0, size=12))
|
|
ping_times = ping_times[ping_times < duration_seconds]
|
|
for pt in ping_times:
|
|
sonar_total += generate_sonar_ping(pt)
|
|
|
|
# === 4. Combine & Normalize ===
|
|
final_mix = 0.2*white_noise + 3.0*sonar_total
|
|
final_mix = final_mix / np.max(np.abs(final_mix))
|
|
|
|
# === 5. Export ===
|
|
file_path = 'test.wav'
|
|
sf.write(file_path, final_mix, sample_rate)
|
|
print(f"✅ Saved to: {file_path}")
|