WKWebView, UIWebView H5標簽input type=file didmis問題處理 選擇圖片攔截

導致問題的html代碼是這一句:<input type = "file" name = "file"> 調用app的UIDocumentMenuViewController控制

問題發生場景:VC presentViewController 顯示 webVC;

或者VC presentViewController 顯示NVC,webVC在NVC上

這時候在H5上的? input type = "file" 觸發后會導致UIDocumentMenuViewController 和 pre出來的VC(顯示webVC的界面)兩個直接dismis掉,

控制臺會打印這么句警告: ?Warning: Attempt to present <UIImagePickerController: 0x1018a0600> on <XXController: 0x100506020> whose view is not in the window hierarchy!?

個人覺得這是apple的一個bug,應該有開發者反饋了才對,但是到目前WKWebView, UIWebView還存在這個問題,具體原因不曉得,坐等apple修復,在這之前可以參考我的處理方式,把那demo里的UIViewController+Dismis_FileUploadPanel ?.h和.m文件拖到項目里就ok了,不需要額外代碼。修復處理邏輯看下文:

bug出現位置

經過分析,發現是WKFileUploadPanel(或 UIWebFileUploadPanel)這么個東西的 _dismisDisplayAnimated: 方法執行的,直接代碼是在UIDocumentMenuViewController控制器關閉后的completion內觸發。

調試堆棧WKWebView


調試堆棧UIWebView

分析后發現 UIDocumentMenuViewController 和 webVC 之間并沒有什么關系(pre關系),只是和WKFileUploadPanel(或 UIWebFileUploadPanel) 這貨有關系(delegate關系),基于這一點結合runtime切入,在presentViewController:animated: 時候對特殊UIDocumentMenuViewController進行標記,

pre標記處理

由于cancel是由UIDocumentMenuViewController發起的,所以也對其進行標記。

dismis處理

然后dismissViewControllerAnimated:animated:時候的completion對標記對象進行區分處理,由于兩次dismis是兩個無關的vc順序執行,所以用一個靜態變量dismisFromFileUploadPanel 來標記是否是UIDocumentMenuViewController之后的dismis。

標記的目的是其它正常的dismis可以正確執行,避免其它bug出現。

更新:新增選擇圖片攔截,可知道選擇的圖片信息,修復選擇圖片攔截bug

分析發現圖片文件選擇走的是UIImagePickerController,而UIImagePickerController是通過代理返回結果集,那么在FileUploadPanel內部就必然有回調方法,否則無法完成圖片獲取操作

之前嘗試runtime對WKFileUploadPanel 或 UIWebFileUploadPanel 采用方法替換攔截測試不可行,

新的攔截思路采用代理攔截器實現,在UIImagePickerController setDelegate:時候增加_UIImagePickerController_IFUP 攔截[imagePickerController: didFinishPickingMediaWithInfo:]代理事件

具體實現看demo:https://github.com/youlianchun/WebView_FileUploadBug

最后編輯于
?著作權歸作者所有,轉載或內容合作請聯系作者
平臺聲明:文章內容(如有圖片或視頻亦包括在內)由作者上傳并發布,文章內容僅代表作者本人觀點,簡書系信息發布平臺,僅提供信息存儲服務。

推薦閱讀更多精彩內容