在活动之外的Webview中显示AlertDialog

时间:2014-09-25 17:01:21

标签: android service webview alertdialog

我一直致力于开发类似于Facebook聊天功能的功能 - 即使他们离开我们的应用程序去查看电子邮件等,我们的用户也需要有效的功能。它需要是能够通过javascript创建AlertDialogs - 从用户切换我们的应用程序内的活动时不受影响的地方。当用户离开应用程序执行其他操作时,该功能可以关闭/隐藏 - 但是当它们返回时它仍然必须存在。

除了使用服务之外,我还没有想过让用户在做其他事情时与我们互动的另一种方式。当我使用服务通过WindowManager创建webview时,webview的JsDialogHelper检测到上下文不是活动并阻止它显示AlertDialogs。

任何想法对于完成这项工作最有帮助。我们需要允许AlertDialogs弹出并交互使用此功能。我们需要webview在活动转换之间保持一致。

是否可以扩展JsDialogHelper以便我可以使用我的代码?有没有更好的方法让我在Facebook应用程序中使用网页浏览功能进行Facebook聊天,我还没有想到呢?如果它能够获得我正在寻找的用户体验,我就可以完成重写。

3 个答案:

答案 0 :(得分:2)

您可以通过将窗口类型设置为Dialog来显示服务中的TYPE_SYSTEM_ALERT。请务必使用传递给JsResult的{​​{1}}实例回复用户所采取的操作。

onJsAlert

向清单文件添加所需权限:

    // maintain reference to JsResult instance passed to onJsAlert, in order
    // communicate back the action taken by the user.
    private JsResult mResult; 

    webView.setWebChromeClient(new WebChromeClient() {
        @Override
        public boolean onJsAlert(WebView view, String url, String message, JsResult result) {
            mResult = result;
            AlertDialog dialog = new AlertDialog.Builder(MyService.this)
                    .setTitle("Custom Dialog")
                    .setMessage("This is our custom dialog, not the one served by JsDialogHelper")
                    .setOnCancelListener(new CancelListener())
                    .setNegativeButton("Cancel", new CancelListener())
                    .setPositiveButton("Ok", new PositiveListener())
                    .create();
            dialog.getWindow().setType(WindowManager.LayoutParams.TYPE_SYSTEM_ALERT);
            dialog.show();

            return true;
        }
    });

    private class CancelListener implements DialogInterface.OnCancelListener,
        DialogInterface.OnClickListener {

        @Override
        public void onCancel(DialogInterface dialogInterface) {
            mResult.cancel();
        }

        @Override
        public void onClick(DialogInterface dialogInterface, int i) {
            mResult.cancel();
        }
    }

    private class PositiveListener implements DialogInterface.OnClickListener {

        @Override
        public void onClick(DialogInterface dialogInterface, int i) {
            mResult.confirm();
        }
    }

替代解决方案: 如果可以构建特定于android webview的Web应用程序,那么您可以创建Javascript接口,这将允许Javascript代码直接调用Android代码,Android代码又为您显示对话框。这避免了<uses-permission android:name="android.permission.SYSTEM_ALERT_WINDOW" /> 路线。

  1. 定义javascript界面​​:
  2. JsDialogHelper
    1. 使用addJavascriptInterface
    2. 绑定Javascript和Android代码之间的界面
        

      webView.addJavascriptInterface(新的WebAppInterface(this),&#34; Android&#34;);

      1. 在Javascript代码中使用界面。
      2. public class WebAppInterface {
            Context context;
        
            WebAppInterface(Context c) {
                context = c;
            }
        
            // Annotation required for api >= 17
            @JavascriptInterface
            public void showDialog() {
                AlertDialog dialog = new AlertDialog.Builder(context)
                        .setTitle("Custom Dialog")
                        .setMessage("This is our custom dialog, not the one served by JsDialogHelper")
                        .create();
                dialog.getWindow().setType(WindowManager.LayoutParams.TYPE_SYSTEM_ALERT);
                dialog.show();
            }
        }
        

答案 1 :(得分:1)

您无法在AlertDialog之外显示Activity

但是,您可以构建一个自定义View,它看起来就像您要显示的对话框,并通过WindowManager在窗口中显示。

例如:

WindowManager windowManager = (WindowManager) getSystemService(WINDOW_SERVICE);

WindowManager.LayoutParams params = new WindowManager.LayoutParams(
                WindowManager.LayoutParams.WRAP_CONTENT, 
                WindowManager.LayoutParams.WRAP_CONTENT
                WindowManager.LayoutParams.TYPE_PHONE,
                0,
                PixelFormat.TRANSLUCENT);

params.gravity = Gravity.CENTER;

windowManager.addView(yourView, params);

上面的代码会在屏幕中央显示您的自定义视图,而不是其他所有内容。您可以通过LayoutInflater扩充视图。

您还需要在清单中添加权限才能显示视图。

<uses-permission android:name="android.permission.SYSTEM_ALERT_WINDOW" />

答案 2 :(得分:1)

我想您可以为JavaScript Interfaceactivity之间的双向通信创建WebView。我自己没有尝试过这个解决方案,但在此之前就已经绊倒了。 SO Question posted here可能对您有所帮助。

我认为您的WebView也会驻留在某个活动中,您可以使用活动的上下文弹出AlertDialog。您只需要在webview中调用活动中的方法(我只需在addJavascriptInterface方法中传递活动对象)。

另一种方法是使用服务并启动一个新的Activity,在其中实现Theme.dialog以用作AlertDialog。

如果它没有解决您的问题,请告诉我。