Skip to content

[material_ui] Add alternative input method for RangeSlider in NavigationMode.directional - #12630

Merged
auto-submit[bot] merged 9 commits into
flutter:mainfrom
mbcorona:port-187816
Sep 18, 2026
Merged

auto-submit[bot] merged 9 commits into
flutter:mainfrom
mbcorona:port-187816

Conversation

@mbcorona

@mbcorona mbcorona commented Aug 26, 2026 •

Copy link
Copy Markdown
Member

Ports flutter/flutter#187816 to material_ui, following the instructions in flutter/flutter#188444. The commits were cherry-picked from the original PR, with only file paths and imports adjusted for this repo.

In NavigationMode.directional (TV remotes, D-pads) the arrow keys are needed to move focus between views, so a focused RangeSlider thumb had no way to adjust its value. This adds the pattern discussed in flutter/flutter#181968:

  • Arrow keys only move focus.
  • Enter on a focused thumb enters a value adjustment mode, where Left and Right adjust the value.
  • Enter again, or losing focus, exits that mode.

NavigationMode.traditional is unchanged: arrow keys adjust the value directly. This mirrors the keyboard handling Slider already has in this package.

Tests

New test group RangeSlider keyboard with NavigationMode.directional in packages/material_ui/test/range_slider_test.dart, covering each case above plus traditional navigation.

Fixes flutter/flutter#181968

Supersedes flutter/flutter#187816, which will be closed with a pointer to this PR.

Pre-Review Checklist

If you need help, consider asking for advice on the #hackers-new channel on Discord.

Note: The Flutter team is currently trialing the use of Gemini Code Assist for GitHub. Comments from the gemini-code-assist bot should not be taken as authoritative feedback from the Flutter team. If you find its comments useful you can update your code accordingly, but if you are unsure or disagree with the feedback, please feel free to wait for a Flutter team member's review for guidance on which automated comments should be addressed.

Footnotes

  1. Regular contributors who have demonstrated familiarity with the repository guidelines only need to comment if the PR is not auto-exempted by repo tooling. ↩ ↩2

@flutter-dashboard flutter-dashboard Bot added the CICD Run CI/CD label Aug 26, 2026
@github-actions github-actions Bot added p: material_ui triage-design Should be looked at in design triage labels Aug 26, 2026

@gemini-code-assist gemini-code-assist Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Code Review

This pull request introduces alternative keyboard input support for RangeSlider when operating in NavigationMode.directional. It adds a toggleable value-adjustment mode to allow arrow keys to either navigate focus or adjust the slider values, along with corresponding tests and a changelog entry. Feedback suggests implementing defensive null checks in _actionHandler instead of using null-assertion operators to prevent potential runtime exceptions if the widget is unmounted.

Comment on lines +680 to +695
void _actionHandler(_AdjustSliderIntent intent, Thumb thumb) {
final slider = _renderObjectKey.currentContext!.findRenderObject()! as _RenderRangeSlider;
final TextDirection directionality = Directionality.of(_renderObjectKey.currentContext!);
final bool increase = switch (intent.type) {
_SliderAdjustmentType.up => true,
_SliderAdjustmentType.down => false,
_SliderAdjustmentType.left => directionality == TextDirection.rtl,
_SliderAdjustmentType.right => directionality == TextDirection.ltr,
};
switch (thumb) {
case Thumb.start:
increase ? slider.increaseStartAction() : slider.decreaseStartAction();
case Thumb.end:
increase ? slider.increaseEndAction() : slider.decreaseEndAction();
}
}

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

medium

Using the null-assertion operator ! on _renderObjectKey.currentContext and findRenderObject() can lead to runtime exceptions if the widget is ever unmounted or in a teardown state when an action is triggered. Following defensive programming practices, it is safer to perform null checks before accessing these properties.

  void _actionHandler(_AdjustSliderIntent intent, Thumb thumb) {
    final BuildContext? context = _renderObjectKey.currentContext;
    if (context == null) {
      return;
    }
    final RenderObject? renderObject = context.findRenderObject();
    if (renderObject == null) {
      return;
    }
    final _RenderRangeSlider slider = renderObject as _RenderRangeSlider;
    final TextDirection directionality = Directionality.of(context);
    final bool increase = switch (intent.type) {
      _SliderAdjustmentType.up => true,
      _SliderAdjustmentType.down => false,
      _SliderAdjustmentType.left => directionality == TextDirection.rtl,
      _SliderAdjustmentType.right => directionality == TextDirection.ltr,
    };
    switch (thumb) {
      case Thumb.start:
        increase ? slider.increaseStartAction() : slider.decreaseStartAction();
      case Thumb.end:
        increase ? slider.increaseEndAction() : slider.decreaseEndAction();
    }
  }

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This mirrors the existing pattern in Slider._actionHandler in this package (slider.dart), which this PR intentionally follows per the porting guidelines. If the defensive style is preferred, I'd suggest changing both Slider and RangeSlider together in a follow-up for consistency.

@QuncCccccc QuncCccccc changed the title [material_ui] Port flutter/flutter #187816 "Add alternative input method for RangeSlider in NavigationMode.directional" [material_ui] Add alternative input method for RangeSlider in NavigationMode.directional Sep 3, 2026
@QuncCccccc QuncCccccc changed the title [material_ui] Add alternative input method for RangeSlider in NavigationMode.directional [material_ui] Add alternative input method for RangeSlider in NavigationMode.directional Sep 3, 2026
@elliette

elliette commented Sep 3, 2026

Copy link
Copy Markdown
Member

Oops didn't notice the original PR was already being reviewed by @navaronbracke - @navaronbracke I've assigned you as reviewer but please let us know if you don't have the bandwidth at the moment and we'll take a look! Thank you :)

@elliette
elliette requested review from navaronbracke and removed request for QuncCccccc and elliette September 3, 2026 18:28

@navaronbracke navaronbracke left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Just some minor nits on the test

Comment thread packages/material_ui/lib/src/range_slider.dart Outdated
Comment thread packages/material_ui/lib/src/range_slider.dart Outdated
Comment thread packages/material_ui/test/range_slider_test.dart
Comment thread packages/material_ui/test/range_slider_test.dart
Comment thread packages/material_ui/test/range_slider_test.dart
@mbcorona mbcorona added the autosubmit Merge PR when tree becomes green via auto submit App label Sep 8, 2026
@auto-submit auto-submit Bot removed the autosubmit Merge PR when tree becomes green via auto submit App label Sep 8, 2026
@auto-submit

auto-submit Bot commented Sep 8, 2026

Copy link
Copy Markdown
Contributor

autosubmit label was removed for flutter/packages/12630, because - The status or check suite Dashboard Checks has failed. Please fix the issues identified (or deflake) before re-applying this label.

@navaronbracke

Copy link
Copy Markdown
Contributor

FYI: dashboard checks is failing for the same reason as to why the tree is red right now.

@mbcorona mbcorona added the autosubmit Merge PR when tree becomes green via auto submit App label Sep 8, 2026
@auto-submit auto-submit Bot removed the autosubmit Merge PR when tree becomes green via auto submit App label Sep 8, 2026
@auto-submit

auto-submit Bot commented Sep 8, 2026

Copy link
Copy Markdown
Contributor

autosubmit label was removed for flutter/packages/12630, because - The status or check suite Dashboard Checks has failed. Please fix the issues identified (or deflake) before re-applying this label.

@mbcorona

Copy link
Copy Markdown
Member Author

Hi @navaronbracke , I adjusted some tests, but it looks like the Dashboard checks are still failing.

@navaronbracke

Copy link
Copy Markdown
Contributor

https://flutter-dashboard.appspot.com/#/presubmit?repo=packages&pr=12630&sha=ac9e232eca4fc27b3e72f48089bcaa759fa95d6a&job=Mac_x64%20ios_build_all_packages%20master

Shows that it is unrelated to your change, though. (you can inspect failures like these by clicking the three dots in the GH action line, then via "view more details on flutter-dashboard" you can select the same task again to get logs)

This task appears to have been cancelled? Other PR's after this one don't hit this, so I'd push an empty commit to rerun?

@mbcorona mbcorona added the autosubmit Merge PR when tree becomes green via auto submit App label Sep 18, 2026
@auto-submit
auto-submit Bot merged commit 8f96e69 into flutter:main Sep 18, 2026
13 checks passed
pull Bot pushed a commit to edisplay/flutter that referenced this pull request Sep 24, 2026
…er#193289)

Roll Packages from c2b58e1a97fb to 431ea69a42e2 (56 revisions)

flutter/packages@c2b58e1...431ea69

2026-09-24 [email protected] [cross_file]
Updates cross_file to a package separated federated plugin
(flutter/packages#11010)
2026-09-23 [email protected] [material_ui]
Remove static access of `copyWith` from `dart fix` golden tests for
`ThemeData/TextTheme` (flutter/packages#12994)
2026-09-23 [email protected] [camera_avfoundation] Replace
deprecated high-resolution capture APIs (flutter/packages#12372)
2026-09-23 [email protected] [pigeon] update nullish checks to use
new isNullish method (flutter/packages#12985)
2026-09-23 [email protected] [ci] Assign batch release PR approver
as reviewer on sync-back PR (flutter/packages#12976)
2026-09-23 [email protected] [image_picker] Fix scaling 10-bit images
(flutter/packages#12557)
2026-09-23 [email protected] [material_ui] Improve
Autocomplete, DrawerHeader, and Tooltip accessibility
(flutter/packages#12918)
2026-09-23 [email protected] [google_fonts] Decouple GoogleFontsLite
for full tree-shaking and add full feature parity
(flutter/packages#12830)
2026-09-23 [email protected] [file_selector]
Ignore flakey `file_selector_android` tests (flutter/packages#12992)
2026-09-23 [email protected] [CI] Remove
bringup from `Mac_arm64 build_all_packages` targets
(flutter/packages#12978)
2026-09-22 [email protected] [material_ui]
Unskip 5 passing web tests in bottom_app_bar_test and text_field_test
(flutter/packages#12983)
2026-09-22 [email protected]
[cupertino_ui] Unskip 5 passing web tests in
adaptive_text_selection_toolbar_test and text_field_test
(flutter/packages#12984)
2026-09-22 [email protected] [go_router] Fix ShellRoute chrome dropped
from semantics tree by ModalBarrier (flutter/packages#12353)
2026-09-22 [email protected] [material_ui]
Add contrastLevel for M3 ColorScheme (flutter/packages#12743)
2026-09-22 [email protected] [go_router] Preserve nested pushes
during config updates (flutter/packages#12611)
2026-09-22 [email protected] [material_ui]
Migrate M3 Chip template to use new gen_defaults
(flutter/packages#12847)
2026-09-22 [email protected] [material_ui] Fix
LocalHistoryEntry leak when double tapping Drawer scrim
(flutter/packages#12552)
2026-09-22 [email protected] Update suggested reviewers
(flutter/packages#12974)
2026-09-22 [email protected] Sync release-material_ui-1.4.0 to
main (flutter/packages#12966)
2026-09-22 [email protected] Sync release-cupertino_ui-1.1.1 to
main (flutter/packages#12965)
2026-09-21 [email protected] [ci] Update repo
for 3.47 stable release (flutter/packages#12959)
2026-09-21 [email protected] Manual roll Flutter from
27fec0e to 4fcd90b (1 revision) (flutter/packages#12904)
2026-09-21 [email protected] Revert "[go_router_builder] Migrate to
material_ui" (flutter/packages#12962)
2026-09-21 [email protected]
[material_ui] Update `material_ui` tests to prevent them from failing
when framework `TextStyle` changes (flutter/packages#12728)
2026-09-21 [email protected] [go_router_builder] Migrate to
material_ui (flutter/packages#12913)
2026-09-21 [email protected] [material_ui,
cupertino_ui] Bump Flutter version from to 3.47 (flutter/packages#12944)
2026-09-21 [email protected] [cupertino_ui] Work around dart2wasm
optional parameter inference bug in example checkbox tests
(flutter/packages#12961)
2026-09-21 [email protected] [cupertino_ui] Work around dart2wasm
optional parameter inference bug in checkbox_test.dart
(flutter/packages#12956)
2026-09-21 [email protected] [google_sign_in] PR 3/4 Migrate
ViewProvider and GID SDK wrappers from Objective-C to Swift
(flutter/packages#12657)
2026-09-21 [email protected] [google_sign_in] PR 2/4 Migrate
the plugin class from Objective-C to Swift. (flutter/packages#12655)
2026-09-20 [email protected]
[cross_file_darwin] iOS/macOS implementation of `cross_file`
(flutter/packages#12910)
2026-09-20 [email protected]
[cross_file_web] Web implementation of `cross_file`
(flutter/packages#12908)
2026-09-20 [email protected] [material_ui]
Migrate M3 `InputChip` template to use new gen_defaults
(flutter/packages#12850)
2026-09-20 [email protected] [material_ui]
Migrate M3 Checkbox defaults to new gen_defaults
(flutter/packages#12816)
2026-09-20 [email protected] [material_ui]
Migrate M3 `FilterChip` template to use new gen_defaults
(flutter/packages#12849)
2026-09-19 [email protected] [material_ui] Announce PopupMenuButton with a
child as a button (flutter/packages#12585)
2026-09-19 [email protected] Roll Flutter (stable) from
9584c67 to 6a19cca (7 revisions) (flutter/packages#12950)
2026-09-18 [email protected] [material_ui]
Reduce the `material_ui` non-wasm web test suite
(flutter/packages#12763)
2026-09-18 [email protected] Replace
`Mac_x64` builders with `Mac_arm64` ones (flutter/packages#12941)
2026-09-18 [email protected]
[in_app_purchase_storekit] Use `_$SKPaymentDiscountWrapperToJson`
(flutter/packages#12721)
2026-09-18 [email protected] [In_app _purchase] README
excerpt examples and changelog (flutter/packages#12739)
2026-09-18 [email protected] [material_ui] Add alternative
input method for `RangeSlider` in `NavigationMode.directional`
(flutter/packages#12630)
2026-09-18 [email protected]
[cross_file_android] Android implementation of `cross_file`
(flutter/packages#12909)
2026-09-18 [email protected]
[camera_platform_interface] Adds videoOutputPath support to
startVideoRecording (flutter/packages#12667)
2026-09-17 [email protected] [cupertino_ui] Migrate a
snippet in `CupertinoCheckbox`'s API doc to `{@example}` and add unit
tests (flutter/packages#12180)
2026-09-17 [email protected] [material_ui]
Default gen_defaults color helper prefix (flutter/packages#12848)
...
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

autosubmit Merge PR when tree becomes green via auto submit App CICD Run CI/CD p: material_ui triage-design Should be looked at in design triage

Projects

None yet

Development

Successfully merging this pull request may close these issues.

RangeSlider needs alternative input method for NavigationMode.directional

3 participants