diff --git a/src/common/hooks/history.ts b/src/common/hooks/history.ts index 0e3c060..3e7bf06 100644 --- a/src/common/hooks/history.ts +++ b/src/common/hooks/history.ts @@ -1,15 +1,16 @@ /* * @Author: ShawnPhang * @Date: 2024-04-18 16:10:07 - * @Description: 事件自动注册,WebWorker处理差分补丁,双栈记录 + * @Description: 事件自动注册,生成差分补丁,使用双栈记录 * 事件自动注册的逻辑是鼠标事件黑名单,键盘事件白名单,跑一段时间看看实际情况如何 * 差分补丁目前已知的问题是,对于预期以外的影响状态树的修改,现在都会写进历史记录,看起来就像多了一段毫无变化的历史栈一样 * 例如图层的 left 在修改后可能为 12.6262638 但为了输入框中显示友好,在 input 组件中将自动格式化为 12.63,这个逻辑以前不会有问题,现在则不能这么做了 * @LastEditors: ShawnPhang - * @LastEditTime: 2024-04-18 18:40:27 + * @LastEditTime: 2024-04-18 20:54:41 */ import { onMounted } from 'vue' -import WebWorker from '@/utils/plugins/webWorker' +// import WebWorker from '@/utils/plugins/webWorker' +import historyFactory from '@/utils/widgets/diffLayouts' import { useHistoryStore, useWidgetStore } from '@/store' const blackClass: string[] = ['operation-item', 'icon-undo', 'icon-redo'] @@ -17,7 +18,9 @@ const whiteKey: string[] = ['ArrowLeft', 'ArrowDown', 'ArrowRight', 'ArrowUp', ' const historyStore = useHistoryStore() const widgetStore = useWidgetStore() -const historyWorker = new WebWorker('history') +// const historyWorker = new WebWorker('history') +const diffLayouts = new historyFactory() + let processing = false let historyTimer: any = null @@ -27,7 +30,11 @@ function noPutHistory(target: any) { } export default () => { - historyWorker.start(null, (changes: any) => { + // historyWorker.start(null, (changes: any) => { + // changes.patches.length > 0 && historyStore.changeHistory(changes) + // processing = false + // }) + diffLayouts.onmessage((changes: any) => { changes.patches.length > 0 && historyStore.changeHistory(changes) processing = false }) @@ -36,7 +43,8 @@ export default () => { 'mousedown', (e: any) => { if (noPutHistory(e.target)) return - historyWorker.send(!processing ? { op: 'diff', data: JSON.stringify(widgetStore.dLayouts) } : null) + // historyWorker.send(!processing ? { op: 'diff', data: JSON.stringify(widgetStore.dLayouts) } : null) + diffLayouts.postMessage(!processing ? { op: 'diff', data: JSON.stringify(widgetStore.dLayouts) } : null) processing = true }, false, @@ -47,7 +55,8 @@ export default () => { if (noPutHistory(e.target)) return clearTimeout(historyTimer) historyTimer = setTimeout(() => { - historyWorker.send({ op: 'done', data: JSON.stringify(widgetStore.dLayouts) }) + // historyWorker.send({ op: 'done', data: JSON.stringify(widgetStore.dLayouts) }) + diffLayouts.postMessage({ op: 'done', data: JSON.stringify(widgetStore.dLayouts) }) }, 150) }, false, @@ -56,7 +65,8 @@ export default () => { 'keydown', (e) => { if (!whiteKey.includes(e.key)) return - historyWorker.send(!processing ? { op: 'diff', data: JSON.stringify(widgetStore.dLayouts) } : null) + // historyWorker.send(!processing ? { op: 'diff', data: JSON.stringify(widgetStore.dLayouts) } : null) + diffLayouts.postMessage(!processing ? { op: 'diff', data: JSON.stringify(widgetStore.dLayouts) } : null) processing = true }, false, @@ -67,7 +77,8 @@ export default () => { if (!whiteKey.includes(e.key)) return clearTimeout(historyTimer) historyTimer = setTimeout(() => { - historyWorker.send({ op: 'done', data: JSON.stringify(widgetStore.dLayouts) }) + // historyWorker.send({ op: 'done', data: JSON.stringify(widgetStore.dLayouts) }) + diffLayouts.postMessage({ op: 'done', data: JSON.stringify(widgetStore.dLayouts) }) }, 150) }, false, diff --git a/src/utils/plugins/webWorker.ts b/src/utils/plugins/webWorker.ts index 140815e..1263c62 100644 --- a/src/utils/plugins/webWorker.ts +++ b/src/utils/plugins/webWorker.ts @@ -3,7 +3,7 @@ * @Date: 2022-03-06 13:53:30 * @Description: 计算密集型任务 * @LastEditors: ShawnPhang - * @LastEditTime: 2024-04-17 15:58:53 + * @LastEditTime: 2024-04-18 20:02:55 */ export default class WebWorker { private worker: Worker | undefined diff --git a/src/utils/widgets/diffLayouts.ts b/src/utils/widgets/diffLayouts.ts new file mode 100644 index 0000000..8a57b4a --- /dev/null +++ b/src/utils/widgets/diffLayouts.ts @@ -0,0 +1,50 @@ +/* + * @Author: ShawnPhang + * @Date: 2023-09-14 11:33:44 + * @Description: 依赖不能直接引入,所以暂时不使用WebWorker + * @LastEditors: ShawnPhang + * @LastEditTime: 2024-04-18 20:52:17 + */ +import diff from 'microdiff' +import { produce, applyPatches, enablePatches } from 'immer' +enablePatches() +const ops: any = { + CHANGE: 'replace', + CREATE: 'add', + REMOVE: 'remove', +} +let cloneData = '' + +export default class { + private notifi: any + constructor() { } + /** + * onmessage + */ + public onmessage(cb: any) { + this.notifi = cb + } + public postMessage(e: any) { + if (e.op === 'done') { + if (!cloneData) return + let fork = JSON.parse(cloneData) + let curArray = JSON.parse(e.data) + // 比较数据差异 + let diffData: any = diff(fork, curArray) + // 生成差分补丁 + fork = produce( + fork, + (draft) => { + for (const d of diffData) { + d.op = ops[d.type] + } + draft = applyPatches(draft, diffData) + }, + (patches, inversePatches) => { + this.notifi({ patches, inversePatches }) + }, + ) + cloneData = '' + } else cloneData = e.data + } +} diff --git a/src/utils/widgets/history.worker.ts b/src/utils/widgets/history.worker.ts index ab59683..61530c8 100644 --- a/src/utils/widgets/history.worker.ts +++ b/src/utils/widgets/history.worker.ts @@ -1,9 +1,9 @@ /* * @Author: ShawnPhang * @Date: 2023-09-14 11:33:44 - * @Description: 历史记录处理 + * @Description: 历史记录处理(无效 * @LastEditors: ShawnPhang - * @LastEditTime: 2024-04-18 13:59:47 + * @LastEditTime: 2024-04-18 20:06:51 */ import diff from 'microdiff' import { produce, applyPatches, enablePatches } from 'immer'