-
Notifications
You must be signed in to change notification settings - Fork 29.7k
[Material] Update slider and slider theme with new sizes, shapes, and color mappings #30390
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Conversation
rami-a
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
LGTM from as much as I know about sliders
| bool isEnabled, | ||
| bool isDiscrete, | ||
| }) { | ||
| isEnabled = isEnabled ?? false; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can these 2 be set to false as default values in the param list instead of here?
| bool isEnabled, | ||
| bool isDiscrete, | ||
| }) { | ||
| isEnabled = isEnabled ?? false; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can these 2 be set to false as default values in the param list instead of here?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Done
| } | ||
|
|
||
| // The following shapes are the material defaults. | ||
| /// Base track shape with default sizing. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Explain just a little more in the first line of the description.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Done
| /// | ||
| /// See also: | ||
| /// | ||
| /// * [Slider] for the component that this is meant to display this shape. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Grammar
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Fixed this, and where it was in other places. Also updated these to follow the "See also" pattern so its more consistent throughout this file.
| /// See also: | ||
| /// | ||
| /// * [Slider] for the component that this is meant to display this shape. | ||
| /// * [SliderThemeData] where an instance of this class is set to inform the |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Capitalize the W in Where
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Changed to adding a comma after the [Foo] to be consistent with the other "See also" sections
| /// shapes. | ||
| /// * [RectangularSliderTrackShape] for a similar track with blunt edges. | ||
| class RoundedRectSliderTrackShape extends SliderTrackShape with BaseSliderTrackShape { | ||
| /// Create a slider track that draws 2 rectangles with rounded outer edges. |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
2 => two
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Done
| return; | ||
| } | ||
|
|
||
| // Assign the track segment paints, which are left: active, right: inactive, |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Are the left and right in RTL?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
And I see one line below that they are.
Change this to leading and trailing instead of right and left and you get all that for free.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I mean the comments will be clear without having to say what happens in RTL.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It is noted that it is reversed for RTL on the next line
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Done
willlarche
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Thank you! It's a big one!!
| isDiscrete: isDiscrete, | ||
| ); | ||
|
|
||
| final Rect leftTrackArcRect = Rect.fromLTWH(trackRect.left, trackRect.top, trackRect.height, trackRect.height); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can you add a comment explaining why you have the height for both width and height/
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Done
| log.clear(); | ||
| }); | ||
|
|
||
| // TODO(clocksmith): delete this test in favor of something in slider_theme_test |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Is this stale?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yes, thanks. Deleted.
| ), | ||
| )); | ||
| expect(tester.renderObject<RenderBox>(find.byType(Slider)).size, const Size(144.0 + 2.0 * 16.0, 600.0)); | ||
| expect(tester.renderObject<RenderBox>(find.byType(Slider)).size, const Size(144.0 + 2.0 * 24.0, 600.0)); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Anywhere you're doing math, you can drop the .0s.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Keeping for consistency within file.
HansMuller
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Everything looks pretty good.
It would be useful to include a regression test that verifies (as best we can) that the new dimensions and appearance of a default enabled/disabled slider never changes. Although this could be done with a golden image test, a unit test would be better at pinpointing the source of regressions. I added similar tests for buttons recently: https://github.com/flutter/flutter/blob/master/packages/flutter/test/material/buttons_test.dart#L18
| // colors come from the ThemeData.colorScheme. These colors, along with | ||
| // the default shapes and text styles are aligned to the Material | ||
| // Guidelines. | ||
| sliderTheme = sliderTheme.copyWith( |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This is OK, since it's straightforward, although it's a bit of a monster. If we added a SliderTheme.merge() method that only changed null properties, then what's going on it might be a little clearer:
final SliderThemeData sliderTheme = SliderTheme.of(
// Non-null widget properties override SliderTheme values.
.copyWith(
activeTrackColor: widget.activeColor,
inactiveTrackColor: widget.inactiveColor,
activeTickMarkColor: widget.inactiveColor,
inactiveTickMarkColor: widget.activeColor,
thumbColor: widget.activeColor,
overlayColor: widget.activeColor?.withOpacity(0.12),
valueIndicatorColor: widget.activeColor)
// Default all of the remaining null SliderTheme properties.
.merge(
activeTrackColor: theme.colorScheme.primary,
inactiveTrackColor: theme.colorScheme.primary.withOpacity(0.24),
disabledActiveTrackColor: theme.colorScheme.onSurface.withOpacity(0.32),
disabledInactiveTrackColor: theme.colorScheme.onSurface.withOpacity(0.12),
activeTickMarkColor: theme.colorScheme.onPrimary.withOpacity(0.54),
inactiveTickMarkColor: theme.colorScheme.primary.withOpacity(0.54),
disabledActiveTickMarkColor: theme.colorScheme.onPrimary.withOpacity(0.12),
disabledInactiveTickMarkColor: theme.colorScheme.onSurface.withOpacity(0.12),
thumbColor: theme.colorScheme.primary,
disabledThumbColor: theme.colorScheme.onSurface.withOpacity(0.38),
overlayColor: theme.colorScheme.primary.withOpacity(0.12),
valueIndicatorColor: theme.colorScheme.primary,
trackShape: _defaultTrackShape,
tickMarkShape: _defaultTickMarkShape,
thumbShape: _defaultThumbShape,
overlayShape: _defaultOverlayShape,
valueIndicatorShape: _defaultValueIndicatorShape,
showValueIndicator:_defaultShowValueIndicator,
valueIndicatorTextStyle: theme.textTheme.body2.copyWith(color: theme.colorScheme.onPrimary),
);
)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
After some experimentation, I do not think the .merge method needed would be similar enough to the merge on TextTheme and TextStyle, so it might be confusing to have .merge methods in different objects that behave differently.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I agree that we haven't established a consistent meaning for "merge" methods and adding one here that works like ListTileTheme.merge but not like TextStyle.merge or Border.merge will not help matters.
We can solve the general problem and then update this monster in a separate PR.
| /// Base track shape that provides an implementation of [getPreferredRect] for | ||
| /// default sizing. | ||
| /// | ||
| /// The [SliderTrackShape]s that use this base class are: |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This shouldn't be needed, DartDoc will generate a list of implementers. A "See also" section that named these subclasses and provided a one-liner explanation of what they mean would be useful.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Done
| /// [parentBox], but is padded by the larger of [RoundSliderOverlayShape] | ||
| /// radius and [RoundSliderThumbShape]. The height is defined by the | ||
| /// [SliderThemeData.trackHeight]. The color is determined by the [Slider]'s | ||
| /// enabled state and the track piece's active state which are defined by: |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
"track piece"?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Updated
| bool isEnabled = false, | ||
| bool isDiscrete = false, | ||
| }) { | ||
| final double thumbWidth = sliderTheme.thumbShape.getPreferredSize(isEnabled, isDiscrete).width; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
assert sliderTheme != null etc. Here and elsewhere.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Done in all getPreferredFoo and paint methods
| // TODO(clocksmith): This needs to be changed to 10 according to spec. | ||
| const RoundSliderThumbShape({ | ||
| this.enabledThumbRadius = 6.0, | ||
| this.enabledThumbRadius = 10.0, |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The doc for the enabledThumbRadius property should admit that the default is 10
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Done
| final Offset bottomKnobStart = Offset( | ||
| _bottomLobeRadius * math.cos(_bottomLobeStartAngle), | ||
| _bottomLobeRadius * math.sin(_bottomLobeStartAngle), | ||
| _bottomLobeRadius * math.sin(_bottomLobeStartAngle) - 2, |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
What's the "-2" doing here (it seems odd to be subtracting 2 from a radians value)? It's OK to say that it was derived "experimentally" so long as we explain what effect it has.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It is the y value of the offset, it was experimentally to get the bottom lobe in the right place after adjusting the lobe radius
HansMuller
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
LGTM
| // colors come from the ThemeData.colorScheme. These colors, along with | ||
| // the default shapes and text styles are aligned to the Material | ||
| // Guidelines. | ||
| sliderTheme = sliderTheme.copyWith( |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I agree that we haven't established a consistent meaning for "merge" methods and adding one here that works like ListTileTheme.merge but not like TextStyle.merge or Border.merge will not help matters.
We can solve the general problem and then update this monster in a separate PR.
… color mappings (2nd attempt) (#31564) #30390 was rolled back. This PR will re-roll it forward. This PR makes a number of changes to the visual appearance of material sliders: Sizes/Shapes ** enabled thumb radius from 6 to 10 ** disabled thumb radius from 4 to 10 with no gap ** default track shape is a rounded rect rather than a rect ** Colors ** all of the colors now use the new color scheme ** overlay opacity has been reduce from 16% to 12% ** value indicator text color now respects the indicator it is on by using onPrimary ** disabledThumb color no respects the surface it is on by using onSurface The slider theme is also now constructed consistently with other theme objects within the ThemeData. By default, all values are null, and have default values that are resolved in the slider itself, rather than in the slider theme.
Description
This PR makes a number of changes to the visual appearance of material sliders:
** enabled thumb radius from 6 to 10
** disabled thumb radius from 4 to 10 with no gap
** default track shape is a rounded rect rather than a rect
**
** all of the colors now use the new color scheme
** overlay opacity has been reduce from 16% to 12%
** value indicator text color now respects the indicator it is on by using onPrimary
** disabledThumb color no respects the surface it is on by using onSurface
The slider theme is also now constructed consistently with other theme objects within the ThemeData. By default, all values are null, and have default values that are resolved in the slider itself, rather than in the slider theme.
Related Issues
Closes #28706
Closes #30314
Closes #30315
Closes #30316
Closes #30317
Tests
No new tests were added, but many had to be updated to the new sizes and colors. Tests for default slider theme data property resolving were removed since the SliderThemeData no longer does that.
Checklist
Before you create this PR confirm that it meets all requirements listed below by checking the relevant checkboxes (
[x]). This will ensure a smooth and quick review process.///).flutter analyze --flutter-repo) does not report any problems on my PR.Breaking Change
https://groups.google.com/forum/#!topic/flutter-announce/w5TGYkN7Fe4