onCreate()中直接添加show popUpWindow的逻辑会导致应用crush掉(onStart的情况同onCreate)。因为在onCreate(),onStart()等activity生命周期函数中,Activity的相关资源还没有完全加载完成,我们知道,popUpWindow是要依靠activity存在的,这个时候activity没有加载完成,所以会导致popUpWindow显示异常
如果要在activity启动时弹出popupwindow,应该在onWindowFocusChanged中弹出,Activity生命周期中,onStart, onResume, onCreate都不是真正visible的时间点,真正的visible时间点是onWindowFocusChanged()函数被执行时。
2.popupwindow如果不在布局中或代码设置背景色,默认背景是透明的,就是popupwindow没有内容的地方是透明的,会显示底下activity的内容
3.popupwindow构造函数最后一个参数意思是是否能获取焦点,如果设置为false,焦点不会设置在popupwindow上,这样点击外部popupwindow不会消失,按返回键时,activity带着popupwindow一起消失,设置为true,就有了焦点,点击外部,popupwindow消失,按返回键,只退出popupwindow
4.popupwindow要在activity退出前dismiss掉,不然会内存泄漏(在new的时候,最后一个参数(是否获取焦点)设置为true,则按back键时,popupwindow会自动执行dismiss,按一次的时候,只推出popupwindow(跟alertdialog一样),设置为false,则按一次直接推出activity,并且不会自动执行dismiss)
5.显示在指定任意位置的pupupwindow
mrbWindow = new PopupWindow(mRbView, ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.WRAP_CONTENT, false); mrbWindow.showAtLocation(getWindow().getDecorView(), Gravity.CENTER,0,0);没有设置背景色也没有内容的区域是透明的,比如以下布局除了textview里的文字,其他地方都是透明的:
<?xml version="1.0" encoding="utf-8"?> <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="match_parent" android:layout_height="match_parent" > <TextView android:layout_width="match_parent" android:layout_height="match_parent" android:layout_marginTop="10dp" android:gravity="center" android:text="合计一元人民币" android:textColor="#ffffff" android:textSize="15sp" /> </RelativeLayout>
以下布局全部是透明的,因为edittext没有任何内容:
<?xml version="1.0" encoding="utf-8"?> <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="match_parent" android:layout_height="match_parent" > <EditText android:layout_width="200dp" android:layout_height="200dp" /> </RelativeLayout>这样会有hint的内容:
<?xml version="1.0" encoding="utf-8"?> <RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android" android:layout_width="match_parent" android:layout_height="match_parent" > <EditText android:hint="abc" android:layout_width="200dp" android:layout_height="200dp" /> </RelativeLayout>
也可以手动设置背景:
popup.setBackgroundDrawable(new ColorDrawable(Color.BLACK));
如果要点击外面对话框消失,必须调用这个方法,并且是否获取焦点设置为true
6.popupwindow弹出时,后面的activity透明度不会变化,如果要变化,可以调用这个方法:
*/ protected void setAlpha(float fAlpha){ WindowManager.LayoutParams params = getWindow().getAttributes(); params.alpha = fAlpha;//设置window的透明度(0-1),0代表完全透明,1代表完全不透明 getWindow().setAttributes(params); }
7.点击popupwindow外面,对话框是否消失:
只有一种情况下点击外侧会消失(同时点击back键,会先退出popupwindow,而不是退出整个activity),创建时,是否获取焦点为true,并且用代码设置了背景色(在布局文件设置都没有用)
其他情况都是点击外侧不消失,按back退出整个activity
8.显示下拉菜单
public void onShowPWMenu(View view) { View mPopWindowView = getLayoutInflater().inflate(R.layout.layout_popmenu, null); // Focusable 为True,PopupWindow的点击事件才会相应 PopupWindow mPopWindow = new PopupWindow(mPopWindowView, 150, 250, true); // 必须在代码中设置一下背景色,点击外面才会隐藏此弹窗 mPopWindow.setBackgroundDrawable(new ColorDrawable(Color.TRANSPARENT)); // Focusable 为False时,不执行则点击外面不会隐藏此弹窗 //mPopWindow.setOutsideTouchable(true); // 显示 默认显示View的正下方,可以使用重载方法设置偏移量来调整位置 mPopWindow.showAsDropDown(view,50,0); }
<?xml version="1.0" encoding="utf-8"?> <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" android:orientation="vertical" android:layout_width="100dp" android:layout_height="120dp" android:background="@drawable/bg_pop_window"> <Button android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_gravity="center_horizontal" android:layout_marginTop="20dp" android:background="@android:color/transparent" android:text="settings" android:textColor="@android:color/white" android:textAllCaps="false"/> <View android:layout_width="wrap_content" android:layout_height="2dp" android:background="@color/material_blue_grey_800"/> <Button android:onClick="onRefresh" android:layout_width="wrap_content" android:layout_height="wrap_content" android:layout_gravity="center_horizontal" android:background="@android:color/transparent" android:text="refresh" android:textColor="@android:color/white" android:textAllCaps="false"/> </LinearLayout>
9.AlertDialog和PopupWindow区别:
AlertDialog默认点击外面会消失,PopupWindow必须满足7中的条件
PopupWindow弹出,背景透明度不变,AlertDialog弹出背景会变暗
AlertDialog的位置固定,而PopupWindow的位置可以随意
10.AlertDialog也可以灵活定制其中的内容,高版本(api21以后,不向下兼容)可以用Builder类的setView方法设置layout:
setView(int layoutResId)
也可以用AlertDialog的setContentView传入layout:
setContentView
这个方法一定要在show之后调用,否则异常
定制layout的xml中没有设置背景,也没有内容的部分同样是透明的