-
Notifications
You must be signed in to change notification settings - Fork 27.5k
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
SplashFactory
in the widgets library
#149963
Conversation
This comment was marked as resolved.
This comment was marked as resolved.
This comment was marked as resolved.
This comment was marked as resolved.
d2ca6ea
to
0cb4025
Compare
BlankMaterial
widgetwidgets
library
9b6bede
to
2795cf3
Compare
This comment was marked as resolved.
This comment was marked as resolved.
This comment was marked as resolved.
This comment was marked as resolved.
This comment was marked as resolved.
This comment was marked as resolved.
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.
@nate-thegrate Have you seen the breaking changes policy? We'll have to follow it if we include these changes that break the Google tests and/or the customer tests. Not saying we shouldn't make these changes though, it could totally be worth it. https://github.com/flutter/flutter/blob/master/docs/contributing/Tree-hygiene.md#handling-breaking-changes
The test failure is caused by Material being changed from a stateful to a stateless widget.
It looks like it would be very easy to migrate the packages repo to fix these breakages, something like this?
- final StatefulElement srcMaterialElement = tester.firstElement(
+ final StatelessElement srcMaterialElement = tester.firstElement(
find.ancestor(
of: find.text('Closed'),
matching: find.byType(Material),
),
);
The other breaking change I see is the removal of debugCheckHasMaterial, which I commented on.
Also @nate-thegrate have you considered using deprecation to mitigate these breaking changes? For example, if we do decide to remove/replace debugCheckHasMaterial, the typical way would be to deprecate it and remove it later.
We could also do something similar for the Stateful=>Stateless breaking change, but it might not be worth it for that one.
Edit: By the way I forgot to say, thank you for the PR! I appreciate you taking a look at the hard problems like this, this is the kind of introspection that Flutter needs to stay great.
Is the discussion about using From #142151:
These are in response to this point:
|
@yakagami thanks for bringing this up! The
I agree with the concern you mentionedβas it is currently, the WidgetStateProperty API feels a bit too clunky. It has a learning curve, and even when you're used to it, it's not super pleasant to look at: InkGestureDetector(
overlayColor: WidgetStateProperty.resolveWith((states) {
if (states.contains(WidgetState.focused) || states.contains(WidgetState.hovered)) {
return Colors.blue;
}
if (states.contains(WidgetState.pressed)) {
return Colors.black;
}
return null;
}),
)
InkGestureDetector(
overlayColor: WidgetStateProperty<Color?>.fromMap({
WidgetState.focused | WidgetState.hovered: Colors.blue,
WidgetState.pressed: Colors.black,
}),
) |
35c5574
to
af3f426
Compare
This comment was marked as outdated.
This comment was marked as outdated.
This comment was marked as resolved.
This comment was marked as resolved.
c16743f
to
342cdb6
Compare
342cdb6
to
80481bd
Compare
Quick status updateβ¦
Let me know what you think! :) |
Preparing for: - flutter/flutter#149963
This comment was marked as outdated.
This comment was marked as outdated.
Earlier this week, I had hopes of splitting this big PR into a couple of smaller PRs, by holding off on migrating to the widgets library. Based on master...nate-thegrate:flutter:SplashFactory-no-migration, unfortunately it'd be splitting 1 big PR into 2 big PRs :( |
'This feature was deprecated after v3.24.0-0.2.pre.', | ||
) | ||
/// An interface for creating ink effects on a [Material]. | ||
typedef MaterialInkController = SplashController; |
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.
Rather than deprecating and typedef-ing this, can it implement the interface and add the addInkFeature
? That way it would not break anyone, and we would not need to add that method as a deprecation in the new class.
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 personally am not worried about breaking anyone here, since data-driven fixes are easy and since interacting with a MaterialInkController
directly is highly unusual.
(As far as implementing the interface, see comment below)
@Deprecated( | ||
'Use addSplash instead. ' | ||
'"Splash effects" no longer rely on a MaterialInkController. ' | ||
'This feature was deprecated after v3.24.0-0.2.pre.', | ||
) | ||
void addInkFeature(Splash feature); |
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.
Since this is a new class, why add something just for it to be deprecated? Let's see if we can make MaterialInkController implement this class instead of a typedef, so this method does not need to be here. It will be less breaking too I think.
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.
Unfortunately, MaterialInkController
was the interface, not the implementation.
Re-implementing the interface within the Material library would involve a lot of duplicated logic, but I do agree that a newly-added deprecated method is very off-putting.
The style guide mentions using extension methods for cases like this one:
Avoid using extension.
Prefer adding methods directly to relevant classes. If that is not possible, create a method that clearly identifies what object(s) it works with and is part of.
(A rare exception can be made for extensions that provide temporary workarounds when deprecating features. In those cases, however, the extensions and all their members must be deprecated in the PR that adds them, and they must be removed in accordance with our deprecation policy.)
The downside of "extension methods aren't easy to discover" isn't much of a downside when the method is deprecated and we'd rather not have people discovering it anyway :)
ErrorHint( | ||
'A SplashController can be provided by an ancestor SplashBox; alternatively, ' | ||
'there are several viable options from the Material libary, including ' | ||
'Material, Card, Dialog, Drawer, and Scaffold.', | ||
), |
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.
If someone is not using the material library, I am not sure if this hint is very helpful.
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.
Fair point, though my guess would be that the majority of the time, the person reading this message is someone using the material library.
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.
Then why are we moving this to the widgets library? :)
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.
Once this migration takes place, I imagine there will be Cupertino widgets that build a SplashBox; once that happens, I think it'd be good to add them to this message.
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.
Would we further alter the error message to account for every widget and library possible? The point I was trying to make was that error messages should be as specific as they can be. Listing widgets that may or may not have to do with the error is not helpful to the user.
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.
+1 on this being a little too specific. You can say something like, "Many existing widgets in Flutter already contain a SplashBox. Alternatively, you can add one yourself."
We maybe should have never had a list of widgets in the original error hint for the material debug check. If something like that changes in the future, I don't trust myself to remember to check the error hints to be correct.
required Offset position, | ||
required Color color, | ||
required TextDirection textDirection, | ||
bool containedInkWell = 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.
This also looks like leakage from Material
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.
β¦well shoot, it looks like deprecating & replacing an abstract method's parameter isn't possible. π
I believe the solution is to use a union type here. An abstract
parent type would probably be ideal for facilitating the migrationβit's not quite as fun as a sealed class
, but not being restricted to a single library means we won't have to bring a bunch of material stuff into the widgets layer!
This would also let us get rid of the useless constructor, so we'll have a clean class with 1 method :)
abstract interface class SplashFactory {
@factory
Splash create( ... );
}
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.
Thanks for catching thisβit very well could have gone unnoticed.
child: _InkFeatures( | ||
key: _inkFeatureRenderer, |
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.
We should rename these, ink is very specifically material.
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's unfortunate that you weren't able to make it to the dash forum where we talked about this process, but I've unresolved an above thread that has the current plan:
- Get a LGTM
- Rename
_RenderInkFeatures
and migrate a whole bunch of tests - Merge
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 a private class being added anew here in the widget layer. We should be able to call it what we intend to call it here. I found no references to _InkFeatures in any tests, which tests are affected by that?
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.
Apologies, it was _RenderInkFeatures
that was causing the issues. Will edit previous comment.
class _RenderInkFeatures extends RenderProxyBox implements SplashController { | ||
_RenderInkFeatures({this.color, required this.vsync}) : super(null); | ||
|
||
/// Enables [InkFeature] animations. |
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.
Same here re: ink references
'Splash effects are no longer exclusive to Material design. ' | ||
'This feature was deprecated after v3.24.0-0.2.pre.', | ||
) | ||
List<Splash> get debugInkFeatures => splashes; |
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.
++
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 one should also be addressed once tests are updated.
1a9e3d5
to
dde079e
Compare
@Piinks and @MitchellGoodwin thank you both very much for the feedback; it feels great to be making progress on this PR after it had been on hold for a while. I'm getting ready to embark on a weekend camping trip; once I'm back I will make updates based on advice given above! |
This pull request has been changed to a draft. The currently pending flutter-gold status will not be able to resolve until a new commit is pushed or the change is marked ready for review again. For more guidance, visit Writing a golden file test for Reviewers: Read the Tree Hygiene page and make sure this patch meets those guidelines before LGTMing. |
2548df3
to
78f166c
Compare
78f166c
to
f4612e7
Compare
Based on the advice given recently, I think maybe the best option is to close this PR and try a different approach: Rather than planning to dump a bunch of test changes here, we could migrate the tests first in their own PR, and then use this pull request as a template for a much cleaner transition :) |
π Link to Design Doc
This pull request transforms ink effects to be completely design system-agnostic.
InkFeature
InteractiveInkFeature
Splash
InteractiveInkFeatureFactory
SplashFactory
SplashBox
MaterialInkController
SplashController
debugCheckHasMaterial
debugCheckSplash
Merging this PR will resolve #147392 and make progress toward #48017.
Handling breakages:
SplashFactory
Β packages#6952SplashBox
breakagesΒ devtools#8176