On a piece of paper analysis of the android window System level, Ativity window and System window differences, this article I say using the system window to implement some of the limitations of floating windows, how we crossed these limits.
Simple floating Window implementation
final WindowManager windowManager = getWindowManager(context);//创建自定义浮窗 FloatView hideDialog = new FloatView(context);WindowManager.LayoutParams params = new WindowManager.LayoutParams();//params.type 窗口类型,主要决定了窗口的层次params.type = WindowManager.LayoutParams.TYPE_PHONE;params.format = PixelFormat.RGBA_8888;//params.flags 描述窗体其他属性的标记位,//LayoutParams.FLAG_NOT_FOCUSABLE表示不能获取输入法焦点params.flags = LayoutParams.FLAG_NOT_FOCUSABLE;params.gravity = Gravity.LEFT | Gravity.TOP;params.width = LayoutParams.MATCH_PARENT;params.height = LayoutParams.MATCH_PARENT;//添加windowManager.addView(hideDialog, dialogParams);
Using WindowManager.LayoutParams.TYPE_PHONE
or WindowManager.LayoutParams.TYPE_SYS_ALERT form type, and then declare the permissions in the Androidmanifest.xml file
Window implementation over permission using floating windows
"Trading Cat" app has passed the floating window authorization, normal use of floating window function.
Windows with types Type_phone, Type_priority_phone, Type_system_alert, Type_system_error, Type_system_error are user-authorized, type Type_ Toast is not required, however in Android 4.4 (API 19) The following type_toast is unable to obtain the focus, the specific source code analysis process can refer to the article:
[Android Floating window Type_toast summary Source analysis] (http://www.90159.com/2015/11/14/Android-Floating-analysis/). So we can do a subdivision process: first get the system version if it is greater than or equal to 19 we use type_toast, less than 19 we use Type_phone window type.
Restrictions on IME
More than 4.4 use type_toast or some small restrictions, if you need the input box in the floating window interaction, Type_toast and Type_phone two types of forms on the input method processing or some difference. When our floating window in the horizontal screen environment (the application under the window is horizontal screen), the input method is the default full screen, we can set the Text property android:imeoptions= "Flagnoextractui" to prohibit the input method of the full screen, You can also set the form properties to Adjustresize to fit the floating window position to prevent the input box from being covered.
However adjustresize this attribute to Type_toast type of form is invalid, I temporarily did not find the corresponding source code support, if you find please let me know. So if you need to enter text in your floating window interaction, you can't use the half-screen IME experience.
To maximize the optimization experience, the process of using a floating window can be refined to:
For the floating window authorization, we can use a method to determine whether authorization:
/** * 判断是否开启浮窗权限,api未公开,使用反射调用 * @return */private static boolean hasAuthorFloatWin(Context context){ if (Device.getSystemVersion() < 19){ return false; } try { AppOpsManager appOps = (AppOpsManager)context.getSystemService(Context.APP_OPS_SERVICE); Class c = appOps.getClass(); Class[] cArg = new Class[3]; cArg[0] = int.class; cArg[1] = int.class; cArg[2] = String.class; Method lMethod = c.getDeclaredMethod("checkOp", cArg); //24是浮窗权限的标记 return (AppOpsManager.MODE_ALLOWED == (Integer) lMethod.invoke(appOps, 24, Binder.getCallingUid(), context.getPackageName())){ } catch(Exception e) { return false; }}
Appopsmanager is introduced after API 19, which can be used by third-party ROMs to manage permissions and give certain permissions to the user to decide, such as floating windows. For more information, see the official documentation: Appopsmanager.
Use floating windows over user authorization