很高興見到你 👋 我是 Flywith24,這是我在掘金髮布的第 53 篇文章。android
「Fragment多返回棧」是一個新的系列,主要追蹤官方對 Fragment 多返回棧這一功能的實現過程,透過該過程,咱們能夠學習官方面對一個新功能是如何進行開發的。git
本文是該系列的開篇,內容分爲三部分:github
本文對上述內容均是簡單介紹,使用圖片的方式形象地表述該部份內容(爲此專門學習了 Sketch 🤣,我這麼拼你好意思不點贊嘛?😋)。微信
關於源碼詳解,以及官方對此多返回棧功能支持所有時間線,可參考我以前的文章 【背上Jetpack之Navigation】想去哪就去哪,Android世界的指南針。markdown
OK,讓咱們開始吧~app
提到返回棧,大多數小夥伴應該想到 Activity 返回棧。其實 Fragment 也是有返回棧的。關於 Fragment 的源碼解析能夠參考我以前寫的 從源碼的角度看Fragment 返回棧 附多返回棧demo。ide
簡單總結一下 Fragment 的返回棧:oop
使用 addToBackStack() 方法能夠將 Fragment 添加到返回棧。其內部將 mAddToBackStack
賦值爲 true。post
FragmentManager
的實現類 FragmentManagerImpl
內部經過 ArrayList<BackStackRecord> mBackStack
管理返回棧。學習
若是 mAddToBackStack
爲 true,則將 Fragment 加入到返回棧。
現有 API,一個 FragmentMnager 只對應一個返回棧。咱們舉一個形象的例子
以下圖所示,Activity 中使用四個 FragmentContainerView
做爲不一樣花色撲克的容器。
其中每一個容器內會按牌面大小順序發牌,如 ♥A → ♥2 → ♥3... 最終收牌時會嚴格按照發牌順序進行回收。效果以下所示:
上述示例使用 Activity 的 FragmentManager 管理全部 Fragment,它們被組織在一個線性的結構裏。咱們能夠將其理解爲 單返回棧。
前文咱們提到,現有 API 一個 FragmentMnager 只對應一個返回棧,官方尚未提供單 FragmentMnager 管理多個返回棧的 API。那麼咱們能夠實現多返回棧嗎?答案是能夠的,咱們能夠使用多個 FragmentManager 來實現。
如上圖所示,綠色部分爲 Fragment 容器,頂部四個 tab 分別對應不一樣花色。建立四個 NavHostFragment
(自定義的,與 navigation 無關)。點擊其中一個花色 tab 便將對應的 NavHostFragment
attach 到容器,並將其它 NavHostFragment
dettach。最終效果以下:
這裏的關鍵是使用了四個 NavHostFragment
(上圖中四個花色的 NavHostFragment 實例不一樣)做爲每一個返回棧的「宿主」,它們擁有本身的 FragmentManager
,維護着本身的返回棧。
Navigation 在管理帶有平級關係的界面時會出現問題,【背上Jetpack之Navigation】想去哪就去哪,Android世界的指南針 一文中已經探討過該問題。
這裏舉例說明一下:
新建 Project,選擇 Bottom Navigation Activity 模版:
該項目由一個 Activity(MainActivity) 以及三個 Fragment(Home,Dashboard,Notifications)組成。
結構示意圖以下:
在內部,三個 Fragment(Home,Dashboard,Notifications)都由 androidx.navigation.fragment.NavHostFragment
管理,即便用 NavHostFragment
的 FragmentManager
管理返回棧。
每次點擊底部按鈕,都會新建 Fragment 實例(但它們的宿主未發生變化):
這裏出現了不符合預期的現象,若是從 HomeFragment 點擊跳轉到 ChildFragment,點擊 Dashboard 按鈕後再點擊 Home 按鈕,因爲 HomeFragment 重建,原來的 ChildFragment 消失。以下圖:
本質上,上面的示例是一個單返回棧的模型。由於三個 Fragment(Home,Dashboard,Notifications)都由 androidx.navigation.fragment.NavHostFragment
直接管理,而目前單個 FragmentManager 僅支持一個返回棧。
而這種平級的模型是須要多返回棧進行管理的,即 Home,Dashboard,Notifications 均擁有各自的返回棧。它們相互獨立,互補影響。但以現有的 API 實現起來比較複雜,實現方式參考多返回棧一節。
上述問題早在 2018 年就已提出,地址 在這。
而在 2021 年 1 月,官方終於開始着手解決這一問題。
該功能將在 Fragment 1.4.0 和 Navigation 2.4.0 版本提供。
Navigation 管理帶有平級關係的界面時,以現有的 API 會產生不符合預期的現象。本質上,該問題是因爲現有的 API 不支持多返回棧形成的。好在官方已開始着手開發這一功能,該功能將在 Fragment 1.4.0 和 Navigation 2.4.0 版本提供。發佈正式版可能須要一年多的時間。雖然很慢,好在有但願。該系列會持續追蹤這一過程,讓咱們看看官方是如何在已有項目上進行新功能開發的吧~😉
咱們下期見。
人老是喜歡作可以得到正反饋(成就感)的事情,若是感受本文內容對你有幫助的話,麻煩點亮一下👍,這對我很重要哦~
我是 Flywith24,人只有經過和別人的討論,才能知道咱們本身的經驗是不是真實的,加我微信交流,讓咱們共同進步。
插入一點廣告,掘金年度打榜投票正在進行中,若是個人文章對您有幫助的話,記得爲我投票哦~ 點此投票。