1
0
mirror of https://github.com/f4exb/sdrangel.git synced 2024-11-13 20:01:46 -05:00

NFM Modulator: effectively modulate

This commit is contained in:
f4exb 2016-11-30 13:39:25 +01:00
parent 9f68e012f3
commit bde6b78d24
3 changed files with 24 additions and 13 deletions

View File

@ -34,6 +34,7 @@ MESSAGE_CLASS_DEFINITION(NFMMod::MsgReportFileSourceStreamTiming, Message)
NFMMod::NFMMod() :
m_modPhasor(0.0f),
m_audioFifo(4, 48000),
m_settingsMutex(QMutex::Recursive),
m_fileSize(0),
@ -47,7 +48,7 @@ NFMMod::NFMMod() :
m_config.m_inputFrequencyOffset = 0;
m_config.m_rfBandwidth = 12500;
m_config.m_afBandwidth = 3000;
m_config.m_fmDeviation = 20;
m_config.m_fmDeviation = 5000;
m_config.m_audioSampleRate = DSPEngine::instance()->getAudioSampleRate();
apply();
@ -89,24 +90,18 @@ void NFMMod::pull(Sample& sample)
if (m_interpolatorDistance > 1.0f) // decimate
{
pullAF(t);
m_modSample.real(((t+1.0f) * m_running.m_fmDeviation * 16384.0f)); // modulate and scale zero frequency carrier
m_modSample.imag(0.0f);
modulateSample();
while (!m_interpolator.decimate(&m_interpolatorDistanceRemain, m_modSample, &ci))
{
pullAF(t);
m_modSample.real(((t+1.0f) * m_running.m_fmDeviation * 16384.0f)); // modulate and scale zero frequency carrier
m_modSample.imag(0.0f);
modulateSample();
}
}
else
{
if (m_interpolator.interpolate(&m_interpolatorDistanceRemain, m_modSample, &ci))
{
pullAF(t);
m_modSample.real(((t+1.0f) * m_running.m_fmDeviation * 16384.0f)); // modulate and scale zero frequency carrier
m_modSample.imag(0.0f);
modulateSample();
}
}
@ -125,6 +120,17 @@ void NFMMod::pull(Sample& sample)
sample.m_imag = (FixReal) ci.imag();
}
void NFMMod::modulateSample()
{
Real t;
pullAF(t);
m_modPhasor += (m_running.m_fmDeviation / (float) m_running.m_audioSampleRate) * m_bandpass.filter(t) * (M_PI / 302.0f);
m_modSample.real(cos(m_modPhasor) * 32678.0f);
m_modSample.imag(sin(m_modPhasor) * 32678.0f);
}
void NFMMod::pullAF(Real& sample)
{
int16_t audioSample[2];
@ -293,11 +299,12 @@ void NFMMod::apply()
m_settingsMutex.unlock();
}
if((m_config.m_afBandwidth != m_running.m_afBandwidth) ||
if ((m_config.m_afBandwidth != m_running.m_afBandwidth) ||
(m_config.m_audioSampleRate != m_running.m_audioSampleRate))
{
m_settingsMutex.lock();
m_lowpass.create(21, m_config.m_audioSampleRate, m_config.m_afBandwidth);
m_lowpass.create(301, m_config.m_audioSampleRate, 250.0);
m_bandpass.create(301, m_config.m_audioSampleRate, 300.0, m_config.m_afBandwidth);
m_settingsMutex.unlock();
}

View File

@ -26,6 +26,7 @@
#include "dsp/nco.h"
#include "dsp/interpolator.h"
#include "dsp/lowpass.h"
#include "dsp/bandpass.h"
#include "dsp/movingaverage.h"
#include "dsp/agc.h"
#include "audio/audiofifo.h"
@ -264,12 +265,14 @@ private:
NCO m_carrierNco;
NCO m_toneNco;
float m_modPhasor; //!< baseband modulator phasor
Complex m_modSample;
Interpolator m_interpolator;
Real m_interpolatorDistance;
Real m_interpolatorDistanceRemain;
bool m_interpolatorConsumed;
Lowpass<Real> m_lowpass;
Bandpass<Real> m_bandpass;
Real m_magsq;
MovingAverage<Real> m_movingAverage;
@ -292,6 +295,7 @@ private:
void apply();
void pullAF(Real& sample);
void modulateSample();
void openFileStream();
void seekFileStream(int seekPercentage);
};

View File

@ -406,7 +406,7 @@ void NFMModGUI::applySettings()
m_nfmMod->configure(m_nfmMod->getInputMessageQueue(),
m_rfBW[ui->rfBW->currentIndex()],
ui->afBW->value() * 1000.0,
ui->fmDev->value() / 100.0f,
ui->fmDev->value() * 100.0f, // value is in '100 Hz
ui->micVolume->value(),
ui->audioMute->isChecked(),
ui->playLoop->isChecked());