大家好,我是子玥酱,一名长期深耕在一线的前端程序媛 👩💻。曾就职于多家知名互联网大厂,目前在某国企负责前端软件研发相关工作,主要聚焦于业务型系统的工程化建设与长期维护。
我持续输出和沉淀前端领域的实战经验,日常关注并分享的技术方向包括前端工程化、小程序、React / RN、Flutter、跨端方案,
在复杂业务落地、组件抽象、性能优化以及多端协作方面积累了大量真实项目经验。
技术方向:前端 / 跨端 / 小程序 / 移动端工程化
内容平台:掘金、知乎、CSDN、简书
创作特点:实战导向、源码拆解、少空谈多落地
文章状态:长期稳定更新,大量原创输出
我的内容主要围绕前端技术实战、真实业务踩坑总结、框架与方案选型思考、行业趋势解读展开。文章不会停留在“API 怎么用”,而是更关注为什么这么设计、在什么场景下容易踩坑、真实项目中如何取舍,希望能帮你在实际工作中少走弯路。
子玥酱 · 前端成长记录官 ✨
👋 如果你正在做前端,或准备长期走前端这条路
📚 关注我,第一时间获取前端行业趋势与实践总结
🎁 可领取11 类前端进阶学习资源(工程化 / 框架 / 跨端 / 面试 / 架构)
💡 一起把技术学“明白”,也用“到位”
持续写作,持续进阶。
愿我们都能在代码和生活里,走得更稳一点 🌱
文章目录
- 什么叫“文档模型”?先别想得太复杂
- App 思维:页面是中心
- PC 世界的第一个现实需求:多窗口编辑
- 正确的顺序,应该是反过来的
- 一个最小但正确的起点
- 文档模型,解决的是“谁拥有状态”的问题
- 错误归属
- 正确归属
- 错误写法
- 正确写法
- 没有文档模型,Undo / Redo 几乎一定会失败
- 自动保存、崩溃恢复,全部依赖文档模型
- 多窗口 + 一个文档,是 PC 应用的常态
- HarmonyOS PC 应用,为什么“尤其需要”文档模型?
- 一个现实的判断标准
- 总结
如果你第一次做 HarmonyOS PC 应用,很可能会先从 UI 入手:
- 页面怎么拆
- 布局怎么做
- 多窗口怎么画
这些都没错,但几乎一定会走弯路。
因为在 PC 世界里,有一个东西比 UI 更早、也更重要:
文档模型(Document Model)。
什么叫“文档模型”?先别想得太复杂
这里说的“文档”,不一定是 Word 那种文件。
它更接近的是:
一个可长期存在、
可被操作、
可被保存 / 恢复的核心对象。
比如:
- 编辑器里的文件
- 设计工具里的工程
- 表格应用里的数据集
- IDE 里的 Project
本质都是:
classDocument{id:stringpath?:stringdirty:booleancontent:any}这才是 PC 应用真正“活着”的东西。
App 思维:页面是中心
很多团队一开始会这么写:
@Componentstruct EditorPage{@Statecontent:string=''}页面存在,内容存在;
页面销毁,内容就没了。
在 App 里,这很常见。但在 PC 应用里,这几乎一定会出事。
PC 世界的第一个现实需求:多窗口编辑
当用户说:
“我想同时打开两个文件。”
你会开始这样改:
@Stateeditors:EditorState[]=[]interfaceEditorState{path:stringcontent:string}短期内能跑,但很快你会发现问题:
- 窗口之间怎么共享?
- 同一个文档被打开两次怎么办?
- 关闭一个窗口,是不是就该销毁内容?
你其实已经在被迫设计文档模型了,只是方式非常被动。
正确的顺序,应该是反过来的
成熟的 PC 应用,顺序通常是:
- 先定义Document
- 再定义Document 生命周期
- 最后才是窗口和 UI 绑定
一个最小但正确的起点
classDocument{id:stringpath?:stringcontent:stringdirty:boolean=false}classDocumentManager{privatedocs=newMap<string,Document>()open(path:string):Documentclose(doc:Document)save(doc:Document)}UI 从一开始就只是“观察者”。
文档模型,解决的是“谁拥有状态”的问题
错误归属
窗口 → 内容正确归属
文档 → 内容 窗口 → 视图代码差异非常明显。
错误写法
@Componentstruct EditorWindow{@Statecontent:string}正确写法
@Componentstruct EditorWindow{doc:Document}TextArea({text:doc.content})没有文档模型,Undo / Redo 几乎一定会失败
这是很多团队“后期才发现”的坑,如果你的状态散落在 UI 里:
@Statetext:string@Statecursor:numberUndo 很快就会变成:
- 只回滚一部分
- 顺序混乱
- 窗口之间不同步
而有了文档模型,你可以直接:
classDocument{history:Command[]}undo(){history.pop().rollback(this)}自动保存、崩溃恢复,全部依赖文档模型
PC 应用默认假设:
进程可能随时死。
这意味着:
- 自动保存
- 会话恢复
- 崩溃后重开
都必须是系统能力级别。
serialize(doc):Snapshotrestore(snapshot):Document如果这些逻辑写在页面里,你根本无法统一处理。
多窗口 + 一个文档,是 PC 应用的常态
再看一个常见场景:
同一个文档
同时在两个窗口里打开
如果没有文档模型,你会遇到:
- 内容不同步
- 保存冲突
- 状态不可预期
有了文档模型,结构会非常清晰:
doc=documentManager.open(path)windowA.bind(doc)windowB.bind(doc)UI 只是不同视角。
HarmonyOS PC 应用,为什么“尤其需要”文档模型?
因为 HarmonyOS 给你的能力是:
- 多窗口
- 多任务
- 长时间运行
- 系统级文件访问
但它不会替你解决:
状态该放哪儿。
如果你不先设计文档模型,后面所有能力都会变成负担。
一个现实的判断标准
你可以用一个问题自检:
如果我现在关掉所有窗口,
这个应用的“核心状态”还在吗?
- 如果答案是“在”——
你大概率走在正确的 PC 路上 - 如果答案是“不在”——
你还在用 App 思维写 PC
总结
为什么 HarmonyOS PC 应用,必须先设计文档模型?
因为在 PC 世界里:
- 窗口是暂时的
- 页面是可替换的
- UI 是表现层
而真正长期存在的,只有:
文档、会话、任务、状态。
如果你先设计 UI,文档模型迟早会反过来逼你重构。
但如果你一开始就把文档模型立住:
UI 会变得很轻
多窗口会变得自然
生命周期问题会自动消失一半