Freqman UI (#1255)

* FreqmanDB direct file
* Clear UI for short lists
* Final touches on freqlist UI.
* Support vertical alignment in NewButton
* New buttons in FreqMan
* Wiring up UI to filewrapper actions
* Work around empty file
This commit is contained in:
Kyle Reed
2023-07-11 13:48:36 -07:00
committed by GitHub
parent 0c599f7d3a
commit 29e495a17f
23 changed files with 979 additions and 660 deletions

View File

@@ -1,6 +1,7 @@
/*
* Copyright (C) 2015 Jared Boone, ShareBrained Technology, Inc.
* Copyright (C) 2016 Furrtek
* Copyright (C) 2023 Kyle Reed
*
* This file is part of PortaPack.
*
@@ -22,278 +23,284 @@
#include "ui_freqman.hpp"
#include "portapack.hpp"
#include "event_m0.hpp"
#include "portapack.hpp"
#include "rtc_time.hpp"
#include "utility.hpp"
#include <memory>
using namespace portapack;
namespace fs = std::filesystem;
namespace ui {
static int32_t current_category_id = 0;
/* FreqManBaseView ***************************************/
size_t FreqManBaseView::current_category_index = 0;
FreqManBaseView::FreqManBaseView(
NavigationView& nav)
: nav_(nav) {
add_children({&options_category,
&label_category,
&button_exit});
add_children(
{&label_category,
&options_category,
&button_exit});
// initialize
refresh_list();
options_category.on_change = [this](size_t category_id, int32_t) {
change_category(category_id);
options_category.on_change = [this](size_t new_index, int32_t) {
change_category(new_index);
};
options_category.set_selected_index(current_category_id);
button_exit.on_select = [this, &nav](Button&) {
nav.pop();
};
refresh_categories();
};
void FreqManBaseView::focus() {
button_exit.focus();
// TODO: Shouldn't be on focus.
if (error_ == ERROR_ACCESS) {
nav_.display_modal("Error", "File acces error", ABORT, nullptr);
nav_.display_modal("Error", "File access error", ABORT, nullptr);
} else if (error_ == ERROR_NOFILES) {
nav_.display_modal("Error", "No database files\nin /freqman", ABORT, nullptr);
nav_.display_modal("Error", "No database files\nin /FREQMAN", ABORT, nullptr);
} else {
options_category.focus();
}
}
void FreqManBaseView::get_freqman_files() {
// Assume this does change much, clear will preserve the existing alloc.
file_list.clear();
void FreqManBaseView::change_category(size_t new_index) {
if (categories().empty())
return;
auto files = scan_root_files(u"FREQMAN", u"*.TXT");
for (auto file : files) {
std::string file_name = file.stem().string();
// don't propose tmp / hidden files in freqman's list
if (file_name.length() && file_name[0] != '.') {
file_list.emplace_back(std::move(file_name));
}
}
};
void FreqManBaseView::change_category(int32_t category_id) {
current_category_id = category_id;
if (file_list.empty()) return;
if (!load_freqman_file(file_list[categories[category_id].second], database, {})) {
current_category_index = new_index;
if (!db_.open(get_freqman_path(current_category()))) {
error_ = ERROR_ACCESS;
}
freqlist_view.set_db(database);
text_empty.hidden(!database.empty());
set_dirty();
freqlist_view.set_db(db_);
}
void FreqManBaseView::refresh_list() {
categories.clear();
get_freqman_files();
void FreqManBaseView::refresh_categories() {
OptionsField::options_t new_categories;
for (size_t n = 0; n < file_list.size(); n++)
categories.emplace_back(std::make_pair(file_list[n].substr(0, 14), n));
scan_root_files(
freqman_dir, u"*.TXT", [&new_categories](const fs::path& path) {
// Skip temp/hidden files.
if (path.empty() || path.native()[0] == u'.')
return;
// Alphabetical sort
std::sort(categories.begin(), categories.end(), [](auto& left, auto& right) {
// The UI layer will truncate long file names when displaying.
new_categories.emplace_back(path.stem().string(), new_categories.size());
});
// Alphabetically sort the categories.
std::sort(new_categories.begin(), new_categories.end(), [](auto& left, auto& right) {
return left.first < right.first;
});
options_category.set_options(categories);
if ((unsigned)current_category_id >= categories.size())
current_category_id = categories.size() - 1;
// Preserve last selection; ensure in range.
current_category_index = clip(current_category_index, 0u, new_categories.size());
auto saved_index = current_category_index;
options_category.set_options(std::move(new_categories));
options_category.set_selected_index(saved_index);
}
void FrequencySaveView::save_current_file() {
save_freqman_file(file_list[categories[current_category_id].second], database);
nav_.pop();
void FreqManBaseView::refresh_list(int delta_selected) {
// Update the index and ensures in bounds.
freqlist_view.set_index(freqlist_view.get_index() + delta_selected);
freqlist_view.set_dirty();
}
void FrequencySaveView::on_save_name() {
text_prompt(nav_, desc_buffer, 28, [this](std::string& buffer) {
database.push_back(std::make_unique<freqman_entry>(freqman_entry{value_, 0, buffer, freqman_type::Single}));
save_current_file();
});
}
void FrequencySaveView::on_save_timestamp() {
database.push_back(std::make_unique<freqman_entry>(freqman_entry{value_, 0, live_timestamp.string(), freqman_type::Single}));
save_current_file();
}
/* FrequencySaveView *************************************/
FrequencySaveView::FrequencySaveView(
NavigationView& nav,
const rf::Frequency value)
: FreqManBaseView(nav),
value_(value) {
desc_buffer.reserve(28);
: FreqManBaseView(nav) {
add_children(
{&labels,
&big_display,
&button_clear,
&button_edit,
&button_save,
&text_description});
// Todo: add back ?
/*for (size_t n = 0; n < database.size(); n++) {
if (database[n].value == value_) {
error_ = ERROR_DUPLICATE;
break;
}
}*/
entry_.type = freqman_type::Single;
entry_.frequency_a = value;
entry_.description = to_string_timestamp(rtc_time::now());
refresh_ui();
add_children({&labels,
&big_display,
&button_save_name,
&button_save_timestamp,
&live_timestamp});
big_display.set(value);
button_save_name.on_select = [this, &nav](Button&) {
on_save_name();
};
button_save_timestamp.on_select = [this, &nav](Button&) {
on_save_timestamp();
button_clear.on_select = [this, &nav](Button&) {
entry_.description = "";
refresh_ui();
};
options_category.on_change = [this, value](size_t category_id, int32_t) {
change_category(category_id);
big_display.set(value);
button_edit.on_select = [this, &nav](Button&) {
temp_buffer_ = entry_.description;
text_prompt(nav_, temp_buffer_, 30, [this](std::string& new_desc) {
entry_.description = new_desc;
refresh_ui();
});
};
button_save.on_select = [this, &nav](Button&) {
db_.insert_entry(entry_, db_.entry_count());
nav_.pop();
};
}
void FrequencyLoadView::refresh_widgets(const bool v) {
freqlist_view.hidden(v);
text_empty.hidden(!v);
// display.fill_rectangle(freqlist_view.screen_rect(), Color::black());
set_dirty();
void FrequencySaveView::refresh_ui() {
big_display.set(entry_.frequency_a);
text_description.set(entry_.description);
}
/* FrequencyLoadView *************************************/
FrequencyLoadView::FrequencyLoadView(
NavigationView& nav)
: FreqManBaseView(nav) {
on_refresh_widgets = [this](bool v) {
refresh_widgets(v);
};
add_children({&freqlist_view});
add_children({&freqlist_view,
&text_empty});
// Resize to fill screen. +2 keeps text out of border.
freqlist_view.set_parent_rect({0, 3 * 8, screen_width, 15 * 16 + 2});
// Resize menu view to fill screen
freqlist_view.set_parent_rect({0, 3 * 8, 240, 30 * 8});
freqlist_view.on_select = [&nav, this](size_t index) {
auto entry = db_[index];
// TODO: Maybe return center of range if user choses a range when the app
// needs a unique frequency, instead of frequency_a?
auto has_range = entry.type == freqman_type::Range ||
entry.type == freqman_type::HamRadio;
freqlist_view.on_select = [&nav, this](FreqManUIList&) {
auto& entry = database[freqlist_view.get_index()];
if (entry->type == freqman_type::Range) {
if (on_range_loaded)
on_range_loaded(entry->frequency_a, entry->frequency_b);
else if (on_frequency_loaded)
on_frequency_loaded(entry->frequency_a);
// TODO: Maybe return center of range if user choses a range when the app
// needs a unique frequency, instead of frequency_a?
// TODO: HamRadio?
} else {
if (on_frequency_loaded)
on_frequency_loaded(entry->frequency_a);
}
if (on_range_loaded && has_range)
on_range_loaded(entry.frequency_a, entry.frequency_b);
else if (on_frequency_loaded)
on_frequency_loaded(entry.frequency_a);
nav_.pop(); // NB: this will call dtor.
};
freqlist_view.on_leave = [this]() {
button_exit.focus();
};
}
void FrequencyManagerView::on_edit_freq(rf::Frequency f) {
database[freqlist_view.get_index()]->frequency_a = f;
save_freqman_file(file_list[categories[current_category_id].second], database);
change_category(current_category_id);
/* FrequencyManagerView **********************************/
void FrequencyManagerView::on_edit_freq() {
// TODO: range edit support?
auto freq_edit_view = nav_.push<FrequencyKeypadView>(current_entry().frequency_a);
freq_edit_view->on_changed = [this](rf::Frequency f) {
auto entry = current_entry();
entry.frequency_a = f;
db_.replace_entry(current_index(), entry);
freqlist_view.set_dirty();
};
}
void FrequencyManagerView::on_edit_desc(NavigationView& nav) {
text_prompt(nav, desc_buffer, 28, [this](std::string& buffer) {
database[freqlist_view.get_index()]->description = std::move(buffer);
save_freqman_file(file_list[categories[current_category_id].second], database);
change_category(current_category_id);
void FrequencyManagerView::on_edit_desc() {
temp_buffer_ = current_entry().description;
text_prompt(nav_, temp_buffer_, 28, [this](std::string& new_desc) {
auto entry = current_entry();
entry.description = std::move(new_desc);
db_.replace_entry(current_index(), entry);
freqlist_view.set_dirty();
});
}
void FrequencyManagerView::on_new_category(NavigationView& nav) {
text_prompt(nav, desc_buffer, 12, [this](std::string& buffer) {
File freqman_file;
create_freqman_file(buffer, freqman_file);
refresh_list();
change_category(current_category_id);
void FrequencyManagerView::on_add_category() {
temp_buffer_.clear();
text_prompt(nav_, temp_buffer_, 12, [this](std::string& new_name) {
if (!new_name.empty()) {
create_freqman_file(new_name);
refresh_categories();
}
});
}
void FrequencyManagerView::on_delete() {
if (database.empty()) {
delete_freqman_file(file_list[categories[current_category_id].second]);
refresh_list();
} else {
database.erase(database.begin() + freqlist_view.get_index());
save_freqman_file(file_list[categories[current_category_id].second], database);
}
change_category(current_category_id);
void FrequencyManagerView::on_del_category() {
nav_.push<ModalMessageView>(
"Delete", "Delete " + current_category() + "\nAre you sure?", YESNO,
[this](bool choice) {
if (choice) {
db_.close(); // Ensure file is closed.
auto path = get_freqman_path(current_category());
delete_file(path);
refresh_categories();
}
});
}
void FrequencyManagerView::refresh_widgets(const bool v) {
button_edit_freq.hidden(v);
button_edit_desc.hidden(v);
button_delete.hidden(v);
text_empty.hidden(!v);
freqlist_view.hidden(v);
labels.hidden(v);
// display.fill_rectangle(freqlist_view.screen_rect(), Color::black());
set_dirty();
void FrequencyManagerView::on_add_entry() {
freqman_entry entry{
.frequency_a = 100'000'000,
.description = std::string{"Entry "} + to_string_dec_uint(db_.entry_count()),
.type = freqman_type::Single,
};
// Add will insert below the currently selected item.
db_.insert_entry(entry, current_index() + 1);
refresh_list(1);
}
FrequencyManagerView::~FrequencyManagerView() {
// save_freqman_file(file_list[categories[current_category_id].second], database);
void FrequencyManagerView::on_del_entry() {
if (db_.empty())
return;
nav_.push<ModalMessageView>(
"Delete", "Delete" + pretty_string(current_entry(), 23) + "\nAre you sure?", YESNO,
[this](bool choice) {
if (choice) {
db_.delete_entry(current_index());
refresh_list();
}
});
}
FrequencyManagerView::FrequencyManagerView(
NavigationView& nav)
: FreqManBaseView(nav) {
on_refresh_widgets = [this](bool v) {
refresh_widgets(v);
add_children(
{&freqlist_view,
&labels,
&button_add_category,
&button_del_category,
&button_edit_freq,
&button_edit_desc,
&button_add_entry,
&button_del_entry});
freqlist_view.on_select = [this](size_t) {
button_edit_freq.focus();
};
add_children({&labels,
&button_new_category,
&freqlist_view,
&text_empty,
&button_edit_freq,
&button_edit_desc,
&button_delete});
freqlist_view.on_select = [this](FreqManUIList&) {
// Allows for quickly exiting control.
freqlist_view.on_leave = [this]() {
button_edit_freq.focus();
};
button_new_category.on_select = [this, &nav](Button&) {
desc_buffer = "";
on_new_category(nav);
button_add_category.on_select = [this]() {
on_add_category();
};
button_edit_freq.on_select = [this, &nav](Button&) {
if (database.empty())
database.push_back(std::make_unique<freqman_entry>(freqman_entry{0, 0, "", freqman_type::Single}));
auto new_view = nav.push<FrequencyKeypadView>(database[freqlist_view.get_index()]->frequency_a);
new_view->on_changed = [this](rf::Frequency f) {
on_edit_freq(f);
};
button_del_category.on_select = [this]() {
on_del_category();
};
button_edit_desc.on_select = [this, &nav](Button&) {
if (database.empty())
database.push_back(std::make_unique<freqman_entry>(freqman_entry{0, 0, "", freqman_type::Single}));
desc_buffer = database[freqlist_view.get_index()]->description;
on_edit_desc(nav);
button_edit_freq.on_select = [this](Button&) {
on_edit_freq();
};
button_delete.on_select = [this, &nav](Button&) {
on_delete();
button_edit_desc.on_select = [this](Button&) {
on_edit_desc();
};
button_add_entry.on_select = [this]() {
on_add_entry();
};
button_del_entry.on_select = [this]() {
on_del_entry();
};
}

View File

@@ -1,6 +1,7 @@
/*
* Copyright (C) 2015 Jared Boone, ShareBrained Technology, Inc.
* Copyright (C) 2016 Furrtek
* Copyright (C) 2023 Kyle Reed
*
* This file is part of PortaPack.
*
@@ -20,15 +21,16 @@
* Boston, MA 02110-1301, USA.
*/
#include "freqman.hpp"
#include "freqman_db.hpp"
#include "ui.hpp"
#include "ui_widget.hpp"
#include "ui_painter.hpp"
#include "ui_freqlist.hpp"
#include "ui_menu.hpp"
#include "ui_navigation.hpp"
#include "ui_painter.hpp"
#include "ui_receiver.hpp"
#include "ui_textentry.hpp"
#include "freqman.hpp"
#include "ui_freqlist.hpp"
#include "ui_widget.hpp"
namespace ui {
@@ -40,74 +42,77 @@ class FreqManBaseView : public View {
void focus() override;
protected:
using option_t = std::pair<std::string, int32_t>;
using options_t = std::vector<option_t>;
using options_t = OptionsField::options_t;
NavigationView& nav_;
freqman_error error_{NO_ERROR};
options_t categories{};
std::function<void(void)> on_select_frequency{nullptr};
std::function<void(bool)> on_refresh_widgets{nullptr};
void get_freqman_files();
void change_category(int32_t category_id);
void refresh_list();
void change_category(size_t new_index);
/* Access the categories directly from the OptionsField.
* This avoids holding multiple copies of the file list. */
const options_t& categories() const { return options_category.options(); }
const auto& current_category() const { return options_category.selected_index_name(); }
auto current_index() const { return freqlist_view.get_index(); }
freqman_entry current_entry() const { return db_[current_index()]; }
void refresh_categories();
void refresh_list(int delta_selected = 0);
freqman_db database{};
std::vector<std::string> file_list{};
FreqmanDB db_{};
/* The top section (category) is 20px tall. */
Labels label_category{
{{0, 4}, "Category:", Color::light_grey()}};
{{0, 2}, "Category:", Color::light_grey()}};
OptionsField options_category{
{9 * 8, 4},
14,
{9 * 8, 2},
14 /* length */,
{}};
FreqManUIList freqlist_view{
{0, 3 * 8, 240, 23 * 8}};
Text text_empty{
{7 * 8, 12 * 8, 16 * 8, 16},
"Empty category !",
};
{0, 3 * 8, screen_width, 12 * 16 + 2 /* 2 Keeps text out of border. */}};
Button button_exit{
{16 * 8, 34 * 8, 14 * 8, 4 * 8},
{15 * 8, 17 * 16, 15 * 8, 2 * 16},
"Exit"};
private:
protected:
/* Static so selected category is persisted across UI instances. */
static size_t current_category_index;
};
// TODO: support for new category.
class FrequencySaveView : public FreqManBaseView {
public:
FrequencySaveView(NavigationView& nav, const rf::Frequency value);
std::string title() const override { return "Save freq."; };
std::string title() const override { return "Save freq"; };
private:
std::string desc_buffer{};
rf::Frequency value_{};
std::string temp_buffer_{};
freqman_entry entry_{};
void on_save_name();
void on_save_timestamp();
void save_current_file();
void refresh_ui();
BigFrequency big_display{
{4, 2 * 16, 28 * 8, 32},
{0, 2 * 16, 28 * 8, 4 * 16},
0};
Labels labels{
{{1 * 8, 12 * 8}, "Save as:", Color::white()}};
{{0 * 8, 6 * 16}, "Description:", Color::white()}};
Button button_save_name{
{1 * 8, 17 * 8, 12 * 8, 48},
"Name (set)"};
Button button_save_timestamp{
{1 * 8, 25 * 8, 12 * 8, 48},
"Timestamp:"};
LiveDateTime live_timestamp{
{14 * 8, 27 * 8, 16 * 8, 16}};
Text text_description{{0 * 8, 7 * 16, 30 * 8, 1 * 16}};
Button button_clear{
{4 * 8, 10 * 16, 10 * 8, 2 * 16},
"Clear"};
Button button_edit{
{16 * 8, 10 * 16, 10 * 8, 2 * 16},
"Edit"};
Button button_save{
{0 * 8, 17 * 16, 15 * 8, 2 * 16},
"Save"};
};
class FrequencyLoadView : public FreqManBaseView {
@@ -116,46 +121,62 @@ class FrequencyLoadView : public FreqManBaseView {
std::function<void(rf::Frequency, rf::Frequency)> on_range_loaded{};
FrequencyLoadView(NavigationView& nav);
std::string title() const override { return "Load freq."; };
private:
void refresh_widgets(const bool v);
std::string title() const override { return "Load freq"; };
};
class FrequencyManagerView : public FreqManBaseView {
public:
FrequencyManagerView(NavigationView& nav);
~FrequencyManagerView();
std::string title() const override { return "Freqman"; };
private:
std::string desc_buffer{};
std::string temp_buffer_{};
void refresh_widgets(const bool v);
void on_edit_freq(rf::Frequency f);
void on_edit_desc(NavigationView& nav);
void on_new_category(NavigationView& nav);
void on_delete();
void on_edit_freq();
void on_edit_desc();
void on_add_category();
void on_del_category();
void on_add_entry();
void on_del_entry();
Labels labels{
{{4 * 8 + 4, 26 * 8}, "Edit:", Color::light_grey()}};
{{5 * 8, 14 * 16 - 4}, "Edit:", Color::light_grey()}};
Button button_new_category{
{23 * 8, 2, 7 * 8, 20},
"New"};
NewButton button_add_category{
{23 * 8, 0 * 16, 7 * 4, 20},
{},
&bitmap_icon_new_file,
Color::white(),
true};
NewButton button_del_category{
{26 * 8 + 4, 0 * 16, 7 * 4, 20},
{},
&bitmap_icon_trash,
Color::red(),
true};
Button button_edit_freq{
{0 * 8, 29 * 8, 14 * 8, 32},
{0 * 8, 15 * 16, 15 * 8, 2 * 16},
"Frequency"};
Button button_edit_desc{
{0 * 8, 34 * 8, 14 * 8, 32},
{0 * 8, 17 * 16, 15 * 8, 2 * 16},
"Description"};
Button button_delete{
{16 * 8, 29 * 8, 14 * 8, 32},
"Delete"};
NewButton button_add_entry{
{15 * 8, 15 * 16, 7 * 8 + 4, 2 * 16},
{},
&bitmap_icon_add,
Color::white(),
true};
NewButton button_del_entry{
{22 * 8 + 4, 15 * 16, 7 * 8 + 4, 2 * 16},
{},
&bitmap_icon_delete,
Color::red(),
true};
};
} /* namespace ui */

View File

@@ -137,8 +137,8 @@ bool ReconView::recon_save_freq(const std::string& freq_file_path, size_t freq_i
entry.bandwidth = last_entry.bandwidth;
entry.type = freqman_type::Single;
std::string frequency_to_add;
get_freq_string(entry, frequency_to_add);
// TODO: Use FreqmanDB
auto frequency_to_add = to_freqman_string(entry);
auto result = recon_file.open(freq_file_path); // First recon if freq is already in txt
if (!result.is_valid()) {
@@ -607,6 +607,7 @@ ReconView::ReconView(NavigationView& nav)
};
button_remove.on_select = [this](ButtonWithEncoder&) {
// TODO: Use FreqmanDB
if (frequency_list.size() > 0) {
if (!manual_mode) {
// scanner or recon (!scanner) mode
@@ -629,8 +630,7 @@ ReconView::ReconView(NavigationView& nav)
auto result = freqman_file.create(freq_file_path);
if (!result.is_valid()) {
for (size_t n = 0; n < frequency_list.size(); n++) {
std::string line;
get_freq_string(*frequency_list[n], line);
auto line = to_freqman_string(*frequency_list[n]);
freqman_file.write_line(line);
}
}
@@ -640,7 +640,6 @@ ReconView::ReconView(NavigationView& nav)
File recon_file{};
File tmp_recon_file{};
std::string tmp_freq_file_path{freq_file_path + ".TMP"};
std::string frequency_to_add{};
freqman_entry entry = current_entry();
entry.frequency_a = freq;
@@ -649,7 +648,7 @@ ReconView::ReconView(NavigationView& nav)
entry.bandwidth = last_entry.bandwidth;
entry.type = freqman_type::Single;
get_freq_string(entry, frequency_to_add);
auto frequency_to_add = to_freqman_string(entry);
delete_file(tmp_freq_file_path);
auto result = tmp_recon_file.create(tmp_freq_file_path); // First recon if freq is already in txt
@@ -833,7 +832,7 @@ ReconView::ReconView(NavigationView& nav)
open_view->on_changed = [this](std::vector<std::string> result) {
input_file = result[0];
output_file = result[1];
freq_file_path = "/FREQMAN/" + output_file + ".TXT";
freq_file_path = get_freqman_path(output_file).string();
recon_save_config_to_sd();
autosave = persistent_memory::recon_autosave_freqs();
@@ -892,7 +891,7 @@ ReconView::ReconView(NavigationView& nav)
// Loading input and output file from settings
recon_load_config_from_sd();
freq_file_path = "/FREQMAN/" + output_file + ".TXT";
freq_file_path = get_freqman_path(output_file).string();
field_recon_match_mode.set_selected_index(recon_match_mode);
field_squelch.set_value(squelch);

View File

@@ -21,12 +21,13 @@
* Boston, MA 02110-1301, USA.
*/
#include "ui_recon_settings.hpp"
#include "ui_navigation.hpp"
#include "ui_fileman.hpp"
#include "ui_navigation.hpp"
#include "ui_recon_settings.hpp"
#include "ui_textentry.hpp"
#include "file.hpp"
#include "freqman_db.hpp"
#include "portapack.hpp"
#include "portapack_persistent_memory.hpp"
@@ -55,11 +56,9 @@ ReconSetupViewMain::ReconSetupViewMain(NavigationView& nav, Rect parent_rect, st
button_load_freqs.on_select = [this, &nav](Button&) {
auto open_view = nav.push<FileLoadView>(".TXT");
open_view->push_dir(freqman_dir);
open_view->on_changed = [this, &nav](std::filesystem::path new_file_path) {
std::string dir_filter = "FREQMAN/";
std::string str_file_path = new_file_path.string();
if (str_file_path.find(dir_filter) != string::npos) { // assert file from the FREQMAN folder
// get the filename without txt extension so we can use load_freqman_file fcn
if (new_file_path.native().find(freqman_dir.native()) == 0) {
_input_file = new_file_path.stem().string();
text_input_file.set(_input_file);
} else {

View File

@@ -314,17 +314,13 @@ ScannerView::ScannerView(
// Button to load txt files from the FREQMAN folder
button_load.on_select = [this, &nav](Button&) {
auto open_view = nav.push<FileLoadView>(".TXT");
open_view->on_changed = [this](std::filesystem::path new_file_path) {
std::string dir_filter = "FREQMAN/";
std::string str_file_path = new_file_path.string();
if (str_file_path.find(dir_filter) != std::string::npos) { // assert file from the FREQMAN folder
open_view->push_dir(freqman_dir);
open_view->on_changed = [this, &nav](std::filesystem::path new_file_path) {
if (new_file_path.native().find(freqman_dir.native()) == 0) {
scan_pause();
// get the filename without txt extension so we can use load_freqman_file fcn
std::string str_file_name = new_file_path.stem().string();
frequency_file_load(str_file_name, true);
frequency_file_load(new_file_path.stem().string(), true);
} else {
nav_.display_modal("LOAD ERROR", "A valid file from\nFREQMAN directory is\nrequired.");
nav.display_modal("LOAD ERROR", "A valid file from\nFREQMAN directory is\nrequired.");
}
};
};
@@ -494,6 +490,7 @@ ScannerView::ScannerView(
bigdisplay_update(BDC_GREY); // Back to grey color
};
// TODO: remove this parsing?
// Button to add current frequency (found during Search) to the Scan Frequency List
button_add.on_select = [this](Button&) {
File scanner_file;