Existe-t-il un moyen de changer la couleur d'arrière-plan du bouton en relief en dégradé? sinon, comment puis-je réaliser quelque chose comme ça?
Vous pouvez en créer un vous-même
class RaisedGradientButton extends StatelessWidget {
final Widget child;
final Gradient gradient;
final double width;
final double height;
final Function onPressed;
const RaisedGradientButton({
Key key,
@required this.child,
this.gradient,
this.width = double.infinity,
this.height = 50.0,
this.onPressed,
}) : super(key: key);
@override
Widget build(BuildContext context) {
return Container(
width: width,
height: 50.0,
decoration: BoxDecoration(gradient: gradient, boxShadow: [
BoxShadow(
color: Colors.grey[500],
offset: Offset(0.0, 1.5),
blurRadius: 1.5,
),
]),
child: Material(
color: Colors.transparent,
child: InkWell(
onTap: onPressed,
child: Center(
child: child,
)),
),
);
}
}
Et utilisez-le n'importe où comme suit:
RaisedGradientButton(
child: Text(
'Button',
style: TextStyle(color: Colors.white),
),
gradient: LinearGradient(
colors: <Color>[Colors.green, Colors.black],
),
onPressed: (){
print('button clicked');
}
),
Vous pouvez continuer à jouer avec l'ombre et les bordures arrondies en modifiant la propriété de décoration du conteneur jusqu'à ce qu'elle corresponde à vos spécifications.
Toutes les solutions ci-dessus ne fonctionnent pas vraiment sans quelques artefacts ou problèmes mineurs (par exemple, effet d'entraînement manquant, bordures indésirables, ne respectant pas le thème minWidth pour les boutons).
La solution ci-dessous ne présente aucun des problèmes ci-dessus (la partie critique consiste à utiliser le widget Ink
pour conserver les capacités d'ondulation sur le gradient ):
RaisedButton(
onPressed: () { },
shape: RoundedRectangleBorder(borderRadius: BorderRadius.circular(80.0)),
padding: const EdgeInsets.all(0.0),
child: Ink(
decoration: const BoxDecoration(
gradient: myGradient,
borderRadius: BorderRadius.all(Radius.circular(80.0)),
),
child: Container(
constraints: const BoxConstraints(minWidth: 88.0, minHeight: 36.0), // min sizes for Material buttons
alignment: Alignment.center,
child: const Text(
'OK',
textAlign: TextAlign.center,
),
),
),
)
Se référer ci-dessous -
RaisedButton(
onPressed: () {},
textColor: Colors.white,
padding: const EdgeInsets.all(0.0),
shape:RoundedRectangleBorder(borderRadius: BorderRadius.circular(80.0)),
child: Container(
decoration: const BoxDecoration(
gradient: LinearGradient(
colors: <Color>[
Color(0xFF0D47A1),
Color(0xFF1976D2),
Color(0xFF42A5F5),
],
),
borderRadius: BorderRadius.all(Radius.circular(80.0))
),
padding: const EdgeInsets.fromLTRB(20, 10, 20, 10),
child: const Text(
'Gradient Button',
style: TextStyle(fontSize: 20)
),
),
)
Gradient le package est disponible dans un pub store qui prend en charge quelques gradients prédéfinis
Vous pouvez créer le bouton dégradé comme
GradientButton(
child: Text('Gradient'),
callback: () {},
gradient: Gradients.backToFuture,
),
Le package contient GradientCard, GradientProgressIndicator, GradientButton, CircularGradientButton et GradientText
Créez simplement un conteneur supplémentaire en tant qu'enfant, définissez la décoration de ce conteneur et créez une couleur dégradée comme vous le souhaitez
Puis après cette utilisation RaisedButton en tant qu'enfant du conteneur ci-dessus comme avec MaterialButton aussi
child: Container(
decoration: BoxDecoration(
gradient: LinearGradient(
colors: [Colors.red, Colors.blue],
begin: FractionalOffset(0.0, 0.0),
end: FractionalOffset(0.5, 0.0),
stops: [0.0, 1.0],
tileMode: TileMode.clamp),
),
child: RaisedButton(
color: Colors.transparent,
child: Text("Ask Permssion"),
onPressed: () {
askPermission();
},
)),
Sortie:
Le doc API Flutter a un exemple de la façon de rendre un RaisedButton
avec un fond dégradé - voir ici https://api.flutter.dev/flutter/material/RaisedButton-class.html
Widget gradientButton = Container(
child: RaisedButton(
onPressed: () { },
textColor: Colors.white,
padding: const EdgeInsets.all(0.0),
child: Container(
width: 300,
decoration: new BoxDecoration(
gradient: new LinearGradient(
colors: [
Color.fromARGB(255, 148, 231, 225),
Color.fromARGB(255, 62, 182, 226)
],
)
),
padding: const EdgeInsets.all(10.0),
child: Text(
"Gradient Button",
textAlign: TextAlign.center,
),
),
),
);
Vous pouvez utiliser un moyen plus simple en utilisant RawMaterialButton
de material.Dart
, vous pouvez également créer une forme arrondie ou circulaire. en voici un exemple simple.
Card(
elevation: 7,
child: Container(
width: 120.0,
height: 75.0,
decoration: BoxDecoration(
gradient: LinearGradient(
begin: Alignment.bottomLeft,
end: Alignment.topRight,
colors: <Color>[
Colors.blue,
Colors.red,
],
),
),
child: RawMaterialButton(
onPressed: () {},
splashColor: Colors.grey,
child: Text(
"Button",
style: TextStyle(color: Colors.white, fontSize: 20.0),
),
),
),
),
Dernier exemple de la documentation https://api.flutter.dev/flutter/material/RaisedButton-class.html
RaisedButton(
onPressed: () {},
textColor: Colors.white,
padding: const EdgeInsets.all(0.0),
child: Container(
decoration: const BoxDecoration(
gradient: LinearGradient(
colors: <Color>[
Color(0xFF0D47A1),
Color(0xFF1976D2),
Color(0xFF42A5F5),
],
),
),
padding: const EdgeInsets.all(10.0),
child: const Text(
'Gradient Button',
style: TextStyle(fontSize: 20)
),
),
);
Je sais que cette question est un peu ancienne .. Mais je me suis retrouvé avec cette exigence et je voulais partager ma solution. Il utilise un Card
et anime l'élévation lorsque le bouton est enfoncé.
import 'package:flutter/material.Dart';
class GradientButton extends StatefulWidget {
final String label;
final VoidCallback onPressed;
final Gradient gradient;
final double elevation;
final double height;
final TextStyle labelStyle;
GradientButton({
@required this.label,
@required this.onPressed,
@required this.gradient,
this.elevation,
this.height,
this.labelStyle,
}) : assert(label != null && onPressed != null),
assert(gradient != null);
@override
_GradientButtonState createState() => _GradientButtonState();
}
class _GradientButtonState extends State<GradientButton> with TickerProviderStateMixin {
AnimationController _animationController;
Animation _animation;
elevateUp(TapDownDetails details) {
_animationController.forward();
}
elevateDown() {
_animationController.reverse();
}
@override
void initState() {
super.initState();
_animationController = AnimationController(duration: Duration(milliseconds: 50), vsync: this);
_animation = Tween(begin: widget.elevation ?? 2.0, end: 12.0).animate(_animationController);
}
@override
Widget build(BuildContext context) {
return AnimatedBuilder(
animation: _animation,
builder: (c, w) {
return GestureDetector(
onTapDown: elevateUp,
onTapCancel: elevateDown,
onTapUp: (value) {
elevateDown();
widget.onPressed();
},
child: Card(
elevation: _animation.value,
shape: RoundedRectangleBorder(
borderRadius: BorderRadius.circular(25.0),
),
child: Container(
width: double.infinity,
height: widget.height ?? 50.0,
decoration: BoxDecoration(
gradient: widget.gradient,
borderRadius: BorderRadius.circular(25.0),
),
child: Center(
child: Text(
widget.label,
style: widget.labelStyle ?? Theme.of(context).textTheme.button,
),
),
),
),
);
},
);
}
}
Il y a de la place pour l'améliorer (peut-être que vous ne voulez pas ces bordures arrondies par défaut), mais l'espoir peut être utile pour certains d'entre vous: D