谈谈如何学习flutter之flutter成神之路
文章目錄
- 為什么要使用Flutter?
- path 環(huán)境變量
- 運行 `flutter doctor`
- 安裝 Android Studio或者VScode
- Bonus: Move Bottom Panel to the side.
- [高效 Dart 語言指南:API 設(shè)計](https://dart.cn/guides/language/effective-dart/design)
- StatelessWidget 是無狀態(tài)控件,沒有自己的私有數(shù)據(jù),是純展示型的控件,基本定義過程如下:
- 定義有狀態(tài)的控件StatefulWidget
- 定義繼承自 `State` 的狀態(tài)類
- 定義和修改私有數(shù)據(jù)
- 學(xué)習(xí)widget
- 性能優(yōu)化
- 優(yōu)化
- 選擇
- 我的系列內(nèi)容主要包括
為什么要使用Flutter?
為什么學(xué)習(xí)flutter是很多人的疑問,在我個人看來
- 提高開發(fā)效率
- 同一份代碼開發(fā)iOS和Android
- 用更少的代碼做更多的事情
- 輕松迭代
- 在應(yīng)用程序運行時更改代碼并重新加載(通過熱重載)
- 修復(fù)崩潰并繼續(xù)從應(yīng)用程序停止的地方進行調(diào)試
- 創(chuàng)建美觀,高度定制的用戶體驗
- 受益于使用Flutter框架提供的豐富的Material Design和Cupertino(iOS風(fēng)格)的widget
- 實現(xiàn)定制、美觀、品牌驅(qū)動的設(shè)計,而不受原生控件的限制
作為一個零基礎(chǔ)的同學(xué)。學(xué)習(xí)flutter無非就是從安裝配置環(huán)境開始,這個是作為編程人員最基礎(chǔ)的了,在這兒,記住一個地址:https://flutter.cn/
path 環(huán)境變量
如果你想在 Windows 控制臺中運行 Flutter 命令,需要按照下面的步驟來將 Flutter 的運行文件路徑加入到 PATH 環(huán)境變量。
- 在開始菜單的搜索功能鍵入「env」,然后選擇 編輯系統(tǒng)環(huán)境變量。
- 在 用戶變量 一欄中,檢查是否有 Path 這個條目:
- 如果存在這個條目,以 ; 分隔已有的內(nèi)容,加入 flutter\bin 目錄的完整路徑。
- 如果不存在的話,在用戶環(huán)境變量中創(chuàng)建一個新的 Path 變量,然后將 flutter\bin 所在的完整路徑作為新變量的值。
運行 flutter doctor
安裝 Android Studio或者VScode
我用 VScode,畢竟輕量化,這兒有幾個插件值得推薦
Bonus: Move Bottom Panel to the side.
Right looks infinitely better.
Having the Panel at the bottom takes up a lot of space that you could use to read more code. Move your panel to the side instead (your code shouldn’t exceed 80 chars anyway) to use space more efficiently. Open Settings by hitting Ctrl + ,. Then, search for "Panel location". Change it from bottom to right.
這個時候環(huán)境搭建基本完成,就開始學(xué)習(xí)吧,學(xué)習(xí)flutter,建議首先看看dart語法相關(guān)的東西
高效 Dart 語言指南:API 設(shè)計
以及類型之間的相互轉(zhuǎn)換,
List Set Map 還是要重點理解一下,
關(guān)于流程控制語句,if else while do while break container switch case 都是有必要的
接下來就是對dart 的一些庫的了解
庫重名的解決,as ,以及show 屏蔽其他,hide顯示其他
學(xué)習(xí)完這些,再去學(xué)習(xí)flutter相關(guān)的,
相信很快就能做一款自己的app了,
flutter相關(guān)的,其實也就是一個widget的學(xué)習(xí)了,widget,分為兩種
Flutter 中的自定義控件分為兩類:
- StatelessWidget 無狀態(tài)控件
- 純展示型控件,沒有自己的私有數(shù)據(jù)和業(yè)務(wù)邏輯
- StatefulWidget 有狀態(tài)控件
- 業(yè)務(wù)邏輯控件,可以定義自己的私有數(shù)據(jù)和業(yè)務(wù)邏輯
StatelessWidget 是無狀態(tài)控件,沒有自己的私有數(shù)據(jù),是純展示型的控件,基本定義過程如下:
class MyMidget extends StatelessWidget {// 構(gòu)造函數(shù):// 其中的 this.title 定義的是命名參數(shù)// @required 用來規(guī)定某個數(shù)據(jù)在初始化的時候是必須要提供的,否則會報錯。MyApp({Key key, @required this.title}) : super(key: key);// final:用于修飾變量,表示單賦值(single-assignment),// 使用final修飾的變量必須進行初始化,一旦被賦值之后,不能夠再次被賦值,否則編譯會報錯。final String title;// build 函數(shù)相當(dāng)于 react.js 中的 render 函數(shù)// 必須 return 一個 UI 結(jié)構(gòu),用來構(gòu)建當(dāng)前控件對應(yīng)的UI界面// 在 StatelessWidget 控件中,build 函數(shù)是必須的@overrideWidget build(BuildContext context) {return Text(title);} }基本使用過程如下:
void main() => runApp(// MyApp() 函數(shù)的調(diào)用,是 new MyApp() 的簡寫形式,// 其中 title 是構(gòu)造函數(shù)的參數(shù),// 且必須傳遞 title 數(shù)據(jù),因為它已被標(biāo)記為 @required 必填項MyApp(title: 'Flutter初體驗鴨') );StatefulWidget 是有狀態(tài)控件,這樣的控件擁有自己的私有數(shù)據(jù)和業(yè)務(wù)邏輯,基本定義過程如下:
定義有狀態(tài)的控件StatefulWidget
// 定義一個 電影詳情 控件,繼承自 StatefulWidget class MovieDetail extends StatefulWidget {// 構(gòu)造函數(shù),初始化當(dāng)前組件必須的 id 屬性MovieDetail({Key key, @required this.id}) : super(key: key);// 電影的Id值final String id;// StatefulWidget 控件必須實現(xiàn) createState 函數(shù)// 在 createState 函數(shù)中,必須返回一個繼承自 State<T> 狀態(tài)類的對象// 這里的 _MovieDetailState 就繼承自 State<T>_MovieDetailState createState() => new _MovieDetailState(); }定義繼承自 State<T> 的狀態(tài)類
// 這個繼承自 State<T> 的類,專門用來定義有狀態(tài)控件的 業(yè)務(wù)邏輯 和 私有數(shù)據(jù) class _MovieDetailState extends State<MovieDetail> {// build 函數(shù)是必須的,用來渲染當(dāng)前有狀態(tài)控件對應(yīng)的 UI 結(jié)構(gòu)@overrideWidget build(BuildContext context) {// 注意:在這個 _MovieDetailState 狀態(tài)類中,可以使用 widget 對象訪問到 StatefulWidget 控件中的數(shù)據(jù)并直接使用// 例如:widget.idreturn Text('MovieDetail --' + widget.id);} }定義和修改私有數(shù)據(jù)
// 這個繼承自 State<T> 的類,專門用來定義有狀態(tài)控件的 業(yè)務(wù)邏輯 和 私有數(shù)據(jù) class _MovieDetailState extends State<MovieDetail> {// 1. 定義私有狀態(tài)數(shù)據(jù)【以 _ 開頭的數(shù)據(jù),是當(dāng)前類的私有數(shù)據(jù)】int _count;// 2. 通過 initState 生命周期函數(shù),來初始化私有數(shù)據(jù)@overridevoid initState() {super.initState();// 2.1 把 _count 的值初始化為 0_count = 0;}// build 函數(shù)是必須的,用來渲染當(dāng)前有狀態(tài)控件對應(yīng)的 UI 結(jié)構(gòu)@overrideWidget build(BuildContext context) {// 注意:在這個 _MovieDetailState 狀態(tài)類中,可以使用 widget 對象訪問到 StatefulWidget 控件中的數(shù)據(jù)并直接使用// 例如:widget.idreturn Column(children: <Widget>[Text('MovieDetail --' + widget.id + ' --- ' + _count.toString()),RaisedButton(child: Icon(Icons.add),// 3. 指定點擊事件的處理函數(shù)為 _addonPressed: _add,)],);}// 4. 定義 _count 自增的函數(shù)【以 _ 開頭的函數(shù),是私有函數(shù)】void _add() {// 如果要為私有數(shù)據(jù)重新賦值,必須調(diào)用 setState() 函數(shù)setState(() {// 讓私有數(shù)據(jù) _count 自增 +1_count++;});} }兩種狀態(tài)的Widget學(xué)習(xí)完了,就是對其他的widget的學(xué)習(xí)了,
學(xué)習(xí)widget
只要記住在他的核心里面,萬物皆可widget
我常用的也就是例如Container、Padding、Center、Align、Row、Column、Stack、ListView等也有上十種。
Flutter單節(jié)點布局控件功能分類:
對于這些,一定要會理解,會用,當(dāng)然,前期的使用還是比較簡單的。控件雖然這么多,但是大部分不會挨個去嘗試。對于大部分人而言,都是佛系的用法,一個控件能夠使用,就一直用到死。在布局上,大方向還是不停的拆,把一張設(shè)計圖,拆成一棵樹,每個節(jié)點根據(jù)需要,選擇合適的控件,然后從根部開始不停嵌套,布局就完成了。到了后期,就不僅僅是頁面的布局了,而在于對控件的選擇
控件種類繁多,真正使用的時候該如何去選擇呢?有萬金油的做法,不管啥都用Container,這也是很多初接觸的人經(jīng)常干的方式。這么做的確可以按照設(shè)計圖把布局給實現(xiàn)了,但是會涉及到一些性能上的問題。在我看來,控件的選擇,按照控件最小功能的標(biāo)準(zhǔn)去選擇。例如需要將子節(jié)點居中,可以使用Container設(shè)置alignment的方式,也可以使用Center。但是從功能上,Center是最小級別的,因此選擇它的話,額外的開銷會最小。將UI實現(xiàn)了,這只是最基本的,當(dāng)達到這一步了,應(yīng)該更多的去思考,如何更好的布局,使得性能更高。
而在我對于以下我稱為多節(jié)點控件
- 列表:GridView、ListView;
- 單列單行或者多列多行:Row、Column、Flow、Wrap、ListBody、Table;
- 顯示位置相關(guān):Stack、IndexedStack、CustomMultiChildLayout。
這幾個空間還是應(yīng)該學(xué)細一點,GridView、ListView、Row、Column、Stack,這幾個控件基本上涵蓋了大部分的布局了。所以更應(yīng)該重點把握。
性能優(yōu)化
剛才也提到,性能優(yōu)化,關(guān)于性能優(yōu)化,可能仁者見仁,并沒有一個統(tǒng)一的說法,畢竟現(xiàn)在Flutter各方面都還不完善。但是,大方向還是有的,盡量使用功能集更小的控件,這個對于渲染效率上還是有所幫助的。
優(yōu)化
在這里我試著去列舉一些,并不一定都正確。
- 如果一個布局多個控件都可以完成,則使用功能最小的,可以參照上面控件分類中的功能劃分來做取舍;
- 對于多節(jié)點控件,如果單節(jié)點控件滿足需求的話,則去使用單節(jié)點控件進行布局;
- 對于ListView,標(biāo)準(zhǔn)構(gòu)造函數(shù)適用于條目比較少的情況,如果條目較多的話,盡量使用ListView.builder;
- 對于GridView,如果需要展示大量的數(shù)據(jù)的話,盡量使用GridView.builder;
- Flow、Wrap、Row、Column四個控件,單純論效率的話,Flow是最高效的,但是使用起來是最復(fù)雜的;
- 如果是單行或者單列的話,Row、Column比Table更高效;
- Stack和CustomMultiChildLayout如果同時滿足需求的話,CustomMultiChildLayout在某些時候效率會更高一些,但是取決于Delegate的實現(xiàn),且使用起來更加的復(fù)雜;
上面所列的比較雜,但是歸納起來,無非這幾點:
- 功能越少的控件,效率越高;
- ListView以及GridView的builder構(gòu)造函數(shù)效率更高;
- 實現(xiàn)起來比較復(fù)雜的控件,效率一般會更高。
選擇
控件的選擇,個人覺得把握大方向就夠了。如果時間緊急,以實現(xiàn)效率最優(yōu)先,如果時間充裕的話,可以按照一些優(yōu)化細則,去做一些選擇。單純控件層面,帶來性能上的改進畢竟十分有限。
可能需要組建的封裝之類的了,良好的代碼封裝,你會發(fā)現(xiàn)可讀性不僅好,還能提高編碼的樂趣,所以我的目標(biāo)就是寫出詩歌一樣的代碼。
比如寫一個登陸頁面:
利用stack結(jié)合Positioned,實現(xiàn)相對定位,你就會發(fā)現(xiàn),代碼結(jié)構(gòu)好看不說,也利于后期的維護
@overrideWidget build(BuildContext context) {return Scaffold(///填充布局body: Container(width: double.infinity,height: double.infinity,//點擊空白區(qū)域 隱藏鍵盤child: GestureDetector(onTap: () {_userNameFocusNode.unfocus();_passwordFocusNode.unfocus();},child: Stack(children: [//第一層 背景buildBackgroundWidget(),//第二層 氣泡Positioned.fill(child: BubbleWidget(),),//第三層 高斯模糊buildFliterWidget(),//第四層 logobuildLogoWidget(),//第五層來個輸入層buildInputWidget(context),//第六層 關(guān)閉按鈕buildCloseWidget(context)],),)),);這也僅僅是頁面布局,后期很重要的就是與后端的數(shù)據(jù)進行交互了。在這個時候,或許用http也可以,但是還是強烈建議,利用dio
至于其他的一些插件,比如 shared_preferences,share,permission_handler,provider等等插件
之后對于Android和ios底層還要有一些理解,這樣,對于個性化需求,也就不成問題了,學(xué)習(xí)是個漫長的過程,需要不斷堅持,
后期我會結(jié)合我的學(xué)習(xí),工作出一個系列,希望大家繼續(xù)關(guān)注
我的系列內(nèi)容主要包括
1.各個組建的用法,走一步,看一步,畢竟組件挺多的
2.我平時用到的三方插件,目前就有36種,我會出一個專欄
3.平時用到的一些經(jīng)驗,我會利用Demo進行演示
4.遇到的一些報錯,以及解決方案
如果大家還有什么想看的,歡迎在評論區(qū)留言,就讓我們一起利他共享,求實精進。
明天會出 一個提綱,大家的喜歡和點贊就是我最大的鼓勵哦。
總結(jié)
以上是生活随笔為你收集整理的谈谈如何学习flutter之flutter成神之路的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: flutter中state详解
- 下一篇: dart语法中list相关详解