mirror of
https://github.com/trezor/trezor-firmware.git
synced 2025-07-22 06:28:13 +00:00
refactor(delizia): use external menu on confirm_action
[no changelog]
This commit is contained in:
parent
1e7108f6d2
commit
566f6fe7cb
@ -71,6 +71,7 @@ extern "C" fn new_confirm_action(n_args: usize, args: *const Obj, kwargs: *mut M
|
||||
.get(Qstr::MP_QSTR_prompt_title)
|
||||
.unwrap_or_else(|_| Obj::const_none())
|
||||
.try_into_option()?;
|
||||
let external_menu: bool = kwargs.get_or(Qstr::MP_QSTR_external_menu, false)?;
|
||||
|
||||
let layout = ModelUI::confirm_action(
|
||||
title,
|
||||
@ -84,6 +85,7 @@ extern "C" fn new_confirm_action(n_args: usize, args: *const Obj, kwargs: *mut M
|
||||
reverse,
|
||||
prompt_screen,
|
||||
prompt_title,
|
||||
external_menu,
|
||||
)?;
|
||||
Ok(LayoutObj::new_root(layout)?.into())
|
||||
};
|
||||
@ -1351,6 +1353,7 @@ pub static mp_module_trezorui_api: Module = obj_module! {
|
||||
/// reverse: bool = False,
|
||||
/// prompt_screen: bool = False,
|
||||
/// prompt_title: str | None = None,
|
||||
/// external_menu: bool = False,
|
||||
/// ) -> LayoutObj[UiResult]:
|
||||
/// """Confirm action."""
|
||||
Qstr::MP_QSTR_confirm_action => obj_fn_kw!(0, new_confirm_action).as_obj(),
|
||||
|
@ -57,6 +57,7 @@ impl FirmwareUI for UIBolt {
|
||||
reverse: bool,
|
||||
_prompt_screen: bool,
|
||||
_prompt_title: Option<TString<'static>>,
|
||||
_external_menu: bool, // TODO: will eventually replace the internal menu
|
||||
) -> Result<impl LayoutMaybeTrace, Error> {
|
||||
let paragraphs = {
|
||||
let action = action.unwrap_or("".into());
|
||||
@ -946,6 +947,7 @@ impl FirmwareUI for UIBolt {
|
||||
false,
|
||||
false,
|
||||
None,
|
||||
false,
|
||||
)
|
||||
}
|
||||
|
||||
|
@ -58,6 +58,7 @@ impl FirmwareUI for UICaesar {
|
||||
reverse: bool,
|
||||
_prompt_screen: bool,
|
||||
_prompt_title: Option<TString<'static>>,
|
||||
_external_menu: bool, // TODO: will eventually replace the internal menu
|
||||
) -> Result<impl LayoutMaybeTrace, Error> {
|
||||
let paragraphs = {
|
||||
let action = action.unwrap_or("".into());
|
||||
|
@ -30,6 +30,8 @@ const MENU_ITEM_INFO: usize = 1;
|
||||
// Extra button at the top-right corner of the Action screen
|
||||
#[derive(PartialEq)]
|
||||
pub enum ConfirmActionExtra {
|
||||
// Shows a menu button that simply returns INFO so it can be handled externally
|
||||
ExternalMenu,
|
||||
// Opens a menu which can (optionally) lead to an extra Info screen, or cancel the action
|
||||
Menu(ConfirmActionMenuStrings),
|
||||
// Shows a cancel button directly
|
||||
@ -114,6 +116,7 @@ impl FlowController for ConfirmAction {
|
||||
fn handle_event(&'static self, msg: FlowMsg) -> Decision {
|
||||
match (self, msg) {
|
||||
(Self::Action, FlowMsg::Cancelled) => self.return_msg(FlowMsg::Cancelled),
|
||||
(Self::Action, FlowMsg::Info) => self.return_msg(FlowMsg::Info),
|
||||
_ => self.do_nothing(),
|
||||
}
|
||||
}
|
||||
@ -143,6 +146,7 @@ impl FlowController for ConfirmActionWithConfirmation {
|
||||
fn handle_event(&'static self, msg: FlowMsg) -> Decision {
|
||||
match (self, msg) {
|
||||
(Self::Action, FlowMsg::Cancelled) => self.return_msg(FlowMsg::Cancelled),
|
||||
(Self::Action, FlowMsg::Info) => self.return_msg(FlowMsg::Info),
|
||||
(Self::Confirmation, FlowMsg::Confirmed) => self.return_msg(FlowMsg::Confirmed),
|
||||
_ => self.do_nothing(),
|
||||
}
|
||||
@ -227,6 +231,7 @@ pub fn new_confirm_action(
|
||||
hold: bool,
|
||||
prompt_screen: bool,
|
||||
prompt_title: TString<'static>,
|
||||
external_menu: bool,
|
||||
) -> Result<SwipeFlow, error::Error> {
|
||||
let paragraphs = {
|
||||
let action = action.unwrap_or("".into());
|
||||
@ -244,9 +249,19 @@ pub fn new_confirm_action(
|
||||
paragraphs.into_paragraphs()
|
||||
};
|
||||
|
||||
if external_menu && (prompt_screen || hold) {
|
||||
return Err(Error::ValueError(
|
||||
c"external_menu currently not supported in tandem with prompt_screen/hold",
|
||||
));
|
||||
}
|
||||
|
||||
new_confirm_action_simple(
|
||||
paragraphs,
|
||||
ConfirmActionExtra::Menu(ConfirmActionMenuStrings::new().with_verb_cancel(verb_cancel)),
|
||||
if external_menu {
|
||||
ConfirmActionExtra::ExternalMenu
|
||||
} else {
|
||||
ConfirmActionExtra::Menu(ConfirmActionMenuStrings::new().with_verb_cancel(verb_cancel))
|
||||
},
|
||||
ConfirmActionStrings::new(title, subtitle, None, prompt_screen.then_some(prompt_title)),
|
||||
hold,
|
||||
None,
|
||||
@ -273,7 +288,7 @@ fn new_confirm_action_uni<T: Component + PaginateFull + MaybeTrace + 'static>(
|
||||
.with_vertical_pages();
|
||||
|
||||
match extra {
|
||||
ConfirmActionExtra::Menu { .. } => {
|
||||
ConfirmActionExtra::Menu { .. } | ConfirmActionExtra::ExternalMenu => {
|
||||
content = content.with_menu_button();
|
||||
}
|
||||
ConfirmActionExtra::Cancel => {
|
||||
@ -327,8 +342,12 @@ fn create_flow(
|
||||
let initial_page: &dyn FlowController = match (extra, prompt_screen.is_some()) {
|
||||
(ConfirmActionExtra::Menu { .. }, false) => &ConfirmActionWithMenu::Action,
|
||||
(ConfirmActionExtra::Menu { .. }, true) => &ConfirmActionWithMenuAndConfirmation::Action,
|
||||
(ConfirmActionExtra::Cancel, false) => &ConfirmAction::Action,
|
||||
(ConfirmActionExtra::Cancel, true) => &ConfirmActionWithConfirmation::Action,
|
||||
(ConfirmActionExtra::Cancel | ConfirmActionExtra::ExternalMenu, false) => {
|
||||
&ConfirmAction::Action
|
||||
}
|
||||
(ConfirmActionExtra::Cancel | ConfirmActionExtra::ExternalMenu, true) => {
|
||||
&ConfirmActionWithConfirmation::Action
|
||||
}
|
||||
};
|
||||
|
||||
(
|
||||
|
@ -61,17 +61,19 @@ impl FirmwareUI for UIDelizia {
|
||||
reverse: bool,
|
||||
prompt_screen: bool,
|
||||
prompt_title: Option<TString<'static>>,
|
||||
external_menu: bool, // TODO: will eventually replace the internal menu
|
||||
) -> Result<impl LayoutMaybeTrace, Error> {
|
||||
let flow = flow::confirm_action::new_confirm_action(
|
||||
title,
|
||||
action,
|
||||
description,
|
||||
subtitle,
|
||||
verb_cancel,
|
||||
if external_menu { None } else { verb_cancel },
|
||||
reverse,
|
||||
hold,
|
||||
prompt_screen,
|
||||
prompt_title.unwrap_or(TString::empty()),
|
||||
external_menu,
|
||||
)?;
|
||||
Ok(flow)
|
||||
}
|
||||
|
@ -57,6 +57,7 @@ impl FirmwareUI for UIEckhart {
|
||||
reverse: bool,
|
||||
_prompt_screen: bool,
|
||||
_prompt_title: Option<TString<'static>>,
|
||||
_external_menu: bool, // TODO: will eventually replace the internal menu
|
||||
) -> Result<impl LayoutMaybeTrace, Error> {
|
||||
let paragraphs = {
|
||||
let action = action.unwrap_or("".into());
|
||||
|
@ -32,6 +32,7 @@ pub trait FirmwareUI {
|
||||
reverse: bool,
|
||||
prompt_screen: bool,
|
||||
prompt_title: Option<TString<'static>>,
|
||||
external_menu: bool, // TODO: will eventually replace the internal menu
|
||||
) -> Result<impl LayoutMaybeTrace, Error>;
|
||||
|
||||
fn confirm_address(
|
||||
|
@ -110,6 +110,7 @@ def confirm_action(
|
||||
reverse: bool = False,
|
||||
prompt_screen: bool = False,
|
||||
prompt_title: str | None = None,
|
||||
external_menu: bool = False,
|
||||
) -> LayoutObj[UiResult]:
|
||||
"""Confirm action."""
|
||||
|
||||
|
@ -39,28 +39,48 @@ def confirm_action(
|
||||
prompt_screen: bool = False,
|
||||
prompt_title: str | None = None,
|
||||
) -> Awaitable[None]:
|
||||
from trezor.ui.layouts.menu import Menu, confirm_with_menu
|
||||
|
||||
if description is not None and description_param is not None:
|
||||
description = description.format(description_param)
|
||||
|
||||
return raise_if_not_confirmed(
|
||||
trezorui_api.confirm_action(
|
||||
title=title,
|
||||
action=action,
|
||||
description=description,
|
||||
subtitle=subtitle,
|
||||
verb=verb,
|
||||
verb_cancel=verb_cancel,
|
||||
hold=hold,
|
||||
hold_danger=hold_danger,
|
||||
reverse=reverse,
|
||||
prompt_screen=prompt_screen,
|
||||
prompt_title=prompt_title or title,
|
||||
),
|
||||
br_name,
|
||||
br_code,
|
||||
exc,
|
||||
flow = trezorui_api.confirm_action(
|
||||
title=title,
|
||||
action=action,
|
||||
description=description,
|
||||
subtitle=subtitle,
|
||||
verb=verb,
|
||||
verb_cancel=verb_cancel,
|
||||
hold=hold,
|
||||
hold_danger=hold_danger,
|
||||
reverse=reverse,
|
||||
prompt_screen=prompt_screen,
|
||||
prompt_title=prompt_title or title,
|
||||
external_menu=not (prompt_screen or hold),
|
||||
)
|
||||
|
||||
if prompt_screen or hold:
|
||||
# Note: multi-step confirm (prompt_screen/hold)
|
||||
# can't work with external menus yet
|
||||
return raise_if_not_confirmed(
|
||||
flow,
|
||||
br_name,
|
||||
br_code,
|
||||
exc,
|
||||
)
|
||||
else:
|
||||
menu = Menu.root(
|
||||
cancel=verb_cancel or TR.buttons__cancel,
|
||||
)
|
||||
|
||||
return confirm_with_menu(
|
||||
flow,
|
||||
menu,
|
||||
br_name,
|
||||
br_code,
|
||||
exc,
|
||||
)
|
||||
|
||||
|
||||
def confirm_single(
|
||||
br_name: str,
|
||||
|
Loading…
Reference in New Issue
Block a user