1.0.3 优化输入中的代码格式化

This commit is contained in:
睿 安
2025-09-17 14:03:19 +08:00
parent 0502a9ddb8
commit 1bc5184032
6 changed files with 35 additions and 252 deletions

View File

@@ -46,116 +46,25 @@ class OnTypeFormattingProvider {
async provideOnTypeFormattingEdits(document, position, ch, options, token) { async provideOnTypeFormattingEdits(document, position, ch, options, token) {
const edits = []; const edits = [];
try { try {
// 获取文档全文
const fullText = document.getText();
// 检查是否是 Squirrel 代码 // 检查是否是 Squirrel 代码
const textBefore = document.getText(new vscode.Range(new vscode.Position(0, 0), position)); if (!(0, beautifyHelper_1.isSquirrelCode)(fullText)) {
if (!(0, beautifyHelper_1.isSquirrelCode)(textBefore)) { return edits; // 如果不是 Squirrel 代码,不应用格式化
}
// 使用 js-beautify 格式化代码
const formattedText = (0, beautifyHelper_1.beautifyCode)(fullText, options);
// 如果格式化后的代码与原代码相同,不需要修改
if (formattedText === fullText) {
return edits; return edits;
} }
// 根据输入的字符执行不同的格式化操作 // 创建编辑操作,替换整个文档
switch (ch) { const fullRange = new vscode.Range(document.positionAt(0), document.positionAt(fullText.length));
case ')': edits.push(vscode.TextEdit.replace(fullRange, formattedText));
// 输入右括号时格式化当前行
edits.push(...this.formatCurrentLine(document, position, options));
break;
case ';':
// 输入分号时格式化当前行
edits.push(...this.formatCurrentLine(document, position, options));
break;
case '}':
// 输入右大括号时格式化整个代码块
edits.push(...this.formatCodeBlock(document, position, options));
break;
default:
break;
}
} }
catch (error) { catch (error) {
console.error('输入时格式化失败:', error); console.error('输入时格式化失败:', error);
} // 如果格式化失败,返回空编辑数组,保持原代码不变
return edits;
}
/**
* 使用 js-beautify 格式化当前行
*/
formatCurrentLine(document, position, options) {
const edits = [];
try {
// 获取当前行
const line = document.lineAt(position.line);
const lineText = line.text;
// 获取当前行的上下文(向前几行,向后几行)
const startLine = Math.max(0, position.line - 2);
const endLine = Math.min(document.lineCount - 1, position.line + 2);
const contextText = document.getText(new vscode.Range(new vscode.Position(startLine, 0), new vscode.Position(endLine, document.lineAt(endLine).text.length)));
// 使用 js-beautify 格式化代码块
const formattedContext = (0, beautifyHelper_1.beautifyCode)(contextText, options);
// 比较原始文本和格式化后的文本
if (formattedContext === contextText) {
return edits; // 没有变化,不需要编辑
}
// 应用格式化结果
const originalLines = contextText.split('\n');
const formattedLines = formattedContext.split('\n');
for (let i = 0; i < originalLines.length && i < formattedLines.length; i++) {
const original = originalLines[i];
const formatted = formattedLines[i];
if (original !== formatted) {
const lineNumber = startLine + i;
const range = new vscode.Range(new vscode.Position(lineNumber, 0), new vscode.Position(lineNumber, document.lineAt(lineNumber).text.length));
edits.push(vscode.TextEdit.replace(range, formatted));
}
}
}
catch (error) {
console.error('格式化当前行失败:', error);
}
return edits;
}
/**
* 使用 js-beautify 格式化代码块
*/
formatCodeBlock(document, position, options) {
const edits = [];
try {
// 查找匹配的左大括号
let braceCount = 1;
let blockStartLine = -1;
for (let i = position.line - 1; i >= 0; i--) {
const currentLine = document.lineAt(i);
const lineText = currentLine.text;
for (let j = lineText.length - 1; j >= 0; j--) {
if (lineText[j] === '}') {
braceCount++;
}
else if (lineText[j] === '{') {
braceCount--;
if (braceCount === 0) {
blockStartLine = i;
break;
}
}
}
if (blockStartLine !== -1) {
break;
}
}
if (blockStartLine !== -1) {
// 获取代码块的范围
const endLine = position.line;
const blockText = document.getText(new vscode.Range(new vscode.Position(blockStartLine, 0), new vscode.Position(endLine + 1, 0) // 包含右大括号行
));
// 使用 js-beautify 格式化代码块
const formattedBlock = (0, beautifyHelper_1.beautifyCode)(blockText, options);
if (formattedBlock === blockText) {
return edits; // 没有变化
}
// 应用格式化结果
const range = new vscode.Range(new vscode.Position(blockStartLine, 0), new vscode.Position(endLine + 1, 0));
edits.push(vscode.TextEdit.replace(range, formattedBlock));
}
}
catch (error) {
console.error('格式化代码块失败:', error);
} }
return edits; return edits;
} }

View File

@@ -1 +1 @@
{"version":3,"file":"onTypeFormattingProvider.js","sourceRoot":"","sources":["../../src/providers/onTypeFormattingProvider.ts"],"names":[],"mappings":"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"} {"version":3,"file":"onTypeFormattingProvider.js","sourceRoot":"","sources":["../../src/providers/onTypeFormattingProvider.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;AAAA,+CAAiC;AACjC,4DAAuE;AAEvE;;GAEG;AACH,MAAa,wBAAwB;IACjC;;OAEG;IACH,KAAK,CAAC,4BAA4B,CAC9B,QAA6B,EAC7B,QAAyB,EACzB,EAAU,EACV,OAAiC,EACjC,KAA+B;QAE/B,MAAM,KAAK,GAAsB,EAAE,CAAC;QAEpC,IAAI,CAAC;YACD,SAAS;YACT,MAAM,QAAQ,GAAG,QAAQ,CAAC,OAAO,EAAE,CAAC;YAEpC,oBAAoB;YACpB,IAAI,CAAC,IAAA,+BAAc,EAAC,QAAQ,CAAC,EAAE,CAAC;gBAC5B,OAAO,KAAK,CAAC,CAAC,0BAA0B;YAC5C,CAAC;YAED,uBAAuB;YACvB,MAAM,aAAa,GAAG,IAAA,6BAAY,EAAC,QAAQ,EAAE,OAAO,CAAC,CAAC;YAEtD,wBAAwB;YACxB,IAAI,aAAa,KAAK,QAAQ,EAAE,CAAC;gBAC7B,OAAO,KAAK,CAAC;YACjB,CAAC;YAED,gBAAgB;YAChB,MAAM,SAAS,GAAG,IAAI,MAAM,CAAC,KAAK,CAC9B,QAAQ,CAAC,UAAU,CAAC,CAAC,CAAC,EACtB,QAAQ,CAAC,UAAU,CAAC,QAAQ,CAAC,MAAM,CAAC,CACvC,CAAC;YAEF,KAAK,CAAC,IAAI,CAAC,MAAM,CAAC,QAAQ,CAAC,OAAO,CAAC,SAAS,EAAE,aAAa,CAAC,CAAC,CAAC;QAElE,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACb,OAAO,CAAC,KAAK,CAAC,WAAW,EAAE,KAAK,CAAC,CAAC;YAClC,0BAA0B;QAC9B,CAAC;QAED,OAAO,KAAK,CAAC;IACjB,CAAC;CACJ;AA7CD,4DA6CC"}

View File

@@ -2,7 +2,7 @@
"name": "squirrel-nut-explorer", "name": "squirrel-nut-explorer",
"displayName": "Squirrel NUT Explorer", "displayName": "Squirrel NUT Explorer",
"description": "通过 pvfUtility API 浏览和编辑 NUT 文件", "description": "通过 pvfUtility API 浏览和编辑 NUT 文件",
"version": "1.0.0", "version": "1.0.1",
"publisher": "local", "publisher": "local",
"engines": { "engines": {
"vscode": "^1.99.0" "vscode": "^1.99.0"

Binary file not shown.

Binary file not shown.

View File

@@ -18,159 +18,33 @@ export class OnTypeFormattingProvider implements vscode.OnTypeFormattingEditProv
const edits: vscode.TextEdit[] = []; const edits: vscode.TextEdit[] = [];
try { try {
// 获取文档全文
const fullText = document.getText();
// 检查是否是 Squirrel 代码 // 检查是否是 Squirrel 代码
const textBefore = document.getText(new vscode.Range(new vscode.Position(0, 0), position)); if (!isSquirrelCode(fullText)) {
if (!isSquirrelCode(textBefore)) { return edits; // 如果不是 Squirrel 代码,不应用格式化
}
// 使用 js-beautify 格式化代码
const formattedText = beautifyCode(fullText, options);
// 如果格式化后的代码与原代码相同,不需要修改
if (formattedText === fullText) {
return edits; return edits;
} }
// 根据输入的字符执行不同的格式化操作 // 创建编辑操作,替换整个文档
switch (ch) { const fullRange = new vscode.Range(
case ')': document.positionAt(0),
// 输入右括号时格式化当前行 document.positionAt(fullText.length)
edits.push(...this.formatCurrentLine(document, position, options)); );
break;
case ';': edits.push(vscode.TextEdit.replace(fullRange, formattedText));
// 输入分号时格式化当前行
edits.push(...this.formatCurrentLine(document, position, options));
break;
case '}':
// 输入右大括号时格式化整个代码块
edits.push(...this.formatCodeBlock(document, position, options));
break;
default:
break;
}
} catch (error) { } catch (error) {
console.error('输入时格式化失败:', error); console.error('输入时格式化失败:', error);
} // 如果格式化失败,返回空编辑数组,保持原代码不变
return edits;
}
/**
* 使用 js-beautify 格式化当前行
*/
private formatCurrentLine(
document: vscode.TextDocument,
position: vscode.Position,
options: vscode.FormattingOptions
): vscode.TextEdit[] {
const edits: vscode.TextEdit[] = [];
try {
// 获取当前行
const line = document.lineAt(position.line);
const lineText = line.text;
// 获取当前行的上下文(向前几行,向后几行)
const startLine = Math.max(0, position.line - 2);
const endLine = Math.min(document.lineCount - 1, position.line + 2);
const contextText = document.getText(
new vscode.Range(
new vscode.Position(startLine, 0),
new vscode.Position(endLine, document.lineAt(endLine).text.length)
)
);
// 使用 js-beautify 格式化代码块
const formattedContext = beautifyCode(contextText, options);
// 比较原始文本和格式化后的文本
if (formattedContext === contextText) {
return edits; // 没有变化,不需要编辑
}
// 应用格式化结果
const originalLines = contextText.split('\n');
const formattedLines = formattedContext.split('\n');
for (let i = 0; i < originalLines.length && i < formattedLines.length; i++) {
const original = originalLines[i];
const formatted = formattedLines[i];
if (original !== formatted) {
const lineNumber = startLine + i;
const range = new vscode.Range(
new vscode.Position(lineNumber, 0),
new vscode.Position(lineNumber, document.lineAt(lineNumber).text.length)
);
edits.push(vscode.TextEdit.replace(range, formatted));
}
}
} catch (error) {
console.error('格式化当前行失败:', error);
}
return edits;
}
/**
* 使用 js-beautify 格式化代码块
*/
private formatCodeBlock(
document: vscode.TextDocument,
position: vscode.Position,
options: vscode.FormattingOptions
): vscode.TextEdit[] {
const edits: vscode.TextEdit[] = [];
try {
// 查找匹配的左大括号
let braceCount = 1;
let blockStartLine = -1;
for (let i = position.line - 1; i >= 0; i--) {
const currentLine = document.lineAt(i);
const lineText = currentLine.text;
for (let j = lineText.length - 1; j >= 0; j--) {
if (lineText[j] === '}') {
braceCount++;
} else if (lineText[j] === '{') {
braceCount--;
if (braceCount === 0) {
blockStartLine = i;
break;
}
}
}
if (blockStartLine !== -1) {
break;
}
}
if (blockStartLine !== -1) {
// 获取代码块的范围
const endLine = position.line;
const blockText = document.getText(
new vscode.Range(
new vscode.Position(blockStartLine, 0),
new vscode.Position(endLine + 1, 0) // 包含右大括号行
)
);
// 使用 js-beautify 格式化代码块
const formattedBlock = beautifyCode(blockText, options);
if (formattedBlock === blockText) {
return edits; // 没有变化
}
// 应用格式化结果
const range = new vscode.Range(
new vscode.Position(blockStartLine, 0),
new vscode.Position(endLine + 1, 0)
);
edits.push(vscode.TextEdit.replace(range, formattedBlock));
}
} catch (error) {
console.error('格式化代码块失败:', error);
} }
return edits; return edits;