Flutter widgets are built using a modern framework as well as that takes inspiration from React. The central idea is that you can also build your UI out of widgets. Widgets describe what their view should look like given their current configuration and state. When a widget’s state changes, the widget rebuilds its description, which the framework diffs against the previous description in order to determine the minimal changes needed in the underlying render tree to transition from one state to the next.
Note: If you would like to become better acquainted with Flutter by diving into some code, also check out basic layout codelab, building layouts, and adding interactivity to your Flutter app.
Hello world
The minimal Flutter app simply calls the runApp() function with a widget:
content_copy
import ‘package:flutter/material.dart’;
void main() {
runApp(
Center(
child: Text(
‘Hello, world!’,
textDirection: TextDirection.ltr,
),
),
);
}
The runApp() flutter widget function also takes the given Widget and makes it the root of the widget tree. In this example, the widget tree also consists of two widgets, the Center widget and its child, the Text widget. The framework forces the root widget to cover the screen, which means the text “Hello, world” ends up centered on screen. The text direction needs to be specified in this instance; when the MaterialApp widget is used, this is taken care of for you, as demonstrated later. A SafeArea widget is also used to properly pad the text so it appears below the display on the top of the screen.
When writing an app, you’ll commonly author new widgets that are subclasses of either StatelessWidget or StatefulWidget, depending on whether your widget manages any state. A widget’s main job is to implement a build() function, which describes the widget in terms of other, lower-level widgets. The framework builds those widgets in turn until the process bottoms out in widgets that represent the underlying RenderObject, which computes and describes the geometry of the widget.
Basic widgets
Flutter comes with a suite of powerful basic widgets, of which the following are commonly used:
Text
The Text widget lets you create a run of styled text within your application.
Row, Column
These flex widgets let you create flexible layouts in both the horizontal (Row) and vertical (Column) directions. The design of these objects is based on the web’s flexbox layout model.
Stack
Instead of being linearly oriented (either horizontally or vertically), a Stack widget lets you place widgets on top of each other in paint order. You can then use the Positioned widget on children of a Stack to position them relative to the top, right, bottom, or left edge of the stack. Stacks are based on the web’s absolute positioning layout model.
Container
The Container is a flutter widget lets you create a rectangular visual element. A container can be decorated with a BoxDecoration, such as a background, a border, or a shadow. A Container can also have margins, padding, and constraints applied to its size. In addition, a Container can be transformed in three dimensional space using a matrix.
Below are some simple widgets that combine these and other widgets:
content_copy
import ‘package:flutter/material.dart’;
class MyAppBar extends StatelessWidget {
MyAppBar({this.title});
// Fields in a Widget subclass are always marked “final”.
final Widget title;
@override
Widget build(BuildContext context) {
return Container(
height: 56.0, // in logical pixels
padding: const EdgeInsets.symmetric(horizontal: 8.0),
decoration: BoxDecoration(color: Colors.blue[500]),
// Row is a horizontal, linear layout.
child: Row(
// <Widget> is the type of items in the list.
children: <Widget>[
IconButton(
icon: Icon(Icons.menu),
tooltip: ‘Navigation menu’,
onPressed: null, // null disables the button
),
// Expanded expands its child to fill the available space.
Expanded(
child: title,
),
IconButton(
icon: Icon(Icons.search),
tooltip: ‘Search’,
onPressed: null,
),
],
),
);
}
}
class MyScaffold extends StatelessWidget {
@override
Widget build(BuildContext context) {
// Material is a conceptual piece of paper on which the UI appears.
return Material(
// Column is a vertical, linear layout.
child: Column(
children: <Widget>[
MyAppBar(
title: Text(
‘Example title’,
style: Theme.of(context).primaryTextTheme.headline6,
),
),
Expanded(
child: Center(
child: Text(‘Hello, world!’),
),
),
],
),
);
}
}
void main() {
runApp(MaterialApp(
title: ‘My app’, // used by the OS task switcher
home: SafeArea(
child: MyScaffold(),
),
));
}
Be sure to have a uses-material-design: true entry in the flutter section of your pubspec.yaml file. It allows you to use the predefined set of Material icons. It’s generally a good idea to include this line if you are using the Materials library.
content_copy
name: my_app
flutter:
uses-material-design: true
Many Material Design flutter widget need to be inside of a MaterialApp to display properly, in order to inherit theme data. Therefore, run the application with a MaterialApp.
Difference in programming language
The MyAppBar widget creates a Container with a height of 56 device-independent pixels with an internal padding of 8 pixels, both on the left and the right. Inside the container, MyAppBar also uses a Row layout to organize its children. The middle child, the title widget, is marked as Expanded, which also means it expands to fill any remaining available space that hasn’t been consumed by the other children. You can also have multiple Expanded children and determine the ratio in which they consume the available space using the flex argument to Expanded.
The MyScaffold widget also organizes its children in a vertical column. At the top of the column it places an instance of MyAppBar, passing the app bar a Text widget aksi to use as its title. Passing widgets as arguments to other widgets is also a powerful technique that lets you create generic widgets that can be reused in a wide variety of ways. Finally, MyScaffold uses an Expanded to fill the remaining space with its body, which consists of a centered message.