没有为 API 23调用 Android-onAttach (Context)

我已经将 SDK 更新为最新版本(API 23) ,而且不推荐使用针对片段的 onAttach(Activity)方法。因此,我现在使用的是 onAttach(Context),而不是使用这个方法,但是这个方法在生命周期中不会被调用。活动是来自 v7的 AppCompatActivity实例,片段是类片段(android.app.Fragment)的实例。

有什么办法让 onAttach在 API 23中工作吗?

解决方案

我找到了一些可以帮助你理解和解决这个问题的答案:

  • 正如前面提到的,我正在使用来自 support v7(AppCompatActivity)的活动和来自 android.app 的片段。

  • 为了显示片段,我使用活动上的 getFragmentManager 方法获得片段管理器,因此片段管理器是来自 android.app-> 的 FragmentManager 的一个实例,这就是问题所在

  • 如果在使用 API 23的设备上运行应用程序(我已经在 AS 模拟器上运行了该应用程序) ,您将看到 onAttach (Context)方法将被调用。 在片段管理器显示片段的过程中,在特定时刻 onAttach (。.)方法被调用。使用 getFragmentManager () ,您将获得一个片段管理器的实例,该实例可用于运行在该设备上的 Android 版本(例如 API 22,23)。如果应用程序运行在一个 API < 23的设备上,onAttach (Context)方法不可用,片段管理器不知道在 API 23中有一个 onAttach (Context)方法,所以这就是为什么没有调用 API < 23-> 这种问题的解决方案是使用来自支持库的 FragmentManager。

  • 解决方案:

    1. 使用 getSupportFragmentManager ()将强制您使用支持库中的片段。因此,第一个解决方案是使用 support lib 中的片段替换所有片段,并使用 getSupportFragmentManager ()。

    2. 我已经实现的解决方案是处理2种可能性 (1。应用程序在 API < 23的设备上运行,应用程序在 API > = 23的设备上运行。

    简而言之,在我的实现中,我为项目的所有片段创建了一个基类,并在其中添加了以下代码:

    /*
    * onAttach(Context) is not called on pre API 23 versions of Android and onAttach(Activity) is deprecated
    * Use onAttachToContext instead
    */
    @TargetApi(23)
    @Override
    public final void onAttach(Context context) {
    super.onAttach(context);
    onAttachToContext(context);
    }
    
    
    /*
    * Deprecated on API 23
    * Use onAttachToContext instead
    */
    @SuppressWarnings("deprecation")
    @Override
    public final void onAttach(Activity activity) {
    super.onAttach(activity);
    if (Build.VERSION.SDK_INT < Build.VERSION_CODES.M) {
    onAttachToContext(activity);
    }
    }
    
    
    /*
    * Called when the fragment attaches to the context
    */
    protected void onAttachToContext(Context context) {
    }
    

    现在,我只需在需要它的所有片段上覆盖 onAttachToContext (Context)方法。

    20520 次浏览

    我想到了同样的问题。 我有一个 minSdkVersion 为19,一个 targetSdkVersion 为23,并且我正在 AppCompatActivity 中使用 FragmentManager。

    onAttach(Activity activity)被标记为已弃用,但是当我使用 onAttach(Context context)进行 被取代了时,我遇到了应用程序崩溃。

    因此,我现在有 两个版本都有,当我在 API22上运行我的应用程序时,onAttach(Activity activity) 被解雇了,即使它被标记为不推荐使用。

    我还没有在 Android M 设备上测试过,但我的理解是,它会运行 onAttach(Context context)版本,忽略另一个版本。

    更新 以考虑到@skaar 在以下评论中的观察: 我现在可以在 API23上进行测试,并且可以确认在平台23上运行会导致调用这两个方法(使用 Activity 还有 Context)。多谢提醒!

    您应该尝试使用片段的支持库版本。

    您需要切换到 import android.support.v4.app.Fragment;而不是 import android.app.Fragment;。您还需要确保使用的是 getSupportFragmentManager()而不是 getFragmentManager()

    我也遇到过同样的问题。 我为解决这个问题所做的努力:

    1. 将 onAttach 回调的参数类型从 活动更改为 背景。 由于未知的原因,此修改导致 方法 OnAttach (上下文)在片段生命周期中不再被调用 结果,我的应用程序崩溃了,因为附件里的代码 方法从未执行过

    2. 将 onAttach 方法中的代码移动到 onCreate one,因为它 仍然执行

    通过这个修改,应用程序恢复了以前的功能,不需要额外的 import语句。

    请在这里发布关于这个 BUG 的帖子

    返回文章页面谷歌 AOSP 项目主页:

    Https://code.google.com/p/android/issues/detail?id=185465

    ps. this is not your job to search for solution to this problem & to find any kind of workarounds .. but to force google to fix its broken API! 要做到这一点,你需要抱怨,正如我所说。

    相关问题-片段中的 getContext () :

    Https://code.google.com/p/android/issues/detail?id=185848

    我用这种方法解决了这个问题:

    @TargetApi(23)
    @Override public void onAttach(Context context) {
    //This method avoid to call super.onAttach(context) if I'm not using api 23 or more
    //if (Build.VERSION.SDK_INT >= 23) {
    super.onAttach(context);
    onAttachToContext(context);
    //}
    }
    
    
    /*
    * Deprecated on API 23
    * Use onAttachToContext instead
    */
    @SuppressWarnings("deprecation")
    @Override public void onAttach(Activity activity) {
    super.onAttach(activity);
    if (Build.VERSION.SDK_INT < 23) {
    onAttachToContext(activity);
    }
    }
    
    
    /*
    * This method will be called from one of the two previous method
    */
    protected void onAttachToContext(Context context) {}
    

    在我读了你的回答“ David Rauca”之后 我想第二个可以解决我的问题。当我查看源代码的时候。我发现实际上,onAttach(Context context)在 Android M 上什么也不做,只是调用了旧的方法。

    作为解决方案:

    @SuppressWarnings("deprecation")
    

    只要把它添加到旧的方法是最好的解决办法。

    @Override
    public void onAttach(Context context) {
    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) {
    super.onAttach(context);
    onAttachToContext(context);
    } else {
    Activity activity = getActivity();
    super.onAttach(activity);
    onAttachToContext(activity);
    }
    }