You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Android:NavigationBarView切换Fragment后GridView数据被清空如何解决?

解决Fragment切换时GridView数据清空的问题

问题原因

你当前使用replace()方法切换Fragment,每次调用都会移除容器内的现有Fragment并添加目标Fragment。尽管你全局保存了FirstFragment的实例,但切换回来时Fragment会重新执行onCreateView()等生命周期方法,如果GridView的数据源没有被持久化,就会出现数据清空的情况。

解决方案

方案一:改用hide()/show()替代replace()(推荐)

这种方式会让所有Fragment实例一直保留在容器中,不会被销毁或重建,数据自然不会丢失。修改你的导航代码如下:

// 初始化时将三个Fragment都添加到容器,仅显示第一个
getSupportFragmentManager().beginTransaction()
        .add(R.id.containers, firstFragment, "first_tag")
        .add(R.id.containers, secondFragment, "second_tag")
        .add(R.id.containers, thirdFragment, "third_tag")
        .hide(secondFragment)
        .hide(thirdFragment)
        .commit();

navigationBarView.setOnItemSelectedListener(new NavigationBarView.OnItemSelectedListener() {
    @Override
    public boolean onNavigationItemSelected(@NonNull MenuItem item) {
        FragmentTransaction transaction = getSupportFragmentManager().beginTransaction();
        // 先隐藏所有Fragment
        transaction.hide(firstFragment)
                .hide(secondFragment)
                .hide(thirdFragment);
        
        switch(item.getItemId()) {
            case R.id.menu_first:
                transaction.show(firstFragment);
                break;
            case R.id.menu_second:
                transaction.show(secondFragment);
                break;
            case R.id.menu_third:
                transaction.show(thirdFragment);
                break;
            default:
                return false;
        }
        transaction.commit();
        return true;
    }
});

方案二:在FirstFragment中持久化数据

如果坚持使用replace(),可以在Fragment的生命周期方法中保存和恢复数据:

// FirstFragment内部代码
private List<YourDataModel> gridData; // 你的GridView数据源
private YourGridViewAdapter adapter;

@Override
public void onSaveInstanceState(@NonNull Bundle outState) {
    super.onSaveInstanceState(outState);
    // 保存数据,注意YourDataModel需要实现Parcelable接口
    outState.putParcelableArrayList("grid_data", new ArrayList<>(gridData));
}

@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
    View view = inflater.inflate(R.layout.fragment_first, container, false);
    GridView gridView = view.findViewById(R.id.grid_view);
    adapter = new YourGridViewAdapter(requireContext());
    gridView.setAdapter(adapter);

    if (savedInstanceState != null) {
        // 恢复之前保存的数据
        gridData = savedInstanceState.getParcelableArrayList("grid_data");
        if (gridData != null) {
            adapter.updateData(gridData);
        } else {
            // 数据为空时重新请求网络
            loadNetworkData();
        }
    } else {
        // 首次加载,请求网络数据
        loadNetworkData();
    }
    return view;
}

// 网络请求方法
private void loadNetworkData() {
    // 执行网络请求,成功后更新gridData和适配器
    // 示例:
    // apiService.fetchData().enqueue(new Callback<List<YourDataModel>>() {
    //     @Override
    //     public void onResponse(Call<List<YourDataModel>> call, Response<List<YourDataModel>> response) {
    //         if (response.isSuccessful() && response.body() != null) {
    //             gridData = response.body();
    //             adapter.updateData(gridData);
    //         }
    //     }
    // });
}

方案三:使用ViewModel共享数据

将数据源托管到ViewModel中,ViewModel的生命周期独立于Fragment,不会随Fragment重建而丢失数据:

// 定义ViewModel
public class FirstFragmentViewModel extends ViewModel {
    private final MutableLiveData<List<YourDataModel>> gridData = new MutableLiveData<>();
    private boolean isDataLoaded = false;

    public LiveData<List<YourDataModel>> getGridData() {
        return gridData;
    }

    public void loadDataIfNeeded() {
        if (!isDataLoaded) {
            // 执行网络请求
            // apiService.fetchData().enqueue(new Callback<List<YourDataModel>>() {
            //     @Override
            //     public void onResponse(Call<List<YourDataModel>> call, Response<List<YourDataModel>> response) {
            //         if (response.isSuccessful() && response.body() != null) {
            //             gridData.postValue(response.body());
            //             isDataLoaded = true;
            //         }
            //     }
            // });
        }
    }
}

// FirstFragment中使用ViewModel
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
    View view = inflater.inflate(R.layout.fragment_first, container, false);
    GridView gridView = view.findViewById(R.id.grid_view);
    FirstFragmentViewModel viewModel = new ViewModelProvider(this).get(FirstFragmentViewModel.class);
    YourGridViewAdapter adapter = new YourGridViewAdapter(requireContext());
    gridView.setAdapter(adapter);

    // 观察数据变化,更新适配器
    viewModel.getGridData().observe(getViewLifecycleOwner(), data -> {
        if (data != null) {
            adapter.updateData(data);
        }
    });

    // 仅在未加载数据时请求
    viewModel.loadDataIfNeeded();
    return view;
}

内容的提问来源于stack exchange,提问作者js u

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.12 23:55:26