diff --git a/src/vs/base/common/filters.ts b/src/vs/base/common/filters.ts index 6ce34e3425d13e82e48d1b4dbc9e9d4ec8a748db..4650340de90aadbdcb8a1f89f944b805f8704c0d 100644 --- a/src/vs/base/common/filters.ts +++ b/src/vs/base/common/filters.ts @@ -454,7 +454,7 @@ const enum Arrow { Top = 0b1, Diag = 0b10, Left = 0b100 } export type FuzzyScore = [number, number[]]; -export function fuzzyScore(pattern: string, word: string, patternMaxWhitespaceIgnore?: number): FuzzyScore { +export function fuzzyScore(pattern: string, word: string, patternMaxWhitespaceIgnore?: number, firstMatchCanBeWeak?: boolean): FuzzyScore { const patternLen = pattern.length > 100 ? 100 : pattern.length; const wordLen = word.length > 100 ? 100 : word.length; @@ -578,6 +578,7 @@ export function fuzzyScore(pattern: string, word: string, patternMaxWhitespaceIg _matchesCount = 0; _topScore = -100; _patternStartPos = patternStartPos; + _firstMatchCanBeWeak = firstMatchCanBeWeak; _findAllMatches(patternLen, wordLen, patternLen === wordLen ? 1 : 0, new LazyArray(), false); if (_matchesCount === 0) { @@ -591,6 +592,7 @@ let _matchesCount: number = 0; let _topMatch: LazyArray; let _topScore: number = 0; let _patternStartPos: number = 0; +let _firstMatchCanBeWeak: boolean = false; function _findAllMatches(patternPos: number, wordPos: number, total: number, matches: LazyArray, lastMatched: boolean): void { @@ -644,7 +646,7 @@ function _findAllMatches(patternPos: number, wordPos: number, total: number, mat if (score === 1) { simpleMatchCount += 1; - if (patternPos === _patternStartPos) { + if (patternPos === _patternStartPos && !_firstMatchCanBeWeak) { // when the first match is a weak // match we discard it return undefined; diff --git a/src/vs/base/test/common/filters.test.ts b/src/vs/base/test/common/filters.test.ts index e6a6f795eed0ec6fc26df30ed6662197db90b596..6ea05657ca98903464fa6d895de0c8bf138cc5a2 100644 --- a/src/vs/base/test/common/filters.test.ts +++ b/src/vs/base/test/common/filters.test.ts @@ -309,6 +309,14 @@ suite('Filters', () => { assertMatches('fo', 'bar\\foo', 'bar\\^f^oo', fuzzyScore); }); + test('fuzzyScore (first match can be weak)', function () { + let fuzzyScoreWeak = (pattern, word) => fuzzyScore(pattern, word, undefined, true); + assertMatches('Three', 'HTMLHRElement', 'H^TML^H^R^El^ement', fuzzyScoreWeak); + assertMatches('tor', 'constructor', 'construc^t^o^r', fuzzyScoreWeak); + assertMatches('ur', 'constructor', 'constr^ucto^r', fuzzyScoreWeak); + assertTopScore(fuzzyScoreWeak, 'tor', 2, 'constructor', 'Thor', 'cTor'); + }); + test('fuzzyScore, many matches', function () { assertMatches( diff --git a/src/vs/workbench/parts/outline/electron-browser/outlineModel.ts b/src/vs/workbench/parts/outline/electron-browser/outlineModel.ts index 7a3c109e48ca87568e3ac81a8e18ba2a6664669b..daaf2ea3e2aaff02b029d9f952a62c324eb41dd9 100644 --- a/src/vs/workbench/parts/outline/electron-browser/outlineModel.ts +++ b/src/vs/workbench/parts/outline/electron-browser/outlineModel.ts @@ -105,7 +105,7 @@ export class OutlineGroup extends TreeElement { } private _updateMatches(pattern: string, item: OutlineElement, topMatch: OutlineElement): OutlineElement { - item.score = fuzzyScore(pattern, item.symbol.name); + item.score = fuzzyScore(pattern, item.symbol.name, undefined, true); if (item.score && (!topMatch || item.score[0] > topMatch.score[0])) { topMatch = item; }