Flutter Button Widget

Flutter button widgets are interactive components that respond to user taps and trigger specific actions in your application. The Flutter framework provides various button types to suit different UI needs and design requirements. Understanding the properties and behavior of each Flutter button widget is crucial for creating intuitive and responsive user interfaces.

Flutter's Material Design implementation offers several button variants, each with distinct visual styles and behaviors. Additionally, Flutter allows you to create custom button widgets for unique design requirements.

ElevatedButton

The ElevatedButton is a Material Design button with elevation that lifts when pressed. It's one of the most commonly used Flutter button widgets, replacing the deprecated RaisedButton from earlier Flutter versions.

Key Properties of ElevatedButton

PropertyTypeDescription
onPressedVoidCallback?Required. The callback function when the button is tapped. If null, the button appears disabled.
onLongPressVoidCallback?Called when the button is long-pressed.
onHoverValueChanged<bool>?Called when pointer enters or exits the button.
styleButtonStyle?Used to customize the button's appearance.
childWidgetThe widget displayed inside the button (usually Text or Icon).
clipBehaviorClipHow to clip the button's content.
autofocusboolWhether the button should take focus initially.

ElevatedButton Example

ElevatedButton(  
  onPressed: () {  
    print('ElevatedButton pressed!');  
  },  
  style: ElevatedButton.styleFrom(  
    foregroundColor: Colors.white,  
    backgroundColor: Colors.blue,  
    elevation: 5,  
    shape: RoundedRectangleBorder(  
      borderRadius: BorderRadius.circular(10),  
    ),  
    padding: EdgeInsets.symmetric(horizontal: 20, vertical: 15),  
  ),  
  child: Text('ElevatedButton'),  
)  

Styling ElevatedButton

The style property allows extensive customization of the Flutter button widget appearance:

ElevatedButton(  
  onPressed: () {},  
  style: ButtonStyle(  
    backgroundColor: MaterialStateProperty.resolveWith<Color>(  
      (Set<MaterialState> states) {  
        if (states.contains(MaterialState.pressed))  
          return Colors.blue.shade700;  
        return Colors.blue;  
      },  
    ),  
    foregroundColor: MaterialStateProperty.all<Color>(Colors.white),  
    elevation: MaterialStateProperty.all<double>(5),  
    shape: MaterialStateProperty.all<RoundedRectangleBorder>(  
      RoundedRectangleBorder(  
        borderRadius: BorderRadius.circular(18.0),  
      ),  
    ),  
  ),  
  child: Text('Custom Styled Button'),  
)  

TextButton

TextButton is a flat button without elevation. It's typically used for less prominent actions, often within dialogs or as an alternative to more prominent buttons.

Key Properties of TextButton

PropertyTypeDescription
onPressedVoidCallback?Required. The callback function when button is tapped.
onLongPressVoidCallback?Called when the button is long-pressed.
styleButtonStyle?Used to customize the button's appearance.
childWidgetThe widget displayed inside the button.

TextButton Example

TextButton(  
  onPressed: () {  
    print('TextButton pressed!');  
  },  
  style: TextButton.styleFrom(  
    foregroundColor: Colors.blue,  
    textStyle: TextStyle(  
      fontSize: 16,  
      fontWeight: FontWeight.bold,  
    ),  
  ),  
  child: Text('TextButton'),  
)  

OutlinedButton

OutlinedButton is a button with an outline border and no fill. It's useful for actions that deserve less emphasis than ElevatedButton but more than TextButton.

Key Properties of OutlinedButton

PropertyTypeDescription
onPressedVoidCallback?Required. The callback function when button is tapped.
onLongPressVoidCallback?Called when the button is long-pressed.
styleButtonStyle?Used to customize the button's appearance.
childWidgetThe widget displayed inside the button.

OutlinedButton Example

OutlinedButton(  
  onPressed: () {  
    print('OutlinedButton pressed!');  
  },  
  style: OutlinedButton.styleFrom(  
    foregroundColor: Colors.purple,  
    side: BorderSide(color: Colors.purple, width: 2),  
    shape: RoundedRectangleBorder(  
      borderRadius: BorderRadius.circular(10),  
    ),  
    padding: EdgeInsets.symmetric(horizontal: 20, vertical: 15),  
  ),  
  child: Text('OutlinedButton'),  
)  

IconButton

IconButton is a button that displays an icon without a background or border. It's commonly used in app bars, toolbars, and other compact UI elements.

Key Properties of IconButton

PropertyTypeDescription
onPressedVoidCallback?Required. The callback function when button is tapped.
iconWidgetRequired. The icon to display (usually an Icon widget).
colorColor?The color for the icon.
splashRadiusdouble?The radius of the splash effect.
tooltipString?Text shown when the user long-presses the button.
iconSizedoubleSize of the icon, defaults to 24.0.
paddingEdgeInsetsGeometryPadding around the icon.

IconButton Example

IconButton(  
  onPressed: () {  
    print('IconButton pressed!');  
  },  
  icon: Icon(Icons.favorite),  
  color: Colors.red,  
  tooltip: 'Favorite',  
  splashRadius: 25,  
  iconSize: 30,  
)  

FloatingActionButton

FloatingActionButton (FAB) is a circular button that floats above the UI, typically used for the primary action on a screen. It's a prominent Flutter button widget for key actions.

Key Properties of FloatingActionButton

PropertyTypeDescription
onPressedVoidCallbackRequired. The callback function when button is tapped.
childWidgetThe widget displayed inside the button (usually an Icon).
tooltipString?Text shown when the user long-presses the button.
foregroundColorColor?The color for the icon/child.
backgroundColorColor?The button's background color.
elevationdouble?The z-coordinate at which to place this button.
miniboolWhether to use a smaller-sized button.
shapeShapeBorder?The shape of the button's material.
extendedboolWhether to create an extended FAB with both an icon and a label.
labelWidget?Used with extended FABs to show a label next to the icon.

FloatingActionButton Example

FloatingActionButton(  
  onPressed: () {  
    print('FAB pressed!');  
  },  
  backgroundColor: Colors.green,  
  child: Icon(Icons.add),  
  tooltip: 'Add Item',  
)  

Extended FloatingActionButton Example

FloatingActionButton.extended(  
  onPressed: () {  
    print('Extended FAB pressed!');  
  },  
  label: Text('Create'),  
  icon: Icon(Icons.add),  
  backgroundColor: Colors.green,  
)  

DropdownButton

DropdownButton is a Flutter button widget that shows a menu when pressed, allowing users to select from a list of items.

Key Properties of DropdownButton

PropertyTypeDescription
itemsList<DropdownMenuItem<T>>?The list of items to display in the dropdown.
valueT?The currently selected value.
onChangedValueChanged<T?>?Called when the user selects an item.
hintWidget?Displayed if no item is selected.
disabledHintWidget?Displayed if dropdown is disabled.
iconWidget?The icon to display next to the button.
styleTextStyle?The text style to use for the items.
underlineWidget?The widget to display as the underline.
isDenseboolWhether to reduce the height of the button.
isExpandedboolWhether the button should expand to fill its parent.

DropdownButton Example

String dropdownValue = 'One';  
  
DropdownButton<String>(  
  value: dropdownValue,  
  icon: Icon(Icons.arrow_drop_down),  
  elevation: 16,  
  style: TextStyle(color: Colors.deepPurple),  
  underline: Container(  
    height: 2,  
    color: Colors.deepPurpleAccent,  
  ),  
  onChanged: (String? newValue) {  
    setState(() {  
      dropdownValue = newValue!;  
    });  
  },  
  items: <String>['One', 'Two', 'Three', 'Four']  
    .map<DropdownMenuItem<String>>((String value) {  
      return DropdownMenuItem<String>(  
        value: value,  
        child: Text(value),  
      );  
    }).toList(),  
)  

PopupMenuButton

PopupMenuButton displays a menu when pressed, similar to a dropdown but typically used for actions rather than selection.

Key Properties of PopupMenuButton

PropertyTypeDescription
itemBuilderPopupMenuItemBuilder<T>Required. Builds the items in the menu.
onSelectedPopupMenuItemSelected<T>?Called when a menu item is selected.
iconWidget?The icon to display for the button.
offsetOffset?The offset of the popup menu from the button.
tooltipString?Text shown when the user long-presses the button.
elevationdouble?The z-coordinate at which to place the menu.
paddingEdgeInsetsGeometry?Padding inside the button.

PopupMenuButton Example

PopupMenuButton<String>(  
  onSelected: (String result) {  
    print('Selected: $result');  
  },  
  itemBuilder: (BuildContext context) => <PopupMenuEntry<String>>[  
    const PopupMenuItem<String>(  
      value: 'edit',  
      child: Text('Edit'),  
    ),  
    const PopupMenuItem<String>(  
      value: 'delete',  
      child: Text('Delete'),  
    ),  
    const PopupMenuItem<String>(  
      value: 'share',  
      child: Text('Share'),  
    ),  
  ],  
  icon: Icon(Icons.more_vert),  
  tooltip: 'Menu',  
)  

InkWell as a Button

InkWell is not technically a button, but it's commonly used to create custom button-like behaviors with Material Design ink splash effects.

Key Properties of InkWell

PropertyTypeDescription
onTapGestureTapCallback?Called when tapped.
onDoubleTapGestureTapCallback?Called when double-tapped.
onLongPressGestureLongPressCallback?Called when long-pressed.
childWidgetThe widget displayed inside the InkWell.
splashColorColor?The color of the splash effect.
highlightColorColor?The color of the highlight effect.
radiusdouble?The radius of the splash effect.

InkWell Button Example

InkWell(  
  onTap: () {  
    print('InkWell tapped!');  
  },  
  splashColor: Colors.blue.withAlpha(30),  
  highlightColor: Colors.blue.withAlpha(15),  
  borderRadius: BorderRadius.circular(10),  
  child: Container(  
    padding: EdgeInsets.symmetric(horizontal: 20, vertical: 10),  
    decoration: BoxDecoration(  
      border: Border.all(color: Colors.blue),  
      borderRadius: BorderRadius.circular(10),  
    ),  
    child: Text(  
      'Custom InkWell Button',  
      style: TextStyle(color: Colors.blue),  
    ),  
  ),  
)  

GestureDetector as a Button

Similar to InkWell, GestureDetector can be used to create custom buttons, but without the Material Design splash effects.

Key Properties of GestureDetector

PropertyTypeDescription
onTapGestureTapCallback?Called when tapped.
onDoubleTapGestureTapCallback?Called when double-tapped.
onLongPressGestureLongPressCallback?Called when long-pressed.
childWidgetThe widget displayed inside the GestureDetector.

GestureDetector Button Example

GestureDetector(  
  onTap: () {  
    print('GestureDetector tapped!');  
  },  
  child: Container(  
    padding: EdgeInsets.symmetric(horizontal: 20, vertical: 10),  
    decoration: BoxDecoration(  
      color: Colors.amber,  
      borderRadius: BorderRadius.circular(10),  
    ),  
    child: Text(  
      'Custom GestureDetector Button',  
      style: TextStyle(color: Colors.white),  
    ),  
  ),  
)  

Custom Button Widgets

Creating custom Flutter button widgets allows for unique designs that match your app's branding. Here's an example of a custom button implementation:

class CustomButton extends StatelessWidget {  
  final String text;  
  final VoidCallback onPressed;  
  final Color color;  
  
  const CustomButton({  
    Key? key,  
    required this.text,  
    required this.onPressed,  
    this.color = Colors.blue,  
  }) : super(key: key);  
  
  @override  
  Widget build(BuildContext context) {  
    return Material(  
      color: Colors.transparent,  
      child: InkWell(  
        onTap: onPressed,  
        borderRadius: BorderRadius.circular(15),  
        child: Container(  
          padding: EdgeInsets.symmetric(horizontal: 25, vertical: 12),  
          decoration: BoxDecoration(  
            color: color,  
            borderRadius: BorderRadius.circular(15),  
            boxShadow: [  
              BoxShadow(  
                color: color.withOpacity(0.5),  
                spreadRadius: 1,  
                blurRadius: 8,  
                offset: Offset(0, 3),  
              ),  
            ],  
          ),  
          child: Text(  
            text,  
            style: TextStyle(  
              color: Colors.white,  
              fontWeight: FontWeight.bold,  
              fontSize: 16,  
            ),  
          ),  
        ),  
      ),  
    );  
  }  
}  
  
// Usage:  
CustomButton(  
  text: 'Custom Flutter Button',  
  onPressed: () {  
    print('Custom button pressed!');  
  },  
  color: Colors.deepPurple,  
)  

Button Theming in Flutter

Flutter allows you to define consistent button styles across your app using themes. This approach ensures visual consistency while reducing code duplication.

Theming ElevatedButton

ThemeData(  
  elevatedButtonTheme: ElevatedButtonThemeData(  
    style: ElevatedButton.styleFrom(  
      foregroundColor: Colors.white,  
      backgroundColor: Colors.purple,  
      elevation: 3,  
      shape: RoundedRectangleBorder(  
        borderRadius: BorderRadius.circular(10),  
      ),  
      padding: EdgeInsets.symmetric(horizontal: 16, vertical: 12),  
    ),  
  ),  
)  

Theming TextButton

ThemeData(  
  textButtonTheme: TextButtonThemeData(  
    style: TextButton.styleFrom(  
      foregroundColor: Colors.purple,  
      textStyle: TextStyle(  
        fontWeight: FontWeight.bold,  
      ),  
    ),  
  ),  
)  

Theming OutlinedButton

ThemeData(  
  outlinedButtonTheme: OutlinedButtonThemeData(  
    style: OutlinedButton.styleFrom(  
      foregroundColor: Colors.teal,  
      side: BorderSide(color: Colors.teal, width: 2),  
      shape: RoundedRectangleBorder(  
        borderRadius: BorderRadius.circular(10),  
      ),  
    ),  
  ),  
)  

Related Topics