From 30e88f4641d2952564e3486999151454b1778d23 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Ioan=20Biz=C4=83u?= Date: Thu, 16 Jan 2025 11:53:58 +0100 Subject: [PATCH] fix(core/ui): make button press cancel current hold --- core/.changelog.d/3772.fixed | 1 + core/embed/rust/src/ui/event/button.rs | 2 ++ .../component/button_controller.rs | 29 ++++++++++++++----- .../component/hold_to_confirm.rs | 3 ++ .../src/ui/layout_samson/component/loader.rs | 22 +++++++++----- 5 files changed, 43 insertions(+), 14 deletions(-) create mode 100644 core/.changelog.d/3772.fixed diff --git a/core/.changelog.d/3772.fixed b/core/.changelog.d/3772.fixed new file mode 100644 index 0000000000..75d35009fe --- /dev/null +++ b/core/.changelog.d/3772.fixed @@ -0,0 +1 @@ +[T3B1] Fix behavior of a button press during "hold to confirm". diff --git a/core/embed/rust/src/ui/event/button.rs b/core/embed/rust/src/ui/event/button.rs index cb0f934356..04d0e32abc 100644 --- a/core/embed/rust/src/ui/event/button.rs +++ b/core/embed/rust/src/ui/event/button.rs @@ -12,8 +12,10 @@ pub enum ButtonEvent { /// Button released up. /// ▲ * | * ▲ ButtonReleased(PhysicalButton), + HoldStarted, HoldEnded, + HoldCanceled, } impl ButtonEvent { diff --git a/core/embed/rust/src/ui/layout_samson/component/button_controller.rs b/core/embed/rust/src/ui/layout_samson/component/button_controller.rs index 4d3463c980..1c1a9339d6 100644 --- a/core/embed/rust/src/ui/layout_samson/component/button_controller.rs +++ b/core/embed/rust/src/ui/layout_samson/component/button_controller.rs @@ -215,19 +215,26 @@ impl ButtonContainer { self.long_pressed_timer.expire(event) } - /// Registering hold event. + /// Registering the hold event pub fn hold_started(&mut self, ctx: &mut EventCtx) { if let ButtonType::HoldToConfirm(htc) = &mut self.button_type { htc.event(ctx, Event::Button(ButtonEvent::HoldStarted)); } } - /// Cancelling hold event. + /// Ending the hold event by releasing the button held pub fn hold_ended(&mut self, ctx: &mut EventCtx) { if let ButtonType::HoldToConfirm(htc) = &mut self.button_type { htc.event(ctx, Event::Button(ButtonEvent::HoldEnded)); } } + + /// Canceling the hold event + pub fn hold_canceled(&mut self, ctx: &mut EventCtx) { + if let ButtonType::HoldToConfirm(htc) = &mut self.button_type { + htc.event(ctx, Event::Button(ButtonEvent::HoldCanceled)); + } + } } /// Component responsible for handling buttons. @@ -469,11 +476,19 @@ impl Component for ButtonController { Some(ButtonControllerMsg::Pressed(ButtonPos::Middle)), ) } else { - self.got_pressed(ctx, b.into()); - ( - ButtonState::BothDown, - Some(ButtonControllerMsg::Pressed(b.into())), - ) + // When a button gets pressed while another one is being held, + // cancel the hold and do not register the press. + match which_down { + PhysicalButton::Left => { + self.left_btn.hold_canceled(ctx); + } + PhysicalButton::Right => { + self.right_btn.hold_canceled(ctx); + } + _ => {} + } + + return None; } } _ => (self.state, None), diff --git a/core/embed/rust/src/ui/layout_samson/component/hold_to_confirm.rs b/core/embed/rust/src/ui/layout_samson/component/hold_to_confirm.rs index 7857c864a0..9ae98b2c03 100644 --- a/core/embed/rust/src/ui/layout_samson/component/hold_to_confirm.rs +++ b/core/embed/rust/src/ui/layout_samson/component/hold_to_confirm.rs @@ -105,6 +105,9 @@ impl Component for HoldToConfirm { self.loader.start_shrinking(ctx, Instant::now()); } } + Event::Button(ButtonEvent::HoldCanceled) => { + self.loader.shrink_completely(ctx, Instant::now()); + } _ => {} }; diff --git a/core/embed/rust/src/ui/layout_samson/component/loader.rs b/core/embed/rust/src/ui/layout_samson/component/loader.rs index 70f2469db9..703b413a15 100644 --- a/core/embed/rust/src/ui/layout_samson/component/loader.rs +++ b/core/embed/rust/src/ui/layout_samson/component/loader.rs @@ -107,13 +107,13 @@ impl Loader { ctx.request_paint(); } - pub fn start_shrinking(&mut self, ctx: &mut EventCtx, now: Instant) { - let mut anim = Animation::new( - display::LOADER_MAX, - display::LOADER_MIN, - self.shrinking_duration, - now, - ); + fn start_shrinking_with_duration( + &mut self, + ctx: &mut EventCtx, + now: Instant, + duration: Duration, + ) { + let mut anim = Animation::new(display::LOADER_MAX, display::LOADER_MIN, duration, now); if let State::Growing(growing) = &self.state { anim.seek_to_value(display::LOADER_MAX - growing.value(now)); } @@ -125,6 +125,14 @@ impl Loader { ctx.request_paint(); } + pub fn start_shrinking(&mut self, ctx: &mut EventCtx, now: Instant) { + self.start_shrinking_with_duration(ctx, now, self.shrinking_duration); + } + + pub fn shrink_completely(&mut self, ctx: &mut EventCtx, now: Instant) { + self.start_shrinking_with_duration(ctx, now, Duration::from_millis(0)); + } + pub fn reset(&mut self) { self.state = State::Initial; }