Skip to content

Commit 2ddfa2e

Browse files
committed
Refactor and test cases
1 parent 4527fd7 commit 2ddfa2e

6 files changed

Lines changed: 246 additions & 109 deletions

File tree

src/vs/editor/common/config/commonEditorConfig.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -404,7 +404,7 @@ const editorConfiguration: IConfigurationNode = {
404404
'editor.autoIndent': {
405405
'type': 'boolean',
406406
'default': EDITOR_DEFAULTS.autoIndent,
407-
'description': nls.localize('autoIndent', "Controls if the editor should automatically adjust the indenation when users type. Indentation Rules of the language must be available. ")
407+
'description': nls.localize('autoIndent', "Controls if the editor should automatically adjust the indenation when users type, paste or move lines. Indentation Rules of the language must be available. ")
408408
},
409409
'editor.suggestOnTriggerCharacters': {
410410
'type': 'boolean',
Lines changed: 37 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,37 @@
1+
/*---------------------------------------------------------------------------------------------
2+
* Copyright (c) Microsoft Corporation. All rights reserved.
3+
* Licensed under the MIT License. See License.txt in the project root for license information.
4+
*--------------------------------------------------------------------------------------------*/
5+
6+
export function getSpaceCnt(str, tabSize) {
7+
let spacesCnt = 0;
8+
9+
for (let i = 0; i < str.length; i++) {
10+
if (str.charAt(i) === '\t') {
11+
spacesCnt += tabSize;
12+
} else {
13+
spacesCnt++;
14+
}
15+
}
16+
17+
return spacesCnt;
18+
}
19+
20+
export function generateIndent(spacesCnt: number, tabSize, insertSpaces) {
21+
spacesCnt = spacesCnt < 0 ? 0 : spacesCnt;
22+
23+
let result = '';
24+
if (!insertSpaces) {
25+
let tabsCnt = Math.floor(spacesCnt / tabSize);
26+
spacesCnt = spacesCnt % tabSize;
27+
for (let i = 0; i < tabsCnt; i++) {
28+
result += '\t';
29+
}
30+
}
31+
32+
for (let i = 0; i < spacesCnt; i++) {
33+
result += ' ';
34+
}
35+
36+
return result;
37+
}

src/vs/editor/contrib/indentation/common/indentation.ts

Lines changed: 9 additions & 41 deletions
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,7 @@ import { TextModel } from 'vs/editor/common/model/textModel';
1919
import { LanguageConfigurationRegistry } from 'vs/editor/common/modes/languageConfigurationRegistry';
2020
import { ShiftCommand } from 'vs/editor/common/commands/shiftCommand';
2121
import { TextEdit } from 'vs/editor/common/modes';
22+
import * as IndentUtil from './indentUtils';
2223

2324
export function shiftIndent(tabSize: number, indentation: string, count?: number): string {
2425
count = count || 1;
@@ -402,7 +403,7 @@ export class AutoIndentOnPaste implements IEditorContribution {
402403
this.callOnModel = dispose(this.callOnModel);
403404

404405
// we are disabled
405-
if (!this.editor.getConfiguration().autoIndent) {
406+
if (!this.editor.getConfiguration().autoIndent || this.editor.getConfiguration().contribInfo.formatOnPaste) {
406407
return;
407408
}
408409

@@ -451,11 +452,11 @@ export class AutoIndentOnPaste implements IEditorContribution {
451452
if (indentOfFirstLine !== null) {
452453
let firstLineText = model.getLineContent(range.startLineNumber);
453454
let oldIndentation = strings.getLeadingWhitespace(firstLineText);
454-
let newSpaceCnt = this.getSpaceCnt(indentOfFirstLine, tabSize);
455-
let oldSpaceCnt = this.getSpaceCnt(oldIndentation, tabSize);
455+
let newSpaceCnt = IndentUtil.getSpaceCnt(indentOfFirstLine, tabSize);
456+
let oldSpaceCnt = IndentUtil.getSpaceCnt(oldIndentation, tabSize);
456457

457458
if (newSpaceCnt !== oldSpaceCnt) {
458-
let newIndent = this.generateIndent(newSpaceCnt, tabSize, insertSpaces);
459+
let newIndent = IndentUtil.generateIndent(newSpaceCnt, tabSize, insertSpaces);
459460
textEdits.push({
460461
range: new Range(range.startLineNumber, 1, range.startLineNumber, oldIndentation.length + 1),
461462
text: newIndent
@@ -483,17 +484,17 @@ export class AutoIndentOnPaste implements IEditorContribution {
483484
}
484485
};
485486
let indentOfSecondLine = LanguageConfigurationRegistry.getGoodIndentForLine(virtualModel, model.getLanguageIdentifier().id, range.startLineNumber + 1, indentConverter);
486-
let newSpaceCntOfSecondLine = this.getSpaceCnt(indentOfSecondLine, tabSize);
487-
let oldSpaceCntOfSecondLine = this.getSpaceCnt(strings.getLeadingWhitespace(model.getLineContent(range.startLineNumber + 1)), tabSize);
487+
let newSpaceCntOfSecondLine = IndentUtil.getSpaceCnt(indentOfSecondLine, tabSize);
488+
let oldSpaceCntOfSecondLine = IndentUtil.getSpaceCnt(strings.getLeadingWhitespace(model.getLineContent(range.startLineNumber + 1)), tabSize);
488489

489490
if (newSpaceCntOfSecondLine !== oldSpaceCntOfSecondLine) {
490491
let spaceCntOffset = newSpaceCntOfSecondLine - oldSpaceCntOfSecondLine;
491492
for (let i = range.startLineNumber + 1; i <= range.endLineNumber; i++) {
492493
let lineContent = model.getLineContent(i);
493494
let originalIndent = strings.getLeadingWhitespace(lineContent);
494-
let originalSpacesCnt = this.getSpaceCnt(originalIndent, tabSize);
495+
let originalSpacesCnt = IndentUtil.getSpaceCnt(originalIndent, tabSize);
495496
let newSpacesCnt = originalSpacesCnt + spaceCntOffset;
496-
let newIndent = this.generateIndent(newSpacesCnt, tabSize, insertSpaces);
497+
let newIndent = IndentUtil.generateIndent(newSpacesCnt, tabSize, insertSpaces);
497498

498499
if (newIndent !== originalIndent) {
499500
textEdits.push({
@@ -519,39 +520,6 @@ export class AutoIndentOnPaste implements IEditorContribution {
519520
this.callOnDispose = dispose(this.callOnDispose);
520521
this.callOnModel = dispose(this.callOnModel);
521522
}
522-
523-
private getSpaceCnt(str, tabSize) {
524-
let spacesCnt = 0;
525-
526-
for (let i = 0; i < str.length; i++) {
527-
if (str.charAt(i) === '\t') {
528-
spacesCnt += tabSize;
529-
} else {
530-
spacesCnt++;
531-
}
532-
}
533-
534-
return spacesCnt;
535-
}
536-
537-
private generateIndent(spacesCnt: number, tabSize, insertSpaces) {
538-
spacesCnt = spacesCnt < 0 ? 0 : spacesCnt;
539-
540-
let result = '';
541-
if (!insertSpaces) {
542-
let tabsCnt = Math.floor(spacesCnt / tabSize);
543-
spacesCnt = spacesCnt % tabSize;
544-
for (let i = 0; i < tabsCnt; i++) {
545-
result += '\t';
546-
}
547-
}
548-
549-
for (let i = 0; i < spacesCnt; i++) {
550-
result += ' ';
551-
}
552-
553-
return result;
554-
}
555523
}
556524

557525
function getIndentationEditOperations(model: ITokenizedModel, builder: IEditOperationBuilder, tabSize: number, tabsToSpaces: boolean): void {

src/vs/editor/contrib/linesOperations/common/moveLinesCommand.ts

Lines changed: 32 additions & 66 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,7 @@ import { Selection } from 'vs/editor/common/core/selection';
1010
import { ICommand, ICursorStateComputerData, IEditOperationBuilder, ITokenizedModel } from 'vs/editor/common/editorCommon';
1111
import { LanguageConfigurationRegistry } from 'vs/editor/common/modes/languageConfigurationRegistry';
1212
import { ShiftCommand } from 'vs/editor/common/commands/shiftCommand';
13+
import * as IndentUtil from 'vs/editor/contrib/indentation/common/indentUtils';
1314

1415
export class MoveLinesCommand implements ICommand {
1516

@@ -113,22 +114,22 @@ export class MoveLinesCommand implements ICommand {
113114
let insertingText = movingLineText;
114115
// Insert line that needs to be moved before
115116

116-
if (this._autoIndent) {
117+
if (this.isAutoIndent(model, s)) {
117118
virtualModel.getLineContent = (lineNumber) => {
118119
if (lineNumber === s.startLineNumber) {
119120
return model.getLineContent(movingLineNumber);
120121
} else {
121122
return model.getLineContent(lineNumber);
122123
}
123124
};
124-
let newIndentation = LanguageConfigurationRegistry.getGoodIndentForLine(virtualModel, model.getLanguageIdAtPosition(
125+
let indentOfMovingLine = LanguageConfigurationRegistry.getGoodIndentForLine(virtualModel, model.getLanguageIdAtPosition(
125126
movingLineNumber, 1), s.startLineNumber, indentConverter);
126-
if (newIndentation !== null) {
127+
if (indentOfMovingLine !== null) {
127128
let oldIndentation = strings.getLeadingWhitespace(model.getLineContent(movingLineNumber));
128-
let newSpaceCnt = this.getSpaceCnt(newIndentation, tabSize);
129-
let oldSpaceCnt = this.getSpaceCnt(oldIndentation, tabSize);
129+
let newSpaceCnt = IndentUtil.getSpaceCnt(indentOfMovingLine, tabSize);
130+
let oldSpaceCnt = IndentUtil.getSpaceCnt(oldIndentation, tabSize);
130131
if (newSpaceCnt !== oldSpaceCnt) {
131-
let newIndentation = this.generateIndent(newSpaceCnt, tabSize, insertSpaces);
132+
let newIndentation = IndentUtil.generateIndent(newSpaceCnt, tabSize, insertSpaces);
132133
insertingText = newIndentation + strings.ltrim(strings.ltrim(movingLineText), '\t');
133134
}
134135
}
@@ -147,27 +148,17 @@ export class MoveLinesCommand implements ICommand {
147148
}
148149
};
149150

150-
let newIndentationForMovingBlock = LanguageConfigurationRegistry.getGoodIndentForLine(virtualModel, model.getLanguageIdAtPosition(
151+
let newIndentatOfMovingBlock = LanguageConfigurationRegistry.getGoodIndentForLine(virtualModel, model.getLanguageIdAtPosition(
151152
movingLineNumber, 1), s.startLineNumber + 1, indentConverter);
152153

153-
if (newIndentationForMovingBlock !== null) {
154-
let oldIndentation = strings.getLeadingWhitespace(model.getLineContent(s.startLineNumber));
155-
let newSpaceCnt = this.getSpaceCnt(newIndentationForMovingBlock, tabSize);
156-
let oldSpaceCnt = this.getSpaceCnt(oldIndentation, tabSize);
154+
if (newIndentatOfMovingBlock !== null) {
155+
const oldIndentation = strings.getLeadingWhitespace(model.getLineContent(s.startLineNumber));
156+
const newSpaceCnt = IndentUtil.getSpaceCnt(newIndentatOfMovingBlock, tabSize);
157+
const oldSpaceCnt = IndentUtil.getSpaceCnt(oldIndentation, tabSize);
157158
if (newSpaceCnt !== oldSpaceCnt) {
158-
let spaceCntOffset = newSpaceCnt - oldSpaceCnt;
159+
const spaceCntOffset = newSpaceCnt - oldSpaceCnt;
159160

160-
for (let i = s.startLineNumber; i <= s.endLineNumber; i++) {
161-
let lineContent = model.getLineContent(i);
162-
let originalIndent = strings.getLeadingWhitespace(lineContent);
163-
let originalSpacesCnt = this.getSpaceCnt(originalIndent, tabSize);
164-
let newSpacesCnt = originalSpacesCnt + spaceCntOffset;
165-
let newIndent = this.generateIndent(newSpacesCnt, tabSize, insertSpaces);
166-
167-
if (newIndent !== originalIndent) {
168-
builder.addEditOperation(new Range(i, 1, i, originalIndent.length + 1), newIndent);
169-
}
170-
}
161+
this.getIndentEditsOfMovingBlock(model, builder, s.startLineNumber, s.endLineNumber, tabSize, insertSpaces, spaceCntOffset);
171162
}
172163
}
173164
} else {
@@ -183,7 +174,7 @@ export class MoveLinesCommand implements ICommand {
183174
// Insert line that needs to be moved after
184175
builder.addEditOperation(new Range(s.endLineNumber, model.getLineMaxColumn(s.endLineNumber), s.endLineNumber, model.getLineMaxColumn(s.endLineNumber)), '\n' + movingLineText);
185176

186-
if (this._autoIndent && (model.getLanguageIdAtPosition(s.startLineNumber, 1) === model.getLanguageIdAtPosition(s.endLineNumber, 1))) {
177+
if (this.isAutoIndent(model, s)) {
187178
virtualModel.getLineContent = (lineNumber: number) => {
188179
if (lineNumber === movingLineNumber) {
189180
return model.getLineContent(s.startLineNumber);
@@ -192,26 +183,16 @@ export class MoveLinesCommand implements ICommand {
192183
}
193184
};
194185

195-
let newIndentation = LanguageConfigurationRegistry.getGoodIndentForLine(virtualModel, model.getLanguageIdAtPosition(s.startLineNumber, 1), movingLineNumber, indentConverter);
196-
if (newIndentation !== null) {
186+
let indentOfFirstLine = LanguageConfigurationRegistry.getGoodIndentForLine(virtualModel, model.getLanguageIdAtPosition(s.startLineNumber, 1), movingLineNumber, indentConverter);
187+
if (indentOfFirstLine !== null) {
197188
// adjust the indentation of the moving block
198-
let oldIndentation = strings.getLeadingWhitespace(model.getLineContent(s.startLineNumber));
199-
let newSpaceCnt = this.getSpaceCnt(newIndentation, tabSize);
200-
let oldSpaceCnt = this.getSpaceCnt(oldIndentation, tabSize);
189+
let oldIndent = strings.getLeadingWhitespace(model.getLineContent(s.startLineNumber));
190+
let newSpaceCnt = IndentUtil.getSpaceCnt(indentOfFirstLine, tabSize);
191+
let oldSpaceCnt = IndentUtil.getSpaceCnt(oldIndent, tabSize);
201192
if (newSpaceCnt !== oldSpaceCnt) {
202193
let spaceCntOffset = newSpaceCnt - oldSpaceCnt;
203194

204-
for (let i = s.startLineNumber; i <= s.endLineNumber; i++) {
205-
let lineContent = model.getLineContent(i);
206-
let originalIndent = strings.getLeadingWhitespace(lineContent);
207-
let originalSpacesCnt = this.getSpaceCnt(originalIndent, tabSize);
208-
let newSpacesCnt = originalSpacesCnt + spaceCntOffset;
209-
let newIndent = this.generateIndent(newSpacesCnt, tabSize, insertSpaces);
210-
211-
if (newIndent !== originalIndent) {
212-
builder.addEditOperation(new Range(i, 1, i, originalIndent.length + 1), newIndent);
213-
}
214-
}
195+
this.getIndentEditsOfMovingBlock(model, builder, s.startLineNumber, s.endLineNumber, tabSize, insertSpaces, spaceCntOffset);
215196
}
216197
}
217198
}
@@ -221,37 +202,22 @@ export class MoveLinesCommand implements ICommand {
221202
this._selectionId = builder.trackSelection(s);
222203
}
223204

224-
private getSpaceCnt(str, tabSize) {
225-
let spacesCnt = 0;
226-
227-
for (let i = 0; i < str.length; i++) {
228-
if (str.charAt(i) === '\t') {
229-
spacesCnt += tabSize;
230-
} else {
231-
spacesCnt++;
232-
}
233-
}
234-
235-
return spacesCnt;
205+
private isAutoIndent(model: ITokenizedModel, selection: Selection) {
206+
return this._autoIndent && (model.getLanguageIdAtPosition(selection.startLineNumber, 1) === model.getLanguageIdAtPosition(selection.endLineNumber, 1));
236207
}
237208

238-
private generateIndent(spacesCnt: number, tabSize, insertSpaces) {
239-
spacesCnt = spacesCnt < 0 ? 0 : spacesCnt;
209+
private getIndentEditsOfMovingBlock(model: ITokenizedModel, builder: IEditOperationBuilder, startLineNumber: number, endLineNumber: number, tabSize: number, insertSpaces: boolean, offset: number) {
210+
for (let i = startLineNumber; i <= endLineNumber; i++) {
211+
let lineContent = model.getLineContent(i);
212+
let originalIndent = strings.getLeadingWhitespace(lineContent);
213+
let originalSpacesCnt = IndentUtil.getSpaceCnt(originalIndent, tabSize);
214+
let newSpacesCnt = originalSpacesCnt + offset;
215+
let newIndent = IndentUtil.generateIndent(newSpacesCnt, tabSize, insertSpaces);
240216

241-
let result = '';
242-
if (!insertSpaces) {
243-
let tabsCnt = Math.floor(spacesCnt / tabSize);
244-
spacesCnt = spacesCnt % tabSize;
245-
for (let i = 0; i < tabsCnt; i++) {
246-
result += '\t';
217+
if (newIndent !== originalIndent) {
218+
builder.addEditOperation(new Range(i, 1, i, originalIndent.length + 1), newIndent);
247219
}
248220
}
249-
250-
for (let i = 0; i < spacesCnt; i++) {
251-
result += ' ';
252-
}
253-
254-
return result;
255221
}
256222

257223
public computeCursorState(model: ITokenizedModel, helper: ICursorStateComputerData): Selection {

0 commit comments

Comments
 (0)