Repository: zng-ui/zng (language: rust)

Issue:
Auto scroll to focused can override scroll commands
<!--
Please, make sure:

- The issue happens in the latest crate release or newer (master branch).
- The issue happens after `cargo update`.
-->

#### I tried this code:

```rust
fn issue() -> impl UiNode {
    let mut txt = Txt::from("");
    for i in 0..1000 {
        use std::fmt::Write as _;
        writeln!(&mut txt, "Line {i}").unwrap();
    }
    txt.end_mut();
    Scroll! {
        id = "scroll";
        child = Text! {
            id = "focusable";
            zng::focus::focusable = true;
            txt;
        };
        child_bottom = Button!(zng::scroll::cmd::SCROLL_TO_TOP_CMD.scoped("scroll")), 10;
    }
}
```

#### Following these steps:

1 - Run.
2 - Scroll to end (press End).
3 - Click button.

#### I saw this happen:

Scrolls up and down again.

#### I expected this to happen:

Scroll up only.



Discussion / hints:

Fix patch:
diff --git a/CHANGELOG.md b/CHANGELOG.md
index f2ac0ea86..08e16bca8 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -50,8 +50,10 @@ fn version_0_5() -> impl UiNode {
         - Removed `FocusChangedCause::is_prev_request`.
 * Add `FocusChangedCause::request_target` helper method.
 * Add `WidgetPath::parent_id` helper method.
-* Fix auto scroll-to-focused not working when the focused child does not subscribe to focus change events.
-* Fix auto scroll-to-focused scrolling when large widget is already visible.
+* Fix auto scroll to focused issues:
+    - When the focused child does not subscribe to focus change events.
+    - Scrolling when large widget is already visible.
+    - Scrolling again to same widget when focus change event did not represent a widget change.
 * Add `WidgetInfo::spatial_bounds`.
 * Fix directional navigation cycling only inside viewport now full spatial bounds of scopes.
 * Add better conversions for `CommandScope`. You can now scope on named widgets directly, `FOO_CMD.scoped("bar-wgt")`.
diff --git a/crates/zng-wgt-scroll/src/node.rs b/crates/zng-wgt-scroll/src/node.rs
index 7c04efe64..18565136c 100644
--- a/crates/zng-wgt-scroll/src/node.rs
+++ b/crates/zng-wgt-scroll/src/node.rs
@@ -649,7 +649,12 @@ pub fn scroll_to_node(child: impl UiNode) -> impl UiNode {
             let self_id = WIDGET.id();
             if let Some(args) = FOCUS_CHANGED_EVENT.on(update) {
                 if let Some(path) = &args.new_focus {
-                    if (scroll_to.is_none() || !scroll_to_from_cmd) && path.contains(self_id) && path.widget_id() != self_id {
+                    if (scroll_to.is_none() || !scroll_to_from_cmd)
+                        && path.contains(self_id)
+                        && path.widget_id() != self_id
+                        && !args.is_enabled_change()
+                        && !args.is_highlight_changed()
+                    {
                         // focus move inside.
                         if let Some(mode) = SCROLL_TO_FOCUSED_MODE_VAR.get() {
                             // scroll_to_focused enabled


Test patch: