muzgen/lib/Sine.cpp

51 lines
1.3 KiB
C++

#include "Sine.hpp"
namespace muz
{
/*explicit*/ Sine::Sine(AudioConf const& conf,
std::unique_ptr<Signal> freq,
std::unique_ptr<Signal> amplitude)
: m_conf { conf }
, m_out_freq {std::vector<float> (m_conf.channels(), 0.0f)}
, m_out_amp {std::vector<float> (m_conf.channels(), 0.0f)}
, m_freq { std::move(freq) }
, m_amplitude { std::move(amplitude) }
{
for (size_t i=0; i<static_cast<size_t>(m_conf.channels()); i++)
{
m_phases.push_back(0.0f);
}
}
/*virtual*/ Sine::~Sine()
{
}
void Sine::next(std::vector<float>& out) /*override*/
{
assert(m_freq);
assert(m_amplitude);
m_freq->next(m_out_freq);
m_amplitude->next(m_out_amp);
if (m_out_freq.size() != m_out_amp.size()
|| m_out_freq.size() != m_phases.size())
{
throw signal_error {"cannot generate sine: channel number mismatch"};
}
for (size_t i=0; i<static_cast<size_t>(m_conf.channels()); i++)
{
float const value = m_out_amp[i] * std::sin(m_phases[i]);
m_phases[i] += 2 * M_PI * m_out_freq[i]
/ static_cast<float>(m_conf.samplerate());
m_phases[i] = std::fmod(m_phases[i], 2.0f * M_PI);
out[i] = value;
}
}
}