diff --git a/src/vs/editor/contrib/find/common/findModel.ts b/src/vs/editor/contrib/find/common/findModel.ts index 9fff3acac845ccfcd51a906b1b9ddadcf0a3a265..83c3bde8e72cce5eeb775704f88a6db198820912 100644 --- a/src/vs/editor/contrib/find/common/findModel.ts +++ b/src/vs/editor/contrib/find/common/findModel.ts @@ -428,8 +428,19 @@ export class FindModelBoundToEditorModel { // Get all the ranges (even more than the highlighted ones) let ranges = this._findMatches(findScope, Number.MAX_VALUE); + let selections = ranges.map(r => new Selection(r.startLineNumber, r.startColumn, r.endLineNumber, r.endColumn)); + + // If one of the ranges is the editor selection, then maintain it as primary + let editorSelection = this._editor.getSelection(); + for (let i = 0, len = selections.length; i < len; i++) { + let sel = selections[i]; + if (sel.equalsRange(editorSelection)) { + selections = [editorSelection].concat(selections.slice(0, i)).concat(selections.slice(i + 1)); + break; + } + } - this._editor.setSelections(ranges.map(r => new Selection(r.startLineNumber, r.startColumn, r.endLineNumber, r.endColumn))); + this._editor.setSelections(selections); } private _executeEditorCommand(source: string, command: editorCommon.ICommand): void { diff --git a/src/vs/editor/contrib/find/test/common/findModel.test.ts b/src/vs/editor/contrib/find/test/common/findModel.test.ts index 266f7bba7903fa05b94e16c32f4014537cde70fa..4af097a3886f2f9249e9e4cc1b68e3ee85ace84e 100644 --- a/src/vs/editor/contrib/find/test/common/findModel.test.ts +++ b/src/vs/editor/contrib/find/test/common/findModel.test.ts @@ -1585,6 +1585,52 @@ suite('FindModel', () => { findState.dispose(); }); + findTest('issue #14143 selectAllMatches should maintain primary cursor if feasible', (editor, cursor) => { + let findState = new FindReplaceState(); + findState.change({ searchString: 'hello', replaceString: 'hi', wholeWord: true }, false); + let findModel = new FindModelBoundToEditorModel(editor, findState); + + assertFindState( + editor, + [1, 1, 1, 1], + null, + [ + [6, 14, 6, 19], + [6, 27, 6, 32], + [7, 14, 7, 19], + [8, 14, 8, 19] + ] + ); + + editor.setSelection(new Range(7, 14, 7, 19)); + + findModel.selectAllMatches(); + + assert.deepEqual(editor.getSelections().map(s => s.toString()), [ + new Selection(7, 14, 7, 19), + new Selection(6, 14, 6, 19), + new Selection(6, 27, 6, 32), + new Selection(8, 14, 8, 19) + ].map(s => s.toString())); + + assert.deepEqual(editor.getSelection().toString(), new Selection(7, 14, 7, 19).toString()); + + assertFindState( + editor, + [7, 14, 7, 19], + null, + [ + [6, 14, 6, 19], + [6, 27, 6, 32], + [7, 14, 7, 19], + [8, 14, 8, 19] + ] + ); + + findModel.dispose(); + findState.dispose(); + }); + findTest('issue #1914: NPE when there is only one find match', (editor, cursor) => { let findState = new FindReplaceState(); findState.change({ searchString: 'cool.h' }, false);