⚡ perf(vscode): 代码阅读预览发给页面的块只记相对位置:块在源码里占的地方记成离前一块多远、自己多长,块里名字的下标从块的开头算,页面从文件开头累加回文件里的位置、和扩展端打交道的地方都在一处换算;靠前改了代码,后面内容没变的块发过去一模一样,扩展端自己的块和发给页面的块分成两种类型
This commit is contained in:
1 parent
3a2815c19c
commit
ad5f559e92
43 files changed
+980
-424
No files matched your search
@@ -1,5 +1,6 @@
|
||||
// @vitest-environment happy-dom
|
||||
|
||||
import type { Placement } from './placement'
|
||||
import type { BlockBox } from './scrollPosition'
|
||||
import { afterEach, describe, expect, it } from 'vitest'
|
||||
import { PageLayout } from './pageLayout'
|
||||
@@ -31,8 +32,13 @@ function level(owner: string | undefined, ...children: HTMLElement[]): HTMLEleme
|
||||
return div('cr-level', owner === undefined ? {} : { 'data-owner': owner }, div('guide'), div('column', {}, ...children))
|
||||
}
|
||||
|
||||
/** 各块在文件里的起始行(页面上不记行号,按块 id 从文档里各块的位置取) */
|
||||
const LINES: Record<string, number> = {}
|
||||
const PLACEMENT: Placement = { of: id => id in LINES ? { offset: 0, line: LINES[id], endLine: LINES[id] } : undefined }
|
||||
|
||||
function card(id: string, line: number, top: number, bottom: number, editing = false): HTMLElement {
|
||||
return place(div('cr-block', { 'data-id': id, 'data-line': String(line), ...(editing && { 'data-editing': '' }) }), top, bottom)
|
||||
LINES[id] = line
|
||||
return place(div('cr-block', { 'data-id': id, ...(editing && { 'data-editing': '' }) }), top, bottom)
|
||||
}
|
||||
|
||||
/**
|
||||
@@ -42,9 +48,9 @@ function page(): { root: HTMLElement, cards: BlockBox[] } {
|
||||
const root = document.createElement('div')
|
||||
root.append(level(
|
||||
undefined,
|
||||
place(div('cr-item', { 'data-line': '0' }, card('0', 0, 0, 100), place(level('0', card('0.0', 2, 120, 300), card('0.1', 8, 320, 500)), 110, 900)), 0, 1000),
|
||||
place(div('cr-item', { 'data-line': '20' }, card('1', 20, 1010, 1500, true)), 1010, 1500),
|
||||
place(div('cr-item', { 'data-line': '40' }, card('2', 40, 1510, 2000)), 1510, 2000),
|
||||
place(div('cr-item', {}, card('0', 0, 0, 100), place(level('0', card('0.0', 2, 120, 300), card('0.1', 8, 320, 500)), 110, 900)), 0, 1000),
|
||||
place(div('cr-item', {}, card('1', 20, 1010, 1500, true)), 1010, 1500),
|
||||
place(div('cr-item', {}, card('2', 40, 1510, 2000)), 1510, 2000),
|
||||
))
|
||||
document.body.append(root)
|
||||
const cards = [[0, 0, 100], [2, 120, 300], [8, 320, 500], [20, 1010, 1500], [40, 1510, 2000]].map(([line, top, bottom]) => ({ line, top, bottom }))
|
||||
@@ -60,7 +66,7 @@ describe('卡片位置量过就记着', () => {
|
||||
it('滚动位置、包含某一行的块:和把全部卡片量一遍算出来的一样', () => {
|
||||
const { root, cards } = page()
|
||||
const layout = new PageLayout()
|
||||
layout.attach(root, null)
|
||||
layout.attach(root, null, () => PLACEMENT)
|
||||
for (const y of [0, 50, 100, 310, 950, 1200, 1999, 2500]) {
|
||||
const found = layout.anchorAt(y)
|
||||
expect(found && { line: found.line, offset: found.offset }, `y ${y}`).toEqual((({ line, offset }) => ({ line, offset }))(anchorAt(cards, y)!))
|
||||
@@ -74,7 +80,7 @@ describe('卡片位置量过就记着', () => {
|
||||
it('钉住的卡片:只算和顶上那一段相交的顶层块,在编辑的不钉;外层卡片的下沿算到它的子层', () => {
|
||||
const { root } = page()
|
||||
const layout = new PageLayout()
|
||||
layout.attach(root, null)
|
||||
layout.attach(root, null, () => PLACEMENT)
|
||||
window.scrollTo(0, 0)
|
||||
const scopes = layout.stickyScopes(48)
|
||||
expect(scopes.map(scope => [scope.id, scope.depth, scope.top, scope.bottom])).toEqual([['0', 0, 0, 900]])
|
||||
@@ -83,7 +89,7 @@ describe('卡片位置量过就记着', () => {
|
||||
it('滚动时不再量:同一份内容问几次都只量一次;只量用到的那几段;内容变了才重量', async () => {
|
||||
const { root } = page()
|
||||
const layout = new PageLayout()
|
||||
layout.attach(root, null)
|
||||
layout.attach(root, null, () => PLACEMENT)
|
||||
layout.anchorAt(0)
|
||||
// 三段顶层块的外框 + 第 0、1 段里的卡片和子层
|
||||
const first = reads
|
||||
@@ -101,7 +107,7 @@ describe('卡片位置量过就记着', () => {
|
||||
it('要滚过去的:目标所在的顶层块连同上下几屏之内的先照常排版,过两帧放回去', async () => {
|
||||
const { root } = page()
|
||||
const layout = new PageLayout()
|
||||
layout.attach(root, null)
|
||||
layout.attach(root, null, () => PLACEMENT)
|
||||
const items = [...root.querySelectorAll('.cr-item')]
|
||||
expect(layout.cardForLine(40)?.line).toBe(40)
|
||||
expect(items.map(item => item.hasAttribute('data-settle'))).toEqual([true, true, true])
|
||||
|
||||
Reference in new issue
Block a user