內(nèi)存泄漏--webview

In Android app development, webview is widely used. However, if you are using webview without caution, it will easily consume a lot of memory. And your app may even crash due to insufficient memory.

The memory issue of webview is well-known, here are two great links about the issue.

Post in English

Post in Chinese

For Android 4.4 and above, Android is using chromium as the core of webview. For Android 3.1 to 4.3, Android is using webkit as the core of webview. Most of the memory leak happens on webkit.

And the blog will briefly summarize the tips to prevent webview memory leak

Tip 1: When clearing the webview reference. Simply set it to null is not enough.webview.destroy()must be called. Example code:

123456789

@OverridepublicvoidonDestroy(){super.onDestroy();if(webView!=null){webView.removeAllViews();webView.destroy();}webView=null;}

Tip 2: Using application context when initializing webview. This means webview should not be initialized from xml. You need to create it programmatically. Example Code:

123

WebViewwebView=newWebView(getApplicationgContext());LinearLayoutlinearLayout=findViewById(R.id.xxx);linearLayout.addView(webView);

By doing this, 90% of the time, webview memory consumption is no longer an issue. However, if you want to play a full screen video in your webview, theonShowCustomerViewofWebChromeClientwill be triggered. And beforeonShowCustomerViewis triggered, the Webkit will do some preprocessing. Due to a bug in Webkit’s implementation, a static variable inhtml5videoviewproxywill hold the webview’s reference which will caused a leak and you cannot do much about it.

Another problem using application context is that when your webview wants to popup a window. In webview’s default behaviour, there is a cast fromApplicationContexttoActivityContextwhich will cause your app crash. Of course, you can implement your own method of handling popup to walk around this problem, but it takes a lot of unnecessary effort.

P.S. we can inject javascript into webview to do many tricks. I will later post another blog about using javascript in webview.

Tip 3: I personally did not test this method, but I think the method is creative and instructive so I am noticing it down here.

The main idea is webkit does not provide us a method to release the reference, so let us do it ourself by reflection. The reason why I did not use it is because it highly depends on webkit’s implementation and you have to write different code for different Android versions.

123456789101112131415161718

publicvoidsetConfigCallback(WindowManagerwindowManager){try{Fieldfield=WebView.class.getDeclaredField("mWebViewCore");field=field.getType().getDeclaredField("mBrowserFrame");field=field.getType().getDeclaredField("sConfigCallback");field.setAccessible(true);ObjectconfigCallback=field.get(null);if(null==configCallback){return;}field=field.getType().getDeclaredField("mWindowManager");field.setAccessible(true);field.set(configCallback,windowManager);}catch(Exceptione){}}

Call the method in onCreate and onDestroy

123456789

publicvoidonCreate(BundlesavedInstanceState){super.onCreate(savedInstanceState);setConfigCallback((WindowManager)getApplicationContext().getSystemService(Context.WINDOW_SERVICE));}publicvoidonDestroy(){setConfigCallback(null);super.onDestroy();}

Ultimate Tip: This method is the ultimate way to solve the problem and many well-known app such as QQ and Wechat are using it as well.

The idea is to start a separate process for webview and kill the process when existing the webview. The drawback of doing this is that you need to handle interprocess communication carefully. My suggestion is you can create apreProcessProxyandpostProcessProxyto handle IPC and passing information around using intent.

Example code: define webview activity in a separate process

12345

Kill the process when destroying the activity

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時(shí)請結(jié)合常識(shí)與多方信息審慎甄別。
平臺(tái)聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點(diǎn),簡書系信息發(fā)布平臺(tái),僅提供信息存儲(chǔ)服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

友情鏈接更多精彩內(nèi)容