Skip to content

Commit

Permalink
Fixes #15774: Use configured word separators for Ctrl+D
Browse files Browse the repository at this point in the history
  • Loading branch information
alexdima committed Feb 28, 2020
1 parent 3d23d67 commit 7f1bde5
Show file tree
Hide file tree
Showing 6 changed files with 42 additions and 6 deletions.
7 changes: 6 additions & 1 deletion src/vs/editor/browser/editorBrowser.ts
Expand Up @@ -13,7 +13,7 @@ import { IPosition, Position } from 'vs/editor/common/core/position';
import { IRange, Range } from 'vs/editor/common/core/range';
import { Selection } from 'vs/editor/common/core/selection';
import * as editorCommon from 'vs/editor/common/editorCommon';
import { IIdentifiedSingleEditOperation, IModelDecoration, IModelDeltaDecoration, ITextModel, ICursorStateComputer } from 'vs/editor/common/model';
import { IIdentifiedSingleEditOperation, IModelDecoration, IModelDeltaDecoration, ITextModel, ICursorStateComputer, IWordAtPosition } from 'vs/editor/common/model';
import { IModelContentChangedEvent, IModelDecorationsChangedEvent, IModelLanguageChangedEvent, IModelLanguageConfigurationChangedEvent, IModelOptionsChangedEvent } from 'vs/editor/common/model/textModelEvents';
import { OverviewRulerZone } from 'vs/editor/common/view/overviewZoneManager';
import { IEditorWhitespace } from 'vs/editor/common/viewLayout/linesLayout';
Expand Down Expand Up @@ -567,6 +567,11 @@ export interface ICodeEditor extends editorCommon.IEditor {
*/
getRawOptions(): IEditorOptions;

/**
* @internal
*/
getConfiguredWordAtPosition(position: Position): IWordAtPosition | null;

/**
* Get value of the current model attached to this editor.
* @see `ITextModel.getValue`
Expand Down
10 changes: 9 additions & 1 deletion src/vs/editor/browser/widget/codeEditorWidget.ts
Expand Up @@ -32,7 +32,7 @@ import { ISelection, Selection } from 'vs/editor/common/core/selection';
import { InternalEditorAction } from 'vs/editor/common/editorAction';
import * as editorCommon from 'vs/editor/common/editorCommon';
import { EditorContextKeys } from 'vs/editor/common/editorContextKeys';
import { EndOfLinePreference, IIdentifiedSingleEditOperation, IModelDecoration, IModelDecorationOptions, IModelDecorationsChangeAccessor, IModelDeltaDecoration, ITextModel, ICursorStateComputer } from 'vs/editor/common/model';
import { EndOfLinePreference, IIdentifiedSingleEditOperation, IModelDecoration, IModelDecorationOptions, IModelDecorationsChangeAccessor, IModelDeltaDecoration, ITextModel, ICursorStateComputer, IWordAtPosition } from 'vs/editor/common/model';
import { ClassName } from 'vs/editor/common/model/intervalTree';
import { ModelDecorationOptions } from 'vs/editor/common/model/textModel';
import { IModelContentChangedEvent, IModelDecorationsChangedEvent, IModelLanguageChangedEvent, IModelLanguageConfigurationChangedEvent, IModelOptionsChangedEvent } from 'vs/editor/common/model/textModelEvents';
Expand All @@ -52,6 +52,7 @@ import { IAccessibilityService } from 'vs/platform/accessibility/common/accessib
import { withNullAsUndefined } from 'vs/base/common/types';
import { MonospaceLineBreaksComputerFactory } from 'vs/editor/common/viewModel/monospaceLineBreaksComputer';
import { DOMLineBreaksComputerFactory } from 'vs/editor/browser/view/domLineBreaksComputer';
import { WordOperations } from 'vs/editor/common/controller/cursorWordOperations';

let EDITOR_ID = 0;

Expand Down Expand Up @@ -376,6 +377,13 @@ export class CodeEditorWidget extends Disposable implements editorBrowser.ICodeE
return this._configuration.getRawOptions();
}

public getConfiguredWordAtPosition(position: Position): IWordAtPosition | null {
if (!this._modelData) {
return null;
}
return WordOperations.getWordAtPosition(this._modelData.model, this._configuration.options.get(EditorOption.wordSeparators), position);
}

public getValue(options: { preserveBOM: boolean; lineEnding: string; } | null = null): string {
if (!this._modelData) {
return '';
Expand Down
23 changes: 23 additions & 0 deletions src/vs/editor/common/controller/cursorWordOperations.ts
Expand Up @@ -10,6 +10,7 @@ import { WordCharacterClass, WordCharacterClassifier, getMapForWordSeparators }
import { Position } from 'vs/editor/common/core/position';
import { Range } from 'vs/editor/common/core/range';
import { Selection } from 'vs/editor/common/core/selection';
import { ITextModel, IWordAtPosition } from 'vs/editor/common/model';

interface IFindWordResult {
/**
Expand Down Expand Up @@ -535,6 +536,28 @@ export class WordOperations {
return new Range(pos.lineNumber, pos.column, toPosition.lineNumber, toPosition.column);
}

private static _createWordAtPosition(model: ITextModel, lineNumber: number, word: IFindWordResult): IWordAtPosition {
const range = new Range(lineNumber, word.start + 1, lineNumber, word.end + 1);
return {
word: model.getValueInRange(range),
startColumn: range.startColumn,
endColumn: range.endColumn
};
}

public static getWordAtPosition(model: ITextModel, _wordSeparators: string, position: Position): IWordAtPosition | null {
const wordSeparators = getMapForWordSeparators(_wordSeparators);
const prevWord = WordOperations._findPreviousWordOnLine(wordSeparators, model, position);
if (prevWord && prevWord.wordType === WordType.Regular && prevWord.start <= position.column - 1 && position.column - 1 <= prevWord.end) {
return WordOperations._createWordAtPosition(model, position.lineNumber, prevWord);
}
const nextWord = WordOperations._findNextWordOnLine(wordSeparators, model, position);
if (nextWord && nextWord.wordType === WordType.Regular && nextWord.start <= position.column - 1 && position.column - 1 <= nextWord.end) {
return WordOperations._createWordAtPosition(model, position.lineNumber, nextWord);
}
return null;
}

public static word(config: CursorConfiguration, model: ICursorSimpleModel, cursor: SingleCursorState, inSelectionMode: boolean, position: Position): SingleCursorState {
const wordSeparators = getMapForWordSeparators(config.wordSeparators);
let prevWord = WordOperations._findPreviousWordOnLine(wordSeparators, model, position);
Expand Down
2 changes: 1 addition & 1 deletion src/vs/editor/contrib/find/findController.ts
Expand Up @@ -39,7 +39,7 @@ export function getSelectionSearchString(editor: ICodeEditor): string | null {
// if selection spans multiple lines, default search string to empty
if (selection.startLineNumber === selection.endLineNumber) {
if (selection.isEmpty()) {
let wordAtPosition = editor.getModel().getWordAtPosition(selection.getStartPosition());
const wordAtPosition = editor.getConfiguredWordAtPosition(selection.getStartPosition());
if (wordAtPosition) {
return wordAtPosition.word;
}
Expand Down
2 changes: 1 addition & 1 deletion src/vs/editor/contrib/linesOperations/linesOperations.ts
Expand Up @@ -960,7 +960,7 @@ export abstract class AbstractCaseAction extends EditorAction {
let selection = selections[i];
if (selection.isEmpty()) {
let cursor = selection.getStartPosition();
let word = model.getWordAtPosition(cursor);
const word = editor.getConfiguredWordAtPosition(cursor);

if (!word) {
continue;
Expand Down
4 changes: 2 additions & 2 deletions src/vs/editor/contrib/multicursor/multicursor.ts
Expand Up @@ -286,7 +286,7 @@ export class MultiCursorSession {

if (s.isEmpty()) {
// selection is empty => expand to current word
const word = editor.getModel().getWordAtPosition(s.getStartPosition());
const word = editor.getConfiguredWordAtPosition(s.getStartPosition());
if (!word) {
return null;
}
Expand Down Expand Up @@ -505,7 +505,7 @@ export class MultiCursorSelectionController extends Disposable implements IEdito
if (!selection.isEmpty()) {
return selection;
}
const word = model.getWordAtPosition(selection.getStartPosition());
const word = this._editor.getConfiguredWordAtPosition(selection.getStartPosition());
if (!word) {
return selection;
}
Expand Down

1 comment on commit 7f1bde5

@rockfruit
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks!

Please sign in to comment.