1. TextButton
在 Flutter 中,TextButton 用于创建一个包含文本的按钮,其想法是创建一个平面按钮,默认情况下高度为 0。但实际上,您可以通过使用 style 属性来自定义其样式。
注意:以前,为了创建平面按钮,我们使用 FlatButton 类。但是,自 2020 年 10 月以来,该类已被标记为过时,并已替换为 TextButton 类。这是 Flutter 开发团队为简化 Flutter API 并使之保持一致所做的努力之一。
TextButton构造函数:
const TextButton({Key key,
@required Widget child,
@required VoidCallback onPressed,
VoidCallback onLongPress,
ButtonStyle style,
FocusNode focusNode,
bool autofocus: false,
Clip clipBehavior: Clip.none
}
)
TextButton 可用于工具栏、对话框等。但有时您需要自定义其样式以避免用户混淆。或者当你作为一个平面按钮使用时,你应该把它放在上下文合适的位置,而不是把它与其他内容混合在一起的TextButton,比如在列表的中间。
TextButton.icon 构造函数:
TextButton.icon(
{Key key,
@required Widget icon,
@required Widget label,
@required VoidCallback onPressed,
VoidCallback onLongPress,
ButtonStyle style,
FocusNode focusNode,
bool autofocus,
Clip clipBehavior}
)
如果 onPressed 和 onLongPress 这两个回调函数都没有指定,TextButton 将被禁用并且触摸时没有响应。
2. 例子
下面是一个包含两个 TextButton 的示例。一种是最简单的TextButton(只包含一个文本标签),另一种是带有backgroundColor和foregroundColor的TextButton。
示例代码如下 -
import 'package:flutter/material.dart';
void main() {
runApp(MyApp());
}
class MyApp extends StatelessWidget {
@override
Widget build(BuildContext context) {
return MaterialApp(
title: 'o7planning',
debugShowCheckedModeBanner: false,
theme: ThemeData(
primarySwatch: Colors.blue,
visualDensity: VisualDensity.adaptivePlatformDensity,
),
home: MyHomePage(),
);
}
}
class MyHomePage extends StatelessWidget {
MyHomePage({Key key}) : super(key: key);
@override
Widget build(BuildContext context) {
return Scaffold(
appBar: AppBar(
title: Text("Flutter TextButton Example")
),
body: Center (
child: Column (
mainAxisAlignment: MainAxisAlignment.spaceAround,
children: [
TextButton (
child: Text("Default TextButton"),
onPressed: () {},
),
TextButton (
child: Text("TextButton With Background and Foreground Color"),
onPressed: () {},
style: ButtonStyle(
backgroundColor: MaterialStateProperty.all<Color>(Colors.greenAccent),
foregroundColor: MaterialStateProperty.all<Color>(Colors.red),
)
)
],
)
)
);
}
}
让 TextButton 包含图标的最方便的方法是使用 TextButton.icon 构造函数。效果如下 -
TextButton.icon (
icon: Icon(Icons.settings),
label: Text("Settings"),
onPressed: () {},
)
3. child属性
child 是 TextButton 最重要的属性。在大多数用例中,它是一个 Text 对象。
@required Widget child
一个简单的子示例是一个文本:
TextButton (
child: Text("Default TextButton"),
onPressed: () {},
)
通过将 Row 对象分配给 child 属性,您可以创建更复杂的 TextButton,例如包含 Icon 和 Text。
// 1 Icon and 1 Text
TextButton (
child: Row (
children: [
Icon(Icons.settings),
SizedBox(width: 5),
Text("Settings")
],
) ,
onPressed: () {},
)
// 2 Icons and 1 Text
TextButton (
child: Row (
children: [
Icon(Icons.directions_bus),
Icon(Icons.train),
SizedBox(width: 5),
Text("Transportation")
],
) ,
onPressed: () {},
)
4. onPressed函数
onPressed 是一个回调函数。当用户单击按钮时调用它。具体来说,当用户完成按下和释放 Button 两个操作时,将发生 onPressed 事件。
@required VoidCallback onPressed
注意:如果 onPressed 和 onLongPress 属性都没有指定,Button 将被禁用并且在触摸时没有响应。
示例代码 -
import 'package:flutter/material.dart';
void main() {
runApp(MyApp());
}
class MyApp extends StatelessWidget {
@override
Widget build(BuildContext context) {
return MaterialApp(
title: 'yiibai.com',
debugShowCheckedModeBanner: false,
theme: ThemeData(
primarySwatch: Colors.blue,
visualDensity: VisualDensity.adaptivePlatformDensity,
),
home: MyHomePage(),
);
}
}
class MyHomePage extends StatefulWidget {
MyHomePage({Key key}) : super(key: key);
@override
State<StatefulWidget> createState() {
return MyHomePageState();
}
}
class MyHomePageState extends State<MyHomePage> {
int pressCount = 0;
@override
Widget build(BuildContext context) {
return Scaffold (
appBar: AppBar(
title: Text("Flutter TextButton Example"),
),
body: Center (
child: TextButton (
child: Text("Click Me! " + this.pressCount.toString()),
onPressed: onPressHander
),
)
);
}
onPressHander() {
this.setState(() {
this.pressCount++;
});
}
}
运行上面代码,效果如下 -
5. onLongPress函数
onLongPress 是一个回调函数。当用户按下按钮的时间超过 LONG_PRESS_TIMEOUT 毫秒时调用它。LongPress 事件将在用户按下 LONG_PRESS_TIMEOUT 毫秒时发生,在此期间 (0 -> LONG_PRESS_TIMEOUT),用户不会移动光标。
VoidCallback onLongPress
如果为 Button 分配两个回调函数 onPressed 和 onLongPress,在任何情况下,最多只能调用一个函数。
LONG_PRESS_TIMEOUT 500 milliseconds
如果用户在 LONG_PRESS_TIMEOUT 时间之前按下并释放它,则只会发生 onPressed 事件。
如果用户按下它的时间超过 LONG_PRESS_TIMEOUT 毫秒,则 onLongPress 事件将发生,Flutter 将忽略此后发生的 onPressed 事件。
示例代码:
import 'package:flutter/material.dart';
void main() {
runApp(MyApp());
}
class MyApp extends StatelessWidget {
@override
Widget build(BuildContext context) {
return MaterialApp(
title: 'yiibai.com',
debugShowCheckedModeBanner: false,
theme: ThemeData(
primarySwatch: Colors.blue,
visualDensity: VisualDensity.adaptivePlatformDensity,
),
home: MyHomePage(),
);
}
}
class MyHomePage extends StatefulWidget {
MyHomePage({Key key}) : super(key: key);
@override
State<StatefulWidget> createState() {
return MyHomePageState();
}
}
class MyHomePageState extends State<MyHomePage> {
int pressedCount = 0;
int longPressCount = 0;
@override
Widget build(BuildContext context) {
return Scaffold (
appBar: AppBar(
title: Text("Pressed: " + this.pressedCount.toString()
+" --- Long Press: " + this.longPressCount.toString()),
),
body: Center (
child: TextButton (
child: Text("Test Me"),
onPressed: onPressHander,
onLongPress: onLongPressHandler
),
)
);
}
onPressHander() {
this.setState(() {
this.pressedCount++;
});
}
onLongPressHandler() {
this.setState(() {
this.longPressCount++;
});
}
}
运行上面示例代码,效果如下 -
6. style属性
style 属性用于自定义 TextButton 的样式。
const ButtonStyle(
{MaterialStateProperty<TextStyle> textStyle,
MaterialStateProperty<Color> backgroundColor,
MaterialStateProperty<Color> foregroundColor,
MaterialStateProperty<Color> overlayColor,
MaterialStateProperty<Color> shadowColor,
MaterialStateProperty<double> elevation,
MaterialStateProperty<EdgeInsetsGeometry> padding,
MaterialStateProperty<Size> minimumSize,
MaterialStateProperty<BorderSide> side,
MaterialStateProperty<OutlinedBorder> shape,
MaterialStateProperty<MouseCursor> mouseCursor,
VisualDensity visualDensity,
MaterialTapTargetSize tapTargetSize,
Duration animationDuration,
bool enableFeedback}
)
例如,具有基于其状态的可变背景颜色和前景色的 TextButton。
TextButton (
child: Text("TextButton 1"),
onPressed: () {},
style: ButtonStyle (
backgroundColor: MaterialStateProperty.resolveWith<Color>(
(Set<MaterialState> states) {
if (states.contains(MaterialState.pressed)) {
return Colors.red;
}
return null; // Use the component's default.
}
),
foregroundColor: MaterialStateProperty.resolveWith<Color>(
(Set<MaterialState> states) {
if (states.contains(MaterialState.pressed)) {
return Colors.yellow;
}
return null; // Use the component's default.
},
)
)
)
例如:处于按下状态的高度为 10 的 TextButton 的高度为 0。
TextButton (
child: Text("TextButton 2"),
onPressed: () {},
style: ButtonStyle(
backgroundColor: MaterialStateProperty.resolveWith<Color>(
(Set<MaterialState> states) {
if (states.contains(MaterialState.disabled)) {
return Colors.black26;
}
return Colors.cyan;
}
),
foregroundColor: MaterialStateProperty.all<Color>(Colors.red),
elevation: MaterialStateProperty.resolveWith<double>(
(Set<MaterialState> states) {
if (states.contains(MaterialState.pressed)
|| states.contains(MaterialState.disabled)) {
return 0;
}
return 10;
},
)
)
)