当弹出窗口显示时,onBackPress未被调用

5

当弹出窗口显示时,我希望处理返回按钮的操作。在某些情况下,我想要关闭它,在某些情况下,我不想在弹出窗口中执行一些任务。

当弹出窗口显示时,Activity的onBackPress方法将不会被调用。那么当弹出窗口显示时,如何捕获返回按钮事件呢?


请返回已翻译的文本:点击此处,并阅读其评论。 - CRUSADER
将背景可绘制设置为非空将始终关闭弹出窗口。我有一些情况,我不想关闭弹出窗口,而是在弹出窗口内执行一些任务。那么,在弹出窗口可见时,是否有任何方法可以捕获后退按键事件? - Nitesh V
5个回答

6
你需要在你的PopupWindow上调用setBackgroundDrawable(),并将背景设置为非null。听起来很奇怪,但如果在你的PopupWindow上没有设置background,它就无法检测到来自Activity的事件,例如点击窗口外部或返回按钮。

几天前我也遇到了同样的问题。我会尝试找到一个SO答案,解释为什么会这样,但可能需要一点时间。与此同时,请尝试一下,应该可以解决。

找到了

我还没有机会测试它,但你可以尝试添加一个keyEventListener,像这样进行操作:

public boolean onKeyDown(int keyCode, KeyEvent event) 
{
    if (keyCode == KeyEvent.KEYCODE_BACK)
    {
         // put your code here
    }

在你的PopupWindow对象中添加setOutsideTouchable(true)并调用update()。如果这样不起作用,那么当弹出窗口显示时,你可能需要禁用返回按钮并在窗口中添加自己的Button。我没有发现其他任何方法可以捕获到返回按钮被按下的事件。


将背景可绘制设置为非空将始终关闭弹出窗口。我有一些情况,我不想关闭弹出窗口,而是在弹出窗口内执行一些任务。那么,在弹出窗口可见时,是否有任何方法可以捕获后退按键事件? - Nitesh V
我已经更新了一些尝试的内容。我希望能够帮到你,但是我不确定在使用PopUpWindow时你想做什么是否可行。 - codeMagic

4

像这样设置背景图形

popup.setBackgroundDrawable(new BitmapDrawable());

然后像这样设置OnDismissListener。
popup.setOnDismissListener(new PopupWindow.OnDismissListener() {
            @Override
            public void onDismiss() {
                //do your code here
            }
        });

3
final PopupWindow popup = new PopupWindow(context);
...
popup.setFocusable(false); //Setting this to true will prevent the events to reach activity below
popup.setBackgroundDrawable(new BitmapDrawable()); //Or anything else, not null!

然后在您的活动中:

@Override
 public void onBackPressed() {
    //your code
 }

1
我会尽力帮忙翻译,以下是您需要翻译的内容:

我知道现在已经晚了,但这可能对其他人有帮助。

有两种方法可以做到这一点:

1)如果弹出窗口焦点对您不重要,则设置

mPopupInfoWindow.setFocusable(false);

因为如果您的弹出窗口处于焦点状态,则不会将按下事件传递回调用onBackPressed()方法的活动

2)如果弹出窗口的焦点对您很重要,请将其设置为true,并在弹出窗口中设置此监听器。这段代码适用于我

 mPopupInfoWindow.getContentView().setFocusableInTouchMode(true);
    mPopupInfoWindow.getContentView().setOnKeyListener(new View.OnKeyListener() {
        @Override
        public boolean onKey(View v, int keyCode, KeyEvent event) {

            if (keyCode == KeyEvent.KEYCODE_BACK) {
                mPopupInfoWindow.dismiss();
                return true;
            }
            return false;
        }
    });

0

我提出了一个更简单的替代方案,您可以考虑一下。其他方法对我没有用。

解决原则:拦截弹出窗口附近的所有按钮点击,但不会拦截任何“返回”按钮。因此,如果您的弹出窗口中有任何需要执行的操作,请在调用dismiss()之前设置指示。在setOnDismissListener()中执行额外的操作(例如getActivity().popupBackStack())。

这种解决方案的优点是,您可以创建自己的CustomPopupWindow并实现此策略。您可以在自定义弹出窗口中隐藏此实现。

步骤1:在实例化弹出窗口时添加以下内容:

boolean isClickHandled = false; 
popupWindow.setOutsideTouchable(true);
popupWindow.setBackgroundDrawable(new ShapeDrawable());
popupWindow.setTouchInterceptor(new View.OnTouchListener() { // or whatever you want
    @Override
    public boolean onTouch(View v, MotionEvent event) {
        isClickHandled = true;
        return false;
    }
});

如果您的弹出窗口中有按钮,请在setOnClickListener.onClick中设置isClickHandled = true并dismiss()。
在您的onDismissListener中,可以执行以下操作:
popupWindow.setOnDismissListener(() -> {
        popupWindow.dismiss();
        if ( !isClickHandled) {
            MainActivity.mainActivity.getSupportFragmentManager().popBackStack();
        }
    });

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接