• 设为首页
  • 点击收藏
  • 手机版
    手机扫一扫访问
    迪恩网络手机版
  • 关注官方公众号
    微信扫一扫关注
    迪恩网络公众号

android - 用包含 viewpager 的 fragment 替换 fragment 时崩溃

[复制链接]
菜鸟教程小白 发表于 2022-12-9 06:51:33 | 显示全部楼层 |阅读模式 打印 上一主题 下一主题

我创建了一个包含 viewpager 的 HomeFragment,并将它添加到 MainActivity,它工作正常。但是当我点击进入另一个像 BucketFragment 这样的 fragment ,然后点击返回 homefragment 时,它崩溃了,抛出了一个空指针异常。

这是 MainActivity

public class MainActivity extends AppCompatActivity implements NavigationView.OnNavigationItemSelectedListener{
    private DrawerLayout mDrawer;
    private HomeFragment mHomeFragment;
    private LikeFragment mLikeFragment;
    private BucketFragment mBucketFragment;

@Override
protected void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main);

    NavigationView navigationView = (NavigationView) findViewById(R.id.nav_view);
    navigationView.setNavigationItemSelectedListener(this);

    // add the fragment content
    FragmentManager fm = getSupportFragmentManager();
    Fragment fragment = fm.findFragmentById(R.id.fragment_container);

    if (fragment == null) {
        fragment = HomeFragment.newInstance();
        mHomeFragment = (HomeFragment) fragment;
        fm.beginTransaction()
                .add(R.id.fragment_container, fragment)
                .commit();
    }
}

@Override
public boolean onNavigationItemSelected(@NonNull MenuItem item) {
    Fragment currentFragment = null;
    Intent intent = null;

    switch (item.getItemId()) {
        case R.id.nav_home:
            if (mHomeFragment == null) {
                mHomeFragment = HomeFragment.newInstance();
            }
            currentFragment = mHomeFragment;
            break;
        case R.id.nav_like:
            if (mLikeFragment == null) {
                mLikeFragment = LikeFragment.newInstance();
            }
            currentFragment = mLikeFragment;
            break;
        case R.id.nav_bucket:
            if (mBucketFragment == null) {
                mBucketFragment = BucketFragment.newInstance();
            }
            currentFragment = mBucketFragment;
            break;
        case R.id.nav_help:
            intent = HelpActivity.newIntent(this);
            break;
        case R.id.nav_feedback:
            intent = FeedBackActivity.newIntent(this);
            break;
        default:break;
    }


    if (currentFragment != null) {
        FragmentManager fm = getSupportFragmentManager();
        fm.beginTransaction()
                .replace(R.id.fragment_container, currentFragment)
                .commit();
        setTitle(item.getTitle());
    } else {
        startActivity(intent);
    }

    mDrawer.closeDrawer(GravityCompat.START);
    return true;
}
}

这里是 HomeFragment

public class HomeFragment extends Fragment {
    private static final int NUM_CATOGARY = 2;

    private ViewPager mViewPager;

    public static HomeFragment newInstance() {
        return new HomeFragment();
}

@Override
public void onCreate(@Nullable Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
}

@Nullable
@Override
public View onCreateView(@NonNull LayoutInflater inflater, @Nullable ViewGroup container, @Nullable Bundle savedInstanceState) {
   View v = inflater.inflate(R.layout.fragment_home, container, false);

   mViewPager = (ViewPager) v.findViewById(R.id.view_pager);
   TabLayout tab = (TabLayout) v.findViewById(R.id.tab);
   tab.setupWithViewPager(mViewPager);

   FragmentManager fm = getChildFragmentManager();

   mViewPager.setAdapter(new FragmentStatePagerAdapter(fm) {
       @Override
       public Fragment getItem(int position) {
           switch (position) {
               case 0:
                   return PopularFragment.newInstance();
               case 1:
                   return RecentFragment.newInstance();
           }
           return null;
       }

       @Override
       public int getCount() {
           return NUM_CATOGARY;
       }

       @Nullable
       @Override
       public CharSequence getPageTitle(int position) {
           switch (position) {
               case 0:
                   return getResources().getText(R.string.tab_popular);
               case 1:
                   return getResources().getText(R.string.tab_recent);
           }
           return null;
       }
   });

   return v;
}
}

fragment_home.xml

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
          android:layout_width="match_parent"
          android:layout_height="match_parent"
androidrientation="vertical">

<android.support.design.widget.TabLayout
    android:id="@+id/tab"
    android:layout_width="match_parent"
    android:layout_height="wrap_content"/>

<android.support.v4.view.ViewPager
    android:id="@+id/view_pager"
    android:layout_width="match_parent"
    android:layout_height="match_parent"/>

当我点击返回 homefragment 时,它会抛出运行时异常

java.lang.NullPointerException: Attempt to invoke virtual method 'java.lang.Object android.util.SparseArray.get(int)' on a null object reference
    at android.support.v4.app.FragmentManagerImpl.getFragment(FragmentManager.java:902)
    at android.support.v4.app.FragmentStatePagerAdapter.restoreState(FragmentStatePagerAdapter.java:216)
    at android.support.v4.view.ViewPager.onRestoreInstanceState(ViewPager.java:1455)
    at android.view.View.dispatchRestoreInstanceState(View.java:14956)
    at android.view.ViewGroup.dispatchRestoreInstanceState(ViewGroup.java:3253)
    at android.view.ViewGroup.dispatchRestoreInstanceState(ViewGroup.java:3259)
    at android.view.View.restoreHierarchyState(View.java:14934)
    at android.support.v4.app.Fragment.restoreViewState(Fragment.java:396)
    at android.support.v4.app.FragmentManagerImpl.moveToState(FragmentManager.java:1445)
    at android.support.v4.app.FragmentManagerImpl.moveFragmentToExpectedState(FragmentManager.java:1750)
    at android.support.v4.app.FragmentManagerImpl.moveToState(FragmentManager.java:1819)
    at android.support.v4.app.BackStackRecord.executeOps(BackStackRecord.java:797)
    at android.support.v4.app.FragmentManagerImpl.executeOps(FragmentManager.java:2590)
    at android.support.v4.app.FragmentManagerImpl.executeOpsTogether(FragmentManager.java:2377)
    at android.support.v4.app.FragmentManagerImpl.removeRedundantOperationsAndExecute(FragmentManager.java:2332)
    at android.support.v4.app.FragmentManagerImpl.execPendingActions(FragmentManager.java:2239)
    at android.support.v4.app.FragmentManagerImpl$1.run(FragmentManager.java:700)
    at android.os.Handler.handleCallback(Handler.java:815)
    at android.os.Handler.dispatchMessage(Handler.java:104)
    at android.os.Looper.loop(Looper.java:207)
    at android.app.ActivityThread.main(ActivityThread.java:5770)
    at java.lang.reflect.Method.invoke(Native Method)
    at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:789)
    at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:679)



Best Answer-推荐答案


问题出在这段代码中

if (currentFragment != null) {
        FragmentManager fm = getSupportFragmentManager();
        fm.beginTransaction()
                .replace(R.id.fragment_container, currentFragment)
                .commit();
        setTitle(item.getTitle());
    }

Replace 方法作为 remove+add 工作,这意味着您在堆栈中没有要返回的 fragment ,因此您应该放置 add 或添加这一行 .addToBackStack(null); .commit 之前。它会将您的操作放到后台,然后您可以使用返回按钮返回

关于android - 用包含 viewpager 的 fragment 替换 fragment 时崩溃,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/48546460/

回复

使用道具 举报

懒得打字嘛,点击右侧快捷回复 【右侧内容,后台自定义】
您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

关注0

粉丝2

帖子830918

发布主题
阅读排行 更多
广告位

扫描微信二维码

查看手机版网站

随时了解更新最新资讯

139-2527-9053

在线客服(服务时间 9:00~18:00)

在线QQ客服
地址:深圳市南山区西丽大学城创智工业园
电邮:jeky_zhao#qq.com
移动电话:139-2527-9053

Powered by 互联科技 X3.4© 2001-2213 极客世界.|Sitemap