Is there a way to programmatically locate all Windows within a given application?

后端 未结 5 1084
孤街浪徒
孤街浪徒 2020-12-02 17:51

Is it possible to programmatically enumerate all of the android.view.Windows, or decor views within an application?

Dialogs for example wil

5条回答
  •  我在风中等你
    2020-12-02 17:57

    I'm not entirely sure this answers the actual question, but it's a better way of getting all root views as suggested in the accepted answer.

    As mentioned there, I've also managed to accomplish this only using reflection, except this code supports All versions from API 14 and above (I haven't checked below):

    public static List getWindowManagerViews() {
        try {
    
            if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.ICE_CREAM_SANDWICH &&
                    Build.VERSION.SDK_INT < Build.VERSION_CODES.JELLY_BEAN_MR1) {
    
                // get the list from WindowManagerImpl.mViews
                Class wmiClass = Class.forName("android.view.WindowManagerImpl");
                Object wmiInstance = wmiClass.getMethod("getDefault").invoke(null);
    
                return viewsFromWM(wmiClass, wmiInstance);
    
            } else if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN_MR1) {
    
                // get the list from WindowManagerGlobal.mViews
                Class wmgClass = Class.forName("android.view.WindowManagerGlobal");
                Object wmgInstance = wmgClass.getMethod("getInstance").invoke(null);
    
                return viewsFromWM(wmgClass, wmgInstance);
            }
    
        } catch (Exception e) {
            e.printStackTrace();
        }
    
        return new ArrayList();
    }
    
    private static List viewsFromWM(Class wmClass, Object wmInstance) throws Exception {
    
        Field viewsField = wmClass.getDeclaredField("mViews");
        viewsField.setAccessible(true);
        Object views = viewsField.get(wmInstance);
    
        if (views instanceof List) {
            return (List) viewsField.get(wmInstance);
        } else if (views instanceof View[]) {
            return Arrays.asList((View[])viewsField.get(wmInstance));
        }
    
        return new ArrayList();
    }
    

提交回复
热议问题