95 const fs::path m_svg_dir;
99 double GetSize(
const wxWindow* parent) {
100 double size = parent->GetCharHeight() * (IsWindows() ? 1.3 : 1.0);
101#if wxCHECK_VERSION(3, 1, 2)
104 size *=
static_cast<double>(parent->ToDIP(100)) / 100.;
108 double pixel_per_mm =
110 size = std::max(size, 7.0 * pixel_per_mm);
115 wxBitmap LoadIcon(
const std::string& filename)
const {
116 fs::path path = m_svg_dir / filename;
117 return LoadSVG(path.string(), m_size, m_size);
120 wxBitmap IconApplyColorScheme(
const wxBitmap proto)
const {
121 if (!proto.IsOk())
return wxNullBitmap;
122 if ((m_cs != GLOBAL_COLOR_SCHEME_DAY) &&
123 (m_cs != GLOBAL_COLOR_SCHEME_RGB)) {
125 wxImage image = proto.ConvertToImage();
126 unsigned char* data = image.GetData();
127 unsigned char* p_idata = data;
128 for (
int i = 0; i < image.GetSize().y; i++) {
129 for (
int j = 0; j < image.GetSize().x; j++) {
130 unsigned char v = *p_idata;
141 return wxBitmap(image);
148 : m_size(GetSize(parent)),
149 m_svg_dir(fs::path(g_Platform->GetSharedDataDir().ToStdString()) /
150 "uidata" /
"MUI_flat"),
151 m_cs(GLOBAL_COLOR_SCHEME_RGB),
152 trashbin_proto(LoadIcon(
"trash_bin.svg")),
153 settings_proto(LoadIcon(
"setting_gear.svg")),
154 filled_circle_proto(LoadIcon(
"circle-on.svg")),
155 open_circle_proto(LoadIcon(
"circle-off.svg")),
156 exclaim_mark_proto(LoadIcon(
"exclaim_mark.svg")),
157 x_mult_proto(LoadIcon(
"X_mult.svg")),
158 check_mark_proto(LoadIcon(
"check_mark.svg")) {
159 trashbin = trashbin_proto;
160 settings = settings_proto;
161 filled_circle = filled_circle_proto;
162 open_circle = open_circle_proto;
163 exclaim_mark = exclaim_mark_proto;
164 x_mult = x_mult_proto;
165 check_mark = check_mark_proto;
168 void SetColorScheme(ColorScheme cs) {
171 trashbin = IconApplyColorScheme(trashbin_proto);
172 settings = IconApplyColorScheme(settings_proto);
173 filled_circle = IconApplyColorScheme(filled_circle_proto);
174 open_circle = IconApplyColorScheme(open_circle_proto);
175 exclaim_mark = IconApplyColorScheme(exclaim_mark_proto);
176 x_mult = IconApplyColorScheme(x_mult_proto);
177 check_mark = IconApplyColorScheme(check_mark_proto);
181 const wxBitmap trashbin_proto;
182 const wxBitmap settings_proto;
183 const wxBitmap filled_circle_proto;
184 const wxBitmap open_circle_proto;
185 const wxBitmap exclaim_mark_proto;
186 const wxBitmap x_mult_proto;
187 const wxBitmap check_mark_proto;
191 wxBitmap filled_circle;
192 wxBitmap open_circle;
193 wxBitmap exclaim_mark;
323 wxWindow* parent,
const std::vector<ConnectionParams*>& connections,
326 : wxGrid(parent, wxID_ANY),
327 m_connections(connections),
328 m_on_conn_delete(on_conn_update),
329 m_last_tooltip_cell(100),
331 m_on_edit_conn(on_edit_conn) {
332 ShowScrollbars(wxSHOW_SB_NEVER, wxSHOW_SB_NEVER);
333 SetTable(
new wxGridStringTable(),
false);
334 GetTable()->AppendCols(8);
337 SetDefaultRowSize(wxWindow::GetCharHeight() * 2);
338 SetColLabelSize(wxWindow::GetCharHeight() * 2);
340 static const std::array<wxString, 7> headers = {
341 "", _(
"Protocol") +
" ", _(
"In/Out"), _(
"Data port"), _(
"Status"),
"",
344 for (
auto hdr = headers.begin(); hdr != headers.end(); hdr++, ic++) {
345 SetColLabelValue(
static_cast<int>(hdr - headers.begin()), *hdr);
346 int col_width = (*hdr).Length() * GetCharWidth();
347 col_width = wxMax(col_width, 6 * GetCharWidth());
348 header_column_widths[ic] = col_width;
349 SetColSize(ic, col_width);
353 SetLabelBackgroundColour(GetGlobalColor(
"DILG1"));
354 SetLabelTextColour(GetGlobalColor(
"DILG3"));
357 SetColAttributes(parent);
360 DisableDragColSize();
361 DisableDragRowSize();
362 wxWindow::Show(GetNumberRows() > 0);
364 GetGridWindow()->Bind(wxEVT_MOTION, [&](wxMouseEvent& ev) {
368 GetGridWindow()->Bind(wxEVT_MOUSEWHEEL,
369 [&](
const wxMouseEvent& ev) {
OnWheel(ev); });
371 Bind(wxEVT_GRID_LABEL_LEFT_CLICK,
372 [&](wxGridEvent& ev) { HandleSort(ev.GetCol()); });
373 Bind(wxEVT_GRID_CELL_LEFT_CLICK,
374 [&](wxGridEvent& ev) { OnClickCell(ev.GetRow(), ev.GetCol()); });
375 Bind(wxEVT_PAINT, [&](wxPaintEvent& ev) {
376 SetColAttributes(
static_cast<wxWindow*
>(ev.GetEventObject()));
379 conn_change_lstnr.
Init(
381 [&](
ObservedEvt&) { OnConnectionChange(m_connections); });
383 void SetColorScheme(ColorScheme cs) {
385 m_icons.SetColorScheme(cs);
389 wxSize GetEstimatedSize() {
391 for (
auto s : header_column_widths) rs += s;
392 return wxSize(rs, -1);
397 auto w =
static_cast<wxScrolledWindow*
>(
398 wxWindow::FindWindowByName(TopScrollWindowName));
399 assert(w &&
"No TopScroll window found");
402 w->GetViewStart(&xpos, &ypos);
405 w->GetScrollPixelsPerUnit(&x, &y);
407 int dir = ev.GetWheelRotation();
408 w->Scroll(-1, ypos - dir / y / 4);
412 void ReloadGrid(
const std::vector<ConnectionParams*>& connections) {
414 m_renderer_status_vector.clear();
416 for (
auto it = connections.begin(); it != connections.end(); it++) {
417 auto row =
static_cast<int>(it - connections.begin());
419 SetCellValue(row, 0, (*it)->bEnabled ?
"1" :
"");
421 m_tooltips[row][0] = _(
"Enabled, click to disable");
423 m_tooltips[row][0] = _(
"Disabled, click to enable");
424 std::string protocol = NavAddr::BusToString((*it)->GetCommProtocol());
425 SetCellValue(row, 1, protocol);
426 SetCellValue(row, 2, (*it)->GetIOTypeValueStr());
427 SetCellValue(row, 3, (*it)->GetStrippedDSPort());
428 m_tooltips[row][3] = (*it)->UserComment;
430 m_tooltips[row][5] = _(
"Edit connection");
432 m_tooltips[row][6] = _(
"Delete connection");
433 SetCellValue(row, 7, (*it)->GetKey());
436 stat_renderer->status = ConnState::Disabled;
437 m_renderer_status_vector.push_back(stat_renderer);
438 SetCellRenderer(row, 4, stat_renderer);
440 wxString sp(protocol);
441 int ssize = sp.Length() * wxWindow::GetCharWidth();
442 header_column_widths[1] = wxMax(header_column_widths[1], ssize);
443 ssize = (*it)->GetIOTypeValueStr().Length() * wxWindow::GetCharWidth();
444 header_column_widths[2] = wxMax(header_column_widths[2], ssize);
445 sp = wxString((*it)->GetStrippedDSPort());
446 ssize = sp.Length() * wxWindow::GetCharWidth();
447 header_column_widths[3] = wxMax(header_column_widths[3], ssize);
450 OnConnectionChange(m_connections);
454 for (
auto val : header_column_widths) {
469 if (row1 == -1 && row2 == -1)
return false;
470 if (row1 == -1)
return false;
471 if (row2 == -1)
return true;
472 int v1 =
static_cast<int>(m_conns->GetCellValue(row1, 4)[0]);
473 int v2 =
static_cast<int>(m_conns->GetCellValue(row2, 4)[0]);
486 auto found = find_if(
487 m_connections.begin(), m_connections.end(),
489 if (found == m_connections.end())
return -1;
490 return static_cast<int>(found - m_connections.begin());
499 auto found = find_if(m_connections.begin(), m_connections.end(),
501 return GetCellValue(row, 7) == p->GetKey();
503 return found != m_connections.end() ? *found :
nullptr;
510 void EnsureRows(
size_t rows) {
511 while (m_tooltips.size() <= rows)
512 m_tooltips.push_back(std::vector<std::string>(7));
513 while (GetNumberRows() <=
static_cast<int>(rows)) AppendRows(1,
false);
517 void SetColAttributes(
const wxWindow* parent) {
520 SetDefaultCellBackgroundColour(GetGlobalColor(
"DILG1"));
522 auto enable_attr =
new wxGridCellAttr();
523 enable_attr->SetAlignment(wxALIGN_CENTRE, wxALIGN_CENTRE);
526 enable_attr->SetRenderer(
529 enable_attr->SetRenderer(
new wxGridCellBoolRenderer());
531 enable_attr->SetEditor(
new wxGridCellBoolEditor());
532 if (IsWindows()) enable_attr->SetBackgroundColour(GetGlobalColor(
"DILG1"));
533 SetColAttr(0, enable_attr);
535 auto protocol_attr =
new wxGridCellAttr();
536 protocol_attr->SetAlignment(wxALIGN_LEFT, wxALIGN_CENTRE);
537 protocol_attr->SetReadOnly(
true);
539 protocol_attr->SetBackgroundColour(GetGlobalColor(
"DILG1"));
540 SetColAttr(1, protocol_attr);
542 auto in_out_attr =
new wxGridCellAttr();
543 in_out_attr->SetAlignment(wxALIGN_CENTRE, wxALIGN_CENTRE);
544 in_out_attr->SetReadOnly(
true);
545 if (IsWindows()) in_out_attr->SetBackgroundColour(GetGlobalColor(
"DILG1"));
546 SetColAttr(2, in_out_attr);
548 auto port_attr =
new wxGridCellAttr();
549 port_attr->SetAlignment(wxALIGN_LEFT, wxALIGN_CENTRE);
550 port_attr->SetReadOnly(
true);
551 if (IsWindows()) port_attr->SetBackgroundColour(GetGlobalColor(
"DILG1"));
552 SetColAttr(3, port_attr);
554 auto status_attr =
new wxGridCellAttr();
555 status_attr->SetAlignment(wxALIGN_CENTRE, wxALIGN_CENTRE);
556 status_attr->SetReadOnly(
true);
557 status_attr->SetFont(parent->GetFont().Scale(1.3));
558 if (IsWindows()) status_attr->SetBackgroundColour(GetGlobalColor(
"DILG1"));
559 SetColAttr(4, status_attr);
561 auto edit_attr =
new wxGridCellAttr();
562 edit_attr->SetAlignment(wxALIGN_CENTRE, wxALIGN_CENTRE);
563 edit_attr->SetFont(parent->GetFont().Scale(1.3));
564 edit_attr->SetReadOnly(
true);
565 if (IsWindows()) edit_attr->SetBackgroundColour(GetGlobalColor(
"DILG1"));
566 SetColAttr(5, edit_attr);
568 auto delete_attr =
new wxGridCellAttr();
569 delete_attr->SetAlignment(wxALIGN_LEFT, wxALIGN_CENTRE);
570 delete_attr->SetFont(parent->GetFont().Scale(1.3));
571 delete_attr->SetTextColour(*wxRED);
572 delete_attr->SetReadOnly(
true);
573 if (IsWindows()) delete_attr->SetBackgroundColour(GetGlobalColor(
"DILG1"));
574 SetColAttr(6, delete_attr);
578 void OnClickCell(
int row,
int col) {
583 }
else if (col == 6) {
589 void OnMouseMove(
const wxMouseEvent& ev) {
590 wxPoint pt = ev.GetPosition();
591 int row = YToRow(pt.y);
592 int col = XToCol(pt.x);
593 if (col < 0 || col >= 7 || row < 0 || row >= GetNumberRows())
return;
594 if (row * 7 + col == m_last_tooltip_cell)
return;
595 m_last_tooltip_cell = row * 7 + col;
596 GetGridWindow()->SetToolTip(m_tooltips[row][col]);
600 void OnConnectionChange(
const std::vector<ConnectionParams*>& connections) {
601 bool refresh_needed =
false;
602 for (
auto it = connections.begin(); it != connections.end(); it++) {
603 ConnState state = m_conn_states.GetDriverState(
604 (*it)->GetCommProtocol(), (*it)->GetStrippedDSPort());
605 if (!(*it)->bEnabled) state = ConnState::Disabled;
606 auto row =
static_cast<int>(it - connections.begin());
608 if (m_renderer_status_vector.size() <
static_cast<size_t>(row + 1))
611 case ConnState::Disabled:
612 if (m_renderer_status_vector[row]->status != ConnState::Disabled) {
613 m_renderer_status_vector[row]->SetBitmap(m_icons.filled_circle);
614 m_renderer_status_vector[row]->status = ConnState::Disabled;
615 refresh_needed =
true;
617 m_tooltips[row][4] = _(
"Disabled");
619 case ConnState::NoStats:
620 if (m_renderer_status_vector[row]->status != ConnState::NoStats) {
621 m_renderer_status_vector[row]->SetBitmap(m_icons.open_circle);
622 m_renderer_status_vector[row]->status = ConnState::NoStats;
623 refresh_needed =
true;
625 m_tooltips[row][4] = _(
"No driver statistics available");
627 case ConnState::NoData:
628 if (m_renderer_status_vector[row]->status != ConnState::NoData) {
629 m_renderer_status_vector[row]->SetBitmap(m_icons.exclaim_mark);
630 m_renderer_status_vector[row]->status = ConnState::NoData;
631 refresh_needed =
true;
633 m_tooltips[row][4] = _(
"No data flowing through connection");
635 case ConnState::Unavailable:
636 if (m_renderer_status_vector[row]->status != ConnState::Unavailable) {
637 m_renderer_status_vector[row]->SetBitmap(m_icons.x_mult);
638 m_renderer_status_vector[row]->status = ConnState::Unavailable;
639 refresh_needed =
true;
641 m_tooltips[row][4] = _(
"The device is unavailable");
644 if (m_renderer_status_vector[row]->status != ConnState::Ok) {
645 m_renderer_status_vector[row]->SetBitmap(m_icons.check_mark);
646 m_renderer_status_vector[row]->status = ConnState::Ok;
647 refresh_needed =
true;
649 m_tooltips[row][4] = _(
"Data is flowing");
653 if (refresh_needed) ForceRefresh();
657 void SetSortingColumn(
int col) {
658 if (GetSortingColumn() != wxNOT_FOUND) {
659 int old_col = GetSortingColumn();
660 auto label = GetColLabelValue(old_col);
661 if (label[0] == kUtfArrowDown[0])
662 SetColLabelValue(old_col, label.substr(2));
664 auto label = GetColLabelValue(col);
665 if (label[0] != kUtfArrowDown[0])
666 SetColLabelValue(col, kUtfArrowDown +
" " + label);
667 wxGrid::SetSortingColumn(col);
672 void HandleSort(
int col) {
674 auto& params = TheConnectionParams();
676 std::sort(params.begin(), params.end(),
ConnCompare(col));
678 std::sort(params.begin(), params.end(), ConnStateCompare(
this));
680 SetSortingColumn(col);
684 void HandleEnable(
int row) {
687 cp->bEnabled = !cp->bEnabled;
688 cp->b_IsSetup = FALSE;
689 SetCellValue(row, 0, cp->bEnabled ?
"1" :
"");
691 m_tooltips[row][0] = _(
"Enabled, click to disable");
693 m_tooltips[row][0] = _(
"Disabled, click to enable");
695 stats.driver_iface = cp->GetStrippedDSPort();
696 stats.driver_bus = cp->GetCommProtocol();
697 m_conn_states.HandleDriverStats(stats);
698 StopAndRemoveCommDriver(cp->GetStrippedDSPort(), cp->GetCommProtocol());
699 if (cp->bEnabled) MakeCommDriver(cp);
700 cp->b_IsSetup =
true;
702 SetCellValue(row, 4, kUtfFilledCircle);
709 void HandleEdit(
int row) {
711 Show(GetNumberRows() > 0);
712 m_on_edit_conn(cp,
true);
717 void HandleDelete(
int row) {
719 auto found = std::find(m_connections.begin(), m_connections.end(), cp);
720 if (found != m_connections.end()) {
721 std::stringstream ss;
722 ss << _(
"Ok to delete connection on ") << (*found)->GetStrippedDSPort();
723 int rcode = OCPNMessageBox(
this, ss.str(), _(
"Delete connection?"),
725 if (rcode != wxID_OK && rcode != wxID_YES)
return;
726 delete (*found)->m_optionsPanel;
727 StopAndRemoveCommDriver((*found)->GetStrippedDSPort(),
728 (*found)->GetCommProtocol());
729 TheConnectionParams().erase(found);
730 if (GetNumberRows() >
static_cast<int>(m_connections.size()))
731 DeleteRows(GetNumberRows() - 1);
732 m_on_conn_delete.
Notify();
737 std::vector<std::vector<std::string>> m_tooltips;
739 const std::vector<ConnectionParams*>& m_connections;
741 int m_last_tooltip_cell;
743 std::vector<BitmapCellRenderer*> m_renderer_status_vector;
744 std::array<int, 7> header_column_widths;
856 : wxPanel(parent, wxID_ANY) {
857 auto sizer =
new wxStaticBoxSizer(wxVERTICAL,
this,
"");
858 sizer->Add(
new BearingsCheckbox(
this), wxSizerFlags().Expand());
859 sizer->Add(
new NmeaFilterRow(
this), wxSizerFlags().Expand());
860 sizer->Add(
new TalkerIdRow(
this), wxSizerFlags().Expand());
861 sizer->Add(
new NetmaskRow(
this), wxSizerFlags().Expand());
863 wxWindow::SetMaxSize(max_size);
868 class BearingsCheckbox :
public wxCheckBox,
public ApplyCancel {
870 BearingsCheckbox(wxWindow* parent)
871 : wxCheckBox(parent, wxID_ANY,
872 _(
"Use magnetic bearing in output sentence APB")) {
873 wxCheckBox::SetValue(g_bMagneticAPB);
876 void Apply()
override { g_bMagneticAPB = GetValue(); }
877 void Cancel()
override { SetValue(g_bMagneticAPB); }
881 class NmeaFilterRow :
public wxPanel,
public ApplyCancel {
882 wxCheckBox* checkbox;
883 wxTextCtrl* filter_period;
886 NmeaFilterRow(wxWindow* parent) : wxPanel(parent) {
887 auto hbox =
new wxBoxSizer(wxHORIZONTAL);
888 checkbox =
new wxCheckBox(
890 _(
"Filter NMEA course and speed data. Filter period: "));
891 checkbox->SetValue(g_bfilter_cogsog);
892 hbox->Add(checkbox, wxSizerFlags().Align(wxALIGN_CENTRE));
894 new wxTextCtrl(
this, wxID_ANY,
"", wxDefaultPosition,
895 wxSize(50, 3 * wxWindow::GetCharWidth()), 0);
896 filter_period->SetValue(std::to_string(g_COGFilterSec));
897 hbox->Add(filter_period, wxSizerFlags().Border());
899 NmeaFilterRow::Cancel();
902 void Apply()
override {
903 std::stringstream ss;
904 ss << filter_period->GetValue();
905 ss >> g_COGFilterSec;
906 g_bfilter_cogsog = checkbox->GetValue();
909 void Cancel()
override {
910 std::stringstream ss;
911 ss << g_COGFilterSec;
912 filter_period->SetValue(ss.str());
913 checkbox->SetValue(g_bfilter_cogsog);
918 class TalkerIdRow :
public wxPanel,
public ApplyCancel {
919 wxTextCtrl* text_ctrl;
922 TalkerIdRow(wxWindow* parent) : wxPanel(parent) {
923 auto hbox =
new wxBoxSizer(wxHORIZONTAL);
924 hbox->Add(
new wxStaticText(
this, wxID_ANY, _(
"NMEA 0183 Talker Id: ")),
925 wxSizerFlags().Align(wxALIGN_CENTRE_VERTICAL).Border());
926 text_ctrl =
new wxTextCtrl(
927 this, wxID_ANY,
"", wxDefaultPosition,
928 wxSize(4 * wxWindow::GetCharWidth(), 3 * wxWindow::GetCharWidth()));
929 text_ctrl->SetToolTip(
930 _(
"Enter a two-letter talker ID to override the default ID in NMEA "
931 "sentences generated by OpenCPN (e.g., GP, HC, EC). This affects "
932 "only sentences created by OpenCPN, not those forwarded from other "
934 text_ctrl->SetValue(g_TalkerIdText);
935 hbox->Add(text_ctrl, wxSizerFlags().Border());
937 TalkerIdRow::Cancel();
940 void Apply()
override { g_TalkerIdText = text_ctrl->GetValue(); }
941 void Cancel()
override { text_ctrl->SetValue(g_TalkerIdText); }
945 class NetmaskRow :
public wxPanel,
public ApplyCancel {
947 NetmaskRow(wxWindow* parent)
949 m_spin_ctrl(
new wxSpinCtrl(
this, wxID_ANY)),
950 m_text(
new wxStaticText(
this, wxID_ANY,
"")) {
951 m_spin_ctrl->SetRange(8, 32);
952 auto hbox =
new wxBoxSizer(wxHORIZONTAL);
953 auto flags = wxSizerFlags().Align(wxALIGN_CENTRE_VERTICAL).Border();
954 hbox->Add(
new wxStaticText(
this, wxID_ANY, _(
"Netmask: ")), flags);
955 hbox->Add(m_text, flags);
956 hbox->Add(
new wxStaticText(
this, wxID_ANY, _(
"length (bits): ")), flags);
957 hbox->Add(m_spin_ctrl, flags);
959 NetmaskRow::Cancel();
961 Bind(wxEVT_SPINCTRL, [&](wxSpinEvent& ev) {
962 m_text->SetLabel(BitsToDottedMask(m_spin_ctrl->GetValue()));
967 void Apply()
override { g_netmask_bits = m_spin_ctrl->GetValue(); }
969 void Cancel()
override {
970 m_spin_ctrl->SetValue(g_netmask_bits);
971 m_text->SetLabel(BitsToDottedMask(m_spin_ctrl->GetValue()));
976 wxSpinCtrl* m_spin_ctrl;
977 wxStaticText* m_text;
984 TopPanel(wxWindow* parent,
const std::vector<ConnectionParams*>& connections,
987 : wxPanel(parent, wxID_ANY),
988 m_evt_add_connection(evt_add_connection),
989 m_connections(connections) {
990 auto vbox =
new wxBoxSizer(wxVERTICAL);
991 auto conn_grid =
new Connections(
this, m_connections, m_evt_add_connection,
993 wxSize panel_max_size(conn_grid->GetEstimatedSize());
994 vbox->AddSpacer(wxWindow::GetCharHeight());
995 auto conn_flags = wxSizerFlags().Border();
996 if (IsAndroid()) conn_flags = wxSizerFlags().Border().Expand();
997 vbox->Add(conn_grid, conn_flags);
999 wxSizerFlags().Border());
1000 vbox->Add(0, wxWindow::GetCharHeight());
1002 wxSizerFlags().Border(wxLEFT | wxDOWN | wxRIGHT).Expand();
1003 m_general_panel =
new GeneralPanel(
this, panel_max_size);
1004 vbox->Add(m_general_panel, panel_flags);
1006 auto advanced_panel =
new AdvancedPanel(
this, panel_max_size);
1007 m_advanced_panel = advanced_panel;
1008 auto on_toggle = [&, advanced_panel, vbox](
bool show) {
1009 advanced_panel->Show(show);
1010 vbox->SetSizeHints(
this);
1013 vbox->Add(
new ShowAdvanced(
this, on_toggle), panel_flags);
1014 vbox->Add(advanced_panel, panel_flags.ReserveSpaceEvenIfHidden());
1017 vbox->SetSizeHints(
this);
1022 auto on_evt_update_connections = [&, conn_grid](
ObservedEvt&) {
1023 conn_grid->ReloadGrid(TheConnectionParams());
1024 conn_grid->Show(conn_grid->GetNumberRows() > 0);
1027 m_add_connection_lstnr.
Init(m_evt_add_connection,
1028 on_evt_update_connections);
1029 m_conn_grid = conn_grid;
1032 void SetColorScheme(ColorScheme cs) {
1033 m_conn_grid->SetColorScheme(cs);
1034 m_general_panel->SetColorScheme(cs);
1036 Connections* GetConnectionsGrid() {
return m_conn_grid; }
1041 const std::vector<ConnectionParams*>& m_connections;
1051 TopScroll(wxWindow* parent,
const std::vector<ConnectionParams*>& connections,
1053 : wxScrolledWindow(parent, wxID_ANY, wxDefaultPosition, wxDefaultSize,
1054 wxVSCROLL | wxHSCROLL, TopScrollWindowName) {
1055 ShowScrollbars(wxSHOW_SB_NEVER, wxSHOW_SB_ALWAYS);
1056 auto vbox =
new wxBoxSizer(wxVERTICAL);
1067 new TopPanel(
this, connections, evt_add_connection, on_edit_connection);
1068 vbox->Add(top_panel, wxSizerFlags(1).Expand());
1072 HandleEditFinish(p, new_mode, ok_cancel);
1076 m_edit_panel->SetPropsLabel(_(
"Edit Selected Connection"));
1077 wxWindow*
options = wxWindow::FindWindowByName(
"Options");
1078 assert(
options &&
"Null Options window!");
1083 m_edit_panel->SetSize(
1084 wxSize(
options->GetSize().x,
options->GetSize().y * fraction / 10));
1085 vbox->Add(m_edit_panel, wxSizerFlags(0).Expand());
1086 m_edit_panel->Hide();
1088 SetScrollRate(0, 10);
1089 if (IsAndroid()) SetScrollRate(1, 1);
1091 SetScrollRate(0, 10);
1092 if (IsAndroid()) SetScrollRate(1, 1);
1095 void SetColorScheme(ColorScheme cs) {
1096 if (top_panel) top_panel->SetColorScheme(cs);
1100 m_edit_panel->SetPropsLabel(_(
"Edit Selected Connection"));
1101 m_edit_panel->SetNewMode(
false);
1102 m_edit_panel->PreloadControls(p);
1103 m_edit_panel->AddOKCancelButtons();
1108 m_edit_panel->SetPropsLabel(_(
"Configure new connection"));
1109 m_edit_panel->SetDefaultConnectionParams();
1110 m_edit_panel->SetNewMode(
true);
1111 m_edit_panel->AddOKCancelButtons();
1115 void SwitchToEditor() {
1118 DimeControl(m_edit_panel);
1119 m_edit_panel->Show();
1120 g_options->ShowOKButtons(
false);
1125 void SwitchToGrid() {
1126 g_options->ShowOKButtons(
true);
1127 m_edit_panel->Hide();
1129 top_panel->GetConnectionsGrid()->
ReloadGrid(TheConnectionParams());
1143 delete cp_orig->m_optionsPanel;
1144 StopAndRemoveCommDriver(cp_orig->GetStrippedDSPort(),
1145 cp_orig->GetCommProtocol());
1147 assert(index != -1 &&
"Cannot look up connection index");
1148 TheConnectionParams()[index] = cp_edited;
1149 cp_edited->b_IsSetup =
false;
1154 if (cp->GetValidPort()) {
1155 cp->b_IsSetup =
false;
1156 TheConnectionParams().push_back(cp);
1159 _(
"Unable to create a connection as configured. "
1160 "Connected port or address was missing.");
1161 auto& noteman = NotificationManager::GetInstance();
1162 noteman.AddNotification(NotificationSeverity::kWarning,
1163 msg.ToStdString(), 60);
1166 UpdateDatastreams();
1167 top_panel->m_evt_add_connection.
Notify();
1171 UpdateDatastreams();