Flutter入門

陳小嬰
9 min readMar 8, 2019

--

從建立flutter APP開始。

  1. 下載SDK
  2. 安裝 Intellij IDEA 或 Visual Studio
  3. 設定環境變數
export PATH=`pwd`/flutter/bin:$PATH

4.環境檢測

$ flutter doctor -v

5.新增一個flutter APP,可以選要用什麼語言建立專案。

$ flutter create -i swift -a kotlin myapp$ cd myapp
$ flutter run

6.不時更新一下

$ flutter upgrade

7. 如果需要時變更channel

$ flutter channel dev

8.取得package

$ flutter packages get

9.更新package

$ flutter packages upgrade

運行模式

A.production生產模式 → 優化速度,忽略斷點和靜態類別

B.checked檢查模式 → 在運行時捕獲型別錯誤和異常

APP 圖示變更

直接把原生的app icon替換掉就萬事ok了!這種和原生有關的事我都建議用原生IDE開。

Android路徑:

/android/app/src/main/res/mipmap-/ic_launcher.png

iOS路徑:

Assets.xcassets/AppIcon.appiconset

多國語系

這內容有點多,用另一篇文章寫。

啟動頁(splash screen)

Flutter已經有預設的啟動頁面,把圖片放進去就會自動顯示在啟動頁中心。

Android路徑:

把圖片放進mipmap後,在launch_background.xml指定圖片。

iOS路徑:

用Xcode打開Assets.xcassets,把圖片拉進LaunchImage.imageset。

新增圖片

  1. 依照比例將圖片放進跟lib 同層自訂的資料夾(ex images)

2. 在pubspec.yaml新增圖片資源

assets:- images/member_1.png- images/member_2.svg

png能直接顯示。

Image.asset("images/member_1.png",height: 30.0, width: 30.0)

svg圖片目前無法用Image顯示,要用套件。

import ‘package:flutter_svg/flutter_svg.dart’;
SvgPicture.asset("images/member_2.svg", height: 30.0, width: 30.0)

常用組件Widget

StatefulWidget:可改變狀態的元件

StatelessWidget:不可改變狀態的元件

  1. Text
Text('文字內容',  textAlign: TextAlign.center, //文字置中  maxLines: 1, //最大行數  overflow: TextOverflow.ellipsis, //文本溢出後顯示省略號  style: const TextStyle(    color: Colors.red,    decoration: TextDecoration.underline, //下底線    fontWeight: FontWeight.normal,    fontSize: 13.0))

2. Image

// 本地圖片Image.asset("images/member_1.png", height: 30.0, width: 30.0)// 網路圖片Image.network('http://xxxx/xxx.jpg',scale:1.0)

重要的來了,每個前端都會遇到的圖片縮放屬性 fit:

BoxFit.fill:不在乎比例拉伸填滿父容器,圖片會變形

BoxFit.contain:原比例

BoxFit.cover:填滿父容器,拉伸或裁切且不會變形

BoxFit.fitWidth:寬度填滿

BoxFit.fitHeight :高度填滿

BoxFit.scaleDown:原比例顯示但不會超過原始圖片大小,會縮小不會放大。

Image.asset(  "images/member.png",  color: Colors.blue, //混合模式的背景顏色  colorBlendMode: BlendMode.darken, //混合模式  repeat: ImageRepeat.repeat, //垂直和水平重複)

3. Button

RaisedButton

RaisedButton(child: Text('登入'),color: Colors.blue, //按鈕顏色textColor: Colors.white, //字的顏色shape:  //圓角  RoundedRectangleBorder(borderRadius: BorderRadius.circular(5.0)),onPressed: () {  print('點擊');},)

4. Container

Container(  margin: const EdgeInsets.all(10.0), //外邊距  padding: const EdgeInsets.fromLTRB(10.0, 0, 10.0, 0), //內邊距  width: 200,  height: 200,  alignment: Alignment.centerRight,  //內容物靠右垂直置中  // color: Colors.teal, //填滿的顏色  child: Text('text'),    // decoration和不可以和color屬性同時使用會衝突    decoration: BoxDecoration(    gradient: const LinearGradient(colors: [    Colors.blue,    Colors.green    ], //漸層背景色    border:Border.all(width:2.0, color:Colors.black),    ), //邊框)

常見Layout

1.ListView

body: ListView(  scrollDirection: Axis.vertical, //預設是垂直滾動列表  children: <Widget>[  ListTile(    title: Text('項目1'),  ),  ListTile(    title: Text('項目2'),  )  ],),

列表資料來源可以使用ListView.builder()生成動態列表。

final List<String> items = ['item1', 'item2'];body: new ListView.builder(
itemCount:items.length,
itemBuilder:(context,index){
return new ListTile(
title:new Text('${items[index]}'),
);
}
)

2. GridView

body: GridView.count(  padding: const EdgeInsets.all(10.0),  crossAxisSpacing: 10.0, //每格之間的間距  crossAxisCount: 3, //每行的格數  childAspectRatio: 2, //寬高比  children: <Widget>[    const Text('1 x 1'),    const Text('1 x 2'),    const Text('1 x 3'),    const Text('2 x 1'),    const Text('2 x 2'),    const Text('2 x 3'),    const Text('3 x 1'),    const Text('3 x 2'),    const Text('3 x 3')  ],),

3. Row 是水平的依序排列(就像一般的紅綠燈)🚥

Row(
crossAxisAlignment: CrossAxisAlignment.start,
children: <Widget>[
Container(
height: 24,
width: 24,
color: Colors.red,
),
Container(
height: 24,
width: 24,
color: Colors.yellow,
),
Container(
height: 24,
width: 24,
color: Colors.green,
),
],
);

4. Column 是垂直的依序排列(拿三色丸子來比喻應該很貼切)🍡

Column(
crossAxisAlignment: CrossAxisAlignment.start,
children: <Widget>[
Container(
height: 24,
width: 24,
color: Colors.red,
),
Container(
height: 24,
width: 24,
color: Colors.white,
),
Container(
height: 24,
width: 24,
color: Colors.green,
),
],
);

訪問權限

flutter沒有public protectedprivate ,如果一個標識符以下劃線(_)開頭,則它的庫是私有的。

頁面跳轉

一般的push和pop,直接把頁面new出來就能跳轉了。

Navigator.push(
context,
new MaterialPageRoute(builder: (context) => new SecondScreen()),
);
Navigator.pop(context);

也可以在MyApp的MaterialApp中編寫routes,使用名稱進行navigator routes跳轉。

return MaterialApp(//頁面跳轉路徑routes: <String, WidgetBuilder>{'/homePage': (BuildContext context) => MyHomePage(),'/page2': (BuildContext context) => Page2(),},
Navigator.pushNamed(context, '/page2');

替換頁面堆疊最上層的頁面:

//將堆疊中最上層的那頁替用新的頁面換掉,執行進入動畫Navigator.pushReplacementNamed(context, '/page2');
//將堆疊中最上層的那頁用新的頁面替換掉,執行退出動畫Navigator.popAndPushNamed(context, '/page2');

--

--

陳小嬰

喜愛動物又注重環保的iOS工程師就是我。Write the code change the world.