23 #include <QMutexLocker> 24 #include <QNetworkAccessManager> 25 #include <QNetworkReply> 55 m_deviceAPI(deviceAPI),
56 m_basebandSampleRate(48000),
57 m_outputSampleRate(48000),
58 m_inputFrequencyOffset(0),
60 m_feedbackAudioFifo(48000),
61 m_settingsMutex(QMutex::Recursive),
150 double magsq = ci.real() * ci.real() + ci.imag() * ci.imag();
292 qDebug(
"AMDemod::pushFeedback: %u/%u audio samples written m_feedbackInterpolatorDistance: %f",
338 qDebug() <<
"AMMod::handleMessage: MsgChannelizerNotification:" 350 qDebug() <<
"AMMod::handleMessage: MsgConfigureChannelizer:" 363 qDebug() <<
"AMMod::handleMessage: MsgConfigureAMMod";
386 std::size_t samplesCount;
416 qDebug() <<
"AMMod::handleMessage: DSPConfigureAudio:" 417 <<
" sampleRate: " << sampleRate
418 <<
" audioType: " << audioType;
458 qDebug() <<
"AMMod::openFileStream: " <<
m_fileName.toStdString().c_str()
474 seekPoint *=
sizeof(
Real);
482 qDebug(
"AMMod::applyAudioSampleRate: %d", sampleRate);
505 qDebug(
"AMMod::applyFeedbackAudioSampleRate: %u", sampleRate);
522 qDebug() <<
"AMMod::applyChannelSettings:" 523 <<
" basebandSampleRate: " << basebandSampleRate
524 <<
" outputSampleRate: " << outputSampleRate
525 <<
" inputFrequencyOffset: " << inputFrequencyOffset;
552 qDebug() <<
"AMMod::applySettings:" 567 <<
" force: " << force;
569 QList<QString> reverseAPIKeys;
572 reverseAPIKeys.append(
"inputFrequencyOffset");
576 reverseAPIKeys.append(
"modFactor");
580 reverseAPIKeys.append(
"volumeFactor");
584 reverseAPIKeys.append(
"channelMute");
588 reverseAPIKeys.append(
"playLoop");
592 reverseAPIKeys.append(
"modAFInput");
597 reverseAPIKeys.append(
"rfBandwidth");
608 reverseAPIKeys.append(
"toneFrequency");
616 reverseAPIKeys.append(
"audioDeviceName");
623 reverseAPIKeys.append(
"audioSampleRate");
630 reverseAPIKeys.append(
"feedbackAudioDeviceName");
637 reverseAPIKeys.append(
"feedbackAudioSampleRate");
679 QString& errorMessage)
690 const QStringList& channelSettingsKeys,
692 QString& errorMessage)
696 bool frequencyOffsetChanged =
false;
698 if (channelSettingsKeys.contains(
"channelMute")) {
701 if (channelSettingsKeys.contains(
"inputFrequencyOffset"))
704 frequencyOffsetChanged =
true;
706 if (channelSettingsKeys.contains(
"modAFInput")) {
709 if (channelSettingsKeys.contains(
"audioDeviceName")) {
712 if (channelSettingsKeys.contains(
"playLoop")) {
715 if (channelSettingsKeys.contains(
"rfBandwidth")) {
718 if (channelSettingsKeys.contains(
"rgbColor")) {
721 if (channelSettingsKeys.contains(
"title")) {
724 if (channelSettingsKeys.contains(
"toneFrequency")) {
727 if (channelSettingsKeys.contains(
"volumeFactor")) {
730 if (channelSettingsKeys.contains(
"modFactor")) {
733 if (channelSettingsKeys.contains(
"useReverseAPI")) {
736 if (channelSettingsKeys.contains(
"reverseAPIAddress")) {
739 if (channelSettingsKeys.contains(
"reverseAPIPort")) {
742 if (channelSettingsKeys.contains(
"reverseAPIDeviceIndex")) {
745 if (channelSettingsKeys.contains(
"reverseAPIChannelIndex")) {
749 if (channelSettingsKeys.contains(
"cwKeyer"))
765 if (frequencyOffsetChanged)
788 QString& errorMessage)
862 if (channelSettingsKeys.contains(
"channelMute") || force) {
865 if (channelSettingsKeys.contains(
"inputFrequencyOffset") || force) {
868 if (channelSettingsKeys.contains(
"modAFInput") || force) {
871 if (channelSettingsKeys.contains(
"audioDeviceName") || force) {
874 if (channelSettingsKeys.contains(
"playLoop") || force) {
877 if (channelSettingsKeys.contains(
"rfBandwidth") || force) {
880 if (channelSettingsKeys.contains(
"rgbColor") || force) {
883 if (channelSettingsKeys.contains(
"title") || force) {
886 if (channelSettingsKeys.contains(
"toneFrequency") || force) {
889 if (channelSettingsKeys.contains(
"volumeFactor") || force) {
892 if (channelSettingsKeys.contains(
"modFactor") || force) {
904 QString channelSettingsURL = QString(
"http://%1:%2/sdrangel/deviceset/%3/channel/%4/settings")
910 m_networkRequest.setHeader(QNetworkRequest::ContentTypeHeader,
"application/json");
912 QBuffer *buffer=
new QBuffer();
913 buffer->open((QBuffer::ReadWrite));
914 buffer->write(swgChannelSettings->
asJson().toUtf8());
920 delete swgChannelSettings;
935 QString channelSettingsURL = QString(
"http://%1:%2/sdrangel/deviceset/%3/channel/%4/settings")
941 m_networkRequest.setHeader(QNetworkRequest::ContentTypeHeader,
"application/json");
943 QBuffer *buffer=
new QBuffer();
944 buffer->open((QBuffer::ReadWrite));
945 buffer->write(swgChannelSettings->
asJson().toUtf8());
951 delete swgChannelSettings;
956 QNetworkReply::NetworkError replyError = reply->error();
960 qWarning() <<
"AMMod::networkManagerFinished:" 961 <<
" error(" << (int) replyError
962 <<
"): " << replyError
963 <<
": " << reply->errorString();
967 QString answer = reply->readAll();
969 qDebug(
"AMMod::networkManagerFinished: reply:\n%s", answer.toStdString().c_str());
void applySettings(const AMModSettings &settings, bool force=false)
void setOriginatorChannelIndex(qint32 originator_channel_index)
void addAudioSink(AudioFifo *audioFifo, MessageQueue *sampleSinkMessageQueue, int outputDeviceIndex=-1)
Add the audio sink.
static const int m_levelNbSamples
void setModFactor(float mod_factor)
int getOutputSampleRate(int outputDeviceIndex=-1)
static const QString m_channelIdURI
void applyChannelSettings(int basebandSampleRate, int outputSampleRate, int inputFrequencyOffset, bool force=false)
void setAudioSampleRate(qint32 audio_sample_rate)
void setAudioDeviceName(QString *audio_device_name)
float m_feedbackVolumeFactor
SWGAMModReport * getAmModReport()
qint32 getReverseApiDeviceIndex()
Complex nextIQ()
Return next complex sample.
bool decimate(Real *distance, const Complex &next, Complex *result)
void webapiFormatChannelReport(SWGSDRangel::SWGChannelReport &response)
void setToneFrequency(float tone_frequency)
void push(Message *message, bool emitSignal=true)
Push message onto queue.
AudioVector m_feedbackAudioBuffer
Real m_interpolatorDistanceRemain
bool m_feedbackAudioEnable
uint16_t m_reverseAPIDeviceIndex
void removeChannelSourceAPI(ChannelAPI *channelAPI, int streamIndex=0)
void setVolumeFactor(float volume_factor)
Real m_feedbackInterpolatorDistanceRemain
static double dbPower(double magsq, double floor=1e-12)
virtual int webapiReportGet(SWGSDRangel::SWGChannelReport &response, QString &errorMessage)
virtual void pullAudio(int nbSamples)
int getInputSampleRate(int inputDeviceIndex=-1)
virtual bool handleMessage(const Message &cmd)
Processing of a message. Returns true if message has actually been processed.
void pushFeedback(Real sample)
void create(int phaseSteps, double sampleRate, double cutoff, double nbTapsPerPhase=4.5)
bool interpolate(Real *distance, const Complex &next, Complex *result)
void seekFileStream(int seekPercentage)
int getDeviceSetIndex() const
int getOutputDeviceIndex(const QString &deviceName) const
void removeChannelSource(ThreadedBasebandSampleSource *sink, int streamIndex=0)
Remove a channel source (Tx)
void setChannelPowerDb(float channel_power_db)
void removeAudioSink(AudioFifo *audioFifo)
Remove the audio sink.
virtual bool deserialize(const QByteArray &data)
void setModAfInput(qint32 mod_af_input)
Interpolator m_interpolator
QString * getReverseApiAddress()
quint32 m_audioSampleRate
void setReverseApiAddress(QString *reverse_api_address)
void processOneSample(Complex &ci)
MessageQueue * getInputMessageQueue()
Get the queue for asynchronous inbound communication.
QByteArray serialize() const
QString m_reverseAPIAddress
void levelChanged(qreal rmsLevel, qreal peakLevel, int numSamples)
static MsgReportFileSourceStreamTiming * create(std::size_t samplesCount)
QNetworkRequest m_networkRequest
void setChannelType(QString *channel_type)
void addChannelSource(ThreadedBasebandSampleSource *sink, int streamIndex=0)
Add a channel source (Tx)
void setOriginatorDeviceSetIndex(qint32 originator_device_set_index)
SWGCWKeyerSettings * getCwKeyer()
uint m_feedbackAudioBufferFill
virtual QByteArray serialize() const
void addAudioSource(AudioFifo *audioFifo, MessageQueue *sampleSourceMessageQueue, int inputDeviceIndex=-1)
Add an audio source.
void setUseReverseApi(qint32 use_reverse_api)
MessageQueue * getInputMessageQueue()
Get the queue for asynchronous inbound communication.
void setReverseApiDeviceIndex(qint32 reverse_api_device_index)
void setPhase(Real phase)
qint64 getInputFrequencyOffset()
bool m_feedbackInterpolatorConsumed
int getBasebandSampleRate() const
#define MESSAGE_CLASS_DEFINITION(Name, BaseClass)
bool getFadeSample(bool on, float &sample)
bool deserialize(const QByteArray &data)
void setChannelMute(qint32 channel_mute)
static DSPEngine * instance()
int m_inputFrequencyOffset
static MsgReportFileSourceStreamData * create(int sampleRate, quint32 recordLength)
CWSmoother & getCWSmoother()
void setChannelSampleRate(qint32 channel_sample_rate)
virtual int webapiSettingsGet(SWGSDRangel::SWGChannelSettings &response, QString &errorMessage)
quint64 m_fileSize
raw file size (bytes)
void pullAF(Real &sample)
virtual void pull(Sample &sample)
AudioVector m_audioBuffer
qint32 getReverseApiPort()
void webapiFormatChannelSettings(SWGSDRangel::SWGChannelSettings &response, const AMModSettings &settings)
void webapiReverseSendSettings(QList< QString > &channelSettingsKeys, const AMModSettings &settings, bool force)
QNetworkAccessManager * m_networkManager
static bool match(const Message *message)
Real m_interpolatorDistance
void setRgbColor(qint32 rgb_color)
void applyFeedbackAudioSampleRate(unsigned int sampleRate)
void setFreq(Real freq, Real sampleRate)
qint32 getReverseApiChannelIndex()
QString m_feedbackAudioDeviceName
This is the audio device you send the audio samples to for audio feedback.
Fixed< IntType, IntBits > sqrt(Fixed< IntType, IntBits > const &x)
static const QString m_channelId
void setDirection(qint32 direction)
uint32_t read(quint8 *data, uint32_t numSamples)
void webapiReverseSendCWSettings(const CWKeyerSettings &settings)
virtual QString asJson() override
uint16_t m_reverseAPIChannelIndex
static void webapiFormatChannelSettings(SWGSDRangel::SWGCWKeyerSettings *apiCwKeyerSettings, const CWKeyerSettings &cwKeyerSettings)
void setAmModSettings(SWGAMModSettings *am_mod_settings)
void calculateLevel(Real &sample)
qint64 m_inputFrequencyOffset
qint32 getUseReverseApi()
void setRfBandwidth(float rf_bandwidth)
ThreadedBasebandSampleSource * m_threadedChannelizer
MovingAverageUtil< double, double, 16 > m_movingAverage
AudioDeviceManager * getAudioDeviceManager()
void networkManagerFinished(QNetworkReply *reply)
qint64 getFrequencyOffset() const
QString m_audioDeviceName
This is the audio device you get the audio samples from.
quint32 m_recordLength
record length in seconds computed from file size
void setInputFrequencyOffset(qint64 input_frequency_offset)
MessageQueue * getMessageQueueToGUI()
static void webapiSettingsPutPatch(const QStringList &channelSettingsKeys, CWKeyerSettings &cwKeyerSettings, SWGSDRangel::SWGCWKeyerSettings *apiCwKeyerSettings)
MessageQueue * m_guiMessageQueue
Input message queue to the GUI.
MessageQueue m_inputMessageQueue
Queue for asynchronous inbound communication.
void setFreq(Real freq, Real sampleRate)
AMMod(DeviceAPI *deviceAPI)
void applyAudioSampleRate(int sampleRate)
int getInputDeviceIndex(const QString &deviceName) const
SWGAMModSettings * getAmModSettings()
int getSampleRate() const
void setCwKeyer(SWGCWKeyerSettings *cw_keyer)
void setTitle(QString *title)
void setPlayLoop(qint32 play_loop)
UpChannelizer * m_channelizer
void addChannelSourceAPI(ChannelAPI *channelAPI, int streamIndex=0)
Interpolator m_feedbackInterpolator
quint32 m_feedbackAudioSampleRate
bool m_interpolatorConsumed
const CWKeyerSettings & getSettings() const
int getIndexInDeviceSet() const
Real next()
Return next real sample.
std::complex< Real > Complex
AMModInputAF m_modAFInput
void setReverseApiPort(qint32 reverse_api_port)
AudioFifo m_feedbackAudioFifo
void setAmModReport(SWGAMModReport *am_mod_report)
void setSampleRate(int sampleRate)
virtual int webapiSettingsPutPatch(bool force, const QStringList &channelSettingsKeys, SWGSDRangel::SWGChannelSettings &response, QString &errorMessage)
T max(const T &x, const T &y)
uint32_t write(const quint8 *data, uint32_t numSamples)
void setReverseApiChannelIndex(qint32 reverse_api_channel_index)
void removeAudioSource(AudioFifo *audioFifo)
Remove an audio source.
QString * getAudioDeviceName()
Real m_feedbackInterpolatorDistance
void configure(MessageQueue *messageQueue, int sampleRate, int centerFrequency)
uint16_t m_reverseAPIPort
T min(const T &x, const T &y)