diff --git a/src/AppFrame.cpp b/src/AppFrame.cpp index 23628b1..ad99319 100644 --- a/src/AppFrame.cpp +++ b/src/AppFrame.cpp @@ -129,33 +129,36 @@ AppFrame::AppFrame() : // Make a menubar wxMenuBar *menuBar = new wxMenuBar; wxMenu *menu = new wxMenu; - - menu->Append(wxID_SET_FREQ_OFFSET, "Set Frequency Offset"); - menu->Append(wxID_SET_PPM, "Set Device PPM"); - wxMenu *dsMenu = new wxMenu; + menu->Append(wxID_OPEN, "&Open Session"); + menu->Append(wxID_SAVE, "&Save Session"); + menu->Append(wxID_SAVEAS, "Save Session &As.."); + menu->AppendSeparator(); + menu->Append(wxID_RESET, "&Reset Session"); +#ifndef __APPLE__ + menu->AppendSeparator(); + menu->Append(wxID_CLOSE); +#endif + + menuBar->Append(menu, wxT("&File")); + + menu = new wxMenu; + + menu->Append(wxID_SET_FREQ_OFFSET, "Frequency Offset"); + menu->Append(wxID_SET_PPM, "Device PPM"); + iqSwapMenuItem = menu->AppendCheckItem(wxID_SET_SWAP_IQ, "Swap I/Q"); + + wxMenu *dsMenu = new wxMenu; + dsMenu->AppendRadioItem(wxID_SET_DS_OFF, "Off"); dsMenu->AppendRadioItem(wxID_SET_DS_I, "I-ADC"); dsMenu->AppendRadioItem(wxID_SET_DS_Q, "Q-ADC"); - - menu->AppendSubMenu(dsMenu, "Direct Sampling"); - wxMenu *sessionMenu = new wxMenu; - sessionMenu->Append(wxID_OPEN, "&Open Session"); - sessionMenu->Append(wxID_SAVE, "&Save Session"); - sessionMenu->Append(wxID_SAVEAS, "Save Session &As.."); - sessionMenu->AppendSeparator(); - sessionMenu->Append(wxID_RESET, "&Reset Session"); + menu->AppendSubMenu(dsMenu, "Direct Sampling"); - menu->AppendSubMenu(sessionMenu, "Session"); + menuBar->Append(menu, wxT("&Settings")); - menu->AppendSeparator(); - - menu->Append(wxID_CLOSE); - - menuBar->Append(menu, wxT("&File")); - menu = new wxMenu; std::vector::iterator devices_i; @@ -183,7 +186,7 @@ AppFrame::AppFrame() : outputDeviceMenuItems[mdevices_i->first] = itm; } - menuBar->Append(menu, wxT("Active Demodulator &Output")); + menuBar->Append(menu, wxT("Audio &Output")); menu = new wxMenu; @@ -340,6 +343,10 @@ void AppFrame::OnMenu(wxCommandEvent& event) { wxGetApp().setDirectSampling(1); } else if (event.GetId() == wxID_SET_DS_Q) { wxGetApp().setDirectSampling(2); + } else if (event.GetId() == wxID_SET_SWAP_IQ) { + bool swap_state = !wxGetApp().getSwapIQ(); + wxGetApp().setSwapIQ(swap_state); + iqSwapMenuItem->Check(swap_state); } else if (event.GetId() == wxID_SET_PPM) { long ofs = wxGetNumberFromUser("Frequency correction for device in PPM.\ni.e. -51 for -51 PPM\n\nNote: you can adjust PPM interactively\nby holding ALT over the frequency tuning bar.\n", "Parts per million (PPM)", "Frequency Correction", wxGetApp().getPPM(), -1000, 1000, this); diff --git a/src/AppFrame.h b/src/AppFrame.h index 8066701..a97ce49 100644 --- a/src/AppFrame.h +++ b/src/AppFrame.h @@ -19,6 +19,7 @@ #define wxID_SET_DS_OFF 2004 #define wxID_SET_DS_I 2005 #define wxID_SET_DS_Q 2006 +#define wxID_SET_SWAP_IQ 2007 #define wxID_THEME_DEFAULT 2100 #define wxID_THEME_SHARP 2101 @@ -78,7 +79,8 @@ private: std::map outputDeviceMenuItems; std::map sampleRateMenuItems; std::map audioSampleRateMenuItems; - + wxMenuItem *iqSwapMenuItem; + std::string currentSessionFile; wxDECLARE_EVENT_TABLE(); diff --git a/src/CubicSDR.cpp b/src/CubicSDR.cpp index 5389fcc..64432bc 100644 --- a/src/CubicSDR.cpp +++ b/src/CubicSDR.cpp @@ -182,6 +182,14 @@ int CubicSDR::getDirectSampling() { return directSamplingMode; } +void CubicSDR::setSwapIQ(bool swapIQ) { + sdrPostThread->setSwapIQ(swapIQ); +} + +bool CubicSDR::getSwapIQ() { + return sdrPostThread->getSwapIQ(); +} + long long CubicSDR::getFrequency() { return frequency; } diff --git a/src/CubicSDR.h b/src/CubicSDR.h index 2536c0c..9ed5c5b 100644 --- a/src/CubicSDR.h +++ b/src/CubicSDR.h @@ -40,6 +40,9 @@ public: void setDirectSampling(int mode); int getDirectSampling(); + void setSwapIQ(bool swapIQ); + bool getSwapIQ(); + void setSampleRate(long long rate_in); long long getSampleRate(); diff --git a/src/sdr/SDRPostThread.cpp b/src/sdr/SDRPostThread.cpp index 9681514..db7450a 100644 --- a/src/sdr/SDRPostThread.cpp +++ b/src/sdr/SDRPostThread.cpp @@ -6,19 +6,21 @@ #include SDRPostThread::SDRPostThread() : - iqDataOutQueue(NULL), iqDataInQueue(NULL), iqVisualQueue(NULL), terminated(false), dcFilter(NULL), num_vis_samples(16384*2) { + iqDataInQueue(NULL), iqDataOutQueue(NULL), iqVisualQueue(NULL), terminated(false), dcFilter(NULL), num_vis_samples(16384*2), swapIQ(false) { // create a lookup table for (unsigned int i = 0; i <= 0xffff; i++) { - liquid_float_complex tmp; + liquid_float_complex tmp,tmp_swap; # if (__BYTE_ORDER == __LITTLE_ENDIAN) - tmp.real = (float(i & 0xff) - 127.4f) * (1.0f/128.0f); - tmp.imag = (float(i >> 8) - 127.4f) * (1.0f/128.0f); + tmp_swap.imag = tmp.real = (float(i & 0xff) - 127.4f) * (1.0f/128.0f); + tmp_swap.real = tmp.imag = (float(i >> 8) - 127.4f) * (1.0f/128.0f); _lut.push_back(tmp); + _lut_swap.push_back(tmp_swap); #else // BIG_ENDIAN - tmp.real = (float(i >> 8) - 127.4f) * (1.0f/128.0f); - tmp.imag = (float(i & 0xff) - 127.4f) * (1.0f/128.0f); + tmp_swap.imag = tmp.real = (float(i >> 8) - 127.4f) * (1.0f/128.0f); + tmp_swap.real = tmp.imag = (float(i & 0xff) - 127.4f) * (1.0f/128.0f); _lut.push_back(tmp); + _lut_swap.push_back(tmp_swap); #endif } } @@ -64,6 +66,14 @@ int SDRPostThread::getNumVisSamples() { return num_vis_samples; } +void SDRPostThread::setSwapIQ(bool swapIQ) { + this->swapIQ.store(swapIQ); +} + +bool SDRPostThread::getSwapIQ() { + return this->swapIQ.load(); +} + void SDRPostThread::threadMain() { int n_read; double seconds = 0.0; @@ -103,8 +113,14 @@ void SDRPostThread::threadMain() { dataOut.resize(dataSize); } - for (int i = 0, iMax = dataSize; i < iMax; i++) { - fpData[i] = _lut[*((uint16_t*)&data_in->data[2*i])]; + if (swapIQ) { + for (int i = 0; i < dataSize; i++) { + fpData[i] = _lut_swap[*((uint16_t*)&data_in->data[2*i])]; + } + } else { + for (int i = 0; i < dataSize; i++) { + fpData[i] = _lut[*((uint16_t*)&data_in->data[2*i])]; + } } iirfilt_crcf_execute_block(dcFilter, &fpData[0], dataSize, &dataOut[0]); diff --git a/src/sdr/SDRPostThread.h b/src/sdr/SDRPostThread.h index 38362eb..11d3f2f 100644 --- a/src/sdr/SDRPostThread.h +++ b/src/sdr/SDRPostThread.h @@ -17,7 +17,10 @@ public: void setNumVisSamples(int num_vis_samples_in); int getNumVisSamples(); - + + void setSwapIQ(bool swapIQ); + bool getSwapIQ(); + void threadMain(); void terminate(); @@ -31,7 +34,9 @@ protected: std::atomic terminated; iirfilt_crcf dcFilter; int num_vis_samples; - + std::atomic swapIQ; + private: std::vector _lut; + std::vector _lut_swap; };