当前位置: 首页 > news >正文

ViewPager FragmentPagerAdapter在系统杀死应用后重建时UI不刷新的问题

解决方案

通过重写getItemId方法,返回Fragment的hashCode

@Override
public long getItemId(int position) {/*** 恢复状态重建时,新的 Fragment 不刷新UI。* 原因:instantiateItem 中通过 mFragmentManager.findFragmentByTag(name) 无法找到新的 Fragment,* 因为 name 是由 container.getId() +  getItemId 组成(其中getItemId默认返回position),二者都没变化* 为了让mFragmentManager正确找到新Fragment,那就让 getItemId(即name) 与 Fragment 绑定,而不仅与position绑定* 这样上述问题得解*/return fragmentList.get(position).hashCode();
}
原理解析
一、默认机制的问题根源

FragmentPagerAdapter中,instantiateItem方法会使用makeFragmentName生成Fragment的唯一标识Tag,组合规则如下:

"android:switcher:" + viewId + ":" + getItemId(position)
  • 默认行为:父类的getItemId()直接返回position。当Activity重建时,相同位置的新旧Fragment生成相同的Tag,导致系统优先从FragmentManager缓存中复用旧实例,而不会调用getItem()创建新Fragment。
二、解决方案的核心逻辑

通过重写getItemId(),使其返回值与Fragment对象本身相关联:

@Override
public long getItemId(int position) {return fragmentList.get(position).hashCode();
}

实现效果

  1. 唯一Tag生成:即使position相同,只要Fragment对象不同,hashCode必然不同,新旧Fragment的Tag不同;
  2. 阻断缓存复用:系统通过findFragmentByTag查找失败,强制调用getItem()创建新Fragment实例;
  3. 数据一致性保证:新Fragment从最新数据源初始化,避免恢复旧状态导致的UI错乱。
三、源码级验证

查看FragmentPagerAdapter.instantiateItem()的关键逻辑:

// 生成唯一标识Tag
final long itemId = getItemId(position);
String name = makeFragmentName(container.getId(), itemId);// 优先从缓存中查找Fragment
Fragment fragment = mFragmentManager.findFragmentByTag(name);
if (fragment != null) {mCurTransaction.attach(fragment); // 命中缓存,直接复用旧实例
} else {fragment = getItem(position);       // 未命中,创建新实例mCurTransaction.add(..., name);
}

在这里插入图片描述
在这里插入图片描述

四、示例代码
public class ServerPagerAdapter extends FragmentPagerAdapter {private final List<ServerFragment> fragmentList;@Overridepublic long getItemId(int position) {return fragmentList.get(position).hashCode(); // 绑定对象哈希值}// 其他代码保持默认实现即可
}

总结

通过重写getItemId改变Fragment的Tag生成规则,从根本上阻断了系统对旧Fragment实例的复用机制。此方案以最小代码改动实现了数据与UI的强一致性,适用于动态数据场景的ViewPager适配。但需注意:长期持有大量Fragment对象可能引发内存压力,建议结合FragmentStatePagerAdapter使用以优化资源回收。

相关文章:

  • 河北省大数据应用创新大赛样题
  • 大模型——快速部署和使用 Deep Research Web UI
  • SOLID 原则在单片机环境下的 C 语言实现示例,结合嵌入式开发常见场景进行详细说明
  • [吾爱出品] 【键鼠自动化工具】支持识别窗口、识图、发送文本、按键组合等
  • 基于AI应用创业IDEA:使用百度搜索开放平台的MCP广场智能推荐MCPServices服务
  • java使用CMU sphinx语音识别
  • Java代理讲解
  • 多层级的对象如何修改、或json格式
  • 回溯算法理论基础
  • Verilog 语法 (二)
  • 小刚说C语言刷题——1565成绩(score)
  • element-ui tabs 组件源码分享
  • 品融电商:以全域增长方法论,解码2025情绪消费新机遇
  • Coze高阶玩法 | 使用Coze制作思维认知提升视频,效率提升300%!(附保姆级教程)
  • OpenHarmony之电源管理子系统公共事件定义
  • Vue选项式 API 与组合式 API
  • jdk-8u202-linux-x64.tar.gz官方下载地址
  • 统计服务器CPU、内存、磁盘、网络IO、队列、数据库占用空间等等信息
  • 大学IP广播系统解决方案:构建数字化智慧化大学校园IP广播平台
  • 创建型设计模式之:简单工厂模式、工厂方法模式、抽象工厂模式、建造者模式和原型模式
  • 伊朗港口爆炸已致46人死亡
  • 美情报机构攻击中国大型商用密码产品提供商,调查报告公布
  • 清华数字政府与治理研究院揭牌:服务数字政府建设需求
  • 持续更新丨伊朗港口爆炸事件已致406人受伤
  • 偷拍拷贝某轨道车技术信息后撰写论文发表,工程师被判一年有期徒刑
  • 最高法改判一起植物新品种侵权案:判赔逾5300万元破纪录