Руководство Flutter TextButton
View more Tutorials:
В Flutter, TextButton используется для создания кнопки, содержащей текст с идеей создания плоской кнопки (flat button) с высотой (elevation) 0 по умолчанию. Но на самом деле вы можете изменить её стиль с помощью свойства style.
Примечание: Раньше для создания плоской кнопки мы использовали класс FlatButton. Однако с октября 2020 года этот класс был помечен как устаревший, и он был заменен классом TextButton. Это одна из попыток команды разработчиков Flutter, которые направленны на упрощение и согласование Flutter API.
TextButton Constructor:
TextButton Constructor
const TextButton({Key key, @required Widget child, @required VoidCallback onPressed, VoidCallback onLongPress, ButtonStyle style, FocusNode focusNode, bool autofocus: false, Clip clipBehavior: Clip.none } )
Можно использовать TextButton в панелях инструментов, диалоговых окнах (Dialog) и т. д. Но иногда вам нужно изменить её стиль (style), чтобы избежать путаницы у пользователей. Или когда вы используете её как плоскую кнопку (flat button), вы должны поместить её на месте, соответствующем контексту. Нельзя помещать TextButton на месте, где она смешивается с другим содержимым, например, в середине списка.
TextButton.icon Constructor:
TextButton.icon Constructor
TextButton.icon( {Key key, @required Widget icon, @required Widget label, @required VoidCallback onPressed, VoidCallback onLongPress, ButtonStyle style, FocusNode focusNode, bool autofocus, Clip clipBehavior} )
Если обе функции callback: onPressed и onLongPress, не указаны, TextButton будет отключена (disabled) и не будет иметь ответа при касании.
Ниже приведен пример, включающий две TextButton. Одна из них - самая простая TextButton (содержащая только одну текстовую метку), а другая - TextButton с цветом фона (backgroundColor) и цветом текста (foregroundColor).

main.dart (ex1)
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: () {}, )
child - это самое важное свойство TextButton. В большинстве случаев это свойство используется в качестве объекта Text.
@required Widget child
Самый простой пример с child - это объект Text:

TextButton ( child: Text("Default TextButton"), onPressed: () {}, )
Путём присвоения объекта Row свойству child, можно создать более сложную TextButton, включающую как Icon, так и Text.

child (ex1)
// 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: () {}, )
onPressed - это функция обратного callback. Она вызывается, когда пользователь нажимает (click) Button. В частности, событие onPressed произойдет, когда пользователь завершит два действия, включающих нажатие (press down) и отпускание (release) кнопки.
@required VoidCallback onPressed

Примечание: Если свойства onPressed и onLongPress не указаны, кнопка будет отключена и не будет реагировать на касания.

main.dart (onPressed - ex1)
import 'package:flutter/material.dart'; void main() { runApp(MyApp()); } class MyApp extends StatelessWidget { @override Widget build(BuildContext context) { return MaterialApp( title: 'o7planning.org', 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++; }); } }
onLongPress - это функция callback. Она вызывается, когда пользователь нажимает (press down) кнопку в течение времени более LONG_PRESS_TIMEOUT миллисекунд. Событие Long-Press будет происходить в LONG_PRESS_TIMEOUT-момент времени после нажатия пользователем, если в течение этого времени (0 -> LONG_PRESS_TIMEOUT) курсор мыши не перемещается.
VoidCallback onLongPress
Если вы назначите две функции callback: onPressed и onLongPress для одной кнопки, то в любой ситуации будет вызвана не более одной функции.
LONG_PRESS_TIMEOUT | 500 milliseconds |

Если пользователь нажмет (press down) и отпустит (release) её до времени LONG_PRESS_TIMEOUT, произойдет только одно событие onPressed.

Если пользователь нажмет её дольше, чем LONG_PRESS_TIMEOUT миллисекунд, произойдет событие onLongPress, и Flutter проигнорирует событие onPressed, которое произойдет после этого.
Например:

main.dart (onLongPress - ex1)
import 'package:flutter/material.dart'; void main() { runApp(MyApp()); } class MyApp extends StatelessWidget { @override Widget build(BuildContext context) { return MaterialApp( title: 'o7planning.org', 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++; }); } }
Свойство style используется для настройки стиля TextButton.
ButtonStyle style
ButtonStyle constructor
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 с изменяемым цветом фона (background color) и цветом текста (foreground color) в зависимости от её состояния.

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. }, ) ) )
Например: TextButton с высотой (elevation) 10, в нажатом состоянии (pressed) будет иметь высоту 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; }, ) ) )
- TODO Link!
- TODO Link!
bool autofocus: false
- TODO Link!
FocusNode focusNode
- TODO Link!
Clip clipBehavior: Clip.none
- TODO Link!