前言

做中文界面时,中英文混排很常见。

产品名里会出现 Mate 60 Pro,技术说明里会出现 HarmonyOS API,设置页里会出现 Wi-Fi、NFC、Bluetooth,订单页和商品页里还会出现 256GB、5G、Pro Max 这类型号信息。

这些内容如果紧贴在一起,阅读时会有一点挤。以前我通常会手动在中文和英文之间加空格,比如写成 HarmonyOS 是华为自研系统。这种方式在静态文案里还可以接受,一旦文本来自接口、用户输入、搜索框或富文本编辑,手动处理就会变得很麻烦。

API 20 开始,ArkUI 文本类组件增加了 enableAutoSpacing,可以开启中文与西文之间的自动间距。API 变更清单中能看到 TextAttribute 新增 enableAutoSpacing(enabled: Optional<boolean>): TextAttribute;华为开发者文档中,RichEditor、TextArea 等组件也已经标注支持 enableAutoSpacing,用于设置是否开启中文与西文自动间距。

这个能力适合解决一个很具体的问题:中文和西文相邻时,让系统在排版阶段补上合适的视觉间隔。它不会改变原始字符串,也不会帮业务清洗文本,只影响组件的显示效果。

一、enableAutoSpacing 解决的是显示层排版问题

以前处理中西文混排,很多人会直接改字符串。

比如接口返回:

const title = 'HarmonyOS是华为自研系统';

页面展示前手动处理成:

const displayTitle = 'HarmonyOS 是华为自研系统';

这个写法在少量固定文案里能用,但不适合做成通用方案。原因很简单,字符串一旦被改掉,后面保存、搜索、复制、比对、埋点都会受影响。显示层只是想看起来更舒服,业务层却拿到了一份被加工过的数据。

enableAutoSpacing 的好处在这里。它把间距处理放在文本渲染阶段,原始字符串不用变。

Text('HarmonyOS是华为自研系统')
  .fontSize(20)
  .enableAutoSpacing(true)

这段代码的重点很清楚。字符串仍然是 HarmonyOS是华为自研系统,组件显示时会在中文和西文之间产生更自然的视觉间隔。

这种能力特别适合几类场景。

技术文案:HarmonyOS API 20 新增 Text 能力

设备型号:Mate 60 Pro 512GB 砚黑

商品信息:iPhone 15 Pro Max 256GB

搜索关键词:HarmonyOS 开发文档

输入内容:请反馈 Wi-Fi 连接异常问题

这些文本里,中文、英文、数字和符号经常混在一起。手动加空格很难保证统一,系统排版层处理会更稳。

二、Text 里的基础写法很简单

Text 组件里直接链式调用即可。

@Entry
@Component
struct AutoSpacingTextDemo {
  build() {
    Column({ space: 16 }) {
      Text('未开启')
        .fontSize(14)
        .fontColor('#666666')

      Text('HarmonyOS是华为自研的分布式操作系统')
        .fontSize(20)
        .padding(12)
        .backgroundColor('#F5F5F5')
        .borderRadius(8)
        .enableAutoSpacing(false)

      Text('已开启')
        .fontSize(14)
        .fontColor('#666666')

      Text('HarmonyOS是华为自研的分布式操作系统')
        .fontSize(20)
        .padding(12)
        .backgroundColor('#F5F5F5')
        .borderRadius(8)
        .enableAutoSpacing(true)
    }
    .width('100%')
    .padding(20)
  }
}

实际开发中,我不会给所有 Text 都加这个属性。正文、标题、列表项、搜索占位文案、表单提示这几类文本更适合先用。纯中文、纯英文、纯数字内容加了也没有太大意义。

动态开关也很简单。

@Entry
@Component
struct DynamicAutoSpacingDemo {
  @State private autoSpacingEnabled: boolean = true;

  build() {
    Column({ space: 20 }) {
      Toggle({ type: ToggleType.Switch, isOn: this.autoSpacingEnabled })
        .onChange((checked: boolean) => {
          this.autoSpacingEnabled = checked;
        })

      Text('Mate 60 Pro 512GB 砚黑')
        .fontSize(22)
        .padding(16)
        .width('100%')
        .backgroundColor('#F5F5F5')
        .borderRadius(8)
        .enableAutoSpacing(this.autoSpacingEnabled)
    }
    .width('100%')
    .padding(24)
  }
}

这个开关适合放在调试页面里。上线后一般不需要暴露给用户,除非应用本身是阅读器、笔记、文档编辑器,用户对排版偏好比较敏感。

三、输入类组件也要一起处理

中西文自动间距的价值不只在静态展示上。搜索框、输入框、反馈框、富文本编辑器里,用户也会输入大量中英文混合内容。

华为开发者文档中,RichEditor 的 enableAutoSpacing(enable: Optional<boolean>) 用于设置是否开启中文与西文的自动间距;TextArea 文档也给出了从 API version 20 开始通过 enableAutoSpacing 设置中西文自动间距的示例;OpenHarmony TextInput 参考中也能看到该属性从 API version 20 开始可用。

Search 场景可以这样写:

@Entry
@Component
struct SearchAutoSpacingDemo {
  @State private keyword: string = '';

  build() {
    Column({ space: 16 }) {
      Search({
        value: this.keyword,
        placeholder: '搜索 HarmonyOS API 20 文档'
      })
        .height(48)
        .enableAutoSpacing(true)
        .onChange((value: string) => {
          this.keyword = value;
        })

      Text(`当前关键词:${this.keyword}`)
        .fontSize(14)
        .fontColor('#666666')
        .enableAutoSpacing(true)
    }
    .width('100%')
    .padding(20)
  }
}

TextInput 适合设备型号、技术关键词、用户昵称等单行输入。

@Entry
@Component
struct TextInputAutoSpacingDemo {
  @State private deviceName: string = '';

  build() {
    Column({ space: 12 }) {
      Text('设备型号')
        .fontSize(14)
        .fontColor('#666666')

      TextInput({
        text: this.deviceName,
        placeholder: '例如 Mate 60 Pro'
      })
        .height(48)
        .enableAutoSpacing(true)
        .onChange((value: string) => {
          this.deviceName = value;
        })
    }
    .width('100%')
    .padding(20)
  }
}

TextArea 适合反馈内容、评论、备注。

@Entry
@Component
struct TextAreaAutoSpacingDemo {
  @State private feedback: string = '';

  build() {
    Column({ space: 12 }) {
      Text('问题反馈')
        .fontSize(14)
        .fontColor('#666666')

      TextArea({
        text: this.feedback,
        placeholder: '请描述 Wi-Fi 连接异常、HarmonyOS 版本等信息'
      })
        .height(140)
        .enableAutoSpacing(true)
        .onChange((value: string) => {
          this.feedback = value;
        })
    }
    .width('100%')
    .padding(20)
  }
}

富文本编辑器更适合笔记、文档、内容创作工具。

@Entry
@Component
struct RichEditorAutoSpacingDemo {
  private controller: RichEditorController = new RichEditorController();

  build() {
    Column({ space: 12 }) {
      Text('编辑内容')
        .fontSize(16)
        .fontWeight(FontWeight.Medium)

      RichEditor({
        controller: this.controller
      })
        .height(220)
        .enableAutoSpacing(true)
        .border({ width: 1, color: '#DDDDDD', radius: 8 })
        .padding(12)
    }
    .width('100%')
    .padding(20)
  }
}

输入类组件还有一个好处。它不会要求用户自己知道哪里该加空格。用户输入 Hello鸿蒙世界,组件展示时会自动处理排版间隔,输入内容本身仍然保持原样。

四、和 letterSpacing、lineHeight 一起用时要克制

enableAutoSpacing 处理的是中文与西文之间的间距。letterSpacing 处理的是字符之间的通用间距。两个属性可以同时出现,但视觉上会叠加。

如果已经设置了较大的 letterSpacing,再开启 enableAutoSpacing,中西文之间可能显得过松。

Text('HarmonyOS API 20 文本排版')
  .fontSize(18)
  .letterSpacing(1)
  .enableAutoSpacing(true)

这种写法不是不能用,但要看真实页面效果。标题类文本可能还可以接受,正文和列表项就容易显得散。

我一般会优先使用 enableAutoSpacing,只有在标题、海报文案、活动页大字需要特殊视觉节奏时,才额外加 letterSpacing

多行文本要重点看 lineHeight

Text('HarmonyOS API 20 增加了中西文自动间距能力,适合用于产品详情、技术说明、搜索输入和表单内容。')
  .fontSize(16)
  .lineHeight(26)
  .enableAutoSpacing(true)
  .width('100%')

中西文自动间距解决的是一行内部的混排观感。段落阅读还要靠字号、行高、段落宽度一起配合。只打开自动间距,不能替代完整的文本排版设计。

textAlign 通常不会影响是否生效,但会影响整体视觉感受。居中标题可以开启自动间距;大段正文更建议使用 TextAlign.Start,阅读会更稳定。

五、落地时更适合做成统一文本组件

如果项目里很多地方都需要中西文混排,不建议每个 Text 都手动加一遍。可以封装一个轻量组件。

@Component
struct MixedText {
  @Prop value: string;
  @Prop size: number = 16;
  @Prop color: ResourceColor = '#182431';
  @Prop autoSpacing: boolean = true;

  build() {
    Text(this.value)
      .fontSize(this.size)
      .fontColor(this.color)
      .enableAutoSpacing(this.autoSpacing)
  }
}

页面里使用时会清爽很多。

MixedText({
  value: 'HarmonyOS API 20 文本排版优化',
  size: 18
})

如果是列表项,也可以统一封装。

@Component
struct ProductTitle {
  @Prop title: string;

  build() {
    Text(this.title)
      .fontSize(16)
      .fontWeight(FontWeight.Medium)
      .maxLines(2)
      .textOverflow({ overflow: TextOverflow.Ellipsis })
      .enableAutoSpacing(true)
  }
}

这样做的好处是,后续如果要关闭某类页面的自动间距,或者只对标题开启,不需要全局搜索替换。

兼容处理也放在封装层更合适。enableAutoSpacing 是 API 20 能力,如果项目还要覆盖更低 API 版本,可以在不同构建目标里保留两份组件实现。高版本组件加 enableAutoSpacing(true),低版本组件只保留基础 Text 样式。不要在每个业务页面都写版本判断,后期维护会很难受。

总结

enableAutoSpacing 是一个很小但很实用的排版能力。它处理的是中文和西文相邻时的显示间隔,原始字符串不会被改动,适合产品名、技术术语、搜索关键词、表单输入、富文本编辑这类高频混排场景。

实际接入时,我会优先在这些位置启用:

产品标题,比如 Mate 60 Pro 512GB 砚黑

技术文案,比如 HarmonyOS API 20 新增能力

搜索框和输入框,比如 搜索 HarmonyOS 开发文档

用户反馈和评论,比如 Wi-Fi 连接异常

富文本编辑,比如笔记、文档、内容创作工具。

视觉上不要指望一个属性解决所有排版问题。字号、行高、段落宽度、文字颜色、信息层级仍然要一起看。enableAutoSpacing 适合处理局部混排细节,完整页面的阅读体验还需要靠整体文本规范来保证。

工程上更建议把它放进统一文本组件或表单组件里。业务页面只管传内容,不需要反复关心每个 Text 有没有加自动间距。后续要做兼容、关闭某些场景、调整排版策略,也能集中处理。

Logo

作为“人工智能6S店”的官方数字引擎,为AI开发者与企业提供一个覆盖软硬件全栈、一站式门户。

更多推荐