"use strict"; const vscode = require("vscode"); const COMPONENT_DECLARATION = /^\s*(component|layout)\s+([A-Za-z_$][\w$]*)\s*\{/gm; function getTagAtPosition(document, position) { const range = document.getWordRangeAtPosition(position, /[A-Za-z_$][\w$]*/); if (!range) { return null; } const name = document.getText(range); if (!/^[A-Z][A-Za-z0-9_$]*$/.test(name)) { return null; } const line = document.lineAt(position.line).text; const offset = document.offsetAt(position); const lineStart = document.offsetAt(new vscode.Position(position.line, 0)); const characterOffset = offset - lineStart; const before = line.slice(0, characterOffset); const after = line.slice(characterOffset); const insideTag = before.lastIndexOf("<") > before.lastIndexOf(">") && after.includes(">"); if (!insideTag) { return null; } return { name, range, }; } async function findDeclaration(name) { const files = await vscode.workspace.findFiles( "**/*.wrn", "**/{node_modules,dist,.wrnexus,.git}/**", ); const matches = []; for (const uri of files) { let document; try { document = await vscode.workspace.openTextDocument(uri); } catch { continue; } const source = document.getText(); COMPONENT_DECLARATION.lastIndex = 0; let match; while ((match = COMPONENT_DECLARATION.exec(source)) !== null) { const declarationName = match[2]; if (declarationName !== name) { continue; } const nameOffset = match.index + match[0].indexOf(declarationName); const start = document.positionAt(nameOffset); const end = document.positionAt(nameOffset + declarationName.length); matches.push(new vscode.Location(uri, new vscode.Range(start, end))); } } return matches; } async function provideDefinition(document, position) { const tag = getTagAtPosition(document, position); if (!tag) { return null; } const matches = await findDeclaration(tag.name); if (matches.length === 0) { return null; } return matches.length === 1 ? matches[0] : matches; } function registerDefinitionProvider(context) { const disposable = vscode.languages.registerDefinitionProvider( { language: "wrn", }, { provideDefinition, }, ); context.subscriptions.push(disposable); } module.exports = { findDeclaration, getTagAtPosition, provideDefinition, registerDefinitionProvider, };