天天看點

android開發使用fragment commit時的一些坑

今天在開發過程中,發現一個問題,花了将近兩個小時才解決。現在我把問題描述一下。我有一個兩個界面(Activity),在第一個activity中使用了幾個tag頁的樣式,每個tag頁對應一個fragment,我寫了一個函數setChartSelector,專門用來進行切換tab頁的,當點選某一個地方時,進入橫屏的界面。橫屏界面也有幾個tag頁,和第一個activity的tab是一樣的。我們的需求是,在橫屏界面選擇某一個tab頁以後,傳回到豎屏界面也要顯示對應。但奇怪的是,我從橫屏傳回,豎屏界面的setChartSelector也執行了,但是在fragment commit送出的時候,出現異常了。異常資訊為:Can not perform this action after onSaveInstanceState。不切換螢幕時,在豎屏都是沒有問題的。請見下圖:

android開發使用fragment commit時的一些坑

這個界面是豎屏,有分時、日k、周k、月k、分鐘,這些tab,其實就是兩個fragment。通過show和hide進行控制的。我們來看看橫屏界面。

android開發使用fragment commit時的一些坑

這個是橫屏,橫豎屏的分時、日k等tab是對應。如果使用者在這個界面選擇日k以後,傳回豎屏,就停留在日k上。我原來以為這簡單,在橫屏界面傳回時通過android eventbus post一個消息給豎屏界面,在豎屏界面接收到消息以後,調用setChartSelector即可。按照我這種想法做了以後就出現在FragmentTransaction commit時報Can not perform this action after onSaveInstanceState的異常,我使用的三星note 3手機測試,這個異常資訊我還是跟蹤調用fragment擷取的,真是一波三折。沒想到這麼簡單的一個功能花了這麼久的時間,于是我就去網上找資料。發現有一個哥們也出現過這種情況,解決這個問題很簡單,将commit(),替換成commitAllowingStateLoss()即可。

問題總算是解決了,但是我并不知道原因。于是我在網上又找到一篇文章。位址:http://zhiweiofli.iteye.com/blog/1539467。也說到這個異常。看完之後,我總算搞清楚原因了。我們知道activity在容易被系統銷毀或者說即将被銷毀時,系統通過回調onSaveInstanceState方法通知我們,以便我們在這個方法内部做一些狀态保持的工作。

然後,我就在豎屏界面重新了這個onSaveInstanceState方法,沒想到跳轉到橫屏界面時,豎屏的這個方法确實會執行。既然調onSaveInstanceState方法了,說明系統可能要回收這個activity,然後你在傳回時commit,那當然就是所提示的。。。 after onSaveInstanceState,也就是說,在 onSaveInstanceState之後不能處理一些事件了。

這可能是android的一個bug。今天特将這個問題記錄下來。

繼續閱讀