Spaces:
Running on Zero
Running on Zero
| from __future__ import annotations | |
| import torch | |
| import torch.nn.functional as F | |
| DEFAULT_EDGE_SILENCE_MS = 250.0 | |
| DEFAULT_EDGE_SILENCE_TOP_DB = 30.0 | |
| def align_length(num_samples: int, multiple_of: int | None) -> int: | |
| if multiple_of is None or multiple_of <= 0: | |
| return int(num_samples) | |
| if num_samples % multiple_of == 0: | |
| return int(num_samples) | |
| return int(((num_samples + multiple_of - 1) // multiple_of) * multiple_of) | |
| def pad_waveform_align_only( | |
| waveform: torch.Tensor, | |
| *, | |
| multiple_of: int | None, | |
| ) -> torch.Tensor: | |
| if multiple_of is None or multiple_of <= 0: | |
| return waveform | |
| target_length = align_length(waveform.size(-1), multiple_of) | |
| delta = target_length - waveform.size(-1) | |
| if delta <= 0: | |
| return waveform | |
| return F.pad(waveform, (0, delta), "constant", 0.0) | |
| def normalize_edge_silence_duration( | |
| waveform: torch.Tensor, | |
| *, | |
| sample_rate: int, | |
| target_silence_duration_ms: float = DEFAULT_EDGE_SILENCE_MS, | |
| top_db: float = DEFAULT_EDGE_SILENCE_TOP_DB, | |
| ) -> torch.Tensor: | |
| mono_waveform = waveform[0] | |
| target_samples = int(round(float(sample_rate) * float(target_silence_duration_ms) / 1000.0)) | |
| amplitude = mono_waveform.abs() | |
| peak = float(amplitude.max().item()) | |
| if peak <= 0.0: | |
| waveform = waveform[..., :target_samples] | |
| current_length = int(waveform.size(-1)) | |
| if current_length < target_samples: | |
| waveform = F.pad(waveform, (0, target_samples - current_length), "constant", 0.0) | |
| return waveform | |
| threshold = peak * (10.0 ** (-float(top_db) / 20.0)) | |
| non_silent = torch.nonzero(amplitude > threshold, as_tuple=False).flatten() | |
| first_non_silent = int(non_silent[0].item()) | |
| last_non_silent = int(non_silent[-1].item()) | |
| leading_silence_samples = first_non_silent | |
| trailing_silence_samples = int(mono_waveform.numel()) - last_non_silent - 1 | |
| leading_delta = target_samples - leading_silence_samples | |
| if leading_delta > 0: | |
| waveform = F.pad(waveform, (leading_delta, 0), "constant", 0.0) | |
| else: | |
| trim_from_start = min(-leading_delta, int(waveform.size(-1))) | |
| waveform = waveform[..., trim_from_start:] | |
| trailing_delta = target_samples - trailing_silence_samples | |
| if trailing_delta > 0: | |
| return F.pad(waveform, (0, trailing_delta), "constant", 0.0) | |
| trim_from_end = min(-trailing_delta, int(waveform.size(-1))) | |
| if trim_from_end <= 0: | |
| return waveform | |
| return waveform[..., :-trim_from_end] | |
| def compute_num_audio_tokens( | |
| num_samples: int, *, audio_samples_per_llm_token: int | |
| ) -> int: | |
| if num_samples % audio_samples_per_llm_token != 0: | |
| raise ValueError( | |
| f"Waveform length {num_samples} is not aligned to token hop {audio_samples_per_llm_token}." | |
| ) | |
| return num_samples // audio_samples_per_llm_token | |