37#include <pulp/signal/detail/fractional_synthesis_hop_accumulator.hpp>
58template <
typename SampleType =
float>
74 if (!std::isfinite(sample_rate) || !(sample_rate > 0.0))
80 && (!std::isfinite(config.max_time_ratio) || config.max_time_ratio < 1.0f))
82 const double max_pitch_ratio =
83 std::exp2(
static_cast<double>(config.max_pitch_semitones) / 12.0);
84 if (!std::isfinite(config.max_pitch_semitones) || config.max_pitch_semitones < 0.0f
85 || !std::isfinite(max_pitch_ratio))
90 config, max_pitch_ratio, target_max_bytes, geometry);
102 sample_rate_ = sample_rate;
108 coordinator_.prepare(fft_size_, config.channels);
111 transient_config.
fft_size = fft_size_;
112 if (config.transient_sensitivity > 0.0f)
113 transient_config.
sensitivity = config.transient_sensitivity;
114 transient_.prepare(transient_config);
118 freeze_config.
channels = config.channels;
120 freeze_.prepare(freeze_config);
122 envelope_ = std::move(prepared_envelope);
128 pitch_smoother_.prepare(sample_rate, smoother_config);
129 formant_smoother_.prepare(sample_rate, smoother_config);
134 ring_mask_ = ring_size_ - 1;
138 drain_buf_.assign(
static_cast<std::size_t
>(geometry.
drain_elements), SampleType{0});
139 drain_ptrs_.resize(
static_cast<size_t>(config.channels));
142 finalize_zero_ptrs_.resize(
static_cast<size_t>(config.channels));
143 for (
int ch = 0; ch < config.channels; ++ch)
144 finalize_zero_ptrs_[
static_cast<size_t>(ch)] =
145 finalize_zero_buf_.data()
146 +
static_cast<size_t>(ch)
153 const int spectral_bins = fft_size_ / 2 + 1;
154 if (config.noise_morphing) {
156 stn_config.
num_bins = spectral_bins;
164 stn_.prepare(stn_config);
165 noise_morphers_.resize(
static_cast<size_t>(config.channels));
170 for (
int ch = 0; ch < config.channels; ++ch)
171 noise_morphers_[
static_cast<size_t>(ch)].prepare(spectral_bins);
172 mag_scratch_.assign(
static_cast<size_t>(spectral_bins), SampleType{0});
173 noise_env_.assign(
static_cast<size_t>(config.channels) * spectral_bins, SampleType{0});
174 noise_spec_.assign(
static_cast<size_t>(spectral_bins), std::complex<SampleType>{});
176 if (config.sinc_resampling) {
178 tap_scratch_.assign(
static_cast<size_t>(resampler_.taps()), SampleType{0});
189 pitch_smoother_.set_target(
190 std::clamp(semitones, -config_.max_pitch_semitones, config_.max_pitch_semitones));
194 formant_smoother_.set_target(
195 std::clamp(semitones, -config_.max_pitch_semitones, config_.max_pitch_semitones));
208 time_ratio_ =
static_cast<SampleType
>(
209 std::clamp(
ratio, 1.0f / config_.max_time_ratio, config_.max_time_ratio));
214 return frames_done_ > 0
215 ?
static_cast<double>(synth_accum_int_)
216 / (
static_cast<double>(frames_done_) * analysis_hop_)
217 :
static_cast<double>(time_ratio_);
221 void process(
const SampleType*
const* in, SampleType*
const* out,
int num_samples) {
223 assert(num_samples <= config_.max_block);
225 feed_engine(in, num_samples);
226 pitch_smoother_.advance(num_samples);
227 formant_smoother_.advance(num_samples);
242 const auto hop =
static_cast<std::int64_t
>(analysis_hop_);
243 for (
int i = 0;
i < num_samples; ++
i) {
244 if (out_count_ < lat) {
245 for (
int ch = 0; ch < config_.channels; ++ch) out[ch][
i] = SampleType{0};
247 const std::int64_t target_in = out_count_ - lat;
248 const std::int64_t f = target_in / hop;
249 if (f + 1 < frames_done_) {
250 const std::int64_t s0 = frame_starts_[
static_cast<size_t>(f & kFrameMapMask)];
251 const std::int64_t s1 =
252 frame_starts_[
static_cast<size_t>((f + 1) & kFrameMapMask)];
254 static_cast<double>(target_in - f * hop) /
static_cast<double>(hop);
255 read_pos_ =
static_cast<double>(s0)
256 + frac *
static_cast<double>(s1 - s0);
257 read_fractional(out,
i);
259 for (
int ch = 0; ch < config_.channels; ++ch) out[ch][
i] = SampleType{0};
271 || num_samples > config_.max_block)
276 feed_engine(in, num_samples);
277 pitch_smoother_.advance(num_samples);
278 formant_smoother_.advance(num_samples);
284 return static_cast<int>(stretch_written_ - stretch_read_);
291 return static_cast<int>(
static_cast<std::int64_t
>(ring_size_)
292 - (stretch_written_ - stretch_read_));
304 return maximum_stream_output_lag_samples_;
313 ? engine_.samples_until_next_frame()
333 if (max_samples <= 0 || max_samples > config_.max_block)
335 if (final_output_limit_ >= 0 && stretch_written_ >= final_output_limit_) {
340 const int padding_remaining = input_closed_
341 ? finalize_padding_remaining_
342 : fft_size_ + 2 * analysis_hop_;
343 const int run = std::min(max_samples, padding_remaining);
344 if (run <= 0 || !can_accept_input(run))
355 if (max_samples <= 0 || max_samples > config_.max_block)
357 if (!input_closed_) {
358 input_closed_ =
true;
359 final_input_count_ = input_count_;
360 finalize_padding_remaining_ = fft_size_ + 2 * analysis_hop_;
362 if (final_output_limit_ >= 0 && stretch_written_ >= final_output_limit_)
366 const int run = std::min(max_samples, finalize_padding_remaining_);
370 feed_engine(finalize_zero_ptrs_.data(), run);
371 pitch_smoother_.advance(run);
372 formant_smoother_.advance(run);
373 finalize_padding_remaining_ -= run;
375 if (final_output_limit_ >= 0 && stretch_written_ >= final_output_limit_)
385 if (out ==
nullptr || num_samples <= 0)
return 0;
387 for (
int i = 0;
i < num_samples; ++
i) {
388 const bool valid = stretch_read_ < stretch_written_;
389 const auto idx =
static_cast<size_t>(stretch_read_ & ring_mask_);
390 for (
int ch = 0; ch < config_.channels; ++ch)
392 ? stretch_ring_[
static_cast<size_t>(ch) * ring_size_ + idx]
404 coordinator_.reset();
407 if (config_.noise_morphing) {
409 for (
auto& m : noise_morphers_) m.reset();
411 std::fill(stretch_ring_.begin(), stretch_ring_.end(), SampleType{0});
412 pitch_smoother_.set_immediate(pitch_smoother_.target());
413 formant_smoother_.set_immediate(formant_smoother_.target());
414 synth_hop_accumulator_.reset();
415 synth_accum_int_ = 0;
417 stretch_written_ = 0;
420 std::fill(std::begin(frame_starts_), std::end(frame_starts_),
421 static_cast<std::int64_t
>(0));
424 input_closed_ =
false;
425 final_input_count_ = 0;
426 final_output_limit_ = -1;
427 finalize_padding_remaining_ = 0;
434 void feed_engine(
const SampleType*
const* in,
int num_samples) {
436 while (done < num_samples) {
442 const int run = std::min(num_samples - done, until);
443 offset_in_block_ = done + run;
444 engine_.
analyze(advance_ptrs(in, done), run,
445 [
this](std::complex<SampleType>*
const* frames,
int bins) {
446 handle_frame(frames, bins);
453 void handle_frame(std::complex<SampleType>*
const* frames,
int bins) {
457 const SampleType pitch_ratio =
459 ?
static_cast<SampleType
>(pitch_smoother_.ratio_at(offset_in_block_))
461 const SampleType formant_ratio =
462 static_cast<SampleType
>(formant_smoother_.ratio_at(offset_in_block_));
469 const int hop = synth_hop_accumulator_.advance(
470 static_cast<double>(stretch) *
static_cast<double>(analysis_hop_),
471 1, max_synthesis_hop_);
474 frame_starts_[
static_cast<size_t>(frames_done_ & kFrameMapMask)] = synth_accum_int_;
475 synth_accum_int_ += hop;
477 update_final_output_limit();
481 freeze_.process_group(frames, config_.channels, bins);
488 config_.noise_morphing
489 && std::abs(
static_cast<double>(stretch - SampleType{1})) > 1
e-4;
501 for (
int k = 0;
k < bins; ++
k)
502 mag_scratch_[
static_cast<size_t>(k)] = std::abs(frames[0][k]);
503 const StnMasksT<SampleType>& masks = stn_.process(mag_scratch_.data());
504 for (
int ch = 0; ch < config_.channels; ++ch) {
505 std::complex<SampleType>*
f = frames[ch];
506 SampleType* env = noise_env_.data() +
static_cast<size_t>(ch) * bins;
507 for (
int k = 0;
k < bins; ++
k) {
508 const SampleType nm = masks.noise[
static_cast<size_t>(
k)];
509 env[
k] = std::abs(f[k]) * nm;
510 f[
k] *= (SampleType{1} - nm);
515 const SampleType reset_amount =
516 config_.transient_preservation
517 ? transient_.analyze(frames, config_.channels, bins)
519 coordinator_.process_group(frames, bins, analysis_hop_, hop, reset_amount);
524 const SampleType warp =
527 envelope_.process_group(frames, config_.channels, bins, warp);
541 const SampleType overlap =
static_cast<SampleType
>(fft_size_)
542 /
static_cast<SampleType
>(hop);
543 const SampleType noise_gain = std::sqrt(
static_cast<SampleType
>(8.0 / 3.0))
544 * std::pow(overlap /
static_cast<SampleType
>(8.0),
545 static_cast<SampleType
>(0.08));
546 for (
int ch = 0; ch < config_.channels; ++ch) {
547 std::complex<SampleType>*
f = frames[ch];
548 SampleType* env = noise_env_.data() +
static_cast<size_t>(ch) * bins;
549 NoiseMorpherT<SampleType>&
m = noise_morphers_[
static_cast<size_t>(ch)];
550 m.set_synthesis_gain(noise_gain);
551 m.push_envelope(env);
552 m.synthesize(SampleType{1}, noise_spec_.data());
553 for (
int k = 0; k < bins; ++k) f[k] += noise_spec_[static_cast<size_t>(k)];
557 engine_.synthesize_frame(frames, hop);
561 void drain_engine() {
562 int avail = engine_.available_output();
564 const int chunk = std::min(avail,
static_cast<int>(
565 drain_buf_.size() /
static_cast<size_t>(config_.channels)));
566 for (
int ch = 0; ch < config_.channels; ++ch)
567 drain_ptrs_[
static_cast<size_t>(ch)] =
568 drain_buf_.data() +
static_cast<size_t>(ch)
569 * (drain_buf_.size() /
static_cast<size_t>(config_.channels));
570 engine_.read_output(drain_ptrs_.data(), chunk);
573 publish =
static_cast<int>(std::min<std::int64_t>(
574 publish, std::max<std::int64_t>(0, final_output_limit_ - stretch_written_)));
577 for (
int ch = 0; ch < config_.channels; ++ch) {
578 const SampleType* src = drain_ptrs_[
static_cast<size_t>(ch)];
579 SampleType*
ring = stretch_ring_.data() +
static_cast<size_t>(ch) * ring_size_;
581 ring[
static_cast<size_t>((stretch_written_ +
i) & ring_mask_)] = src[
i];
588 bool can_accept_input(
int num_samples)
const {
589 const auto frames =
static_cast<std::int64_t
>(num_samples / analysis_hop_ + 2);
590 const auto worst_output = frames *
static_cast<std::int64_t
>(max_synthesis_hop_);
594 void update_final_output_limit() {
595 if (!input_closed_ || final_output_limit_ >= 0)
return;
596 const auto hop =
static_cast<std::int64_t
>(analysis_hop_);
597 const auto frame = final_input_count_ / hop;
598 if (frames_done_ <= frame + 1)
return;
599 const auto s0 = frame_starts_[
static_cast<size_t>(frame & kFrameMapMask)];
600 const auto s1 = frame_starts_[
static_cast<size_t>((frame + 1) & kFrameMapMask)];
601 const auto offset = final_input_count_ - frame * hop;
602 const long double mapped =
static_cast<long double>(s0)
603 +
static_cast<long double>(s1 - s0)
604 *
static_cast<long double>(offset)
605 /
static_cast<long double>(hop);
606 final_output_limit_ =
static_cast<std::int64_t
>(std::llround(mapped));
607 assert(final_output_limit_ >= stretch_written_);
613 void read_fractional(SampleType*
const* out,
int i) {
614 if (stretch_written_ < 4) {
615 for (
int ch = 0; ch < config_.channels; ++ch) out[ch][
i] = SampleType{0};
618 const auto i1 =
static_cast<std::int64_t
>(read_pos_);
619 const SampleType
t =
static_cast<SampleType
>(read_pos_ -
static_cast<double>(i1));
620 const std::int64_t last = stretch_written_ - 1;
621 const auto clamp_idx = [&](std::int64_t
p) {
622 return static_cast<size_t>(std::clamp<std::int64_t>(p, 0, last) & ring_mask_);
624 if (config_.sinc_resampling) {
625 const int taps = resampler_.taps();
626 const int half = resampler_.half_width();
627 for (
int ch = 0; ch < config_.channels; ++ch) {
628 const SampleType*
ring = stretch_ring_.data()
629 +
static_cast<size_t>(ch) * ring_size_;
632 for (
int k = 0;
k < taps; ++
k)
633 tap_scratch_[
static_cast<size_t>(k)] =
634 ring[clamp_idx(i1 + k - half + 1)];
635 out[ch][
i] = resampler_.apply(tap_scratch_.data(), t);
639 for (
int ch = 0; ch < config_.channels; ++ch) {
640 const SampleType*
ring = stretch_ring_.data()
641 +
static_cast<size_t>(ch) * ring_size_;
642 const SampleType p0 =
ring[clamp_idx(i1 - 1)];
643 const SampleType p1 =
ring[clamp_idx(i1)];
644 const SampleType p2 =
ring[clamp_idx(i1 + 1)];
645 const SampleType p3 =
ring[clamp_idx(i1 + 2)];
646 const SampleType
a =
static_cast<SampleType
>(0.5)
647 * (-p0 +
static_cast<SampleType
>(3) * p1
648 -
static_cast<SampleType
>(3) * p2 + p3);
649 const SampleType
b = p0 -
static_cast<SampleType
>(2.5) * p1
650 +
static_cast<SampleType
>(2) * p2
651 -
static_cast<SampleType
>(0.5) * p3;
652 const SampleType
c =
static_cast<SampleType
>(0.5) * (p2 - p0);
653 out[ch][
i] = ((
a *
t +
b) *
t +
c) * t + p1;
657 const SampleType*
const* advance_ptrs(
const SampleType*
const* in,
int offset) {
658 for (
int ch = 0; ch < config_.channels; ++ch)
659 in_ptrs_scratch_[ch] = in[ch] + offset;
660 return in_ptrs_scratch_;
663 static constexpr int kReadGuard = 8;
664 static constexpr int kFrameMapMask = 63;
666 RealtimePitchTimeConfig config_;
667 double sample_rate_ = 48000.0;
668 int fft_size_ = 4096;
669 int analysis_hop_ = 512;
670 SampleType time_ratio_ = SampleType{1};
672 SpectralFrameEngineT<SampleType> engine_;
673 MultichannelPhaseCoordinatorT<SampleType> coordinator_;
674 SpectralEnvelopeShifterT<SampleType> envelope_;
675 TransientPhasePolicyT<SampleType> transient_;
676 FreezeHoldT<SampleType> freeze_;
677 LatencyAwareControlSmoother pitch_smoother_;
678 LatencyAwareControlSmoother formant_smoother_;
681 StnDecomposerT<SampleType> stn_;
682 std::vector<NoiseMorpherT<SampleType>> noise_morphers_;
683 std::vector<SampleType> mag_scratch_;
684 std::vector<SampleType> noise_env_;
685 std::vector<std::complex<SampleType>> noise_spec_;
688 SincResamplerT<SampleType> resampler_;
689 std::vector<SampleType> tap_scratch_;
693 std::vector<SampleType> stretch_ring_;
694 std::vector<SampleType> drain_buf_;
695 std::vector<SampleType*> drain_ptrs_;
696 std::vector<SampleType> finalize_zero_buf_;
697 std::vector<const SampleType*> finalize_zero_ptrs_;
700 detail::FractionalSynthesisHopAccumulator synth_hop_accumulator_;
701 std::int64_t synth_accum_int_ = 0;
702 std::int64_t frames_done_ = 0;
703 std::int64_t stretch_written_ = 0;
704 std::int64_t stretch_read_ = 0;
705 double read_pos_ = 0.0;
706 std::int64_t frame_starts_[kFrameMapMask + 1] = {};
707 std::int64_t out_count_ = 0;
708 std::int64_t input_count_ = 0;
709 int offset_in_block_ = 0;
710 int max_synthesis_hop_ = 0;
711 int maximum_stream_output_lag_samples_ = 0;
712 bool input_closed_ =
false;
713 std::int64_t final_input_count_ = 0;
714 std::int64_t final_output_limit_ = -1;
715 int finalize_padding_remaining_ = 0;
@ semitone
Definition latency_aware_control_smoother.hpp:33
Definition realtime_pitch_time_processor.hpp:59
double achieved_time_ratio() const
Hop-quantized stretch actually applied so far (time_stretch mode).
Definition realtime_pitch_time_processor.hpp:213
int read_stretched(SampleType *const *out, int num_samples)
time_stretch mode: pop stretched samples (caller respects available_stretched(); excess is zero-fille...
Definition realtime_pitch_time_processor.hpp:384
void set_pitch_semitones(float semitones)
Definition realtime_pitch_time_processor.hpp:188
PitchTimePrepareStatus prepare(double sample_rate, const RealtimePitchTimeConfig &config, std::uint64_t target_max_bytes=kTargetAddressMaximumBytes)
RT contract: prepare() allocates and sizes all spectral, smoothing, ring, drain, noise-morphing,...
Definition realtime_pitch_time_processor.hpp:70
int samples_until_next_analysis_frame() const noexcept
Samples remaining before the next analysis frame completes.
Definition realtime_pitch_time_processor.hpp:311
void set_time_ratio(float ratio)
time_stretch mode only; > 1 lengthens. Takes effect at the next frame.
Definition realtime_pitch_time_processor.hpp:207
int input_priming_samples() const
Input required before the first final stretched sample can become readable.
Definition realtime_pitch_time_processor.hpp:298
PitchTimeStreamFinalizeStatus finalize(int max_samples)
Bounded finalization variant.
Definition realtime_pitch_time_processor.hpp:352
int latency_samples() const
Fixed pipeline delay of process() in realtime_pitch mode.
Definition realtime_pitch_time_processor.hpp:185
int maximum_stream_output_lag_samples() const noexcept
Admission-time causal stream delay bound in output samples for every ratio accepted by set_time_ratio...
Definition realtime_pitch_time_processor.hpp:303
void reset()
Definition realtime_pitch_time_processor.hpp:402
int available_stretched() const
time_stretch mode: stretched samples ready to read.
Definition realtime_pitch_time_processor.hpp:283
void set_formant_semitones(float semitones)
Definition realtime_pitch_time_processor.hpp:193
PitchTimeStreamFinalizeStatus finalize()
Seal the finite input stream and advance at most one prepared input block of zero padding.
Definition realtime_pitch_time_processor.hpp:322
int output_free_space() const
Remaining prepared output-ring capacity.
Definition realtime_pitch_time_processor.hpp:289
PitchTimeStreamFeedStatus feed(const SampleType *const *in, int num_samples)
time_stretch mode: atomically push one bounded input block.
Definition realtime_pitch_time_processor.hpp:269
int output_alignment_samples() const
Definition realtime_pitch_time_processor.hpp:299
void set_formant_mode(FormantMode mode)
Definition realtime_pitch_time_processor.hpp:198
PitchTimeStreamFinalizePlan plan_finalize(int max_samples) const noexcept
Allocation-free, non-mutating preflight for bounded finalization.
Definition realtime_pitch_time_processor.hpp:330
int fft_size() const
Definition realtime_pitch_time_processor.hpp:186
void set_frozen(bool frozen)
Freeze (infinite hold) of the current input moment.
Definition realtime_pitch_time_processor.hpp:203
bool is_frozen() const
Definition realtime_pitch_time_processor.hpp:204
void process(const SampleType *const *in, SampleType *const *out, int num_samples)
realtime_pitch mode: consume and produce exactly num_samples.
Definition realtime_pitch_time_processor.hpp:221
RealtimePitchTimeProcessorT()=default
Definition spectral_envelope_shifter.hpp:51
SourceFilterAnalysisStatus prepare(const SpectralEnvelopeShifterConfig &config)
RT contract: prepare() allocates FFT and scratch/envelope storage and is not audio-thread safe.
Definition spectral_envelope_shifter.hpp:76
void analyze(const SampleType *const *in, int num_samples, Fn &&on_frames)
Split API — analysis only.
Definition spectral_frame_engine.hpp:524
int samples_until_next_frame() const
Samples that must still be fed before the next analysis frame completes (>= 1).
Definition spectral_frame_engine.hpp:512
Spectral freeze / infinite hold for phase-vocoder frame groups.
Sample-accurate, block-size-independent control smoothing with independent attack/release time consta...
Phase-vocoder phase propagation for coherent channel groups.
@ publish
Definition component.hpp:89
@ f
Definition pitch.hpp:25
@ b
Definition pitch.hpp:31
@ ring
Definition string.hpp:18
@ half
Definition units.hpp:290
Definition additive_bank.hpp:218
@ Ok
Definition source_filter_analysis.hpp:29
@ realtime_pitch
Definition realtime_pitch_time_geometry.hpp:26
@ time_stretch
Definition realtime_pitch_time_geometry.hpp:26
RealtimePitchTimeProcessorT< float > RealtimePitchTimeProcessor
Definition realtime_pitch_time_processor.hpp:718
@ c
Definition spectrum_trace.hpp:35
RealtimePitchTimeProcessorT< double > RealtimePitchTimeProcessor64
Definition realtime_pitch_time_processor.hpp:719
@ needs_drain
Definition realtime_pitch_time_geometry.hpp:39
@ invalid_mode
Definition realtime_pitch_time_geometry.hpp:41
@ invalid_request
Definition realtime_pitch_time_geometry.hpp:42
@ ready
Definition realtime_pitch_time_geometry.hpp:38
@ complete
Definition realtime_pitch_time_geometry.hpp:40
PitchTimeStreamFinalizeStatus
Definition realtime_pitch_time_geometry.hpp:30
@ invalid_mode
Definition realtime_pitch_time_geometry.hpp:34
@ draining
Definition realtime_pitch_time_geometry.hpp:31
@ invalid_request
Definition realtime_pitch_time_geometry.hpp:35
@ backpressure
Definition realtime_pitch_time_geometry.hpp:32
@ complete
Definition realtime_pitch_time_geometry.hpp:33
@ quality
Definition realtime_pitch_time_geometry.hpp:25
@ ratio
base_frequency_hz * ratio.
Definition fm_operator_engine.hpp:20
constexpr int kRealtimePitchTimeMaximumChannels
Definition realtime_pitch_time_geometry.hpp:79
constexpr std::uint64_t kTargetAddressMaximumBytes
Definition checked_allocation.hpp:9
@ a
Definition formant_filter_bank.hpp:20
@ i
Definition formant_filter_bank.hpp:20
@ e
Definition formant_filter_bank.hpp:20
PitchTimePrepareStatus
Definition realtime_pitch_time_geometry.hpp:50
@ unrepresentable_capacity
Definition realtime_pitch_time_geometry.hpp:58
@ invalid_channel_count
Definition realtime_pitch_time_geometry.hpp:53
@ invalid_sample_rate
Definition realtime_pitch_time_geometry.hpp:52
@ invalid_max_time_ratio
Definition realtime_pitch_time_geometry.hpp:55
@ prepared
Definition realtime_pitch_time_geometry.hpp:51
@ invalid_max_pitch_semitones
Definition realtime_pitch_time_geometry.hpp:56
@ invalid_max_block
Definition realtime_pitch_time_geometry.hpp:54
PitchTimeStreamFeedStatus
Definition realtime_pitch_time_geometry.hpp:29
@ accepted
Definition realtime_pitch_time_geometry.hpp:29
@ invalid_request
Definition realtime_pitch_time_geometry.hpp:29
@ input_closed
Definition realtime_pitch_time_geometry.hpp:29
@ backpressure
Definition realtime_pitch_time_geometry.hpp:29
FormantMode
Definition realtime_pitch_time_geometry.hpp:27
@ preserve
Definition realtime_pitch_time_geometry.hpp:27
PitchTimePrepareStatus checked_realtime_pitch_time_prepared_geometry(const RealtimePitchTimeConfig &config, double max_pitch_ratio, std::uint64_t requested_max_bytes, RealtimePitchTimePreparedGeometry< SampleType > &prepared) noexcept
Derive all processor geometry and compose the retained-storage contracts of its owned DSP primitives ...
Definition realtime_pitch_time_geometry.hpp:101
@ m
Definition input_events.hpp:40
@ p
Definition input_events.hpp:40
@ k
Definition input_events.hpp:40
@ t
Definition input_events.hpp:41
@ stretch
Definition design_ir.hpp:57
Time-stretch the noise component of a sound by morphing, not by phase-vocoder propagation.
Pure configuration and retained-storage admission for the realtime pitch/time processor.
Fractional-delay resampling by a Kaiser-windowed sinc kernel.
Spectral-envelope estimation and formant warping for phase-vocoder frame groups.
Streaming STFT analysis + weighted overlap-add (WOLA) synthesis for DSP-grade spectral processing — d...
Sines / Transients / Noise (STN) decomposition of a spectral frame stream by median-filter masking.
Two sizing modes.
Definition freeze_hold.hpp:410
int fft_size
Definition freeze_hold.hpp:411
int analysis_hop
Definition freeze_hold.hpp:413
int channels
Definition freeze_hold.hpp:412
Definition latency_aware_control_smoother.hpp:35
float attack_seconds
Definition latency_aware_control_smoother.hpp:37
float release_seconds
Definition latency_aware_control_smoother.hpp:38
Domain domain
Definition latency_aware_control_smoother.hpp:36
Definition realtime_pitch_time_geometry.hpp:45
Definition realtime_pitch_time_geometry.hpp:61
Definition realtime_pitch_time_geometry.hpp:82
std::uint64_t finalize_zero_elements
Definition realtime_pitch_time_geometry.hpp:94
std::uint64_t drain_elements
Definition realtime_pitch_time_geometry.hpp:93
int maximum_stream_output_lag_samples
Conservative output-domain delay required by a causal time-stretch stream over the complete admitted ...
Definition realtime_pitch_time_geometry.hpp:91
int ring_size
Definition realtime_pitch_time_geometry.hpp:86
int fft_size
Definition realtime_pitch_time_geometry.hpp:84
SpectralFrameEngineConfig engine_config
Definition realtime_pitch_time_geometry.hpp:83
int analysis_hop
Definition realtime_pitch_time_geometry.hpp:85
std::uint64_t stretch_ring_elements
Definition realtime_pitch_time_geometry.hpp:92
Definition spectral_envelope_shifter.hpp:38
int fft_size
Definition spectral_envelope_shifter.hpp:39
int true_envelope_iterations
True-envelope refinement passes (0 = plain liftering).
Definition spectral_envelope_shifter.hpp:45
int max_block
Definition spectral_frame_engine.hpp:60
int max_synthesis_hop
Definition spectral_frame_engine.hpp:61
Definition stn_decomposer.hpp:39
int freq_median
odd; bins for the vertical (transient) median
Definition stn_decomposer.hpp:42
bool causal
Align the masks to the NEWEST pushed frame instead of the ring's center frame.
Definition stn_decomposer.hpp:59
int num_bins
fft_size/2 + 1
Definition stn_decomposer.hpp:40
int time_median
odd; frames for the horizontal (tonal) median
Definition stn_decomposer.hpp:41
Definition transient_phase_policy.hpp:38
int fft_size
Definition transient_phase_policy.hpp:39
float sensitivity
Definition transient_phase_policy.hpp:41
Spectral-flux transient detection for phase-vocoder streams.