diff --git a/firmware/application/Makefile b/firmware/application/Makefile index 4aa171a4..5b2262e6 100755 --- a/firmware/application/Makefile +++ b/firmware/application/Makefile @@ -175,7 +175,6 @@ CPPSRC = main.cpp \ tpms_app.cpp \ ert_app.cpp \ ../common/ert_packet.cpp \ - spectrum_analysis_app.cpp \ sd_card.cpp \ file.cpp \ log_file.cpp \ diff --git a/firmware/application/analog_audio_app.cpp b/firmware/application/analog_audio_app.cpp index d5094c60..47cfb814 100644 --- a/firmware/application/analog_audio_app.cpp +++ b/firmware/application/analog_audio_app.cpp @@ -30,33 +30,6 @@ using namespace portapack; #include "utility.hpp" -AnalogAudioModel::AnalogAudioModel(ReceiverModel::Mode mode) { - receiver_model.set_baseband_configuration({ - .mode = toUType(mode), - .sampling_rate = 3072000, - .decimation_factor = 1, - }); - receiver_model.set_baseband_bandwidth(1750000); - - switch(mode) { - case ReceiverModel::Mode::NarrowbandFMAudio: - configure_nbfm(2); - break; - - case ReceiverModel::Mode::WidebandFMAudio: - configure_wfm(); - break; - - case ReceiverModel::Mode::AMAudio: - configure_am(0); - break; - - default: - break; - } - -} - struct NBFMMode { const fir_taps_real<24> decim_0; const fir_taps_real<32> decim_1; @@ -122,3 +95,227 @@ void AnalogAudioModel::configure_am(const size_t index) { shared_memory.baseband_queue.push(message); clock_manager.set_base_audio_clock_divider(4); } + +namespace ui { + +/* AnalogAudioView *******************************************************/ + +AnalogAudioView::AnalogAudioView( + NavigationView& nav +) { + add_children({ { + &rssi, + &channel, + &audio, + &field_frequency, + &field_lna, + &field_vga, + &options_modulation, + &field_volume, + &view_frequency_options, + &view_rf_gain_options, + &waterfall, + } }); + + field_frequency.set_value(receiver_model.tuning_frequency()); + field_frequency.set_step(receiver_model.frequency_step()); + field_frequency.on_change = [this](rf::Frequency f) { + this->on_tuning_frequency_changed(f); + }; + field_frequency.on_edit = [this, &nav]() { + // TODO: Provide separate modal method/scheme? + auto new_view = nav.push(receiver_model.tuning_frequency()); + new_view->on_changed = [this](rf::Frequency f) { + this->on_tuning_frequency_changed(f); + this->field_frequency.set_value(f); + }; + }; + + field_frequency.on_show_options = [this]() { + this->on_show_options_frequency(); + }; + + field_lna.set_value(receiver_model.lna()); + field_lna.on_change = [this](int32_t v) { + this->on_lna_changed(v); + }; + + field_lna.on_show_options = [this]() { + this->on_show_options_rf_gain(); + }; + + field_vga.set_value(receiver_model.vga()); + field_vga.on_change = [this](int32_t v_db) { + this->on_vga_changed(v_db); + }; + + options_modulation.set_by_value(1); + options_modulation.on_change = [this](size_t n, OptionsField::value_t v) { + (void)n; + this->on_modulation_changed(v); + }; + + field_volume.set_value((receiver_model.headphone_volume() - wolfson::wm8731::headphone_gain_range.max).decibel() + 99); + field_volume.on_change = [this](int32_t v) { + this->on_headphone_volume_changed(v); + }; + + view_frequency_options.hidden(true); + view_frequency_options.set_step(receiver_model.frequency_step()); + view_frequency_options.on_change_step = [this](rf::Frequency f) { + this->on_frequency_step_changed(f); + }; + view_frequency_options.set_reference_ppm_correction(receiver_model.reference_ppm_correction()); + view_frequency_options.on_change_reference_ppm_correction = [this](int32_t v) { + this->on_reference_ppm_correction_changed(v); + }; + + view_rf_gain_options.hidden(true); + view_rf_gain_options.set_rf_amp(receiver_model.rf_amp()); + view_rf_gain_options.on_change_rf_amp = [this](bool enable) { + this->on_rf_amp_changed(enable); + }; +} + +AnalogAudioView::~AnalogAudioView() { + // TODO: Manipulating audio codec here, and in ui_receiver.cpp. Good to do + // both? + audio_codec.headphone_mute(); + + receiver_model.disable(); +} + +void AnalogAudioView::on_show() { + View::on_show(); + // TODO: Terrible kludge because widget system doesn't notify Waterfall that + // it's being shown or hidden. +} + +void AnalogAudioView::on_hide() { + // TODO: Terrible kludge because widget system doesn't notify Waterfall that + // it's being shown or hidden. + waterfall.on_hide(); + View::on_hide(); +} + +void AnalogAudioView::set_parent_rect(const Rect new_parent_rect) { + View::set_parent_rect(new_parent_rect); + + const ui::Rect waterfall_rect { 0, header_height, new_parent_rect.width(), static_cast(new_parent_rect.height() - header_height) }; + waterfall.set_parent_rect(waterfall_rect); +} + +void AnalogAudioView::focus() { + field_frequency.focus(); +} + +void AnalogAudioView::on_tuning_frequency_changed(rf::Frequency f) { + receiver_model.set_tuning_frequency(f); +} + +void AnalogAudioView::on_baseband_bandwidth_changed(uint32_t bandwidth_hz) { + receiver_model.set_baseband_bandwidth(bandwidth_hz); +} + +void AnalogAudioView::on_rf_amp_changed(bool v) { + receiver_model.set_rf_amp(v); +} + +void AnalogAudioView::on_lna_changed(int32_t v_db) { + receiver_model.set_lna(v_db); +} + +void AnalogAudioView::on_vga_changed(int32_t v_db) { + receiver_model.set_vga(v_db); +} + +void AnalogAudioView::on_modulation_changed(int32_t mode) { + // remove_child(widget_content.get()); + // widget_content.reset(); + + // TODO: Terrible kludge because widget system doesn't notify Waterfall that + // it's being shown or hidden. + waterfall.on_hide(); + + switch(mode) { + default: + case 1: + receiver_model.set_baseband_configuration({ + .mode = toUType(ReceiverModel::Mode::AMAudio), + .sampling_rate = 3072000, + .decimation_factor = 1, + }); + receiver_model.set_baseband_bandwidth(1750000); + receiver_model.enable(); + model.configure_am(0); + waterfall.on_show(); + break; + + case 2: + receiver_model.set_baseband_configuration({ + .mode = toUType(ReceiverModel::Mode::NarrowbandFMAudio), + .sampling_rate = 3072000, + .decimation_factor = 1, + }); + receiver_model.set_baseband_bandwidth(1750000); + receiver_model.enable(); + model.configure_nbfm(1); + waterfall.on_show(); + break; + + case 3: + receiver_model.set_baseband_configuration({ + .mode = toUType(ReceiverModel::Mode::WidebandFMAudio), + .sampling_rate = 3072000, + .decimation_factor = 1, + }); + receiver_model.set_baseband_bandwidth(1750000); + receiver_model.enable(); + model.configure_wfm(); + waterfall.on_show(); + break; + + case 4: + receiver_model.set_baseband_configuration({ + .mode = 4, + .sampling_rate = 20000000, + .decimation_factor = 1, + }); + receiver_model.set_baseband_bandwidth(12000000); + receiver_model.enable(); + waterfall.on_show(); + break; + } +} + +void AnalogAudioView::on_show_options_frequency() { + view_rf_gain_options.hidden(true); + field_lna.set_style(nullptr); + + view_frequency_options.hidden(false); + field_frequency.set_style(&view_frequency_options.style()); +} + +void AnalogAudioView::on_show_options_rf_gain() { + view_frequency_options.hidden(true); + field_frequency.set_style(nullptr); + + view_rf_gain_options.hidden(false); + field_lna.set_style(&view_frequency_options.style()); +} + +void AnalogAudioView::on_frequency_step_changed(rf::Frequency f) { + receiver_model.set_frequency_step(f); + field_frequency.set_step(f); +} + +void AnalogAudioView::on_reference_ppm_correction_changed(int32_t v) { + receiver_model.set_reference_ppm_correction(v); +} + +void AnalogAudioView::on_headphone_volume_changed(int32_t v) { + const auto new_volume = volume_t::decibel(v - 99) + wolfson::wm8731::headphone_gain_range.max; + receiver_model.set_headphone_volume(new_volume); +} + +} /* namespace ui */ diff --git a/firmware/application/analog_audio_app.hpp b/firmware/application/analog_audio_app.hpp index a598a6b4..7a1920dd 100644 --- a/firmware/application/analog_audio_app.hpp +++ b/firmware/application/analog_audio_app.hpp @@ -23,13 +23,14 @@ #define __ANALOG_AUDIO_APP_H__ #include "receiver_model.hpp" + +#include "ui_receiver.hpp" #include "ui_spectrum.hpp" +#include "ui_font_fixed_8x16.hpp" + class AnalogAudioModel { public: - AnalogAudioModel(ReceiverModel::Mode mode); - -private: void configure_nbfm(const size_t index); void configure_wfm(); void configure_am(const size_t index); @@ -37,16 +38,110 @@ private: namespace ui { -class AnalogAudioView : public spectrum::WaterfallWidget { +constexpr Style style_options_group { + .font = font::fixed_8x16, + .background = Color::blue(), + .foreground = Color::white(), +}; + +class AnalogAudioView : public View { public: - AnalogAudioView( - ReceiverModel::Mode mode - ) : model { mode } - { - } + AnalogAudioView(NavigationView& nav); + ~AnalogAudioView(); + + void on_show() override; + void on_hide() override; + + void set_parent_rect(const Rect new_parent_rect) override; + + void focus() override; private: AnalogAudioModel model; + + static constexpr ui::Dim header_height = 2 * 16; + + RSSI rssi { + { 21 * 8, 0, 6 * 8, 4 }, + }; + + Channel channel { + { 21 * 8, 5, 6 * 8, 4 }, + }; + + Audio audio { + { 21 * 8, 10, 6 * 8, 4 }, + }; + + FrequencyField field_frequency { + { 5 * 8, 0 * 16 }, + }; + + LNAGainField field_lna { + { 15 * 8, 0 * 16 } + }; + + NumberField field_vga { + { 18 * 8, 0 * 16}, + 2, + { max2837::vga::gain_db_range.minimum, max2837::vga::gain_db_range.maximum }, + max2837::vga::gain_db_step, + ' ', + }; + + OptionsField options_modulation { + { 0 * 8, 0 * 16 }, + 4, + { + { " AM ", 1 }, + { "NFM ", 2 }, + { "WFM ", 3 }, + { "SPEC", 4 }, + } + }; + + NumberField field_volume { + { 28 * 8, 0 * 16 }, + 2, + { 0, 99 }, + 1, + ' ', + }; + + FrequencyOptionsView view_frequency_options { + { 0 * 8, 1 * 16, 30 * 8, 1 * 16 }, + &style_options_group + }; + + RadioGainOptionsView view_rf_gain_options { + { 0 * 8, 1 * 16, 30 * 8, 1 * 16 }, + &style_options_group + }; +/* + AmplitudeModulationOptionsView view_am_modulation_options { + { 0 * 8, 1 * 16, 30 * 8, 1 * 16 }, + &style_options_group + }; + + FrequencyModulationOptionsView view_fm_modulation_options { + { 0 * 8, 1 * 16, 30 * 8, 1 * 16 }, + &style_options_group + }; +*/ + spectrum::WaterfallWidget waterfall; + + void on_tuning_frequency_changed(rf::Frequency f); + void on_baseband_bandwidth_changed(uint32_t bandwidth_hz); + void on_rf_amp_changed(bool v); + void on_lna_changed(int32_t v_db); + void on_vga_changed(int32_t v_db); + void on_modulation_changed(int32_t v); + void on_show_options_frequency(); + void on_show_options_rf_gain(); + void on_frequency_step_changed(rf::Frequency f); + void on_reference_ppm_correction_changed(int32_t v); + void on_headphone_volume_changed(int32_t v); + void on_edit_frequency(); }; } /* namespace ui */ diff --git a/firmware/application/spectrum_analysis_app.cpp b/firmware/application/spectrum_analysis_app.cpp deleted file mode 100644 index de3a14b0..00000000 --- a/firmware/application/spectrum_analysis_app.cpp +++ /dev/null @@ -1,34 +0,0 @@ -/* - * Copyright (C) 2014 Jared Boone, ShareBrained Technology, Inc. - * - * This file is part of PortaPack. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. If not, write to - * the Free Software Foundation, Inc., 51 Franklin Street, - * Boston, MA 02110-1301, USA. - */ - -#include "spectrum_analysis_app.hpp" - -#include "portapack.hpp" -using namespace portapack; - -SpectrumAnalysisModel::SpectrumAnalysisModel() { - receiver_model.set_baseband_configuration({ - .mode = 4, - .sampling_rate = 20000000, - .decimation_factor = 1, - }); - receiver_model.set_baseband_bandwidth(12000000); -} diff --git a/firmware/application/spectrum_analysis_app.hpp b/firmware/application/spectrum_analysis_app.hpp deleted file mode 100644 index 9e8196af..00000000 --- a/firmware/application/spectrum_analysis_app.hpp +++ /dev/null @@ -1,44 +0,0 @@ -/* - * Copyright (C) 2014 Jared Boone, ShareBrained Technology, Inc. - * - * This file is part of PortaPack. - * - * This program is free software; you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation; either version 2, or (at your option) - * any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program; see the file COPYING. If not, write to - * the Free Software Foundation, Inc., 51 Franklin Street, - * Boston, MA 02110-1301, USA. - */ - -#ifndef __SPECTRUM_ANALYSIS_APP_H__ -#define __SPECTRUM_ANALYSIS_APP_H__ - -#include "receiver_model.hpp" -#include "ui_spectrum.hpp" - -class SpectrumAnalysisModel { -public: - SpectrumAnalysisModel(); -}; - -namespace ui { - -class SpectrumAnalysisView : public spectrum::WaterfallWidget { -public: - -private: - SpectrumAnalysisModel model; -}; - -} /* namespace ui */ - -#endif/*__SPECTRUM_ANALYSIS_APP_H__*/ diff --git a/firmware/application/ui_navigation.cpp b/firmware/application/ui_navigation.cpp index 6a21d215..364db962 100644 --- a/firmware/application/ui_navigation.cpp +++ b/firmware/application/ui_navigation.cpp @@ -27,8 +27,8 @@ #include "ui_setup.hpp" #include "ui_debug.hpp" -#include "ui_receiver.hpp" +#include "analog_audio_app.hpp" #include "ais_app.hpp" #include "ert_app.hpp" #include "tpms_app.hpp" @@ -140,7 +140,7 @@ TranspondersMenuView::TranspondersMenuView(NavigationView& nav) { ReceiverMenuView::ReceiverMenuView(NavigationView& nav) { add_items<2>({ { - { "Audio", [&nav](){ nav.push(); } }, + { "Audio", [&nav](){ nav.push(); } }, { "Transponders", [&nav](){ nav.push(); } }, } }); } diff --git a/firmware/application/ui_receiver.cpp b/firmware/application/ui_receiver.cpp index 4263a84c..f80db742 100644 --- a/firmware/application/ui_receiver.cpp +++ b/firmware/application/ui_receiver.cpp @@ -26,11 +26,7 @@ using namespace portapack; #include "string_format.hpp" -#include "analog_audio_app.hpp" -#include "ais_app.hpp" -#include "tpms_app.hpp" -#include "ert_app.hpp" -#include "spectrum_analysis_app.hpp" +#include "max2837.hpp" namespace ui { @@ -322,184 +318,4 @@ void LNAGainField::on_focus() { } } -/* ReceiverView **********************************************************/ - -ReceiverView::ReceiverView( - NavigationView& nav -) { - add_children({ { - &rssi, - &channel, - &audio, - &field_frequency, - &field_lna, - &field_vga, - &options_modulation, - &field_volume, - &view_frequency_options, - &view_rf_gain_options, - } }); - - field_frequency.set_value(receiver_model.tuning_frequency()); - field_frequency.set_step(receiver_model.frequency_step()); - field_frequency.on_change = [this](rf::Frequency f) { - this->on_tuning_frequency_changed(f); - }; - field_frequency.on_edit = [this, &nav]() { - // TODO: Provide separate modal method/scheme? - auto new_view = nav.push(receiver_model.tuning_frequency()); - new_view->on_changed = [this](rf::Frequency f) { - this->on_tuning_frequency_changed(f); - this->field_frequency.set_value(f); - }; - }; - field_frequency.on_show_options = [this]() { - this->on_show_options_frequency(); - }; - - field_lna.set_value(receiver_model.lna()); - field_lna.on_change = [this](int32_t v) { - this->on_lna_changed(v); - }; - field_lna.on_show_options = [this]() { - this->on_show_options_rf_gain(); - }; - - field_vga.set_value(receiver_model.vga()); - field_vga.on_change = [this](int32_t v_db) { - this->on_vga_changed(v_db); - }; - - options_modulation.set_by_value(receiver_model.modulation()); - options_modulation.on_change = [this](size_t n, OptionsField::value_t v) { - (void)n; - this->on_modulation_changed(static_cast(v)); - }; - - field_volume.set_value((receiver_model.headphone_volume() - wolfson::wm8731::headphone_gain_range.max).decibel() + 99); - field_volume.on_change = [this](int32_t v) { - this->on_headphone_volume_changed(v); - }; - - view_frequency_options.hidden(true); - view_frequency_options.set_step(receiver_model.frequency_step()); - view_frequency_options.on_change_step = [this](rf::Frequency f) { - this->on_frequency_step_changed(f); - }; - view_frequency_options.set_reference_ppm_correction(receiver_model.reference_ppm_correction()); - view_frequency_options.on_change_reference_ppm_correction = [this](int32_t v) { - this->on_reference_ppm_correction_changed(v); - }; - - view_rf_gain_options.hidden(true); - view_rf_gain_options.set_rf_amp(receiver_model.rf_amp()); - view_rf_gain_options.on_change_rf_amp = [this](bool enable) { - this->on_rf_amp_changed(enable); - }; - - receiver_model.enable(); -} - -ReceiverView::~ReceiverView() { - - // TODO: Manipulating audio codec here, and in ui_receiver.cpp. Good to do - // both? - audio_codec.headphone_mute(); - - receiver_model.disable(); -} - -void ReceiverView::on_show() { - View::on_show(); - - // TODO: Separate concepts of baseband "modulation" and receiver "mode". - on_modulation_changed(static_cast(receiver_model.modulation())); -} - -void ReceiverView::on_hide() { - on_modulation_changed(static_cast(-1)); - - View::on_hide(); -} - -void ReceiverView::focus() { - field_frequency.focus(); -} - -void ReceiverView::on_tuning_frequency_changed(rf::Frequency f) { - receiver_model.set_tuning_frequency(f); -} - -void ReceiverView::on_baseband_bandwidth_changed(uint32_t bandwidth_hz) { - receiver_model.set_baseband_bandwidth(bandwidth_hz); -} - -void ReceiverView::on_rf_amp_changed(bool v) { - receiver_model.set_rf_amp(v); -} - -void ReceiverView::on_lna_changed(int32_t v_db) { - receiver_model.set_lna(v_db); -} - -void ReceiverView::on_vga_changed(int32_t v_db) { - receiver_model.set_vga(v_db); -} - -void ReceiverView::on_modulation_changed(ReceiverModel::Mode mode) { - remove_child(widget_content.get()); - widget_content.reset(); - - switch(mode) { - case ReceiverModel::Mode::AMAudio: - case ReceiverModel::Mode::NarrowbandFMAudio: - case ReceiverModel::Mode::WidebandFMAudio: - widget_content = std::make_unique(mode); - break; - - case ReceiverModel::Mode::SpectrumAnalysis: - widget_content = std::make_unique(); - break; - - default: - break; - } - - if( widget_content ) { - add_child(widget_content.get()); - const ui::Rect rect { 0, header_height, parent_rect.width(), static_cast(parent_rect.height() - header_height) }; - widget_content->set_parent_rect(rect); - } -} - -void ReceiverView::on_show_options_frequency() { - view_rf_gain_options.hidden(true); - field_lna.set_style(nullptr); - - view_frequency_options.hidden(false); - field_frequency.set_style(&view_frequency_options.style()); -} - -void ReceiverView::on_show_options_rf_gain() { - view_frequency_options.hidden(true); - field_frequency.set_style(nullptr); - - view_rf_gain_options.hidden(false); - field_lna.set_style(&view_frequency_options.style()); -} - -void ReceiverView::on_frequency_step_changed(rf::Frequency f) { - receiver_model.set_frequency_step(f); - field_frequency.set_step(f); -} - -void ReceiverView::on_reference_ppm_correction_changed(int32_t v) { - receiver_model.set_reference_ppm_correction(v); -} - -void ReceiverView::on_headphone_volume_changed(int32_t v) { - const auto new_volume = volume_t::decibel(v - 99) + wolfson::wm8731::headphone_gain_range.max; - receiver_model.set_headphone_volume(new_volume); -} - } /* namespace ui */ diff --git a/firmware/application/ui_receiver.hpp b/firmware/application/ui_receiver.hpp index 6ab20236..fa74f970 100644 --- a/firmware/application/ui_receiver.hpp +++ b/firmware/application/ui_receiver.hpp @@ -23,19 +23,11 @@ #define __UI_RECEIVER_H__ #include "ui.hpp" -#include "ui_font_fixed_8x16.hpp" #include "ui_navigation.hpp" #include "ui_painter.hpp" #include "ui_widget.hpp" -#include "utility.hpp" - -#include "max2837.hpp" #include "rf_path.hpp" -#include "volume.hpp" -#include "wm8731.hpp" - -#include "receiver_model.hpp" #include #include @@ -323,98 +315,6 @@ public: void on_focus() override; }; -constexpr Style style_options_group { - .font = font::fixed_8x16, - .background = Color::blue(), - .foreground = Color::white(), -}; - -class ReceiverView : public View { -public: - ReceiverView(NavigationView& nav); - ~ReceiverView(); - - void on_show() override; - void on_hide() override; - - void focus() override; - -private: - static constexpr ui::Dim header_height = 2 * 16; - - RSSI rssi { - { 21 * 8, 0, 6 * 8, 4 }, - }; - - Channel channel { - { 21 * 8, 5, 6 * 8, 4 }, - }; - - Audio audio { - { 21 * 8, 10, 6 * 8, 4 }, - }; - - FrequencyField field_frequency { - { 5 * 8, 0 * 16 }, - }; - - LNAGainField field_lna { - { 15 * 8, 0 * 16 } - }; - - NumberField field_vga { - { 18 * 8, 0 * 16}, - 2, - { max2837::vga::gain_db_range.minimum, max2837::vga::gain_db_range.maximum }, - max2837::vga::gain_db_step, - ' ', - }; - - OptionsField options_modulation { - { 0 * 8, 0 * 16 }, - 4, - { - { " AM ", toUType(ReceiverModel::Mode::AMAudio) }, - { "NFM ", toUType(ReceiverModel::Mode::NarrowbandFMAudio) }, - { "WFM ", toUType(ReceiverModel::Mode::WidebandFMAudio) }, - { "SPEC", toUType(ReceiverModel::Mode::SpectrumAnalysis) }, - } - }; - - NumberField field_volume { - { 28 * 8, 0 * 16 }, - 2, - { 0, 99 }, - 1, - ' ', - }; - - FrequencyOptionsView view_frequency_options { - { 0 * 8, 1 * 16, 30 * 8, 1 * 16 }, - &style_options_group - }; - - RadioGainOptionsView view_rf_gain_options { - { 0 * 8, 1 * 16, 30 * 8, 1 * 16 }, - &style_options_group - }; - - std::unique_ptr widget_content; - - void on_tuning_frequency_changed(rf::Frequency f); - void on_baseband_bandwidth_changed(uint32_t bandwidth_hz); - void on_rf_amp_changed(bool v); - void on_lna_changed(int32_t v_db); - void on_vga_changed(int32_t v_db); - void on_modulation_changed(ReceiverModel::Mode mode); - void on_show_options_frequency(); - void on_show_options_rf_gain(); - void on_frequency_step_changed(rf::Frequency f); - void on_reference_ppm_correction_changed(int32_t v); - void on_headphone_volume_changed(int32_t v); - void on_edit_frequency(); -}; - } /* namespace ui */ #endif/*__UI_RECEIVER_H__*/