Spaces:
Sleeping
Sleeping
| """ | |
| Audio Utilities - Shared audio loading functions with MP3 support | |
| """ | |
| import os | |
| from typing import Tuple | |
| import numpy as np | |
| import soundfile as sf | |
| from scipy import signal | |
| import logging | |
| logger = logging.getLogger(__name__) | |
| try: | |
| import torch | |
| TORCH_AVAILABLE = True | |
| except ImportError: | |
| TORCH_AVAILABLE = False | |
| def load_audio(audio_path: str, target_sr: int = 16000) -> Tuple[np.ndarray, int]: | |
| """ | |
| Load audio file with MP3 support using soundfile. | |
| Returns: Tuple of (audio_array, sample_rate) | |
| """ | |
| samples, sr = sf.read(audio_path, dtype='float32') | |
| if len(samples.shape) > 1: | |
| samples = samples.mean(axis=1) | |
| if sr != target_sr: | |
| samples = resample_audio(samples, sr, target_sr) | |
| return samples, target_sr | |
| def resample_audio(samples: np.ndarray, orig_sr: int, target_sr: int) -> np.ndarray: | |
| """Resample audio using scipy""" | |
| if orig_sr == target_sr: | |
| return samples | |
| duration = len(samples) / orig_sr | |
| new_length = int(duration * target_sr) | |
| resampled = signal.resample(samples, new_length) | |
| return resampled.astype(np.float32) | |
| def load_audio_torch(audio_path: str, target_sr: int = 16000) -> "torch.Tensor": | |
| """Load audio and return as torch tensor""" | |
| samples, sr = load_audio(audio_path, target_sr) | |
| if TORCH_AVAILABLE: | |
| return torch.from_numpy(samples).float() | |
| else: | |
| raise ImportError("PyTorch is required for load_audio_torch") | |
| def extract_advanced_features(audio_path: str, sample_rate: int = 16000) -> dict: | |
| """Extract advanced features using librosa (Flux, MFCC)""" | |
| import librosa | |
| try: | |
| # Load short segment for speed (max 10s) | |
| y, sr = librosa.load(audio_path, duration=10, sr=sample_rate) | |
| # Spectral Flux (Change in spectrum over time) | |
| onset_env = librosa.onset.onset_strength(y=y, sr=sr) | |
| flux = float(np.mean(onset_env)) | |
| # MFCC Variance (Timbre complexity) | |
| mfcc = librosa.feature.mfcc(y=y, sr=sr, n_mfcc=13) | |
| mfcc_var = float(np.mean(np.var(mfcc, axis=1))) | |
| return {"spectral_flux": flux, "mfcc_variance": mfcc_var} | |
| except Exception as e: | |
| logger.error(f"Error extracting advanced features: {e}") | |
| return {"spectral_flux": 0.0, "mfcc_variance": 0.0} | |