我的活动中有一个PopupWindow,即使我正在与我的活动进行交互(比如在我的列表上滚动),我的PopupWindow仍会显示。我可以滚动浏览我的列表,PopupWindow仍在那里。
我想要实现的是当我在屏幕上触摸/滚动/点击/等不是PopupWindow时,我想要关闭PopupWindow。就像菜单的工作方式一样。如果您在菜单外单击,菜单将被取消。
我已经尝试了setOutsideTouchable(true)
,但它不会关闭窗口。感谢。
答案 0 :(得分:123)
如果您触摸窗外,请尝试设置setBackgroundDrawable
PopupWindow
关闭窗口。
答案 1 :(得分:112)
我发现除了WareNinja对接受的答案的评论之外,所提供的答案都没有给我工作,而Marcin S.可能也会有效。这是适合我的部分:
myPopupWindow.setBackgroundDrawable(new BitmapDrawable());
myPopupWindow.setOutsideTouchable(true);
可替换地:
myPopupWindow.setFocusable(true);
不确定区别是什么,但ListPopupWindow源代码在使用setModal将其模态设置为true时实际使用后者,因此至少Android开发人员认为这是一种可行的方法,而且它只有一行。
答案 2 :(得分:50)
我遇到了同样的问题,并将其修复为以下代码。它对我来说很好。
// Closes the popup window when touch outside.
mPopupWindow.setOutsideTouchable(true);
mPopupWindow.setFocusable(true);
// Removes default background.
mPopupWindow.setBackgroundDrawable(new ColorDrawable(Color.TRANSPARENT));
顺便说一句,不要使用BitmapDrawable弃用的构造函数,使用此 新的ColorDrawable(android.R.color.transparent) 来替换默认背景。
玩得开心@。@
答案 3 :(得分:21)
我知道现在已经很晚了,但我注意到人们仍然对弹出窗口有问题。我已经决定编写一个完整的工作示例,您可以通过触摸或单击其外部或仅触摸窗口本身来关闭弹出窗口。为此,请创建一个新的PopupWindow类并复制以下代码:
<强> PopupWindow.class 强>
public class PopupWindow extends android.widget.PopupWindow
{
Context ctx;
Button btnDismiss;
TextView lblText;
View popupView;
public PopupWindow(Context context)
{
super(context);
ctx = context;
popupView = LayoutInflater.from(context).inflate(R.layout.popup, null);
setContentView(popupView);
btnDismiss = (Button)popupView.findViewById(R.id.btn_dismiss);
lblText = (TextView)popupView.findViewById(R.id.text);
setHeight(WindowManager.LayoutParams.WRAP_CONTENT);
setWidth(WindowManager.LayoutParams.WRAP_CONTENT);
// Closes the popup window when touch outside of it - when looses focus
setOutsideTouchable(true);
setFocusable(true);
// Removes default black background
setBackgroundDrawable(new BitmapDrawable());
btnDismiss.setOnClickListener(new Button.OnClickListener(){
@Override
public void onClick(View v) {
dismiss();
}});
// Closes the popup window when touch it
/* this.setTouchInterceptor(new View.OnTouchListener() {
@Override
public boolean onTouch(View v, MotionEvent event) {
if (event.getAction() == MotionEvent.ACTION_MOVE) {
dismiss();
}
return true;
}
}); */
} // End constructor
// Attaches the view to its parent anchor-view at position x and y
public void show(View anchor, int x, int y)
{
showAtLocation(anchor, Gravity.CENTER, x, y);
}
}
现在为弹出窗口创建布局: 的 popup.xml 强>
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout
xmlns:android="http://schemas.android.com/apk/res/android"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_margin="1dp"
android:orientation="vertical"
android:padding="10dp" >
<TextView
android:id="@+id/text"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:gravity="center"
android:padding="5dp"
android:text="PopupWindow Example"
android:textColor="#000000"
android:textSize="17sp"
android:textStyle="italic" />
<FrameLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_gravity="center_vertical">
<Button
android:id="@+id/btn_dismiss"
style="?android:attr/buttonStyleSmall"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Dismiss"
android:visibility="gone" />
<TextView
android:id="@+id/lbl_dismiss"
android:layout_width="fill_parent"
android:layout_height="wrap_content"
android:gravity="center"
android:text="Touch outside of this box to dismiss"
android:textColor="#ffffff"
android:textStyle="bold" />
</FrameLayout>
在主活动中创建PopupWindow类的实例:
final PopupWindow popupWindow = new PopupWindow(this);
popupWindow.show(findViewById(R.id.YOUR_MAIN_LAYOUT), 0, -250);
其中YOUR_MAIN_LAYOUT是弹出popupWindow的当前活动的布局
答案 4 :(得分:10)
感谢@ LunaKong的回答和@ HourGlass的确认。我不想做一个重复的评论,但只想简明扼要。
// Closes the popup window when touch outside. This method was written informatively in Google's docs.
mPopupWindow.setOutsideTouchable(true);
// Set focus true to prevent a touch event to go to a below view (main layout), which works like a dialog with 'cancel' property => Try it! And you will know what I mean.
mPopupWindow.setFocusable(true);
// Removes default background.
mPopupWindow.setBackgroundDrawable(new ColorDrawable(Color.TRANSPARENT));
Mttdat。
答案 5 :(得分:6)
请注意,对于使用popupWindow.setOutsideTouchable(true)
取消,
你需要像下面的代码一样制作宽度和高度wrap_content
:
PopupWindow popupWindow = new PopupWindow(
G.layoutInflater.inflate(R.layout.lay_dialog_support, null, false),
WindowManager.LayoutParams.WRAP_CONTENT,
WindowManager.LayoutParams.WRAP_CONTENT, true);
popupWindow.setBackgroundDrawable(new ColorDrawable(Color.TRANSPARENT));
popupWindow.setOutsideTouchable(true);
popupWindow.setFocusable(true);
popupWindow.showAtLocation(view, Gravity.RIGHT, 0, 0);
答案 6 :(得分:4)
对于ListPopupWindow
,在显示时将窗口设置为模态。
mListPopupWindow.setModal(true);
这样,点击ListPopupWindow
外部就会将其解雇。
答案 7 :(得分:3)
mPopWindow.setFocusable(true);
答案 8 :(得分:3)
将窗口背景设置为透明:
PopupWindow.getBackground().setAlpha(0);
在布局中设置背景后。工作正常。
答案 9 :(得分:2)
@LunaKong建议工作就像一个魅力。
但是设置 mPopupWindow.setFocusable(false)。会删除使弹出窗口消失所需的不必要的触摸。
例如: 让我们考虑屏幕上有一个弹出窗口,您即将点击一个按钮。 所以在这种情况下,(如果mpopwindow.setFocusable(true)) 在弹出窗口按钮的第一次点击将解散。 但是你必须再次点击才能使按钮工作。 如果**(mpopwindwo.setFocusable(假)** 单击按钮关闭弹出窗口并触发按钮单击。 希望能帮助到你。
答案 10 :(得分:1)
popupWindow.setTouchable(true);
popupWindow.setFocusable(true);
popupWindow.showAtLocation(popupView, Gravity.CENTER, 0, 0);
点击/触摸屏幕时会关闭PopupWindow。确保在showAtLocation之前设置了focusable true。
答案 11 :(得分:1)
在某些情况下,使弹出窗口可以调焦是不可取的(例如,您可能不希望它从另一个视图中窃取焦点)。
另一种方法是使用触摸拦截器:
popupWindow.setOutsideTouchable(true);
popupWindow.setTouchInterceptor(new View.OnTouchListener() {
@Override
public boolean onTouch(View v, MotionEvent event) {
if (event.getAction() == MotionEvent.ACTION_OUTSIDE) {
popupWindow.dismiss();
}
return false;
}
});
答案 12 :(得分:1)
如果此弹出窗口是另一个活动,并且您将其大小减小到原始屏幕 并且您要启用或禁用外部区域。您可以通过以下代码简单地启用或禁用外部区域:
启用:
YourActivity.this.setFinishOnTouchOutside(true);
禁用:
YourActivity.this.setFinishOnTouchOutside(false);
答案 13 :(得分:0)
使用View popupView关闭popupWindow
`popupView.setOnClickListener(new View.OnClickListener() {
@Override
public void onClick(View view) {
popupWindow.dismiss();
}
});
` 如果使用此功能,还可以将onClickClick设置为popupWindow内部的任何按钮
答案 14 :(得分:0)
您可以使用isOutsideTouchable
OR isFocusable
在外部触摸时关闭弹出窗口
popupWindow.isOutsideTouchable = true // dismiss popupwindow when touch outside
popupWindow.isFocusable = true // dismiss popupwindow when touch outside AND when press back button
注意
目前,经过测试,我看到setBackgroundDrawable
不帮助我们关闭弹出窗口
如果您查看PopupWindow
(PopupWindow->PopupDecorView->dispatchKeyEvent
和PopupWindow->PopupDecorView->onTouchEvent
)中的关闭代码。您会看到,按返回按钮时,它们在ACTION_UP
上关闭,而当触摸外部时,它们在ACTION_UP
或ACTION_OUTSIDE