mirror of
https://github.com/microsoft/vscode.git
synced 2026-04-23 18:19:12 +01:00
Add editor.indentSize option
This is an attempt to address issue #10339. Background: Currently, the `editor.tabSize` option does two things - it specifies the width of the tab character and it specifies how many columns to advance when the tab key is pressed. However, there is code in the wild that has a mix of spaces and tabs that expects these two values to be different. These generally use and indent size of 2 or 4 and spaces are used for indentation until the indent becomes >= 8. The tab character size is excpected to be 8 and groups of 8 spaces are replaced with a tab character. Indent levels end up looking like 2 spaces, 4 spaces, 6 spaces, 1 tab, 1 tab + 2 spaces, and so on. Implementation: In the editor options, a new option, `editor.indentSize` is added. This, in conjunction with `editor.tabSize` has the same semantics as `indent_size` and `tab_width` in the well known [EditorConfig specification][1]. > indent_size: a whole number defining the number of columns used for each indentation level and the width of soft tabs (when supported). When set to "tab", the value of tab_width (if specified) will be used. > > tab_width: a whole number defining the number of columns used to represent a tab character. This defaults to the value of indent_size and doesn't usually need to be specified. [1]: editorconfig.org The new `indentSize` option takes a numeric value or "tab" just as EditorConfig's `indent_size`. The default value is set to "tab" so that current default behavior of VS Code does not change and existing user settings will not break. When getting the new `indentSize` option programatically, it always returns a numeric value (just as `tabSize` does when set to the deprecated "auto" value). In the text editor model, a new property is added for `indentSize`. Unlike the configuration options where the value of one property influences the other, In this code `tabSize` now should only mean "the width of the tab character" and `indentSize` should only mean "how may columns is one indent". The cursor operations and shift command are updated to reflect these new semantics.
This commit is contained in:
@@ -176,6 +176,7 @@ export interface MainThreadDocumentsShape extends IDisposable {
|
||||
|
||||
export interface ITextEditorConfigurationUpdate {
|
||||
tabSize?: number | 'auto';
|
||||
indentSize?: number | 'tab';
|
||||
insertSpaces?: boolean | 'auto';
|
||||
cursorStyle?: TextEditorCursorStyle;
|
||||
lineNumbers?: TextEditorLineNumbersStyle;
|
||||
@@ -183,6 +184,7 @@ export interface ITextEditorConfigurationUpdate {
|
||||
|
||||
export interface IResolvedTextEditorConfiguration {
|
||||
tabSize: number;
|
||||
indentSize: number;
|
||||
insertSpaces: boolean;
|
||||
cursorStyle: TextEditorCursorStyle;
|
||||
lineNumbers: TextEditorLineNumbersStyle;
|
||||
|
||||
@@ -142,6 +142,7 @@ export class ExtHostTextEditorOptions implements vscode.TextEditorOptions {
|
||||
private _id: string;
|
||||
|
||||
private _tabSize: number;
|
||||
private _indentSize: number;
|
||||
private _insertSpaces: boolean;
|
||||
private _cursorStyle: TextEditorCursorStyle;
|
||||
private _lineNumbers: TextEditorLineNumbersStyle;
|
||||
@@ -154,6 +155,7 @@ export class ExtHostTextEditorOptions implements vscode.TextEditorOptions {
|
||||
|
||||
public _accept(source: IResolvedTextEditorConfiguration): void {
|
||||
this._tabSize = source.tabSize;
|
||||
this._indentSize = source.indentSize;
|
||||
this._insertSpaces = source.insertSpaces;
|
||||
this._cursorStyle = source.cursorStyle;
|
||||
this._lineNumbers = source.lineNumbers;
|
||||
@@ -200,6 +202,47 @@ export class ExtHostTextEditorOptions implements vscode.TextEditorOptions {
|
||||
}));
|
||||
}
|
||||
|
||||
public get indentSize(): number | string {
|
||||
return this._indentSize;
|
||||
}
|
||||
|
||||
private _validateIndentSize(value: number | string): number | 'tab' | null {
|
||||
if (value === 'tab') {
|
||||
return 'tab';
|
||||
}
|
||||
if (typeof value === 'number') {
|
||||
let r = Math.floor(value);
|
||||
return (r > 0 ? r : null);
|
||||
}
|
||||
if (typeof value === 'string') {
|
||||
let r = parseInt(value, 10);
|
||||
if (isNaN(r)) {
|
||||
return null;
|
||||
}
|
||||
return (r > 0 ? r : null);
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
public set indentSize(value: number | string) {
|
||||
let indentSize = this._validateIndentSize(value);
|
||||
if (indentSize === null) {
|
||||
// ignore invalid call
|
||||
return;
|
||||
}
|
||||
if (typeof indentSize === 'number') {
|
||||
if (this._indentSize === indentSize) {
|
||||
// nothing to do
|
||||
return;
|
||||
}
|
||||
// reflect the new indentSize value immediately
|
||||
this._indentSize = indentSize;
|
||||
}
|
||||
warnOnError(this._proxy.$trySetOptions(this._id, {
|
||||
indentSize: indentSize
|
||||
}));
|
||||
}
|
||||
|
||||
public get insertSpaces(): boolean | string {
|
||||
return this._insertSpaces;
|
||||
}
|
||||
@@ -273,6 +316,19 @@ export class ExtHostTextEditorOptions implements vscode.TextEditorOptions {
|
||||
}
|
||||
}
|
||||
|
||||
if (typeof newOptions.indentSize !== 'undefined') {
|
||||
let indentSize = this._validateIndentSize(newOptions.indentSize);
|
||||
if (indentSize === 'tab') {
|
||||
hasUpdate = true;
|
||||
bulkConfigurationUpdate.indentSize = indentSize;
|
||||
} else if (typeof indentSize === 'number' && this._indentSize !== indentSize) {
|
||||
// reflect the new indentSize value immediately
|
||||
this._indentSize = indentSize;
|
||||
hasUpdate = true;
|
||||
bulkConfigurationUpdate.indentSize = indentSize;
|
||||
}
|
||||
}
|
||||
|
||||
if (typeof newOptions.insertSpaces !== 'undefined') {
|
||||
let insertSpaces = this._validateInsertSpaces(newOptions.insertSpaces);
|
||||
if (insertSpaces === 'auto') {
|
||||
|
||||
Reference in New Issue
Block a user