55 lines
1.8 KiB
C++
55 lines
1.8 KiB
C++
// NativeMixer.h — track gain/pan + master brickwall limiter (T13).
|
|
//
|
|
// MIRROR server render pipeline (`app/core/render_engine.py` track volume/pan
|
|
// + `app/core/mastering_engine.py` _apply_limiter):
|
|
// - track gain: 10^(dB/20)
|
|
// - pan constant-power: theta = ((pan+1)/2)*pi/2, L *= cos(theta), R *= sin(theta)
|
|
// (pan == 0 -> unity, khong nhan — dung nhu render_engine.py)
|
|
// - master: tong cac track (processInPlace ap dung gain/pan roi limiter)
|
|
// - brickwall limiter: t_lin = 10^(thresholdDb/20) (clamp -24..0, default -1);
|
|
// k = 1/max(0.02, t_lin); tk = tanh(k); out = tanh(x*k)/tk; roi hard clip [-1,1]
|
|
// (clip giong render_project sau apply_mastering).
|
|
//
|
|
// Audio thread an toan: chi setTrack/setLimiter tu UI thread truoc khi
|
|
// AudioStart; processInPlace doc state da set, khong lock, khong cap phat.
|
|
#pragma once
|
|
#include <cstdint>
|
|
#include <cmath>
|
|
|
|
namespace sonicforge {
|
|
|
|
using int32 = int32_t;
|
|
|
|
struct TrackGainPan
|
|
{
|
|
float gainLin = 1.0f; // 10^(dB/20)
|
|
float panL = 1.0f; // cos(theta)
|
|
float panR = 1.0f; // sin(theta)
|
|
|
|
static TrackGainPan fromDbPan (float gainDb, float pan);
|
|
};
|
|
|
|
class NativeMixer
|
|
{
|
|
public:
|
|
// gainDb: -inf..+inf dB; pan: -1..+1 (clamp). Mirrors render_engine.py.
|
|
void setTrack (const TrackGainPan& t) { m_track = t; }
|
|
|
|
// thresholdDb clamp -24..0, NaN -> -1 (mirror _clamp trong mastering_engine).
|
|
void setLimiter (bool active, float thresholdDb);
|
|
|
|
// Ap track gain/pan vao buffer roi (neu active) limiter + hard clip [-1,1]
|
|
// ngay tai buffer (in-place). frames > 0.
|
|
void processInPlace (float* outL, float* outR, int32 frames) const;
|
|
|
|
bool limiterActive () const { return m_limActive; }
|
|
|
|
private:
|
|
TrackGainPan m_track;
|
|
bool m_limActive = false;
|
|
float m_limK = 1.0f; // 1/max(0.02, t_lin)
|
|
float m_limTk = 1.0f; // tanh(k)
|
|
};
|
|
|
|
} // namespace sonicforge
|