【问题标题】:Android power button and webview or possibly activity lifecycleAndroid 电源按钮和 webview 或可能的活动生命周期
【发布时间】:2016-02-15 18:29:01
【问题描述】:

我在使用 webview 和电源按钮时遇到活动生命周期问题。

我在 webview 中加载带有游戏的 javascript 页面,并且我将 webview 保留在应用程序上下文中,因此它可以在 Activity 破坏中幸存下来。我知道我不应该像这样保存视图,但我有非常具体的场景,它是唯一的解决方案。在应用程序之间切换时它工作正常(即使使用“不保留活动”调试标志)但是当我这样做时:

  1. 使用 webview 运行活动
  2. 游戏加载到 webview 后,按电源按钮关闭屏幕
  3. 重新打开屏幕
  4. 解锁屏幕(向上滑动)
  5. activity 会加载,但是 webview 没有加载,只是黑屏

我尝试打印出所有活动生命周期方法,并且在两种情况下都相同。这两种情况有什么区别?

代码应用上下文:

public class MyApp extends Application {
    private WebView mWebView;

    //getter, setter ...
    //preserving webview in app context
}

代码活动:

public void onCreate() {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main);
    initWebView();
}

private void initWebView() {
    MyApp app = (MyApp) getApplication();
    mWebView = app.getWebView();
    if (!app.isWebViewInitialized()) {
        mWebView.getSettings().setJavaScriptEnabled(true);
        mWebView.getSettings().setDomStorageEnabled(true);
        mWebView.requestFocus();
        mWebView.addJavascriptInterface(new JavascriptInterface(this), "JSInterface");
        mWebView.loadUrl("http://js-game-url.com");
        mWebView.setLayoutParams(new LinearLayout.LayoutParams(LinearLayout.LayoutParams.MATCH_PARENT, LinearLayout.LayoutParams.MATCH_PARENT));
        mWebView.setWebViewClient(new WebViewClient());

        app.setWebViewInitialized(true);
    } else {
        try {
            ((ViewGroup) mWebView.getParent()).removeView(mWebView);
            //todo remake the try catch
        } catch(NullPointerException e) {
            System.out.println("Null");    //todo remove try catch
        }
    }


    webviewPlaceholder = (RelativeLayout) findViewById(R.id.rlayout2);
    webviewPlaceholder.addView(mWebView);
}

protected void onPause() {
    super.onPause();
    webviewPlaceholder.removeView(mWebView);
}

protected void onResume() {
    super.onResume();
    initWebView();
}

protected void onDestroy() {
    super.onDestroy();
    webviewPlaceholder.removeView(mWebView);
}

我肯定错过了一些简单的东西,但我找不到解决方案。

【问题讨论】:

  • 对不起,我删除了我的其他答案。在尝试了解您要做什么之后,我认为这是不可能的。 WebView 并非旨在通过保存持久状态来像完整的 Web 浏览器一样长时间保存(甚至 saveState 和 restoreState 方法都不会做你想做的事情。如果你真的需要保存状态,你将不得不构建WebView 内容和应用程序之间的 javascript 桥梁,并确保它可以保存和恢复您需要的任何内容。
  • 它工作正常,您可以终止活动,并且 webview 与游戏进度一起正确存储,并在再次创建活动后重新加载。问题是当您使用电源按钮关闭屏幕与在 2 个打开的活动之间切换时,活动的生命周期可能存在一些差异。
  • 如果JS还没有加载,当你关闭屏幕时,你的工作很可能会停止,因为你没有CPU的唤醒锁。如果您完全加载游戏,然后在加载完所有内容后关闭屏幕会发生什么?
  • @Darwind 在这两种情况下,webview 都不会加载,但我想我知道问题出在哪里。它不是活动生命周期,而是 javascript 或游戏生命周期。因为当窗口失去焦点时游戏会自行暂停,并且我认为 js 在这两种情况下会触发不同的事件,所以我必须通过一些简单的示例对其进行测试。
  • 是的,我是对的 - webview 在我的场景中没有获得焦点:mWebView.requestFocus();解决了问题

标签: android android-activity webview android-lifecycle


【解决方案1】:

这不是活动生命周期的问题,而是 webview javascript 生命周期。当重新打开屏幕后重新创建活动时,webview 没有获得焦点。这修复了它:

mWebView.requestFocus();

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2023-04-05
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2013-01-13
    • 2011-12-18
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多