✨ feat(vscode): 代码阅读的调用与构造:跨多行写的调用排成「新建 / 调用 名字 · N 个参数」一行,实参摊成参数 / 值表;Python 查被调用名字的定义分新建和调用,查到后刷新
This commit is contained in:
1 parent
ebf228cdc7
commit
ecc415d763
30 files changed
+1033
-157
No files matched your search
@@ -1,4 +1,4 @@
|
||||
import type { BlockAttributes, CodeBlock, DisplayName, KindBadge, LanguageAdapter, LibraryRule, Markdown, Node, PreviewText, PropertyRow, RuleContext, Segment, SourceDocument, SourceRange, TextBlock, TokenRole, Translator } from './contract'
|
||||
import type { BlockAttributes, BlockKind, CodeBlock, DisplayName, KindBadge, LanguageAdapter, LibraryRule, Markdown, Node, PreviewTable, PreviewText, PropertyRow, RuleContext, Segment, SourceDocument, SourceRange, TextBlock, TokenRole, Translator } from './contract'
|
||||
import type { TreeSitterRuntime } from './runtime'
|
||||
import { blockAttributes } from './attributes'
|
||||
import { commonIndent, splitLines } from './editText'
|
||||
@@ -33,9 +33,9 @@ interface BlockViewBase {
|
||||
|
||||
/**
|
||||
* 发给 webview 的一块(可序列化):函数、类、枚举、异常、导入、常量、变量块和库规则的卡片预览时是属性表,注释块是 Markdown 说明,其余是一行译文。
|
||||
* 一行译文的块带说明(TextBlock.doc)时 doc 是翻译插件给的 Markdown 原文,预览排在译文下面。
|
||||
* 一行译文下面依次是:跨几行写的调用摊开各个实参的表(TextTranslation.table),块的说明(TextBlock.doc,翻译插件给的 Markdown 原文)。
|
||||
*/
|
||||
export type BlockView = BlockViewBase & ({ translation: PreviewText, doc?: Markdown } | { properties: PropertyRow[] })
|
||||
export type BlockView = BlockViewBase & ({ translation: PreviewText, table?: PreviewTable, doc?: Markdown } | { properties: PropertyRow[] })
|
||||
|
||||
interface Line { start: number, end: number }
|
||||
|
||||
@@ -159,10 +159,13 @@ export function toBlockViews(blocks: CodeBlock[], document: SourceDocument, tran
|
||||
codeTokens: colorLines(root, source, lines, startRow, endRow, indent, adapter.tokenRole),
|
||||
}
|
||||
}
|
||||
/** 一行译文,带说明的块连着说明。 */
|
||||
const textView = (block: TextBlock): { translation: PreviewText, doc?: Markdown } => {
|
||||
const doc = block.doc && translator?.doc(block.doc, document)
|
||||
return { translation: translator ? translator.translate(block, document) : [], ...(doc && { doc }) }
|
||||
/** 一行译文,连着摊开实参的表、块的说明(有才有)。 */
|
||||
const textView = (block: TextBlock): { translation: PreviewText, table?: PreviewTable, doc?: Markdown } => {
|
||||
if (!translator)
|
||||
return { translation: [] }
|
||||
const { text, table } = translator.translate(block, document)
|
||||
const doc = block.doc && translator.doc(block.doc, document)
|
||||
return { translation: text, ...(table && { table }), ...(doc && { doc }) }
|
||||
}
|
||||
/** 按源码先后逐块给位置记号:先序遍历,块的记号在它的子块之前要 */
|
||||
const anchors = new BlockAnchors()
|
||||
@@ -215,7 +218,10 @@ export interface DocumentViews {
|
||||
displayNames: DisplayName[]
|
||||
}
|
||||
|
||||
/** 解析一份源码并转成视图数据(中文名记号交给翻译插件去掉);语法树用完即释放。 */
|
||||
/**
|
||||
* 解析一份源码并转成视图数据(中文名记号交给翻译插件去掉);语法树用完即释放。
|
||||
* calleeKind 交出调用的名字的定义眼下查到是哪种块(SourceDocument.calleeKind)。
|
||||
*/
|
||||
export async function readBlockViews(
|
||||
runtime: Pick<TreeSitterRuntime, 'parse'>,
|
||||
adapter: LanguageAdapter,
|
||||
@@ -223,14 +229,46 @@ export async function readBlockViews(
|
||||
languageId: string,
|
||||
source: string,
|
||||
rules: RuleRun = NO_RULES,
|
||||
calleeKind?: SourceDocument['calleeKind'],
|
||||
): Promise<DocumentViews> {
|
||||
const tree = await runtime.parse(adapter, languageId, source)
|
||||
try {
|
||||
const { names, markers } = adapter.displayNames?.find(tree.rootNode, source, languageId) ?? { names: [], markers: [] }
|
||||
const blocks = toBlockViews(adapter.toBlocks(tree.rootNode, source, languageId), { source, language: adapter, markers }, translator, rules)
|
||||
const document: SourceDocument = { source, language: adapter, markers, ...(calleeKind && { calleeKind }) }
|
||||
const blocks = toBlockViews(adapter.toBlocks(tree.rootNode, source, languageId), document, translator, rules)
|
||||
return { blocks, displayNames: names }
|
||||
}
|
||||
finally {
|
||||
tree.delete()
|
||||
}
|
||||
}
|
||||
|
||||
/** 块树里自己的名字(见 ownName)盖住 offset 的最里层那块的种类;offset 不在哪块的名字上时没有。 */
|
||||
export function blockKindAt(blocks: readonly CodeBlock[], offset: number): BlockKind | undefined {
|
||||
for (const block of blocks) {
|
||||
const inner = blockKindAt(block.children, offset)
|
||||
if (inner)
|
||||
return inner
|
||||
const name = ownName(block)
|
||||
if (name && name.startIndex <= offset && offset < name.endIndex)
|
||||
return block.kind
|
||||
}
|
||||
return undefined
|
||||
}
|
||||
|
||||
/** 解析一份源码,offset 处的名字定义的是哪种块(见 blockKindAt);语法树用完即释放。 */
|
||||
export async function readDefinitionKind(
|
||||
runtime: Pick<TreeSitterRuntime, 'parse'>,
|
||||
adapter: LanguageAdapter,
|
||||
languageId: string,
|
||||
source: string,
|
||||
offset: number,
|
||||
): Promise<BlockKind | undefined> {
|
||||
const tree = await runtime.parse(adapter, languageId, source)
|
||||
try {
|
||||
return blockKindAt(adapter.toBlocks(tree.rootNode, source, languageId), offset)
|
||||
}
|
||||
finally {
|
||||
tree.delete()
|
||||
}
|
||||
}
|
||||
Reference in new issue
Block a user