[譯] 為什麼每個 Android 開發者都應該嘗試 Flutter

ALVIN君發表於2018-07-30

幾個月前,我寫過一篇題為“為什麼 Flutter 能最好地改變移動開發”的文章。雖然已經過去了一段時間,但是我對 Flutter 的熱愛依然非常強烈;事實上,當我繼續使用它時,我意識到了我之前忽略了 Flutter 獨特方面的重要性。不要誤會我的意思 —— 我仍然認為 Flutter 最強大的一點就是如何解決跨平臺開發的許多問題。但最近我開始關注移動開發發展的更多領域,特別是宣告性使用者介面的概念。

[譯] 為什麼每個 Android 開發者都應該嘗試 Flutter

攝影者:來自 UnsplashChris Charles

我相信你已經聽過一系列關於為什麼 Android 開發者應該關注 Flutter 的若干論據(如果你還沒有看過,請讓我謙遜地建議你瞧瞧這個),但是我想指出一個我還沒有真正解決的大問題,那就是 Flutter 可以讓你對 App 開發有完全不同的看法。首先,你的應用本身將採用不同的方式構建 —— 但更重要的是,實際的 UI 開發通過將其合併到你的 Dart 程式碼(而不是 XML)中而被推到前臺,因此使它成為了“一等公民”。一旦你的 UI 程式碼突然出現在一種非標記語言中,你就會意識到你突然有了構建應用的可能性。說實話,在使用 Flutter 之後,我開始討厭在 Android 上編寫 UI 程式碼;因為在 Android 中步驟更加繁瑣,雖然你仍然可以使用資料繫結等工具構建響應式應用,但它實際上比 Flutter 中要花費更多的時間。

當你考慮在 Android 中整合動畫和其他動態資料時,使用 Flutter 的論點變得更加有力。整合動畫可能會不太方便,有時你可能不得不拒絕設計師的要求,因為要實現他們的需求太難了。謝天謝地,Flutter 改變了這一切。如果你一直在關注 Flutter,你可能已經從 Fluttery 聽說過 Flutter 挑戰。這些挑戰展示了構建具有大量自定義元件和精美設計(包括動畫)的複雜 UI 的快速和直觀性。在 Android 上實現這樣的東西會變得非常困難 —— 特別是因為與 Flutter 不同,Android 的檢視基於繼承而非組合,這使得構建檢視變得更加複雜。

下面,讓我們切入正題:使用 Flutter 構建宣告性 UI,這改變了 UI 開發的一切。現在也許你在想,Android 佈局不也是以宣告方式構建的嗎? 答案是肯定的,但事實不是。使用 XML 來定義佈局讓我們有了以宣告方式定義佈局的感覺,但如果你的檢視是完全靜態的,並且所有資料都是以 XML 格式設定的,那麼這種感覺才真正成立。不幸的是,這種情況幾乎從未發生過;一旦新增動態資料和類似列表之類的東西,你自然必須使用一些 Java / Kotlin 程式碼將資料繫結到檢視。然後我們最終得到某種 ViewModel,它將資料設定為檢視。想象一下,這就像在 Android 上呼叫 textView.text =“Hello Medium!” 一樣。在 Flutter 上,這是完全不同的:你建立了一個包含某個狀態的視窗元件類,然後根據該狀態以宣告方式定義你的佈局。每當狀態改變時,我們呼叫 setState() 來重新渲染我們改變的元件樹的部分。讓我們看一下如何在 Flutter 中使用 API,並使用結果渲染一個 List:

@override
Widget build(BuildContext context) {
  return new FutureBuilder<Repositories>(
    future: apiClient.getUserRepositoriesFuture(username),
    builder: (BuildContext context, 
        AsyncSnapshot<Repositories> snapshot) {
      if (snapshot.hasError)
        return new Center(child: new Text("Network error"));
      if (!snapshot.hasData)
        return new Center(
          child: new CircularProgressIndicator(),
        );
      return new ListView.builder(
        itemCount: snapshot.data.nodes.length,
        itemBuilder: (BuildContext context, int index) =>
            new RepoPreviewTile(
              repository: snapshot.data.nodes[index],
            ),
      );
    },
  );
}
複製程式碼

在這裡,我們使用了 FutureBuilder 來等待網路呼叫(Future)的完成。一旦網路呼叫完成,出現結果或錯誤,FutureBuilder 元件會在內部呼叫 setState 來呼叫所提供的 builder 方法來重新渲染。正如你在這個例子中看到的,一切都是宣告式的。在 Android 上做同樣的事情通常需要一個被動的 XML 佈局,然後需要一些其他類來手動設定狀態,比如 Adapter 和檢視模型。這種方法的問題在於,狀態可能與螢幕上渲染的狀態不同。這就是為什麼我們希望擁有像 Flutter 為我們提供的那樣的宣告性佈局。我們最終編寫的程式碼要少得多,同時將狀態繫結到要在螢幕上顯示的內容。

有了這些宣告性佈局,我們也開始對架構進行了不同的思考。突然間,reactive 這個詞出現了,我們談論了更多的是關於狀態管理的內容,而不是架構。有了 Flutter,像 MVP 和 MVVM 這樣的架構已經沒有多大有意義了;我們不再使用它們了,而是考慮狀態如何流經我們的應用。狀態突然成為討論的一個重要部分,我們將投入越來越多精力去思考構建應用的新方法上。這對我們所有人來說都是一次新的旅程,有許多事情可以解決,但最重要的是,這是我們開闊視野的機會。

坦白地說,Flutter 也不只有陽光和彩虹。我目前正在與 Flutter 合作開展一個更大的專案來了解它的弱點,迄今為止我遇到的最大缺陷是缺乏基礎設施。當我嘗試使用 Graphql-API 時,這個問題就非常明顯;雖然有庫確實會這樣做,但它們並沒有接近 Android 與 Apollo 的關係。不過,好訊息是,Flutter 迎頭趕上只是時間的問題,在此期間擴充套件現有的庫,甚至建立自己的庫並不困難。請注意,你可能需要花一些時間投入在應用程式的基礎設施中,而對於 Android 和 iOS 來說,情況通常並非如此 —— 畢竟,天下沒有免費的午餐。

最後,我最近從使用 Flutter 中得到的最大啟示之一就是,體驗這種構建 UI 的宣告方式以及它對狀態管理的影響是非常有用的。我覺得 Flutter 太棒了;不過,我告誡你不要把它當作解決你所有問題的銀彈,而應該是作為一種創新的工具,它可以比在 Android 上更快地構建漂亮的自定義 UI。更重要的是,它展示了強大的宣告性佈局功能,並讓你將應用視為渲染狀態,而不是非連貫性 Activity,檢視和檢視模型 —— 僅此而言,我強烈建議你嘗試一下 Flutter。

如果發現譯文存在錯誤或其他需要改進的地方,歡迎到 掘金翻譯計劃 對譯文進行修改並 PR,也可獲得相應獎勵積分。文章開頭的 本文永久連結 即為本文在 GitHub 上的 MarkDown 連結。


掘金翻譯計劃 是一個翻譯優質網際網路技術文章的社群,文章來源為 掘金 上的英文分享文章。內容覆蓋 AndroidiOS前端後端區塊鏈產品設計人工智慧等領域,想要檢視更多優質譯文請持續關注 掘金翻譯計劃官方微博知乎專欄

相關文章