一、Flutter 是什么?
Flutter 是 Google 推出的 UI 框架,幫助開發者通過一套代碼同時運行在 iOS 和 Android 上,構建媲美原生體驗的精美應用!實際上 Flutter 不止于移動平臺,正逐漸從移動設備擴展到多個平臺,例如 Web、macOS、Windows、Linux、嵌入式設備等,因此 Flutter 是適用于所有屏幕的便攜式界面框架,Flutter 一切皆是 Widget;自繪 UI;Flutter 只接管 UI 層,藍牙等系統功能通過插件的形式提供。
二、Flutter 有哪些特點?
- 美觀:可對 UI 實現像素級的控制,且內置 UI 庫 ( Material、Cupertino )
- 快速:硬件加速圖形引擎、代碼被編譯成機器碼
- 高效:保持應用狀態的熱重載 ( hot reload )
- 開放:完全開源的項目 ( BSD 開源協議 )
三 、Flutter 系統架構
Flutter 使用 C、C++、Dart 和 Skia ( 2D 渲染引擎 ) 構建,詳情見 Flutter 系統架構
Flutter ( Android / iOS )Flutter Web
四、Flutter 與前端的一些對比
技術都是相通的,尋找相似點能讓我們快速上手一門新技術。
Flutter 與前端有不少相似點,比如 Flutter 借鑒了 React 響應式 UI 編程的思想,Flutter 也有 Flexbox、Grid 布局,此外 Dart 與 JavaScript 的語法有不少相似點。
實際上,Flutter 項目正是誕生于 Chrome 團隊,詳情見 “聽 Flutter 創始人 Eric 為你講述 Flutter 的故事”。此外,Dart 設計之初是為了取代 JavaScript,只不過最終取代失敗,因而轉換定位,服務于 Flutter。
Flutter | 前端 | |
---|---|---|
編程語言 | Dart | JavaScript |
響應式 UI 編程 | 借鑒 React | React、Vue、Angular |
狀態管理 | Provider、Redux、Mobx | Redux、Mobx、Vuex |
頁面樣式 | Widgets | CSS、styled-component |
UI 庫 | 官方內置 Material Design、Cupertino | 社區 Ant Design、Element |
內嵌視圖 | PlatformView | iframe |
開發和調試工具 | Dart DevTools | Chrome DevTools |
編輯器 | VS Code、Android Studio | VS Code、Sublime Text |
在線編輯器 | DartPad、CodePen | CodePen、JSFiddle |
包管理工具 | pub | npm、yarn |
Dart | JavaScript | |
---|---|---|
編譯 | 即時編譯 (JIT) 或提前編譯 (AOT) | 即時編譯 ( JIT ) |
異步非阻塞 | 單線程、事件循環、微任務、宏任務 | 單線程、事件循環、微任務、宏任務 |
異步編程 | Future、async、await | Promise、async、await |
類型系統 | type safestatic type checking and runtime checks | TypeScriptstatic type definitions |
繼承 | Class | 原型鏈 |
密集型計算 | Isolate | Web Worker |
Flutter | CSS | |
---|---|---|
樣式化文本 | Text、RichText | font-size、font-weight、font-family... |
盒模型 | 只有 border-box | box-sizing: content-box、border-box; |
彈性盒子布局 | Row、Column | display: flex、inline-flex;flex-direction: row、column; |
網格布局 | Grid | display: grid; |
定位方式 | Aligin、Stack & Positioned、Slivers | position: static、relative、absolute、sticky、fixed |
變換 ( 旋轉 縮放 傾斜 平移等 ) | Transform | transform |
舉個
Transform transform
// Flutter Dart
var container = Container( // grey box
color: Colors.grey[300],
width: 320,
height: 240,
child: Center(
child: Text(
"Lorem ipsum",
style: TextStyle(
fontWeight: FontWeight.w900,
fontSize: 24,
fontFamily: "Georgia",
),
),
),
);
五、Flutter 為什么選擇 Dart ?
- Flutter 選擇開發語言時,使用 4 個主要維度進行評估,Dart 在所有評估維度上都取得高分
- 開發者的生產力
- 面向對象
- 穩定可期的高性能表現
- 快速內存分配
2 . Dart 的運行時和編譯器支持 Flutter 的兩個關鍵特性
- 基于 JIT ( 即時編譯 ) 的快速開發周期,允許在帶類型的語言中支持形變和有狀態熱重載
- 一個能產出高效率 ARM 代碼的 AOT (Ahead of time 提前編譯) 編譯器,從而確??焖賳拥哪芰涂深A期的生產版本運行性能
3 . Dart團隊就在你身邊:與 Dart 社區展開了密切合作,Dart 社區積極投入資源改進 Dart,以便在 Flutter 中更易使用
六、Flutter 性能為何能夠媲美原生應用?
Flutter | Android、iOS | Hybrid | React Native、Weex |
---|---|---|---|
七、Flutter 與原生交互
1 . PlatformChannel
適用于不帶 UI 的功能,Flutter 與原生約定通道方法,原生通過 API 的形式提供定位、藍牙、傳感器等系統功能,或者復用客戶端 SDK,提供請求、上傳、美顏、人臉識別、推送、 IM 等基礎功能
2 . PlatformView
適用于帶 UI 的功能,Flutter 內嵌原生視圖,例如地圖、WebView 等
// Flutter Dart
var container = Container( // grey box
color: Colors.grey[300],
width: 320,
height: 240,
child: Center(
child: Text(
"Lorem ipsum",
style: TextStyle(
fontWeight: FontWeight.w900,
fontSize: 24,
fontFamily: "Georgia",
),
),
),
);
3 . Texture
適用于帶 UI 的功能,原生提供圖像數據 ( 相機拍攝畫面、視頻播放幀 ),Flutter 通過 ID 引用原生存放于 GPU 的圖像數據,然后自定義 UI,例如相機、相冊、播放器等
八、Flutter 開發體驗:"UI as Code"
Flutter 的 UI 代碼使用 Dart 語言,其優點如下:
-
Flutter 的聲明式 UI 編寫方法能夠直觀地描述 UI 結構 ( 借鑒 React )
-
不需要為 UI 布局學習額外的語法
-
不需要維護代碼之外的 UI 定義文件
-
但是,也存在幾個問題:
問題一:復雜 UI 邏輯會使用命令式語法,打破代碼結構和 UI 視覺結構的一致性 ( 代碼看起來更像是命令式的而不是聲明式的 )
image.png
Widget build(BuildContext context) {
List<SegmentedTabBarItem> items = [];
List genders = ["男生", "女生", "不限"];
for (int i = 0; i < genders.length; i++) {
items.add(SegmentedTabBarItem(
text: genders[i],
width: 102,
radius: 8,
fontWeight: FontWeight.w500,
selectedTextColor: Colors.white,
duration: Duration(milliseconds: 0),
));
}
return SegmentedTabBar(
tabItemSpacing: 6.5,
tabBarRadius: $rem(12),
tabIndex: genderIndex,
padding: EdgeInsets.symmetric(horizontal: 0),
selectedItemBackgroundColor: Colors.purple,
duration: Duration(milliseconds: 0),
children: items,
onSelected: (int index) {
setState(() {
genderIndex = index;
});
},
);
}
SegmentedTabBar 在概念和視覺上都應該先于 items 出現。但是由于語法局限,這個空間關系被反了過來。代碼看起來更像是命令式而不是聲明式。
解決方案:在 Dart 2.3 中加入了針對 UI 編程優化的新語法元素,即可以在集合數據類型的定義中使用 if 和 for 這樣的流程控制元素。
Widget build(BuildContext context) {
return SegmentedTabBar(
tabItemSpacing: 6.5,
tabBarRadius: $rem(12),
tabIndex: genderIndex,
padding: EdgeInsets.symmetric(horizontal: 0),
selectedItemBackgroundColor: Colors.purple,
duration: Duration(milliseconds: 0),
children: <SegmentedTabBarItem>[
for (String label in ["男生", "女生", "不限"])
SegmentedTabBarItem(
text: label,
width: 102,
radius: 8,
fontWeight: FontWeight.w500,
selectedTextColor: Colors.white,
duration: Duration(milliseconds: 0),
),
],
onSelected: (int index) {
setState(() {
genderIndex = index;
});
},
);
}
問題二:多層嵌套之后不容易對 UI 的構成做到一目了然
解決方案:IDE 中加入了 Editor UI Guides
image.png
九、Flutter 開發調試工具
Demo 演示
參考資料
- Flutter architectural overview
- Flutter for web developers
- Understanding constraints
- How is Flutter different for app development
- Dart asynchronous programming: Isolates and event loops
- 聽 Flutter 創始人 Eric 為你講述 Flutter 的故事
- Flutter 最新進展與未來展望
- 深入 Flutter 的高性能圖形渲染
- Flutter 的性能測試與理論
- Flutter 的渲染機制
- Flutter 的分層設計
- Flutter 系統架構
- Flutter 實戰