in src/language/providers/elementCompletion.ts [477:562]
export function getTagNearestTrigger(
document: vscode.TextDocument,
position: vscode.Position,
triggerText: string,
triggerLine: number,
triggerPos: number,
itemsOnLine: number,
nsPrefix: string
): [string, vscode.Position] {
let [startLine, startPos] = [triggerLine, triggerPos]
let tagNearestTrigger = 'none'
if (
itemsOnLine === 0 &&
document.lineCount === 1 &&
position.character === 0
) {
return ['emptySchema', position]
}
while (true) {
let [foundTag, foundLine, foundPos] = nearestTag(
document,
position,
nsPrefix,
startLine,
startPos
)
if (itemsOnLine > 1) {
const afterTriggerText = triggerText.substring(triggerPos)
const afterTriggerPos = afterTriggerText.indexOf('<') + triggerPos
const beforeTriggerText = triggerText.substring(0, triggerPos)
const lastOpenTagBeforeTriggerPos = beforeTriggerText.lastIndexOf('<')
const beforeTriggerPos = beforeTriggerText.lastIndexOf('>')
const beforeTriggerTag = beforeTriggerText.substring(
lastOpenTagBeforeTriggerPos
)
if (
triggerPos === afterTriggerPos &&
triggerPos === beforeTriggerPos + 1 &&
!beforeTriggerTag.startsWith('</')
) {
tagNearestTrigger = foundTag
return [tagNearestTrigger, new vscode.Position(foundLine, foundPos)]
}
}
startLine = foundLine
let [endTag, endTagLine, endTagPos] = getCloseTag(
document,
position,
nsPrefix,
foundTag,
foundLine,
foundPos
)
if (itemsOnLine > 1 && foundLine === triggerLine) {
if (foundTag === endTag && endTagPos >= triggerPos) {
tagNearestTrigger = foundTag
return [tagNearestTrigger, new vscode.Position(foundLine, foundPos)]
}
if (endTag === 'none') {
startLine = foundLine - 1
} else {
startPos = foundPos - 1
}
}
if (itemsOnLine < 2) {
if (
(foundTag === endTag && endTagLine >= triggerLine) ||
endTag === 'xml version'
) {
tagNearestTrigger = foundTag
return [tagNearestTrigger, new vscode.Position(foundLine, foundPos)]
}
startLine = foundLine - 1
}
}
}