mirror of
https://github.com/vicliu624/trail-mate.git
synced 2026-07-21 02:51:03 +00:00
Refine node info UI and peer announcements
This commit is contained in:
File diff suppressed because it is too large
Load Diff
@@ -1,66 +1,10 @@
|
||||
/**
|
||||
* UI Wireframe / Layout Tree (Node Info - matches provided mock)
|
||||
* --------------------------------------------------------------------
|
||||
*
|
||||
* Root (COLUMN)
|
||||
* +------------------------------------------------------------------+
|
||||
* | Header (TopBar) [< Back] NODE INFO [Battery] |
|
||||
* +------------------------------------------------------------------+
|
||||
* | TopRow (ROW, grow) |
|
||||
* | +-------------------------+ +---------------------------------+ |
|
||||
* | | Info Card (left) | | Location Card (right) | |
|
||||
* | | +---------------------+ | | +---------------------------+ | |
|
||||
* | | | Avatar (S) | | | | Title: Location | | |
|
||||
* | | | Name: ALFA-3 | | | +---------------------------+ | |
|
||||
* | | | Desc: Relay Node | | | | Map Placeholder | | |
|
||||
* | | +---------------------+ | | | [Map image] | | |
|
||||
* | | | ID: !a1b2c3 | | | +---------------------------+ | |
|
||||
* | | | Role: Router | | | | Lat,Lon +/-Acc Alt | | |
|
||||
* | | +---------------------+ | | +---------------------------+ | |
|
||||
* | | | | | Updated: 2m ago | | |
|
||||
* | +-------------------------+ | +---------------------------+ | |
|
||||
* | +---------------------------------+ |
|
||||
* | |
|
||||
* | Link Panel (full width) |
|
||||
* | +------------------------------------------------------------+ |
|
||||
* | | Title: Link | |
|
||||
* | +------------------------------------------------------------+ |
|
||||
* | | RSSI: -112 SNR: 7.5 Ch: 478.875 SF: 7 BW: 125k | |
|
||||
* | +------------------------------------------------------------+ |
|
||||
* | | Hop: 2 Last heard: 18s | |
|
||||
* | +------------------------------------------------------------+ |
|
||||
* +------------------------------------------------------------------+
|
||||
*
|
||||
* Tree view:
|
||||
* Root(COL)
|
||||
* - Header
|
||||
* - Content(COL)
|
||||
* - TopRow(ROW, grow=1)
|
||||
* - InfoCard(COL)
|
||||
* - InfoHeader(ROW)
|
||||
* - InfoFooter(ROW)
|
||||
* - LocationCard(COL, grow=1)
|
||||
* - LocationHeader
|
||||
* - LocationMap(grow=1)
|
||||
* - LocationCoords
|
||||
* - LocationUpdated
|
||||
* - LinkPanel(COL)
|
||||
* - LinkHeader
|
||||
* - LinkRow1
|
||||
* - LinkRow2
|
||||
*
|
||||
* Preconditions:
|
||||
* - Root uses LV_FLEX_FLOW_COLUMN.
|
||||
* - TopRow uses LV_FLEX_FLOW_ROW.
|
||||
* - LinkPanel uses LV_FLEX_FLOW_COLUMN.
|
||||
*/
|
||||
|
||||
/**
|
||||
* @file node_info_page_layout.cpp
|
||||
* @brief Node info page layout
|
||||
* @brief Node info page layout helpers
|
||||
*/
|
||||
|
||||
#include "ui/screens/node_info/node_info_page_layout.h"
|
||||
|
||||
#include "ui/page/page_profile.h"
|
||||
#include "ui/widgets/top_bar.h"
|
||||
|
||||
@@ -73,8 +17,36 @@ namespace layout
|
||||
|
||||
namespace
|
||||
{
|
||||
constexpr lv_coord_t kScreenWidth = 480;
|
||||
constexpr lv_coord_t kBaseContentHeight = 192;
|
||||
|
||||
lv_coord_t resolve_parent_width(lv_obj_t* parent)
|
||||
{
|
||||
if (parent)
|
||||
{
|
||||
const lv_coord_t width = lv_obj_get_width(parent);
|
||||
if (width > 0)
|
||||
{
|
||||
return width;
|
||||
}
|
||||
}
|
||||
|
||||
const lv_coord_t width = lv_display_get_physical_horizontal_resolution(nullptr);
|
||||
return width > 0 ? width : 320;
|
||||
}
|
||||
|
||||
lv_coord_t resolve_parent_height(lv_obj_t* parent)
|
||||
{
|
||||
if (parent)
|
||||
{
|
||||
const lv_coord_t height = lv_obj_get_height(parent);
|
||||
if (height > 0)
|
||||
{
|
||||
return height;
|
||||
}
|
||||
}
|
||||
|
||||
const lv_coord_t height = lv_display_get_physical_vertical_resolution(nullptr);
|
||||
return height > 0 ? height : 240;
|
||||
}
|
||||
|
||||
lv_coord_t top_bar_height()
|
||||
{
|
||||
@@ -83,196 +55,45 @@ lv_coord_t top_bar_height()
|
||||
: static_cast<lv_coord_t>(::ui::widgets::kTopBarHeight);
|
||||
}
|
||||
|
||||
lv_coord_t screen_height()
|
||||
{
|
||||
return top_bar_height() + kBaseContentHeight;
|
||||
}
|
||||
constexpr int kContentPadX = 8;
|
||||
constexpr int kContentPadY = 4;
|
||||
constexpr int kCardGapX = 8;
|
||||
constexpr int kRowGap = 8;
|
||||
|
||||
constexpr int kTopRowX = kContentPadX;
|
||||
constexpr int kTopRowY = kContentPadY;
|
||||
constexpr int kTopRowWidth = kScreenWidth - (kContentPadX * 2);
|
||||
constexpr int kTopRowHeight = 118;
|
||||
|
||||
constexpr int kInfoCardWidth = 190;
|
||||
constexpr int kInfoCardHeight = 118;
|
||||
constexpr int kLocationCardWidth = 266;
|
||||
constexpr int kLocationCardHeight = 118;
|
||||
|
||||
constexpr int kLinkPanelX = kContentPadX;
|
||||
constexpr int kLinkPanelY = kTopRowY + kTopRowHeight + kRowGap;
|
||||
constexpr int kLinkPanelWidth = kTopRowWidth;
|
||||
constexpr int kLinkPanelHeight = 60;
|
||||
|
||||
constexpr int kLocationHeaderHeight = 22;
|
||||
constexpr int kLocationMapHeight = 52;
|
||||
constexpr int kLocationCoordsHeight = 18;
|
||||
constexpr int kLocationUpdatedHeight = 18;
|
||||
|
||||
constexpr int kInfoHeaderHeight = 70;
|
||||
constexpr int kInfoFooterHeight = 36;
|
||||
|
||||
constexpr int kLinkHeaderHeight = 20;
|
||||
constexpr int kLinkRowHeight = 16;
|
||||
|
||||
void make_non_scrollable(lv_obj_t* obj)
|
||||
void make_plain(lv_obj_t* obj)
|
||||
{
|
||||
lv_obj_clear_flag(obj, LV_OBJ_FLAG_SCROLLABLE);
|
||||
lv_obj_set_scrollbar_mode(obj, LV_SCROLLBAR_MODE_OFF);
|
||||
lv_obj_set_style_pad_all(obj, 0, 0);
|
||||
lv_obj_set_style_border_width(obj, 0, 0);
|
||||
lv_obj_set_style_radius(obj, 0, 0);
|
||||
}
|
||||
|
||||
} // namespace
|
||||
|
||||
lv_obj_t* create_root(lv_obj_t* parent)
|
||||
{
|
||||
lv_obj_t* root = lv_obj_create(parent);
|
||||
lv_obj_set_size(root, kScreenWidth, screen_height());
|
||||
lv_obj_set_size(root, resolve_parent_width(parent), resolve_parent_height(parent));
|
||||
lv_obj_set_pos(root, 0, 0);
|
||||
lv_obj_set_style_pad_all(root, 0, 0);
|
||||
make_non_scrollable(root);
|
||||
make_plain(root);
|
||||
return root;
|
||||
}
|
||||
|
||||
lv_obj_t* create_header(lv_obj_t* root)
|
||||
{
|
||||
lv_obj_t* header = lv_obj_create(root);
|
||||
lv_obj_set_size(header, kScreenWidth, top_bar_height());
|
||||
lv_obj_set_size(header, lv_obj_get_width(root), top_bar_height());
|
||||
lv_obj_set_pos(header, 0, 0);
|
||||
make_non_scrollable(header);
|
||||
make_plain(header);
|
||||
return header;
|
||||
}
|
||||
|
||||
lv_obj_t* create_content(lv_obj_t* root)
|
||||
{
|
||||
const lv_coord_t header_h = top_bar_height();
|
||||
lv_obj_t* content = lv_obj_create(root);
|
||||
lv_obj_set_size(content, kScreenWidth, kBaseContentHeight);
|
||||
lv_obj_set_pos(content, 0, top_bar_height());
|
||||
lv_obj_set_style_pad_all(content, 0, 0);
|
||||
make_non_scrollable(content);
|
||||
lv_obj_set_size(content, lv_obj_get_width(root), lv_obj_get_height(root) - header_h);
|
||||
lv_obj_set_pos(content, 0, header_h);
|
||||
make_plain(content);
|
||||
return content;
|
||||
}
|
||||
|
||||
lv_obj_t* create_top_row(lv_obj_t* content)
|
||||
{
|
||||
lv_obj_t* row = lv_obj_create(content);
|
||||
lv_obj_set_size(row, kTopRowWidth, kTopRowHeight);
|
||||
lv_obj_set_pos(row, kTopRowX, kTopRowY);
|
||||
lv_obj_set_style_pad_all(row, 0, 0);
|
||||
make_non_scrollable(row);
|
||||
return row;
|
||||
}
|
||||
|
||||
lv_obj_t* create_info_card(lv_obj_t* top_row)
|
||||
{
|
||||
lv_obj_t* card = lv_obj_create(top_row);
|
||||
lv_obj_set_size(card, kInfoCardWidth, kInfoCardHeight);
|
||||
lv_obj_set_pos(card, 0, 0);
|
||||
lv_obj_set_style_pad_all(card, 0, 0);
|
||||
make_non_scrollable(card);
|
||||
return card;
|
||||
}
|
||||
|
||||
lv_obj_t* create_info_header(lv_obj_t* info_card)
|
||||
{
|
||||
lv_obj_t* header = lv_obj_create(info_card);
|
||||
lv_obj_set_size(header, kInfoCardWidth, kInfoHeaderHeight);
|
||||
lv_obj_set_pos(header, 0, 0);
|
||||
lv_obj_set_style_pad_all(header, 0, 0);
|
||||
make_non_scrollable(header);
|
||||
return header;
|
||||
}
|
||||
|
||||
lv_obj_t* create_info_footer(lv_obj_t* info_card)
|
||||
{
|
||||
lv_obj_t* footer = lv_obj_create(info_card);
|
||||
lv_obj_set_size(footer, 170, kInfoFooterHeight);
|
||||
lv_obj_set_pos(footer, 10, 70);
|
||||
lv_obj_set_style_pad_all(footer, 0, 0);
|
||||
make_non_scrollable(footer);
|
||||
return footer;
|
||||
}
|
||||
|
||||
lv_obj_t* create_location_card(lv_obj_t* top_row)
|
||||
{
|
||||
lv_obj_t* card = lv_obj_create(top_row);
|
||||
lv_obj_set_size(card, kLocationCardWidth, kLocationCardHeight);
|
||||
lv_obj_set_pos(card, kInfoCardWidth + kCardGapX, 0);
|
||||
lv_obj_set_style_pad_all(card, 0, 0);
|
||||
make_non_scrollable(card);
|
||||
return card;
|
||||
}
|
||||
|
||||
lv_obj_t* create_location_header(lv_obj_t* location_card)
|
||||
{
|
||||
lv_obj_t* header = lv_obj_create(location_card);
|
||||
lv_obj_set_size(header, kLocationCardWidth, kLocationHeaderHeight);
|
||||
lv_obj_set_pos(header, 0, 0);
|
||||
lv_obj_set_style_pad_all(header, 0, 0);
|
||||
make_non_scrollable(header);
|
||||
return header;
|
||||
}
|
||||
|
||||
lv_obj_t* create_location_map(lv_obj_t* location_card)
|
||||
{
|
||||
lv_obj_t* map = lv_obj_create(location_card);
|
||||
lv_obj_set_size(map, 246, kLocationMapHeight);
|
||||
lv_obj_set_pos(map, 10, 30);
|
||||
lv_obj_set_style_pad_all(map, 0, 0);
|
||||
make_non_scrollable(map);
|
||||
return map;
|
||||
}
|
||||
|
||||
lv_obj_t* create_location_coords(lv_obj_t* location_card)
|
||||
{
|
||||
lv_obj_t* coords = lv_obj_create(location_card);
|
||||
lv_obj_set_size(coords, 246, kLocationCoordsHeight);
|
||||
lv_obj_set_pos(coords, 10, 86);
|
||||
lv_obj_set_style_pad_all(coords, 0, 0);
|
||||
make_non_scrollable(coords);
|
||||
return coords;
|
||||
}
|
||||
|
||||
lv_obj_t* create_location_updated(lv_obj_t* location_card)
|
||||
{
|
||||
lv_obj_t* updated = lv_obj_create(location_card);
|
||||
lv_obj_set_size(updated, 246, kLocationUpdatedHeight);
|
||||
lv_obj_set_pos(updated, 10, 106);
|
||||
lv_obj_set_style_pad_all(updated, 0, 0);
|
||||
make_non_scrollable(updated);
|
||||
return updated;
|
||||
}
|
||||
|
||||
lv_obj_t* create_link_panel(lv_obj_t* content)
|
||||
{
|
||||
lv_obj_t* panel = lv_obj_create(content);
|
||||
lv_obj_set_size(panel, kLinkPanelWidth, kLinkPanelHeight);
|
||||
lv_obj_set_pos(panel, kLinkPanelX, kLinkPanelY);
|
||||
lv_obj_set_style_pad_all(panel, 0, 0);
|
||||
make_non_scrollable(panel);
|
||||
return panel;
|
||||
}
|
||||
|
||||
lv_obj_t* create_link_header(lv_obj_t* link_panel)
|
||||
{
|
||||
lv_obj_t* header = lv_obj_create(link_panel);
|
||||
lv_obj_set_size(header, kLinkPanelWidth, kLinkHeaderHeight);
|
||||
lv_obj_set_pos(header, 0, 0);
|
||||
lv_obj_set_style_pad_all(header, 0, 0);
|
||||
make_non_scrollable(header);
|
||||
return header;
|
||||
}
|
||||
|
||||
lv_obj_t* create_link_row(lv_obj_t* link_panel)
|
||||
{
|
||||
lv_obj_t* row = lv_obj_create(link_panel);
|
||||
lv_obj_set_size(row, kLinkPanelWidth, kLinkRowHeight);
|
||||
lv_obj_set_style_pad_all(row, 0, 0);
|
||||
make_non_scrollable(row);
|
||||
return row;
|
||||
}
|
||||
|
||||
} // namespace layout
|
||||
} // namespace ui
|
||||
} // namespace node_info
|
||||
|
||||
@@ -216,16 +216,16 @@ void enter(const shell::Host* host, lv_obj_t* parent)
|
||||
lv_obj_center(stack);
|
||||
|
||||
lv_obj_t* title = lv_label_create(stack);
|
||||
::ui::i18n::set_label_text(title, page_subtitle());
|
||||
lv_obj_set_style_text_font(title, &lv_font_montserrat_18, 0);
|
||||
::ui::i18n::set_label_text(title, page_subtitle());
|
||||
|
||||
s_status_label = lv_label_create(stack);
|
||||
::ui::i18n::set_label_text(s_status_label, "Waiting for host...");
|
||||
lv_obj_set_style_text_font(s_status_label, &lv_font_montserrat_18, 0);
|
||||
::ui::i18n::set_label_text(s_status_label, "Waiting for host...");
|
||||
|
||||
s_count_label = lv_label_create(stack);
|
||||
::ui::i18n::set_label_text(s_count_label, "RX: 0 TX: 0");
|
||||
lv_obj_set_style_text_font(s_count_label, &lv_font_montserrat_16, 0);
|
||||
::ui::i18n::set_label_text(s_count_label, "RX: 0 TX: 0");
|
||||
|
||||
if (!s_timer)
|
||||
{
|
||||
|
||||
@@ -272,26 +272,26 @@ void enter(const shell::Host* host, lv_obj_t* parent)
|
||||
if (!platform::ui::device::card_ready())
|
||||
{
|
||||
lv_obj_t* error_label = lv_label_create(s_content);
|
||||
::ui::i18n::set_label_text(error_label, "SD Card Not Found\nPlease insert SD card");
|
||||
lv_obj_center(error_label);
|
||||
lv_obj_set_style_text_font(error_label, &lv_font_montserrat_18, LV_PART_MAIN);
|
||||
lv_obj_set_style_text_color(error_label, lv_color_hex(0xCC0000), LV_PART_MAIN);
|
||||
::ui::i18n::set_label_text(error_label, "SD Card Not Found\nPlease insert SD card");
|
||||
lv_obj_center(error_label);
|
||||
return;
|
||||
}
|
||||
|
||||
s_status_label = lv_label_create(s_content);
|
||||
::ui::i18n::set_label_text(s_status_label, "Initializing...");
|
||||
lv_obj_center(s_status_label);
|
||||
lv_obj_set_style_text_font(s_status_label, &lv_font_montserrat_18, LV_PART_MAIN);
|
||||
lv_obj_set_style_text_color(s_status_label, lv_color_hex(0x3A2A1A), LV_PART_MAIN);
|
||||
lv_obj_set_style_text_align(s_status_label, LV_TEXT_ALIGN_CENTER, LV_PART_MAIN);
|
||||
::ui::i18n::set_label_text(s_status_label, "Initializing...");
|
||||
lv_obj_center(s_status_label);
|
||||
|
||||
lv_obj_t* info_label = lv_label_create(s_content);
|
||||
::ui::i18n::set_label_text(info_label, "Press Back to exit USB mode");
|
||||
lv_obj_align(info_label, LV_ALIGN_BOTTOM_MID, 0, -20);
|
||||
lv_obj_set_style_text_font(info_label, &lv_font_montserrat_14, LV_PART_MAIN);
|
||||
lv_obj_set_style_text_color(info_label, lv_color_hex(0x6A5646), LV_PART_MAIN);
|
||||
lv_obj_set_style_text_opa(info_label, LV_OPA_80, LV_PART_MAIN);
|
||||
::ui::i18n::set_label_text(info_label, "Press Back to exit USB mode");
|
||||
lv_obj_align(info_label, LV_ALIGN_BOTTOM_MID, 0, -20);
|
||||
|
||||
update_status_label();
|
||||
|
||||
|
||||
Reference in New Issue
Block a user