diff --git a/core/embed/rust/src/ui/api/firmware_upy.rs b/core/embed/rust/src/ui/api/firmware_upy.rs index 02afc39198..f5facd4c73 100644 --- a/core/embed/rust/src/ui/api/firmware_upy.rs +++ b/core/embed/rust/src/ui/api/firmware_upy.rs @@ -232,6 +232,20 @@ extern "C" fn new_confirm_modify_output(n_args: usize, args: *const Obj, kwargs: unsafe { util::try_with_args_and_kwargs(n_args, args, kwargs, block) } } +extern "C" fn new_confirm_more(n_args: usize, args: *const Obj, kwargs: *mut Map) -> Obj { + let block = move |_args: &[Obj], kwargs: &Map| { + let title: TString = kwargs.get(Qstr::MP_QSTR_title)?.try_into()?; + let button: TString = kwargs.get(Qstr::MP_QSTR_button)?.try_into()?; + let button_style_confirm: bool = + kwargs.get_or(Qstr::MP_QSTR_button_style_confirm, false)?; + let items: Obj = kwargs.get(Qstr::MP_QSTR_items)?; + + let layout = ModelUI::confirm_more(title, button, button_style_confirm, items)?; + Ok(LayoutObj::new_root(layout)?.into()) + }; + unsafe { util::try_with_args_and_kwargs(n_args, args, kwargs, block) } +} + extern "C" fn new_confirm_properties(n_args: usize, args: *const Obj, kwargs: *mut Map) -> Obj { let block = move |_args: &[Obj], kwargs: &Map| { let title: TString = kwargs.get(Qstr::MP_QSTR_title)?.try_into()?; @@ -953,6 +967,17 @@ pub static mp_module_trezorui_api: Module = obj_module! { /// """Decrease or increase output amount.""" Qstr::MP_QSTR_confirm_modify_output => obj_fn_kw!(0, new_confirm_modify_output).as_obj(), + /// def confirm_more( + /// *, + /// title: str, + /// button: str, + /// button_style_confirm: bool = False, + /// items: Iterable[tuple[int, str | bytes]], + /// ) -> LayoutObj[UiResult]: + /// """Confirm long content with the possibility to go back from any page. + /// Meant to be used with confirm_with_info on model TT and TR.""" + Qstr::MP_QSTR_confirm_more => obj_fn_kw!(0, new_confirm_more).as_obj(), + /// def confirm_properties( /// *, /// title: str, diff --git a/core/embed/rust/src/ui/model_mercury/ui_features_fw.rs b/core/embed/rust/src/ui/model_mercury/ui_features_fw.rs index dae608e7fc..2b7380af61 100644 --- a/core/embed/rust/src/ui/model_mercury/ui_features_fw.rs +++ b/core/embed/rust/src/ui/model_mercury/ui_features_fw.rs @@ -269,6 +269,17 @@ impl UIFeaturesFirmware for ModelMercuryFeatures { Ok(layout) } + fn confirm_more( + _title: TString<'static>, + _button: TString<'static>, + _button_style_confirm: bool, + _items: Obj, + ) -> Result { + Err::, Error>(Error::ValueError( + c"confirm_more not implemented", + )) + } + fn confirm_reset_device(recovery: bool) -> Result { let flow = flow::confirm_reset::new_confirm_reset(recovery)?; Ok(flow) diff --git a/core/embed/rust/src/ui/model_tr/layout.rs b/core/embed/rust/src/ui/model_tr/layout.rs index a247efea3b..5f73a86cd4 100644 --- a/core/embed/rust/src/ui/model_tr/layout.rs +++ b/core/embed/rust/src/ui/model_tr/layout.rs @@ -648,32 +648,6 @@ extern "C" fn new_multiple_pages_texts(n_args: usize, args: *const Obj, kwargs: unsafe { util::try_with_args_and_kwargs(n_args, args, kwargs, block) } } -extern "C" fn new_confirm_more(n_args: usize, args: *const Obj, kwargs: *mut Map) -> Obj { - let block = move |_args: &[Obj], kwargs: &Map| { - let title: TString = kwargs.get(Qstr::MP_QSTR_title)?.try_into()?; - let button: TString<'static> = kwargs.get(Qstr::MP_QSTR_button)?.try_into()?; - let items: Obj = kwargs.get(Qstr::MP_QSTR_items)?; - - let mut paragraphs = ParagraphVecLong::new(); - - for para in IterBuf::new().try_iterate(items)? { - let [font, text]: [Obj; 2] = util::iter_into_array(para)?; - let style: &TextStyle = theme::textstyle_number(font.try_into()?); - let text: TString = text.try_into()?; - paragraphs.add(Paragraph::new(style, text)); - } - - content_in_button_page( - title, - paragraphs.into_paragraphs(), - button, - Some("<".into()), - false, - ) - }; - unsafe { util::try_with_args_and_kwargs(n_args, args, kwargs, block) } -} - #[no_mangle] pub static mp_module_trezorui2: Module = obj_module! { /// from trezor import utils @@ -767,14 +741,4 @@ pub static mp_module_trezorui2: Module = obj_module! { /// ) -> LayoutObj[UiResult]: /// """Show multiple texts, each on its own page.""" Qstr::MP_QSTR_multiple_pages_texts => obj_fn_kw!(0, new_multiple_pages_texts).as_obj(), - - /// def confirm_more( - /// *, - /// title: str, - /// button: str, - /// items: Iterable[tuple[int, str | bytes]], - /// ) -> object: - /// """Confirm long content with the possibility to go back from any page. - /// Meant to be used with confirm_with_info.""" - Qstr::MP_QSTR_confirm_more => obj_fn_kw!(0, new_confirm_more).as_obj(), }; diff --git a/core/embed/rust/src/ui/model_tr/ui_features_fw.rs b/core/embed/rust/src/ui/model_tr/ui_features_fw.rs index 0f24fd338a..a97173c9c0 100644 --- a/core/embed/rust/src/ui/model_tr/ui_features_fw.rs +++ b/core/embed/rust/src/ui/model_tr/ui_features_fw.rs @@ -312,6 +312,30 @@ impl UIFeaturesFirmware for ModelTRFeatures { ) } + fn confirm_more( + title: TString<'static>, + button: TString<'static>, + _button_style_confirm: bool, + items: Obj, + ) -> Result { + let mut paragraphs = ParagraphVecLong::new(); + + for para in IterBuf::new().try_iterate(items)? { + let [font, text]: [Obj; 2] = util::iter_into_array(para)?; + let style: &TextStyle = theme::textstyle_number(font.try_into()?); + let text: TString = text.try_into()?; + paragraphs.add(Paragraph::new(style, text)); + } + + content_in_button_page( + title, + paragraphs.into_paragraphs(), + button, + Some("<".into()), + false, + ) + } + fn confirm_properties( title: TString<'static>, items: Obj, diff --git a/core/embed/rust/src/ui/model_tt/layout.rs b/core/embed/rust/src/ui/model_tt/layout.rs index abb023c6d1..04fafed3dc 100644 --- a/core/embed/rust/src/ui/model_tt/layout.rs +++ b/core/embed/rust/src/ui/model_tt/layout.rs @@ -457,40 +457,6 @@ extern "C" fn new_confirm_total(n_args: usize, args: *const Obj, kwargs: *mut Ma unsafe { util::try_with_args_and_kwargs(n_args, args, kwargs, block) } } -extern "C" fn new_confirm_more(n_args: usize, args: *const Obj, kwargs: *mut Map) -> Obj { - let block = move |_args: &[Obj], kwargs: &Map| { - let title: TString = kwargs.get(Qstr::MP_QSTR_title)?.try_into()?; - let button: TString = kwargs.get(Qstr::MP_QSTR_button)?.try_into()?; - let button_style_confirm: bool = - kwargs.get_or(Qstr::MP_QSTR_button_style_confirm, false)?; - let items: Obj = kwargs.get(Qstr::MP_QSTR_items)?; - - let mut paragraphs = ParagraphVecLong::new(); - - for para in IterBuf::new().try_iterate(items)? { - let [font, text]: [Obj; 2] = util::iter_into_array(para)?; - let style: &TextStyle = theme::textstyle_number(font.try_into()?); - let text: TString = text.try_into()?; - paragraphs.add(Paragraph::new(style, text)); - } - - let obj = LayoutObj::new(Frame::left_aligned( - theme::label_title(), - title, - ButtonPage::new(paragraphs.into_paragraphs(), theme::BG) - .with_cancel_confirm(None, Some(button)) - .with_confirm_style(if button_style_confirm { - theme::button_confirm() - } else { - theme::button_default() - }) - .with_back_button(), - ))?; - Ok(obj.into()) - }; - unsafe { util::try_with_args_and_kwargs(n_args, args, kwargs, block) } -} - #[no_mangle] pub static mp_module_trezorui2: Module = obj_module! { /// from trezor import utils @@ -542,17 +508,6 @@ pub static mp_module_trezorui2: Module = obj_module! { /// ) -> LayoutObj[UiResult]: /// """Transaction summary. Always hold to confirm.""" Qstr::MP_QSTR_confirm_total => obj_fn_kw!(0, new_confirm_total).as_obj(), - - /// def confirm_more( - /// *, - /// title: str, - /// button: str, - /// button_style_confirm: bool = False, - /// items: Iterable[tuple[int, str | bytes]], - /// ) -> LayoutObj[UiResult]: - /// """Confirm long content with the possibility to go back from any page. - /// Meant to be used with confirm_with_info.""" - Qstr::MP_QSTR_confirm_more => obj_fn_kw!(0, new_confirm_more).as_obj(), }; #[cfg(test)] diff --git a/core/embed/rust/src/ui/model_tt/ui_features_fw.rs b/core/embed/rust/src/ui/model_tt/ui_features_fw.rs index c64b07b835..3bed216d4c 100644 --- a/core/embed/rust/src/ui/model_tt/ui_features_fw.rs +++ b/core/embed/rust/src/ui/model_tt/ui_features_fw.rs @@ -270,6 +270,36 @@ impl UIFeaturesFirmware for ModelTTFeatures { Ok(layout) } + fn confirm_more( + title: TString<'static>, + button: TString<'static>, + button_style_confirm: bool, + items: Obj, + ) -> Result { + let mut paragraphs = ParagraphVecLong::new(); + + for para in IterBuf::new().try_iterate(items)? { + let [font, text]: [Obj; 2] = util::iter_into_array(para)?; + let style: &TextStyle = theme::textstyle_number(font.try_into()?); + let text: TString = text.try_into()?; + paragraphs.add(Paragraph::new(style, text)); + } + + let layout = RootComponent::new(Frame::left_aligned( + theme::label_title(), + title, + ButtonPage::new(paragraphs.into_paragraphs(), theme::BG) + .with_cancel_confirm(None, Some(button)) + .with_confirm_style(if button_style_confirm { + theme::button_confirm() + } else { + theme::button_default() + }) + .with_back_button(), + )); + Ok(layout) + } + fn confirm_properties( title: TString<'static>, items: Obj, diff --git a/core/embed/rust/src/ui/ui_features_fw.rs b/core/embed/rust/src/ui/ui_features_fw.rs index f997304647..298d3dbcb2 100644 --- a/core/embed/rust/src/ui/ui_features_fw.rs +++ b/core/embed/rust/src/ui/ui_features_fw.rs @@ -80,6 +80,13 @@ pub trait UIFeaturesFirmware { amount_new: TString<'static>, ) -> Result; + fn confirm_more( + title: TString<'static>, + button: TString<'static>, + button_style_confirm: bool, + items: Obj, // TODO: replace Obj + ) -> Result; + fn confirm_properties( title: TString<'static>, items: Obj, // TODO: replace Obj` diff --git a/core/mocks/generated/trezorui2.pyi b/core/mocks/generated/trezorui2.pyi index 54b56fdda6..28eccc4271 100644 --- a/core/mocks/generated/trezorui2.pyi +++ b/core/mocks/generated/trezorui2.pyi @@ -234,17 +234,6 @@ def multiple_pages_texts( items: list[str], ) -> LayoutObj[UiResult]: """Show multiple texts, each on its own page.""" - - -# rust/src/ui/model_tr/layout.rs -def confirm_more( - *, - title: str, - button: str, - items: Iterable[tuple[int, str | bytes]], -) -> object: - """Confirm long content with the possibility to go back from any page. - Meant to be used with confirm_with_info.""" from trezor import utils from trezorui_api import * @@ -297,15 +286,3 @@ def confirm_total( cancel_arrow: bool = False, ) -> LayoutObj[UiResult]: """Transaction summary. Always hold to confirm.""" - - -# rust/src/ui/model_tt/layout.rs -def confirm_more( - *, - title: str, - button: str, - button_style_confirm: bool = False, - items: Iterable[tuple[int, str | bytes]], -) -> LayoutObj[UiResult]: - """Confirm long content with the possibility to go back from any page. - Meant to be used with confirm_with_info.""" diff --git a/core/mocks/generated/trezorui_api.pyi b/core/mocks/generated/trezorui_api.pyi index 9b4ba221a2..dfaee79592 100644 --- a/core/mocks/generated/trezorui_api.pyi +++ b/core/mocks/generated/trezorui_api.pyi @@ -180,6 +180,18 @@ def confirm_modify_output( """Decrease or increase output amount.""" +# rust/src/ui/api/firmware_upy.rs +def confirm_more( + *, + title: str, + button: str, + button_style_confirm: bool = False, + items: Iterable[tuple[int, str | bytes]], +) -> LayoutObj[UiResult]: + """Confirm long content with the possibility to go back from any page. + Meant to be used with confirm_with_info on model TT and TR.""" + + # rust/src/ui/api/firmware_upy.rs def confirm_properties( *, diff --git a/core/src/trezor/ui/layouts/tr/__init__.py b/core/src/trezor/ui/layouts/tr/__init__.py index ca566c0b19..211600ffa9 100644 --- a/core/src/trezor/ui/layouts/tr/__init__.py +++ b/core/src/trezor/ui/layouts/tr/__init__.py @@ -591,7 +591,7 @@ async def _confirm_ask_pagination( data = hexlify(data).decode() - confirm_more_layout = trezorui2.confirm_more( + confirm_more_layout = trezorui_api.confirm_more( title=title, button=TR.buttons__confirm, items=[(ui.NORMAL, description), (ui.MONO, data)], diff --git a/core/src/trezor/ui/layouts/tt/__init__.py b/core/src/trezor/ui/layouts/tt/__init__.py index da790c94d6..4d5e04d067 100644 --- a/core/src/trezor/ui/layouts/tt/__init__.py +++ b/core/src/trezor/ui/layouts/tt/__init__.py @@ -519,7 +519,7 @@ async def _confirm_ask_pagination( data = hexlify(data).decode() - confirm_more_layout = trezorui2.confirm_more( + confirm_more_layout = trezorui_api.confirm_more( title=title, button=TR.buttons__confirm, button_style_confirm=True,