鸿蒙学习实战之路-Reader Kit文本缩放因子监听最佳实践

鸿蒙学习实战之路-Reader Kit文本缩放因子监听最佳实践

最近好多朋友问我:"西兰花啊,我用Reader Kit做的阅读器,在智慧多窗模式下字体突然变得不对劲了,咋整?"害,这问题我太熟了!这就是文本缩放因子在搞鬼 o(╯□╰)o

今天这篇,我就手把手带你解决Reader Kit在多窗、分屏等场景下文本缩放的问题,教你怎么监听缩放因子变化并自动更新页面排版,全程不超过10分钟(不含调试时间)~


一、问题出在哪?

在智慧多窗、分屏等场景下,系统会调整文本缩放因子Display.scaledDensity属性。如果你的阅读器没有监听这个变化,就会出现字体大小不对、排版混乱的问题。

简单来说,就是你的阅读器还在用旧的缩放因子,但系统已经换了新的,就像你还在用去年的日历一样,肯定不对劲 _

解决思路很简单:

  1. 监听文本缩放因子变化
  2. 对比系统值和当前值
  3. 如果不一致,更新ReaderSetting并重新排版

二、需要用到的接口

咱们做这个功能,主要需要用到几个接口:

接口名 描述
display.on 监听屏幕显示属性变化,相当于安装个"监控摄像头"~
display.off 取消监听,相当于关掉"监控摄像头"~
setPageConfig 设置或修改页面排版属性,相当于重新排版引擎~
AppStorage 应用级状态管理,相当于"广播站",在页面间传递信号~
@StorageLink 监听AppStorage状态变化,相当于"收音机",接收信号并执行操作~

三、开发准备

在开始之前,你需要先按照之前的教程构建一个基本的阅读器,就像要先有房子才能装监控一样 _

如果没有构建阅读器,可以先去看看"构建阅读器"那篇文章。


四、具体实现步骤

1. 导入相关模块

首先,咱们需要导入需要的模块:

typescript 复制代码
import { display } from '@kit.ArkUI';
import { hilog } from '@kit.PerformanceAnalysisKit';

就像炒菜前要先备好调料一样,先把工具都准备好~

2. 在阅读页监听缩放因子变化

在阅读器页面的aboutToAppear生命周期中注册监听,在aboutToDisappear中取消监听:

typescript 复制代码
@Entry
@Component
struct Reader {
  private screenDensityCallBack: Callback<number> | null = null;

  aboutToAppear(): void {
    this.registerScreenDensityChange();
    hilog.info(0x0000, 'testTag',
      'aboutToAppear : current scaledDensity = ' + this.readerSetting.scaledDensity + ', change scaledDensity = ' +
      display.getDefaultDisplaySync().scaledDensity);
  }

  /**
   * 注册文本缩放因子变化监听
   */
  registerScreenDensityChange() {
    this.screenDensityCallBack = (data: number) => {
      let displaySync = display.getDefaultDisplaySync();
      let scaledDensity = displaySync.scaledDensity;

      // 对比系统值和当前值
      if (scaledDensity !== this.readerSetting.scaledDensity) {
        // 通过AppStorage设置标记
        AppStorage.setOrCreate('isDensityChange', true);
        // 退出阅读页
        this.getUIContext().getRouter().back();
      }
    }

    display.on('change', this.screenDensityCallBack);
  }

  aboutToDisappear(): void {
    // 记得取消监听,不然会有内存泄漏
    display.off('change', this.screenDensityCallBack);
  }

  build() {
    // 阅读器UI实现
  }
}

🥦 西兰花警告 :

我有个朋友忘记在aboutToDisappear中取消监听,结果内存泄漏,debug了半天才发现!血泪教训啊朋友们!

3. 在上级页面监听变化并重新进入阅读页

在上级页面(比如Index)中使用@StorageLink监听变化,当缩放因子改变时自动重新进入阅读页:

typescript 复制代码
import { hilog } from '@kit.PerformanceAnalysisKit';

@Entry
@Component
struct Index {
  /**
   * 系统字体缩放因子是否发生变化,如果变化需要重启阅读器
   */
  @StorageLink('isDensityChange') isDensityChange: boolean = false;

  onPageShow(): void {
    // 文本缩放因子变化需要重新打开书籍
    if (this.isDensityChange) {
      this.jumper();
      AppStorage.setOrCreate('isDensityChange', false);
    }
  }

  private jumper() {
    this.getUIContext().getRouter().pushUrl({ url: "pages/Reader" }).catch(() => {
      hilog.error(0x0000, 'testTag', 'pushUrl failed');
    });
  }

  build() {
    // 上级页面UI实现
  }
}

🥦 西兰花小贴士 :

记得在重新进入后把isDensityChange设为false,不然会一直重复进入阅读页,死循环就麻烦了 o(╯□╰)o

4. 保存和恢复阅读进度

重新进入阅读页时,需要保存和恢复阅读进度。可以参考"阅读进度通知"章节的内容:

typescript 复制代码
// 退出前保存进度
// 在Reader页面的aboutToDisappear或back方法中保存

// 重新进入时恢复进度
// 在Reader页面的aboutToAppear中通过startPlay接口继续阅读

这样用户就不会因为缩放因子变化而丢失阅读进度,体验会好很多 _


五、完整流程总结

整个监听和更新的流程就像这样:

  1. 用户进入阅读页,注册缩放因子监听
  2. 用户切换到多窗/分屏模式,系统改变缩放因子
  3. display.on回调触发,检测到缩放因子变化
  4. 设置isDensityChange标记,退出阅读页
  5. 上级页面的onPageShow检测到标记变化
  6. 自动重新进入阅读页,使用新的缩放因子重新排版
  7. 恢复阅读进度,用户继续阅读

整个流程无缝衔接,用户几乎感觉不到有什么变化,就是字体和排版自动适配了 (┓( ´∀` )┏


六、常见问题

Q1: 为什么不直接在阅读页更新缩放因子?

A: 因为ReaderKit的setPageConfig需要在页面重新加载后才能生效,直接更新可能不会立即反映到UI上。所以采用了退出重进的方式。

Q2: 会影响阅读体验吗?

A: 不会!因为我们保存了阅读进度,重新进入后会自动跳转到原来的位置,用户几乎感觉不到有变化。

Q3: 除了智慧多窗,还有哪些场景会触发?

A: 分屏、悬浮窗、系统字体大小调整等场景都可能触发缩放因子变化,所以监听是很有必要的。


七、文档资源

官方文档链接:


八、总结

监听文本缩放因子变化是Reader Kit开发中的一个重要功能,特别是在多窗、分屏等场景下。

核心要点:

  1. 使用display.on监听缩放因子变化
  2. 通过AppStorage在页面间传递状态
  3. 检测到变化后退出重进,重新排版
  4. 保存和恢复阅读进度,保证用户体验

🥦 西兰花警告 :

记得在aboutToDisappear中取消监听,不然会有内存泄漏!这个坑我已经替你踩过了 o(╥﹏╥)o


下一步行动

建议你:

  1. 先在阅读器中添加缩放因子监听
  2. 测试多窗、分屏场景下的效果
  3. 完善阅读进度保存和恢复功能
  4. 优化重新进入时的动画效果

记住,不教理论,只给你能跑的代码和避坑指南! _


我是盐焗西兰花,

不教理论,只给你能跑的代码和避坑指南。

下期见!🥦

相关推荐
今天只学一颗糖7 小时前
1、《深入理解计算机系统》--计算机系统介绍
linux·笔记·学习·系统架构
testpassportcn8 小时前
AWS DOP-C02 認證完整解析|AWS DevOps Engineer Professional 考試
网络·学习·改行学it
游乐码11 小时前
c#变长关键字和参数默认值
学习·c#
饭碗、碗碗香12 小时前
【Python学习笔记】:Python的hashlib算法简明指南:选型、场景与示例
笔记·python·学习
魔力军12 小时前
Rust学习Day4: 所有权、引用和切片介绍
开发语言·学习·rust
wubba lubba dub dub75012 小时前
第三十六周 学习周报
学习
学编程的闹钟13 小时前
PHP字符串表示方式全解析
学习
Lbs_gemini060313 小时前
01-01-01 C++编程知识 C++入门 工具安装
c语言·开发语言·c++·学习·算法
饭碗、碗碗香14 小时前
【Python学习笔记】:Python 加密算法全景指南:原理、对比与工程化选型
笔记·python·学习
麟听科技14 小时前
HarmonyOS 6.0+ APP智能种植监测系统开发实战:农业传感器联动与AI种植指导落地
人工智能·分布式·学习·华为·harmonyos