Flutter控件--Scaffold

flutter控件練習demo地址githubgit

1. 簡介

Scaffold 實現了基本的Material Design佈局結構github

在Material設計中定義的單個界面上的各類佈局元素,在 Scaffold 中都有支持,好比 左邊欄(Drawers)、snack bars、以及 (底部彈窗)bottom sheets。(底部導航欄)BottomNavigationBarbash

2. 基本用法

Scaffold 有下面幾個主要屬性:app

  • appBar:顯示在界面頂部的一個 AppBarless

  • body:當前界面所顯示的主要內容 Widgetide

  • floatingActionButton:Material設計中所定義的 FAB,界面的主要功能按鈕函數

  • floatingActionButtonLocation:floatingActionButton 的位置佈局

  • floatingActionButtonAnimator:floatingActionButton 的動畫動畫

  • drawer:左邊側邊欄控件ui

  • endDrawer:右邊側邊欄控件

  • backgroundColor: 內容的背景顏色,默認使用的是 ThemeData.scaffoldBackgroundColor 的值

  • bottomNavigationBar: 顯示在頁面底部的導航欄

  • bottomSheet: 底部彈出來的東西(基本上沒用)

  • persistentFooterButtons:固定在下方顯示的按鈕,好比對話框下方的肯定、取消按鈕 (基本上沒用)

  • resizeToAvoidBottomPadding:控制界面內容 body 是否從新佈局來避免底部被覆蓋了,好比當鍵盤顯示的時候,從新佈局避免被鍵盤蓋住內容。默認值爲 true。

3. Demo圖片

4. Demo

import 'package:flutter/material.dart';

void main() => runApp(MyApp());

class MyApp extends StatelessWidget {
  // This widget is the root of your application.
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      title: 'Flutter Demo',
      theme: ThemeData(
        primarySwatch: Colors.blue,
      ),
      home: ScaffoldDemo(),
    );
  }
}


class ScaffoldDemo extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return new Scaffold(
      appBar: _appBar(),
      body: _body(),
      floatingActionButton: new FloatingActionButton(
        tooltip: 'Add', // used by assistive technologies
        child: new Icon(Icons.add),
        onPressed: null,
      ),
      floatingActionButtonLocation: FloatingActionButtonLocation.centerFloat,
      floatingActionButtonAnimator: FloatingActionButtonAnimator.scaling,
      drawer: _drawer(context),
      endDrawer: Drawer(child: Text("右抽屜")),
      bottomNavigationBar: _BottomNavigationBar(),
    );
  }

  AppBar _appBar() {
    return new AppBar(
      // 若是有 側邊欄  右邊是默認的事條目,點擊默認打開 左側邊欄。 若是沒有側邊欄,就顯示返回箭頭
      title: new Text('Example title'),
      actions: <Widget>[
        new IconButton(
          icon: new Icon(Icons.search),
          tooltip: 'Search', // 長按的一個提示
          onPressed: null,
        ),
        new IconButton(
          icon: new Icon(Icons.access_time),
          tooltip: 'time',
          onPressed: null,
        ),
      ],
    );
  }

  Drawer _drawer(BuildContext context) {
    return Drawer(
      child: ListView(
        padding: EdgeInsets.zero,
        children: <Widget>[
          DrawerHeader(
            decoration: BoxDecoration(
              color: Colors.lightBlueAccent,
            ),
            child: Center(
              child: SizedBox(
                width: 60.0,
                height: 60.0,
                child: CircleAvatar(
                  child: Text('頭像'),
                ),
              ),
            ),
          ),
          ListTile(
            title: Text('Item 1'),
            leading: new CircleAvatar(
              child: new Icon(Icons.school),
            ),
            onTap: () {
              Navigator.pop(context);
            },
          ),
          ListTile(
            title: Text('Item 2'),
            leading: new CircleAvatar(
              child: new Text('B2'),
            ),
            onTap: () {
              Navigator.pop(context);
            },
          ),
          ListTile(
            title: Text('Item 3'),
            leading: new CircleAvatar(
              child: new Icon(Icons.list),
            ),
            onTap: () {
              Navigator.pop(context);
            },
          ),
        ],
      ),
    );
  }

  Builder _body() {
    return Builder(builder: (BuildContext context) {
      return Center(
        child: Column(
          children: <Widget>[
            RaisedButton(
              child: Text('顯示snackbar (Text 沒有 onPressed 屬性)'),
              onPressed: () {
                Scaffold.of(context).showSnackBar(SnackBar(
                  content: Text('我是snackbar'),
                ));
              },
            ),
            RaisedButton(
              child: Text('顯示BottomSheet (Text 沒有 onPressed 屬性)'),
              onPressed: () {
                Scaffold.of(context).showBottomSheet((BuildContext context) {
                  return ListView(
                    padding: EdgeInsets.zero,
                    children: <Widget>[
                      ListTile(
                        title: Text('Item 1'),
                        leading: new CircleAvatar(
                          child: new Icon(Icons.school),
                        ),
                        onTap: () {
                          Navigator.pop(context);
                        },
                      ),
                      ListTile(
                        title: Text('Item 2'),
                        leading: new CircleAvatar(
                          child: new Text('B2'),
                        ),
                        onTap: () {
                          Navigator.pop(context);
                        },
                      ),
                      ListTile(
                        title: Text('Item 3'),
                        leading: new CircleAvatar(
                          child: new Icon(Icons.list),
                        ),
                        onTap: () {
                          Navigator.pop(context);
                        },
                      ),
                    ],
                  );
                });
              },
            ),
          ],
        ),
      );
    });
  }

}

// BottomNavigationBar 默認的實例
class _BottomNavigationBar extends StatefulWidget {
  const _BottomNavigationBar() : super();
  @override
  State<StatefulWidget> createState() => _BottomNavigationBarFullDefault();
}


// BottomNavigationBar 默認的實例,有狀態
class _BottomNavigationBarFullDefault extends State {
  int _currentIndex = 1;

  void _onItemTapped(int index) {
    if(mounted) {
      setState(() {
        _currentIndex = index;
      });
    }
  }

  @override
  Widget build(BuildContext context) {
    return BottomNavigationBar(
      type: BottomNavigationBarType.fixed, // BottomNavigationBarType 中定義的類型,有 fixed 和 shifting 兩種類型
      iconSize: 24.0, // BottomNavigationBarItem 中 icon 的大小
      currentIndex: _currentIndex, // 當前所高亮的按鈕index
      onTap: _onItemTapped, // 點擊裏面的按鈕的回調函數,參數爲當前點擊的按鈕 index
      fixedColor:  Colors.blue, // 若是 type 類型爲 fixed,則經過 fixedColor 設置選中 item 的顏色
      items: <BottomNavigationBarItem> [

        BottomNavigationBarItem(
            title:  Text("主頁"), icon:  Icon(Icons.home)),
        BottomNavigationBarItem(
            title:  Text("發現"), icon:  Icon(Icons.search)),
        BottomNavigationBarItem(
            title:  Text("個人"), icon:  Icon(Icons.image)),

      ],
    );
  }
}

複製代碼

注意點

  • 當有 導航欄的時候 appbar 左邊默認的是條目,而且點開能打開導航欄。也能夠手動設置icon
  • build(BuildContext context)在 Scaffold.of(context)以前時,會報錯 ,須要 Builder(builder: (BuildContext context) {})包裹起來才能調用 或者 final GlobalKey _scaffoldKey = GlobalKey(); 來吊起來
  • BottomNavigationBar 默認就是有狀態的本身點擊,本身就能夠改變狀態
  • 必須引入import 'package:flutter/material.dart',而且根必須是MaterialApp,由於他就屬於MaterialApp中的東西

使用ScaffoldState

ScaffoldState 能夠代替打開側邊欄和snackbar
_scaffoldKey.currentState.openDrawer();默認打開左邊側邊欄
_scaffoldKey.currentState.showSnackBar

import 'package:flutter/material.dart';

class ScaffoldStateDemo extends StatefulWidget {
  @override
  State<StatefulWidget> createState() => _ScaffoldStateDemo();
}

class _ScaffoldStateDemo extends State with SingleTickerProviderStateMixin {
  final GlobalKey<ScaffoldState> _scaffoldKey = GlobalKey<ScaffoldState>();

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      key: _scaffoldKey,
      appBar: AppBar(
        title: Text("ScaffoldStateDemo"),
      ),
      body: RaisedButton(
        child: Text('顯示snackbar'),
        onPressed: _showSnackBar,
      ),
    );
  }

  _showSnackBar() {
    _scaffoldKey.currentState
        .showSnackBar(SnackBar(content: Text("經過ScaffoldState打開的")));
  }
}
複製代碼
相關文章
相關標籤/搜索