4

I have an issue with WebView, basically I am loading in a forum that has embedded videos in places, if you play a video then rotate the device the video keeps playing in the background and you can get to it to stop it. This also occurs when you minimize the app. Is there a way to stop this?

This is my WebView code I am using.

super.onCreate(savedInstanceState);

        setContentView(R.layout.activity_main);

        this.view = (WebView) findViewById(R.id.webView);

        view.setWebViewClient(new WebViewClient() {
            @Override
            public boolean shouldOverrideUrlLoading(WebView view, String url) {
                if (url != null && url.contains("grcade")) {
                    view.loadUrl(url);
                    view.getSettings().setJavaScriptEnabled(true);
                    return true;
                } else {
                    view.getContext().startActivity(
                            new Intent(Intent.ACTION_VIEW, Uri.parse(url)));
                    return true;
                }
            }
        });

        view.setDownloadListener(new DownloadListener() {
            public void onDownloadStart(String url, String userAgent,
                                        String contentDisposition, String mimetype,
                                        long contentLength) {
                Intent i = new Intent(Intent.ACTION_VIEW);
                i.setData(Uri.parse(url));
                startActivity(i);
            }


        });

        if(savedInstanceState == null){

            String url = "http://grcade.co.uk";
            view.getSettings().setJavaScriptEnabled(true);
            view.loadUrl(url);
            view.getSettings().setSupportZoom(true);
            view.getSettings().setBuiltInZoomControls(true);
            view.getSettings().setDisplayZoomControls(false);
            view.getSettings().setLoadWithOverviewMode(true);

            view.setBackgroundColor(Color.WHITE);

        }

        final SwipeRefreshLayout pulltoRefresh = (SwipeRefreshLayout) findViewById(R.id.pullToRefresh);

        pulltoRefresh.setOnRefreshListener(new SwipeRefreshLayout.OnRefreshListener() {
            @Override
            public void onRefresh() {
                view.reload();
                pulltoRefresh.setRefreshing(false);

            }
        });
    }

    @Override
    public void onSaveInstanceState (Bundle outState)
    {
        super.onSaveInstanceState(outState);
        view.saveState(outState);
    }

    @Override
    public void onRestoreInstanceState(Bundle savedInstanceState)
    {
        super.onRestoreInstanceState(savedInstanceState);
        view.restoreState(savedInstanceState);
        view.getSettings().setJavaScriptEnabled(true);
    }

    //Main WebView Panel End

Any help would be appreciated as I am very confused, I am stopped it occuring with going back but the same method wont work as adding it in causes the app revert to the default webview URL rather than reloading the page the user was on.

Thanks.

Errkal
  • 67
  • 1
  • 8

2 Answers2

13

Pausing/Resuming the Video

The simple way to do this is to pause the WebView when you wish the video to stop playing (i.e. when the app goes into the background). This is simply accomplished by the following code:

WebView view = (WebView) findViewById(R.id.webView);
view.onPause();    // This will pause videos and needs to be called for EVERY WebView you create
view.pauseTimers(); // This will pause JavaScript and layout for ALL WebViews and only needs to be called once to affect all WebViews

The best place to handle this logic is to put your pausing code in the onPause() method of your Activity, and to resume the WebView when the activity comes back in view of the user in onResume:

WebView mWebView; // Initialize this somewhere

@Override
protected void onPause(){
    super.onPause();
    if(mWebView != null){
        mWebView.onPause();
        mWebView.pauseTimers();
    }
}

@Override
protected void onResume(){
    super.onResume();
    if(mWebView != null){
        mWebView.onResume();
        mWebView.resumeTimers();
    }
}

You may be interested in the onPause and onResume as well as the pauseTimers/resumeTimers methods in the WebView.

Handling Orientation Changes

If you don't want your Activity to restart when you rotate the screen (which will stop the WebView from being recreated) then just put

android:configChanges="orientation|screenSize|keyboardHidden|keyboard"

in the <activity> tag of your Activity in your AndroidManifest file. This is not a good practice to follow normally, but when you are using a complex native view like the WebView, it is okay to do (Android web browsers use this to avoid being recreated on rotate). What will happen when using this tag is that the layout will just be resized to fit the landscape orientation and you will have to manually handle any layout specific changes that were being handled using -port or -land folders in your resources. If you are only using one layout though then it is not a problem.

Please see this question/answer for more info on this, and note that it is not encouraged but it will work.

Community
  • 1
  • 1
anthonycr
  • 4,146
  • 1
  • 28
  • 35
  • Thanks for this, I am probably be stupid but where does this go ? I added the view.onpause stuff after if(savedInstanceState == null){ but it just leads to a blank screen. If it helps I can post the full code of my MainActivity so you see what else is there. – Errkal Aug 03 '15 at 19:31
  • You should put the pausing code in the onPause method of your activity where you create your WebView. You can probably just drop the code from the second snippet right into your Activity and then just replace the references to `mWebView` with `this.view` or whatever you named your WebView variable and it hopefully will work. Let me know. – anthonycr Aug 03 '15 at 20:53
  • That works awesome for minimise and restor the video comes back paused perfectly. however when you rotate you are left with a blank screen, is there a way to make this handle rotation too ? – Errkal Aug 04 '15 at 17:30
  • @KelvinBrotherston that's actually a separate issue... it sounds like you aren't saving and restoring the WebView correctly when the Activity restarts. Try putting `android:configChanges="orientation|screenSize|keyboardHidden|keyboard"` in the Activity tag in your AndroidManifest file and see if it fixes that problem. It will stop the activity from restarting when you rotate, which is fine if you don't care about having a different layout for portrait mode. I've updated my answer with info about this. – anthonycr Aug 04 '15 at 17:42
  • why not `mWebView.onResume();` in onResume method? – user25 Aug 21 '16 at 15:23
-1

When minimizing the app, you need to pause your webview. Use this code to pause your webview

Class.forName("android.webkit.WebView")
                        .getMethod("onPause", (Class[]) null)
                        .invoke(webview, (Object[]) null);

And about "Video plays even you rotate your phone", this is the functionality not a bug !

Bunny
  • 576
  • 4
  • 19
  • Hi, for the rotate, I may not have mentioned but you don't see the video, it is hidden so it can't be functionality as what is the point in running the video you cant see ? I will try the onPause though. Thanks :) – Errkal Aug 03 '15 at 13:51
  • Can you post some image for landscape mode ? – Bunny Aug 03 '15 at 13:53
  • Will do later as not have my device with me, basically it shows the page you were on with the embeded video not playing (if you tap it it will load the video and start it) but the video you start before rotation you can hear the audio from playing but can't get to it or stop it without killing the app. – Errkal Aug 03 '15 at 13:54
  • Please do not use reflection to pause the WebView when the method to pause it is a public API! This is unnecessary and a bad idea. – anthonycr Aug 03 '15 at 13:56
  • @anthonycr how would you recommend achieving what I need? EDIT: Just seen it :) – Errkal Aug 03 '15 at 14:13
  • @KelvinBrotherston you use the same method, but just don't access it using reflection as in this answer. Refer the answer I posted or the WebView documentation itself: http://developer.android.com/reference/android/webkit/WebView.html#onPause() – anthonycr Aug 03 '15 at 14:17