⚡ perf(vscode): 代码阅读预览发给页面的块只记相对位置:块在源码里占的地方记成离前一块多远、自己多长,块里名字的下标从块的开头算,页面从文件开头累加回文件里的位置、和扩展端打交道的地方都在一处换算;靠前改了代码,后面内容没变的块发过去一模一样,扩展端自己的块和发给页面的块分成两种类型
This commit is contained in:
1 parent
3a2815c19c
commit
ad5f559e92
43 files changed
+980
-424
No files matched your search
@@ -1,12 +1,15 @@
|
||||
import type { FileAttribute } from '../attributes'
|
||||
import type { BlockView } from '../blockView'
|
||||
import type { PageCard } from '../editor/messages'
|
||||
import type { ChangedBlock, DiffStats, RemovedBlock } from './blockDiff'
|
||||
import type { DiffBase } from './diffBase'
|
||||
import { pageCard, pageMarks, sourceLines } from '../editor/pageBlocks'
|
||||
import { splitLines } from '../editText'
|
||||
import { diffBlockTrees } from './blockDiff'
|
||||
|
||||
/** 删掉的一块(见 RemovedBlock),带上种类的名字:旧版本里才有的种类,新文件的筛选属性里查不到它叫什么。 */
|
||||
export interface RemovedView extends RemovedBlock {
|
||||
/** 删掉的一块(见 RemovedBlock)发给页面的样子:旧版本里它自己的内容(见 pageCard),带上种类的名字(旧版本里才有的种类,新文件的筛选属性里查不到它叫什么)。 */
|
||||
export interface RemovedView extends Omit<RemovedBlock, 'block'> {
|
||||
block: PageCard
|
||||
kindName: string
|
||||
}
|
||||
|
||||
@@ -49,6 +52,20 @@ function kindNames(attributes: readonly FileAttribute[]): Map<string, string> {
|
||||
return new Map(attributes.find(attribute => attribute.id === 'kind')?.values.map(value => [value.id, value.name]))
|
||||
}
|
||||
|
||||
/** 各块的开头(第一行的行首)在文件里的下标,按块的记号:卡片里要标的改动发给页面时从块的开头算(见 pageMarks) */
|
||||
function blockStarts({ blocks, source }: SentDocument): Map<string, number> {
|
||||
const lines = sourceLines(source)
|
||||
const starts = new Map<string, number>()
|
||||
const visit = (list: readonly BlockView[]): void => {
|
||||
for (const block of list) {
|
||||
starts.set(block.anchor, lines.start(block.startLine))
|
||||
visit(block.children)
|
||||
}
|
||||
}
|
||||
visit(blocks)
|
||||
return starts
|
||||
}
|
||||
|
||||
/** 按基准比出来的差异:基准里没有这个文件时整份是新文件,否则两棵块树比(见 diffBlockTrees)。 */
|
||||
export function documentDiff(base: DiffBase, sent: SentDocument, old: { source: string, document: OldDocument } | null): DocumentDiff {
|
||||
const common = { base: base.label, version: sent.version, lineCount: splitLines(sent.source).length }
|
||||
@@ -56,7 +73,13 @@ export function documentDiff(base: DiffBase, sent: SentDocument, old: { source:
|
||||
return { ...common, newFile: base.missing, blocks: {}, removed: [], stats: NO_CHANGES }
|
||||
const { blocks, removed, stats } = diffBlockTrees({ blocks: old.document.blocks, source: old.source }, sent)
|
||||
const kinds = kindNames(old.document.attributes)
|
||||
return { ...common, blocks, removed: removed.map(item => ({ ...item, kindName: kinds.get(item.block.kind) ?? item.block.kind })), stats }
|
||||
const starts = blockStarts(sent)
|
||||
return {
|
||||
...common,
|
||||
blocks: Object.fromEntries(Object.entries(blocks).map(([anchor, changed]) => [anchor, changed.marks ? { ...changed, marks: pageMarks(changed.marks, starts.get(anchor) ?? 0) } : changed])),
|
||||
removed: removed.map(item => ({ ...item, block: pageCard(item.block, 0), kindName: kinds.get(item.block.kind) ?? item.block.kind })),
|
||||
stats,
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
Reference in new issue
Block a user