前言:
這是我參與8月更文挑戰的第 12 天,活動詳情檢視:8月更文挑戰。為應掘金的八月更文挑戰
,我準備在本月挑選 31
個以前沒有介紹過的元件,進行全面分析和屬性介紹。這些文章將來會作為 Flutter 元件集錄
的重要素材。希望可以堅持下去,你的支援將是我最大的動力~
本系列 | 元件文章 | 列表 |
---|---|---|
1.NotificationListener | 2.Dismissible | 3.Switch |
4.Scrollbar | 5.ClipPath | 6.CupertinoActivityIndicator |
7.Opacity | 8.FadeTransition | 9. AnimatedOpacity |
10. FadeInImage | 11. Offstage | 12. TickerMode[本文] |
一、認識 TickerMode 元件
可能絕大多數的人都沒聽說過這個元件,更沒用過。我們都知道 Ticker
是動畫控制器的底層驅動力,TickerMode
元件可以禁用/啟用
子樹下所有的 Ticker
,也就是說它可以讓子樹的所有動畫無效或生效。我們可以通過動畫控制器來主動控制動畫的開啟或停止,那 TickerMode
元件的價值何在,它又是如何實現控制子樹所有的動畫呢?帶著這些問題,我們今天就來詳細分析一下 TickerMode
元件。
1.TickerMode 基本資訊
下面是 TickerMode
元件類的定義
和 構造方法
,可以看出它繼承自 StatelessWidget
。例項化時必須傳入布林型的 enabled
和 child
元件。
2. TickerMode 的使用
下面通過一個案例測試一下 TickerMode
元件,如下 buildTestContent
方法構建的是下面的三個元件,被TickerMode
包裹。buildOutSwitch
是上面的Switch
開關,它在 TickerMode
元件之外。
可見,當上面的Switch
開關開啟 _disable
為 true
時,TickerMode
的 enabled
為 false
。此時下面的兩個 loading
元件就停止了運動。從這可以看出,我們並沒有對兩個 loading
元件的動畫控制器執行任何操作,也沒有
改變元件屬性進行重建
。就可以直接禁用/啟用
它們的動畫,是不是非常神奇。像這樣可以隨意插拔,幾乎沒有任何耦合性,卻能完成某個功能的元件,可以增加使用的靈活性。
@override
Widget build(BuildContext context) {
return Column(
mainAxisSize: MainAxisSize.min,
children: [
buildOutSwitch(),
TickerMode( //<--- 使用 TickerMode
enabled: !_disable,
child: buildTestContent()),
],
);
}
Widget buildOutSwitch() => Wrap(
alignment: WrapAlignment.center,
crossAxisAlignment: WrapCrossAlignment.center,
children:[
Text('TickerMode外的Switch:'),
Switch(
value: _disable,
onChanged: _onChanged,
)] ,
);
Widget buildTestContent() => Wrap(
alignment: WrapAlignment.center,
crossAxisAlignment: WrapCrossAlignment.center,
spacing: 20,
children: [
Switch(
value: _disable,
onChanged: _onChanged,
),
CupertinoActivityIndicator(),
CircularProgressIndicator(),
],
);
複製程式碼
可能你會疑惑,我為什麼要在測試案例的下面一排放一個 Switch
?這樣可以更好地說明 TickerMode
的作用範圍。如下,點選下面的 Switch
,同樣也會切換 _disable
的狀態,可以看出由於下排的 Switch
上層的 TickerMode
被設為 disable:true
,動畫被禁用了。對比兩個 Switch
的表現,你就能明白 TickerMode
的作用範圍是在子樹中。
二、 TickerMode 的原始碼實現
1. TickerMode 原始碼分析
TickerMode
元件的原始碼非常簡單,主要就是三個處理,分別是 構造方法
、build
構造、通過 of
靜態方法檢視 enabled
的值。其中 build
方法返回的是 _EffectiveTickerMode
, of
靜態方法查通過 dependOnInheritedWidgetOfExactType
來查詢上級的 _EffectiveTickerMode
元件。那麼用腳指頭都能想出來 _EffectiveTickerMode
一定是一個 InheritedWidget
,且持有 enabled
資料。
2._EffectiveTickerMode
原始碼分析
果不其然,_EffectiveTickerMode
繼承自 InheritedWidget
,並持有 enabled
資料。這樣該資料就可以在子樹中共享。這樣看來,動畫的體系中,應該會通過上下文獲取這個值,對 Trick
進行處理。如果你也就看完 《Flutter 動畫探索 - 流光幻影》,那麼這裡應該就能銜接上了。
3. TickerMode 控制動畫的原理
我們在使用動畫時,都會使用 SingleTickerProviderStateMixin
或 TickerProviderStateMixin
來建立 動畫控制器
。《Flutter 動畫探索 - 流光幻影》的第 16 篇介紹了 Ticker
和 TickerProvider
的原始碼。
比如在 SingleTickerProviderStateMixin
中的一個不起眼的地方,有著一句不起眼的程式碼,這就是 TickerMode 控制動畫的原理
。不知道有多少人能說清 didChangeDependencies
的用途和回撥的時機,又有的多少人整天吵著這個狀態管理框架,那個路由管理工具。連最基本的乘法口訣都背不好,就去學奧數?
TickerProviderStateMixin
中也是類似,通過 TickerMode.of
獲取上層的值,來更新 Ticker
的 muted
屬性。
很多看似毫不起眼
的東西,都是至關重要的存在,也許某一處小細節,就可以讓你豁然開朗。從這裡也能看出 TickerMode
只會對 SingleTickerProviderStateMixin
或 TickerProviderStateMixin
生效。也就是說,如果你是自己建立的 Ticker
,並且沒有在 didChangeDependencies
回撥中進行處理,那麼 TickerMode
就管不住這個 Ticker
。那TickerMode
的使用方式到這裡就介紹完畢,那本文到這裡就結束了,謝謝觀看,明天見~