连续编辑:拖拽预览与最终提交不能共享进程级会话
自动关联目录:连续编辑:拖拽预览与最终提交不能共享进程级会话
核心判断:滑杆和 Gizmo 的高频预览应合并成一次用户意图;但“当前正在编辑哪个对象和属性”若保存在进程级变量中,就无法抵御多面板、多文档、嵌套工具和迟到结束事件。
一、连续编辑不是多次普通写入
拖动位置或滑杆时,界面需要每帧看到预览,但历史只应出现一步。工程中已有 Begin/Finish 记录以及 Commit、Cancel、Append 语义,能借用外层批次合并细粒度写入,这是正确方向。
隐患在于活动记录、对象和属性路径由全局状态保存。只要第二个面板启动编辑、Prefab 预览切换作用域,或旧控件在重建后才发出 End,后来的事件就可能结束别人的事务。
二、把手势提升为有所有权的会话
struct EditGestureToken {
GestureId id;
EditSessionId session;
EditScopeId scope;
ObjectId object;
PropertyPath property;
Generation generation;
FrontendId owner;
};
Token BeginGesture(Target t, FrontendId owner);
void Preview(Token t, Value v); // 只写预览层或可恢复暂态
void Commit(Token t, Value final);// 一次模型提交 + 一条 Undo
void Cancel(Token t); // 恢复 Begin 时基线每个事件都携带 token;会话、作用域、对象或 generation 不匹配就拒绝。控件销毁、焦点丢失、文档关闭和 Play 切换必须显式 Cancel,而不是等待一个可能永远不来的 MouseUp。
三、UE 中预览与事实要分层
Transform Gizmo 可以临时驱动组件显示,但权威内容模型只在 Commit 时写一次;若必须实时写 UObject,应在 Begin 冻结基线,并让 Cancel 无条件恢复。属性通知还要区分 Interactive 与 ValueSet,避免每个拖动采样触发昂贵重建、Cook 或网络发布。
四、验证与反思
用交错序列测试两个面板同时拖动、文档切换、控件重建、外层批次嵌套、丢失 End 和迟到 End。断言一次手势最多产生一条历史,旧 token 永远不能提交到新会话。
核心经验是:连续编辑的合并键不是“对象 + 属性”两个全局变量,而是由具体前端拥有、受文档生命周期约束的一次交互身份。
许可协议:CC BY
作者:Davids
本文链接:https://hustjjd.github.io/b96ae72f.html
更新于:2026年10月14日