@@ -98,6 +98,7 @@ export class InterfaceManager extends DisposableObject {
9898
9999 super ( ) ;
100100 this . push ( this . _diagnosticCollection ) ;
101+ this . push ( vscode . window . onDidChangeTextEditorSelection ( this . handleSelectionChange . bind ( this ) ) ) ;
101102 }
102103
103104 // Returns the webview panel, creating it if it doesn't already
@@ -398,16 +399,54 @@ export class InterfaceManager extends DisposableObject {
398399 sortState : info . sortState
399400 } ;
400401 }
402+
403+ private handleSelectionChange ( event : vscode . TextEditorSelectionChangeEvent ) {
404+ if ( event . kind === vscode . TextEditorSelectionChangeKind . Command ) {
405+ return ; // Ignore selection events we caused ourselves.
406+ }
407+ let editor = vscode . window . activeTextEditor ;
408+ if ( editor !== undefined ) {
409+ editor . setDecorations ( shownLocationDecoration , [ ] ) ;
410+ editor . setDecorations ( shownLocationLineDecoration , [ ] ) ;
411+ }
412+ }
401413}
402414
415+ const findMatchBackground = new vscode . ThemeColor ( 'editor.findMatchBackground' ) ;
416+ const findRangeHighlightBackground = new vscode . ThemeColor ( 'editor.findRangeHighlightBackground' ) ;
417+
418+ const shownLocationDecoration = vscode . window . createTextEditorDecorationType ( {
419+ backgroundColor : findMatchBackground ,
420+ } ) ;
421+
422+ const shownLocationLineDecoration = vscode . window . createTextEditorDecorationType ( {
423+ backgroundColor : findRangeHighlightBackground ,
424+ isWholeLine : true
425+ } ) ;
426+
403427async function showLocation ( loc : ResolvableLocationValue , databaseItem : DatabaseItem ) : Promise < void > {
404428 const resolvedLocation = tryResolveLocation ( loc , databaseItem ) ;
405429 if ( resolvedLocation ) {
406430 const doc = await workspace . openTextDocument ( resolvedLocation . uri ) ;
407431 const editor = await Window . showTextDocument ( doc , vscode . ViewColumn . One ) ;
408- const sel = new vscode . Selection ( resolvedLocation . range . start , resolvedLocation . range . end ) ;
409- editor . selection = sel ;
410- editor . revealRange ( sel , vscode . TextEditorRevealType . InCenter ) ;
432+ let range = resolvedLocation . range ;
433+ // When highlighting the range, vscode's occurrence-match and bracket-match highlighting will
434+ // trigger based on where we place the cursor/selection, and will compete for the user's attention.
435+ // For reference:
436+ // - Occurences are highlighted when the cursor is next to or inside a word or a whole word is selected.
437+ // - Brackets are highlighted when the cursor is next to a bracket and there is an empty selection.
438+ // - Multi-line selections explicitly highlight line-break characters, but multi-line decorators do not.
439+ //
440+ // For single-line ranges, select the whole range, mainly to disable bracket highlighting.
441+ // For multi-line ranges, place the cursor at the beginning to avoid visual artifacts from selected line-breaks.
442+ // Multi-line ranges are usually large enough to overshadow the noise from bracket highlighting.
443+ let selectionEnd = ( range . start . line === range . end . line )
444+ ? range . end
445+ : range . start ;
446+ editor . selection = new vscode . Selection ( range . start , selectionEnd ) ;
447+ editor . revealRange ( range , vscode . TextEditorRevealType . InCenter ) ;
448+ editor . setDecorations ( shownLocationDecoration , [ range ] ) ;
449+ editor . setDecorations ( shownLocationLineDecoration , [ range ] ) ;
411450 }
412451}
413452
0 commit comments