美文网首页Android开发学习
Android Tip : Android 获取当前Activi

Android Tip : Android 获取当前Activi

作者: 二手认知 | 来源:发表于2016-06-29 01:04 被阅读8604次

    【Android Tip】
    Android 获取当前Activity对象的方式:
    背景:(当你不能使用this获取Activity对象)如何方便地当前Activity对象
    思路:

    1.维护对象栈

    维护一个Activity的対象栈,在每个Activity的生命周期方法执行的时候,控制add和remove,栈顶元素就是当前的Activity对象。为了代码的复用,这个操作可以写在BaseActivity中,这个思路很正常。代码就不贴了。

    2. 反射

    使用反射来获取当前Activity对象。(个人认为是相对优雅和解耦的方式)
    查看源码发现 Activity Thread 这个类管理着所有的Activity对象,也就持有所有的Activity对象,使用反射获得当前ActivityThread对象
    ,然后就能拿到当前的Activity对象
    示例:

    public static Activity getCurrentActivity () {
        try {
            Class activityThreadClass = Class.forName("android.app.ActivityThread");
            Object activityThread = activityThreadClass.getMethod("currentActivityThread").invoke(
                    null);
            Field activitiesField = activityThreadClass.getDeclaredField("mActivities");
            activitiesField.setAccessible(true);
            Map activities = (Map) activitiesField.get(activityThread);
            for (Object activityRecord : activities.values()) {
                Class activityRecordClass = activityRecord.getClass();
                Field pausedField = activityRecordClass.getDeclaredField("paused");
                pausedField.setAccessible(true);
                if (!pausedField.getBoolean(activityRecord)) {
                    Field activityField = activityRecordClass.getDeclaredField("activity");
                    activityField.setAccessible(true);
                    Activity activity = (Activity) activityField.get(activityRecord);
                    return activity;
                }
            }
        } catch (ClassNotFoundException e) {
            e.printStackTrace();
        } catch (InvocationTargetException e) {
            e.printStackTrace();
        } catch (NoSuchMethodException e) {
            e.printStackTrace();
        } catch (NoSuchFieldException e) {
            e.printStackTrace();
        } catch (IllegalAccessException e) {
            e.printStackTrace();
        }
        return null;
    }
    

    由于源码的设计并不是用来做当前的操作,所以源码修改可能导致该方法不能用,而且,评论区也出现了拿不到activitys的情况,说明该方法稳定性也不是最佳。

    3. (推荐)Framework回调

    Android自 API 14开始引入了一个方法,即Applicationd的registerActivityLifecycleCallbacks方法,用来监听所有Activity的生命周期回调,比如onActivityCreated,onActivityResumed等。
    So,一个简单的实现如下:

    public class BaseApplication extends Application {
        //为避免内存泄漏使用弱引用
        private WeakReference<Activity> mCurrentActivity;
        @Override
        public void onCreate () {
            super.onCreate();
            if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.ICE_CREAM_SANDWICH) {
                registerActivityLifecycleCallbacks(new ActivityLifecycleCallbacks() {
                    @Override
                    public void onActivityCreated (Activity activity, Bundle bundle) {
                        //do nothing
                    }
    
                    @Override
                    public void onActivityStarted (Activity activity) {
                        //do nothing
                    }
    
                    @Override
                    public void onActivityResumed (Activity activity) {
                        mCurrentActivity = new WeakReference<>(activity);
                    }
    
                    @Override
                    public void onActivityPaused (Activity activity) {
                        //do nothing
                    }
    
                    @Override
                    public void onActivityStopped (Activity activity) {
                        //do nothing
                    }
    
                    @Override
                    public void onActivitySaveInstanceState (Activity activity, Bundle bundle) {
                        //do nothing
                    }
    
                    @Override
                    public void onActivityDestroyed (Activity activity) {
                        //do nothing
                    }
                });
            }
        }
    }
    

    思路来自:stackoverflow

    相关文章

      网友评论

      • 57f9d9d03c02:很感谢作者,我在工作中也因为页面过多找不到遇到不少问题,虽然作者提到的方法有很多,有些看不懂,对我帮助很大,谢谢你。
      • developer_w:非常感谢楼主的分享
      • 5b6d928c6604:你好 mActivities 取到的是空 是哪里的问题。。。
        fd6ea0887f76:你好,你的这里解决了吗,我现在也是一直获取为空? 还没有查明是哪里的原因..
      • b359f169db1b:感谢楼主分享,正好有这个需求
      • 0e987fb1052f:很好用!在采用MVP时可以在View中管理跳转动画!

      本文标题:Android Tip : Android 获取当前Activi

      本文链接:https://www.haomeiwen.com/subject/xkatjttx.html