Flutter — 如何讓你的 Flutter 程式碼容易修改?

Andy Lu
Mar 2, 2024
Image by Pexels from Pixabay

Everything is widget,開發 Flutter 的時後,因為它是聲明式的語法,如果一個稍微複雜的頁面,很可能就會使用很多 widget ,進而容易寫出落落長的超大 widget(而且很複雜)。

這個情況在我現在維護的專案上尤其嚴重,在同一支檔案中有個三、四百行也是很常見的事(甚至更多)。

而當檔案行數越多時,越不容易看到整個頁面的架構,要找到要修改的點時,比起簡潔的檔案要困難的許多。

如果你也跟我一樣在維護複雜的 Flutter 專案,以下是我的建議:

按照 widget 的大小採用不同的命名方式

在檔案命名的時候,我習慣將整頁的 widget 的檔案名稱後面加上 _page 後綴字,如:login_page.dart ,當然其類別名稱就為 LoginPage 。 若是使用如 BottomNavigationBar 分隔不同的頁面,可以將檔案名稱後面加上 _layout 後綴字,表示是一個大的子頁面。 再者,假如是一個頁面中的小物件,可以加上 widget 或是不加。 當我們採用不同命名規則時,就可以輕鬆在檔案目錄內看到不同的檔案類型,如此就可以一眼看出我們該去哪個檔案修改。

將常常使用的小物件,包成共用的 widget

我們在修改的時候,有些時候經常會有類似的調整,如加上相同的 padding,使用相同的 BoxDecoration... 等,如果在每個使用的地方都有特別的參數,當需要調整時,將會是一場災難,因為有可能會沒辦法一口氣修改所有的物件,造成不一致的情況。

有這種情況時,我們可以將這些細部的調整包成一個 widget 來使用,並將其放在獨立的檔案中,這樣一來,如果需要調整時,只要調整這個 widget,所有使用到的地方就可以一口氣作修改。

筆者目前在開發時,設計師採用的設計方式是原子設計 — 先設計物件,再將這些物件套用在畫面中,所以實作時,就可以先將這些物件建立好,之後就可以使用堆積木的方式來使用這些物件。

不過將這些設定值包起來時,需要考慮共用性,如果貿然的包起來,有可能會在後續的使用上更麻煩。如:將 Expanded 包起來,當使用的頁面上原本就有 Expanded 時,就有可能會發生錯誤。

使用 partpart of 拆分子物件

上一點提到如果有共用的子物件,我們可以把這個物件拆出並放在新檔案內,並在其他頁面重複使用。但如果我們不希望讓這個子物件可以被重複使用呢?換句話說,這個子物件只用於現在的頁面內,而我們只是為了方便閱讀,避免單一檔案太過冗長,於是將這個物件拆至其他的檔案中。 將物件由目前頁面拆出之後,放在新建的檔案內,我們可以在檔案的最上方加上 part of '主頁面檔案位置' ,表示這個檔案是這個檔案的一部分,並在原頁面上加入 part '子物件檔案位置' 用以宣告有一個子物件可以使用。 使用 partpart of 就可以讓目前頁面的內容更為簡便,也就更容易檢視。

使用狀態管理,如 BLoCProvider...

一個頁面中,如果將頁面以及商業邏輯都包在一起,當新需求、 Bug 來臨,這種程式碼會讓我們難以修改。如果可以將邏輯的部分拆至 BLoC 或是 Provider 中,在該頁面只需要管理其狀態,也就是說狀態的調整邏輯就不會跟 UI 混在一起,當需要針對任何一部分修改都會相對容易,更不用說把商業邏輯與 UI 拆分,就更容易加上 Unit Test。

結論

因為 Flutter 的特性,容易造成在一個檔案包含太多內容、讓程式碼的長度太長而不易修改、除蟲。 為了避免這個情況,我們只要適當的將檔案內容搬移到其他地方,藉由一些簡單的重構方式,就可以大幅度縮減單一檔案的大小。

而將狀態管理邏輯整合進頁面內時,就可以讓 UI 與商業邏輯分離,UI 只會根據狀態來改變,而不需要處理其背後的邏輯。這樣一來,當需求來臨,我們就能夠輕易的找到修改的地方,快快樂樂的解決手上的問題。

後記

好久沒有寫 Flutter 文章了,前面的文章都是寫 Kotlin 為主,最近換到新公司,是以 Flutter 開發,而我又是唯一個 Flutter 工程師,我應該會有很多心得分享吧 XD

如果覺得我的文章不錯,有幫助到你,可以👏拍手鼓勵我。

謝謝

--

--

Andy Lu

Android/Flutter developer, Kotlin Expert, like to learn and share.