CubicSDR/src/FrequencyDialog.cpp

247 lines
8.4 KiB
C++

// Copyright (c) Charles J. Cliffe
// SPDX-License-Identifier: GPL-2.0+
#include "FrequencyDialog.h"
#include "wx/clipbrd.h"
#include <sstream>
#include "CubicSDR.h"
wxBEGIN_EVENT_TABLE(FrequencyDialog, wxDialog)
EVT_CHAR_HOOK(FrequencyDialog::OnChar)
EVT_SHOW(FrequencyDialog::OnShow)
wxEND_EVENT_TABLE()
FrequencyDialog::FrequencyDialog(wxWindow * parent, wxWindowID id, const wxString & title, DemodulatorInstance *demod, const wxPoint & position,
const wxSize & size, long style, FrequencyDialogTarget targetMode, wxString initString) :
wxDialog(parent, id, title, position, size, style) {
wxString freqStr;
activeDemod = demod;
this->targetMode = targetMode;
this->initialString = initString;
if (targetMode == FDIALOG_TARGET_DEFAULT) {
if (activeDemod) {
freqStr = frequencyToStr(activeDemod->getFrequency());
} else {
freqStr = frequencyToStr(wxGetApp().getFrequency());
}
}
if (targetMode == FDIALOG_TARGET_BANDWIDTH) {
std::string lastDemodType = activeDemod?activeDemod->getDemodulatorType():wxGetApp().getDemodMgr().getLastDemodulatorType();
if (lastDemodType == "USB" || lastDemodType == "LSB") {
freqStr = frequencyToStr(wxGetApp().getDemodMgr().getLastBandwidth()/2);
} else {
freqStr = frequencyToStr(wxGetApp().getDemodMgr().getLastBandwidth());
}
}
if (targetMode == FDIALOG_TARGET_WATERFALL_LPS) {
freqStr = std::to_string(wxGetApp().getAppFrame()->getWaterfallDataThread()->getLinesPerSecond());
}
if (targetMode == FDIALOG_TARGET_SPECTRUM_AVG) {
freqStr = std::to_string(wxGetApp().getSpectrumProcessor()->getFFTAverageRate());
}
if (targetMode == FDIALOG_TARGET_GAIN) {
if (wxGetApp().getActiveGainEntry() != "") {
freqStr = std::to_string((int)wxGetApp().getGain(wxGetApp().getActiveGainEntry()));
}
}
dialogText = new wxTextCtrl(this, wxID_FREQ_INPUT, freqStr, wxPoint(6, 1), wxSize(size.GetWidth() - 20, size.GetHeight() - 70),
wxTE_PROCESS_ENTER);
dialogText->SetFont(wxFont(20, wxFONTFAMILY_TELETYPE, wxFONTSTYLE_NORMAL, wxFONTWEIGHT_BOLD));
Centre();
if (initString != "" && initString.length() == 1) {
dialogText->SetValue(initString);
dialogText->SetSelection(2, 2);
dialogText->SetFocus();
} else {
if (initString != "") {
dialogText->SetValue(initString);
}
dialogText->SetSelection(-1, -1);
}
}
void FrequencyDialog::OnChar(wxKeyEvent& event) {
int c = event.GetKeyCode();
long long freq, freq2, freq_ctr, range_bw;
double dblval;
std::string lastDemodType = activeDemod?activeDemod->getDemodulatorType():wxGetApp().getDemodMgr().getLastDemodulatorType();
std::string strValue = dialogText->GetValue().ToStdString();
bool ranged = false;
std::string strValue2;
size_t range_pos;
switch (c) {
case WXK_RETURN:
case WXK_NUMPAD_ENTER:
// Do Stuff
ranged = false;
if ((range_pos = strValue.find_first_of("-")) > 0) {
strValue2 = strValue.substr(range_pos+1);
strValue = strValue.substr(0,range_pos);
if (targetMode == FDIALOG_TARGET_DEFAULT && !activeDemod && strValue.length() && strValue2.length()) {
ranged = true;
}
}
if (targetMode == FDIALOG_TARGET_DEFAULT) {
if (ranged) {
freq = strToFrequency(strValue);
freq2 = strToFrequency(strValue2);
} else {
freq = strToFrequency(strValue);
}
if (activeDemod) {
activeDemod->setTracking(true);
activeDemod->setFollow(true);
activeDemod->setFrequency(freq);
activeDemod->updateLabel(freq);
} else {
if (ranged && (freq || freq2)) {
if (freq > freq2) {
std::swap(freq,freq2);
}
range_bw = (freq2-freq);
freq_ctr = freq + (range_bw/2);
if (range_bw > wxGetApp().getSampleRate()) {
range_bw = wxGetApp().getSampleRate();
}
if (range_bw < 30000) {
range_bw = 30000;
}
if (freq == freq2) {
wxGetApp().setFrequency(freq_ctr);
wxGetApp().getAppFrame()->setViewState(freq_ctr);
} else {
if (wxGetApp().getSampleRate()/4 > range_bw) {
wxGetApp().setFrequency(freq_ctr + wxGetApp().getSampleRate()/4);
} else {
wxGetApp().setFrequency(freq_ctr);
}
wxGetApp().getAppFrame()->setViewState(freq_ctr, range_bw);
}
} else {
wxGetApp().setFrequency(freq);
}
}
}
if (targetMode == FDIALOG_TARGET_BANDWIDTH) {
freq = strToFrequency(strValue);
if (lastDemodType == "USB" || lastDemodType == "LSB") {
freq *= 2;
}
if (activeDemod) {
activeDemod->setBandwidth(freq);
} else {
wxGetApp().getDemodMgr().setLastBandwidth(freq);
}
}
if (targetMode == FDIALOG_TARGET_WATERFALL_LPS) {
try {
freq = std::stoi(strValue);
} catch (exception e) {
Close();
break;
}
if (freq > 1024) {
freq = 1024;
}
if (freq < 1) {
freq = 1;
}
wxGetApp().getAppFrame()->setWaterfallLinesPerSecond(freq);
}
if (targetMode == FDIALOG_TARGET_SPECTRUM_AVG) {
try {
dblval = std::stod(strValue);
} catch (exception e) {
Close();
break;
}
if (dblval > 0.99) {
dblval = 0.99;
}
if (dblval < 0.1) {
dblval = 0.1;
}
wxGetApp().getAppFrame()->setSpectrumAvgSpeed(dblval);
}
if (targetMode == FDIALOG_TARGET_GAIN) {
try {
freq = std::stoi(strValue);
} catch (exception e) {
break;
}
SDRDeviceInfo *devInfo = wxGetApp().getDevice();
std::string gainName = wxGetApp().getActiveGainEntry();
if (gainName == "") {
break;
}
SDRRangeMap gains = devInfo->getGains(SOAPY_SDR_RX, 0);
if (freq > gains[gainName].maximum()) {
freq = gains[gainName].maximum();
}
if (freq < gains[gainName].minimum()) {
freq = gains[gainName].minimum();
}
wxGetApp().setGain(gainName, freq);
wxGetApp().getAppFrame()->refreshGainUI();
}
Close();
break;
case WXK_ESCAPE:
Close();
break;
}
std::string allowed("0123456789.MKGHZmkghz");
// Support '-' for range
if (targetMode == FDIALOG_TARGET_DEFAULT && !activeDemod && strValue.length() > 0) {
allowed.append("-");
}
if (allowed.find_first_of(c) != std::string::npos || c == WXK_DELETE || c == WXK_BACK || c == WXK_NUMPAD_DECIMAL
|| (c >= WXK_NUMPAD0 && c <= WXK_NUMPAD9)) {
#ifdef __linux__
dialogText->OnChar(event);
event.Skip();
#else
event.DoAllowNextEvent();
#endif
} else if (event.ControlDown() && c == 'V') {
// Alter clipboard contents to remove unwanted chars
wxTheClipboard->Open();
wxTextDataObject data;
wxTheClipboard->GetData(data);
std::string clipText = data.GetText().ToStdString();
std::string pasteText = filterChars(clipText, std::string(allowed));
wxTheClipboard->SetData(new wxTextDataObject(pasteText));
wxTheClipboard->Close();
event.Skip();
} else if (c == WXK_RIGHT || c == WXK_LEFT || event.ControlDown()) {
event.Skip();
}
}
void FrequencyDialog::OnShow(wxShowEvent &event) {
if (initialString.length() == 1) {
dialogText->SetFocus();
dialogText->SetSelection(2, 2);
}
event.Skip();
}