【技術流】Android 截屏監聽:如何實現截圖分享功能?
1. 背景 :
具體來說就是,檢測到了用戶在應用內有截圖,彈出一個分享界面, 在截圖下方添加一個二維碼,進行分享。
2. 前言
Android系統沒有直接對截屏事件監聽的介面,也沒有廣播,只能自己動手來豐衣足食,一般有三種方法。
- 利用FileObserver監聽某個目錄中資源變化情況
- 利用ContentObserver監聽全部資源的變化
- 監聽截屏快捷按鍵 ( 由於廠商自定義Android系統的多樣性,再加上快捷鍵的不同以及第三方應用,監聽截屏快捷鍵這事基本不靠譜,可以直接忽略 )
3.Android截屏系統做的事情
通過讀源碼(TakeScreenshotService 和 GlobalScreenshot )總結Android截屏系統做的事情:
- 保存截屏Bitmap到本地文件
- 把圖片記錄插入到ContentProvider中
- 發送一個截圖相關的Notification
解決方法:
- 利用FileObserver監聽某個目錄中資源變化情況
- 利用ContentObserver監聽全部資源的變化
4. FileObserver 與 ContentObserver 比較
對於截圖監聽有兩種常用方案
方案一: 通過FileObserver監聽截屏文件夾,當有新的截屏文件產生時,調用設定的回調函數執行相關操作。
優點:
- 實現簡單
缺點:
- 不同手機默認的截屏路徑可能不同,需要做適配處理
- 不同手機截屏觸發的事件名稱可能不同,需要測試適配
- 監聽到截屏事件後馬上獲取圖片獲取不到,需要延遲一段時間
方案二:通過ContentObserver監聽多媒體圖片庫資源的變化。當手機上有新的圖片文件產生時都會通過MediaProvider類向圖片資料庫插入一條記錄,以方便系統的圖片庫進行圖片查詢,可以通過ContentObserver接收圖片插入事件,並獲取插入圖片的URI。
優點:
- 不同手機觸發的事件是一樣的
缺點:
- 不同手機截屏文件的前綴可能不同,需要做適配
- 監聽到截屏事件後馬上獲取圖片獲取不到,需要延遲一段時間
4.1 FileObserver實現
最開始就是想到這個方法, 當FileObserver監聽某個目錄中資源變化情況,時候獲取到文件路徑
a. 關鍵代碼:
- 監聽到截屏事件後馬上獲取圖片獲取不到,可能需要延遲一段時間。 做while循環,收到Create時間後,Thread.sleep(600), 當嘗試最大次數(MAX_TRYS)失敗後放棄。
- SNAP_SHOT_FOLDER_PATH 的路徑不同手機不一樣,要去適配各種手機的路徑
- 需要許可權,否則可能收不到事件。
(如果沒有收到事件,檢查一下許可權和監聽的目錄)
b. 小結:
- 每一次截屏,有多個事件回調
- 每一次截屏,不同的手機,事件回調可能有些不同。
- 不同的手機,默認截屏圖片儲存的文件夾可能不同
- FileObserver只能監聽文件夾中子文件和子文件夾的變化情況,不能監聽子文件夾內部的資源變化
基於 不同的手機,默認截屏圖片儲存的文件夾可能不同 和 可能收不到事件,這種方法並不能適用於所有的機型。
4.2 .ContentObserver實現
放棄了FileObserver方法, 最後選擇了ContentObserver方法。通過ContentObserver監聽多媒體圖片庫資源的變化。當手機上有新的圖片文件產生時都會通過MediaProvider類向圖片資料庫插入一條記錄,以方便系統的圖片庫進行圖片查詢,可以通過ContentObserver接收圖片插入事件,並獲取插入圖片的URI。
a.步驟
(1)添加許可權
(2)初始化、註冊和取消監聽
(3)媒體內容觀察者 (觀察媒體資料庫的改變)
(4)數據改變時查詢資料庫中最後加入的一條數據,處理獲取到的第一行數據。
(5)處理監聽到的資源, 設置最大等待時間500ms (因為某些魅族手機保存有延遲)
(6)設置回調工具
b. 遇到問題:主要問題都在第五步:
(1)因為某些魅族手機保存有延遲 , 輪詢與延遲,設置最大等待時間500ms
(2)要判斷是否是截屏,有可能是用戶自己再文件夾中添加了一張圖片
c. 小結:
- ContentObserver會監聽到所有圖片資源的變化情況,要做好去重過濾工作
- 根據uri去讀取ContentProvider內容時候,記得關閉cursor,防止內存泄漏
- 關鍵字可擴展,大大增加的監聽的範圍,比FileObserver好用多了,但是去重過濾會比FileObserver複雜一些。
5. 二維碼拼接(bitmap)
- Bitmap縱向拼接
參考文獻
1、Android 截屏事件監聽https://juejin.im/entry/58647ee9128fe1006d0f4454
2、嚴選Android-截圖分享功能實現與踩坑分享 http://ks.netease.com/blog?id=7038
3、Android App內截屏監控及塗鴉功能實現 https://www.jianshu.com/p/2e6d52abf115
本文作者:吳思博,網易杭州研究院文學漫畫產品部。
推薦閱讀:
※Android 6.0 還需要使用綠色守護嗎?
※JS 如何獲取和監聽屏幕方向的改變?
※如何看待 MIUI 測試手機會員去廣告功能?
※如何看待三星旗艦s8/s8+ 也是混用快閃記憶體晶元?
※為什麼安卓國行比水貨貴那麼多?