From 940f31c3fb7dd08c2e5bcb204915634afce6d776 Mon Sep 17 00:00:00 2001 From: Martin Milata Date: Thu, 7 Mar 2024 00:49:49 +0100 Subject: [PATCH] feat(core/ui): T3T1 frame --- core/embed/rust/src/ui/component/label.rs | 10 +++ .../component/address_details.rs | 12 +--- .../component/coinjoin_progress.rs | 1 - .../src/ui/model_mercury/component/frame.rs | 65 +++++++------------ .../embed/rust/src/ui/model_mercury/layout.rs | 36 ++-------- .../rust/src/ui/model_mercury/theme/mod.rs | 14 ++-- 6 files changed, 52 insertions(+), 86 deletions(-) diff --git a/core/embed/rust/src/ui/component/label.rs b/core/embed/rust/src/ui/component/label.rs index 33c0d4f613..2faac8a2a5 100644 --- a/core/embed/rust/src/ui/component/label.rs +++ b/core/embed/rust/src/ui/component/label.rs @@ -37,11 +37,21 @@ impl<'a> Label<'a> { Self::new(text, Alignment::Center, style) } + pub fn top_aligned(mut self) -> Self { + self.vertical = Alignment::Start; + self + } + pub fn vertically_centered(mut self) -> Self { self.vertical = Alignment::Center; self } + pub fn bottom_aligned(mut self) -> Self { + self.vertical = Alignment::End; + self + } + pub fn text(&self) -> &TString<'a> { &self.text } diff --git a/core/embed/rust/src/ui/model_mercury/component/address_details.rs b/core/embed/rust/src/ui/model_mercury/component/address_details.rs index 76dd85b139..cd2a661bd2 100644 --- a/core/embed/rust/src/ui/model_mercury/component/address_details.rs +++ b/core/embed/rust/src/ui/model_mercury/component/address_details.rs @@ -60,21 +60,15 @@ where } let result = Self { qr_code: Frame::left_aligned( - theme::label_title(), qr_title, Qr::new(qr_address, case_sensitive)?.with_border(7), ) .with_cancel_button() .with_border(theme::borders_horizontal_scroll()), - details: Frame::left_aligned( - theme::label_title(), - details_title, - para.into_paragraphs(), - ) - .with_cancel_button() - .with_border(theme::borders_horizontal_scroll()), + details: Frame::left_aligned(details_title, para.into_paragraphs()) + .with_cancel_button() + .with_border(theme::borders_horizontal_scroll()), xpub_view: Frame::left_aligned( - theme::label_title(), " \n ".into(), Paragraph::new(&theme::TEXT_MONO, "".into()).into_paragraphs(), ) diff --git a/core/embed/rust/src/ui/model_mercury/component/coinjoin_progress.rs b/core/embed/rust/src/ui/model_mercury/component/coinjoin_progress.rs index 9b6b194947..91e3778cfd 100644 --- a/core/embed/rust/src/ui/model_mercury/component/coinjoin_progress.rs +++ b/core/embed/rust/src/ui/model_mercury/component/coinjoin_progress.rs @@ -71,7 +71,6 @@ where value: 0, indeterminate, content: Frame::centered( - theme::label_title(), TR::coinjoin__title_progress.try_into()?, Split::bottom(RECTANGLE_HEIGHT, 0, Empty, inner), ) diff --git a/core/embed/rust/src/ui/model_mercury/component/frame.rs b/core/embed/rust/src/ui/model_mercury/component/frame.rs index 34cbc3feec..0e33d24f98 100644 --- a/core/embed/rust/src/ui/model_mercury/component/frame.rs +++ b/core/embed/rust/src/ui/model_mercury/component/frame.rs @@ -13,6 +13,8 @@ use crate::{ use super::{Button, ButtonMsg, CancelInfoConfirmMsg}; +const TITLE_HEIGHT: i16 = 42; + pub struct Frame { border: Insets, title: Child>, @@ -31,14 +33,10 @@ impl Frame where T: Component, { - pub fn new( - style: TextStyle, - alignment: Alignment, - title: TString<'static>, - content: T, - ) -> Self { + pub fn new(alignment: Alignment, title: TString<'static>, content: T) -> Self { + let style: TextStyle = theme::label_title_main(); Self { - title: Child::new(Label::new(title, alignment, style)), + title: Child::new(Label::new(title, alignment, style).vertically_centered()), subtitle: None, border: theme::borders(), button: None, @@ -48,15 +46,15 @@ where } pub fn left_aligned(style: TextStyle, title: TString<'static>, content: T) -> Self { - Self::new(style, Alignment::Start, title, content) + Self::new(Alignment::Start, title, content) } pub fn right_aligned(style: TextStyle, title: TString<'static>, content: T) -> Self { - Self::new(style, Alignment::End, title, content) + Self::new(Alignment::End, title, content) } pub fn centered(style: TextStyle, title: TString<'static>, content: T) -> Self { - Self::new(style, Alignment::Center, title, content) + Self::new(Alignment::Center, title, content) } pub fn with_border(mut self, border: Insets) -> Self { @@ -64,7 +62,9 @@ where self } - pub fn with_subtitle(mut self, style: TextStyle, subtitle: TString<'static>) -> Self { + pub fn with_subtitle(mut self, subtitle: TString<'static>) -> Self { + let style = theme::label_title_sub(); + self.title = Child::new(self.title.into_inner().top_aligned()); self.subtitle = Some(Child::new(Label::new( subtitle, self.title.inner().alignment(), @@ -93,7 +93,7 @@ where } pub fn with_info_button(self) -> Self { - self.with_button(theme::ICON_CORNER_INFO, CancelInfoConfirmMsg::Info) + self.with_button(theme::ICON_MENU, CancelInfoConfirmMsg::Info) } pub fn inner(&self) -> &T { @@ -126,38 +126,23 @@ where type Msg = FrameMsg; fn place(&mut self, bounds: Rect) -> Rect { - const TITLE_SPACE: i16 = theme::BUTTON_SPACING; + let (mut header_area, content_area) = bounds.split_top(TITLE_HEIGHT); + let content_area = content_area.inset(Insets::right(TITLE_SPACE)); - let bounds = bounds.inset(self.border); - // Allowing for little longer titles to fit in - const TITLE_EXTRA_SPACE: Insets = Insets::right(2); if let Some(b) = &mut self.button { - let button_side = theme::CORNER_BUTTON_SIDE; - let (header_area, button_area) = bounds.split_right(button_side); - let (button_area, _) = button_area.split_top(button_side); + let (rest, button_area) = header_area.split_right(TITLE_HEIGHT); + header_area = rest; b.place(button_area); - let title_area = self.title.place(header_area.outset(TITLE_EXTRA_SPACE)); - let remaining = header_area.inset(Insets::top(title_area.height())); - let subtitle_area = self.subtitle.place(remaining); - - let title_height = title_area.height() + subtitle_area.height(); - let header_height = title_height.max(button_side); - if title_height < button_side { - self.title - .place(title_area.translate(Offset::y((button_side - title_height) / 2))); - self.subtitle - .place(subtitle_area.translate(Offset::y((button_side - title_height) / 2))); - } - let content_area = bounds.inset(Insets::top(header_height + TITLE_SPACE)); - self.content.place(content_area); - } else { - let title_area = self.title.place(bounds.outset(TITLE_EXTRA_SPACE)); - let remaining = bounds.inset(Insets::top(title_area.height())); - let subtitle_area = self.subtitle.place(remaining); - let remaining = remaining.inset(Insets::top(subtitle_area.height())); - let content_area = remaining.inset(Insets::top(TITLE_SPACE)); - self.content.place(content_area); } + + if self.subtitle.is_some() { + let title_area = self.title.place(header_area); + let remaining = header_area.inset(Insets::top(title_area.height())); + let _subtitle_area = self.subtitle.place(remaining); + } else { + self.title.place(header_area); + } + self.content.place(content_area); bounds } diff --git a/core/embed/rust/src/ui/model_mercury/layout.rs b/core/embed/rust/src/ui/model_mercury/layout.rs index 2d18aa1cde..4dc112d6f5 100644 --- a/core/embed/rust/src/ui/model_mercury/layout.rs +++ b/core/embed/rust/src/ui/model_mercury/layout.rs @@ -411,7 +411,7 @@ extern "C" fn new_confirm_action(n_args: usize, args: *const Obj, kwargs: *mut M if hold && hold_danger { page = page.with_confirm_style(theme::button_danger()) } - let obj = LayoutObj::new(Frame::left_aligned(theme::label_title(), title, page))?; + let obj = LayoutObj::new(Frame::left_aligned(title, page))?; Ok(obj.into()) }; unsafe { util::try_with_args_and_kwargs(n_args, args, kwargs, block) } @@ -442,7 +442,6 @@ extern "C" fn new_confirm_emphasized(n_args: usize, args: *const Obj, kwargs: *m } let obj = LayoutObj::new(Frame::left_aligned( - theme::label_title(), title, ButtonPage::new(FormattedText::new(ops).vertically_centered(), theme::BG) .with_cancel_confirm(None, verb), @@ -540,9 +539,9 @@ impl ConfirmBlobParams { if self.hold { page = page.with_hold()? } - let mut frame = Frame::left_aligned(theme::label_title(), self.title, page); + let mut frame = Frame::left_aligned(self.title, page); if let Some(subtitle) = self.subtitle { - frame = frame.with_subtitle(theme::label_subtitle(), subtitle); + frame = frame.with_subtitle(subtitle); } if self.info_button { frame = frame.with_info_button(); @@ -608,7 +607,6 @@ extern "C" fn new_confirm_address(n_args: usize, args: *const Obj, kwargs: *mut let obj = LayoutObj::new( Frame::left_aligned( - theme::label_title(), title, ButtonPage::new(paragraphs, theme::BG) .with_swipe_left() @@ -639,7 +637,7 @@ extern "C" fn new_confirm_properties(n_args: usize, args: *const Obj, kwargs: *m ButtonPage::new(paragraphs.into_paragraphs(), theme::BG) .with_cancel_confirm(None, Some(TR::buttons__confirm.try_into()?)) }; - let obj = LayoutObj::new(Frame::left_aligned(theme::label_title(), title, page))?; + let obj = LayoutObj::new(Frame::left_aligned(title, page))?; Ok(obj.into()) }; unsafe { util::try_with_args_and_kwargs(n_args, args, kwargs, block) } @@ -673,7 +671,6 @@ extern "C" fn new_confirm_homescreen(n_args: usize, args: *const Obj, kwargs: *m let tr_change: StrBuffer = TR::buttons__change.try_into()?; let buttons = Button::cancel_confirm_text(None, Some(tr_change)); let obj = LayoutObj::new(Frame::centered( - theme::label_title(), title, Dialog::new(painter::jpeg_painter(buffer_func, size, 1), buttons), ))?; @@ -700,11 +697,7 @@ extern "C" fn new_confirm_reset_device(n_args: usize, args: *const Obj, kwargs: Button::with_text(button).styled(theme::button_confirm()), true, ); - let obj = LayoutObj::new(Frame::left_aligned( - theme::label_title(), - title, - Dialog::new(paragraphs, buttons), - ))?; + let obj = LayoutObj::new(Frame::left_aligned(title, Dialog::new(paragraphs, buttons)))?; Ok(obj.into()) }; unsafe { util::try_with_args_and_kwargs(n_args, args, kwargs, block) } @@ -773,7 +766,6 @@ extern "C" fn new_show_info_with_cancel(n_args: usize, args: *const Obj, kwargs: let obj = LayoutObj::new( Frame::left_aligned( - theme::label_title(), title, SimplePage::new(paragraphs.into_paragraphs(), axis, theme::BG) .with_swipe_right_to_go_back(), @@ -838,7 +830,7 @@ extern "C" fn new_confirm_total(n_args: usize, args: *const Obj, kwargs: *mut Ma if info_button { page = page.with_swipe_left(); } - let mut frame = Frame::left_aligned(theme::label_title(), title, page); + let mut frame = Frame::left_aligned(title, page); if info_button { frame = frame.with_info_button(); } @@ -872,7 +864,6 @@ extern "C" fn new_confirm_modify_output(n_args: usize, args: *const Obj, kwargs: let tr_title: StrBuffer = TR::modify_amount__title.try_into()?; let obj = LayoutObj::new(Frame::left_aligned( - theme::label_title(), tr_title, ButtonPage::<_, StrBuffer>::new(paragraphs, theme::BG) .with_cancel_confirm(Some("^".into()), Some(TR::buttons__continue.try_into()?)), @@ -916,7 +907,6 @@ extern "C" fn new_confirm_modify_fee(n_args: usize, args: *const Obj, kwargs: *m let obj = LayoutObj::new( Frame::left_aligned( - theme::label_title(), title, ButtonPage::<_, StrBuffer>::new(paragraphs, theme::BG) .with_hold()? @@ -1039,7 +1029,7 @@ extern "C" fn new_confirm_fido(n_args: usize, args: *const Obj, kwargs: *mut Map let fido_page = FidoConfirm::new(app_name, get_page, page_count, icon, controls); - let obj = LayoutObj::new(Frame::centered(theme::label_title(), title, fido_page))?; + let obj = LayoutObj::new(Frame::centered(title, fido_page))?; Ok(obj.into()) }; unsafe { util::try_with_args_and_kwargs(n_args, args, kwargs, block) } @@ -1136,7 +1126,6 @@ extern "C" fn new_show_simple(n_args: usize, args: *const Obj, kwargs: *mut Map) let obj = if let Some(t) = title { LayoutObj::new(Frame::left_aligned( - theme::label_title(), t, Dialog::new( Paragraphs::new([Paragraph::new(&theme::TEXT_NORMAL, description)]), @@ -1197,7 +1186,6 @@ extern "C" fn new_confirm_with_info(n_args: usize, args: *const Obj, kwargs: *mu let buttons = Button::cancel_info_confirm(button, info_button); let obj = LayoutObj::new(Frame::left_aligned( - theme::label_title(), title, Dialog::new(paragraphs.into_paragraphs(), buttons), ))?; @@ -1222,7 +1210,6 @@ extern "C" fn new_confirm_more(n_args: usize, args: *const Obj, kwargs: *mut Map } let obj = LayoutObj::new(Frame::left_aligned( - theme::label_title(), title, ButtonPage::new(paragraphs.into_paragraphs(), theme::BG) .with_cancel_confirm(None, Some(button)) @@ -1251,7 +1238,6 @@ extern "C" fn new_confirm_coinjoin(n_args: usize, args: *const Obj, kwargs: *mut let tr_title: StrBuffer = TR::coinjoin__title.try_into()?; let obj = LayoutObj::new(Frame::left_aligned( - theme::label_title(), tr_title, ButtonPage::<_, StrBuffer>::new(paragraphs, theme::BG).with_hold()?, ))?; @@ -1326,7 +1312,6 @@ extern "C" fn new_select_word(n_args: usize, args: *const Obj, kwargs: *mut Map) let paragraphs = Paragraphs::new([Paragraph::new(&theme::TEXT_DEMIBOLD, description)]); let obj = LayoutObj::new(Frame::left_aligned( - theme::label_title(), title, Dialog::new(paragraphs, Button::select_word(words)), ))?; @@ -1347,7 +1332,6 @@ extern "C" fn new_show_share_words(n_args: usize, args: *const Obj, kwargs: *mut } let obj = LayoutObj::new(Frame::left_aligned( - theme::label_title(), title, ButtonPage::<_, StrBuffer>::new(paragraphs.into_paragraphs(), theme::BG) .with_hold()? @@ -1377,7 +1361,6 @@ extern "C" fn new_request_number(n_args: usize, args: *const Obj, kwargs: *mut M }; let obj = LayoutObj::new(Frame::left_aligned( - theme::label_title(), title, NumberInputDialog::new(min_count, max_count, count, callback)?, ))?; @@ -1405,7 +1388,6 @@ extern "C" fn new_show_checklist(n_args: usize, args: *const Obj, kwargs: *mut M } let obj = LayoutObj::new(Frame::left_aligned( - theme::label_title(), title, Dialog::new( Checklist::from_paragraphs( @@ -1451,7 +1433,6 @@ extern "C" fn new_confirm_recovery(n_args: usize, args: *const Obj, kwargs: *mut let obj = if info_button { LayoutObj::new(Frame::left_aligned( - theme::label_title(), notification, Dialog::new( paragraphs, @@ -1463,7 +1444,6 @@ extern "C" fn new_confirm_recovery(n_args: usize, args: *const Obj, kwargs: *mut ))? } else { LayoutObj::new(Frame::left_aligned( - theme::label_title(), notification, Dialog::new(paragraphs, Button::cancel_confirm_text(None, Some(button))), ))? @@ -1488,7 +1468,6 @@ extern "C" fn new_select_word_count(n_args: usize, args: *const Obj, kwargs: *mu )); let obj = LayoutObj::new(Frame::left_aligned( - theme::label_title(), title, Dialog::new(paragraphs, SelectWordCount::new()), ))?; @@ -1533,7 +1512,6 @@ extern "C" fn new_show_remaining_shares(n_args: usize, args: *const Obj, kwargs: let tr_title: StrBuffer = TR::recovery__title_remaining_shares.try_into()?; let obj = LayoutObj::new(Frame::left_aligned( - theme::label_title(), tr_title, ButtonPage::<_, StrBuffer>::new(paragraphs.into_paragraphs(), theme::BG) .with_cancel_confirm(None, Some(TR::buttons__continue.try_into()?)) diff --git a/core/embed/rust/src/ui/model_mercury/theme/mod.rs b/core/embed/rust/src/ui/model_mercury/theme/mod.rs index 56fd5f5607..557d4aa418 100644 --- a/core/embed/rust/src/ui/model_mercury/theme/mod.rs +++ b/core/embed/rust/src/ui/model_mercury/theme/mod.rs @@ -154,9 +154,9 @@ pub const fn button_moreinfo() -> ButtonStyleSheet { text_color: FG, button_color: BG, background_color: BG, - border_color: GREY_DARK, - border_radius: RADIUS, - border_width: 2, + border_color: BG, + border_radius: 0, + border_width: 1, }, active: &ButtonStyle { font: Font::BOLD, @@ -172,9 +172,9 @@ pub const fn button_moreinfo() -> ButtonStyleSheet { text_color: GREY_LIGHT, button_color: BG, background_color: BG, - border_color: GREY_DARK, - border_radius: RADIUS, - border_width: 2, + border_color: BG, + border_radius: 0, + border_width: 1, }, } } @@ -231,5 +231,5 @@ pub const RESULT_FOOTER_START: i16 = 171; /// | 6 | /// +----------+ pub const fn borders() -> Insets { - Insets::new(6, 6, 6, 6) + Insets::new(0, 0, 0, 0) }