From 65c7bd2af05ebab58a0f68f324d20d2a64f85960 Mon Sep 17 00:00:00 2001 From: "tamas.kiss" Date: Tue, 24 May 2016 21:23:27 +0200 Subject: [PATCH 001/217] IThemeDecorationRenderOptions extended with background-size property To be able to show images with arbitrary size on the gutter margin, the css property 'background-size' has been made configurable. --- .../browser/services/codeEditorServiceImpl.ts | 10 +++-- src/vs/editor/common/editorCommon.ts | 1 + .../services/decorationRenderOptions.test.ts | 41 +++++++++++++++++++ src/vs/vscode.d.ts | 7 ++++ 4 files changed, 56 insertions(+), 3 deletions(-) create mode 100644 src/vs/editor/test/browser/services/decorationRenderOptions.test.ts diff --git a/src/vs/editor/browser/services/codeEditorServiceImpl.ts b/src/vs/editor/browser/services/codeEditorServiceImpl.ts index 3e35030ea3f..075333c11cf 100644 --- a/src/vs/editor/browser/services/codeEditorServiceImpl.ts +++ b/src/vs/editor/browser/services/codeEditorServiceImpl.ts @@ -16,9 +16,9 @@ export class CodeEditorServiceImpl extends AbstractCodeEditorService { private _styleSheet: HTMLStyleElement; private _decorationRenderOptions: {[key:string]:DecorationRenderOptions}; - constructor() { + constructor(styleSheet = dom.createStyleSheet()) { super(); - this._styleSheet = dom.createStyleSheet(); + this._styleSheet = styleSheet; this._decorationRenderOptions = Object.create(null); } @@ -129,6 +129,7 @@ class DecorationRenderOptions implements IModelDecorationOptions { letterSpacing: 'letter-spacing:{0};', gutterIconPath: 'background:url(\'{0}\') center center no-repeat;', + gutterIconSize: 'background-size:{0};', }; /** @@ -209,7 +210,10 @@ class DecorationRenderOptions implements IModelDecorationOptions { let cssTextArr = []; if (typeof opts.gutterIconPath !== 'undefined') { - cssTextArr.push(strings.format(this._CSS_MAP.gutterIconPath, URI.file(opts.gutterIconPath).toString())); + cssTextArr.push(strings.format(this._CSS_MAP.gutterIconPath, URI.parse(opts.gutterIconPath).toString())); + if (typeof opts.gutterIconSize !== 'undefined') { + cssTextArr.push(strings.format(this._CSS_MAP.gutterIconSize, opts.gutterIconSize)); + } } return cssTextArr.join(''); diff --git a/src/vs/editor/common/editorCommon.ts b/src/vs/editor/common/editorCommon.ts index ebee3689655..f2be01c94f4 100644 --- a/src/vs/editor/common/editorCommon.ts +++ b/src/vs/editor/common/editorCommon.ts @@ -3192,6 +3192,7 @@ export interface IThemeDecorationRenderOptions { letterSpacing?: string; gutterIconPath?: string; + gutterIconSize?: string; overviewRulerColor?: string; } diff --git a/src/vs/editor/test/browser/services/decorationRenderOptions.test.ts b/src/vs/editor/test/browser/services/decorationRenderOptions.test.ts new file mode 100644 index 00000000000..93bd94c1a1a --- /dev/null +++ b/src/vs/editor/test/browser/services/decorationRenderOptions.test.ts @@ -0,0 +1,41 @@ +/*--------------------------------------------------------------------------------------------- + * Copyright (c) Microsoft Corporation. All rights reserved. + * Licensed under the MIT License. See License.txt in the project root for license information. + *--------------------------------------------------------------------------------------------*/ +'use strict'; + +import * as assert from 'assert'; +import * as dom from 'vs/base/browser/dom'; +import {CodeEditorServiceImpl} from 'vs/editor/browser/services/codeEditorServiceImpl'; +import {IDecorationRenderOptions, IModelDecorationOptions, IModelDecorationOverviewRulerOptions, IThemeDecorationRenderOptions, OverviewRulerLane} from 'vs/editor/common/editorCommon'; + +suite('Browser Services - EditorLayoutProvider', () => { + var options: IDecorationRenderOptions = { + gutterIconPath: 'https://github.com/Microsoft/vscode/blob/master/resources/linux/code.png', + gutterIconSize: 'contain', + backgroundColor: 'red', + borderColor: 'yellow' + }; + test('register and resolve decoration type', () => { + var s = new CodeEditorServiceImpl(); + s.registerDecorationType('example', options); + assert.notEqual(s.resolveDecorationType('example'), undefined); + }); + test('remove decoration type', () => { + var s = new CodeEditorServiceImpl(); + s.registerDecorationType('example', options); + assert.notEqual(s.resolveDecorationType('example'), undefined); + s.removeDecorationType('example'); + assert.throws(() => s.resolveDecorationType('example')); + }); + test('css properties', () => { + var styleSheet = dom.createStyleSheet(); + var s = new CodeEditorServiceImpl(styleSheet); + s.registerDecorationType('example', options); + var sheet = styleSheet.sheet.toString(); + assert(sheet.indexOf('background: url(\'https://github.com/Microsoft/vscode/blob/master/resources/linux/code.png\') center center no-repeat;') > 0); + assert(sheet.indexOf('background-size: contain;') > 0); + assert(sheet.indexOf('border-color: yellow;') > 0); + assert(sheet.indexOf('background-color: red;') > 0); + }); +}); diff --git a/src/vs/vscode.d.ts b/src/vs/vscode.d.ts index e94baed1c95..972486555eb 100644 --- a/src/vs/vscode.d.ts +++ b/src/vs/vscode.d.ts @@ -693,6 +693,13 @@ declare namespace vscode { */ gutterIconPath?: string; + /** + * Specifies the size of the gutter icon. + * Available values are 'auto', 'contain', 'cover' and any percentage value. + * For further information: https://msdn.microsoft.com/en-us/library/jj127316(v=vs.85).aspx + */ + gutterIconSize?: string; + /** * The color of the decoration in the overview ruler. Use rgba() and define transparent colors to play well with other decorations. */ From 1257bcddf22174920b34530d7c723370edaadbaf Mon Sep 17 00:00:00 2001 From: Christian Heilmann Date: Thu, 2 Jun 2016 19:53:07 +0200 Subject: [PATCH 002/217] Adding autocomplete values of to input/select/textarea https://html.spec.whatwg.org/multipage/forms.html#inappropriate-for-the-control This allows for lots of great auto completion for forms. --- src/vs/languages/html/common/htmlTags.ts | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/src/vs/languages/html/common/htmlTags.ts b/src/vs/languages/html/common/htmlTags.ts index dd5cd7b05c1..20800807ae8 100644 --- a/src/vs/languages/html/common/htmlTags.ts +++ b/src/vs/languages/html/common/htmlTags.ts @@ -283,13 +283,13 @@ export const HTML_TAGS: ITagSet = { ['form', 'for']), input: new HTMLTagSpecification( nls.localize('tags.input', 'The input element represents a typed data field, usually with a form control to allow the user to edit the data.'), - ['accept', 'alt', 'autocomplete:o', 'autofocus:v', 'checked:v', 'dirname', 'disabled:v', 'form', 'formaction', 'formenctype:et', 'formmethod:fm', 'formnovalidate:v', 'formtarget', 'height', 'inputmode:im', 'list', 'max', 'maxlength', 'min', 'minlength', 'multiple:v', 'name', 'pattern', 'placeholder', 'readonly:v', 'required:v', 'size', 'src', 'step', 'type:t', 'value', 'width']), + ['accept', 'alt', 'autocomplete:inputautocomplete', 'autofocus:v', 'checked:v', 'dirname', 'disabled:v', 'form', 'formaction', 'formenctype:et', 'formmethod:fm', 'formnovalidate:v', 'formtarget', 'height', 'inputmode:im', 'list', 'max', 'maxlength', 'min', 'minlength', 'multiple:v', 'name', 'pattern', 'placeholder', 'readonly:v', 'required:v', 'size', 'src', 'step', 'type:t', 'value', 'width']), button: new HTMLTagSpecification( nls.localize('tags.button', 'The button element represents a button labeled by its contents.'), ['autofocus:v', 'disabled:v', 'form', 'formaction', 'formenctype:et', 'formmethod:fm', 'formnovalidate:v', 'formtarget', 'name', 'type:bt', 'value']), select: new HTMLTagSpecification( nls.localize('tags.select', 'The select element represents a control for selecting amongst a set of options.'), - ['autocomplete:o', 'autofocus:v', 'disabled:v', 'form', 'multiple:v', 'name', 'required:v', 'size']), + ['autocomplete:inputautocomplete', 'autofocus:v', 'disabled:v', 'form', 'multiple:v', 'name', 'required:v', 'size']), datalist: new HTMLTagSpecification( nls.localize('tags.datalist', 'The datalist element represents a set of option elements that represent predefined options for other controls. In the rendering, the datalist element represents nothing and it, along with its children, should be hidden.')), optgroup: new HTMLTagSpecification( @@ -300,7 +300,7 @@ export const HTML_TAGS: ITagSet = { ['disabled:v', 'label', 'selected:v', 'value']), textarea: new HTMLTagSpecification( nls.localize('tags.textarea', 'The textarea element represents a multiline plain text edit control for the element\'s raw value. The contents of the control represent the control\'s default value.'), - ['autocomplete:o', 'autofocus:v', 'cols', 'dirname', 'disabled:v', 'form', 'inputmode:im', 'maxlength', 'minlength', 'name', 'placeholder', 'readonly:v', 'required:v', 'rows', 'wrap:w']), + ['autocomplete:inputautocomplete', 'autofocus:v', 'cols', 'dirname', 'disabled:v', 'form', 'inputmode:im', 'maxlength', 'minlength', 'name', 'placeholder', 'readonly:v', 'required:v', 'rows', 'wrap:w']), output: new HTMLTagSpecification( nls.localize('tags.output', 'The output element represents the result of a calculation performed by the application, or the result of a user action.'), ['for', 'form', 'name']), @@ -449,6 +449,7 @@ export function getHTML5TagProvider(): IHTMLTagProvider { xo: ['anonymous', 'use-credentials'], sb: ['allow-forms', 'allow-modals', 'allow-pointer-lock', 'allow-popups', 'allow-popups-to-escape-sandbox', 'allow-same-origin', 'allow-scripts', 'allow-top-navigation'], tristate: ['true', 'false', 'mixed', 'undefined'], + inputautocomplete: ['additional-name', 'address-level1', 'address-level2', 'address-level3', 'address-level4', 'address-line1', 'address-line2', 'address-line3', 'bday', 'bday-year', 'bday-day', 'bday-month', 'billing', 'cc-additional-name', 'cc-csc', 'cc-exp', 'cc-exp-month', 'cc-exp-year', 'cc-family-name', 'cc-given-name', 'cc-name', 'cc-number', 'cc-type', 'country', 'country-name', 'current-password', 'email', 'family-name', 'fax', 'given-name', 'home', 'honorific-prefix', 'honorific-suffix', 'impp', 'language', 'mobile', 'name', 'new-password', 'nickname', 'organization', 'organization-title', 'pager', 'photo', 'postal-code', 'sex', 'shipping', 'street-address', 't].sort()el-area-code', 'tel', 'tel-country-code', 'tel-extension', 'tel-local', 'tel-local-prefix', 'tel-local-suffix', 'tel-national', 'transaction-amount', 'transaction-currency', 'url', 'username', 'work'], autocomplete: ['inline', 'list', 'both', 'none'], current: ['page', 'step', 'location', 'date', 'time', 'true', 'false'], dropeffect: ['copy', 'move', 'link', 'execute', 'popup', 'none'], From 997eaca8286d059a0fd1750393bdea3414d85a15 Mon Sep 17 00:00:00 2001 From: Christian Heilmann Date: Thu, 2 Jun 2016 19:59:29 +0200 Subject: [PATCH 003/217] Slight typo in autocomplete values --- src/vs/languages/html/common/htmlTags.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/vs/languages/html/common/htmlTags.ts b/src/vs/languages/html/common/htmlTags.ts index 20800807ae8..33f49952ed4 100644 --- a/src/vs/languages/html/common/htmlTags.ts +++ b/src/vs/languages/html/common/htmlTags.ts @@ -449,7 +449,7 @@ export function getHTML5TagProvider(): IHTMLTagProvider { xo: ['anonymous', 'use-credentials'], sb: ['allow-forms', 'allow-modals', 'allow-pointer-lock', 'allow-popups', 'allow-popups-to-escape-sandbox', 'allow-same-origin', 'allow-scripts', 'allow-top-navigation'], tristate: ['true', 'false', 'mixed', 'undefined'], - inputautocomplete: ['additional-name', 'address-level1', 'address-level2', 'address-level3', 'address-level4', 'address-line1', 'address-line2', 'address-line3', 'bday', 'bday-year', 'bday-day', 'bday-month', 'billing', 'cc-additional-name', 'cc-csc', 'cc-exp', 'cc-exp-month', 'cc-exp-year', 'cc-family-name', 'cc-given-name', 'cc-name', 'cc-number', 'cc-type', 'country', 'country-name', 'current-password', 'email', 'family-name', 'fax', 'given-name', 'home', 'honorific-prefix', 'honorific-suffix', 'impp', 'language', 'mobile', 'name', 'new-password', 'nickname', 'organization', 'organization-title', 'pager', 'photo', 'postal-code', 'sex', 'shipping', 'street-address', 't].sort()el-area-code', 'tel', 'tel-country-code', 'tel-extension', 'tel-local', 'tel-local-prefix', 'tel-local-suffix', 'tel-national', 'transaction-amount', 'transaction-currency', 'url', 'username', 'work'], + inputautocomplete: ['additional-name', 'address-level1', 'address-level2', 'address-level3', 'address-level4', 'address-line1', 'address-line2', 'address-line3', 'bday', 'bday-year', 'bday-day', 'bday-month', 'billing', 'cc-additional-name', 'cc-csc', 'cc-exp', 'cc-exp-month', 'cc-exp-year', 'cc-family-name', 'cc-given-name', 'cc-name', 'cc-number', 'cc-type', 'country', 'country-name', 'current-password', 'email', 'family-name', 'fax', 'given-name', 'home', 'honorific-prefix', 'honorific-suffix', 'impp', 'language', 'mobile', 'name', 'new-password', 'nickname', 'organization', 'organization-title', 'pager', 'photo', 'postal-code', 'sex', 'shipping', 'street-address', 'tel-area-code', 'tel', 'tel-country-code', 'tel-extension', 'tel-local', 'tel-local-prefix', 'tel-local-suffix', 'tel-national', 'transaction-amount', 'transaction-currency', 'url', 'username', 'work'], autocomplete: ['inline', 'list', 'both', 'none'], current: ['page', 'step', 'location', 'date', 'time', 'true', 'false'], dropeffect: ['copy', 'move', 'link', 'execute', 'popup', 'none'], From 597ff9e532c263e0bc89d3efe8f8eca77001b000 Mon Sep 17 00:00:00 2001 From: "tamas.kiss" Date: Thu, 26 May 2016 06:17:53 +0200 Subject: [PATCH 004/217] Horizontal selection movement implemented This commit adds the horizontal alternatives of the move line up / down commands. This fixes #5251 --- src/vs/editor/browser/editor.all.ts | 1 + .../common/carretOperations.ts | 65 ++++++++++++++++ .../common/moveCarretCommand.ts | 74 +++++++++++++++++++ .../test/common/moveCarretCommand.test.ts | 70 ++++++++++++++++++ 4 files changed, 210 insertions(+) create mode 100644 src/vs/editor/contrib/carretOperations/common/carretOperations.ts create mode 100644 src/vs/editor/contrib/carretOperations/common/moveCarretCommand.ts create mode 100644 src/vs/editor/contrib/carretOperations/test/common/moveCarretCommand.test.ts diff --git a/src/vs/editor/browser/editor.all.ts b/src/vs/editor/browser/editor.all.ts index 9a3a4165faa..84d92706363 100644 --- a/src/vs/editor/browser/editor.all.ts +++ b/src/vs/editor/browser/editor.all.ts @@ -24,6 +24,7 @@ import 'vs/css!vs/editor/contrib/inPlaceReplace/browser/inPlaceReplace'; import 'vs/editor/contrib/inPlaceReplace/common/inPlaceReplace'; import 'vs/editor/contrib/iPadShowKeyboard/browser/iPadShowKeyboard'; import 'vs/editor/contrib/linesOperations/common/linesOperations'; +import 'vs/editor/contrib/carretOperations/common/carretOperations'; import 'vs/editor/contrib/links/browser/links'; import 'vs/editor/contrib/multicursor/common/multicursor'; import 'vs/editor/contrib/outlineMarker/browser/outlineMarker'; diff --git a/src/vs/editor/contrib/carretOperations/common/carretOperations.ts b/src/vs/editor/contrib/carretOperations/common/carretOperations.ts new file mode 100644 index 00000000000..aa21fcca2cd --- /dev/null +++ b/src/vs/editor/contrib/carretOperations/common/carretOperations.ts @@ -0,0 +1,65 @@ +/*--------------------------------------------------------------------------------------------- + * Copyright (c) Microsoft Corporation. All rights reserved. + * Licensed under the MIT License. See License.txt in the project root for license information. + *--------------------------------------------------------------------------------------------*/ +'use strict'; + +import * as nls from 'vs/nls'; +import {KeyCode, KeyMod} from 'vs/base/common/keyCodes'; +import {TPromise} from 'vs/base/common/winjs.base'; +import {EditorAction} from 'vs/editor/common/editorAction'; +import {ICommand, ICommonCodeEditor, IEditorActionDescriptorData} from 'vs/editor/common/editorCommon'; +import {CommonEditorRegistry, ContextKey, EditorActionDescriptor} from 'vs/editor/common/editorCommonExtensions'; +import {MoveCarretCommand} from './moveCarretCommand'; + +class MoveCarretAction extends EditorAction { + + private left:boolean; + + constructor(descriptor:IEditorActionDescriptorData, editor:ICommonCodeEditor, left:boolean) { + super(descriptor, editor); + this.left = left; + } + + public run():TPromise { + + var commands:ICommand[] = []; + var selections = this.editor.getSelections(); + + for (var i = 0; i < selections.length; i++) { + commands.push(new MoveCarretCommand(selections[i], this.left)); + } + + this.editor.executeCommands(this.id, commands); + + return TPromise.as(true); + } +} + +class MoveCarretLeftAction extends MoveCarretAction { + static ID = 'editor.action.moveCarretLeftAction'; + + constructor(descriptor:IEditorActionDescriptorData, editor:ICommonCodeEditor) { + super(descriptor, editor, true); + } +} + +class MoveCarretRightAction extends MoveCarretAction { + static ID = 'editor.action.moveCarretRightAction'; + + constructor(descriptor:IEditorActionDescriptorData, editor:ICommonCodeEditor) { + super(descriptor, editor, false); + } +} + +CommonEditorRegistry.registerEditorAction(new EditorActionDescriptor(MoveCarretLeftAction, MoveCarretLeftAction.ID, nls.localize('carret.moveLeft', "Move Carret Left"), { + context: ContextKey.EditorTextFocus, + primary: KeyMod.Alt | KeyCode.LeftArrow, + linux: { primary: KeyMod.Alt | KeyCode.LeftArrow } +}, 'Move Carret Left')); + +CommonEditorRegistry.registerEditorAction(new EditorActionDescriptor(MoveCarretRightAction, MoveCarretRightAction.ID, nls.localize('carret.moveRight', "Move Carret Right"), { + context: ContextKey.EditorTextFocus, + primary: KeyMod.Alt | KeyCode.RightArrow, + linux: { primary: KeyMod.Alt | KeyCode.LeftArrow } +}, 'Move Carret Right')); \ No newline at end of file diff --git a/src/vs/editor/contrib/carretOperations/common/moveCarretCommand.ts b/src/vs/editor/contrib/carretOperations/common/moveCarretCommand.ts new file mode 100644 index 00000000000..05e5c5739e0 --- /dev/null +++ b/src/vs/editor/contrib/carretOperations/common/moveCarretCommand.ts @@ -0,0 +1,74 @@ +/*--------------------------------------------------------------------------------------------- + * Copyright (c) Microsoft Corporation. All rights reserved. + * Licensed under the MIT License. See License.txt in the project root for license information. + *--------------------------------------------------------------------------------------------*/ +'use strict'; + +import {Range} from 'vs/editor/common/core/range'; +import {Selection} from 'vs/editor/common/core/selection'; +import {ICommand, ICursorStateComputerData, IEditOperationBuilder, ITokenizedModel} from 'vs/editor/common/editorCommon'; + +export class MoveCarretCommand implements ICommand { + + private _selection: Selection; + private _isMovingLeft: boolean; + + private _cutStartIndex: number; + private _cutEndIndex: number; + private _moved: boolean; + + private _selectionId: string; + + constructor(selection: Selection, isMovingLeft: boolean) { + this._selection = selection; + this._isMovingLeft = isMovingLeft; + } + + public getEditOperations(model: ITokenizedModel, builder: IEditOperationBuilder): void { + var s = this._selection; + this._selectionId = builder.trackSelection(s); + if (s.startLineNumber !== s.endLineNumber) { + return; + } + if (this._isMovingLeft && s.startColumn === 0) { + return; + } else if (!this._isMovingLeft && s.endColumn === model.getLineMaxColumn(s.startLineNumber)) { + return; + } + + var lineNumber = s.selectionStartLineNumber; + var lineContent = model.getLineContent(lineNumber); + + var left; + var middle; + var right; + + if (this._isMovingLeft) { + left = lineContent.substring(0, s.startColumn - 2); + middle = lineContent.substring(s.startColumn - 1, s.endColumn - 1); + right = lineContent.substring(s.startColumn - 2, s.startColumn - 1) + lineContent.substring(s.endColumn - 1); + } else { + left = lineContent.substring(0, s.startColumn - 1) + lineContent.substring(s.endColumn - 1, s.endColumn); + middle = lineContent.substring(s.startColumn - 1, s.endColumn - 1); + right = lineContent.substring(s.endColumn); + } + + var newLineContent = left + middle + right; + + builder.addEditOperation(new Range(lineNumber, 1, lineNumber, model.getLineMaxColumn(lineNumber)), null); + builder.addEditOperation(new Range(lineNumber, 1, lineNumber, 1), newLineContent); + + this._cutStartIndex = s.startColumn + (this._isMovingLeft ? -1 : 1); + this._cutEndIndex = this._cutStartIndex + s.endColumn - s.startColumn; + this._moved = true; + } + + public computeCursorState(model: ITokenizedModel, helper: ICursorStateComputerData): Selection { + var result = helper.getTrackedSelection(this._selectionId); + if (this._moved) { + result = result.setStartPosition(result.startLineNumber, this._cutStartIndex); + result = result.setEndPosition(result.startLineNumber, this._cutEndIndex); + } + return result; + } +} diff --git a/src/vs/editor/contrib/carretOperations/test/common/moveCarretCommand.test.ts b/src/vs/editor/contrib/carretOperations/test/common/moveCarretCommand.test.ts new file mode 100644 index 00000000000..999f3dc305e --- /dev/null +++ b/src/vs/editor/contrib/carretOperations/test/common/moveCarretCommand.test.ts @@ -0,0 +1,70 @@ +/*--------------------------------------------------------------------------------------------- + * Copyright (c) Microsoft Corporation. All rights reserved. + * Licensed under the MIT License. See License.txt in the project root for license information. + *--------------------------------------------------------------------------------------------*/ +'use strict'; + +import {Selection} from 'vs/editor/common/core/selection'; +import {MoveCarretCommand} from 'vs/editor/contrib/carretOperations/common/moveCarretCommand'; +import {testCommand} from 'vs/editor/test/common/commands/commandTestUtils'; + + +function testMoveCarretLeftCommand(lines: string[], selection: Selection, expectedLines: string[], expectedSelection: Selection): void { + testCommand(lines, null, selection, (sel) => new MoveCarretCommand(sel, true), expectedLines, expectedSelection); +} + +function testMoveCarretRightCommand(lines: string[], selection: Selection, expectedLines: string[], expectedSelection: Selection): void { + testCommand(lines, null, selection, (sel) => new MoveCarretCommand(sel, false), expectedLines, expectedSelection); +} + +suite('Editor Contrib - Move Carret Command', () => { + + test('move selection to left', function () { + testMoveCarretLeftCommand( + [ + '012345' + ], + new Selection(1, 3, 1, 5), + [ + '023145' + ], + new Selection(1, 2, 1, 4) + ); + }); + test('move selection to right', function () { + testMoveCarretRightCommand( + [ + '012345' + ], + new Selection(1, 3, 1, 5), + [ + '014235' + ], + new Selection(1, 4, 1, 6) + ); + }); + test('move selection to left - from first column - no change', function () { + testMoveCarretLeftCommand( + [ + '012345' + ], + new Selection(1, 1, 1, 1), + [ + '012345' + ], + new Selection(1, 1, 1, 1) + ); + }); + test('move selection to right - from last column - no change', function () { + testMoveCarretRightCommand( + [ + '012345' + ], + new Selection(1, 5, 1, 7), + [ + '012345' + ], + new Selection(1, 5, 1, 7) + ); + }); +}); \ No newline at end of file From 9217e494f0afdde41da2dfcfad595fd842a05af1 Mon Sep 17 00:00:00 2001 From: Jan Niklas Hasse Date: Tue, 7 Jun 2016 15:48:24 +0200 Subject: [PATCH 005/217] Highlight .mk files as a Makefile --- extensions/make/syntaxes/Makefile.plist | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/extensions/make/syntaxes/Makefile.plist b/extensions/make/syntaxes/Makefile.plist index 2e5c5110243..5b6b3591cae 100644 --- a/extensions/make/syntaxes/Makefile.plist +++ b/extensions/make/syntaxes/Makefile.plist @@ -8,6 +8,7 @@ makefile GNUmakefile OCamlMakefile + mk name Makefile @@ -718,4 +719,4 @@ uuid FF1825E8-6B1C-11D9-B883-000D93589AF6 - \ No newline at end of file + From a7270a3fc6d2a2ac91855c49d794784a2f8ad49f Mon Sep 17 00:00:00 2001 From: Eshwar Andhavarapu Date: Thu, 9 Jun 2016 20:31:32 +0200 Subject: [PATCH 006/217] Added .dsql and .psql filetypes .psql - It appears this is used by PostgreSQL .dsql - this is used by Microsoft's very own SQL Studio Tools when working with APS/PDW --- extensions/sql/syntaxes/SQL.plist | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/extensions/sql/syntaxes/SQL.plist b/extensions/sql/syntaxes/SQL.plist index ea46a924a92..04dedd3fd84 100644 --- a/extensions/sql/syntaxes/SQL.plist +++ b/extensions/sql/syntaxes/SQL.plist @@ -7,6 +7,8 @@ sql ddl dml + dsql + psql keyEquivalent ^~S @@ -762,4 +764,4 @@ uuid C49120AC-6ECC-11D9-ACC8-000D93589AF6 - \ No newline at end of file + From 2dfecbb5413a45530bbcc80d5dd2147364cad19f Mon Sep 17 00:00:00 2001 From: kieferrm Date: Fri, 20 May 2016 17:26:04 -0700 Subject: [PATCH 007/217] theme support in htmlPreview --- src/vs/platform/theme/common/themes.ts | 4 ++ .../workbench/parts/html/browser/webview.html | 46 +++++++++++++--- .../workbench/parts/html/browser/webview.ts | 54 ++++++++++++++++--- 3 files changed, 89 insertions(+), 15 deletions(-) diff --git a/src/vs/platform/theme/common/themes.ts b/src/vs/platform/theme/common/themes.ts index 0fedb5ecfd0..24bfada0768 100644 --- a/src/vs/platform/theme/common/themes.ts +++ b/src/vs/platform/theme/common/themes.ts @@ -8,6 +8,10 @@ export function isLightTheme(themeId: string) { return /vs($| )/.test(themeId); } +export function isDarkTheme(themeId: string) { + return /vs-dark($| )/.test(themeId); +} + export function getSyntaxThemeId(themeId: string) { return themeId.split(' ')[1]; } diff --git a/src/vs/workbench/parts/html/browser/webview.html b/src/vs/workbench/parts/html/browser/webview.html index 4bf4659054a..278cbab58a1 100644 --- a/src/vs/workbench/parts/html/browser/webview.html +++ b/src/vs/workbench/parts/html/browser/webview.html @@ -9,26 +9,46 @@ ", "t": "", "r": { "dark_plus": ".vs-dark .token rgb(212, 212, 212)", @@ -396,7 +506,7 @@ } }, { - "c": " ", + "c": " This is a div _with_ underscores", "t": "", "r": { "dark_plus": ".vs-dark .token rgb(212, 212, 212)", @@ -407,18 +517,7 @@ } }, { - "c": "", - "t": "entity.md.name.tag.tag-script", - "r": { - "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.entity.name.tag rgb(86, 156, 214)", - "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.entity.name.tag rgb(128, 0, 0)", - "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.entity.name.tag rgb(86, 156, 214)", - "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.entity.name.tag rgb(128, 0, 0)", - "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.entity.name.tag rgb(86, 156, 214)" - } - }, - { - "c": " This is a div ", + "c": " and a & bold element.", "t": "", "r": { "dark_plus": ".vs-dark .token rgb(212, 212, 212)", @@ -429,18 +528,7 @@ } }, { - "c": "_with_", - "t": "emphasis.md", - "r": { - "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.emphasis rgb(212, 212, 212)", - "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.emphasis rgb(0, 0, 0)", - "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.emphasis rgb(212, 212, 212)", - "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.emphasis rgb(0, 0, 0)", - "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.emphasis rgb(255, 255, 255)" - } - }, - { - "c": " underscores", + "c": " ", "t": "", "r": { "dark_plus": ".vs-dark .token rgb(212, 212, 212)", @@ -462,41 +561,8 @@ } }, { - "c": "", - "t": "entity.md.name.tag.tag-b", + "t": "any.block.definition.end.html.markdown.meta.paragraph.punctuation.tag", "r": { - "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.entity.name.tag rgb(86, 156, 214)", - "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.entity.name.tag rgb(128, 0, 0)", - "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.entity.name.tag rgb(86, 156, 214)", - "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.entity.name.tag rgb(128, 0, 0)", - "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.entity.name.tag rgb(86, 156, 214)" + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.meta.tag rgb(128, 128, 128)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.meta.tag rgb(128, 0, 0)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.meta.tag rgb(128, 128, 128)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.meta.tag rgb(128, 0, 0)", + "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.meta.tag rgb(128, 128, 128)" } }, { - "c": "bold", - "t": "", + "c": "*", + "t": "definition.list.markdown.markup.punctuation.unnumbered", "r": { - "dark_plus": ".vs-dark .token rgb(212, 212, 212)", - "light_plus": ".vs .token rgb(0, 0, 0)", - "dark_vs": ".vs-dark .token rgb(212, 212, 212)", - "light_vs": ".vs .token rgb(0, 0, 0)", - "hc_black": ".hc-black .token rgb(255, 255, 255)" - } - }, - { - "c": "", - "t": "entity.md.name.tag.tag-b", - "r": { - "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.entity.name.tag rgb(86, 156, 214)", - "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.entity.name.tag rgb(128, 0, 0)", - "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.entity.name.tag rgb(86, 156, 214)", - "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.entity.name.tag rgb(128, 0, 0)", - "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.entity.name.tag rgb(86, 156, 214)" - } - }, - { - "c": " element.", - "t": "", - "r": { - "dark_plus": ".vs-dark .token rgb(212, 212, 212)", - "light_plus": ".vs .token rgb(0, 0, 0)", - "dark_vs": ".vs-dark .token rgb(212, 212, 212)", - "light_vs": ".vs .token rgb(0, 0, 0)", - "hc_black": ".hc-black .token rgb(255, 255, 255)" - } - }, - { - "c": " ", - "t": "", - "r": { - "dark_plus": ".vs-dark .token rgb(212, 212, 212)", - "light_plus": ".vs .token rgb(0, 0, 0)", - "dark_vs": ".vs-dark .token rgb(212, 212, 212)", - "light_vs": ".vs .token rgb(0, 0, 0)", - "hc_black": ".hc-black .token rgb(255, 255, 255)" - } - }, - { - "c": "", - "t": "entity.md.name.tag.tag-style", - "r": { - "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.entity.name.tag rgb(86, 156, 214)", - "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.entity.name.tag rgb(128, 0, 0)", - "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.entity.name.tag rgb(86, 156, 214)", - "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.entity.name.tag rgb(128, 0, 0)", - "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.entity.name.tag rgb(86, 156, 214)" - } - }, - { - "c": "", - "t": "entity.md.name.tag.tag-div", - "r": { - "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.entity.name.tag rgb(86, 156, 214)", - "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.entity.name.tag rgb(128, 0, 0)", - "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.entity.name.tag rgb(86, 156, 214)", - "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.entity.name.tag rgb(128, 0, 0)", - "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.entity.name.tag rgb(86, 156, 214)" - } - }, - { - "c": "* ", - "t": "keyword.md", - "r": { - "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.keyword rgb(86, 156, 214)", - "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.keyword rgb(0, 0, 255)", - "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.keyword rgb(86, 156, 214)", - "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.keyword rgb(0, 0, 255)", - "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.keyword rgb(86, 156, 214)" - } - }, { "c": "Bullet lists are easy too", - "t": "", + "t": "list.markdown.markup.meta.paragraph.unnumbered", "r": { - "dark_plus": ".vs-dark .token rgb(212, 212, 212)", - "light_plus": ".vs .token rgb(0, 0, 0)", - "dark_vs": ".vs-dark .token rgb(212, 212, 212)", - "light_vs": ".vs .token rgb(0, 0, 0)", + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.list rgb(103, 150, 230)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.list rgb(4, 81, 165)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.list rgb(103, 150, 230)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.list rgb(0, 0, 0)", "hc_black": ".hc-black .token rgb(255, 255, 255)" } }, { - "c": "- ", - "t": "keyword.md", + "c": "-", + "t": "definition.list.markdown.markup.punctuation.unnumbered", "r": { - "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.keyword rgb(86, 156, 214)", - "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.keyword rgb(0, 0, 255)", - "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.keyword rgb(86, 156, 214)", - "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.keyword rgb(0, 0, 255)", - "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.keyword rgb(86, 156, 214)" - } - }, - { - "c": "Another one", - "t": "", - "r": { - "dark_plus": ".vs-dark .token rgb(212, 212, 212)", - "light_plus": ".vs .token rgb(0, 0, 0)", - "dark_vs": ".vs-dark .token rgb(212, 212, 212)", - "light_vs": ".vs .token rgb(0, 0, 0)", + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.punctuation.list rgb(103, 150, 230)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.punctuation.list rgb(4, 81, 165)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.punctuation.list rgb(103, 150, 230)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.punctuation.list rgb(4, 81, 165)", "hc_black": ".hc-black .token rgb(255, 255, 255)" } }, { - "c": "+ ", - "t": "keyword.md", + "c": " ", + "t": "list.markdown.markup.unnumbered", "r": { - "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.keyword rgb(86, 156, 214)", - "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.keyword rgb(0, 0, 255)", - "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.keyword rgb(86, 156, 214)", - "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.keyword rgb(0, 0, 255)", - "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.keyword rgb(86, 156, 214)" + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.list rgb(103, 150, 230)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.list rgb(4, 81, 165)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.list rgb(103, 150, 230)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.list rgb(0, 0, 0)", + "hc_black": ".hc-black .token rgb(255, 255, 255)" } }, { "c": "Another one", - "t": "", + "t": "list.markdown.markup.meta.paragraph.unnumbered", "r": { - "dark_plus": ".vs-dark .token rgb(212, 212, 212)", - "light_plus": ".vs .token rgb(0, 0, 0)", - "dark_vs": ".vs-dark .token rgb(212, 212, 212)", - "light_vs": ".vs .token rgb(0, 0, 0)", + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.list rgb(103, 150, 230)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.list rgb(4, 81, 165)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.list rgb(103, 150, 230)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.list rgb(0, 0, 0)", + "hc_black": ".hc-black .token rgb(255, 255, 255)" + } + }, + { + "c": "+", + "t": "definition.list.markdown.markup.punctuation.unnumbered", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.punctuation.list rgb(103, 150, 230)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.punctuation.list rgb(4, 81, 165)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.punctuation.list rgb(103, 150, 230)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.punctuation.list rgb(4, 81, 165)", + "hc_black": ".hc-black .token rgb(255, 255, 255)" + } + }, + { + "c": " ", + "t": "list.markdown.markup.unnumbered", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.list rgb(103, 150, 230)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.list rgb(4, 81, 165)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.list rgb(103, 150, 230)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.list rgb(0, 0, 0)", + "hc_black": ".hc-black .token rgb(255, 255, 255)" + } + }, + { + "c": "Another one", + "t": "list.markdown.markup.meta.paragraph.unnumbered", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.list rgb(103, 150, 230)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.list rgb(4, 81, 165)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.list rgb(103, 150, 230)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.list rgb(0, 0, 0)", "hc_black": ".hc-black .token rgb(255, 255, 255)" } }, { "c": "This is a paragraph, which is text surrounded by", - "t": "", + "t": "markdown.meta.paragraph", "r": { "dark_plus": ".vs-dark .token rgb(212, 212, 212)", "light_plus": ".vs .token rgb(0, 0, 0)", @@ -837,7 +705,7 @@ }, { "c": "whitespace. Paragraphs can be on one", - "t": "", + "t": "markdown.meta.paragraph", "r": { "dark_plus": ".vs-dark .token rgb(212, 212, 212)", "light_plus": ".vs .token rgb(0, 0, 0)", @@ -848,7 +716,7 @@ }, { "c": "line (or many), and can drone on for hours.", - "t": "", + "t": "markdown.meta.paragraph", "r": { "dark_plus": ".vs-dark .token rgb(212, 212, 212)", "light_plus": ".vs .token rgb(0, 0, 0)", @@ -859,7 +727,7 @@ }, { "c": "Now some inline markup like ", - "t": "", + "t": "markdown.meta.paragraph", "r": { "dark_plus": ".vs-dark .token rgb(212, 212, 212)", "light_plus": ".vs .token rgb(0, 0, 0)", @@ -869,19 +737,41 @@ } }, { - "c": "_italics_", - "t": "emphasis.md", + "c": "_", + "t": "definition.italic.markdown.markup.meta.paragraph.punctuation", "r": { - "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.emphasis rgb(212, 212, 212)", - "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.emphasis rgb(0, 0, 0)", - "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.emphasis rgb(212, 212, 212)", - "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.emphasis rgb(0, 0, 0)", - "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.emphasis rgb(255, 255, 255)" + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.italic rgb(86, 156, 214)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.italic rgb(0, 0, 128)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.italic rgb(86, 156, 214)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.italic rgb(0, 0, 128)", + "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.markup.italic rgb(255, 255, 255)" + } + }, + { + "c": "italics", + "t": "italic.markdown.markup.meta.paragraph", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.italic rgb(86, 156, 214)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.italic rgb(0, 0, 128)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.italic rgb(86, 156, 214)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.italic rgb(0, 0, 128)", + "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.markup.italic rgb(255, 255, 255)" + } + }, + { + "c": "_", + "t": "definition.italic.markdown.markup.meta.paragraph.punctuation", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.italic rgb(86, 156, 214)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.italic rgb(0, 0, 128)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.italic rgb(86, 156, 214)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.italic rgb(0, 0, 128)", + "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.markup.italic rgb(255, 255, 255)" } }, { "c": ", ", - "t": "", + "t": "markdown.meta.paragraph", "r": { "dark_plus": ".vs-dark .token rgb(212, 212, 212)", "light_plus": ".vs .token rgb(0, 0, 0)", @@ -891,19 +781,41 @@ } }, { - "c": "**bold**", - "t": "md.strong", + "c": "**", + "t": "bold.definition.markdown.markup.meta.paragraph.punctuation", "r": { - "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.strong rgb(212, 212, 212)", - "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.strong rgb(0, 0, 0)", - "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.strong rgb(212, 212, 212)", - "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.strong rgb(0, 0, 0)", - "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.strong rgb(255, 255, 255)" + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.bold rgb(86, 156, 214)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.bold rgb(0, 0, 128)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.bold rgb(86, 156, 214)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.bold rgb(0, 0, 128)", + "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.markup.bold rgb(255, 255, 255)" + } + }, + { + "c": "bold", + "t": "bold.markdown.markup.meta.paragraph", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.bold rgb(86, 156, 214)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.bold rgb(0, 0, 128)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.bold rgb(86, 156, 214)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.bold rgb(0, 0, 128)", + "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.markup.bold rgb(255, 255, 255)" + } + }, + { + "c": "**", + "t": "bold.definition.markdown.markup.meta.paragraph.punctuation", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.bold rgb(86, 156, 214)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.bold rgb(0, 0, 128)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.bold rgb(86, 156, 214)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.bold rgb(0, 0, 128)", + "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.markup.bold rgb(255, 255, 255)" } }, { "c": ",", - "t": "", + "t": "markdown.meta.paragraph", "r": { "dark_plus": ".vs-dark .token rgb(212, 212, 212)", "light_plus": ".vs .token rgb(0, 0, 0)", @@ -914,7 +826,7 @@ }, { "c": "and ", - "t": "", + "t": "markdown.meta.paragraph", "r": { "dark_plus": ".vs-dark .token rgb(212, 212, 212)", "light_plus": ".vs .token rgb(0, 0, 0)", @@ -924,13 +836,35 @@ } }, { - "c": "`code()`", - "t": "md.variable", + "c": "`", + "t": "definition.inline.markdown.markup.meta.paragraph.punctuation.raw", "r": { - "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.variable rgb(156, 220, 254)", - "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.variable rgb(0, 16, 128)", - "dark_vs": ".vs-dark .token rgb(212, 212, 212)", - "light_vs": ".vs .token rgb(0, 0, 0)", + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.inline.raw rgb(206, 145, 120)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.inline.raw rgb(128, 0, 0)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.inline.raw rgb(206, 145, 120)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.inline.raw rgb(128, 0, 0)", + "hc_black": ".hc-black .token rgb(255, 255, 255)" + } + }, + { + "c": "code()", + "t": "inline.markdown.markup.meta.paragraph.raw", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.inline.raw rgb(206, 145, 120)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.inline.raw rgb(128, 0, 0)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.inline.raw rgb(206, 145, 120)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.inline.raw rgb(128, 0, 0)", + "hc_black": ".hc-black .token rgb(255, 255, 255)" + } + }, + { + "c": "`", + "t": "definition.inline.markdown.markup.meta.paragraph.punctuation.raw", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.inline.raw rgb(206, 145, 120)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.inline.raw rgb(128, 0, 0)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.inline.raw rgb(206, 145, 120)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.inline.raw rgb(128, 0, 0)", "hc_black": ".hc-black .token rgb(255, 255, 255)" } }, @@ -946,8 +880,52 @@ } }, { - "c": "in_words_are ignored.", - "t": "", + "c": "in", + "t": "markdown.meta.paragraph", + "r": { + "dark_plus": ".vs-dark .token rgb(212, 212, 212)", + "light_plus": ".vs .token rgb(0, 0, 0)", + "dark_vs": ".vs-dark .token rgb(212, 212, 212)", + "light_vs": ".vs .token rgb(0, 0, 0)", + "hc_black": ".hc-black .token rgb(255, 255, 255)" + } + }, + { + "c": "_", + "t": "definition.italic.markdown.markup.meta.paragraph.punctuation", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.italic rgb(86, 156, 214)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.italic rgb(0, 0, 128)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.italic rgb(86, 156, 214)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.italic rgb(0, 0, 128)", + "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.markup.italic rgb(255, 255, 255)" + } + }, + { + "c": "words", + "t": "italic.markdown.markup.meta.paragraph", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.italic rgb(86, 156, 214)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.italic rgb(0, 0, 128)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.italic rgb(86, 156, 214)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.italic rgb(0, 0, 128)", + "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.markup.italic rgb(255, 255, 255)" + } + }, + { + "c": "_", + "t": "definition.italic.markdown.markup.meta.paragraph.punctuation", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.italic rgb(86, 156, 214)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.italic rgb(0, 0, 128)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.italic rgb(86, 156, 214)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.italic rgb(0, 0, 128)", + "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.markup.italic rgb(255, 255, 255)" + } + }, + { + "c": "are ignored.", + "t": "markdown.meta.paragraph", "r": { "dark_plus": ".vs-dark .token rgb(212, 212, 212)", "light_plus": ".vs .token rgb(0, 0, 0)", @@ -958,7 +936,7 @@ }, { "c": "````application/json", - "t": "", + "t": "markdown.meta.paragraph", "r": { "dark_plus": ".vs-dark .token rgb(212, 212, 212)", "light_plus": ".vs .token rgb(0, 0, 0)", @@ -968,8 +946,8 @@ } }, { - "c": " ", - "t": "", + "c": " { value: [\"or with a mime type\"] }", + "t": "markdown.meta.paragraph", "r": { "dark_plus": ".vs-dark .token rgb(212, 212, 212)", "light_plus": ".vs .token rgb(0, 0, 0)", @@ -978,20 +956,9 @@ "hc_black": ".hc-black .token rgb(255, 255, 255)" } }, - { - "c": "{ value: [\"or with a mime type\"] }", - "t": "md.string.target", - "r": { - "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.string rgb(206, 145, 120)", - "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.string rgb(163, 21, 21)", - "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.string rgb(206, 145, 120)", - "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.string rgb(163, 21, 21)", - "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.string rgb(206, 145, 120)" - } - }, { "c": "````", - "t": "", + "t": "markdown.meta.paragraph", "r": { "dark_plus": ".vs-dark .token rgb(212, 212, 212)", "light_plus": ".vs .token rgb(0, 0, 0)", @@ -1002,117 +969,172 @@ }, { "c": ">", - "t": "comment.md", + "t": "definition.markdown.markup.punctuation.quote", "r": { - "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.comment rgb(96, 139, 78)", - "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.comment rgb(0, 128, 0)", - "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.comment rgb(96, 139, 78)", - "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.comment rgb(0, 128, 0)", - "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.comment rgb(124, 166, 104)" + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.punctuation.quote rgb(103, 150, 230)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.punctuation.quote rgb(4, 81, 165)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.punctuation.quote rgb(103, 150, 230)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.punctuation.quote rgb(4, 81, 165)", + "hc_black": ".hc-black .token rgb(255, 255, 255)" } }, { - "c": " Blockquotes are like quoted text in email replies", - "t": "", + "c": " ", + "t": "markdown.markup.quote", "r": { - "dark_plus": ".vs-dark .token rgb(212, 212, 212)", - "light_plus": ".vs .token rgb(0, 0, 0)", - "dark_vs": ".vs-dark .token rgb(212, 212, 212)", - "light_vs": ".vs .token rgb(0, 0, 0)", + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.quote rgb(103, 150, 230)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.quote rgb(4, 81, 165)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.quote rgb(103, 150, 230)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.quote rgb(0, 0, 0)", + "hc_black": ".hc-black .token rgb(255, 255, 255)" + } + }, + { + "c": "Blockquotes are like quoted text in email replies", + "t": "markdown.markup.meta.paragraph.quote", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.quote rgb(103, 150, 230)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.quote rgb(4, 81, 165)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.quote rgb(103, 150, 230)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.quote rgb(0, 0, 0)", "hc_black": ".hc-black .token rgb(255, 255, 255)" } }, { "c": ">>", - "t": "comment.md", + "t": "definition.markdown.markup.punctuation.quote", "r": { - "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.comment rgb(96, 139, 78)", - "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.comment rgb(0, 128, 0)", - "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.comment rgb(96, 139, 78)", - "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.comment rgb(0, 128, 0)", - "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.comment rgb(124, 166, 104)" - } - }, - { - "c": " And, they can be nested", - "t": "", - "r": { - "dark_plus": ".vs-dark .token rgb(212, 212, 212)", - "light_plus": ".vs .token rgb(0, 0, 0)", - "dark_vs": ".vs-dark .token rgb(212, 212, 212)", - "light_vs": ".vs .token rgb(0, 0, 0)", + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.punctuation.quote rgb(103, 150, 230)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.punctuation.quote rgb(4, 81, 165)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.punctuation.quote rgb(103, 150, 230)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.punctuation.quote rgb(4, 81, 165)", "hc_black": ".hc-black .token rgb(255, 255, 255)" } }, { - "c": "1. ", - "t": "keyword.md", + "c": " ", + "t": "markdown.markup.quote", "r": { - "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.keyword rgb(86, 156, 214)", - "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.keyword rgb(0, 0, 255)", - "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.keyword rgb(86, 156, 214)", - "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.keyword rgb(0, 0, 255)", - "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.keyword rgb(86, 156, 214)" + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.quote rgb(103, 150, 230)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.quote rgb(4, 81, 165)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.quote rgb(103, 150, 230)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.quote rgb(0, 0, 0)", + "hc_black": ".hc-black .token rgb(255, 255, 255)" + } + }, + { + "c": "And, they can be nested", + "t": "markdown.markup.meta.paragraph.quote", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.quote rgb(103, 150, 230)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.quote rgb(4, 81, 165)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.quote rgb(103, 150, 230)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.quote rgb(0, 0, 0)", + "hc_black": ".hc-black .token rgb(255, 255, 255)" + } + }, + { + "c": "1.", + "t": "definition.list.markdown.markup.numbered.punctuation", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.punctuation.list rgb(103, 150, 230)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.punctuation.list rgb(4, 81, 165)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.punctuation.list rgb(103, 150, 230)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.punctuation.list rgb(4, 81, 165)", + "hc_black": ".hc-black .token rgb(255, 255, 255)" + } + }, + { + "c": " ", + "t": "list.markdown.markup.numbered", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.list rgb(103, 150, 230)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.list rgb(4, 81, 165)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.list rgb(103, 150, 230)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.list rgb(0, 0, 0)", + "hc_black": ".hc-black .token rgb(255, 255, 255)" } }, { "c": "A numbered list", - "t": "", + "t": "list.markdown.markup.meta.numbered.paragraph", "r": { - "dark_plus": ".vs-dark .token rgb(212, 212, 212)", - "light_plus": ".vs .token rgb(0, 0, 0)", - "dark_vs": ".vs-dark .token rgb(212, 212, 212)", - "light_vs": ".vs .token rgb(0, 0, 0)", + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.list rgb(103, 150, 230)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.list rgb(4, 81, 165)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.list rgb(103, 150, 230)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.list rgb(0, 0, 0)", "hc_black": ".hc-black .token rgb(255, 255, 255)" } }, { - "c": "2. ", - "t": "keyword.md", + "c": "2.", + "t": "definition.list.markdown.markup.numbered.punctuation", "r": { - "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.keyword rgb(86, 156, 214)", - "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.keyword rgb(0, 0, 255)", - "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.keyword rgb(86, 156, 214)", - "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.keyword rgb(0, 0, 255)", - "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.keyword rgb(86, 156, 214)" + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.punctuation.list rgb(103, 150, 230)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.punctuation.list rgb(4, 81, 165)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.punctuation.list rgb(103, 150, 230)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.punctuation.list rgb(4, 81, 165)", + "hc_black": ".hc-black .token rgb(255, 255, 255)" + } + }, + { + "c": " ", + "t": "list.markdown.markup.numbered", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.list rgb(103, 150, 230)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.list rgb(4, 81, 165)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.list rgb(103, 150, 230)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.list rgb(0, 0, 0)", + "hc_black": ".hc-black .token rgb(255, 255, 255)" } }, { "c": "Which is numbered", - "t": "", + "t": "list.markdown.markup.meta.numbered.paragraph", "r": { - "dark_plus": ".vs-dark .token rgb(212, 212, 212)", - "light_plus": ".vs .token rgb(0, 0, 0)", - "dark_vs": ".vs-dark .token rgb(212, 212, 212)", - "light_vs": ".vs .token rgb(0, 0, 0)", + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.list rgb(103, 150, 230)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.list rgb(4, 81, 165)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.list rgb(103, 150, 230)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.list rgb(0, 0, 0)", "hc_black": ".hc-black .token rgb(255, 255, 255)" } }, { - "c": "3. ", - "t": "keyword.md", + "c": "3.", + "t": "definition.list.markdown.markup.numbered.punctuation", "r": { - "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.keyword rgb(86, 156, 214)", - "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.keyword rgb(0, 0, 255)", - "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.keyword rgb(86, 156, 214)", - "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.keyword rgb(0, 0, 255)", - "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.keyword rgb(86, 156, 214)" + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.punctuation.list rgb(103, 150, 230)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.punctuation.list rgb(4, 81, 165)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.punctuation.list rgb(103, 150, 230)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.punctuation.list rgb(4, 81, 165)", + "hc_black": ".hc-black .token rgb(255, 255, 255)" + } + }, + { + "c": " ", + "t": "list.markdown.markup.numbered", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.list rgb(103, 150, 230)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.list rgb(4, 81, 165)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.list rgb(103, 150, 230)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.list rgb(0, 0, 0)", + "hc_black": ".hc-black .token rgb(255, 255, 255)" } }, { "c": "With periods and a space", - "t": "", + "t": "list.markdown.markup.meta.numbered.paragraph", "r": { - "dark_plus": ".vs-dark .token rgb(212, 212, 212)", - "light_plus": ".vs .token rgb(0, 0, 0)", - "dark_vs": ".vs-dark .token rgb(212, 212, 212)", - "light_vs": ".vs .token rgb(0, 0, 0)", + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.list rgb(103, 150, 230)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.list rgb(4, 81, 165)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.list rgb(103, 150, 230)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.list rgb(0, 0, 0)", "hc_black": ".hc-black .token rgb(255, 255, 255)" } }, { "c": "And now some code:", - "t": "", + "t": "markdown.meta.paragraph", "r": { "dark_plus": ".vs-dark .token rgb(212, 212, 212)", "light_plus": ".vs .token rgb(0, 0, 0)", @@ -1123,29 +1145,29 @@ }, { "c": " // Code is just text indented a bit", - "t": "md.string", + "t": "block.markdown.markup.raw", "r": { - "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.string rgb(206, 145, 120)", - "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.string rgb(163, 21, 21)", - "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.string rgb(206, 145, 120)", - "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.string rgb(163, 21, 21)", - "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.string rgb(206, 145, 120)" + "dark_plus": ".vs-dark .token rgb(212, 212, 212)", + "light_plus": ".vs .token rgb(0, 0, 0)", + "dark_vs": ".vs-dark .token rgb(212, 212, 212)", + "light_vs": ".vs .token rgb(0, 0, 0)", + "hc_black": ".hc-black .token rgb(255, 255, 255)" } }, { "c": " which(is_easy) to_remember();", - "t": "md.string", + "t": "block.markdown.markup.raw", "r": { - "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.string rgb(206, 145, 120)", - "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.string rgb(163, 21, 21)", - "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.string rgb(206, 145, 120)", - "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.string rgb(163, 21, 21)", - "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.string rgb(206, 145, 120)" + "dark_plus": ".vs-dark .token rgb(212, 212, 212)", + "light_plus": ".vs .token rgb(0, 0, 0)", + "dark_vs": ".vs-dark .token rgb(212, 212, 212)", + "light_vs": ".vs .token rgb(0, 0, 0)", + "hc_black": ".hc-black .token rgb(255, 255, 255)" } }, { "c": "And a block", - "t": "", + "t": "markdown.meta.paragraph", "r": { "dark_plus": ".vs-dark .token rgb(212, 212, 212)", "light_plus": ".vs .token rgb(0, 0, 0)", @@ -1156,32 +1178,98 @@ }, { "c": "~~~", - "t": "md.string", + "t": "markdown.meta.paragraph", "r": { - "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.string rgb(206, 145, 120)", - "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.string rgb(163, 21, 21)", - "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.string rgb(206, 145, 120)", - "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.string rgb(163, 21, 21)", - "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.string rgb(206, 145, 120)" - } - }, - { - "c": "// Markdown extra adds un-indented code blocks too", - "t": "md.source.variable", - "r": { - "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.variable rgb(156, 220, 254)", - "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.variable rgb(0, 16, 128)", + "dark_plus": ".vs-dark .token rgb(212, 212, 212)", + "light_plus": ".vs .token rgb(0, 0, 0)", "dark_vs": ".vs-dark .token rgb(212, 212, 212)", "light_vs": ".vs .token rgb(0, 0, 0)", "hc_black": ".hc-black .token rgb(255, 255, 255)" } }, { - "c": "if (this_is_more_code == true && !indented) {", - "t": "md.source.variable", + "c": "// Markdown extra adds un-indented code blocks too", + "t": "markdown.meta.paragraph", "r": { - "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.variable rgb(156, 220, 254)", - "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.variable rgb(0, 16, 128)", + "dark_plus": ".vs-dark .token rgb(212, 212, 212)", + "light_plus": ".vs .token rgb(0, 0, 0)", + "dark_vs": ".vs-dark .token rgb(212, 212, 212)", + "light_vs": ".vs .token rgb(0, 0, 0)", + "hc_black": ".hc-black .token rgb(255, 255, 255)" + } + }, + { + "c": "if (this", + "t": "markdown.meta.paragraph", + "r": { + "dark_plus": ".vs-dark .token rgb(212, 212, 212)", + "light_plus": ".vs .token rgb(0, 0, 0)", + "dark_vs": ".vs-dark .token rgb(212, 212, 212)", + "light_vs": ".vs .token rgb(0, 0, 0)", + "hc_black": ".hc-black .token rgb(255, 255, 255)" + } + }, + { + "c": "_", + "t": "definition.italic.markdown.markup.meta.paragraph.punctuation", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.italic rgb(86, 156, 214)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.italic rgb(0, 0, 128)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.italic rgb(86, 156, 214)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.italic rgb(0, 0, 128)", + "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.markup.italic rgb(255, 255, 255)" + } + }, + { + "c": "is", + "t": "italic.markdown.markup.meta.paragraph", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.italic rgb(86, 156, 214)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.italic rgb(0, 0, 128)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.italic rgb(86, 156, 214)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.italic rgb(0, 0, 128)", + "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.markup.italic rgb(255, 255, 255)" + } + }, + { + "c": "_", + "t": "definition.italic.markdown.markup.meta.paragraph.punctuation", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.italic rgb(86, 156, 214)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.italic rgb(0, 0, 128)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.italic rgb(86, 156, 214)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.italic rgb(0, 0, 128)", + "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.markup.italic rgb(255, 255, 255)" + } + }, + { + "c": "more_code == true ", + "t": "markdown.meta.paragraph", + "r": { + "dark_plus": ".vs-dark .token rgb(212, 212, 212)", + "light_plus": ".vs .token rgb(0, 0, 0)", + "dark_vs": ".vs-dark .token rgb(212, 212, 212)", + "light_vs": ".vs .token rgb(0, 0, 0)", + "hc_black": ".hc-black .token rgb(255, 255, 255)" + } + }, + { + "c": "&&", + "t": "markdown.meta.other.paragraph.valid-ampersand", + "r": { + "dark_plus": ".vs-dark .token rgb(212, 212, 212)", + "light_plus": ".vs .token rgb(0, 0, 0)", + "dark_vs": ".vs-dark .token rgb(212, 212, 212)", + "light_vs": ".vs .token rgb(0, 0, 0)", + "hc_black": ".hc-black .token rgb(255, 255, 255)" + } + }, + { + "c": " !indented) {", + "t": "markdown.meta.paragraph", + "r": { + "dark_plus": ".vs-dark .token rgb(212, 212, 212)", + "light_plus": ".vs .token rgb(0, 0, 0)", "dark_vs": ".vs-dark .token rgb(212, 212, 212)", "light_vs": ".vs .token rgb(0, 0, 0)", "hc_black": ".hc-black .token rgb(255, 255, 255)" @@ -1189,10 +1277,10 @@ }, { "c": " // tild wrapped code blocks, also not indented", - "t": "md.source.variable", + "t": "markdown.meta.paragraph", "r": { - "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.variable rgb(156, 220, 254)", - "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.variable rgb(0, 16, 128)", + "dark_plus": ".vs-dark .token rgb(212, 212, 212)", + "light_plus": ".vs .token rgb(0, 0, 0)", "dark_vs": ".vs-dark .token rgb(212, 212, 212)", "light_vs": ".vs .token rgb(0, 0, 0)", "hc_black": ".hc-black .token rgb(255, 255, 255)" @@ -1200,10 +1288,10 @@ }, { "c": "}", - "t": "md.source.variable", + "t": "markdown.meta.paragraph", "r": { - "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.variable rgb(156, 220, 254)", - "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.variable rgb(0, 16, 128)", + "dark_plus": ".vs-dark .token rgb(212, 212, 212)", + "light_plus": ".vs .token rgb(0, 0, 0)", "dark_vs": ".vs-dark .token rgb(212, 212, 212)", "light_vs": ".vs .token rgb(0, 0, 0)", "hc_black": ".hc-black .token rgb(255, 255, 255)" @@ -1211,18 +1299,18 @@ }, { "c": "~~~", - "t": "md.string", + "t": "markdown.meta.paragraph", "r": { - "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.string rgb(206, 145, 120)", - "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.string rgb(163, 21, 21)", - "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.string rgb(206, 145, 120)", - "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.string rgb(163, 21, 21)", - "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.string rgb(206, 145, 120)" + "dark_plus": ".vs-dark .token rgb(212, 212, 212)", + "light_plus": ".vs .token rgb(0, 0, 0)", + "dark_vs": ".vs-dark .token rgb(212, 212, 212)", + "light_vs": ".vs .token rgb(0, 0, 0)", + "hc_black": ".hc-black .token rgb(255, 255, 255)" } }, { "c": "Text with", - "t": "", + "t": "markdown.meta.paragraph", "r": { "dark_plus": ".vs-dark .token rgb(212, 212, 212)", "light_plus": ".vs .token rgb(0, 0, 0)", @@ -1233,7 +1321,7 @@ }, { "c": "two trailing spaces", - "t": "", + "t": "markdown.meta.paragraph", "r": { "dark_plus": ".vs-dark .token rgb(212, 212, 212)", "light_plus": ".vs .token rgb(0, 0, 0)", @@ -1244,7 +1332,7 @@ }, { "c": "(on the right)", - "t": "", + "t": "markdown.meta.paragraph", "r": { "dark_plus": ".vs-dark .token rgb(212, 212, 212)", "light_plus": ".vs .token rgb(0, 0, 0)", @@ -1255,7 +1343,7 @@ }, { "c": "can be used", - "t": "", + "t": "markdown.meta.paragraph", "r": { "dark_plus": ".vs-dark .token rgb(212, 212, 212)", "light_plus": ".vs .token rgb(0, 0, 0)", @@ -1266,7 +1354,7 @@ }, { "c": "for things like poems", - "t": "", + "t": "markdown.meta.paragraph", "r": { "dark_plus": ".vs-dark .token rgb(212, 212, 212)", "light_plus": ".vs .token rgb(0, 0, 0)", @@ -1276,19 +1364,41 @@ } }, { - "c": "### Horizontal rules", - "t": "entity.md.name.tag", + "c": "###", + "t": "${1/(#)(#)?(#)?(#)?(#)?(#)?/${6:?6:${5:?5:${4:?4:${3:?3:${2:?2:1}}}}}/}.definition.heading.markdown.markup.punctuation", "r": { - "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.entity.name.tag rgb(86, 156, 214)", - "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.entity.name.tag rgb(128, 0, 0)", - "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.entity.name.tag rgb(86, 156, 214)", - "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.entity.name.tag rgb(128, 0, 0)", - "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.entity.name.tag rgb(86, 156, 214)" + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.heading rgb(86, 156, 214)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.heading rgb(128, 0, 0)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.heading rgb(86, 156, 214)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.heading rgb(128, 0, 0)", + "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.markup.heading rgb(103, 150, 230)" + } + }, + { + "c": " ", + "t": "${1/(#)(#)?(#)?(#)?(#)?(#)?/${6:?6:${5:?5:${4:?4:${3:?3:${2:?2:1}}}}}/}.heading.markdown.markup", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.heading rgb(86, 156, 214)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.heading rgb(128, 0, 0)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.heading rgb(86, 156, 214)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.heading rgb(128, 0, 0)", + "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.markup.heading rgb(103, 150, 230)" + } + }, + { + "c": "Horizontal rules", + "t": "${1/(#)(#)?(#)?(#)?(#)?(#)?/${6:?6:${5:?5:${4:?4:${3:?3:${2:?2:1}}}}}/}.entity.heading.markdown.markup.name.section", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.heading rgb(86, 156, 214)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.heading rgb(128, 0, 0)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.heading rgb(86, 156, 214)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.heading rgb(128, 0, 0)", + "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.markup.heading rgb(103, 150, 230)" } }, { "c": "* * * *", - "t": "md.meta.separator", + "t": "markdown.meta.separator", "r": { "dark_plus": ".vs-dark .token rgb(212, 212, 212)", "light_plus": ".vs .token rgb(0, 0, 0)", @@ -1299,7 +1409,7 @@ }, { "c": "****", - "t": "md.meta.separator", + "t": "markdown.meta.separator", "r": { "dark_plus": ".vs-dark .token rgb(212, 212, 212)", "light_plus": ".vs .token rgb(0, 0, 0)", @@ -1310,18 +1420,29 @@ }, { "c": "--------------------------", - "t": "attribute-name.entity.md.other", + "t": "markdown.meta.separator", "r": { - "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.entity.other.attribute-name rgb(156, 220, 254)", - "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.entity.other.attribute-name rgb(255, 0, 0)", - "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.entity.other.attribute-name rgb(156, 220, 254)", - "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.entity.other.attribute-name rgb(255, 0, 0)", - "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.entity.other.attribute-name rgb(156, 220, 254)" + "dark_plus": ".vs-dark .token rgb(212, 212, 212)", + "light_plus": ".vs .token rgb(0, 0, 0)", + "dark_vs": ".vs-dark .token rgb(212, 212, 212)", + "light_vs": ".vs .token rgb(0, 0, 0)", + "hc_black": ".hc-black .token rgb(255, 255, 255)" } }, { - "c": "![", - "t": "link.md.string", + "c": "!", + "t": "image.inline.markdown.meta.paragraph", + "r": { + "dark_plus": ".vs-dark .token rgb(212, 212, 212)", + "light_plus": ".vs .token rgb(0, 0, 0)", + "dark_vs": ".vs-dark .token rgb(212, 212, 212)", + "light_vs": ".vs .token rgb(0, 0, 0)", + "hc_black": ".hc-black .token rgb(255, 255, 255)" + } + }, + { + "c": "[", + "t": "begin.definition.image.inline.markdown.meta.paragraph.punctuation.string", "r": { "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.string rgb(206, 145, 120)", "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.string rgb(163, 21, 21)", @@ -1332,18 +1453,7 @@ }, { "c": "picture alt", - "t": "", - "r": { - "dark_plus": ".vs-dark .token rgb(212, 212, 212)", - "light_plus": ".vs .token rgb(0, 0, 0)", - "dark_vs": ".vs-dark .token rgb(212, 212, 212)", - "light_vs": ".vs .token rgb(0, 0, 0)", - "hc_black": ".hc-black .token rgb(255, 255, 255)" - } - }, - { - "c": "](/images/photo.jpeg \"Title is optional\")", - "t": "link.md.string", + "t": "description.image.inline.link.markdown.meta.other.paragraph.string", "r": { "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.string rgb(206, 145, 120)", "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.string rgb(163, 21, 21)", @@ -1353,19 +1463,151 @@ } }, { - "c": "## Markdown plus tables ##", - "t": "entity.md.name.tag", + "c": "]", + "t": "definition.end.image.inline.markdown.meta.paragraph.punctuation.string", "r": { - "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.entity.name.tag rgb(86, 156, 214)", - "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.entity.name.tag rgb(128, 0, 0)", - "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.entity.name.tag rgb(86, 156, 214)", - "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.entity.name.tag rgb(128, 0, 0)", - "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.entity.name.tag rgb(86, 156, 214)" + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.string rgb(206, 145, 120)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.string rgb(163, 21, 21)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.string rgb(206, 145, 120)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.string rgb(163, 21, 21)", + "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.string rgb(206, 145, 120)" + } + }, + { + "c": "(", + "t": "definition.image.inline.markdown.meta.metadata.paragraph.punctuation", + "r": { + "dark_plus": ".vs-dark .token rgb(212, 212, 212)", + "light_plus": ".vs .token rgb(0, 0, 0)", + "dark_vs": ".vs-dark .token rgb(212, 212, 212)", + "light_vs": ".vs .token rgb(0, 0, 0)", + "hc_black": ".hc-black .token rgb(255, 255, 255)" + } + }, + { + "c": "/images/photo.jpeg", + "t": "image.inline.link.markdown.markup.meta.paragraph.underline", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.underline rgb(212, 212, 212)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.underline rgb(0, 0, 0)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.underline rgb(212, 212, 212)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.underline rgb(0, 0, 0)", + "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.markup.underline rgb(255, 255, 255)" + } + }, + { + "c": " ", + "t": "image.inline.markdown.meta.paragraph", + "r": { + "dark_plus": ".vs-dark .token rgb(212, 212, 212)", + "light_plus": ".vs .token rgb(0, 0, 0)", + "dark_vs": ".vs-dark .token rgb(212, 212, 212)", + "light_vs": ".vs .token rgb(0, 0, 0)", + "hc_black": ".hc-black .token rgb(255, 255, 255)" + } + }, + { + "c": "\"", + "t": "definition.description.image.inline.link.markdown.meta.other.paragraph.punctuation.string.title", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.string rgb(206, 145, 120)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.string rgb(163, 21, 21)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.string rgb(206, 145, 120)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.string rgb(163, 21, 21)", + "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.string rgb(206, 145, 120)" + } + }, + { + "c": "Title is optional", + "t": "description.image.inline.link.markdown.meta.other.paragraph.string.title", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.string rgb(206, 145, 120)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.string rgb(163, 21, 21)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.string rgb(206, 145, 120)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.string rgb(163, 21, 21)", + "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.string rgb(206, 145, 120)" + } + }, + { + "c": "\"", + "t": "definition.description.image.inline.link.markdown.meta.other.paragraph.punctuation.string.title", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.string rgb(206, 145, 120)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.string rgb(163, 21, 21)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.string rgb(206, 145, 120)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.string rgb(163, 21, 21)", + "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.string rgb(206, 145, 120)" + } + }, + { + "c": ")", + "t": "definition.image.inline.markdown.meta.metadata.paragraph.punctuation", + "r": { + "dark_plus": ".vs-dark .token rgb(212, 212, 212)", + "light_plus": ".vs .token rgb(0, 0, 0)", + "dark_vs": ".vs-dark .token rgb(212, 212, 212)", + "light_vs": ".vs .token rgb(0, 0, 0)", + "hc_black": ".hc-black .token rgb(255, 255, 255)" + } + }, + { + "c": "##", + "t": "${1/(#)(#)?(#)?(#)?(#)?(#)?/${6:?6:${5:?5:${4:?4:${3:?3:${2:?2:1}}}}}/}.definition.heading.markdown.markup.punctuation", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.heading rgb(86, 156, 214)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.heading rgb(128, 0, 0)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.heading rgb(86, 156, 214)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.heading rgb(128, 0, 0)", + "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.markup.heading rgb(103, 150, 230)" + } + }, + { + "c": " ", + "t": "${1/(#)(#)?(#)?(#)?(#)?(#)?/${6:?6:${5:?5:${4:?4:${3:?3:${2:?2:1}}}}}/}.heading.markdown.markup", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.heading rgb(86, 156, 214)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.heading rgb(128, 0, 0)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.heading rgb(86, 156, 214)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.heading rgb(128, 0, 0)", + "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.markup.heading rgb(103, 150, 230)" + } + }, + { + "c": "Markdown plus tables", + "t": "${1/(#)(#)?(#)?(#)?(#)?(#)?/${6:?6:${5:?5:${4:?4:${3:?3:${2:?2:1}}}}}/}.entity.heading.markdown.markup.name.section", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.heading rgb(86, 156, 214)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.heading rgb(128, 0, 0)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.heading rgb(86, 156, 214)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.heading rgb(128, 0, 0)", + "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.markup.heading rgb(103, 150, 230)" + } + }, + { + "c": " ", + "t": "${1/(#)(#)?(#)?(#)?(#)?(#)?/${6:?6:${5:?5:${4:?4:${3:?3:${2:?2:1}}}}}/}.heading.markdown.markup", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.heading rgb(86, 156, 214)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.heading rgb(128, 0, 0)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.heading rgb(86, 156, 214)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.heading rgb(128, 0, 0)", + "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.markup.heading rgb(103, 150, 230)" + } + }, + { + "c": "##", + "t": "${1/(#)(#)?(#)?(#)?(#)?(#)?/${6:?6:${5:?5:${4:?4:${3:?3:${2:?2:1}}}}}/}.definition.heading.markdown.markup.punctuation", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.heading rgb(86, 156, 214)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.heading rgb(128, 0, 0)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.heading rgb(86, 156, 214)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.heading rgb(128, 0, 0)", + "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.markup.heading rgb(103, 150, 230)" } }, { "c": "| Header | Header | Right |", - "t": "", + "t": "markdown.meta.paragraph", "r": { "dark_plus": ".vs-dark .token rgb(212, 212, 212)", "light_plus": ".vs .token rgb(0, 0, 0)", @@ -1376,7 +1618,7 @@ }, { "c": "| ------ | ------ | -----: |", - "t": "", + "t": "markdown.meta.paragraph", "r": { "dark_plus": ".vs-dark .token rgb(212, 212, 212)", "light_plus": ".vs .token rgb(0, 0, 0)", @@ -1387,7 +1629,7 @@ }, { "c": "| Cell | Cell | $10 |", - "t": "", + "t": "markdown.meta.paragraph", "r": { "dark_plus": ".vs-dark .token rgb(212, 212, 212)", "light_plus": ".vs .token rgb(0, 0, 0)", @@ -1398,205 +1640,7 @@ }, { "c": "| Cell | Cell | $20 |", - "t": "", - "r": { - "dark_plus": ".vs-dark .token rgb(212, 212, 212)", - "light_plus": ".vs .token rgb(0, 0, 0)", - "dark_vs": ".vs-dark .token rgb(212, 212, 212)", - "light_vs": ".vs .token rgb(0, 0, 0)", - "hc_black": ".hc-black .token rgb(255, 255, 255)" - } - }, - { - "c": "* ", - "t": "keyword.md", - "r": { - "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.keyword rgb(86, 156, 214)", - "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.keyword rgb(0, 0, 255)", - "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.keyword rgb(86, 156, 214)", - "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.keyword rgb(0, 0, 255)", - "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.keyword rgb(86, 156, 214)" - } - }, - { - "c": "Outer pipes on tables are optional", - "t": "", - "r": { - "dark_plus": ".vs-dark .token rgb(212, 212, 212)", - "light_plus": ".vs .token rgb(0, 0, 0)", - "dark_vs": ".vs-dark .token rgb(212, 212, 212)", - "light_vs": ".vs .token rgb(0, 0, 0)", - "hc_black": ".hc-black .token rgb(255, 255, 255)" - } - }, - { - "c": "* ", - "t": "keyword.md", - "r": { - "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.keyword rgb(86, 156, 214)", - "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.keyword rgb(0, 0, 255)", - "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.keyword rgb(86, 156, 214)", - "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.keyword rgb(0, 0, 255)", - "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.keyword rgb(86, 156, 214)" - } - }, - { - "c": "Colon used for alignment (right versus left)", - "t": "", - "r": { - "dark_plus": ".vs-dark .token rgb(212, 212, 212)", - "light_plus": ".vs .token rgb(0, 0, 0)", - "dark_vs": ".vs-dark .token rgb(212, 212, 212)", - "light_vs": ".vs .token rgb(0, 0, 0)", - "hc_black": ".hc-black .token rgb(255, 255, 255)" - } - }, - { - "c": "## Markdown plus definition lists ##", - "t": "entity.md.name.tag", - "r": { - "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.entity.name.tag rgb(86, 156, 214)", - "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.entity.name.tag rgb(128, 0, 0)", - "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.entity.name.tag rgb(86, 156, 214)", - "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.entity.name.tag rgb(128, 0, 0)", - "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.entity.name.tag rgb(86, 156, 214)" - } - }, - { - "c": "Bottled water", - "t": "", - "r": { - "dark_plus": ".vs-dark .token rgb(212, 212, 212)", - "light_plus": ".vs .token rgb(0, 0, 0)", - "dark_vs": ".vs-dark .token rgb(212, 212, 212)", - "light_vs": ".vs .token rgb(0, 0, 0)", - "hc_black": ".hc-black .token rgb(255, 255, 255)" - } - }, - { - "c": ": ", - "t": "keyword.md", - "r": { - "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.keyword rgb(86, 156, 214)", - "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.keyword rgb(0, 0, 255)", - "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.keyword rgb(86, 156, 214)", - "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.keyword rgb(0, 0, 255)", - "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.keyword rgb(86, 156, 214)" - } - }, - { - "c": "$ 1.25", - "t": "", - "r": { - "dark_plus": ".vs-dark .token rgb(212, 212, 212)", - "light_plus": ".vs .token rgb(0, 0, 0)", - "dark_vs": ".vs-dark .token rgb(212, 212, 212)", - "light_vs": ".vs .token rgb(0, 0, 0)", - "hc_black": ".hc-black .token rgb(255, 255, 255)" - } - }, - { - "c": ": ", - "t": "keyword.md", - "r": { - "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.keyword rgb(86, 156, 214)", - "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.keyword rgb(0, 0, 255)", - "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.keyword rgb(86, 156, 214)", - "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.keyword rgb(0, 0, 255)", - "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.keyword rgb(86, 156, 214)" - } - }, - { - "c": "$ 1.55 (Large)", - "t": "", - "r": { - "dark_plus": ".vs-dark .token rgb(212, 212, 212)", - "light_plus": ".vs .token rgb(0, 0, 0)", - "dark_vs": ".vs-dark .token rgb(212, 212, 212)", - "light_vs": ".vs .token rgb(0, 0, 0)", - "hc_black": ".hc-black .token rgb(255, 255, 255)" - } - }, - { - "c": "Milk", - "t": "", - "r": { - "dark_plus": ".vs-dark .token rgb(212, 212, 212)", - "light_plus": ".vs .token rgb(0, 0, 0)", - "dark_vs": ".vs-dark .token rgb(212, 212, 212)", - "light_vs": ".vs .token rgb(0, 0, 0)", - "hc_black": ".hc-black .token rgb(255, 255, 255)" - } - }, - { - "c": "Pop", - "t": "", - "r": { - "dark_plus": ".vs-dark .token rgb(212, 212, 212)", - "light_plus": ".vs .token rgb(0, 0, 0)", - "dark_vs": ".vs-dark .token rgb(212, 212, 212)", - "light_vs": ".vs .token rgb(0, 0, 0)", - "hc_black": ".hc-black .token rgb(255, 255, 255)" - } - }, - { - "c": ": ", - "t": "keyword.md", - "r": { - "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.keyword rgb(86, 156, 214)", - "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.keyword rgb(0, 0, 255)", - "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.keyword rgb(86, 156, 214)", - "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.keyword rgb(0, 0, 255)", - "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.keyword rgb(86, 156, 214)" - } - }, - { - "c": "$ 1.75", - "t": "", - "r": { - "dark_plus": ".vs-dark .token rgb(212, 212, 212)", - "light_plus": ".vs .token rgb(0, 0, 0)", - "dark_vs": ".vs-dark .token rgb(212, 212, 212)", - "light_vs": ".vs .token rgb(0, 0, 0)", - "hc_black": ".hc-black .token rgb(255, 255, 255)" - } - }, - { - "c": "* ", - "t": "keyword.md", - "r": { - "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.keyword rgb(86, 156, 214)", - "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.keyword rgb(0, 0, 255)", - "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.keyword rgb(86, 156, 214)", - "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.keyword rgb(0, 0, 255)", - "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.keyword rgb(86, 156, 214)" - } - }, - { - "c": "Multiple definitions and terms are possible", - "t": "", - "r": { - "dark_plus": ".vs-dark .token rgb(212, 212, 212)", - "light_plus": ".vs .token rgb(0, 0, 0)", - "dark_vs": ".vs-dark .token rgb(212, 212, 212)", - "light_vs": ".vs .token rgb(0, 0, 0)", - "hc_black": ".hc-black .token rgb(255, 255, 255)" - } - }, - { - "c": "* ", - "t": "keyword.md", - "r": { - "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.keyword rgb(86, 156, 214)", - "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.keyword rgb(0, 0, 255)", - "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.keyword rgb(86, 156, 214)", - "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.keyword rgb(0, 0, 255)", - "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.keyword rgb(86, 156, 214)" - } - }, - { - "c": "Definitions can include multiple paragraphs too", - "t": "", + "t": "markdown.meta.paragraph", "r": { "dark_plus": ".vs-dark .token rgb(212, 212, 212)", "light_plus": ".vs .token rgb(0, 0, 0)", @@ -1607,7 +1651,128 @@ }, { "c": "*", - "t": "", + "t": "definition.list.markdown.markup.punctuation.unnumbered", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.punctuation.list rgb(103, 150, 230)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.punctuation.list rgb(4, 81, 165)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.punctuation.list rgb(103, 150, 230)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.punctuation.list rgb(4, 81, 165)", + "hc_black": ".hc-black .token rgb(255, 255, 255)" + } + }, + { + "c": " ", + "t": "list.markdown.markup.unnumbered", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.list rgb(103, 150, 230)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.list rgb(4, 81, 165)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.list rgb(103, 150, 230)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.list rgb(0, 0, 0)", + "hc_black": ".hc-black .token rgb(255, 255, 255)" + } + }, + { + "c": "Outer pipes on tables are optional", + "t": "list.markdown.markup.meta.paragraph.unnumbered", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.list rgb(103, 150, 230)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.list rgb(4, 81, 165)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.list rgb(103, 150, 230)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.list rgb(0, 0, 0)", + "hc_black": ".hc-black .token rgb(255, 255, 255)" + } + }, + { + "c": "*", + "t": "definition.list.markdown.markup.punctuation.unnumbered", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.punctuation.list rgb(103, 150, 230)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.punctuation.list rgb(4, 81, 165)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.punctuation.list rgb(103, 150, 230)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.punctuation.list rgb(4, 81, 165)", + "hc_black": ".hc-black .token rgb(255, 255, 255)" + } + }, + { + "c": " ", + "t": "list.markdown.markup.unnumbered", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.list rgb(103, 150, 230)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.list rgb(4, 81, 165)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.list rgb(103, 150, 230)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.list rgb(0, 0, 0)", + "hc_black": ".hc-black .token rgb(255, 255, 255)" + } + }, + { + "c": "Colon used for alignment (right versus left)", + "t": "list.markdown.markup.meta.paragraph.unnumbered", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.list rgb(103, 150, 230)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.list rgb(4, 81, 165)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.list rgb(103, 150, 230)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.list rgb(0, 0, 0)", + "hc_black": ".hc-black .token rgb(255, 255, 255)" + } + }, + { + "c": "##", + "t": "${1/(#)(#)?(#)?(#)?(#)?(#)?/${6:?6:${5:?5:${4:?4:${3:?3:${2:?2:1}}}}}/}.definition.heading.markdown.markup.punctuation", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.heading rgb(86, 156, 214)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.heading rgb(128, 0, 0)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.heading rgb(86, 156, 214)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.heading rgb(128, 0, 0)", + "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.markup.heading rgb(103, 150, 230)" + } + }, + { + "c": " ", + "t": "${1/(#)(#)?(#)?(#)?(#)?(#)?/${6:?6:${5:?5:${4:?4:${3:?3:${2:?2:1}}}}}/}.heading.markdown.markup", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.heading rgb(86, 156, 214)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.heading rgb(128, 0, 0)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.heading rgb(86, 156, 214)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.heading rgb(128, 0, 0)", + "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.markup.heading rgb(103, 150, 230)" + } + }, + { + "c": "Markdown plus definition lists", + "t": "${1/(#)(#)?(#)?(#)?(#)?(#)?/${6:?6:${5:?5:${4:?4:${3:?3:${2:?2:1}}}}}/}.entity.heading.markdown.markup.name.section", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.heading rgb(86, 156, 214)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.heading rgb(128, 0, 0)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.heading rgb(86, 156, 214)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.heading rgb(128, 0, 0)", + "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.markup.heading rgb(103, 150, 230)" + } + }, + { + "c": " ", + "t": "${1/(#)(#)?(#)?(#)?(#)?(#)?/${6:?6:${5:?5:${4:?4:${3:?3:${2:?2:1}}}}}/}.heading.markdown.markup", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.heading rgb(86, 156, 214)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.heading rgb(128, 0, 0)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.heading rgb(86, 156, 214)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.heading rgb(128, 0, 0)", + "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.markup.heading rgb(103, 150, 230)" + } + }, + { + "c": "##", + "t": "${1/(#)(#)?(#)?(#)?(#)?(#)?/${6:?6:${5:?5:${4:?4:${3:?3:${2:?2:1}}}}}/}.definition.heading.markdown.markup.punctuation", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.heading rgb(86, 156, 214)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.heading rgb(128, 0, 0)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.heading rgb(86, 156, 214)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.heading rgb(128, 0, 0)", + "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.markup.heading rgb(103, 150, 230)" + } + }, + { + "c": "Bottled water", + "t": "markdown.meta.paragraph", "r": { "dark_plus": ".vs-dark .token rgb(212, 212, 212)", "light_plus": ".vs .token rgb(0, 0, 0)", @@ -1617,19 +1782,8 @@ } }, { - "c": "[ABBR]", - "t": "link.md.string", - "r": { - "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.string rgb(206, 145, 120)", - "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.string rgb(163, 21, 21)", - "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.string rgb(206, 145, 120)", - "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.string rgb(163, 21, 21)", - "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.string rgb(206, 145, 120)" - } - }, - { - "c": ": Markdown plus abbreviations (produces an ", - "t": "", + "c": ": $ 1.25", + "t": "markdown.meta.paragraph", "r": { "dark_plus": ".vs-dark .token rgb(212, 212, 212)", "light_plus": ".vs .token rgb(0, 0, 0)", @@ -1639,8 +1793,140 @@ } }, { - "c": "", - "t": "entity.md.name.tag.tag-abbr", + "c": ": $ 1.55 (Large)", + "t": "markdown.meta.paragraph", + "r": { + "dark_plus": ".vs-dark .token rgb(212, 212, 212)", + "light_plus": ".vs .token rgb(0, 0, 0)", + "dark_vs": ".vs-dark .token rgb(212, 212, 212)", + "light_vs": ".vs .token rgb(0, 0, 0)", + "hc_black": ".hc-black .token rgb(255, 255, 255)" + } + }, + { + "c": "Milk", + "t": "markdown.meta.paragraph", + "r": { + "dark_plus": ".vs-dark .token rgb(212, 212, 212)", + "light_plus": ".vs .token rgb(0, 0, 0)", + "dark_vs": ".vs-dark .token rgb(212, 212, 212)", + "light_vs": ".vs .token rgb(0, 0, 0)", + "hc_black": ".hc-black .token rgb(255, 255, 255)" + } + }, + { + "c": "Pop", + "t": "markdown.meta.paragraph", + "r": { + "dark_plus": ".vs-dark .token rgb(212, 212, 212)", + "light_plus": ".vs .token rgb(0, 0, 0)", + "dark_vs": ".vs-dark .token rgb(212, 212, 212)", + "light_vs": ".vs .token rgb(0, 0, 0)", + "hc_black": ".hc-black .token rgb(255, 255, 255)" + } + }, + { + "c": ": $ 1.75", + "t": "markdown.meta.paragraph", + "r": { + "dark_plus": ".vs-dark .token rgb(212, 212, 212)", + "light_plus": ".vs .token rgb(0, 0, 0)", + "dark_vs": ".vs-dark .token rgb(212, 212, 212)", + "light_vs": ".vs .token rgb(0, 0, 0)", + "hc_black": ".hc-black .token rgb(255, 255, 255)" + } + }, + { + "c": "*", + "t": "definition.list.markdown.markup.punctuation.unnumbered", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.punctuation.list rgb(103, 150, 230)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.punctuation.list rgb(4, 81, 165)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.punctuation.list rgb(103, 150, 230)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.punctuation.list rgb(4, 81, 165)", + "hc_black": ".hc-black .token rgb(255, 255, 255)" + } + }, + { + "c": " ", + "t": "list.markdown.markup.unnumbered", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.list rgb(103, 150, 230)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.list rgb(4, 81, 165)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.list rgb(103, 150, 230)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.list rgb(0, 0, 0)", + "hc_black": ".hc-black .token rgb(255, 255, 255)" + } + }, + { + "c": "Multiple definitions and terms are possible", + "t": "list.markdown.markup.meta.paragraph.unnumbered", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.list rgb(103, 150, 230)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.list rgb(4, 81, 165)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.list rgb(103, 150, 230)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.list rgb(0, 0, 0)", + "hc_black": ".hc-black .token rgb(255, 255, 255)" + } + }, + { + "c": "*", + "t": "definition.list.markdown.markup.punctuation.unnumbered", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.punctuation.list rgb(103, 150, 230)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.punctuation.list rgb(4, 81, 165)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.punctuation.list rgb(103, 150, 230)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.punctuation.list rgb(4, 81, 165)", + "hc_black": ".hc-black .token rgb(255, 255, 255)" + } + }, + { + "c": " ", + "t": "list.markdown.markup.unnumbered", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.list rgb(103, 150, 230)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.list rgb(4, 81, 165)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.list rgb(103, 150, 230)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.list rgb(0, 0, 0)", + "hc_black": ".hc-black .token rgb(255, 255, 255)" + } + }, + { + "c": "Definitions can include multiple paragraphs too", + "t": "list.markdown.markup.meta.paragraph.unnumbered", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.markup.list rgb(103, 150, 230)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.markup.list rgb(4, 81, 165)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.markup.list rgb(103, 150, 230)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.markup.list rgb(0, 0, 0)", + "hc_black": ".hc-black .token rgb(255, 255, 255)" + } + }, + { + "c": "*[ABBR]: Markdown plus abbreviations (produces an ", + "t": "markdown.meta.paragraph", + "r": { + "dark_plus": ".vs-dark .token rgb(212, 212, 212)", + "light_plus": ".vs .token rgb(0, 0, 0)", + "dark_vs": ".vs-dark .token rgb(212, 212, 212)", + "light_vs": ".vs .token rgb(0, 0, 0)", + "hc_black": ".hc-black .token rgb(255, 255, 255)" + } + }, + { + "c": "<", + "t": "any.begin.definition.html.inline.markdown.meta.paragraph.punctuation.tag", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.meta.tag rgb(128, 128, 128)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.meta.tag rgb(128, 0, 0)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.meta.tag rgb(128, 128, 128)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.meta.tag rgb(128, 0, 0)", + "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.meta.tag rgb(128, 128, 128)" + } + }, + { + "c": "abbr", + "t": "any.entity.html.inline.markdown.meta.name.paragraph.tag", "r": { "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.entity.name.tag rgb(86, 156, 214)", "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.entity.name.tag rgb(128, 0, 0)", @@ -1649,9 +1935,20 @@ "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.entity.name.tag rgb(86, 156, 214)" } }, + { + "c": ">", + "t": "any.definition.end.html.inline.markdown.meta.paragraph.punctuation.tag", + "r": { + "dark_plus": ".vs-dark.vscode-theme-defaults-themes-dark_plus-json .token.meta.tag rgb(128, 128, 128)", + "light_plus": ".vs.vscode-theme-defaults-themes-light_plus-json .token.meta.tag rgb(128, 0, 0)", + "dark_vs": ".vs-dark.vscode-theme-defaults-themes-dark_vs-json .token.meta.tag rgb(128, 128, 128)", + "light_vs": ".vs.vscode-theme-defaults-themes-light_vs-json .token.meta.tag rgb(128, 0, 0)", + "hc_black": ".hc-black.vscode-theme-defaults-themes-hc_black-json .token.meta.tag rgb(128, 128, 128)" + } + }, { "c": " tag)", - "t": "", + "t": "markdown.meta.paragraph", "r": { "dark_plus": ".vs-dark .token rgb(212, 212, 212)", "light_plus": ".vs .token rgb(0, 0, 0)", From b740f389ca686a3b0ac2311a15cb3b509f9f80e4 Mon Sep 17 00:00:00 2001 From: Johannes Rieken Date: Wed, 15 Jun 2016 16:34:41 +0200 Subject: [PATCH 092/217] add support context menu --- .../actions/common/commandsExtensionPoint.ts | 8 +-- .../workbench/actionBarContributions.ts | 50 ++++++++++++++----- 2 files changed, 43 insertions(+), 15 deletions(-) diff --git a/src/vs/platform/actions/common/commandsExtensionPoint.ts b/src/vs/platform/actions/common/commandsExtensionPoint.ts index 7cfeed653e9..ca84d3024f8 100644 --- a/src/vs/platform/actions/common/commandsExtensionPoint.ts +++ b/src/vs/platform/actions/common/commandsExtensionPoint.ts @@ -18,8 +18,10 @@ export interface ResourceFilter { pattern?: string; } +export type Where = 'editor/primary' | 'editor/secondary' | 'context'; + export interface Context { - where: 'editor/primary' | 'editor/secondary'; + where: Where; when: string | string[] | ResourceFilter | ResourceFilter[]; } @@ -69,8 +71,8 @@ namespace validation { if (!context) { return true; } - if (context.where !== 'editor/primary' && context.where !== 'editor/secondary') { - rejects.push(localize('requireenumtype', "property `where` is mandatory and must be one of `editor/primary`, `editor/secondary`")); + if (context.where !== 'editor/primary' && context.where !== 'editor/secondary' && context.where !== 'context/explorer') { + rejects.push(localize('requireenumtype', "property `where` is mandatory and must be one of `editor/primary`, `editor/secondary`, or `context/explorer`")); return false; } if (typeof context.when !== 'object' && typeof context.when !== 'string' && !Array.isArray(context.when)) { diff --git a/src/vs/platform/actions/workbench/actionBarContributions.ts b/src/vs/platform/actions/workbench/actionBarContributions.ts index bdf9322c9ce..5f3d8f5089c 100644 --- a/src/vs/platform/actions/workbench/actionBarContributions.ts +++ b/src/vs/platform/actions/workbench/actionBarContributions.ts @@ -15,11 +15,11 @@ import {IExtensionService} from 'vs/platform/extensions/common/extensions'; import {IThemeService} from 'vs/workbench/services/themes/common/themeService'; import {isLightTheme} from 'vs/platform/theme/common/themes'; import {IKeybindingService} from 'vs/platform/keybinding/common/keybindingService'; -import {commands, Context, CommandAction} from '../common/commandsExtensionPoint'; +import {commands, Context, Where, CommandAction} from '../common/commandsExtensionPoint'; import matches from 'vs/editor/common/modes/languageSelector'; import {getUntitledOrFileResource} from 'vs/workbench/common/editor'; -class Contributor extends ActionBarContributor { +abstract class BaseActionBarContributor extends ActionBarContributor { constructor( @IModeService private _modeService: IModeService, @@ -30,20 +30,22 @@ class Contributor extends ActionBarContributor { super(); } + protected abstract _wheres(): { primary: Where; secondary: Where }; + public hasActions(context: any): boolean { - return this.getActions(context).length > 0; + return this._wheres().primary && this.getActions(context).length > 0; } public getActions(context: any): IAction[] { - return this._getActions(context, 'editor/primary'); + return this._getActions(context, this._wheres().primary); } public hasSecondaryActions(context: any): boolean { - return this.getSecondaryActions(context).length > 0; + return this._wheres().secondary && this.getSecondaryActions(context).length > 0; } public getSecondaryActions(context: any): IAction[] { - return this._getActions(context, 'editor/secondary'); + return this._getActions(context, this._wheres().secondary); } private _getActions(context: any, where: string): IAction[]{ @@ -54,11 +56,7 @@ class Contributor extends ActionBarContributor { return []; } - private _getResource(context: any): URI { - if (context.input !== void 0 && context.editor !== void 0 && context.position !== void 0 ) { - return getUntitledOrFileResource(context.input, true); - } - } + protected abstract _getResource(context: any): URI; private _getCommandActions(resource: URI, where: string): IAction[] { const result: IAction[] = []; @@ -91,6 +89,33 @@ class Contributor extends ActionBarContributor { } } +class EditorContributor extends BaseActionBarContributor { + + protected _wheres(): { primary: Where; secondary: Where } { + return { primary: 'editor/primary', secondary: 'editor/secondary' }; + } + protected _getResource(context: any): URI { + if (context.input !== void 0 && context.editor !== void 0 && context.position !== void 0 ) { + return getUntitledOrFileResource(context.input, true); + } + } +} + +class ContextMenuContributor extends BaseActionBarContributor { + + protected _wheres(): { primary: Where; secondary: Where } { + return { secondary: 'context', primary: undefined }; + } + + protected _getResource(context: any): URI { + if (context.element) { + if (context.element.resource instanceof URI) { + return context.element.resource; + } + } + } +} + class CommandItem extends ActionItem { constructor( @@ -131,4 +156,5 @@ class CommandItem extends ActionItem { } } -Registry.as(Extensions.Actionbar).registerActionBarContributor(Scope.EDITOR, Contributor); \ No newline at end of file +Registry.as(Extensions.Actionbar).registerActionBarContributor(Scope.EDITOR, EditorContributor); +Registry.as(Extensions.Actionbar).registerActionBarContributor(Scope.VIEWER, ContextMenuContributor); \ No newline at end of file From 11e5950ddacca5d2bceb05576a1d92542512b3f0 Mon Sep 17 00:00:00 2001 From: isidor Date: Wed, 15 Jun 2016 16:59:25 +0200 Subject: [PATCH 093/217] Listen on explorer view collapse / expand to expand the fixed open editors view fixes #6666 --- .../parts/files/browser/explorerViewlet.ts | 17 ++++++++++++++++- .../parts/files/browser/views/explorerView.ts | 10 ++++++++++ .../files/browser/views/openEditorsView.ts | 8 ++++---- 3 files changed, 30 insertions(+), 5 deletions(-) diff --git a/src/vs/workbench/parts/files/browser/explorerViewlet.ts b/src/vs/workbench/parts/files/browser/explorerViewlet.ts index 3211cd13212..5556a5e773b 100644 --- a/src/vs/workbench/parts/files/browser/explorerViewlet.ts +++ b/src/vs/workbench/parts/files/browser/explorerViewlet.ts @@ -6,7 +6,7 @@ 'use strict'; import 'vs/css!./media/explorerviewlet'; -import {IDisposable} from 'vs/base/common/lifecycle'; +import {IDisposable, dispose} from 'vs/base/common/lifecycle'; import {IAction} from 'vs/base/common/actions'; import {TPromise} from 'vs/base/common/winjs.base'; import {Dimension, Builder} from 'vs/base/browser/builder'; @@ -47,6 +47,7 @@ export class ExplorerViewlet extends Viewlet { private viewletSettings: any; private viewletState: FileViewletState; private dimension: Dimension; + private toDispose: IDisposable[]; private viewletVisibleContextKey: IKeybindingContextKey; @@ -67,6 +68,7 @@ export class ExplorerViewlet extends Viewlet { this.viewletSettings = this.getMemento(storageService, Scope.WORKSPACE); this.configurationService.onDidUpdateConfiguration(e => this.onConfigurationUpdated(e.config)); + this.toDispose = []; } public create(parent: Builder): TPromise { @@ -175,6 +177,18 @@ export class ExplorerViewlet extends Viewlet { const headerSize = this.openEditorsVisible ? undefined : 0; // If open editors are not visible set header size explicitly to 0, otherwise let it be computed by super class. this.explorerView = explorerView = explorerInstantiator.createInstance(ExplorerView, this.viewletState, this.getActionRunner(), this.viewletSettings, headerSize); + + // Listen on explorer view collapse / expand to grow / shrink the fixed open editors view #6666 + this.toDispose.push(this.explorerView.addListener2('collapse', () => { + if (this.openEditorsView) { + this.openEditorsView.updateBodySize(Number.MAX_VALUE); + } + })); + this.toDispose.push(this.explorerView.addListener2('expand', () => { + if (this.openEditorsView) { + this.openEditorsView.updateBodySize(); + } + })); } // No workspace @@ -288,6 +302,7 @@ export class ExplorerViewlet extends Viewlet { } public dispose(): void { + this.toDispose = dispose(this.toDispose); if (this.splitView) { this.splitView.dispose(); this.splitView = null; diff --git a/src/vs/workbench/parts/files/browser/views/explorerView.ts b/src/vs/workbench/parts/files/browser/views/explorerView.ts index 369c87d6f11..263e22d1d86 100644 --- a/src/vs/workbench/parts/files/browser/views/explorerView.ts +++ b/src/vs/workbench/parts/files/browser/views/explorerView.ts @@ -104,6 +104,16 @@ export class ExplorerView extends CollapsibleViewletView { super.renderHeader(container); } + public collapse(): void { + super.collapse(); + this.emit('collapse'); + } + + public expand(): void { + super.expand(); + this.emit('expand'); + } + public renderBody(container: HTMLElement): void { this.treeContainer = super.renderViewTree(container); DOM.addClass(this.treeContainer, 'explorer-folders-view'); diff --git a/src/vs/workbench/parts/files/browser/views/openEditorsView.ts b/src/vs/workbench/parts/files/browser/views/openEditorsView.ts index 37431614a3d..97b5db0af27 100644 --- a/src/vs/workbench/parts/files/browser/views/openEditorsView.ts +++ b/src/vs/workbench/parts/files/browser/views/openEditorsView.ts @@ -166,7 +166,7 @@ export class OpenEditorsView extends AdaptiveCollapsibleViewletView { private structuralTreeUpdate(): void { // View size - this.expandedBodySize = this.getExpandedBodySize(this.model); + this.updateBodySize(); // Show groups only if there is more than 1 group const treeInput = this.model.groups.length === 1 ? this.model.groups[0] : this.model; // TODO@Isidor temporary workaround due to a partial tree refresh issue @@ -212,7 +212,7 @@ export class OpenEditorsView extends AdaptiveCollapsibleViewletView { } // Adjust expanded body size - this.expandedBodySize = this.getExpandedBodySize(this.model); + this.updateBodySize(); } private updateDirtyIndicator(): void { @@ -226,8 +226,8 @@ export class OpenEditorsView extends AdaptiveCollapsibleViewletView { } } - private getExpandedBodySize(model: IEditorStacksModel): number { - return OpenEditorsView.computeExpandedBodySize(model, this.visibleOpenEditors, this.dynamicHeight); + public updateBodySize(newSize?: number): void { + this.expandedBodySize = newSize ? newSize : OpenEditorsView.computeExpandedBodySize(this.model, this.visibleOpenEditors, this.dynamicHeight); } private static computeExpandedBodySize(model: IEditorStacksModel, visibleOpenEditors = OpenEditorsView.DEFAULT_VISIBLE_OPEN_EDITORS, dynamicHeight = OpenEditorsView.DEFAULT_DYNAMIC_HEIGHT): number { From 67d03ac26b44c34d9a21d572df7874df37731c47 Mon Sep 17 00:00:00 2001 From: Johannes Rieken Date: Wed, 15 Jun 2016 17:03:39 +0200 Subject: [PATCH 094/217] more explicit context menu location: 'explorer/context' --- src/vs/platform/actions/common/commandsExtensionPoint.ts | 2 +- src/vs/platform/actions/workbench/actionBarContributions.ts | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/src/vs/platform/actions/common/commandsExtensionPoint.ts b/src/vs/platform/actions/common/commandsExtensionPoint.ts index ca84d3024f8..abbfe4c3198 100644 --- a/src/vs/platform/actions/common/commandsExtensionPoint.ts +++ b/src/vs/platform/actions/common/commandsExtensionPoint.ts @@ -18,7 +18,7 @@ export interface ResourceFilter { pattern?: string; } -export type Where = 'editor/primary' | 'editor/secondary' | 'context'; +export type Where = 'editor/primary' | 'editor/secondary' | 'explorer/context'; export interface Context { where: Where; diff --git a/src/vs/platform/actions/workbench/actionBarContributions.ts b/src/vs/platform/actions/workbench/actionBarContributions.ts index 5f3d8f5089c..c386f8002b4 100644 --- a/src/vs/platform/actions/workbench/actionBarContributions.ts +++ b/src/vs/platform/actions/workbench/actionBarContributions.ts @@ -104,7 +104,7 @@ class EditorContributor extends BaseActionBarContributor { class ContextMenuContributor extends BaseActionBarContributor { protected _wheres(): { primary: Where; secondary: Where } { - return { secondary: 'context', primary: undefined }; + return { secondary: 'explorer/context', primary: undefined }; } protected _getResource(context: any): URI { From 73f3255527ff73b917be764b2212ad31a4db3f3c Mon Sep 17 00:00:00 2001 From: Johannes Rieken Date: Wed, 15 Jun 2016 17:10:36 +0200 Subject: [PATCH 095/217] fix validation issue --- src/vs/platform/actions/common/commandsExtensionPoint.ts | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/vs/platform/actions/common/commandsExtensionPoint.ts b/src/vs/platform/actions/common/commandsExtensionPoint.ts index abbfe4c3198..4c59a6625de 100644 --- a/src/vs/platform/actions/common/commandsExtensionPoint.ts +++ b/src/vs/platform/actions/common/commandsExtensionPoint.ts @@ -71,8 +71,8 @@ namespace validation { if (!context) { return true; } - if (context.where !== 'editor/primary' && context.where !== 'editor/secondary' && context.where !== 'context/explorer') { - rejects.push(localize('requireenumtype', "property `where` is mandatory and must be one of `editor/primary`, `editor/secondary`, or `context/explorer`")); + if (context.where !== 'editor/primary' && context.where !== 'editor/secondary' && context.where !== 'explorer/context') { + rejects.push(localize('requireenumtype', "property `where` is mandatory and must be one of `editor/primary`, `editor/secondary`, or `explorer/context`")); return false; } if (typeof context.when !== 'object' && typeof context.when !== 'string' && !Array.isArray(context.when)) { From 93b0a04aa50076e22d59d3a2d071aebcfde302f8 Mon Sep 17 00:00:00 2001 From: Benjamin Pasero Date: Wed, 15 Jun 2016 17:51:06 +0200 Subject: [PATCH 096/217] reuse code to extract resources from DND --- src/vs/base/browser/dnd.ts | 32 +++++++++++++++++++ .../parts/editor/sideBySideEditorControl.ts | 24 ++------------ .../browser/parts/editor/tabsTitleControl.ts | 28 ++-------------- 3 files changed, 36 insertions(+), 48 deletions(-) diff --git a/src/vs/base/browser/dnd.ts b/src/vs/base/browser/dnd.ts index 91ae11f9880..766bf046cd3 100644 --- a/src/vs/base/browser/dnd.ts +++ b/src/vs/base/browser/dnd.ts @@ -6,6 +6,7 @@ 'use strict'; import {$} from 'vs/base/browser/builder'; +import URI from 'vs/base/common/uri'; /** * A helper that will execute a provided function when the provided HTMLElement receives @@ -39,4 +40,35 @@ export class DelayedDragHandler { public dispose(): void { this.clearDragTimeout(); } +} + +export function extractResources(e: DragEvent): URI[] { + const resources: URI[] = []; + if (e.dataTransfer.types.length > 0) { + + // Check for in-app DND + const rawData = e.dataTransfer.getData(e.dataTransfer.types[0]); + if (rawData) { + try { + resources.push(URI.parse(rawData)); + } catch (error) { + // Invalid URI + } + } + + // Check for native file transfer + if (e.dataTransfer && e.dataTransfer.files) { + for (let i = 0; i < e.dataTransfer.files.length; i++) { + if (e.dataTransfer.files[i] && e.dataTransfer.files[i].path) { + try { + resources.push(URI.file(e.dataTransfer.files[i].path)); + } catch (error) { + // Invalid URI + } + } + } + } + } + + return resources; } \ No newline at end of file diff --git a/src/vs/workbench/browser/parts/editor/sideBySideEditorControl.ts b/src/vs/workbench/browser/parts/editor/sideBySideEditorControl.ts index cb688c820c4..9b751e1daa2 100644 --- a/src/vs/workbench/browser/parts/editor/sideBySideEditorControl.ts +++ b/src/vs/workbench/browser/parts/editor/sideBySideEditorControl.ts @@ -34,6 +34,7 @@ import {TabsTitleControl} from 'vs/workbench/browser/parts/editor/tabsTitleContr import {NoTabsTitleControl} from 'vs/workbench/browser/parts/editor/noTabsTitleControl'; import {IEditorStacksModel, IStacksModelChangeEvent, IWorkbenchEditorConfiguration} from 'vs/workbench/common/editor'; import {ITitleAreaControl} from 'vs/workbench/browser/parts/editor/titleControl'; +import {extractResources} from 'vs/base/browser/dnd'; export enum Rochade { NONE, @@ -762,28 +763,7 @@ export class SideBySideEditorControl implements ISideBySideEditorControl, IVerti node.addEventListener(DOM.EventType.DROP, (e: DragEvent) => { DOM.EventHelper.stop(e); - const droppedResources: URI[] = []; - if (e.dataTransfer.types.length > 0) { - - // Check for in-app DND - const rawData = e.dataTransfer.getData(e.dataTransfer.types[0]); - if (rawData) { - const resource = URI.parse(rawData); - if (resource.scheme === 'file' || resource.scheme === 'untitled') { - droppedResources.push(resource); - } - } - - // Check for native file transfer - if (e.dataTransfer && e.dataTransfer.files) { - for (let i = 0; i < e.dataTransfer.files.length; i++) { - if (e.dataTransfer.files[i] && e.dataTransfer.files[i].path) { - droppedResources.push(URI.file(e.dataTransfer.files[i].path)); - } - } - } - } - + const droppedResources = extractResources(e).filter(r => r.scheme === 'file' || r.scheme === 'untitled'); if (droppedResources.length) { window.focus(); // make sure this window has focus so that the open call reaches the right window! this.openFromDrop(droppedResources, e.toElement).done(null, errors.onUnexpectedError); diff --git a/src/vs/workbench/browser/parts/editor/tabsTitleControl.ts b/src/vs/workbench/browser/parts/editor/tabsTitleControl.ts index 71fdc5b8df2..aa987ce75c5 100644 --- a/src/vs/workbench/browser/parts/editor/tabsTitleControl.ts +++ b/src/vs/workbench/browser/parts/editor/tabsTitleControl.ts @@ -11,7 +11,6 @@ import {IAction} from 'vs/base/common/actions'; import {prepareActions} from 'vs/workbench/browser/actionBarRegistry'; import arrays = require('vs/base/common/arrays'); import errors = require('vs/base/common/errors'); -import URI from 'vs/base/common/uri'; import DOM = require('vs/base/browser/dom'); import {isMacintosh} from 'vs/base/common/platform'; import {MIME_BINARY} from 'vs/base/common/mime'; @@ -33,6 +32,7 @@ import {TitleControl} from 'vs/workbench/browser/parts/editor/titleControl'; import {IDisposable, dispose} from 'vs/base/common/lifecycle'; import {ScrollableElement} from 'vs/base/browser/ui/scrollbar/scrollableElement'; import {ScrollbarVisibility} from 'vs/base/browser/ui/scrollbar/scrollableElementOptions'; +import {extractResources} from 'vs/base/browser/dnd'; export class TabsTitleControl extends TitleControl { @@ -472,31 +472,7 @@ export class TabsTitleControl extends TitleControl { } private handleExternalDrop(e: DragEvent, targetPosition: Position, targetIndex: number): void { - let resources: URI[] = []; - - if (e.dataTransfer.types.length > 0) { - - // Check for in-app DND - const rawData = e.dataTransfer.getData(e.dataTransfer.types[0]); - if (rawData) { - const resource = URI.parse(rawData); - if (resource.scheme === 'file' || resource.scheme === 'untitled') { - resources.push(resource); - } - } - - // Check for external app DND - else if (e.dataTransfer && e.dataTransfer.files) { - let thepaths: string[] = []; - for (let i = 0; i < e.dataTransfer.files.length; i++) { - if (e.dataTransfer.files[i] && (e.dataTransfer.files[i]).path) { - thepaths.push(e.dataTransfer.files[i].path); - } - } - - resources = thepaths.map(p => URI.file(p)); - } - } + const resources = extractResources(e).filter(r => r.scheme === 'file' || r.scheme === 'untitled'); // Open resources if found if (resources.length) { From dc72db46c64052f6ff099eb459fd1b0fa9fa56c4 Mon Sep 17 00:00:00 2001 From: Benjamin Pasero Date: Wed, 15 Jun 2016 18:04:57 +0200 Subject: [PATCH 097/217] dnd drop feedback on editor area --- .../browser/parts/editor/media/sidebyside.css | 13 ++++++++++++ .../parts/editor/sideBySideEditorControl.ts | 20 +++++++++++++++++-- src/vs/workbench/browser/workbench.ts | 5 +++-- 3 files changed, 34 insertions(+), 4 deletions(-) diff --git a/src/vs/workbench/browser/parts/editor/media/sidebyside.css b/src/vs/workbench/browser/parts/editor/media/sidebyside.css index 5a018fd4084..a5364281c05 100644 --- a/src/vs/workbench/browser/parts/editor/media/sidebyside.css +++ b/src/vs/workbench/browser/parts/editor/media/sidebyside.css @@ -11,6 +11,19 @@ background-color: #252526; } +.vs .monaco-workbench .editor > .content.dropfeedback { + background-color: #DDECFF; +} + +.vs-dark .monaco-workbench .editor > .content.dropfeedback { + background-color: #383B3D; +} + +.hc-black .monaco-workbench .editor > .content.dropfeedback { + background: none !important; + border: 2px dashed #f38518; +} + .vs .monaco-workbench .editor > .content.dragged { border-left: 1px solid #E7E7E7; border-right: 1px solid #E7E7E7; diff --git a/src/vs/workbench/browser/parts/editor/sideBySideEditorControl.ts b/src/vs/workbench/browser/parts/editor/sideBySideEditorControl.ts index 9b751e1daa2..23866339f12 100644 --- a/src/vs/workbench/browser/parts/editor/sideBySideEditorControl.ts +++ b/src/vs/workbench/browser/parts/editor/sideBySideEditorControl.ts @@ -760,15 +760,31 @@ export class SideBySideEditorControl implements ISideBySideEditorControl, IVerti private enableDropTarget(node: HTMLElement): void { // Let a dropped file open inside Code (only if dropped over editor area) - node.addEventListener(DOM.EventType.DROP, (e: DragEvent) => { + this.toDispose.push(DOM.addDisposableListener(node, DOM.EventType.DROP, (e: DragEvent) => { DOM.EventHelper.stop(e); + DOM.removeClass(node, 'dropfeedback'); const droppedResources = extractResources(e).filter(r => r.scheme === 'file' || r.scheme === 'untitled'); if (droppedResources.length) { window.focus(); // make sure this window has focus so that the open call reaches the right window! this.openFromDrop(droppedResources, e.toElement).done(null, errors.onUnexpectedError); } - }); + })); + + // Drag over + this.toDispose.push(DOM.addDisposableListener(node, DOM.EventType.DRAG_OVER, (e: DragEvent) => { + DOM.addClass(node, 'dropfeedback'); + })); + + // Drag leave + this.toDispose.push(DOM.addDisposableListener(node, DOM.EventType.DRAG_LEAVE, (e: DragEvent) => { + DOM.removeClass(node, 'dropfeedback'); + })); + + // Drag end + this.toDispose.push(DOM.addDisposableListener(node, DOM.EventType.DRAG_END, (e: DragEvent) => { + DOM.removeClass(node, 'dropfeedback'); + })); } private openFromDrop(resources: URI[], target: HTMLElement): TPromise { diff --git a/src/vs/workbench/browser/workbench.ts b/src/vs/workbench/browser/workbench.ts index fd4259566f4..ec7e2128491 100644 --- a/src/vs/workbench/browser/workbench.ts +++ b/src/vs/workbench/browser/workbench.ts @@ -676,10 +676,11 @@ export class Workbench implements IPartService { // We update the editorpart class to indicate if an editor is opened or not // through a delay to accomodate for fast editor switching + const editorContainer = this.editorPart.getContainer(); if (visibleEditors === 0) { - this.editorBackgroundDelayer.trigger(() => this.editorPart.getContainer().addClass('empty')); + this.editorBackgroundDelayer.trigger(() => editorContainer.addClass('empty')); } else { - this.editorBackgroundDelayer.trigger(() => this.editorPart.getContainer().removeClass('empty')); + this.editorBackgroundDelayer.trigger(() => editorContainer.removeClass('empty')); } } From 4880adda755782f25c19cd275a91eaafb607b536 Mon Sep 17 00:00:00 2001 From: Johannes Rieken Date: Wed, 15 Jun 2016 18:06:06 +0200 Subject: [PATCH 098/217] pass on the resource to which the command is contributed --- .../actions/common/commandsExtensionPoint.ts | 2 +- .../actions/workbench/actionBarContributions.ts | 17 ++++++++++++++--- 2 files changed, 15 insertions(+), 4 deletions(-) diff --git a/src/vs/platform/actions/common/commandsExtensionPoint.ts b/src/vs/platform/actions/common/commandsExtensionPoint.ts index 4c59a6625de..aea19486fbb 100644 --- a/src/vs/platform/actions/common/commandsExtensionPoint.ts +++ b/src/vs/platform/actions/common/commandsExtensionPoint.ts @@ -273,7 +273,7 @@ export class CommandAction extends Action { const activationEvent = `onCommand:${command.command}`; this._actionCallback = (...args: any[]) => { return extensionService.activateByEvent(activationEvent).then(() => { - return keybindingService.executeCommand(command.command); + return keybindingService.executeCommand(command.command, ...args); }); }; } diff --git a/src/vs/platform/actions/workbench/actionBarContributions.ts b/src/vs/platform/actions/workbench/actionBarContributions.ts index c386f8002b4..9370482ab5a 100644 --- a/src/vs/platform/actions/workbench/actionBarContributions.ts +++ b/src/vs/platform/actions/workbench/actionBarContributions.ts @@ -15,7 +15,7 @@ import {IExtensionService} from 'vs/platform/extensions/common/extensions'; import {IThemeService} from 'vs/workbench/services/themes/common/themeService'; import {isLightTheme} from 'vs/platform/theme/common/themes'; import {IKeybindingService} from 'vs/platform/keybinding/common/keybindingService'; -import {commands, Context, Where, CommandAction} from '../common/commandsExtensionPoint'; +import {commands, Command, Context, Where, CommandAction} from '../common/commandsExtensionPoint'; import matches from 'vs/editor/common/modes/languageSelector'; import {getUntitledOrFileResource} from 'vs/workbench/common/editor'; @@ -64,10 +64,10 @@ abstract class BaseActionBarContributor extends ActionBarContributor { const {context} = command; if (Array.isArray(context)) { if (context.some(context => this._matches(context, resource, where))) { - result.push(new CommandAction(command, this._extensionService, this._keybindingsService)); + result.push(this._createAction(command, resource)); } } else if (context && this._matches(context, resource, where)) { - result.push(new CommandAction(command, this._extensionService, this._keybindingsService)); + result.push(this._createAction(command, resource)); } } return result; @@ -87,6 +87,17 @@ abstract class BaseActionBarContributor extends ActionBarContributor { return new CommandItem(uri, action, this._themeService); } } + + private _createAction(command: Command, context: URI): CommandAction { + return new class extends CommandAction { + run() { + // TODO@joh,ben This is a workaround for the actionbar + // overwriting the context of the action item + return super.run(context); + } + + }(command, this._extensionService, this._keybindingsService); + } } class EditorContributor extends BaseActionBarContributor { From 07c5c4aeb4e89c974b8effe7ac6c44da7e4803e9 Mon Sep 17 00:00:00 2001 From: Joao Moreno Date: Wed, 15 Jun 2016 18:06:29 +0200 Subject: [PATCH 099/217] git service logging --- .../workbench/parts/git/electron-browser/electronGitService.ts | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/vs/workbench/parts/git/electron-browser/electronGitService.ts b/src/vs/workbench/parts/git/electron-browser/electronGitService.ts index 4e07fda9bec..d7fd4354506 100644 --- a/src/vs/workbench/parts/git/electron-browser/electronGitService.ts +++ b/src/vs/workbench/parts/git/electron-browser/electronGitService.ts @@ -185,7 +185,8 @@ export class ElectronGitService extends GitService { env: { ATOM_SHELL_INTERNAL_RUN_AS_NODE: 1, PIPE_LOGGING: 'true', - AMD_ENTRYPOINT: 'vs/workbench/parts/git/node/gitApp' + AMD_ENTRYPOINT: 'vs/workbench/parts/git/node/gitApp', + VERBOSE_LOGGING: String(!contextService.getConfiguration().env.isBuilt || contextService.getConfiguration().env.verboseLogging) } } ); From 50b395d9593d529d4078e84a9ef776e953c5c3a8 Mon Sep 17 00:00:00 2001 From: Joao Moreno Date: Wed, 15 Jun 2016 18:08:25 +0200 Subject: [PATCH 100/217] fix stray processes related to #7527 --- src/bootstrap.js | 15 +++++++++++++++ src/vs/base/parts/ipc/node/ipc.cp.ts | 22 ++++++++++------------ 2 files changed, 25 insertions(+), 12 deletions(-) diff --git a/src/bootstrap.js b/src/bootstrap.js index 093706562c6..dbee2f96865 100644 --- a/src/bootstrap.js +++ b/src/bootstrap.js @@ -109,4 +109,19 @@ process.on('uncaughtException', function (err) { } }); +// Kill oneself if one's parent dies. Much drama. +if (process.env['VSCODE_PARENT_PID']) { + const parentPid = Number(process.env['VSCODE_PARENT_PID']); + + if (typeof parentPid === 'number' && !isNaN(parentPid)) { + setInterval(function () { + try { + process.kill(parentPid, 0); // throws an exception if the main process doesn't exist anymore. + } catch (e) { + process.exit(); + } + }, 5000); + } +} + require('./bootstrap-amd').bootstrap(process.env['AMD_ENTRYPOINT']); \ No newline at end of file diff --git a/src/vs/base/parts/ipc/node/ipc.cp.ts b/src/vs/base/parts/ipc/node/ipc.cp.ts index 70a7f4dbd81..49fbaeba84e 100644 --- a/src/vs/base/parts/ipc/node/ipc.cp.ts +++ b/src/vs/base/parts/ipc/node/ipc.cp.ts @@ -104,22 +104,20 @@ export class Client implements IClient, IDisposable { private get client(): IPCClient { if (!this._client) { const args = this.options && this.options.args ? this.options.args : []; - let forkOpts:any = undefined; + const forkOpts = Object.create(null); - if (this.options) { - forkOpts = Object.create(null); + forkOpts.env = assign(clone(process.env), { 'VSCODE_PARENT_PID': String(process.pid) }); - if (this.options.env) { - forkOpts.env = assign(clone(process.env), this.options.env); - } + if (this.options && this.options.env) { + forkOpts.env = assign(forkOpts.env, this.options.env); + } - if (typeof this.options.debug === 'number') { - forkOpts.execArgv = ['--nolazy', '--debug=' + this.options.debug]; - } + if (this.options && typeof this.options.debug === 'number') { + forkOpts.execArgv = ['--nolazy', '--debug=' + this.options.debug]; + } - if (typeof this.options.debugBrk === 'number') { - forkOpts.execArgv = ['--nolazy', '--debug-brk=' + this.options.debugBrk]; - } + if (this.options && typeof this.options.debugBrk === 'number') { + forkOpts.execArgv = ['--nolazy', '--debug-brk=' + this.options.debugBrk]; } this.child = fork(this.modulePath, args, forkOpts); From 431a72d7e0a7e747f903eb0c09f5063aedf2277d Mon Sep 17 00:00:00 2001 From: isidor Date: Wed, 15 Jun 2016 18:20:08 +0200 Subject: [PATCH 101/217] revert Listen on explorer view collapse / expand to expand the fixed open editors view --- .../parts/files/browser/explorerViewlet.ts | 17 +---------------- .../parts/files/browser/views/explorerView.ts | 10 ---------- .../files/browser/views/openEditorsView.ts | 8 ++++---- 3 files changed, 5 insertions(+), 30 deletions(-) diff --git a/src/vs/workbench/parts/files/browser/explorerViewlet.ts b/src/vs/workbench/parts/files/browser/explorerViewlet.ts index 5556a5e773b..3211cd13212 100644 --- a/src/vs/workbench/parts/files/browser/explorerViewlet.ts +++ b/src/vs/workbench/parts/files/browser/explorerViewlet.ts @@ -6,7 +6,7 @@ 'use strict'; import 'vs/css!./media/explorerviewlet'; -import {IDisposable, dispose} from 'vs/base/common/lifecycle'; +import {IDisposable} from 'vs/base/common/lifecycle'; import {IAction} from 'vs/base/common/actions'; import {TPromise} from 'vs/base/common/winjs.base'; import {Dimension, Builder} from 'vs/base/browser/builder'; @@ -47,7 +47,6 @@ export class ExplorerViewlet extends Viewlet { private viewletSettings: any; private viewletState: FileViewletState; private dimension: Dimension; - private toDispose: IDisposable[]; private viewletVisibleContextKey: IKeybindingContextKey; @@ -68,7 +67,6 @@ export class ExplorerViewlet extends Viewlet { this.viewletSettings = this.getMemento(storageService, Scope.WORKSPACE); this.configurationService.onDidUpdateConfiguration(e => this.onConfigurationUpdated(e.config)); - this.toDispose = []; } public create(parent: Builder): TPromise { @@ -177,18 +175,6 @@ export class ExplorerViewlet extends Viewlet { const headerSize = this.openEditorsVisible ? undefined : 0; // If open editors are not visible set header size explicitly to 0, otherwise let it be computed by super class. this.explorerView = explorerView = explorerInstantiator.createInstance(ExplorerView, this.viewletState, this.getActionRunner(), this.viewletSettings, headerSize); - - // Listen on explorer view collapse / expand to grow / shrink the fixed open editors view #6666 - this.toDispose.push(this.explorerView.addListener2('collapse', () => { - if (this.openEditorsView) { - this.openEditorsView.updateBodySize(Number.MAX_VALUE); - } - })); - this.toDispose.push(this.explorerView.addListener2('expand', () => { - if (this.openEditorsView) { - this.openEditorsView.updateBodySize(); - } - })); } // No workspace @@ -302,7 +288,6 @@ export class ExplorerViewlet extends Viewlet { } public dispose(): void { - this.toDispose = dispose(this.toDispose); if (this.splitView) { this.splitView.dispose(); this.splitView = null; diff --git a/src/vs/workbench/parts/files/browser/views/explorerView.ts b/src/vs/workbench/parts/files/browser/views/explorerView.ts index 263e22d1d86..369c87d6f11 100644 --- a/src/vs/workbench/parts/files/browser/views/explorerView.ts +++ b/src/vs/workbench/parts/files/browser/views/explorerView.ts @@ -104,16 +104,6 @@ export class ExplorerView extends CollapsibleViewletView { super.renderHeader(container); } - public collapse(): void { - super.collapse(); - this.emit('collapse'); - } - - public expand(): void { - super.expand(); - this.emit('expand'); - } - public renderBody(container: HTMLElement): void { this.treeContainer = super.renderViewTree(container); DOM.addClass(this.treeContainer, 'explorer-folders-view'); diff --git a/src/vs/workbench/parts/files/browser/views/openEditorsView.ts b/src/vs/workbench/parts/files/browser/views/openEditorsView.ts index 97b5db0af27..37431614a3d 100644 --- a/src/vs/workbench/parts/files/browser/views/openEditorsView.ts +++ b/src/vs/workbench/parts/files/browser/views/openEditorsView.ts @@ -166,7 +166,7 @@ export class OpenEditorsView extends AdaptiveCollapsibleViewletView { private structuralTreeUpdate(): void { // View size - this.updateBodySize(); + this.expandedBodySize = this.getExpandedBodySize(this.model); // Show groups only if there is more than 1 group const treeInput = this.model.groups.length === 1 ? this.model.groups[0] : this.model; // TODO@Isidor temporary workaround due to a partial tree refresh issue @@ -212,7 +212,7 @@ export class OpenEditorsView extends AdaptiveCollapsibleViewletView { } // Adjust expanded body size - this.updateBodySize(); + this.expandedBodySize = this.getExpandedBodySize(this.model); } private updateDirtyIndicator(): void { @@ -226,8 +226,8 @@ export class OpenEditorsView extends AdaptiveCollapsibleViewletView { } } - public updateBodySize(newSize?: number): void { - this.expandedBodySize = newSize ? newSize : OpenEditorsView.computeExpandedBodySize(this.model, this.visibleOpenEditors, this.dynamicHeight); + private getExpandedBodySize(model: IEditorStacksModel): number { + return OpenEditorsView.computeExpandedBodySize(model, this.visibleOpenEditors, this.dynamicHeight); } private static computeExpandedBodySize(model: IEditorStacksModel, visibleOpenEditors = OpenEditorsView.DEFAULT_VISIBLE_OPEN_EDITORS, dynamicHeight = OpenEditorsView.DEFAULT_DYNAMIC_HEIGHT): number { From 88ac2c349cfaeb5eb52cc3911f3d0900f40d1b1a Mon Sep 17 00:00:00 2001 From: Benjamin Pasero Date: Wed, 15 Jun 2016 18:24:04 +0200 Subject: [PATCH 102/217] fix action enablement in group --- src/vs/workbench/browser/parts/editor/tabsTitleControl.ts | 1 + 1 file changed, 1 insertion(+) diff --git a/src/vs/workbench/browser/parts/editor/tabsTitleControl.ts b/src/vs/workbench/browser/parts/editor/tabsTitleControl.ts index aa987ce75c5..6ab51f16e55 100644 --- a/src/vs/workbench/browser/parts/editor/tabsTitleControl.ts +++ b/src/vs/workbench/browser/parts/editor/tabsTitleControl.ts @@ -337,6 +337,7 @@ export class TabsTitleControl extends TitleControl { this.showEditorsOfLeftGroup.enabled = isOverflowing; this.showEditorsOfCenterGroup.enabled = isOverflowing; this.showEditorsOfRightGroup.enabled = isOverflowing; + this.showAllEditorsAction.enabled = isOverflowing; } private hookTabListeners(tab: HTMLElement, identifier: IEditorIdentifier): void { From ff2ae899ec6a3c1b6d525f8fbd6f2041f0aaecff Mon Sep 17 00:00:00 2001 From: Benjamin Pasero Date: Wed, 15 Jun 2016 18:45:16 +0200 Subject: [PATCH 103/217] avoid comment leak to html --- src/vs/workbench/electron-browser/index.html | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/vs/workbench/electron-browser/index.html b/src/vs/workbench/electron-browser/index.html index 0863286ed10..015cf62f40c 100644 --- a/src/vs/workbench/electron-browser/index.html +++ b/src/vs/workbench/electron-browser/index.html @@ -208,7 +208,7 @@ - + ' - ].join('\n'); - } - - public clearInput(): void { - - // Reset IFrame - this.clearIFrame(); - - super.clearInput(); - } - - private clearIFrame(): void { - this.iframeBuilder.src('about:blank'); - this.iframeBuilder.removeProperty(IFrameEditor.RESOURCE_PROPERTY); - - // Focus Listener - this.clearFocusTracker(); - } - - private clearFocusTracker(): void { - if (this.focusTracker) { - this.focusTracker.dispose(); - this.focusTracker = null; - } - } - - public layout(dimension: Dimension): void { - - // Pass on to IFrame Container and IFrame - this.iframeContainer.size(dimension.width, dimension.height); - this.iframeBuilder.size(dimension.width, dimension.height); - } - - public focus(): void { - this.iframeContainer.domFocus(); - } - - public changePosition(position: Position): void { - super.changePosition(position); - - // reparenting an IFRAME into another DOM element yields weird results when the contents are made - // of a string and not a URL. to be on the safe side we reload the iframe when the position changes - // and we do it using a timeout of 0 to reload only after the position has been changed in the DOM - setTimeout(() => this.reload(true)); - } - - /** - * Reloads the contents of the iframe in this editor by reapplying the input. - */ - public reload(clearIFrame?: boolean): void { - if (this.input) { - if (clearIFrame) { - this.clearIFrame(); - } - - this.doSetInput(this.input).done(null, errors.onUnexpectedError); - } - } - - public dispose(): void { - - // Destroy Container - this.iframeContainer.destroy(); - - // Focus Listener - this.clearFocusTracker(); - - super.dispose(); - } -} \ No newline at end of file diff --git a/src/vs/workbench/browser/parts/editor/media/iframeeditor.css b/src/vs/workbench/browser/parts/editor/media/iframeeditor.css deleted file mode 100644 index 86f2f2a3543..00000000000 --- a/src/vs/workbench/browser/parts/editor/media/iframeeditor.css +++ /dev/null @@ -1,13 +0,0 @@ -/*--------------------------------------------------------------------------------------------- - * Copyright (c) Microsoft Corporation. All rights reserved. - * Licensed under the MIT License. See License.txt in the project root for license information. - *--------------------------------------------------------------------------------------------*/ - -.monaco-workbench .iframe-container .iframe { - box-sizing: border-box; -} - -.monaco-workbench .iframe-container.ipad-touch-enabled { - -webkit-overflow-scrolling: touch; - overflow: auto; -} \ No newline at end of file diff --git a/src/vs/workbench/browser/parts/editor/sideBySideEditorControl.ts b/src/vs/workbench/browser/parts/editor/sideBySideEditorControl.ts index bfbfd2e6a71..2d2555c4584 100644 --- a/src/vs/workbench/browser/parts/editor/sideBySideEditorControl.ts +++ b/src/vs/workbench/browser/parts/editor/sideBySideEditorControl.ts @@ -879,7 +879,7 @@ export class SideBySideEditorControl implements ISideBySideEditorControl, IVerti DOM.EventHelper.stop(e); - // Overlay the editor area with a div to be able to capture all mouse events (helps when iframes are used in any editor) + // Overlay the editor area with a div to be able to capture all mouse events let overlayDiv = $('div').style({ position: 'absolute', top: SideBySideEditorControl.EDITOR_TITLE_HEIGHT + 'px', diff --git a/src/vs/workbench/common/editor/iframeEditorInput.ts b/src/vs/workbench/common/editor/iframeEditorInput.ts deleted file mode 100644 index fc9bf180112..00000000000 --- a/src/vs/workbench/common/editor/iframeEditorInput.ts +++ /dev/null @@ -1,106 +0,0 @@ -/*--------------------------------------------------------------------------------------------- - * Copyright (c) Microsoft Corporation. All rights reserved. - * Licensed under the MIT License. See License.txt in the project root for license information. - *--------------------------------------------------------------------------------------------*/ -'use strict'; - -import {TPromise} from 'vs/base/common/winjs.base'; -import {EditorModel, EditorInput} from 'vs/workbench/common/editor'; -import URI from 'vs/base/common/uri'; - -/** - * An editor input to use with the IFrameEditor. - */ -export abstract class IFrameEditorInput extends EditorInput { - - public static ID: string = 'workbench.editors.iFrameEditorInput'; - - private resource: URI; - private name: string; - private description: string; - private cachedModel: EditorModel; - - constructor(resource: URI, name: string, description: string) { - super(); - - this.resource = resource; - this.name = name; - this.description = description; - } - - public getTypeId(): string { - return IFrameEditorInput.ID; - } - - public getResource(): URI { - return this.resource; - } - - public getName(): string { - return this.name; - } - - public getDescription(): string { - return this.description; - } - - public resolve(refresh?: boolean): TPromise { - let modelPromise: TPromise; - - // Use Cached Model - if (this.cachedModel && !refresh) { - modelPromise = TPromise.as(this.cachedModel); - } - - // Refresh Cached Model - else if (this.cachedModel && refresh) { - modelPromise = this.cachedModel.load(); - } - - // Create Model and Load - else { - let model = this.createModel(); - modelPromise = model.load(); - } - - return modelPromise.then((resolvedModel: EditorModel) => { - this.cachedModel = resolvedModel; - - return this.cachedModel; - }); - } - - /** - * Subclasses override this method to provide their own implementation. - */ - protected abstract createModel(): EditorModel; - - /** - * Subclasses override this method to create a new input from a given resource. - */ - public abstract createNew(resource: URI): IFrameEditorInput; - - public matches(otherInput: any): boolean { - if (super.matches(otherInput) === true) { - return true; - } - - if (otherInput instanceof IFrameEditorInput) { - let otherIFrameEditorInput = otherInput; - - // Otherwise compare by properties - return otherIFrameEditorInput.resource.toString() === this.resource.toString(); - } - - return false; - } - - public dispose(): void { - if (this.cachedModel) { - this.cachedModel.dispose(); - this.cachedModel = null; - } - - super.dispose(); - } -} \ No newline at end of file diff --git a/src/vs/workbench/common/editor/iframeEditorModel.ts b/src/vs/workbench/common/editor/iframeEditorModel.ts deleted file mode 100644 index 95ae8957d7b..00000000000 --- a/src/vs/workbench/common/editor/iframeEditorModel.ts +++ /dev/null @@ -1,52 +0,0 @@ -/*--------------------------------------------------------------------------------------------- - * Copyright (c) Microsoft Corporation. All rights reserved. - * Licensed under the MIT License. See License.txt in the project root for license information. - *--------------------------------------------------------------------------------------------*/ -'use strict'; - -import URI from 'vs/base/common/uri'; -import {EditorModel} from 'vs/workbench/common/editor'; - -export interface IFrameContents { - head: string; - body: string; - tail: string; -} - -/** - * An editor model that represents the resolved state for an iframe editor input. After the model has been - * resolved it knows which content to pass to the iframe editor. The contents will be set directly into the - * iframe. The contents have to ensure that e.g. a base URL is set so that relative links or images can be - * resolved. - */ -export class IFrameEditorModel extends EditorModel { - private _resource: URI; - - private head: string; - private body: string; - private tail: string; - - constructor(resource:URI) { - super(); - - this._resource = resource; - } - - public get resource(): URI { - return this._resource; - } - - public setContents(head: string, body: string, tail: string): void { - this.head = head; - this.body = body; - this.tail = tail; - } - - public getContents(): IFrameContents { - return { - head: this.head, - body: this.body, - tail: this.tail - }; - } -} \ No newline at end of file diff --git a/src/vs/workbench/electron-browser/media/shell.css b/src/vs/workbench/electron-browser/media/shell.css index afa1a414b90..e93e5d2e299 100644 --- a/src/vs/workbench/electron-browser/media/shell.css +++ b/src/vs/workbench/electron-browser/media/shell.css @@ -169,7 +169,6 @@ outline: 0 !important; /* activity bar indicates focus custom */ } -.monaco-shell .part.editor .iframe-container, .monaco-shell .part.editor .binary-container { outline: 0 !important; } diff --git a/src/vs/workbench/parts/files/browser/fileTracker.ts b/src/vs/workbench/parts/files/browser/fileTracker.ts index 094046949e1..7ebfdbc57bd 100644 --- a/src/vs/workbench/parts/files/browser/fileTracker.ts +++ b/src/vs/workbench/parts/files/browser/fileTracker.ts @@ -17,9 +17,7 @@ import {BaseTextEditor} from 'vs/workbench/browser/parts/editor/textEditor'; import {LocalFileChangeEvent, TextFileChangeEvent, VIEWLET_ID, BINARY_FILE_EDITOR_ID, EventType as FileEventType, ITextFileService, AutoSaveMode, ModelState} from 'vs/workbench/parts/files/common/files'; import {FileChangeType, FileChangesEvent, EventType as CommonFileEventType} from 'vs/platform/files/common/files'; import {FileEditorInput} from 'vs/workbench/parts/files/browser/editors/fileEditorInput'; -import {IFrameEditorInput} from 'vs/workbench/common/editor/iframeEditorInput'; import {TextFileEditorModel, CACHE} from 'vs/workbench/parts/files/common/editors/textFileEditorModel'; -import {IFrameEditor} from 'vs/workbench/browser/parts/editor/iframeEditor'; import {EventType as WorkbenchEventType, UntitledEditorEvent} from 'vs/workbench/common/events'; import {IEditorGroupService} from 'vs/workbench/services/group/common/groupService'; import {IUntitledEditorService} from 'vs/workbench/services/untitled/common/untitledEditorService'; @@ -228,14 +226,6 @@ export class FileTracker implements IWorkbenchContribution { } } } - - // IFrame Editor Input - else if (input instanceof IFrameEditorInput) { - let iFrameInput = input; - if (e.contains(iFrameInput.getResource(), FileChangeType.UPDATED)) { - (editor).reload(); - } - } }); } @@ -273,8 +263,6 @@ export class FileTracker implements IWorkbenchContribution { let inputResource: URI; if (input instanceof FileEditorInput) { inputResource = (input).getResource(); - } else if (input instanceof IFrameEditorInput) { - inputResource = (input).getResource(); } // Editor Input with associated Resource @@ -306,16 +294,6 @@ export class FileTracker implements IWorkbenchContribution { // Reopen File Input if (input instanceof FileEditorInput) { editorInput = this.instantiationService.createInstance(FileEditorInput, reopenFileResource, mimeHint || MIME_UNKNOWN, void 0); - } - - // Reopen IFrame Input - else if (input instanceof IFrameEditorInput) { - let iFrameInput = input; - - editorInput = iFrameInput.createNew(reopenFileResource); - } - - if (editorInput) { this.editorService.openEditor(editorInput, editorOptions, editor.position).done(null, errors.onUnexpectedError); } } @@ -381,11 +359,6 @@ export class FileTracker implements IWorkbenchContribution { else if (input instanceof FileEditorInput && this.containsResource(input, resource)) { inputsContainingPath.push(input); } - - // IFrame Input - else if (input instanceof IFrameEditorInput && this.containsResource(input, resource)) { - inputsContainingPath.push(input); - } }); inputsContainingPath.forEach((input) => { @@ -404,13 +377,10 @@ export class FileTracker implements IWorkbenchContribution { } private containsResource(input: FileEditorInput, resource: URI): boolean; - private containsResource(input: IFrameEditorInput, resource: URI): boolean; private containsResource(input: EditorInput, resource: URI): boolean { let fileResource: URI; if (input instanceof FileEditorInput) { fileResource = (input).getResource(); - } else { - fileResource = (input).getResource(); } if (paths.isEqualOrParent(fileResource.fsPath, resource.fsPath)) { @@ -452,18 +422,6 @@ export class FileTracker implements IWorkbenchContribution { return false; // never dispose unsaved models } - if (this.editorService.getVisibleEditors().some(e => { - if (e.input instanceof IFrameEditorInput) { - let iFrameInputResource = (e.input).getResource(); - - return iFrameInputResource && iFrameInputResource.toString() === textModel.getResource().toString(); - } - - return false; - })) { - return false; // never dispose models that are used in iframe inputs - } - return true; } diff --git a/src/vs/workbench/parts/files/browser/media/ViewSource.svg b/src/vs/workbench/parts/files/browser/media/ViewSource.svg deleted file mode 100644 index 85a001dccc2..00000000000 --- a/src/vs/workbench/parts/files/browser/media/ViewSource.svg +++ /dev/null @@ -1,3 +0,0 @@ - -]> \ No newline at end of file diff --git a/src/vs/workbench/parts/files/browser/media/ViewSource_inverse.svg b/src/vs/workbench/parts/files/browser/media/ViewSource_inverse.svg deleted file mode 100644 index f6302185aa4..00000000000 --- a/src/vs/workbench/parts/files/browser/media/ViewSource_inverse.svg +++ /dev/null @@ -1 +0,0 @@ - \ No newline at end of file diff --git a/src/vs/workbench/parts/files/browser/media/fileactions.css b/src/vs/workbench/parts/files/browser/media/fileactions.css index 35920336957..497b0be5379 100644 --- a/src/vs/workbench/parts/files/browser/media/fileactions.css +++ b/src/vs/workbench/parts/files/browser/media/fileactions.css @@ -75,22 +75,6 @@ background: url('Preview_inverse.svg') center center no-repeat; } -.monaco-workbench .iframe-editor-action.view-source { - background: url('ViewSource.svg') center center no-repeat; -} - -.vs-dark .monaco-workbench .iframe-editor-action.view-source { - background: url('ViewSource_inverse.svg') center center no-repeat; -} - -.monaco-workbench .iframe-editor-action.refresh { - background: url('Refresh.svg') center center no-repeat; -} - -.vs-dark .monaco-workbench .iframe-editor-action.refresh { - background: url('Refresh_inverse.svg') center center no-repeat; -} - .explorer-viewlet .explorer-open-editors .close-editor-action { background: url("action-close.svg") center center no-repeat; } @@ -122,7 +106,6 @@ /* High Contrast Theming */ .hc-black .monaco-workbench .explorer-action, .hc-black .monaco-workbench .quick-open-sidebyside, -.hc-black .monaco-workbench .iframe-editor-action, .hc-black .monaco-workbench .file-editor-action.action-open-preview { background: none; } @@ -155,14 +138,6 @@ content: url('SplitEditor_inverse.svg'); } -.hc-black .monaco-workbench .iframe-editor-action.view-source:before { - content: url('ViewSource_inverse.svg'); -} - -.hc-black .monaco-workbench .iframe-editor-action.refresh:before { - content: url('Refresh_inverse.svg'); -} - .hc-black .monaco-workbench .file-editor-action.action-open-preview:before { content: url('Preview_inverse.svg'); } diff --git a/src/vs/workbench/parts/files/browser/views/openEditorsViewer.ts b/src/vs/workbench/parts/files/browser/views/openEditorsViewer.ts index 2bb57b64c37..1063cd2fb94 100644 --- a/src/vs/workbench/parts/files/browser/views/openEditorsViewer.ts +++ b/src/vs/workbench/parts/files/browser/views/openEditorsViewer.ts @@ -495,7 +495,7 @@ export class DragAndDrop extends treedefaults.DefaultDragAndDrop { } const resource = element.getResource(); - // Some open editors do not have a resource (markdown preview) so use the name as drag identifier instead #7021 + // Some open editors do not have a resource so use the name as drag identifier instead #7021 return resource ? resource.toString() : element.editorInput.getName(); } diff --git a/src/vs/workbench/parts/html/browser/htmlPreviewPart.ts b/src/vs/workbench/parts/html/browser/htmlPreviewPart.ts index b1e6c0c4c1f..574d209b380 100644 --- a/src/vs/workbench/parts/html/browser/htmlPreviewPart.ts +++ b/src/vs/workbench/parts/html/browser/htmlPreviewPart.ts @@ -24,7 +24,7 @@ import {IOpenerService} from 'vs/platform/opener/common/opener'; import Webview from './webview'; /** - * An implementation of editor for showing HTML content in an IFrame by leveraging the IFrameEditorInput. + * An implementation of editor for showing HTML content in an IFrame by leveraging the HTML input. */ export class HtmlPreviewPart extends BaseEditor { diff --git a/src/vs/workbench/parts/markdown/browser/markdown.contribution.ts b/src/vs/workbench/parts/markdown/browser/markdown.contribution.ts deleted file mode 100644 index 81e10719bdc..00000000000 --- a/src/vs/workbench/parts/markdown/browser/markdown.contribution.ts +++ /dev/null @@ -1,37 +0,0 @@ -/*--------------------------------------------------------------------------------------------- - * Copyright (c) Microsoft Corporation. All rights reserved. - * Licensed under the MIT License. See License.txt in the project root for license information. - *--------------------------------------------------------------------------------------------*/ -'use strict'; - -import {Registry} from 'vs/platform/platform'; -import URI from 'vs/base/common/uri'; -import {IEditorRegistry, Extensions as EditorExtensions, IEditorInputFactory} from 'vs/workbench/browser/parts/editor/baseEditor'; -import {EditorInput} from 'vs/workbench/common/editor'; -import {MarkdownEditorInput} from 'vs/workbench/parts/markdown/common/markdownEditorInput'; -import {MarkdownFileTracker} from 'vs/workbench/parts/markdown/browser/markdownExtension'; -import {IWorkbenchContributionsRegistry, Extensions as WorkbenchExtensions} from 'vs/workbench/common/contributions'; -import {IInstantiationService} from 'vs/platform/instantiation/common/instantiation'; - -// Register Editor Input Factory -class MarkdownInputFactory implements IEditorInputFactory { - - constructor() {} - - public serialize(editorInput: EditorInput): string { - let markdownInput = editorInput; - - return markdownInput.getResource().toString(); - } - - public deserialize(instantiationService: IInstantiationService, resourceRaw: string): EditorInput { - return instantiationService.createInstance(MarkdownEditorInput, URI.parse(resourceRaw), void 0, void 0); - } -} - -(Registry.as(EditorExtensions.Editors)).registerEditorInputFactory(MarkdownEditorInput.ID, MarkdownInputFactory); - -// Register Markdown File Tracker -(Registry.as(WorkbenchExtensions.Workbench)).registerWorkbenchContribution( - MarkdownFileTracker -); \ No newline at end of file diff --git a/src/vs/workbench/parts/markdown/browser/markdownActions.contribution.ts b/src/vs/workbench/parts/markdown/browser/markdownActions.contribution.ts deleted file mode 100644 index e91f579bdeb..00000000000 --- a/src/vs/workbench/parts/markdown/browser/markdownActions.contribution.ts +++ /dev/null @@ -1,114 +0,0 @@ -/*--------------------------------------------------------------------------------------------- - * Copyright (c) Microsoft Corporation. All rights reserved. - * Licensed under the MIT License. See License.txt in the project root for license information. - *--------------------------------------------------------------------------------------------*/ - -'use strict'; - -import nls = require('vs/nls'); -import {Registry} from 'vs/platform/platform'; -import {IAction} from 'vs/base/common/actions'; -import {SyncActionDescriptor} from 'vs/platform/actions/common/actions'; -import {Scope, IActionBarRegistry, Extensions as ActionBarExtensions, ActionBarContributor} from 'vs/workbench/browser/actionBarRegistry'; -import {asFileResource, FileEditorInput} from 'vs/workbench/parts/files/common/files'; -import mime = require('vs/base/common/mime'); -import {IEditorInputActionContext, IEditorInputAction, EditorInputActionContributor} from 'vs/workbench/browser/parts/editor/baseEditor'; -import {OpenPreviewToSideAction, GlobalTogglePreviewMarkdownAction, PreviewMarkdownEditorInputAction, PreviewMarkdownAction} from 'vs/workbench/parts/markdown/browser/markdownActions'; -import {MARKDOWN_MIME} from 'vs/workbench/parts/markdown/common/markdown'; -import {IWorkbenchActionRegistry, Extensions as ActionExtensions} from 'vs/workbench/common/actionRegistry'; -import {IInstantiationService} from 'vs/platform/instantiation/common/instantiation'; -import {KeyMod, KeyCode} from 'vs/base/common/keyCodes'; - -class ExplorerViewerActionContributor extends ActionBarContributor { - - constructor(@IInstantiationService private instantiationService: IInstantiationService) { - super(); - } - - public hasSecondaryActions(context: any): boolean { - let element = context.element; - - // Contribute only on file resources - let fileResource = asFileResource(element); - if (!fileResource) { - return false; - } - - return !fileResource.isDirectory && mime.guessMimeTypes(fileResource.resource.fsPath).indexOf(MARKDOWN_MIME) >= 0; - } - - public getSecondaryActions(context: any): IAction[] { - let actions: IAction[] = []; - - if (this.hasSecondaryActions(context)) { - let fileResource = asFileResource(context.element); - - // Open Markdown - let action = this.instantiationService.createInstance(PreviewMarkdownAction, fileResource.resource); - action.order = 0; // on top of other actions - actions.push(action); - } - - return actions; - } -} - -class MarkdownFilesActionContributor extends EditorInputActionContributor { - - constructor(@IInstantiationService private instantiationService: IInstantiationService) { - super(); - } - - /* We override toId() to make the caching of actions based on the mime of the input if given */ - protected toId(context: IEditorInputActionContext): string { - let id = super.toId(context); - - let mime = this.getMimeFromContext(context); - if (mime) { - id += mime; - } - - return id; - } - - private getMimeFromContext(context: IEditorInputActionContext): string { - if (context && context.input && context.input instanceof FileEditorInput) { - let fileInput = context.input; - return fileInput.getMime(); - } - - return null; - } - - public hasActionsForEditorInput(context: IEditorInputActionContext): boolean { - const input = context.input; - if (input instanceof FileEditorInput) { - const fileResource = input.getResource(); - - return mime.guessMimeTypes(fileResource.fsPath).indexOf(MARKDOWN_MIME) >= 0; - } - - return false; - } - - public getActionsForEditorInput(context: IEditorInputActionContext): IEditorInputAction[] { - if (this.hasActionsForEditorInput(context)) { - return [ - this.instantiationService.createInstance(PreviewMarkdownEditorInputAction) - ]; - } - - return []; - } -} - -// Contribute to viewers and editors of markdown files -let actionBarRegistry = Registry.as(ActionBarExtensions.Actionbar); -actionBarRegistry.registerActionBarContributor(Scope.VIEWER, ExplorerViewerActionContributor); -actionBarRegistry.registerActionBarContributor(Scope.EDITOR, MarkdownFilesActionContributor); - -let category = nls.localize('markdown', "Markdown"); - -let workbenchActionsRegistry = Registry.as(ActionExtensions.WorkbenchActions); -workbenchActionsRegistry.registerWorkbenchAction(new SyncActionDescriptor(GlobalTogglePreviewMarkdownAction, GlobalTogglePreviewMarkdownAction.ID, GlobalTogglePreviewMarkdownAction.LABEL, { primary: KeyMod.CtrlCmd | KeyMod.Shift | KeyCode.KEY_V }), 'Markdown: Toggle Preview', category); -workbenchActionsRegistry.registerWorkbenchAction(new SyncActionDescriptor(OpenPreviewToSideAction, OpenPreviewToSideAction.ID, OpenPreviewToSideAction.LABEL, { primary: KeyMod.chord(KeyMod.CtrlCmd | KeyCode.KEY_K, KeyCode.KEY_V) }), 'Markdown: Open Preview to the Side', category); \ No newline at end of file diff --git a/src/vs/workbench/parts/markdown/browser/markdownActions.ts b/src/vs/workbench/parts/markdown/browser/markdownActions.ts deleted file mode 100644 index 5df4b4d0851..00000000000 --- a/src/vs/workbench/parts/markdown/browser/markdownActions.ts +++ /dev/null @@ -1,156 +0,0 @@ -/*--------------------------------------------------------------------------------------------- - * Copyright (c) Microsoft Corporation. All rights reserved. - * Licensed under the MIT License. See License.txt in the project root for license information. - *--------------------------------------------------------------------------------------------*/ - -'use strict'; - -import 'vs/css!./media/markdownactions'; -import {TPromise} from 'vs/base/common/winjs.base'; -import {Action} from 'vs/base/common/actions'; -import URI from 'vs/base/common/uri'; -import errors = require('vs/base/common/errors'); -import nls = require('vs/nls'); -import {FileEditorInput} from 'vs/workbench/parts/files/common/files'; -import {EditorInputAction} from 'vs/workbench/browser/parts/editor/baseEditor'; -import {getUntitledOrFileResource, IEditorContext} from 'vs/workbench/common/editor'; -import {MarkdownEditorInput} from 'vs/workbench/parts/markdown/common/markdownEditorInput'; -import {IWorkbenchEditorService} from 'vs/workbench/services/editor/common/editorService'; -import {IInstantiationService} from 'vs/platform/instantiation/common/instantiation'; -import {IMessageService, Severity} from 'vs/platform/message/common/message'; - -export class GlobalTogglePreviewMarkdownAction extends Action { - - public static ID = 'workbench.action.markdown.togglePreview'; - public static LABEL = nls.localize('toggleMarkdownPreview', "Toggle Preview"); - - constructor( - id: string, - label: string, - @IInstantiationService private instantiationService: IInstantiationService, - @IWorkbenchEditorService private editorService: IWorkbenchEditorService, - @IMessageService private messageService: IMessageService - ) { - super(id, label); - } - - public run(event?: any): TPromise { - let activeInput = this.editorService.getActiveEditorInput(); - - // View source if we are in a markdown file already - if (activeInput instanceof MarkdownEditorInput) { - this.editorService.openEditor({ - resource: activeInput.getResource() - }).done(null, errors.onUnexpectedError); - } - - // Otherwise try to open as markdown preview - else { - let msg: string; - - let resource = getUntitledOrFileResource(activeInput); - if (resource) { - let action = this.instantiationService.createInstance(PreviewMarkdownAction, resource); - action.run().done(() => action.dispose(), errors.onUnexpectedError); - } else { - msg = nls.localize('markdownPreviewNoFile', "Open a Markdown file first to show a preview."); - } - - if (msg) { - this.messageService.show(Severity.Info, msg); - } - } - - - return TPromise.as(true); - } -} - -export class OpenPreviewToSideAction extends Action { - - public static ID = 'workbench.action.markdown.openPreviewSideBySide'; - public static LABEL = nls.localize('openPreviewSideBySide', "Open Preview to the Side"); - - constructor( - id: string, - label: string, - @IInstantiationService private instantiationService: IInstantiationService, - @IWorkbenchEditorService private editorService: IWorkbenchEditorService, - @IMessageService private messageService: IMessageService - ) { - super(id, label); - } - - public run(context?: IEditorContext): TPromise { - let activeInput = this.editorService.getActiveEditorInput(); - - // Do nothing if already in markdown preview - if (activeInput instanceof MarkdownEditorInput) { - return TPromise.as(true); - } - - // Otherwise try to open as markdown preview to the side - else { - let msg: string; - - let resource = getUntitledOrFileResource(activeInput); - if (resource) { - let input = this.instantiationService.createInstance(MarkdownEditorInput, resource, void 0, void 0); - - return this.editorService.openEditor(input, null, true /* to the side */); - } else { - msg = nls.localize('markdownPreviewNoFile', "Open a Markdown file first to show a preview."); - } - - if (msg) { - this.messageService.show(Severity.Info, msg); - } - } - - - return TPromise.as(true); - } -} - -export class PreviewMarkdownAction extends Action { - private markdownResource: URI; - - constructor( - markdownResource: URI, - @IInstantiationService private instantiationService: IInstantiationService, - @IWorkbenchEditorService private editorService: IWorkbenchEditorService - ) { - super('workbench.markdown.action.previewFromExplorer', nls.localize('openPreview', "Open Preview")); - - this.markdownResource = markdownResource; - } - - public run(context?: IEditorContext): TPromise { - let input = this.instantiationService.createInstance(MarkdownEditorInput, this.markdownResource, void 0, void 0); - - return this.editorService.openEditor(input); - } -} - -export class PreviewMarkdownEditorInputAction extends EditorInputAction { - - constructor( - @IInstantiationService private instantiationService: IInstantiationService, - @IWorkbenchEditorService private editorService: IWorkbenchEditorService - ) { - super('workbench.markdown.action.previewFromEditor', nls.localize('openPreview', "Open Preview")); - - this.class = 'markdown-action action-preview'; - this.order = 100; // far end - } - - public run(context: IEditorContext): TPromise { - let input = this.input; - const event = context ? context.event : null; - - let sideBySide = !!(event && (event.ctrlKey || event.metaKey)); - let markdownInput = this.instantiationService.createInstance(MarkdownEditorInput, input.getResource(), void 0, void 0); - - return this.editorService.openEditor(markdownInput, null, sideBySide); - } -} \ No newline at end of file diff --git a/src/vs/workbench/parts/markdown/browser/markdownExtension.ts b/src/vs/workbench/parts/markdown/browser/markdownExtension.ts deleted file mode 100644 index 0c372e37a9c..00000000000 --- a/src/vs/workbench/parts/markdown/browser/markdownExtension.ts +++ /dev/null @@ -1,205 +0,0 @@ -/*--------------------------------------------------------------------------------------------- - * Copyright (c) Microsoft Corporation. All rights reserved. - * Licensed under the MIT License. See License.txt in the project root for license information. - *--------------------------------------------------------------------------------------------*/ -'use strict'; - -import types = require('vs/base/common/types'); -import URI from 'vs/base/common/uri'; -import {EventType} from 'vs/base/common/events'; -import {FileChangeType, FileChangesEvent, EventType as FileEventType} from 'vs/platform/files/common/files'; -import paths = require('vs/base/common/paths'); -import {getBaseThemeId} from 'vs/platform/theme/common/themes'; -import {IWorkbenchContribution} from 'vs/workbench/common/contributions'; -import {IFrameEditor} from 'vs/workbench/browser/parts/editor/iframeEditor'; -import {MarkdownEditorInput} from 'vs/workbench/parts/markdown/common/markdownEditorInput'; -import {IWorkbenchEditorService} from 'vs/workbench/services/editor/common/editorService'; -import {IWorkspaceContextService} from 'vs/workbench/services/workspace/common/contextService'; -import {IConfigurationService, IConfigurationServiceEvent} from 'vs/platform/configuration/common/configuration'; -import {IModelService} from 'vs/editor/common/services/modelService'; -import {IEventService} from 'vs/platform/event/common/event'; -import {IInstantiationService} from 'vs/platform/instantiation/common/instantiation'; -import {IModeService} from 'vs/editor/common/services/modeService'; -import {IThemeService} from 'vs/workbench/services/themes/common/themeService'; -import {IDisposable, dispose} from 'vs/base/common/lifecycle'; -import {IEditorGroupService} from 'vs/workbench/services/group/common/groupService'; - -interface ILanguageConfiguration { - markdown: { - styles: string[]; - }; -} - -// This extension tracks markdown files for changes to update markdown editors and inputs accordingly. -export class MarkdownFileTracker implements IWorkbenchContribution { - - private static RELOAD_MARKDOWN_DELAY = 300; // delay before reloading markdown preview after user typing - - private fileChangeListener: IDisposable; - private configFileChangeListener: IDisposable; - private themeChangeListener: IDisposable; - private editorInputChangeListener: IDisposable; - private markdownConfigurationThumbprint: string; - private markdownConfigurationPaths: string[]; - private reloadTimeout: number; - private hasModelListenerOnResourcePath: { [resource: string]: boolean; }; - - constructor( - @IModeService private modeService: IModeService, - @IEventService private eventService: IEventService, - @IWorkbenchEditorService private editorService: IWorkbenchEditorService, - @IEditorGroupService private editorGroupService: IEditorGroupService, - @IConfigurationService private configurationService: IConfigurationService, - @IWorkspaceContextService private contextService: IWorkspaceContextService, - @IModelService private modelService: IModelService, - @IInstantiationService private instantiationService: IInstantiationService, - @IThemeService private themeService: IThemeService - ) { - this.markdownConfigurationPaths = []; - this.hasModelListenerOnResourcePath = Object.create(null); - - this.configureMode(themeService.getTheme()); - - this.registerListeners(); - } - - private registerListeners(): void { - this.fileChangeListener = this.eventService.addListener2(FileEventType.FILE_CHANGES, (e: FileChangesEvent) => this.onFileChanges(e)); - this.configFileChangeListener = this.configurationService.onDidUpdateConfiguration(e => this.onConfigFileChange(e)); - - // reload markdown editors when their resources change - this.editorInputChangeListener = this.editorGroupService.onEditorsChanged(() => this.onEditorsChanged()); - - // initially read the config for CSS styles in preview - this.readMarkdownConfiguration(this.configurationService.getConfiguration()); - - // listen to theme changes - this.themeChangeListener = this.themeService.onDidThemeChange(themeId => { - this.configureMode(themeId); - this.reloadMarkdownEditors(true); - }); - } - - private onEditorsChanged(): void { - let input = this.editorService.getActiveEditorInput(); - if (input instanceof MarkdownEditorInput) { - let markdownResource = input.getResource(); - let editorModel = this.modelService.getModel(markdownResource); - if (editorModel && !this.hasModelListenerOnResourcePath[markdownResource.toString()]) { - let toUnbind: IDisposable[] = []; - let unbind = () => { - toUnbind = dispose(toUnbind); - - this.hasModelListenerOnResourcePath[markdownResource.toString()] = false; - }; - - // Listen on changes to the underlying resource of the markdown preview - toUnbind.push(editorModel.onDidChangeContent(() => { - if (this.reloadTimeout) { - window.clearTimeout(this.reloadTimeout); - } - - this.reloadTimeout = setTimeout(() => { - if (!this.reloadMarkdownEditors(false, markdownResource)) { - unbind(); - } - }, MarkdownFileTracker.RELOAD_MARKDOWN_DELAY); - })); - - // Mark as being listened - this.hasModelListenerOnResourcePath[markdownResource.toString()] = true; - - // Unbind when input or model gets disposed - toUnbind.push(input.addListener2(EventType.DISPOSE, unbind)); - toUnbind.push(editorModel.onWillDispose(unbind)); - } - } - } - - private configureMode(theme: string): void { - if (theme) { - let baseTheme = getBaseThemeId(theme); - this.modeService.configureMode('text/x-web-markdown', { theme: baseTheme }); - } - } - - public getId(): string { - return 'vs.markdown.filetracker'; - } - - private onConfigFileChange(e: IConfigurationServiceEvent): void { - - // reload markdown editors if styles change - if (this.readMarkdownConfiguration(e.config)) { - this.reloadMarkdownEditors(true); - } - } - - private readMarkdownConfiguration(languageConfiguration: ILanguageConfiguration): boolean { - let oldMarkdownConfigurationThumbprint = this.markdownConfigurationThumbprint; - let newMarkdownConfigurationThumbprint: string; - - // Reset old - this.markdownConfigurationThumbprint = null; - this.markdownConfigurationPaths = []; - - if (languageConfiguration) { - let markdownConfiguration = languageConfiguration.markdown; - if (markdownConfiguration && types.isArray(markdownConfiguration.styles)) { - newMarkdownConfigurationThumbprint = markdownConfiguration.styles.join(''); - - let styles: string[] = markdownConfiguration.styles.map((style: string) => paths.makePosixAbsolute(paths.normalize(style))); - this.markdownConfigurationPaths = styles; - } - } - - // Remember as current - this.markdownConfigurationThumbprint = newMarkdownConfigurationThumbprint; - - return (oldMarkdownConfigurationThumbprint !== newMarkdownConfigurationThumbprint); - } - - private onFileChanges(e: FileChangesEvent): void { - - // If any of the markdown CSS styles have updated, reload all markdown editors - if (this.markdownConfigurationPaths.length && e.containsAny(this.markdownConfigurationPaths.map((p) => this.contextService.toResource(p)), FileChangeType.UPDATED)) { - this.reloadMarkdownEditors(true); - } - } - - private reloadMarkdownEditors(clearIFrame: boolean, resource?: URI): boolean { - let didReload = false; - - let editors = this.editorService.getVisibleEditors(); - editors.forEach((editor) => { - - // Only applicable to markdown editor inputs in iframe editors - let input = editor.input; - if (input instanceof MarkdownEditorInput && editor instanceof IFrameEditor) { - if (!resource || resource.toString() === input.getResource().toString()) { - (editor).reload(clearIFrame); - didReload = true; - } - } - }); - - return didReload; - } - - public dispose(): void { - if (this.fileChangeListener) { - this.fileChangeListener.dispose(); - this.fileChangeListener = null; - } - - if (this.configFileChangeListener) { - this.configFileChangeListener.dispose(); - this.configFileChangeListener = null; - } - - if (this.editorInputChangeListener) { - this.editorInputChangeListener.dispose(); - this.editorInputChangeListener = null; - } - } -} \ No newline at end of file diff --git a/src/vs/workbench/parts/markdown/browser/media/Preview.svg b/src/vs/workbench/parts/markdown/browser/media/Preview.svg deleted file mode 100644 index 000f46386e1..00000000000 --- a/src/vs/workbench/parts/markdown/browser/media/Preview.svg +++ /dev/null @@ -1 +0,0 @@ - \ No newline at end of file diff --git a/src/vs/workbench/parts/markdown/browser/media/Preview_inverse.svg b/src/vs/workbench/parts/markdown/browser/media/Preview_inverse.svg deleted file mode 100644 index 6b95a3a2474..00000000000 --- a/src/vs/workbench/parts/markdown/browser/media/Preview_inverse.svg +++ /dev/null @@ -1 +0,0 @@ - \ No newline at end of file diff --git a/src/vs/workbench/parts/markdown/browser/media/markdownactions.css b/src/vs/workbench/parts/markdown/browser/media/markdownactions.css deleted file mode 100644 index 29cf5d0699f..00000000000 --- a/src/vs/workbench/parts/markdown/browser/media/markdownactions.css +++ /dev/null @@ -1,36 +0,0 @@ -/*--------------------------------------------------------------------------------------------- - * Copyright (c) Microsoft Corporation. All rights reserved. - * Licensed under the MIT License. See License.txt in the project root for license information. - *--------------------------------------------------------------------------------------------*/ - -/* Editor Actions */ - -.vs .monaco-workbench .markdown-action.action-preview { - background: url('Preview.svg') center center no-repeat; -} - -.vs-dark .monaco-workbench .markdown-action.action-preview { - background: url('Preview_inverse.svg') center center no-repeat; -} - -/* High Contrast Theming */ - -.hc-black .monaco-workbench .markdown-action.action-preview, -.hc-black .monaco-workbench .markdown-action.view-source, -.hc-black .monaco-workbench .markdown-action.refresh { - background: none; -} - -.hc-black .monaco-workbench .markdown-action.action-preview:before, -.hc-black .monaco-workbench .markdown-action.view-source:before, -.hc-black .monaco-workbench .markdown-action.refresh:before { - position: absolute; - top: 12px; - left: 8px; - height: 16px; - width: 16px; -} - -.hc-black .monaco-workbench .markdown-action.action-preview:before { - content: url('Preview_inverse.svg'); -} \ No newline at end of file diff --git a/src/vs/workbench/parts/markdown/common/markdown.ts b/src/vs/workbench/parts/markdown/common/markdown.ts deleted file mode 100644 index 1a5c2a93b1b..00000000000 --- a/src/vs/workbench/parts/markdown/common/markdown.ts +++ /dev/null @@ -1,8 +0,0 @@ -/*--------------------------------------------------------------------------------------------- - * Copyright (c) Microsoft Corporation. All rights reserved. - * Licensed under the MIT License. See License.txt in the project root for license information. - *--------------------------------------------------------------------------------------------*/ -'use strict'; - -export const MARKDOWN_MIME = 'text/x-web-markdown'; -export const MARKDOWN_MODE_ID = 'markdown'; \ No newline at end of file diff --git a/src/vs/workbench/parts/markdown/common/markdownEditorInput.ts b/src/vs/workbench/parts/markdown/common/markdownEditorInput.ts deleted file mode 100644 index 7ef61c1327e..00000000000 --- a/src/vs/workbench/parts/markdown/common/markdownEditorInput.ts +++ /dev/null @@ -1,53 +0,0 @@ -/*--------------------------------------------------------------------------------------------- - * Copyright (c) Microsoft Corporation. All rights reserved. - * Licensed under the MIT License. See License.txt in the project root for license information. - *--------------------------------------------------------------------------------------------*/ -'use strict'; - -import nls = require('vs/nls'); -import URI from 'vs/base/common/uri'; -import paths = require('vs/base/common/paths'); -import labels = require('vs/base/common/labels'); -import {IFrameEditorInput} from 'vs/workbench/common/editor/iframeEditorInput'; -import {MarkdownEditorModel} from 'vs/workbench/parts/markdown/common/markdownEditorModel'; -import {EditorModel} from 'vs/workbench/common/editor'; -import {IInstantiationService} from 'vs/platform/instantiation/common/instantiation'; -import {IWorkspaceContextService} from 'vs/platform/workspace/common/workspace'; - -/** - * An editor input to show a rendered version of a markdown file. - */ -export class MarkdownEditorInput extends IFrameEditorInput { - - public static ID: string = 'vs.markdown'; - - constructor( - resource: URI, - label: string, - description: string, - @IInstantiationService private instantiationService: IInstantiationService, - @IWorkspaceContextService private contextService: IWorkspaceContextService - ) { - super(resource, label || nls.localize('preview', "Preview '{0}'", paths.basename(resource.fsPath)), description || labels.getPathLabel(paths.dirname(resource.fsPath), contextService)); - } - - public createNew(resource: URI): MarkdownEditorInput { - return this.instantiationService.createInstance(MarkdownEditorInput, resource, void 0, void 0); - } - - public getTypeId(): string { - return MarkdownEditorInput.ID; - } - - protected createModel(): EditorModel { - return this.instantiationService.createInstance(MarkdownEditorModel, this.getResource()); - } - - public matches(otherInput: any): boolean { - if (!(otherInput instanceof MarkdownEditorInput)) { - return false; - } - - return super.matches(otherInput); - } -} \ No newline at end of file diff --git a/src/vs/workbench/parts/markdown/common/markdownEditorModel.ts b/src/vs/workbench/parts/markdown/common/markdownEditorModel.ts deleted file mode 100644 index 131e7d97340..00000000000 --- a/src/vs/workbench/parts/markdown/common/markdownEditorModel.ts +++ /dev/null @@ -1,104 +0,0 @@ -/*--------------------------------------------------------------------------------------------- - * Copyright (c) Microsoft Corporation. All rights reserved. - * Licensed under the MIT License. See License.txt in the project root for license information. - *--------------------------------------------------------------------------------------------*/ -'use strict'; - -import {TPromise} from 'vs/base/common/winjs.base'; -import nls = require('vs/nls'); -import URI from 'vs/base/common/uri'; -import paths = require('vs/base/common/paths'); -import {IFrameEditorModel} from 'vs/workbench/common/editor/iframeEditorModel'; -import {EditorModel} from 'vs/workbench/common/editor'; -import {IModel} from 'vs/editor/common/editorCommon'; -import {IEmitOutput} from 'vs/editor/common/modes'; -import {isLightTheme} from 'vs/platform/theme/common/themes'; -import {MARKDOWN_MIME, MARKDOWN_MODE_ID} from 'vs/workbench/parts/markdown/common/markdown'; -import {IWorkbenchEditorService} from 'vs/workbench/services/editor/common/editorService'; -import {IThemeService} from 'vs/workbench/services/themes/common/themeService'; -import {IWorkspaceContextService} from 'vs/platform/workspace/common/workspace'; - -interface IMarkdownWorkerOutput extends IEmitOutput { - head: string; - body: string; - tail: string; -} - -/** - * The editor model for markdown inputs. Using a library to convert markdown text into HTML from a resource with the provided path. - */ -export class MarkdownEditorModel extends IFrameEditorModel { - - constructor( - resource: URI, - @IWorkbenchEditorService private editorService: IWorkbenchEditorService, - @IWorkspaceContextService private contextService: IWorkspaceContextService, - @IThemeService private themeService: IThemeService - ) { - super(resource); - } - - public load(): TPromise { - let isCanceled = false; - let codeEditorModel: IModel; - - // Create a new promise here to be able to return this model even in case of an error - return new TPromise((c, e) => { - - // On Error: Show error to user as rendered HTML - let onError = (error: Error) => { - try { - let theme = this.themeService.getTheme(); - let usesLightTheme = isLightTheme(theme); - - let markdownError = nls.localize('markdownError', "Unable to open '{0}' for Markdown rendering. Please make sure the file exists and that it is a valid Markdown file.", paths.basename(this.resource.fsPath)); - this.setContents('', markdownError, ''); - c(this); - } catch (error) { - e(error); // be very careful that this promise always completes - } - }; - - // On Success: Show output as rendered HTML - let onSuccess = (model: IModel) => { - try { - let mode = model.getMode(); - let absoluteWorkerResourcesPath = require.toUrl('vs/languages/markdown/common'); // TODO@Ben technical debt: worker cannot resolve path absolute - if (mode && !!mode.emitOutputSupport && mode.getId() === MARKDOWN_MODE_ID) { - (mode).emitOutputSupport.getEmitOutput(this.resource, absoluteWorkerResourcesPath).then((output: IMarkdownWorkerOutput) => { - this.setContents(output.head, output.body, output.tail); - - c(this); - }, onError); - } else { - onError(null); // mode does not support output - } - } catch (error) { - onError(error); // be very careful that this promise always completes - } - }; - - // Resolve the text editor model using editor service to benefit from the local editor model cache - this.editorService.resolveEditorModel({ - resource: this.resource, - mime: MARKDOWN_MIME - }).then((model) => { - if (isCanceled) { - return; - } - - codeEditorModel = model.textEditorModel; - - return codeEditorModel.whenModeIsReady(); - }).then(() => { - if (isCanceled) { - return; - } - - onSuccess(codeEditorModel); - }, onError); - }, () => { - isCanceled = true; - }); - } -} \ No newline at end of file diff --git a/src/vs/workbench/workbench.main.ts b/src/vs/workbench/workbench.main.ts index 151b2f97767..489914e4be0 100644 --- a/src/vs/workbench/workbench.main.ts +++ b/src/vs/workbench/workbench.main.ts @@ -50,9 +50,6 @@ import 'vs/workbench/parts/output/browser/output.contribution'; import 'vs/workbench/parts/terminal/electron-browser/terminal.contribution'; -// import 'vs/workbench/parts/markdown/browser/markdown.contribution'; -// import 'vs/workbench/parts/markdown/browser/markdownActions.contribution'; - import 'vs/workbench/browser/workbench'; import 'vs/workbench/parts/tasks/electron-browser/task.contribution'; From 9151d223cc495c6052cd20795d60ea80f15fd32f Mon Sep 17 00:00:00 2001 From: Benjamin Pasero Date: Thu, 16 Jun 2016 14:07:29 +0200 Subject: [PATCH 136/217] remove emitOutputSupport --- src/vs/editor/common/modes.ts | 22 ------------------- .../debug/test/node/debugAdapter.test.ts | 2 +- 2 files changed, 1 insertion(+), 23 deletions(-) diff --git a/src/vs/editor/common/modes.ts b/src/vs/editor/common/modes.ts index 515911f0a27..f498798c0ff 100644 --- a/src/vs/editor/common/modes.ts +++ b/src/vs/editor/common/modes.ts @@ -216,12 +216,6 @@ export interface IMode { */ inplaceReplaceSupport?:IInplaceReplaceSupport; - /** - * Optional adapter to support output for a model (e.g. markdown -> html) - * @internal - */ - emitOutputSupport?:IEmitOutputSupport; - /** * Optional adapter to support configuring this mode. * @internal @@ -827,22 +821,6 @@ export interface IInplaceReplaceSupport { navigateValueSet(resource:URI, range:editorCommon.IRange, up:boolean):TPromise; } -/** - * Interface used to get output for a language that supports transformation (e.g. markdown -> html) - * @internal - */ -export interface IEmitOutputSupport { - getEmitOutput(resource:URI):TPromise; -} -/** - * @internal - */ -export interface IEmitOutput { - filename?:string; - content:string; -} - - /** * A link inside the editor. */ diff --git a/src/vs/workbench/parts/debug/test/node/debugAdapter.test.ts b/src/vs/workbench/parts/debug/test/node/debugAdapter.test.ts index ddbbf0c60c6..38a7b767775 100644 --- a/src/vs/workbench/parts/debug/test/node/debugAdapter.test.ts +++ b/src/vs/workbench/parts/debug/test/node/debugAdapter.test.ts @@ -46,7 +46,7 @@ suite('Debug - Adapter', () => { program: 'readme.md' } ] - } + }; setup(() => { adapter = new Adapter(rawAdapter, null, { extensionFolderPath, id: 'adapter', name: 'myAdapter', version: '1.0.0', publisher: 'vscode', isBuiltin: false, engines: null }); From 7ffaba1ba558c6474ac3aa3cd1ff761adcf6d1d4 Mon Sep 17 00:00:00 2001 From: Benjamin Pasero Date: Thu, 16 Jun 2016 14:07:42 +0200 Subject: [PATCH 137/217] fix warning --- extensions/css/server/src/test/scss/scssCompletion.test.ts | 1 - 1 file changed, 1 deletion(-) diff --git a/extensions/css/server/src/test/scss/scssCompletion.test.ts b/extensions/css/server/src/test/scss/scssCompletion.test.ts index a65357da0bb..619336c36a9 100644 --- a/extensions/css/server/src/test/scss/scssCompletion.test.ts +++ b/extensions/css/server/src/test/scss/scssCompletion.test.ts @@ -8,7 +8,6 @@ import * as assert from 'assert'; import {SCSSParser} from '../../parser/scssParser'; import {SCSSCompletion} from '../../services/scssCompletion'; -import * as nodes from '../../parser/cssNodes'; import {TextDocument, Position} from 'vscode-languageserver'; import {assertCompletion, ItemDescription} from '../css/completion.test'; From a5e3e5ee99cc84299d27c7141d5596005d7546ff Mon Sep 17 00:00:00 2001 From: Benjamin Pasero Date: Thu, 16 Jun 2016 14:25:57 +0200 Subject: [PATCH 138/217] simplify open from dnd --- .../parts/editor/sideBySideEditorControl.ts | 25 ++++--------------- 1 file changed, 5 insertions(+), 20 deletions(-) diff --git a/src/vs/workbench/browser/parts/editor/sideBySideEditorControl.ts b/src/vs/workbench/browser/parts/editor/sideBySideEditorControl.ts index 2d2555c4584..4f069876200 100644 --- a/src/vs/workbench/browser/parts/editor/sideBySideEditorControl.ts +++ b/src/vs/workbench/browser/parts/editor/sideBySideEditorControl.ts @@ -7,7 +7,6 @@ import 'vs/css!./media/sidebyside'; import arrays = require('vs/base/common/arrays'); -import {TPromise} from 'vs/base/common/winjs.base'; import Event, {Emitter} from 'vs/base/common/event'; import {StandardMouseEvent} from 'vs/base/browser/mouseEvent'; import types = require('vs/base/common/types'); @@ -17,7 +16,6 @@ import {ProgressBar} from 'vs/base/browser/ui/progressbar/progressbar'; import {BaseEditor} from 'vs/workbench/browser/parts/editor/baseEditor'; import DOM = require('vs/base/browser/dom'); import errors = require('vs/base/common/errors'); -import URI from 'vs/base/common/uri'; import {IWorkbenchEditorService, GroupArrangement} from 'vs/workbench/services/editor/common/editorService'; import {IContextMenuService} from 'vs/platform/contextview/browser/contextView'; import {Position, POSITIONS} from 'vs/platform/editor/common/editor'; @@ -765,7 +763,11 @@ export class SideBySideEditorControl implements ISideBySideEditorControl, IVerti const droppedResources = extractResources(e).filter(r => r.scheme === 'file' || r.scheme === 'untitled'); if (droppedResources.length) { window.focus(); // make sure this window has focus so that the open call reaches the right window! - $this.openFromDrop(droppedResources, position).done(null, errors.onUnexpectedError); + + // Open all + $this.editorService.openEditors(droppedResources.map(resource => { return { input: { resource, options: { pinned: true } }, position }; })) + .then(() => $this.editorGroupService.focusGroup(position)) + .done(null, errors.onUnexpectedError); } } @@ -829,23 +831,6 @@ export class SideBySideEditorControl implements ISideBySideEditorControl, IVerti }); } - private openFromDrop(resources: URI[], position: Position): TPromise { - - // One resource to open: always pick position of the drop - if (resources.length === 1) { - return this.editorService.openEditor({ resource: resources[0], options: { pinned: true } }, position); - } - - // Multiple resources to open with tabs: open them all in target position - const showsTabs = this.configurationService.getConfiguration().workbench.editor.showTabs; - if (showsTabs) { - return this.editorService.openEditors(resources.map(resource => { return { input: { resource, options: { pinned: true } }, position }; })).then(() => this.editorGroupService.focusGroup(position)); - } - - // Multiple resources without tabs: open them side by side - return this.editorService.openEditors(resources.map((resource, index) => { return { input: { resource, options: { pinned: true } }, position: Math.min(index, Position.RIGHT) }; })); - } - private createTitleControl(position: Position): void { const useTabs = !!this.configurationService.getConfiguration().workbench.editor.showTabs; From c89369d4051b0fd1c83237ac59f83b538219f9e5 Mon Sep 17 00:00:00 2001 From: Benjamin Pasero Date: Thu, 16 Jun 2016 14:46:23 +0200 Subject: [PATCH 139/217] handle orphaned dnd overlay --- .../parts/editor/sideBySideEditorControl.ts | 21 +++++++++++++------ 1 file changed, 15 insertions(+), 6 deletions(-) diff --git a/src/vs/workbench/browser/parts/editor/sideBySideEditorControl.ts b/src/vs/workbench/browser/parts/editor/sideBySideEditorControl.ts index 4f069876200..35a004a7ae2 100644 --- a/src/vs/workbench/browser/parts/editor/sideBySideEditorControl.ts +++ b/src/vs/workbench/browser/parts/editor/sideBySideEditorControl.ts @@ -754,11 +754,12 @@ export class SideBySideEditorControl implements ISideBySideEditorControl, IVerti private enableDropTarget(node: HTMLElement): void { const $this = this; + const overlayId = 'monaco-workbench-editor-drop-overlay'; let overlay: Builder; function onDrop(e: DragEvent, position: Position): void { DOM.removeClass(node, 'dropfeedback'); - destroyOverlays(); + destroyOverlay(); const droppedResources = extractResources(e).filter(r => r.scheme === 'file' || r.scheme === 'untitled'); if (droppedResources.length) { @@ -771,7 +772,7 @@ export class SideBySideEditorControl implements ISideBySideEditorControl, IVerti } } - function destroyOverlays(): void { + function destroyOverlay(): void { if (overlay) { overlay.destroy(); overlay = void 0; @@ -789,7 +790,7 @@ export class SideBySideEditorControl implements ISideBySideEditorControl, IVerti width: '100%', height: '100%', zIndex: 3000000 - }).id('monaco-workbench-editor-drop-overlay'); + }).id(overlayId); overlay.appendTo(container); overlay.on(DOM.EventType.DROP, (e: DragEvent) => { @@ -798,7 +799,7 @@ export class SideBySideEditorControl implements ISideBySideEditorControl, IVerti }); overlay.on([DOM.EventType.DRAG_LEAVE, DOM.EventType.DRAG_END], () => { - destroyOverlays(); + destroyOverlay(); }); } }); @@ -814,7 +815,15 @@ export class SideBySideEditorControl implements ISideBySideEditorControl, IVerti // Drag over this.toDispose.push(DOM.addDisposableListener(node, DOM.EventType.DRAG_OVER, (e: DragEvent) => { DOM.addClass(node, 'dropfeedback'); - createOverlay(e.target); + + const target = e.target; + if (target) { + if (overlay && target.id !== overlayId) { + destroyOverlay(); // somehow we managed to move the mouse quickly out of the current overlay, so destroy it + } + + createOverlay(target); + } })); // Drag leave @@ -826,7 +835,7 @@ export class SideBySideEditorControl implements ISideBySideEditorControl, IVerti [node, window].forEach(container => { this.toDispose.push(DOM.addDisposableListener(container, DOM.EventType.DRAG_END, (e: DragEvent) => { DOM.removeClass(node, 'dropfeedback'); - destroyOverlays(); + destroyOverlay(); })); }); } From 705b6bdc7437a48a71e8dd7e6c8af803f367a6ad Mon Sep 17 00:00:00 2001 From: Alex Dima Date: Thu, 16 Jun 2016 14:57:15 +0200 Subject: [PATCH 140/217] Mark optional arguments in editor API --- src/vs/editor/browser/standalone/standaloneEditor.ts | 4 ++-- src/vs/monaco.d.ts | 4 ++-- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/src/vs/editor/browser/standalone/standaloneEditor.ts b/src/vs/editor/browser/standalone/standaloneEditor.ts index 685f0fc3cb9..277b41d54f5 100644 --- a/src/vs/editor/browser/standalone/standaloneEditor.ts +++ b/src/vs/editor/browser/standalone/standaloneEditor.ts @@ -51,7 +51,7 @@ export function setupServices(services: IEditorOverrideServices): IEditorOverrid * `domElement` should be empty (not contain other dom nodes). * The editor will read the size of `domElement`. */ -export function create(domElement:HTMLElement, options:IEditorConstructionOptions, services:IEditorOverrideServices):ICodeEditor { +export function create(domElement:HTMLElement, options?:IEditorConstructionOptions, services?:IEditorOverrideServices):ICodeEditor { startup.initStaticServicesIfNecessary(); services = shallowClone(services); @@ -76,7 +76,7 @@ export function create(domElement:HTMLElement, options:IEditorConstructionOption * `domElement` should be empty (not contain other dom nodes). * The editor will read the size of `domElement`. */ -export function createDiffEditor(domElement:HTMLElement, options:IDiffEditorConstructionOptions, services: IEditorOverrideServices):IDiffEditor { +export function createDiffEditor(domElement:HTMLElement, options?:IDiffEditorConstructionOptions, services?: IEditorOverrideServices):IDiffEditor { startup.initStaticServicesIfNecessary(); services = shallowClone(services); diff --git a/src/vs/monaco.d.ts b/src/vs/monaco.d.ts index e238c559fe8..374c3be8984 100644 --- a/src/vs/monaco.d.ts +++ b/src/vs/monaco.d.ts @@ -752,14 +752,14 @@ declare module monaco.editor { * `domElement` should be empty (not contain other dom nodes). * The editor will read the size of `domElement`. */ - export function create(domElement: HTMLElement, options: IEditorConstructionOptions, services: IEditorOverrideServices): ICodeEditor; + export function create(domElement: HTMLElement, options?: IEditorConstructionOptions, services?: IEditorOverrideServices): ICodeEditor; /** * Create a new diff editor under `domElement`. * `domElement` should be empty (not contain other dom nodes). * The editor will read the size of `domElement`. */ - export function createDiffEditor(domElement: HTMLElement, options: IDiffEditorConstructionOptions, services: IEditorOverrideServices): IDiffEditor; + export function createDiffEditor(domElement: HTMLElement, options?: IDiffEditorConstructionOptions, services?: IEditorOverrideServices): IDiffEditor; /** * Create a new editor model. From f3fea48bddc98d2ad15205d47bce02d246d671fc Mon Sep 17 00:00:00 2001 From: Alex Dima Date: Thu, 16 Jun 2016 14:57:25 +0200 Subject: [PATCH 141/217] Fix configuration service in standalone editor --- src/vs/editor/browser/standalone/simpleServices.ts | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/src/vs/editor/browser/standalone/simpleServices.ts b/src/vs/editor/browser/standalone/simpleServices.ts index d673ee1348f..116ab5bd97d 100644 --- a/src/vs/editor/browser/standalone/simpleServices.ts +++ b/src/vs/editor/browser/standalone/simpleServices.ts @@ -25,6 +25,7 @@ import {IWorkspaceContextService} from 'vs/platform/workspace/common/workspace'; import * as editorCommon from 'vs/editor/common/editorCommon'; import {ICodeEditor, IDiffEditor} from 'vs/editor/browser/editorBrowser'; import {Selection} from 'vs/editor/common/core/selection'; +import {IEventService} from 'vs/platform/event/common/event'; export class SimpleEditor implements IEditor { @@ -281,6 +282,11 @@ export class SimpleExtensionService extends AbstractExtensionService { return TPromise.as(resources.map((resource) => { return { From a403b5269c7ab5b0f241aabbeb478fcda6821162 Mon Sep 17 00:00:00 2001 From: Alex Dima Date: Thu, 16 Jun 2016 14:57:41 +0200 Subject: [PATCH 142/217] standalone editor version bump --- build/monaco/package.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/build/monaco/package.json b/build/monaco/package.json index 98eaf317c1e..8cbf0f8435b 100644 --- a/build/monaco/package.json +++ b/build/monaco/package.json @@ -1,7 +1,7 @@ { "name": "monaco-editor-core", "private": true, - "version": "0.4.0", + "version": "0.4.1", "description": "A browser based code editor", "author": "Microsoft Corporation", "license": "MIT", From f28b05903764fce673c084bf515eff3bc92da809 Mon Sep 17 00:00:00 2001 From: Benjamin Pasero Date: Thu, 16 Jun 2016 15:18:12 +0200 Subject: [PATCH 143/217] support dnd from tab into editor area --- .../parts/editor/sideBySideEditorControl.ts | 33 ++++++++++++++----- .../browser/parts/editor/tabsTitleControl.ts | 33 ++++++++++--------- .../browser/parts/editor/titleControl.ts | 15 +++++++++ 3 files changed, 58 insertions(+), 23 deletions(-) diff --git a/src/vs/workbench/browser/parts/editor/sideBySideEditorControl.ts b/src/vs/workbench/browser/parts/editor/sideBySideEditorControl.ts index 35a004a7ae2..6c4423d9d67 100644 --- a/src/vs/workbench/browser/parts/editor/sideBySideEditorControl.ts +++ b/src/vs/workbench/browser/parts/editor/sideBySideEditorControl.ts @@ -16,6 +16,7 @@ import {ProgressBar} from 'vs/base/browser/ui/progressbar/progressbar'; import {BaseEditor} from 'vs/workbench/browser/parts/editor/baseEditor'; import DOM = require('vs/base/browser/dom'); import errors = require('vs/base/common/errors'); +import {isMacintosh} from 'vs/base/common/platform'; import {IWorkbenchEditorService, GroupArrangement} from 'vs/workbench/services/editor/common/editorService'; import {IContextMenuService} from 'vs/platform/contextview/browser/contextView'; import {Position, POSITIONS} from 'vs/platform/editor/common/editor'; @@ -29,8 +30,9 @@ import {IKeybindingService} from 'vs/platform/keybinding/common/keybindingServic import {IExtensionService} from 'vs/platform/extensions/common/extensions'; import {IDisposable, dispose} from 'vs/base/common/lifecycle'; import {TabsTitleControl} from 'vs/workbench/browser/parts/editor/tabsTitleControl'; +import {TitleControl} from 'vs/workbench/browser/parts/editor/titleControl'; import {NoTabsTitleControl} from 'vs/workbench/browser/parts/editor/noTabsTitleControl'; -import {IEditorStacksModel, IStacksModelChangeEvent, IWorkbenchEditorConfiguration} from 'vs/workbench/common/editor'; +import {IEditorStacksModel, IStacksModelChangeEvent, IWorkbenchEditorConfiguration, EditorOptions} from 'vs/workbench/common/editor'; import {ITitleAreaControl} from 'vs/workbench/browser/parts/editor/titleControl'; import {extractResources} from 'vs/base/browser/dnd'; @@ -761,14 +763,29 @@ export class SideBySideEditorControl implements ISideBySideEditorControl, IVerti DOM.removeClass(node, 'dropfeedback'); destroyOverlay(); - const droppedResources = extractResources(e).filter(r => r.scheme === 'file' || r.scheme === 'untitled'); - if (droppedResources.length) { - window.focus(); // make sure this window has focus so that the open call reaches the right window! + // Check for transfer from title control + const draggedEditor = TitleControl.getDraggedEditor(); + if (draggedEditor) { + const isCopy = (e.ctrlKey && !isMacintosh) || (e.altKey && isMacintosh); + if (isCopy) { + $this.editorService.openEditor(draggedEditor.editor, EditorOptions.create({ pinned: true }), position).done(null, errors.onUnexpectedError); + } else { + const sourcePosition = $this.stacks.positionOfGroup(draggedEditor.group); + $this.editorGroupService.moveEditor(draggedEditor.editor, sourcePosition, position); + } + } - // Open all - $this.editorService.openEditors(droppedResources.map(resource => { return { input: { resource, options: { pinned: true } }, position }; })) - .then(() => $this.editorGroupService.focusGroup(position)) - .done(null, errors.onUnexpectedError); + // Check for URI transfer + else { + const droppedResources = extractResources(e).filter(r => r.scheme === 'file' || r.scheme === 'untitled'); + if (droppedResources.length) { + window.focus(); // make sure this window has focus so that the open call reaches the right window! + + // Open all + $this.editorService.openEditors(droppedResources.map(resource => { return { input: { resource, options: { pinned: true } }, position }; })) + .then(() => $this.editorGroupService.focusGroup(position)) + .done(null, errors.onUnexpectedError); + } } } diff --git a/src/vs/workbench/browser/parts/editor/tabsTitleControl.ts b/src/vs/workbench/browser/parts/editor/tabsTitleControl.ts index ff9d2326f29..1749369bdbe 100644 --- a/src/vs/workbench/browser/parts/editor/tabsTitleControl.ts +++ b/src/vs/workbench/browser/parts/editor/tabsTitleControl.ts @@ -35,9 +35,6 @@ import {ScrollbarVisibility} from 'vs/base/browser/ui/scrollbar/scrollableElemen import {extractResources} from 'vs/base/browser/dnd'; export class TabsTitleControl extends TitleControl { - - private static draggedEditor: IEditorIdentifier; - private titleContainer: HTMLElement; private tabsContainer: HTMLElement; private activeTab: HTMLElement; @@ -127,20 +124,23 @@ export class TabsTitleControl extends TitleControl { const targetIndex = group.count; // Local DND - if (TabsTitleControl.draggedEditor) { + const draggedEditor = TitleControl.getDraggedEditor(); + if (draggedEditor) { DOM.EventHelper.stop(e, true); - const sourcePosition = this.stacks.positionOfGroup(TabsTitleControl.draggedEditor.group); + const sourcePosition = this.stacks.positionOfGroup(draggedEditor.group); // Move editor to target position and index - if (this.isMoveOperation(e, TabsTitleControl.draggedEditor.group, group)) { - this.editorGroupService.moveEditor(TabsTitleControl.draggedEditor.editor, sourcePosition, targetPosition, targetIndex); + if (this.isMoveOperation(e, draggedEditor.group, group)) { + this.editorGroupService.moveEditor(draggedEditor.editor, sourcePosition, targetPosition, targetIndex); } // Copy: just open editor at target index else { - this.editorService.openEditor(TabsTitleControl.draggedEditor.editor, EditorOptions.create({ pinned: true, index: targetIndex }), targetPosition).done(null, errors.onUnexpectedError); + this.editorService.openEditor(draggedEditor.editor, EditorOptions.create({ pinned: true, index: targetIndex }), targetPosition).done(null, errors.onUnexpectedError); } + + this.onEditorDragEnd(); } // External DND @@ -416,7 +416,7 @@ export class TabsTitleControl extends TitleControl { // Drag start this.tabDisposeables.push(DOM.addDisposableListener(tab, DOM.EventType.DRAG_START, (e: DragEvent) => { DOM.addClass(tab, 'dragged'); - TabsTitleControl.draggedEditor = { editor, group }; + this.onEditorDragStart({ editor, group }); e.dataTransfer.effectAllowed = 'copyMove'; // Enable support to drag a file to desktop @@ -440,7 +440,7 @@ export class TabsTitleControl extends TitleControl { this.tabDisposeables.push(DOM.addDisposableListener(tab, DOM.EventType.DRAG_END, (e: DragEvent) => { DOM.removeClass(tab, 'dragged'); DOM.removeClass(tab, 'dropfeedback'); - TabsTitleControl.draggedEditor = void 0; + this.onEditorDragEnd(); })); // Drop @@ -449,20 +449,23 @@ export class TabsTitleControl extends TitleControl { const targetIndex = group.indexOf(editor); // Local DND - if (TabsTitleControl.draggedEditor) { + const draggedEditor = TabsTitleControl.getDraggedEditor(); + if (draggedEditor) { DOM.EventHelper.stop(e, true); - const sourcePosition = this.stacks.positionOfGroup(TabsTitleControl.draggedEditor.group); + const sourcePosition = this.stacks.positionOfGroup(draggedEditor.group); // Move editor to target position and index - if (this.isMoveOperation(e, TabsTitleControl.draggedEditor.group, group)) { - this.editorGroupService.moveEditor(TabsTitleControl.draggedEditor.editor, sourcePosition, targetPosition, targetIndex); + if (this.isMoveOperation(e, draggedEditor.group, group)) { + this.editorGroupService.moveEditor(draggedEditor.editor, sourcePosition, targetPosition, targetIndex); } // Copy: just open editor at target index else { - this.editorService.openEditor(TabsTitleControl.draggedEditor.editor, EditorOptions.create({ pinned: true, index: targetIndex }), targetPosition).done(null, errors.onUnexpectedError); + this.editorService.openEditor(draggedEditor.editor, EditorOptions.create({ pinned: true, index: targetIndex }), targetPosition).done(null, errors.onUnexpectedError); } + + this.onEditorDragEnd(); } // External DND diff --git a/src/vs/workbench/browser/parts/editor/titleControl.ts b/src/vs/workbench/browser/parts/editor/titleControl.ts index 834d233657e..789fb025af6 100644 --- a/src/vs/workbench/browser/parts/editor/titleControl.ts +++ b/src/vs/workbench/browser/parts/editor/titleControl.ts @@ -51,6 +51,9 @@ export interface ITitleAreaControl { } export abstract class TitleControl { + + private static draggedEditor: IEditorIdentifier; + protected stacks: IEditorStacksModel; protected context: IEditorGroup; protected toDispose: IDisposable[]; @@ -98,6 +101,18 @@ export abstract class TitleControl { this.registerListeners(); } + public static getDraggedEditor(): IEditorIdentifier { + return TitleControl.draggedEditor; + } + + protected onEditorDragStart(editor: IEditorIdentifier): void { + TitleControl.draggedEditor = editor; + } + + protected onEditorDragEnd(): void { + TitleControl.draggedEditor = void 0; + } + private registerListeners(): void { this.toDispose.push(this.configurationService.onDidUpdateConfiguration(e => this.onConfigurationUpdated(e.config))); } From cece7cef2c785f22961269725ff679b1554eb306 Mon Sep 17 00:00:00 2001 From: Benjamin Pasero Date: Thu, 16 Jun 2016 15:39:57 +0200 Subject: [PATCH 144/217] overlay tweak when tabs disabled --- .../workbench/browser/parts/editor/sideBySideEditorControl.ts | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/src/vs/workbench/browser/parts/editor/sideBySideEditorControl.ts b/src/vs/workbench/browser/parts/editor/sideBySideEditorControl.ts index 6c4423d9d67..2dc74ae75aa 100644 --- a/src/vs/workbench/browser/parts/editor/sideBySideEditorControl.ts +++ b/src/vs/workbench/browser/parts/editor/sideBySideEditorControl.ts @@ -800,9 +800,11 @@ export class SideBySideEditorControl implements ISideBySideEditorControl, IVerti if (!overlay) { $this.visibleEditorContainers.forEach((container, index) => { if (container && DOM.isAncestor(target, container.getHTMLElement())) { + const useTabs = !!$this.configurationService.getConfiguration().workbench.editor.showTabs; + overlay = $('div').style({ position: 'absolute', - top: SideBySideEditorControl.EDITOR_TITLE_HEIGHT + 'px', + top: useTabs ? SideBySideEditorControl.EDITOR_TITLE_HEIGHT + 'px' : 0, left: 0, width: '100%', height: '100%', From e8f9e12fd8c54771cd4c7c3250c499226e77ade3 Mon Sep 17 00:00:00 2001 From: Benjamin Pasero Date: Thu, 16 Jun 2016 15:42:08 +0200 Subject: [PATCH 145/217] fix tests --- .../test/common/editor/editorStacksModel.test.ts | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/src/vs/workbench/test/common/editor/editorStacksModel.test.ts b/src/vs/workbench/test/common/editor/editorStacksModel.test.ts index c4061070cd0..28864d6f511 100644 --- a/src/vs/workbench/test/common/editor/editorStacksModel.test.ts +++ b/src/vs/workbench/test/common/editor/editorStacksModel.test.ts @@ -29,7 +29,7 @@ function create(): EditorStacksModel { services.set(IWorkspaceContextService, new TestContextService()); const config = new TestConfigurationService(); - config.setUserConfiguration('workbench', { editorOpenPositioning: 'right' }); + config.setUserConfiguration('workbench', { editor: { openPositioning: 'right' }}); services.set(IConfigurationService, config); let inst = new InstantiationService(services); @@ -599,7 +599,7 @@ suite('Editor Stacks Model', () => { const config = new TestConfigurationService(); services.set(IConfigurationService, config); - config.setUserConfiguration('workbench', { editorOpenPositioning: 'left' }); + config.setUserConfiguration('workbench', { editor: { openPositioning: 'left' }}); let inst = new InstantiationService(services); @@ -1132,7 +1132,7 @@ suite('Editor Stacks Model', () => { const lifecycle = new TestLifecycleService(); services.set(ILifecycleService, lifecycle); const config = new TestConfigurationService(); - config.setUserConfiguration('workbench', { editorOpenPositioning: 'right' }); + config.setUserConfiguration('workbench', { editor: { openPositioning: 'right' }}); services.set(IConfigurationService, config); let inst = new InstantiationService(services); @@ -1176,7 +1176,7 @@ suite('Editor Stacks Model', () => { const lifecycle = new TestLifecycleService(); services.set(ILifecycleService, lifecycle); const config = new TestConfigurationService(); - config.setUserConfiguration('workbench', { editorOpenPositioning: 'right' }); + config.setUserConfiguration('workbench', { editor: { openPositioning: 'right' }}); services.set(IConfigurationService, config); let inst = new InstantiationService(services); @@ -1258,7 +1258,7 @@ suite('Editor Stacks Model', () => { const lifecycle = new TestLifecycleService(); services.set(ILifecycleService, lifecycle); const config = new TestConfigurationService(); - config.setUserConfiguration('workbench', { editorOpenPositioning: 'right' }); + config.setUserConfiguration('workbench', { editor: { openPositioning: 'right' }}); services.set(IConfigurationService, config); let inst = new InstantiationService(services); @@ -1308,7 +1308,7 @@ suite('Editor Stacks Model', () => { const lifecycle = new TestLifecycleService(); services.set(ILifecycleService, lifecycle); const config = new TestConfigurationService(); - config.setUserConfiguration('workbench', { editorOpenPositioning: 'right' }); + config.setUserConfiguration('workbench', { editor: { openPositioning: 'right' }}); services.set(IConfigurationService, config); let inst = new InstantiationService(services); @@ -1350,7 +1350,7 @@ suite('Editor Stacks Model', () => { const lifecycle = new TestLifecycleService(); services.set(ILifecycleService, lifecycle); const config = new TestConfigurationService(); - config.setUserConfiguration('workbench', { editorOpenPositioning: 'right' }); + config.setUserConfiguration('workbench', { editor: { openPositioning: 'right' }}); services.set(IConfigurationService, config); let inst = new InstantiationService(services); From 28ffb39e390661f2e17c274e7a77c14c9ee54d3a Mon Sep 17 00:00:00 2001 From: Benjamin Pasero Date: Thu, 16 Jun 2016 15:51:33 +0200 Subject: [PATCH 146/217] log workbench editor config to telemetry --- src/vs/workbench/browser/parts/editor/editorPart.ts | 5 ++++- src/vs/workbench/browser/workbench.ts | 8 +------- src/vs/workbench/electron-browser/shell.ts | 4 ++-- src/vs/workbench/parts/files/browser/textFileServices.ts | 1 - 4 files changed, 7 insertions(+), 11 deletions(-) diff --git a/src/vs/workbench/browser/parts/editor/editorPart.ts b/src/vs/workbench/browser/parts/editor/editorPart.ts index 0897b7283d2..65698c97df7 100644 --- a/src/vs/workbench/browser/parts/editor/editorPart.ts +++ b/src/vs/workbench/browser/parts/editor/editorPart.ts @@ -128,7 +128,10 @@ export class EditorPart extends Part implements IEditorPart, IEditorGroupService this.stacks = this.instantiationService.createInstance(EditorStacksModel); - this.previewEditors = configurationService.getConfiguration().workbench.editor.enablePreview; + const editorConfig = configurationService.getConfiguration().workbench.editor; + this.previewEditors = editorConfig.enablePreview; + + this.telemetryService.publicLog('workbenchEditorConfiguration', editorConfig); this.registerListeners(); } diff --git a/src/vs/workbench/browser/workbench.ts b/src/vs/workbench/browser/workbench.ts index 91fcca6568e..a8e8ea11622 100644 --- a/src/vs/workbench/browser/workbench.ts +++ b/src/vs/workbench/browser/workbench.ts @@ -48,9 +48,7 @@ import {WorkbenchKeybindingService} from 'vs/workbench/services/keybinding/elect import {IWorkspace, IConfiguration} from 'vs/platform/workspace/common/workspace'; import {IKeybindingService} from 'vs/platform/keybinding/common/keybindingService'; import {IActivityService} from 'vs/workbench/services/activity/common/activityService'; -import {IExtensionService} from 'vs/platform/extensions/common/extensions'; import {IViewletService} from 'vs/workbench/services/viewlet/common/viewletService'; -import {IConfigurationService} from 'vs/platform/configuration/common/configuration'; import {IPanelService} from 'vs/workbench/services/panel/common/panelService'; import {WorkbenchMessageService} from 'vs/workbench/services/message/browser/messageService'; import {IWorkbenchEditorService} from 'vs/workbench/services/editor/common/editorService'; @@ -62,7 +60,6 @@ import {IInstantiationService} from 'vs/platform/instantiation/common/instantiat import {ServiceCollection} from 'vs/platform/instantiation/common/serviceCollection'; import {ILifecycleService} from 'vs/platform/lifecycle/common/lifecycle'; import {IMessageService} from 'vs/platform/message/common/message'; -import {ITelemetryService} from 'vs/platform/telemetry/common/telemetry'; import {IThreadService} from 'vs/platform/thread/common/thread'; import {MainThreadService} from 'vs/platform/thread/common/mainThreadService'; import {IStatusbarService} from 'vs/platform/statusbar/common/statusbar'; @@ -129,15 +126,12 @@ export class Workbench implements IPartService { serviceCollection: ServiceCollection, @IInstantiationService private instantiationService: IInstantiationService, @IUntitledEditorService private untitledEditorService: IUntitledEditorService, - @IConfigurationService private configurationService: IConfigurationService, @IEventService private eventService: IEventService, @IWorkbenchWorkspaceContextService private contextService: IWorkbenchWorkspaceContextService, @IStorageService private storageService: IStorageService, - @ITelemetryService private telemetryService: ITelemetryService, @ILifecycleService private lifecycleService: ILifecycleService, @IMessageService private messageService: IMessageService, - @IThreadService private threadService: IThreadService, - @IExtensionService private extensionService: IExtensionService + @IThreadService private threadService: IThreadService ) { // Validate params diff --git a/src/vs/workbench/electron-browser/shell.ts b/src/vs/workbench/electron-browser/shell.ts index 909afe86b43..1fe6954a74c 100644 --- a/src/vs/workbench/electron-browser/shell.ts +++ b/src/vs/workbench/electron-browser/shell.ts @@ -20,7 +20,7 @@ import timer = require('vs/base/common/timer'); import {Workbench} from 'vs/workbench/browser/workbench'; import {Storage, inMemoryLocalStorageInstance} from 'vs/workbench/common/storage'; import {ITelemetryService, NullTelemetryService} from 'vs/platform/telemetry/common/telemetry'; -import {ITelemetryAppenderChannel,TelemetryAppenderClient} from 'vs/platform/telemetry/common/telemetryIpc'; +import {ITelemetryAppenderChannel, TelemetryAppenderClient} from 'vs/platform/telemetry/common/telemetryIpc'; import {TelemetryService, ITelemetryServiceConfig} from 'vs/platform/telemetry/common/telemetryService'; import {IdleMonitor, UserStatus} from 'vs/platform/telemetry/browser/idleMonitor'; import ErrorTelemetry from 'vs/platform/telemetry/browser/errorTelemetry'; @@ -244,7 +244,7 @@ export class WorkbenchShell { this.telemetryService.publicLog(status === UserStatus.Active ? TelemetryService.IDLE_STOP_EVENT_NAME : TelemetryService.IDLE_START_EVENT_NAME - )); + )); disposables.add(telemetryService, errorTelemetry, listener, idleMonitor); } else { diff --git a/src/vs/workbench/parts/files/browser/textFileServices.ts b/src/vs/workbench/parts/files/browser/textFileServices.ts index ec4470e98ce..b6d01ba64e4 100644 --- a/src/vs/workbench/parts/files/browser/textFileServices.ts +++ b/src/vs/workbench/parts/files/browser/textFileServices.ts @@ -57,7 +57,6 @@ export abstract class TextFileService implements ITextFileService { const configuration = this.configurationService.getConfiguration(); this.onConfigurationChange(configuration); - // we want to find out about this setting from telemetry this.telemetryService.publicLog('autoSave', this.getAutoSaveConfiguration()); } From e520a4208b364e9cb215677f95bb50b3f7264298 Mon Sep 17 00:00:00 2001 From: Martin Aeschlimann Date: Thu, 16 Jun 2016 15:49:33 +0200 Subject: [PATCH 147/217] fixes #7730: [json] Referencing **local** JSON schema from another local schema --- .../json/server/src/jsonSchemaService.ts | 23 +++-- extensions/json/server/src/jsonServerMain.ts | 7 +- .../json/server/src/test/schema.test.ts | 85 +++++++++++++++---- 3 files changed, 87 insertions(+), 28 deletions(-) diff --git a/extensions/json/server/src/jsonSchemaService.ts b/extensions/json/server/src/jsonSchemaService.ts index 9eccb77c117..60614b7adf8 100644 --- a/extensions/json/server/src/jsonSchemaService.ts +++ b/extensions/json/server/src/jsonSchemaService.ts @@ -128,7 +128,7 @@ class SchemaHandle implements ISchemaHandle { public getResolvedSchema(): Thenable { if (!this.resolvedSchema) { this.resolvedSchema = this.getUnresolvedSchema().then(unresolved => { - return this.service.resolveSchemaContent(unresolved); + return this.service.resolveSchemaContent(unresolved, this.url); }); } return this.resolvedSchema; @@ -357,17 +357,21 @@ export class JSONSchemaService implements IJSONSchemaService { ); } - public resolveSchemaContent(schemaToResolve: UnresolvedSchema): Thenable { + public resolveSchemaContent(schemaToResolve: UnresolvedSchema, schemaURL: string): Thenable { let resolveErrors: string[] = schemaToResolve.errors.slice(0); let schema = schemaToResolve.schema; + let contextService = this.contextService; let findSection = (schema: IJSONSchema, path: string): any => { if (!path) { return schema; } let current: any = schema; - path.substr(1).split('/').some((part) => { + if (path[0] === '/') { + path = path.substr(1); + } + path.split('/').some((part) => { current = current[part]; return !current; }); @@ -388,18 +392,21 @@ export class JSONSchemaService implements IJSONSchemaService { delete node.$ref; }; - let resolveExternalLink = (node: any, uri: string, linkPath: string): Thenable => { + let resolveExternalLink = (node: any, uri: string, linkPath: string, parentSchemaURL: string): Thenable => { + if (contextService && !/^\w+:\/\/.*/.test(uri)) { + uri = contextService.resolveRelativePath(uri, parentSchemaURL); + } return this.getOrAddSchemaHandle(uri).getUnresolvedSchema().then(unresolvedSchema => { if (unresolvedSchema.errors.length) { let loc = linkPath ? uri + '#' + linkPath : uri; resolveErrors.push(localize('json.schema.problemloadingref', 'Problems loading reference \'{0}\': {1}', loc, unresolvedSchema.errors[0])); } resolveLink(node, unresolvedSchema.schema, linkPath); - return resolveRefs(node, unresolvedSchema.schema); + return resolveRefs(node, unresolvedSchema.schema, uri); }); }; - let resolveRefs = (node: IJSONSchema, parentSchema: IJSONSchema): Thenable => { + let resolveRefs = (node: IJSONSchema, parentSchema: IJSONSchema, parentSchemaURL: string): Thenable => { let toWalk : IJSONSchema[] = [node]; let seen: IJSONSchema[] = []; @@ -438,7 +445,7 @@ export class JSONSchemaService implements IJSONSchemaService { if (next.$ref) { let segments = next.$ref.split('#', 2); if (segments[0].length > 0) { - openPromises.push(resolveExternalLink(next, segments[0], segments[1])); + openPromises.push(resolveExternalLink(next, segments[0], segments[1], parentSchemaURL)); continue; } else { resolveLink(next, parentSchema, segments[1]); @@ -451,7 +458,7 @@ export class JSONSchemaService implements IJSONSchemaService { return Promise.all(openPromises); }; - return resolveRefs(schema, schema).then(_ => new ResolvedSchema(schema, resolveErrors)); + return resolveRefs(schema, schema, schemaURL).then(_ => new ResolvedSchema(schema, resolveErrors)); } public getSchemaForResource(resource: string, document: Parser.JSONDocument): Thenable { diff --git a/extensions/json/server/src/jsonServerMain.ts b/extensions/json/server/src/jsonServerMain.ts index 57dfca9c782..fa57e8f72dd 100644 --- a/extensions/json/server/src/jsonServerMain.ts +++ b/extensions/json/server/src/jsonServerMain.ts @@ -13,6 +13,7 @@ import {xhr, XHROptions, XHRResponse, configure as configureHttpRequests} from ' import path = require('path'); import fs = require('fs'); import URI from './utils/uri'; +import * as URL from 'url'; import Strings = require('./utils/strings'); import {ISchemaAssociations} from './jsonSchemaService'; import {JSONDocument} from './jsonParser'; @@ -71,11 +72,7 @@ connection.onInitialize((params: InitializeParams): InitializeResult => { let workspaceContext = { resolveRelativePath: (relativePath: string, resource: string) => { - if (typeof relativePath === 'string' && resource) { - let resourceURI = URI.parse(resource); - return URI.file(path.normalize(path.join(path.dirname(resourceURI.fsPath), relativePath))).toString(); - } - return void 0; + return URL.resolve(resource, relativePath); } }; diff --git a/extensions/json/server/src/test/schema.test.ts b/extensions/json/server/src/test/schema.test.ts index e4388ff8659..b2f145c1fc2 100644 --- a/extensions/json/server/src/test/schema.test.ts +++ b/extensions/json/server/src/test/schema.test.ts @@ -10,6 +10,7 @@ import JsonSchema = require('../jsonSchema'); import Json = require('jsonc-parser'); import Parser = require('../jsonParser'); import fs = require('fs'); +import url = require('url'); import path = require('path'); import {XHROptions, XHRResponse} from 'request-light'; @@ -43,8 +44,14 @@ suite('JSON Schema', () => { return Promise.reject({ responseText: '', status: 404 }); } + let workspaceContext = { + resolveRelativePath: (relativePath: string, resource: string) => { + return url.resolve(resource, relativePath); + } + }; + test('Resolving $refs', function(testDone) { - var service = new SchemaService.JSONSchemaService(requestServiceMock); + var service = new SchemaService.JSONSchemaService(requestServiceMock, workspaceContext); service.setSchemaContributions({ schemas: { "https://myschemastore/main" : { id: 'https://myschemastore/main', @@ -73,9 +80,9 @@ suite('JSON Schema', () => { }); }); - + test('Resolving $refs 2', function(testDone) { - var service = new SchemaService.JSONSchemaService(requestServiceMock); + var service = new SchemaService.JSONSchemaService(requestServiceMock, workspaceContext); service.setSchemaContributions({ schemas: { "http://json.schemastore.org/swagger-2.0" : { id: 'http://json.schemastore.org/swagger-2.0', @@ -112,8 +119,56 @@ suite('JSON Schema', () => { }); + test('Resolving $refs 3', function(testDone) { + var service = new SchemaService.JSONSchemaService(requestServiceMock, workspaceContext); + service.setSchemaContributions({ schemas: { + "https://myschemastore/main/schema1.json" : { + id: 'https://myschemastore/schema1.json', + type: 'object', + properties: { + p1: { + '$ref': 'schema2.json#/definitions/hello' + }, + p2: { + '$ref': './schema2.json#/definitions/hello' + }, + p3: { + '$ref': '/main/schema2.json#/definitions/hello' + } + } + }, + "https://myschemastore/main/schema2.json" :{ + id: 'https://myschemastore/main/schema2.json', + definitions: { + "hello": { + "type": "string", + "enum": [ "object" ], + } + } + } + }}); + + service.getResolvedSchema('https://myschemastore/main/schema1.json').then(fs => { + assert.deepEqual(fs.schema.properties['p1'], { + type: 'string', + enum: [ "object" ] + }); + assert.deepEqual(fs.schema.properties['p2'], { + type: 'string', + enum: [ "object" ] + }); + assert.deepEqual(fs.schema.properties['p3'], { + type: 'string', + enum: [ "object" ] + }); + }).then(() => testDone(), (error) => { + testDone(error); + }); + + }); + test('FileSchema', function(testDone) { - var service = new SchemaService.JSONSchemaService(requestServiceMock); + var service = new SchemaService.JSONSchemaService(requestServiceMock, workspaceContext); service.setSchemaContributions({ schemas: { "main" : { @@ -142,7 +197,7 @@ suite('JSON Schema', () => { }); test('Array FileSchema', function(testDone) { - var service = new SchemaService.JSONSchemaService(requestServiceMock); + var service = new SchemaService.JSONSchemaService(requestServiceMock, workspaceContext); service.setSchemaContributions({ schemas: { "main" : { @@ -174,7 +229,7 @@ suite('JSON Schema', () => { }); test('Missing subschema', function(testDone) { - var service = new SchemaService.JSONSchemaService(requestServiceMock); + var service = new SchemaService.JSONSchemaService(requestServiceMock, workspaceContext); service.setSchemaContributions({ schemas: { "main" : { @@ -197,7 +252,7 @@ suite('JSON Schema', () => { }); test('Preloaded Schema', function(testDone) { - var service = new SchemaService.JSONSchemaService(requestServiceMock); + var service = new SchemaService.JSONSchemaService(requestServiceMock, workspaceContext); var id = 'https://myschemastore/test1'; var schema : JsonSchema.IJSONSchema = { type: 'object', @@ -225,7 +280,7 @@ suite('JSON Schema', () => { }); test('External Schema', function(testDone) { - var service = new SchemaService.JSONSchemaService(requestServiceMock); + var service = new SchemaService.JSONSchemaService(requestServiceMock, workspaceContext); var id = 'https://myschemastore/test1'; var schema : JsonSchema.IJSONSchema = { type: 'object', @@ -254,7 +309,7 @@ suite('JSON Schema', () => { test('Resolving in-line $refs', function (testDone) { - var service = new SchemaService.JSONSchemaService(requestServiceMock); + var service = new SchemaService.JSONSchemaService(requestServiceMock, workspaceContext); var id = 'https://myschemastore/test1'; var schema:JsonSchema.IJSONSchema = { @@ -292,7 +347,7 @@ suite('JSON Schema', () => { }); test('Resolving in-line $refs automatically for external schemas', function(testDone) { - var service = new SchemaService.JSONSchemaService(requestServiceMock); + var service = new SchemaService.JSONSchemaService(requestServiceMock, workspaceContext); var id = 'https://myschemastore/test1'; var schema:JsonSchema.IJSONSchema = { id: 'main', @@ -329,7 +384,7 @@ suite('JSON Schema', () => { test('Clearing External Schemas', function(testDone) { - var service = new SchemaService.JSONSchemaService(requestServiceMock); + var service = new SchemaService.JSONSchemaService(requestServiceMock, workspaceContext); var id1 = 'http://myschemastore/test1'; var schema1:JsonSchema.IJSONSchema = { type: 'object', @@ -370,7 +425,7 @@ suite('JSON Schema', () => { }); test('Schema contributions', function(testDone) { - var service = new SchemaService.JSONSchemaService(requestServiceMock); + var service = new SchemaService.JSONSchemaService(requestServiceMock, workspaceContext); service.setSchemaContributions({ schemas: { "http://myschemastore/myschemabar" : { @@ -420,7 +475,7 @@ suite('JSON Schema', () => { test('Resolving circular $refs', function(testDone) { - var service : SchemaService.IJSONSchemaService = new SchemaService.JSONSchemaService(requestServiceMock); + var service : SchemaService.IJSONSchemaService = new SchemaService.JSONSchemaService(requestServiceMock, workspaceContext); var input = { "$schema": "http://schema.management.azure.com/schemas/2015-01-01/deploymentTemplate.json#", @@ -463,7 +518,7 @@ suite('JSON Schema', () => { test('Resolving circular $refs, invalid document', function(testDone) { - var service : SchemaService.IJSONSchemaService = new SchemaService.JSONSchemaService(requestServiceMock); + var service : SchemaService.IJSONSchemaService = new SchemaService.JSONSchemaService(requestServiceMock, workspaceContext); var input = { "$schema": "http://schema.management.azure.com/schemas/2015-01-01/deploymentTemplate.json#", @@ -498,7 +553,7 @@ suite('JSON Schema', () => { test('Validate Azure Resource Dfinition', function(testDone) { - var service : SchemaService.IJSONSchemaService = new SchemaService.JSONSchemaService(requestServiceMock); + var service : SchemaService.IJSONSchemaService = new SchemaService.JSONSchemaService(requestServiceMock, workspaceContext); var input = { "$schema": "http://schema.management.azure.com/schemas/2015-01-01/deploymentTemplate.json#", From c5429332d4ac326a94a6c5e87fffefcb14d10e84 Mon Sep 17 00:00:00 2001 From: isidor Date: Thu, 16 Jun 2016 16:13:52 +0200 Subject: [PATCH 148/217] debug: editing variable support fixes #7744 --- .../parts/debug/browser/debugViewer.ts | 31 +++++++++++++++---- .../parts/debug/browser/debugViews.ts | 15 +++++++++ src/vs/workbench/parts/debug/common/debug.ts | 5 +++ .../debug/electron-browser/debugActions.ts | 22 +++++++++++++ .../debug/electron-browser/debugService.ts | 12 +++++++ .../parts/debug/node/rawDebugSession.ts | 4 +++ .../debug/test/common/mockDebugService.ts | 4 +++ 7 files changed, 87 insertions(+), 6 deletions(-) diff --git a/src/vs/workbench/parts/debug/browser/debugViewer.ts b/src/vs/workbench/parts/debug/browser/debugViewer.ts index 7d04b40f549..18efc7e919f 100644 --- a/src/vs/workbench/parts/debug/browser/debugViewer.ts +++ b/src/vs/workbench/parts/debug/browser/debugViewer.ts @@ -82,7 +82,8 @@ export function renderVariable(tree: tree.ITree, variable: model.Variable, data: } } -function renderRenameBox(debugService: debug.IDebugService, contextViewService: IContextViewService, tree: tree.ITree, element: any, container: HTMLElement, placeholder: string, ariaLabel: string): void { +function renderRenameBox(debugService: debug.IDebugService, contextViewService: IContextViewService, tree: tree.ITree, element: any, + container: HTMLElement, initialValue: string, placeholder: string, ariaLabel: string): void { let inputBoxContainer = dom.append(container, $('.inputBoxContainer')); let inputBox = new inputbox.InputBox(inputBoxContainer, contextViewService, { validationOptions: { @@ -93,7 +94,7 @@ function renderRenameBox(debugService: debug.IDebugService, contextViewService: ariaLabel: ariaLabel }); - inputBox.value = element.name ? element.name : ''; + inputBox.value = initialValue ? initialValue : ''; inputBox.focus(); let disposed = false; @@ -110,6 +111,10 @@ function renderRenameBox(debugService: debug.IDebugService, contextViewService: debugService.renameFunctionBreakpoint(element.getId(), inputBox.value).done(null, errors.onUnexpectedError); } else if (element instanceof model.FunctionBreakpoint && !element.name) { debugService.removeFunctionBreakpoints(element.getId()).done(null, errors.onUnexpectedError); + } else if (element instanceof model.Variable && renamed) { + debugService.setVariable(element, inputBox.value) + // if everything went fine we need to refresh that tree element since his value updated + .done(() => tree.refresh(element, false), errors.onUnexpectedError); } tree.clearHighlight(); @@ -525,11 +530,13 @@ export class VariablesActionProvider implements renderer.IActionProvider { public getSecondaryActions(tree: tree.ITree, element: any): TPromise { let actions: actions.Action[] = []; const variable = element; - actions.push(this.instantiationService.createInstance(debugactions.AddToWatchExpressionsAction, debugactions.AddToWatchExpressionsAction.ID, debugactions.AddToWatchExpressionsAction.LABEL, variable)); if (variable.reference === 0) { + actions.push(this.instantiationService.createInstance(debugactions.SetValueAction, debugactions.SetValueAction.ID, debugactions.SetValueAction.LABEL, variable)); actions.push(this.instantiationService.createInstance(debugactions.CopyValueAction, debugactions.CopyValueAction.ID, debugactions.CopyValueAction.LABEL, variable)); + actions.push(new actionbar.Separator()); } + actions.push(this.instantiationService.createInstance(debugactions.AddToWatchExpressionsAction, debugactions.AddToWatchExpressionsAction.ID, debugactions.AddToWatchExpressionsAction.LABEL, variable)); return TPromise.as(actions); } @@ -587,6 +594,13 @@ export class VariablesRenderer implements tree.IRenderer { private static SCOPE_TEMPLATE_ID = 'scope'; private static VARIABLE_TEMPLATE_ID = 'variable'; + constructor( + @debug.IDebugService private debugService: debug.IDebugService, + @IContextViewService private contextViewService: IContextViewService + ) { + // noop + } + public getHeight(tree: tree.ITree, element: any): number { return 22; } @@ -622,7 +636,12 @@ export class VariablesRenderer implements tree.IRenderer { if (templateId === VariablesRenderer.SCOPE_TEMPLATE_ID) { this.renderScope(element, templateData); } else { - renderVariable(tree, element, templateData, true); + if (element === this.debugService.getViewModel().getSelectedExpression()) { + renderRenameBox(this.debugService, this.contextViewService, tree, element, (templateData).expression, + (element).value, null, nls.localize('variableValueAriaLabel', "Type new variable value")); + } else { + renderVariable(tree, element, templateData, true); + } } } @@ -798,7 +817,7 @@ export class WatchExpressionsRenderer implements tree.IRenderer { private renderWatchExpression(tree: tree.ITree, watchExpression: debug.IExpression, data: IWatchExpressionTemplateData): void { let selectedExpression = this.debugService.getViewModel().getSelectedExpression(); if ((selectedExpression instanceof model.Expression && selectedExpression.getId() === watchExpression.getId()) || (watchExpression instanceof model.Expression && !watchExpression.name)) { - renderRenameBox(this.debugService, this.contextViewService, tree, watchExpression, data.expression, nls.localize('watchExpressionPlaceholder', "Expression to watch"), nls.localize('watchExpressionInputAriaLabel', "Type watch expression")); + renderRenameBox(this.debugService, this.contextViewService, tree, watchExpression, data.expression, watchExpression.name, nls.localize('watchExpressionPlaceholder', "Expression to watch"), nls.localize('watchExpressionInputAriaLabel', "Type watch expression")); } data.actionBar.context = watchExpression; @@ -1071,7 +1090,7 @@ export class BreakpointsRenderer implements tree.IRenderer { private renderFunctionBreakpoint(tree: tree.ITree, functionBreakpoint: debug.IFunctionBreakpoint, data: IFunctionBreakpointTemplateData): void { const selected = this.debugService.getViewModel().getSelectedFunctionBreakpoint(); if (!functionBreakpoint.name || (selected && selected.getId() === functionBreakpoint.getId())) { - renderRenameBox(this.debugService, this.contextViewService, tree, functionBreakpoint, data.breakpoint, nls.localize('functionBreakpointPlaceholder', "Function to break on"), nls.localize('functionBreakPointInputAriaLabel', "Type function breakpoint")); + renderRenameBox(this.debugService, this.contextViewService, tree, functionBreakpoint, data.breakpoint, functionBreakpoint.name, nls.localize('functionBreakpointPlaceholder', "Function to break on"), nls.localize('functionBreakPointInputAriaLabel', "Type function breakpoint")); } else { this.debugService.getModel().areBreakpointsActivated() ? tree.removeTraits('disabled', [functionBreakpoint]) : tree.addTraits('disabled', [functionBreakpoint]); data.name.textContent = functionBreakpoint.name; diff --git a/src/vs/workbench/parts/debug/browser/debugViews.ts b/src/vs/workbench/parts/debug/browser/debugViews.ts index a453566c715..6bc164fb0a6 100644 --- a/src/vs/workbench/parts/debug/browser/debugViews.ts +++ b/src/vs/workbench/parts/debug/browser/debugViews.ts @@ -98,6 +98,21 @@ export class VariablesView extends viewlet.CollapsibleViewletView { this.telemetryService.publicLog('debug/variables/selected'); } })); + + this.toDispose.push(this.debugService.getViewModel().onDidSelectExpression(expression => { + if (!expression || !(expression instanceof Variable)) { + return; + } + + this.tree.refresh(expression, false).then(() => { + this.tree.setHighlight(expression); + this.tree.addOneTimeDisposableListener(events.EventType.HIGHLIGHT, (e: tree.IHighlightEvent) => { + if (!e.highlight) { + this.debugService.getViewModel().setSelectedExpression(null); + } + }); + }).done(null, errors.onUnexpectedError); + })); } private onFocusStackFrame(stackFrame: debug.IStackFrame): void { diff --git a/src/vs/workbench/parts/debug/common/debug.ts b/src/vs/workbench/parts/debug/common/debug.ts index ce74fb5c4f7..9e9346d9e0e 100644 --- a/src/vs/workbench/parts/debug/common/debug.ts +++ b/src/vs/workbench/parts/debug/common/debug.ts @@ -358,6 +358,11 @@ export interface IDebugService { */ appendReplOutput(value: string, severity?: severity): void; + /** + * Sets the value for the variable against the debug adapter. + */ + setVariable(variable: IExpression, value: string): TPromise; + /** * Adds a new watch expression and evaluates it against the debug adapter. */ diff --git a/src/vs/workbench/parts/debug/electron-browser/debugActions.ts b/src/vs/workbench/parts/debug/electron-browser/debugActions.ts index 76c5f3eb635..7fa9ee5ecaa 100644 --- a/src/vs/workbench/parts/debug/electron-browser/debugActions.ts +++ b/src/vs/workbench/parts/debug/electron-browser/debugActions.ts @@ -543,6 +543,28 @@ export class EditorConditionalBreakpointAction extends EditorAction { } } +export class SetValueAction extends AbstractDebugAction { + static ID = 'workbench.debug.viewlet.action.setValue'; + static LABEL = nls.localize('setValue', "Set Value"); + + constructor(id: string, label: string, private variable: model.Variable, @IDebugService debugService: IDebugService, @IKeybindingService keybindingService: IKeybindingService) { + super(id, label, null, debugService, keybindingService); + } + + public run(): TPromise { + if (this.variable instanceof model.Variable) { + this.debugService.getViewModel().setSelectedExpression(this.variable); + } + + return TPromise.as(null); + } + + protected isEnabled(state: debug.State): boolean { + const session = this.debugService.getActiveSession(); + return super.isEnabled(state) && state === debug.State.Stopped && session && session.configuration.capabilities.supportsSetVariable; + } +} + export class CopyValueAction extends AbstractDebugAction { static ID = 'workbench.debug.viewlet.action.copyValue'; static LABEL = nls.localize('copyValue', "Copy Value"); diff --git a/src/vs/workbench/parts/debug/electron-browser/debugService.ts b/src/vs/workbench/parts/debug/electron-browser/debugService.ts index f8bbd38e5a2..f03fee1d1cb 100644 --- a/src/vs/workbench/parts/debug/electron-browser/debugService.ts +++ b/src/vs/workbench/parts/debug/electron-browser/debugService.ts @@ -483,6 +483,18 @@ export class DebugService implements debug.IDebugService { this.model.removeReplExpressions(); } + public setVariable(variable: debug.IExpression, value: string): TPromise { + if (!this.session || !(variable instanceof model.Variable)) { + return TPromise.as(null); + } + + return this.session.setVarialbe({ + name: variable.name, + value, + variablesReference: (variable).parent.reference + }).then(() => variable.value = value); + } + public addWatchExpression(name: string): TPromise { return this.model.addWatchExpression(this.session, this.viewModel.getFocusedStackFrame(), name); } diff --git a/src/vs/workbench/parts/debug/node/rawDebugSession.ts b/src/vs/workbench/parts/debug/node/rawDebugSession.ts index ebf053776f5..e5a8f4e3f27 100644 --- a/src/vs/workbench/parts/debug/node/rawDebugSession.ts +++ b/src/vs/workbench/parts/debug/node/rawDebugSession.ts @@ -246,6 +246,10 @@ export class RawDebugSession extends v8.V8Protocol implements debug.IRawDebugSes return this.send('pause', args); } + public setVarialbe(args: DebugProtocol.SetVariableArguments): TPromise { + return this.send('setVariable', args); + } + public disconnect(restart = false, force = false): TPromise { if (this.stopServerPending && force) { return this.stopServer(); diff --git a/src/vs/workbench/parts/debug/test/common/mockDebugService.ts b/src/vs/workbench/parts/debug/test/common/mockDebugService.ts index 6d68cacbd48..bd5d6ce8d54 100644 --- a/src/vs/workbench/parts/debug/test/common/mockDebugService.ts +++ b/src/vs/workbench/parts/debug/test/common/mockDebugService.ts @@ -126,6 +126,10 @@ export class MockDebugService implements debug.IDebugService { public pause(threadId: number): TPromise { return TPromise.as(null); } + + public setVariable(variable: debug.IExpression, value: string): TPromise { + return TPromise.as(null); + } } From 2790a73ac95bc1617ab6269188600ca92abe89d0 Mon Sep 17 00:00:00 2001 From: Benjamin Pasero Date: Thu, 16 Jun 2016 16:30:15 +0200 Subject: [PATCH 149/217] fix tabs in hc theme --- .../browser/parts/editor/media/tabstitle.css | 3 ++- .../browser/parts/editor/media/titlecontrol.css | 12 +++++++++++- 2 files changed, 13 insertions(+), 2 deletions(-) diff --git a/src/vs/workbench/browser/parts/editor/media/tabstitle.css b/src/vs/workbench/browser/parts/editor/media/tabstitle.css index c67751c9140..2277c93a835 100644 --- a/src/vs/workbench/browser/parts/editor/media/tabstitle.css +++ b/src/vs/workbench/browser/parts/editor/media/tabstitle.css @@ -41,7 +41,7 @@ } .hc-black .monaco-workbench > .part.editor > .content > .one-editor-container > .title.active .tabs-container > .tab.active { - border: 1px solid #6FC3DF; + border: 1px solid #f38518; } .monaco-workbench > .part.editor > .content > .one-editor-container > .title .tabs-container > .tab:first-child { @@ -135,6 +135,7 @@ content: url('close-dirty-inverse.svg'); } +.hc-black .monaco-workbench > .part.editor > .content > .one-editor-container > .title .tabs-container > .tab .close-editor-action, .hc-black .monaco-workbench > .part.editor > .content > .one-editor-container > .title .tabs-container > .tab.dirty .close-editor-action:hover { content: url('close-inverse.svg'); } diff --git a/src/vs/workbench/browser/parts/editor/media/titlecontrol.css b/src/vs/workbench/browser/parts/editor/media/titlecontrol.css index 48f9740dcf7..d0380420643 100644 --- a/src/vs/workbench/browser/parts/editor/media/titlecontrol.css +++ b/src/vs/workbench/browser/parts/editor/media/titlecontrol.css @@ -58,6 +58,11 @@ background-repeat: no-repeat; } +.hc-black .monaco-workbench > .part.editor > .content > .one-editor-container > .title .title-actions .action-label, +.hc-black .monaco-workbench > .part.editor > .content > .one-editor-container > .title .group-actions .action-label { + line-height: initial; +} + .monaco-workbench > .part.editor > .content > .one-editor-container > .title .group-actions .action-label .label, .monaco-workbench > .part.editor > .content > .one-editor-container > .title .title-actions .action-label .label { display: none; @@ -122,8 +127,13 @@ width: 16px; } -.hc-black .monaco-workbench .close-editor-action { +.hc-black .monaco-workbench .close-editor-action:before { content: url('close-inverse.svg'); + position: absolute; + top: 12px; + left: 8px; + height: 16px; + width: 16px; } .hc-black .monaco-workbench .split-editor-action:before { From efc666655b580ccf6877e88dce9f7dffd2df18dd Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Jo=C3=A3o=20Moreno?= Date: Thu, 16 Jun 2016 16:34:40 +0200 Subject: [PATCH 150/217] travis: split compile & optimize --- .travis.yml | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/.travis.yml b/.travis.yml index bb3740c7c41..07c1ba2c9a7 100644 --- a/.travis.yml +++ b/.travis.yml @@ -37,6 +37,7 @@ install: script: - gulp hygiene - gulp electron - - gulp compile optimize-vscode + - gulp compile + - gulp optimize-vscode - ./scripts/test.sh - ./scripts/test-integration.sh From 1ebfb1b687c4345ac9c6da39051431a46c120a65 Mon Sep 17 00:00:00 2001 From: Alex Dima Date: Thu, 16 Jun 2016 16:34:19 +0200 Subject: [PATCH 151/217] Add createDiffNavigator API --- build/monaco/monaco.d.ts.recipe | 6 +- build/monaco/package.json | 2 +- .../standalone/standaloneCodeEditor.ts | 55 ++++++------------- .../browser/standalone/standaloneEditor.ts | 26 +++++++-- src/vs/monaco.d.ts | 39 ++++++++++++- 5 files changed, 81 insertions(+), 47 deletions(-) diff --git a/build/monaco/monaco.d.ts.recipe b/build/monaco/monaco.d.ts.recipe index a0afea10940..4ca3735197c 100644 --- a/build/monaco/monaco.d.ts.recipe +++ b/build/monaco/monaco.d.ts.recipe @@ -53,7 +53,11 @@ declare module monaco { declare module monaco.editor { #includeAll(vs/editor/browser/standalone/standaloneEditor;modes.=>languages.): -#include(vs/editor/browser/standalone/standaloneCodeEditor): IEditorConstructionOptions, IDiffEditorConstructionOptions +#include(vs/editor/browser/standalone/standaloneCodeEditor): IEditorConstructionOptions, IDiffEditorConstructionOptions, IStandaloneCodeEditor, IStandaloneDiffEditor +export interface ICommandHandler { + (...args:any[]): void; +} +#include(vs/platform/keybinding/common/keybindingService): IKeybindingContextKey #include(vs/editor/browser/standalone/standaloneServices): IEditorOverrideServices #include(vs/platform/markers/common/markers): IMarkerData #include(vs/editor/browser/standalone/colorizer): IColorizerOptions, IColorizerElementOptions diff --git a/build/monaco/package.json b/build/monaco/package.json index 8cbf0f8435b..7e6d2be7ba7 100644 --- a/build/monaco/package.json +++ b/build/monaco/package.json @@ -1,7 +1,7 @@ { "name": "monaco-editor-core", "private": true, - "version": "0.4.1", + "version": "0.4.2", "description": "A browser based code editor", "author": "Microsoft Corporation", "license": "MIT", diff --git a/src/vs/editor/browser/standalone/standaloneCodeEditor.ts b/src/vs/editor/browser/standalone/standaloneCodeEditor.ts index 189031214bb..2ed5ebddaaf 100644 --- a/src/vs/editor/browser/standalone/standaloneCodeEditor.ts +++ b/src/vs/editor/browser/standalone/standaloneCodeEditor.ts @@ -7,11 +7,9 @@ import {IDisposable, dispose} from 'vs/base/common/lifecycle'; import {IContextViewService} from 'vs/platform/contextview/browser/contextView'; -import {IEditorService} from 'vs/platform/editor/common/editor'; import {IInstantiationService} from 'vs/platform/instantiation/common/instantiation'; import {AbstractKeybindingService} from 'vs/platform/keybinding/browser/keybindingServiceImpl'; import {ICommandHandler, IKeybindingContextKey, IKeybindingService} from 'vs/platform/keybinding/common/keybindingService'; -import {IMarkerService} from 'vs/platform/markers/common/markers'; import {RemoteTelemetryServiceHelper} from 'vs/platform/telemetry/common/remoteTelemetryService'; import {ITelemetryService} from 'vs/platform/telemetry/common/telemetry'; import {IActionDescriptor, ICodeEditorWidgetCreationOptions, IDiffEditorOptions, IModel, IModelChangedEvent, EventType} from 'vs/editor/common/editorCommon'; @@ -21,6 +19,7 @@ import {StandaloneKeybindingService} from 'vs/editor/browser/standalone/simpleSe import {IEditorContextViewService, IEditorOverrideServices, ensureStaticPlatformServices, getOrCreateStaticServices} from 'vs/editor/browser/standalone/standaloneServices'; import {CodeEditorWidget} from 'vs/editor/browser/widget/codeEditorWidget'; import {DiffEditorWidget} from 'vs/editor/browser/widget/diffEditorWidget'; +import {ICodeEditor, IDiffEditor} from 'vs/editor/browser/editorBrowser'; /** * The options to create an editor. @@ -44,12 +43,22 @@ export interface IEditorConstructionOptions extends ICodeEditorWidgetCreationOpt export interface IDiffEditorConstructionOptions extends IDiffEditorOptions { } -export class StandaloneEditor extends CodeEditorWidget { +export interface IStandaloneCodeEditor extends ICodeEditor { + addCommand(keybinding:number, handler:ICommandHandler, context:string): string; + createContextKey(key: string, defaultValue: T): IKeybindingContextKey; + addAction(descriptor:IActionDescriptor): void; +} + +export interface IStandaloneDiffEditor extends IDiffEditor { + addCommand(keybinding:number, handler:ICommandHandler, context:string): string; + createContextKey(key: string, defaultValue: T): IKeybindingContextKey; + addAction(descriptor:IActionDescriptor): void; +} + +export class StandaloneEditor extends CodeEditorWidget implements IStandaloneCodeEditor { - private _editorService:IEditorService; private _standaloneKeybindingService: StandaloneKeybindingService; private _contextViewService:IEditorContextViewService; - private _markerService: IMarkerService; private _ownsModel:boolean; private _toDispose2: IDisposable[]; @@ -61,9 +70,7 @@ export class StandaloneEditor extends CodeEditorWidget { @ICodeEditorService codeEditorService: ICodeEditorService, @IKeybindingService keybindingService: IKeybindingService, @ITelemetryService telemetryService: ITelemetryService, - @IContextViewService contextViewService: IContextViewService, - @IEditorService editorService: IEditorService, - @IMarkerService markerService: IMarkerService + @IContextViewService contextViewService: IContextViewService ) { if (keybindingService instanceof AbstractKeybindingService) { (keybindingService).setInstantiationService(instantiationService); @@ -77,8 +84,6 @@ export class StandaloneEditor extends CodeEditorWidget { } this._contextViewService = contextViewService; - this._editorService = editorService; - this._markerService = markerService; this._toDispose2 = toDispose; let model: IModel = null; @@ -110,10 +115,6 @@ export class StandaloneEditor extends CodeEditorWidget { this.dispose(); } - public getMarkerService():IMarkerService { - return this._markerService; - } - public addCommand(keybinding:number, handler:ICommandHandler, context:string): string { if (!this._standaloneKeybindingService) { console.warn('Cannot add command because the editor is configured with an unrecognized KeybindingService'); @@ -146,14 +147,6 @@ export class StandaloneEditor extends CodeEditorWidget { } } - public getTelemetryService():ITelemetryService { - return this._telemetryService; - } - - public getEditorService():IEditorService { - return this._editorService; - } - _attachModel(model:IModel):void { super._attachModel(model); if (this._view) { @@ -170,13 +163,11 @@ export class StandaloneEditor extends CodeEditorWidget { } } -export class StandaloneDiffEditor extends DiffEditorWidget { +export class StandaloneDiffEditor extends DiffEditorWidget implements IStandaloneDiffEditor { private _contextViewService:IEditorContextViewService; private _standaloneKeybindingService: StandaloneKeybindingService; private _toDispose2: IDisposable[]; - private _markerService: IMarkerService; - private _telemetryService: ITelemetryService; constructor( domElement:HTMLElement, @@ -185,9 +176,6 @@ export class StandaloneDiffEditor extends DiffEditorWidget { @IInstantiationService instantiationService: IInstantiationService, @IKeybindingService keybindingService: IKeybindingService, @IContextViewService contextViewService: IContextViewService, - @IEditorService editorService: IEditorService, - @IMarkerService markerService: IMarkerService, - @ITelemetryService telemetryService: ITelemetryService, @IEditorWorkerService editorWorkerService: IEditorWorkerService ) { if (keybindingService instanceof AbstractKeybindingService) { @@ -202,9 +190,6 @@ export class StandaloneDiffEditor extends DiffEditorWidget { this._contextViewService = contextViewService; - this._markerService = markerService; - this._telemetryService = telemetryService; - this._toDispose2 = toDispose; this._contextViewService.setContainer(this._containerDomElement); @@ -219,10 +204,6 @@ export class StandaloneDiffEditor extends DiffEditorWidget { this.dispose(); } - public getMarkerService():IMarkerService { - return this._markerService; - } - public addCommand(keybinding:number, handler:ICommandHandler, context:string): string { if (!this._standaloneKeybindingService) { console.warn('Cannot add command because the editor is configured with an unrecognized KeybindingService'); @@ -254,10 +235,6 @@ export class StandaloneDiffEditor extends DiffEditorWidget { }); } } - - public getTelemetryService():ITelemetryService { - return this._telemetryService; - } } export var startup = (function() { diff --git a/src/vs/editor/browser/standalone/standaloneEditor.ts b/src/vs/editor/browser/standalone/standaloneEditor.ts index 277b41d54f5..fddf853ee19 100644 --- a/src/vs/editor/browser/standalone/standaloneEditor.ts +++ b/src/vs/editor/browser/standalone/standaloneEditor.ts @@ -9,7 +9,7 @@ import 'vs/css!./media/standalone-tokens'; import * as editorCommon from 'vs/editor/common/editorCommon'; import {ContentWidgetPositionPreference, OverlayWidgetPositionPreference} from 'vs/editor/browser/editorBrowser'; import {ShallowCancelThenPromise} from 'vs/base/common/async'; -import {StandaloneEditor, StandaloneDiffEditor, startup, IEditorConstructionOptions, IDiffEditorConstructionOptions} from 'vs/editor/browser/standalone/standaloneCodeEditor'; +import {StandaloneEditor, IStandaloneCodeEditor, StandaloneDiffEditor, IStandaloneDiffEditor, startup, IEditorConstructionOptions, IDiffEditorConstructionOptions} from 'vs/editor/browser/standalone/standaloneCodeEditor'; import {ScrollbarVisibility} from 'vs/base/browser/ui/scrollbar/scrollableElementOptions'; import {IEditorOverrideServices, ensureDynamicPlatformServices, ensureStaticPlatformServices} from 'vs/editor/browser/standalone/standaloneServices'; import {IDisposable} from 'vs/base/common/lifecycle'; @@ -20,12 +20,12 @@ import {ServiceCollection} from 'vs/platform/instantiation/common/serviceCollect import {InstantiationService} from 'vs/platform/instantiation/common/instantiationService'; import {IModel} from 'vs/editor/common/editorCommon'; import {IModelService} from 'vs/editor/common/services/modelService'; -import {ICodeEditor, IDiffEditor} from 'vs/editor/browser/editorBrowser'; import {Colorizer, IColorizerElementOptions, IColorizerOptions} from 'vs/editor/browser/standalone/colorizer'; import {SimpleEditorService} from 'vs/editor/browser/standalone/simpleServices'; import * as modes from 'vs/editor/common/modes'; import {EditorWorkerClient} from 'vs/editor/common/services/editorWorkerServiceImpl'; import {IMarkerData} from 'vs/platform/markers/common/markers'; +import {DiffNavigator} from 'vs/editor/contrib/diffNavigator/common/diffNavigator'; function shallowClone(obj:T): T { let r:T = {}; @@ -51,7 +51,7 @@ export function setupServices(services: IEditorOverrideServices): IEditorOverrid * `domElement` should be empty (not contain other dom nodes). * The editor will read the size of `domElement`. */ -export function create(domElement:HTMLElement, options?:IEditorConstructionOptions, services?:IEditorOverrideServices):ICodeEditor { +export function create(domElement:HTMLElement, options?:IEditorConstructionOptions, services?:IEditorOverrideServices):IStandaloneCodeEditor { startup.initStaticServicesIfNecessary(); services = shallowClone(services); @@ -76,7 +76,7 @@ export function create(domElement:HTMLElement, options?:IEditorConstructionOptio * `domElement` should be empty (not contain other dom nodes). * The editor will read the size of `domElement`. */ -export function createDiffEditor(domElement:HTMLElement, options?:IDiffEditorConstructionOptions, services?: IEditorOverrideServices):IDiffEditor { +export function createDiffEditor(domElement:HTMLElement, options?:IDiffEditorConstructionOptions, services?: IEditorOverrideServices):IStandaloneDiffEditor { startup.initStaticServicesIfNecessary(); services = shallowClone(services); @@ -96,6 +96,23 @@ export function createDiffEditor(domElement:HTMLElement, options?:IDiffEditorCon return result; } +export interface IDiffNavigator { + canNavigate():boolean; + next():void; + previous():void; + dispose():void; +} + +export interface IDiffNavigatorOptions { + followsCaret?:boolean; + ignoreCharChanges?:boolean; + alwaysRevealFirst?:boolean; +} + +export function createDiffNavigator(diffEditor:IStandaloneDiffEditor, opts?:IDiffNavigatorOptions): IDiffNavigator { + return new DiffNavigator(diffEditor, opts); +} + function prepareServices(domElement: HTMLElement, services: IEditorOverrideServices): { ctx: IEditorOverrideServices; toDispose: IDisposable[]; } { services = ensureStaticPlatformServices(services); var toDispose = ensureDynamicPlatformServices(domElement, services); @@ -371,6 +388,7 @@ export function createMonacoEditorAPI(): typeof monaco.editor { // methods create: create, createDiffEditor: createDiffEditor, + createDiffNavigator: createDiffNavigator, createModel: createModel, setModelLanguage: setModelLanguage, diff --git a/src/vs/monaco.d.ts b/src/vs/monaco.d.ts index 374c3be8984..7fa814ce385 100644 --- a/src/vs/monaco.d.ts +++ b/src/vs/monaco.d.ts @@ -752,14 +752,29 @@ declare module monaco.editor { * `domElement` should be empty (not contain other dom nodes). * The editor will read the size of `domElement`. */ - export function create(domElement: HTMLElement, options?: IEditorConstructionOptions, services?: IEditorOverrideServices): ICodeEditor; + export function create(domElement: HTMLElement, options?: IEditorConstructionOptions, services?: IEditorOverrideServices): IStandaloneCodeEditor; /** * Create a new diff editor under `domElement`. * `domElement` should be empty (not contain other dom nodes). * The editor will read the size of `domElement`. */ - export function createDiffEditor(domElement: HTMLElement, options?: IDiffEditorConstructionOptions, services?: IEditorOverrideServices): IDiffEditor; + export function createDiffEditor(domElement: HTMLElement, options?: IDiffEditorConstructionOptions, services?: IEditorOverrideServices): IStandaloneDiffEditor; + + export interface IDiffNavigator { + canNavigate(): boolean; + next(): void; + previous(): void; + dispose(): void; + } + + export interface IDiffNavigatorOptions { + followsCaret?: boolean; + ignoreCharChanges?: boolean; + alwaysRevealFirst?: boolean; + } + + export function createDiffNavigator(diffEditor: IStandaloneDiffEditor, opts?: IDiffNavigatorOptions): IDiffNavigator; /** * Create a new editor model. @@ -879,6 +894,26 @@ declare module monaco.editor { export interface IDiffEditorConstructionOptions extends IDiffEditorOptions { } + export interface IStandaloneCodeEditor extends ICodeEditor { + addCommand(keybinding: number, handler: ICommandHandler, context: string): string; + createContextKey(key: string, defaultValue: T): IKeybindingContextKey; + addAction(descriptor: IActionDescriptor): void; + } + + export interface IStandaloneDiffEditor extends IDiffEditor { + addCommand(keybinding: number, handler: ICommandHandler, context: string): string; + createContextKey(key: string, defaultValue: T): IKeybindingContextKey; + addAction(descriptor: IActionDescriptor): void; + } + export interface ICommandHandler { + (...args: any[]): void; + } + + export interface IKeybindingContextKey { + set(value: T): void; + reset(): void; + } + export interface IEditorOverrideServices { } From c3a4c2a5dae5073cf153394a34ca976f0368dbfd Mon Sep 17 00:00:00 2001 From: Benjamin Pasero Date: Thu, 16 Jun 2016 16:45:47 +0200 Subject: [PATCH 152/217] use tablist role model for tabs --- src/vs/workbench/browser/parts/editor/editorPart.ts | 1 + src/vs/workbench/browser/parts/editor/tabsTitleControl.ts | 5 +++++ 2 files changed, 6 insertions(+) diff --git a/src/vs/workbench/browser/parts/editor/editorPart.ts b/src/vs/workbench/browser/parts/editor/editorPart.ts index 65698c97df7..e6344c0d5d5 100644 --- a/src/vs/workbench/browser/parts/editor/editorPart.ts +++ b/src/vs/workbench/browser/parts/editor/editorPart.ts @@ -322,6 +322,7 @@ export class EditorPart extends Part implements IEditorPart, IEditorGroupService // Build Container off-DOM editorContainer = $().div({ 'class': 'editor-container', + 'role': 'tabpanel', id: descriptor.getId() }, (div) => { newlyCreatedEditorContainerBuilder = div; diff --git a/src/vs/workbench/browser/parts/editor/tabsTitleControl.ts b/src/vs/workbench/browser/parts/editor/tabsTitleControl.ts index 1749369bdbe..b979a0c6668 100644 --- a/src/vs/workbench/browser/parts/editor/tabsTitleControl.ts +++ b/src/vs/workbench/browser/parts/editor/tabsTitleControl.ts @@ -75,6 +75,7 @@ export class TabsTitleControl extends TitleControl { // Tabs Container this.tabsContainer = document.createElement('div'); + this.tabsContainer.setAttribute('role', 'tablist'); DOM.addClass(this.tabsContainer, 'tabs-container'); // Custom Scrollbar @@ -195,9 +196,11 @@ export class TabsTitleControl extends TitleControl { // Active state if (isActive) { DOM.addClass(tabContainer, 'active'); + tabContainer.setAttribute('aria-selected', 'true'); this.activeTab = tabContainer; } else { DOM.removeClass(tabContainer, 'active'); + tabContainer.setAttribute('aria-selected', 'false'); } // Dirty State @@ -265,6 +268,8 @@ export class TabsTitleControl extends TitleControl { const tabContainer = document.createElement('div'); tabContainer.draggable = true; tabContainer.tabIndex = 0; + tabContainer.setAttribute('role', 'tab'); + tabContainer.setAttribute('aria-label', editor.getName()); DOM.addClass(tabContainer, 'tab monaco-editor-background'); tabContainers.push(tabContainer); From efa84e329a32c779c0a2b6c929686c6e9308e704 Mon Sep 17 00:00:00 2001 From: Benjamin Pasero Date: Thu, 16 Jun 2016 16:51:01 +0200 Subject: [PATCH 153/217] does this help for #7662 ? --- src/vs/workbench/browser/parts/editor/media/tabstitle.css | 2 +- src/vs/workbench/browser/parts/editor/tabsTitleControl.ts | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/src/vs/workbench/browser/parts/editor/media/tabstitle.css b/src/vs/workbench/browser/parts/editor/media/tabstitle.css index 2277c93a835..5a9ceec4949 100644 --- a/src/vs/workbench/browser/parts/editor/media/tabstitle.css +++ b/src/vs/workbench/browser/parts/editor/media/tabstitle.css @@ -11,7 +11,7 @@ .monaco-workbench > .part.editor > .content > .one-editor-container > .title .tabs-container { display: flex; - overflow: scroll; + /*overflow: scroll;*/ background-color: rgba(128, 128, 128, 0.2); height: 35px; } diff --git a/src/vs/workbench/browser/parts/editor/tabsTitleControl.ts b/src/vs/workbench/browser/parts/editor/tabsTitleControl.ts index b979a0c6668..2e8e005186f 100644 --- a/src/vs/workbench/browser/parts/editor/tabsTitleControl.ts +++ b/src/vs/workbench/browser/parts/editor/tabsTitleControl.ts @@ -87,7 +87,7 @@ export class TabsTitleControl extends TitleControl { canUseTranslate3d: true, horizontalScrollbarSize: 3 }); - this.tabsContainer.style.overflow = 'scroll'; // custom scrollbar is eager on removing this style but we want it for DND scroll feedback + // this.tabsContainer.style.overflow = 'scroll'; // custom scrollbar is eager on removing this style but we want it for DND scroll feedback this.scrollbar.onScroll(e => { this.tabsContainer.scrollLeft = e.scrollLeft; From c423fe96d24f2513005b670d5c2a08d45bba5d22 Mon Sep 17 00:00:00 2001 From: Benjamin Pasero Date: Thu, 16 Jun 2016 16:59:19 +0200 Subject: [PATCH 154/217] stop creating models with same URI --- src/vs/workbench/common/editor/stringEditorInput.ts | 3 +-- src/vs/workbench/common/editor/textEditorModel.ts | 7 +++++-- 2 files changed, 6 insertions(+), 4 deletions(-) diff --git a/src/vs/workbench/common/editor/stringEditorInput.ts b/src/vs/workbench/common/editor/stringEditorInput.ts index f9b9b3298ea..3e166c9c57e 100644 --- a/src/vs/workbench/common/editor/stringEditorInput.ts +++ b/src/vs/workbench/common/editor/stringEditorInput.ts @@ -44,8 +44,7 @@ export class StringEditorInput extends EditorInput { } protected getResource(): URI { - // Subclasses can implement to associate a resource with the input - return null; + return null; // Subclasses can implement to associate a resource with the input } public getTypeId(): string { diff --git a/src/vs/workbench/common/editor/textEditorModel.ts b/src/vs/workbench/common/editor/textEditorModel.ts index 6b717be5bd2..b723b57cab9 100644 --- a/src/vs/workbench/common/editor/textEditorModel.ts +++ b/src/vs/workbench/common/editor/textEditorModel.ts @@ -60,8 +60,11 @@ export abstract class BaseTextEditorModel extends EditorModel implements ITextEd // To avoid flickering, give the mode at most 50ms to load. If the mode doesn't load in 50ms, proceed creating the model with a mode promise return TPromise.any([TPromise.timeout(50), this.getOrCreateMode(this.modeService, mime, firstLineText)]).then(() => { - let model = this.modelService.createModel(value, this.getOrCreateMode(this.modeService, mime, firstLineText), resource); - this.createdEditorModel = true; + let model = this.modelService.getModel(resource); + if (!model) { + model = this.modelService.createModel(value, this.getOrCreateMode(this.modeService, mime, firstLineText), resource); + this.createdEditorModel = true; + } this.textEditorModelHandle = model.uri; From 9dede062419ea7a167356b8f136fc6f674ae327b Mon Sep 17 00:00:00 2001 From: Benjamin Pasero Date: Thu, 16 Jun 2016 17:00:51 +0200 Subject: [PATCH 155/217] still pass in value and mode if model exists --- src/vs/workbench/common/editor/textEditorModel.ts | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/src/vs/workbench/common/editor/textEditorModel.ts b/src/vs/workbench/common/editor/textEditorModel.ts index b723b57cab9..a892bf50539 100644 --- a/src/vs/workbench/common/editor/textEditorModel.ts +++ b/src/vs/workbench/common/editor/textEditorModel.ts @@ -61,9 +61,13 @@ export abstract class BaseTextEditorModel extends EditorModel implements ITextEd // To avoid flickering, give the mode at most 50ms to load. If the mode doesn't load in 50ms, proceed creating the model with a mode promise return TPromise.any([TPromise.timeout(50), this.getOrCreateMode(this.modeService, mime, firstLineText)]).then(() => { let model = this.modelService.getModel(resource); + let mode = this.getOrCreateMode(this.modeService, mime, firstLineText); if (!model) { - model = this.modelService.createModel(value, this.getOrCreateMode(this.modeService, mime, firstLineText), resource); + model = this.modelService.createModel(value, mode, resource); this.createdEditorModel = true; + } else { + model.setValue(value); + model.setMode(mode); } this.textEditorModelHandle = model.uri; From 0fde58dced591a95c7272a0ec19ab55604067267 Mon Sep 17 00:00:00 2001 From: Benjamin Pasero Date: Thu, 16 Jun 2016 17:13:22 +0200 Subject: [PATCH 156/217] compare string inputs by resource if present --- src/vs/workbench/common/editor/stringEditorInput.ts | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/src/vs/workbench/common/editor/stringEditorInput.ts b/src/vs/workbench/common/editor/stringEditorInput.ts index 3e166c9c57e..08e817bfe3b 100644 --- a/src/vs/workbench/common/editor/stringEditorInput.ts +++ b/src/vs/workbench/common/editor/stringEditorInput.ts @@ -144,6 +144,13 @@ export class StringEditorInput extends EditorInput { return true; } + // If we have resource URIs, use those to compare + const resource = this.getResource(); + const otherResource = otherStringEditorInput.getResource(); + if (resource && otherResource) { + return resource.toString() === otherResource.toString(); + } + // Otherwise compare by properties return otherStringEditorInput.value === this.value && otherStringEditorInput.mime === this.mime && From d64cd45e9656dfa821b611dbfd451daa0b64ecc3 Mon Sep 17 00:00:00 2001 From: Johannes Rieken Date: Thu, 16 Jun 2016 16:05:59 +0200 Subject: [PATCH 157/217] Add generic version of Array.isArray --- src/typings/lib.array-ext.d.ts | 8 ++++++++ 1 file changed, 8 insertions(+) create mode 100644 src/typings/lib.array-ext.d.ts diff --git a/src/typings/lib.array-ext.d.ts b/src/typings/lib.array-ext.d.ts new file mode 100644 index 00000000000..59e1c0fc956 --- /dev/null +++ b/src/typings/lib.array-ext.d.ts @@ -0,0 +1,8 @@ +/*--------------------------------------------------------------------------------------------- + * Copyright (c) Microsoft Corporation. All rights reserved. + * Licensed under the MIT License. See License.txt in the project root for license information. + *--------------------------------------------------------------------------------------------*/ + +interface ArrayConstructor { + isArray(arg: any): arg is Array; +} \ No newline at end of file From b248889d39aa9981b4b5035afbe9a487b3ec3ab8 Mon Sep 17 00:00:00 2001 From: Johannes Rieken Date: Thu, 16 Jun 2016 16:42:53 +0200 Subject: [PATCH 158/217] inline context, have one per command --- extensions/markdown/package.json | 39 ++-- extensions/markdown/package.nls.json | 5 +- .../actions/common/commandsExtensionPoint.ts | 99 +++++----- .../workbench/actionBarContributions.ts | 175 ++++++++++-------- 4 files changed, 168 insertions(+), 150 deletions(-) diff --git a/extensions/markdown/package.json b/extensions/markdown/package.json index e40ac15c0f6..47e7652b3bb 100644 --- a/extensions/markdown/package.json +++ b/extensions/markdown/package.json @@ -43,29 +43,30 @@ { "command": "extension.previewMarkdown", "title": "%markdown.previewMarkdown.title%", - "context": [{ - "where": "editor/primary", - "when": "markdown", - "icon": { - "light": "./media/Preview.svg", - "dark": "./media/Preview_inverse.svg" - } - },{ - "where": "editor/primary", - "when": { "scheme": "markdown" }, - "icon": { - "light": "./media/ViewSource.svg", - "dark": "./media/ViewSource_inverse.svg" - } - }] + "category": "%markdown.category%", + "icon": { + "light": "./media/Preview.svg", + "dark": "./media/Preview_inverse.svg" + }, + "where": ["editor/primary", "explorer/context"], + "when": "markdown" + }, + { + "title": "%markdown.previewMarkdown.title%", + "category": "%markdown.category%", + "icon": { + "light": "./media/ViewSource.svg", + "dark": "./media/ViewSource_inverse.svg" + }, + "where": ["editor/primary"], + "when": { "scheme": "markdown" }, + "command": "extension.previewMarkdown" }, { "command": "extension.previewMarkdownSide", "title": "%markdown.previewMarkdownSide.title%", - "context": { - "where": "editor/secondary", - "when": "markdown" - } + "where": "editor/secondary", + "when": "markdown" } ], "keybindings": [ diff --git a/extensions/markdown/package.nls.json b/extensions/markdown/package.nls.json index 341e838ed68..d41fc234818 100644 --- a/extensions/markdown/package.nls.json +++ b/extensions/markdown/package.nls.json @@ -1,4 +1,5 @@ { - "markdown.previewMarkdown.title" : "Markdown: Toggle Preview", - "markdown.previewMarkdownSide.title" : "Markdown: Open Preview to the Side" + "markdown.category" : "Markdown", + "markdown.previewMarkdown.title" : "Toggle Preview", + "markdown.previewMarkdownSide.title" : "Open Preview to the Side" } \ No newline at end of file diff --git a/src/vs/platform/actions/common/commandsExtensionPoint.ts b/src/vs/platform/actions/common/commandsExtensionPoint.ts index c36c6c7c18d..b10db1143d0 100644 --- a/src/vs/platform/actions/common/commandsExtensionPoint.ts +++ b/src/vs/platform/actions/common/commandsExtensionPoint.ts @@ -18,40 +18,52 @@ export interface ResourceFilter { pattern?: string; } -export type Where = 'editor/primary' | 'editor/secondary' | 'explorer/context'; - -export interface Context { - where: Where; - when: string | string[] | ResourceFilter | ResourceFilter[]; - icon?: string | ThemableIcon; -} +export type Locations = 'editor/primary' | 'editor/secondary' | 'explorer/context'; export interface ThemableIcon { dark: string; light: string; } - export interface Command { command: string; title: string; category?: string; - context?: Context | Context[]; + where?: Locations | Locations[]; + when?: string | string[] | ResourceFilter | ResourceFilter[]; + icon?: string | ThemableIcon; } -function isThemableIcon(thing: any): thing is ThemableIcon { +export function isThemableIcon(thing: any): thing is ThemableIcon { return typeof thing === 'object' && thing && typeof (thing).dark === 'string' && typeof (thing).light === 'string'; } -function isCommands(thing: Command | Command[]): thing is Command[] { - return Array.isArray(thing); -} -function isContexts(thing: Context | Context[]): thing is Context[] { - return Array.isArray(thing); -} namespace validation { + function isValidWhere(where: Locations | Locations[], user: IExtensionPointUser): boolean { + if (Array.isArray(where)) { + return where.every(where => isValidWhere(where, user)); + } else if (['editor/primary', 'editor/secondary', 'explorer/context'].indexOf(where) < 0) { + user.collector.error(localize('optwhere', "property `where` can be omitted or must be a valid enum value")); + return false; + } + return true; + } + + function isValidWhen(when: string | string[] | ResourceFilter | ResourceFilter[], user: IExtensionPointUser): boolean { + if (Array.isArray(when)) { + for (let w of when) { + if (!isValidWhen(w, user)) { + return false; + } + } + } else if (typeof when === 'string' || typeof when === 'object') { + return true; + } + user.collector.error(localize('requirefilter', "property `when` is mandatory and must be a string or like `{language, scheme, pattern}`")); + return false; + } function isValidIcon(icon: string | ThemableIcon, user: IExtensionPointUser): boolean { if (typeof icon === 'undefined') { @@ -67,34 +79,6 @@ namespace validation { return false; } - function isValidContext(context: Context, user: IExtensionPointUser): boolean { - if (!context) { - return true; - } - if (context.where !== 'editor/primary' && context.where !== 'editor/secondary' && context.where !== 'explorer/context') { - user.collector.error(localize('requireenumtype', "property `where` is mandatory and must be one of `editor/primary`, `editor/secondary`, or `explorer/context`")); - return false; - } - if (typeof context.when !== 'object' && typeof context.when !== 'string' && !Array.isArray(context.when)) { - user.collector.error(localize('requirefilter', "property `when` is mandatory and must be like `{language, scheme, pattern}`")); - return false; - } - if (!isValidIcon(context.icon, user)) { - return false; - } - - // make icon paths absolute - let {icon} = context; - if (typeof icon === 'string') { - context.icon = join(user.description.extensionFolderPath, icon); - } else if(isThemableIcon(icon)) { - icon.dark = join(user.description.extensionFolderPath, icon.dark); - icon.light = join(user.description.extensionFolderPath, icon.light); - } - - return true; - } - export function isValidCommand(candidate: Command, user: IExtensionPointUser): boolean { if (!candidate) { user.collector.error(localize('nonempty', "expected non-empty value.")); @@ -112,16 +96,19 @@ namespace validation { user.collector.error(localize('optstring', "property `{0}` can be omitted or must be of type `string`", 'category')); return false; } - if (candidate.context) { - let {context} = candidate; - if (isContexts(context)) { - if (!context.every(context => isValidContext(context, user))) { - return false; - } - } else if (!isValidContext(context, user)) { - return false; - } + if (!isValidIcon(candidate.icon, user)) { + return false; } + + // make icon paths absolute + let {icon} = candidate; + if (typeof icon === 'string') { + candidate.icon = join(user.description.extensionFolderPath, icon); + } else if(isThemableIcon(icon)) { + icon.dark = join(user.description.extensionFolderPath, icon.dark); + icon.light = join(user.description.extensionFolderPath, icon.light); + } + return true; } @@ -238,7 +225,7 @@ function handleCommand(command: Command, user: IExtensionPointUser): void { ExtensionsRegistry.registerExtensionPoint('commands', schema.commandContribution).setHandler(extensions => { for (let extension of extensions) { const {value} = extension; - if (isCommands(value)) { + if (Array.isArray(value)) { for (let command of value) { handleCommand(command, extension); } @@ -258,8 +245,8 @@ export class CommandAction extends Action { @IKeybindingService keybindingService: IKeybindingService ) { super(command.command, command.title); + this.order = Number.MAX_VALUE; - // callback that (1) activates the extension and (2) dispatches the command const activationEvent = `onCommand:${command.command}`; this._actionCallback = (...args: any[]) => { return extensionService.activateByEvent(activationEvent).then(() => { @@ -267,4 +254,4 @@ export class CommandAction extends Action { }); }; } -} +} \ No newline at end of file diff --git a/src/vs/platform/actions/workbench/actionBarContributions.ts b/src/vs/platform/actions/workbench/actionBarContributions.ts index 8a5707c1d76..ca6c71536f5 100644 --- a/src/vs/platform/actions/workbench/actionBarContributions.ts +++ b/src/vs/platform/actions/workbench/actionBarContributions.ts @@ -8,110 +8,153 @@ import {Registry} from 'vs/platform/platform'; import URI from 'vs/base/common/uri'; import {IAction, Action} from 'vs/base/common/actions'; +import {IDisposable} from 'vs/base/common/lifecycle'; import {BaseActionItem, ActionItem} from 'vs/base/browser/ui/actionbar/actionbar'; import {Scope, IActionBarRegistry, Extensions, ActionBarContributor} from 'vs/workbench/browser/actionBarRegistry'; import {IModeService} from 'vs/editor/common/services/modeService'; import {IExtensionService} from 'vs/platform/extensions/common/extensions'; import {IThemeService} from 'vs/workbench/services/themes/common/themeService'; import {isLightTheme} from 'vs/platform/theme/common/themes'; +import {IInstantiationService} from 'vs/platform/instantiation/common/instantiation'; import {IKeybindingService} from 'vs/platform/keybinding/common/keybindingService'; -import {commands, Command, Context, Where, CommandAction} from '../common/commandsExtensionPoint'; +import {commands, CommandAction, Command, Locations} from '../common/commandsExtensionPoint'; import matches from 'vs/editor/common/modes/languageSelector'; import {getUntitledOrFileResource} from 'vs/workbench/common/editor'; -class ContextAction extends CommandAction { +class ResolvedCommand { + + constructor( + private _command: Command, + @IInstantiationService private _instantiationService: IInstantiationService, + @IThemeService private _themeService: IThemeService, + @IModeService private _modeService: IModeService + ) { + + } + + matches(location: Locations, resource: URI): boolean { + const {where, when} = this._command; + if (!where || !when) { + return false; + } + // (1) check for location + if (Array.isArray(where)) { + if (where.every(where => where !== location)) { + return false; + } + } else if (where !== location) { + return false; + } + // (2) check for resource + if (!matches(when, resource, this._modeService.getModeIdByFilenameOrFirstLine(resource.fsPath))) { + return false; + } + + return true; + } + + createAction(resource: URI): ScopedCommandAction { + return this._instantiationService.createInstance(ScopedCommandAction, this._command, resource); + } +} + +class ScopedCommandAction extends CommandAction { + + private _themeListener: IDisposable; constructor( - public context: Context, - public resource: URI, command: Command, + private _resource: URI, + @IThemeService private _themeService: IThemeService, @IExtensionService extensionService: IExtensionService, @IKeybindingService keybindingService: IKeybindingService ) { super(command, extensionService, keybindingService); } + dispose() { + this._themeListener.dispose(); + super.dispose(); + } + + get icon(): string { + const {icon} = this.command; + if (!icon) { + return; + } + if (typeof icon === 'string') { + return icon; + } else { + return isLightTheme(this._themeService.getTheme()) + ? icon.light + : icon.dark; + } + } + run() { - return super.run(this.resource); + return super.run(this._resource); } } abstract class BaseActionBarContributor extends ActionBarContributor { + private _isReady: boolean = false; + private _contributedActions: ResolvedCommand[]; + constructor( - @IModeService private _modeService: IModeService, @IExtensionService private _extensionService: IExtensionService, - @IKeybindingService private _keybindingsService: IKeybindingService, - @IThemeService private _themeService: IThemeService + @IInstantiationService private _instantationService: IInstantiationService ) { super(); + this._extensionService.onReady().then(() => { + this._contributedActions = commands.map(command => _instantationService.createInstance(ResolvedCommand, command)); + this._isReady = true; + }); } - protected abstract _wheres(): { primary: Where; secondary: Where }; + protected abstract _wheres(): { primary: Locations; secondary: Locations }; + + protected abstract _getResource(context: any): URI; public hasActions(context: any): boolean { - return this._wheres().primary && this.getActions(context).length > 0; + return this._isReady && this._wheres().primary && this.getActions(context).length > 0; + } + + public hasSecondaryActions(context: any): boolean { + return this._isReady && this._wheres().secondary && this.getSecondaryActions(context).length > 0; } public getActions(context: any): IAction[] { return this._getActions(context, this._wheres().primary); } - public hasSecondaryActions(context: any): boolean { - return this._wheres().secondary && this.getSecondaryActions(context).length > 0; - } - public getSecondaryActions(context: any): IAction[] { return this._getActions(context, this._wheres().secondary); } - private _getActions(context: any, where: string): IAction[]{ + private _getActions(context: any, where: Locations): IAction[] { const uri = this._getResource(context); - if (uri) { - return this._getCommandActions(uri, where); - } - return []; - } - - protected abstract _getResource(context: any): URI; - - private _getCommandActions(resource: URI, where: string): IAction[] { const result: IAction[] = []; - for (let command of commands) { - const {context} = command; - if (Array.isArray(context)) { - for (let ctx of context) { - if (this._matches(ctx, resource, where)) { - result.push(new ContextAction(ctx, resource, command, this._extensionService, this._keybindingsService)); - break; - } + if (uri) { + for (let command of this._contributedActions) { + if (command.matches(where, uri)) { + result.push(command.createAction(uri)); } - } else if (context && this._matches(context, resource, where)) { - result.push(new ContextAction(context, resource, command, this._extensionService, this._keybindingsService)); } } return result; } - private _matches(context: Context, resource: URI, where: string): boolean { - if (context.where !== where) { - return false; - } - const language = this._modeService.getModeIdByFilenameOrFirstLine(resource.fsPath); - return matches(context.when, resource, language); - } - public getActionItem(context: any, action: Action): BaseActionItem { - if (action instanceof ContextAction) { - const uri = this._getResource(context); - return new CommandItem(uri, action, this._themeService); + if (action instanceof ScopedCommandAction) { + return this._instantationService.createInstance(CommandActionItem, action); } } } class EditorContributor extends BaseActionBarContributor { - protected _wheres(): { primary: Where; secondary: Where } { + protected _wheres(): { primary: Locations; secondary: Locations } { return { primary: 'editor/primary', secondary: 'editor/secondary' }; } protected _getResource(context: any): URI { @@ -134,7 +177,7 @@ class EditorContributor extends BaseActionBarContributor { class ContextMenuContributor extends BaseActionBarContributor { - protected _wheres(): { primary: Where; secondary: Where } { + protected _wheres(): { primary: Locations; secondary: Locations } { return { secondary: 'explorer/context', primary: undefined }; } @@ -147,43 +190,29 @@ class ContextMenuContributor extends BaseActionBarContributor { } } -class CommandItem extends ActionItem { +class CommandActionItem extends ActionItem { constructor( - context: any, - action: ContextAction, + action: ScopedCommandAction, @IThemeService private _themeService: IThemeService ) { - super(context, action, { icon: Boolean(action.context.icon), label: !Boolean(action.context.icon) }); + super(undefined, action, { icon: Boolean(action.icon), label: !Boolean(action.icon) }); - if (typeof action.context.icon === 'object') { - this._themeService.onDidThemeChange(this._updateIcon, this, this.callOnDispose); - } + this._themeService.onDidThemeChange(this._updateClass, this, this.callOnDispose); } _updateClass(): void { super._updateClass(); - this._updateIcon(); + + const element = this.$e.getHTMLElement(); + const {icon} = this._action; + if (icon && element.classList.contains('icon')) { + element.style.backgroundImage = `url("${icon}")`; + } } - private _updateIcon(): void { - const element = this.$e.getHTMLElement(); - - const {context: {icon}} = this._action; - let iconUri: string; - - if (element.classList.contains('icon')) { - if (!icon) { - return; - } else if (typeof icon === 'string') { - iconUri = icon; - } else { - iconUri = isLightTheme(this._themeService.getTheme()) - ? icon.light - : icon.dark; - } - element.style.backgroundImage = `url("${iconUri}")`; - } + onClick(event: Event): void { + super.onClick(event); } } From 8c54612791c6b583d5e48389ff7cd22c36c537e5 Mon Sep 17 00:00:00 2001 From: Johannes Rieken Date: Thu, 16 Jun 2016 17:35:07 +0200 Subject: [PATCH 159/217] workaround context challanges when updating title actions --- .../workbench/actionBarContributions.ts | 23 ++++++++++--------- .../parts/html/browser/htmlPreviewPart.ts | 21 +++++++++-------- 2 files changed, 23 insertions(+), 21 deletions(-) diff --git a/src/vs/platform/actions/workbench/actionBarContributions.ts b/src/vs/platform/actions/workbench/actionBarContributions.ts index ca6c71536f5..906dc9496c5 100644 --- a/src/vs/platform/actions/workbench/actionBarContributions.ts +++ b/src/vs/platform/actions/workbench/actionBarContributions.ts @@ -19,7 +19,7 @@ import {IInstantiationService} from 'vs/platform/instantiation/common/instantiat import {IKeybindingService} from 'vs/platform/keybinding/common/keybindingService'; import {commands, CommandAction, Command, Locations} from '../common/commandsExtensionPoint'; import matches from 'vs/editor/common/modes/languageSelector'; -import {getUntitledOrFileResource} from 'vs/workbench/common/editor'; +import {EditorInput} from 'vs/workbench/common/editor'; class ResolvedCommand { @@ -158,18 +158,19 @@ class EditorContributor extends BaseActionBarContributor { return { primary: 'editor/primary', secondary: 'editor/secondary' }; } protected _getResource(context: any): URI { - if (!context.input || !context.editor) { + const {input, position, editor} = context; + if (typeof position !== 'number' || !editor) { + //todo@ben I get called two times with different + //but very similar looking context-objects in case + //an editor is created the first time return; } - let candidate: URI; - candidate = getUntitledOrFileResource(context.input, true); - if(candidate) { - return candidate; - } - if (typeof context.input.getResource === 'function') { - candidate = context.input.getResource(); - if (candidate instanceof URI) { - return candidate; + if (input instanceof EditorInput) { + if (typeof input.getResource === 'function') { + const candidate = context.input.getResource(); + if (candidate instanceof URI) { + return candidate; + } } } } diff --git a/src/vs/workbench/parts/html/browser/htmlPreviewPart.ts b/src/vs/workbench/parts/html/browser/htmlPreviewPart.ts index 574d209b380..3de0dc39df4 100644 --- a/src/vs/workbench/parts/html/browser/htmlPreviewPart.ts +++ b/src/vs/workbench/parts/html/browser/htmlPreviewPart.ts @@ -144,16 +144,17 @@ export class HtmlPreviewPart extends BaseEditor { return TPromise.wrapError('Invalid input'); } - return this._editorService.resolveEditorModel({ resource: (input).getResource() }).then(model => { - if (model instanceof BaseTextEditorModel) { - this._model = model.textEditorModel; - } - if (!this._model) { - return TPromise.wrapError(localize('html.voidInput', "Invalid editor input.")); - } - this._modelChangeSubscription = this._model.onDidChangeContent(() => this.webview.contents = this._model.getLinesContent()); - this.webview.contents = this._model.getLinesContent(); - return super.setInput(input, options); + return super.setInput(input, options).then(() => { + return this._editorService.resolveEditorModel({ resource: (input).getResource() }).then(model => { + if (model instanceof BaseTextEditorModel) { + this._model = model.textEditorModel; + } + if (!this._model) { + return TPromise.wrapError(localize('html.voidInput', "Invalid editor input.")); + } + this._modelChangeSubscription = this._model.onDidChangeContent(() => this.webview.contents = this._model.getLinesContent()); + this.webview.contents = this._model.getLinesContent(); + }); }); } } From 6a1b806b3d3ff52c3e0f78d5060babb486580cee Mon Sep 17 00:00:00 2001 From: Johannes Rieken Date: Thu, 16 Jun 2016 17:59:13 +0200 Subject: [PATCH 160/217] fix update regression --- extensions/markdown/src/extension.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/extensions/markdown/src/extension.ts b/extensions/markdown/src/extension.ts index 65b09e9c231..bc0835469d2 100644 --- a/extensions/markdown/src/extension.ts +++ b/extensions/markdown/src/extension.ts @@ -62,7 +62,7 @@ function isMarkdownFile(document: vscode.TextDocument) { } function getMarkdownUri(document: vscode.TextDocument) { - return document.uri.with({ scheme: 'markdown', path: String(document.version), query: document.uri.toString() }); + return document.uri.with({ scheme: 'markdown', path: document.uri.path + '.rendered', query: document.uri.toString() }); } function openPreview(sideBySide?: boolean): void { From 438266ee677c0a21e9c3e98de3c024781e1aee3a Mon Sep 17 00:00:00 2001 From: isidor Date: Thu, 16 Jun 2016 18:06:06 +0200 Subject: [PATCH 161/217] debug: use the body.value as the new value for the variable #7744 --- src/vs/workbench/parts/debug/electron-browser/debugService.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/vs/workbench/parts/debug/electron-browser/debugService.ts b/src/vs/workbench/parts/debug/electron-browser/debugService.ts index f03fee1d1cb..4d1a0458c8d 100644 --- a/src/vs/workbench/parts/debug/electron-browser/debugService.ts +++ b/src/vs/workbench/parts/debug/electron-browser/debugService.ts @@ -492,7 +492,7 @@ export class DebugService implements debug.IDebugService { name: variable.name, value, variablesReference: (variable).parent.reference - }).then(() => variable.value = value); + }).then(response => variable.value = response.body.value); } public addWatchExpression(name: string): TPromise { From a91bc054c32d089adfce1e9362a568d642147cca Mon Sep 17 00:00:00 2001 From: Johannes Rieken Date: Thu, 16 Jun 2016 18:18:08 +0200 Subject: [PATCH 162/217] not yet fit for explorer contribution --- extensions/markdown/package.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/extensions/markdown/package.json b/extensions/markdown/package.json index 47e7652b3bb..0a9ad0e646e 100644 --- a/extensions/markdown/package.json +++ b/extensions/markdown/package.json @@ -48,7 +48,7 @@ "light": "./media/Preview.svg", "dark": "./media/Preview_inverse.svg" }, - "where": ["editor/primary", "explorer/context"], + "where": ["editor/primary"], "when": "markdown" }, { From adb98bed825df72065330c626814459fa0e90f11 Mon Sep 17 00:00:00 2001 From: Benjamin Pasero Date: Thu, 16 Jun 2016 18:57:01 +0200 Subject: [PATCH 163/217] fix npe --- src/vs/workbench/common/editor/textEditorModel.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/vs/workbench/common/editor/textEditorModel.ts b/src/vs/workbench/common/editor/textEditorModel.ts index a892bf50539..2172ac930ff 100644 --- a/src/vs/workbench/common/editor/textEditorModel.ts +++ b/src/vs/workbench/common/editor/textEditorModel.ts @@ -60,7 +60,7 @@ export abstract class BaseTextEditorModel extends EditorModel implements ITextEd // To avoid flickering, give the mode at most 50ms to load. If the mode doesn't load in 50ms, proceed creating the model with a mode promise return TPromise.any([TPromise.timeout(50), this.getOrCreateMode(this.modeService, mime, firstLineText)]).then(() => { - let model = this.modelService.getModel(resource); + let model = resource && this.modelService.getModel(resource); let mode = this.getOrCreateMode(this.modeService, mime, firstLineText); if (!model) { model = this.modelService.createModel(value, mode, resource); From 2c5cf24d6a74624cad8c789a8bdcc02859b1a4c5 Mon Sep 17 00:00:00 2001 From: Benjamin Pasero Date: Thu, 16 Jun 2016 20:08:21 +0200 Subject: [PATCH 164/217] Weird state with editors (fixes #7782) --- .../browser/parts/editor/editor.contribution.ts | 10 +++++----- src/vs/workbench/browser/parts/sidebar/sidebarPart.ts | 2 +- 2 files changed, 6 insertions(+), 6 deletions(-) diff --git a/src/vs/workbench/browser/parts/editor/editor.contribution.ts b/src/vs/workbench/browser/parts/editor/editor.contribution.ts index 8992087a523..b890a243ec6 100644 --- a/src/vs/workbench/browser/parts/editor/editor.contribution.ts +++ b/src/vs/workbench/browser/parts/editor/editor.contribution.ts @@ -291,10 +291,10 @@ registry.registerWorkbenchAction(new SyncActionDescriptor(CloseOtherEditorsInGro registry.registerWorkbenchAction(new SyncActionDescriptor(CloseEditorsInOtherGroupsAction, CloseEditorsInOtherGroupsAction.ID, CloseEditorsInOtherGroupsAction.LABEL), 'View: Close Editors in Other Groups', category); registry.registerWorkbenchAction(new SyncActionDescriptor(SplitEditorAction, SplitEditorAction.ID, SplitEditorAction.LABEL, { primary: KeyMod.CtrlCmd | KeyCode.US_BACKSLASH }), 'View: Split Editor', category); registry.registerWorkbenchAction(new SyncActionDescriptor(NavigateBetweenGroupsAction, NavigateBetweenGroupsAction.ID, NavigateBetweenGroupsAction.LABEL), 'View: Navigate Between Editor Groups', category); -registry.registerWorkbenchAction(new SyncActionDescriptor(FocusFirstGroupAction, FocusFirstGroupAction.ID, FocusFirstGroupAction.LABEL, { primary: KeyMod.CtrlCmd | KeyCode.KEY_1 }, KbExpr.has('!config.workbench.showEditorTabs')), 'View: Focus Left Editor Group', category); -registry.registerWorkbenchAction(new SyncActionDescriptor(FocusSecondGroupAction, FocusSecondGroupAction.ID, FocusSecondGroupAction.LABEL, { primary: KeyMod.CtrlCmd | KeyCode.KEY_2 }, KbExpr.has('!config.workbench.showEditorTabs')), 'View: Focus Center Editor Group', category); -registry.registerWorkbenchAction(new SyncActionDescriptor(FocusThirdGroupAction, FocusThirdGroupAction.ID, FocusThirdGroupAction.LABEL, { primary: KeyMod.CtrlCmd | KeyCode.KEY_3 }, KbExpr.has('!config.workbench.showEditorTabs')), 'View: Focus Right Editor Group', category); -registry.registerWorkbenchAction(new SyncActionDescriptor(FocusLastEditorInStackAction, FocusLastEditorInStackAction.ID, FocusLastEditorInStackAction.LABEL, { primary: KeyMod.CtrlCmd | KeyCode.KEY_0 }, KbExpr.has('config.workbench.showEditorTabs')), 'View: Focus Last Editor in Group', category); +registry.registerWorkbenchAction(new SyncActionDescriptor(FocusFirstGroupAction, FocusFirstGroupAction.ID, FocusFirstGroupAction.LABEL, { primary: KeyMod.CtrlCmd | KeyCode.KEY_1 }, KbExpr.has('!config.workbench.editor.showTabs')), 'View: Focus Left Editor Group', category); +registry.registerWorkbenchAction(new SyncActionDescriptor(FocusSecondGroupAction, FocusSecondGroupAction.ID, FocusSecondGroupAction.LABEL, { primary: KeyMod.CtrlCmd | KeyCode.KEY_2 }, KbExpr.has('!config.workbench.editor.showTabs')), 'View: Focus Center Editor Group', category); +registry.registerWorkbenchAction(new SyncActionDescriptor(FocusThirdGroupAction, FocusThirdGroupAction.ID, FocusThirdGroupAction.LABEL, { primary: KeyMod.CtrlCmd | KeyCode.KEY_3 }, KbExpr.has('!config.workbench.editor.showTabs')), 'View: Focus Right Editor Group', category); +registry.registerWorkbenchAction(new SyncActionDescriptor(FocusLastEditorInStackAction, FocusLastEditorInStackAction.ID, FocusLastEditorInStackAction.LABEL, { primary: KeyMod.CtrlCmd | KeyCode.KEY_0 }, KbExpr.has('config.workbench.editor.showTabs')), 'View: Focus Last Editor in Group', category); registry.registerWorkbenchAction(new SyncActionDescriptor(EvenGroupWidthsAction, EvenGroupWidthsAction.ID, EvenGroupWidthsAction.LABEL), 'View: Even Editor Group Widths', category); registry.registerWorkbenchAction(new SyncActionDescriptor(MaximizeGroupAction, MaximizeGroupAction.ID, MaximizeGroupAction.LABEL), 'View: Maximize Editor Group and Hide Sidebar', category); registry.registerWorkbenchAction(new SyncActionDescriptor(MinimizeOtherGroupsAction, MinimizeOtherGroupsAction.ID, MinimizeOtherGroupsAction.LABEL), 'View: Minimize Other Editor Groups', category); @@ -331,7 +331,7 @@ for (let i = 0; i < 9; i++) { KeybindingsRegistry.registerCommandDesc({ id: 'workbench.action.openEditorAtIndex' + visibleIndex, weight: KeybindingsRegistry.WEIGHT.workbenchContrib(), - when: KbExpr.has('config.workbench.showEditorTabs'), + when: KbExpr.has('config.workbench.editor.showTabs'), primary: KeyMod.CtrlCmd | toKeyCode(visibleIndex), handler: accessor => { const editorService = accessor.get(IWorkbenchEditorService); diff --git a/src/vs/workbench/browser/parts/sidebar/sidebarPart.ts b/src/vs/workbench/browser/parts/sidebar/sidebarPart.ts index 609e408a6eb..ede8570b8fd 100644 --- a/src/vs/workbench/browser/parts/sidebar/sidebarPart.ts +++ b/src/vs/workbench/browser/parts/sidebar/sidebarPart.ts @@ -129,4 +129,4 @@ export class FocusSideBarAction extends Action { let registry = Registry.as(ActionExtensions.WorkbenchActions); registry.registerWorkbenchAction(new SyncActionDescriptor(FocusSideBarAction, FocusSideBarAction.ID, FocusSideBarAction.LABEL, { primary: KeyMod.CtrlCmd | KeyCode.KEY_0 -}, KbExpr.has('!config.workbench.showEditorTabs')), 'View: Focus into Side Bar', nls.localize('viewCategory', "View")); +}, KbExpr.has('!config.workbench.editor.showTabs')), 'View: Focus into Side Bar', nls.localize('viewCategory', "View")); From f2cbc150f7c8addd0579208c3bb3aceca4fa99c9 Mon Sep 17 00:00:00 2001 From: Daniel Imms Date: Thu, 16 Jun 2016 11:26:39 -0700 Subject: [PATCH 165/217] Update xterm.js version --- package.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/package.json b/package.json index 218a57fec22..9dd9d64c2d1 100644 --- a/package.json +++ b/package.json @@ -31,7 +31,7 @@ "vscode-debugprotocol": "1.9.0", "vscode-textmate": "1.1.0", "winreg": "1.2.0", - "xterm": "git+https://github.com/sourcelair/xterm.js.git#9d34ed8", + "xterm": "git+https://github.com/sourcelair/xterm.js.git#09d67a6", "yauzl": "2.3.1" }, "devDependencies": { From 93e65224d7598017bfa0b188a0d82b66a2ee9698 Mon Sep 17 00:00:00 2001 From: Daniel Imms Date: Thu, 16 Jun 2016 11:41:18 -0700 Subject: [PATCH 166/217] Add linux setup link to packages Fixes #6559 --- resources/linux/debian/control.template | 2 +- resources/linux/rpm/code.spec.template | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/resources/linux/debian/control.template b/resources/linux/debian/control.template index f92290eb12b..1d1cc3c4a83 100644 --- a/resources/linux/debian/control.template +++ b/resources/linux/debian/control.template @@ -9,4 +9,4 @@ Homepage: https://code.visualstudio.com/ Installed-Size: @@INSTALLEDSIZE@@ Replaces: visual-studio-@@NAME@@ Description: Code editing. Redefined. - Visual Studio Code is a new choice of tool that combines the simplicity of a code editor with what developers need for the core edit-build-debug cycle. + Visual Studio Code is a new choice of tool that combines the simplicity of a code editor with what developers need for the core edit-build-debug cycle. See https://code.visualstudio.com/docs/setup/linux for installation instructions and FAQ. diff --git a/resources/linux/rpm/code.spec.template b/resources/linux/rpm/code.spec.template index 52abe620fe0..17b1c63b7d9 100644 --- a/resources/linux/rpm/code.spec.template +++ b/resources/linux/rpm/code.spec.template @@ -12,7 +12,7 @@ Requires: glibc >= 2.15 AutoReq: 0 %description -Visual Studio Code is a new choice of tool that combines the simplicity of a code editor with what developers need for the core edit-build-debug cycle. +Visual Studio Code is a new choice of tool that combines the simplicity of a code editor with what developers need for the core edit-build-debug cycle. See https://code.visualstudio.com/docs/setup/linux for installation instructions and FAQ. %install mkdir -p %{buildroot}/usr/share/@@NAME@@ From 1c93c8e2438980b365068d5bbea7a5b6ef326422 Mon Sep 17 00:00:00 2001 From: Benjamin Pasero Date: Fri, 17 Jun 2016 07:37:09 +0200 Subject: [PATCH 167/217] wip --- .../browser/parts/editor/media/sidebyside.css | 8 ++ .../parts/editor/sideBySideEditorControl.ts | 74 ++++++++++++++----- 2 files changed, 64 insertions(+), 18 deletions(-) diff --git a/src/vs/workbench/browser/parts/editor/media/sidebyside.css b/src/vs/workbench/browser/parts/editor/media/sidebyside.css index 5eeb1bf17ed..6be7b4f9775 100644 --- a/src/vs/workbench/browser/parts/editor/media/sidebyside.css +++ b/src/vs/workbench/browser/parts/editor/media/sidebyside.css @@ -11,6 +11,14 @@ background-color: #252526; } +#monaco-workbench-editor-move-overlay, +#monaco-workbench-editor-drop-overlay { + position: absolute; + left: 0; + width: 100%; + height: 100%; + z-index: 3000000; +} .vs #monaco-workbench-editor-drop-overlay, .vs .monaco-workbench .editor.empty > .content.dropfeedback { diff --git a/src/vs/workbench/browser/parts/editor/sideBySideEditorControl.ts b/src/vs/workbench/browser/parts/editor/sideBySideEditorControl.ts index 2dc74ae75aa..13c9b90fd34 100644 --- a/src/vs/workbench/browser/parts/editor/sideBySideEditorControl.ts +++ b/src/vs/workbench/browser/parts/editor/sideBySideEditorControl.ts @@ -85,6 +85,7 @@ export class SideBySideEditorControl implements ISideBySideEditorControl, IVerti private static MIN_EDITOR_WIDTH = 170; private static EDITOR_TITLE_HEIGHT = 35; private static SNAP_TO_MINIMIZED_THRESHOLD = 50; + private static SHOW_SPLIT_DROP_FEEDBACK_THRESHOLD = 50; private stacks: IEditorStacksModel; @@ -757,9 +758,10 @@ export class SideBySideEditorControl implements ISideBySideEditorControl, IVerti private enableDropTarget(node: HTMLElement): void { const $this = this; const overlayId = 'monaco-workbench-editor-drop-overlay'; + const splitToPropertyKey = 'splitToPosition'; let overlay: Builder; - function onDrop(e: DragEvent, position: Position): void { + function onDrop(e: DragEvent, position: Position, splitTo?: Position): void { DOM.removeClass(node, 'dropfeedback'); destroyOverlay(); @@ -781,10 +783,21 @@ export class SideBySideEditorControl implements ISideBySideEditorControl, IVerti if (droppedResources.length) { window.focus(); // make sure this window has focus so that the open call reaches the right window! - // Open all - $this.editorService.openEditors(droppedResources.map(resource => { return { input: { resource, options: { pinned: true } }, position }; })) - .then(() => $this.editorGroupService.focusGroup(position)) + if (splitTo === Position.LEFT && position === Position.LEFT && $this.stacks.groups.length === 1) { + $this.editorService.openEditors(droppedResources.map(resource => { return { input: { resource, options: { pinned: true } }, position: Position.CENTER }; })) + .then(() => { + $this.editorGroupService.moveGroup(Position.LEFT, Position.CENTER); + $this.editorGroupService.focusGroup(position); + }) .done(null, errors.onUnexpectedError); + } + + // Open all + else { + $this.editorService.openEditors(droppedResources.map(resource => { return { input: { resource, options: { pinned: true } }, position }; })) + .then(() => $this.editorGroupService.focusGroup(position)) + .done(null, errors.onUnexpectedError); + } } } } @@ -796,25 +809,55 @@ export class SideBySideEditorControl implements ISideBySideEditorControl, IVerti } } + function positionOverlay(e: DragEvent, groups: number, position: Position): void { + const target = e.target; + const posXOnOverlay = e.offsetX; + const overlayWidth = target.clientWidth; + + if (groups === POSITIONS.length) { + return; // do not show split feedback when we already at the maximum + } + + if (posXOnOverlay + SideBySideEditorControl.SHOW_SPLIT_DROP_FEEDBACK_THRESHOLD > overlayWidth) { + overlay.setProperty(splitToPropertyKey, position === Position.LEFT ? Position.CENTER : Position.RIGHT); + overlay.style({ + left: '50%', + width: '50%', + }); + } else if (posXOnOverlay < SideBySideEditorControl.SHOW_SPLIT_DROP_FEEDBACK_THRESHOLD) { + overlay.setProperty(splitToPropertyKey, position === Position.LEFT ? Position.LEFT : Position.CENTER); + overlay.style({ + width: '50%' + }); + } else { + overlay.removeProperty(splitToPropertyKey); + overlay.style({ + left: '0', + width: '100%' + }); + } + } + function createOverlay(target: HTMLElement): void { if (!overlay) { - $this.visibleEditorContainers.forEach((container, index) => { + const containers = $this.visibleEditorContainers.filter(c => !!c); + containers.forEach((container, index) => { if (container && DOM.isAncestor(target, container.getHTMLElement())) { const useTabs = !!$this.configurationService.getConfiguration().workbench.editor.showTabs; overlay = $('div').style({ - position: 'absolute', - top: useTabs ? SideBySideEditorControl.EDITOR_TITLE_HEIGHT + 'px' : 0, - left: 0, - width: '100%', - height: '100%', - zIndex: 3000000 + top: useTabs ? SideBySideEditorControl.EDITOR_TITLE_HEIGHT + 'px' : 0 }).id(overlayId); + overlay.appendTo(container); overlay.on(DOM.EventType.DROP, (e: DragEvent) => { DOM.EventHelper.stop(e, true); - onDrop(e, index); + onDrop(e, index, overlay.getProperty(splitToPropertyKey)); + }); + + overlay.on(DOM.EventType.DRAG_OVER, (e: DragEvent) => { + positionOverlay(e, containers.length, index); }); overlay.on([DOM.EventType.DRAG_LEAVE, DOM.EventType.DRAG_END], () => { @@ -894,12 +937,7 @@ export class SideBySideEditorControl implements ISideBySideEditorControl, IVerti // Overlay the editor area with a div to be able to capture all mouse events let overlayDiv = $('div').style({ - position: 'absolute', - top: SideBySideEditorControl.EDITOR_TITLE_HEIGHT + 'px', - left: 0, - width: '100%', - height: '100%', - zIndex: 3000000 + top: SideBySideEditorControl.EDITOR_TITLE_HEIGHT + 'px' }).id('monaco-workbench-editor-move-overlay'); overlayDiv.appendTo(this.parent); From dfd22e210d9515eca5062f6cdf3dad76bf889c49 Mon Sep 17 00:00:00 2001 From: Joao Moreno Date: Fri, 17 Jun 2016 08:49:29 +0200 Subject: [PATCH 168/217] fix query length from 1000 to ids.length --- .../extensionManagement/node/extensionManagementUtil.ts | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/src/vs/platform/extensionManagement/node/extensionManagementUtil.ts b/src/vs/platform/extensionManagement/node/extensionManagementUtil.ts index 16e731698e5..38f64108a0c 100644 --- a/src/vs/platform/extensionManagement/node/extensionManagementUtil.ts +++ b/src/vs/platform/extensionManagement/node/extensionManagementUtil.ts @@ -36,7 +36,11 @@ export function getOutdatedExtensions(extensionsService: IExtensionManagementSer return extensionsService.getInstalled().then(installed => { const ids = installed.map(getExtensionId); - return galleryService.query({ ids, pageSize: 1000 }).then(result => { + if (installed.length === 0) { + return TPromise.as([]); + } + + return galleryService.query({ ids, pageSize: ids.length }).then(result => { const available = result.firstPage; return available.filter(extension => { From 7cec6dec5850a73b919c105a05f4a52aaa8551ca Mon Sep 17 00:00:00 2001 From: Joao Moreno Date: Fri, 17 Jun 2016 09:02:43 +0200 Subject: [PATCH 169/217] :lipstick: --- src/vs/workbench/electron-browser/main.contribution.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/vs/workbench/electron-browser/main.contribution.ts b/src/vs/workbench/electron-browser/main.contribution.ts index 0ffb3c42635..dfa74e52f95 100644 --- a/src/vs/workbench/electron-browser/main.contribution.ts +++ b/src/vs/workbench/electron-browser/main.contribution.ts @@ -80,7 +80,7 @@ configurationRegistry.registerConfiguration({ 'type': 'string', 'enum': ['none', 'default'], 'default': 'default', - 'description': nls.localize('updateChannel', "Configure the update channel to receive updates from. Requires a restart after change.") + 'description': nls.localize('updateChannel', "Configure whether you receive automatic updates from an update channel. Requires a restart after change.") } } }); \ No newline at end of file From e65d79b1709dbb23e840f100ccd3f4be74e57b52 Mon Sep 17 00:00:00 2001 From: isidor Date: Fri, 17 Jun 2016 10:15:25 +0200 Subject: [PATCH 170/217] open editors: also us index of open editor in group for id fixes #7781 --- src/vs/workbench/parts/files/browser/views/openEditorsViewer.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/vs/workbench/parts/files/browser/views/openEditorsViewer.ts b/src/vs/workbench/parts/files/browser/views/openEditorsViewer.ts index 1063cd2fb94..bfc700188ee 100644 --- a/src/vs/workbench/parts/files/browser/views/openEditorsViewer.ts +++ b/src/vs/workbench/parts/files/browser/views/openEditorsViewer.ts @@ -50,7 +50,7 @@ export class OpenEditor { } public getId(): string { - return `openeditor:${this.group.id}:${this.editor.getName()}:${this.editor.getDescription()}`; + return `openeditor:${this.group.id}:${this.group.indexOf(this.editor)}:${this.editor.getName()}:${this.editor.getDescription()}`; } public isPreview(): boolean { From 16331b1a5730fd7059c64bd289f903950e140942 Mon Sep 17 00:00:00 2001 From: Benjamin Pasero Date: Fri, 17 Jun 2016 10:19:07 +0200 Subject: [PATCH 171/217] drag to split --- .../browser/parts/editor/editorPart.ts | 4 +- .../parts/editor/sideBySideEditorControl.ts | 70 ++++++++++++++----- 2 files changed, 53 insertions(+), 21 deletions(-) diff --git a/src/vs/workbench/browser/parts/editor/editorPart.ts b/src/vs/workbench/browser/parts/editor/editorPart.ts index e6344c0d5d5..bdae70268ef 100644 --- a/src/vs/workbench/browser/parts/editor/editorPart.ts +++ b/src/vs/workbench/browser/parts/editor/editorPart.ts @@ -932,8 +932,8 @@ export class EditorPart extends Part implements IEditorPart, IEditorGroupService // Validate width ratios const positions = rightEditors.length ? 3 : centerEditors.length ? 2 : 1; - if (!widthRatios || widthRatios.length !== positions) { - widthRatios = (positions === 3) ? [0.33, 0.33, 0.34] : (positions === 2) ? [0.5, 0.5] : [1]; + if (widthRatios.length !== positions) { + widthRatios = void 0; // being taken care of by the layouting } // Open each input respecting the options. Since there can only be one active editor in each diff --git a/src/vs/workbench/browser/parts/editor/sideBySideEditorControl.ts b/src/vs/workbench/browser/parts/editor/sideBySideEditorControl.ts index 13c9b90fd34..11071d07b9e 100644 --- a/src/vs/workbench/browser/parts/editor/sideBySideEditorControl.ts +++ b/src/vs/workbench/browser/parts/editor/sideBySideEditorControl.ts @@ -85,7 +85,6 @@ export class SideBySideEditorControl implements ISideBySideEditorControl, IVerti private static MIN_EDITOR_WIDTH = 170; private static EDITOR_TITLE_HEIGHT = 35; private static SNAP_TO_MINIMIZED_THRESHOLD = 50; - private static SHOW_SPLIT_DROP_FEEDBACK_THRESHOLD = 50; private stacks: IEditorStacksModel; @@ -765,15 +764,45 @@ export class SideBySideEditorControl implements ISideBySideEditorControl, IVerti DOM.removeClass(node, 'dropfeedback'); destroyOverlay(); + const editorService = $this.editorService; + const groupService = $this.editorGroupService; + const stacks = groupService.getStacksModel(); + + const splitEditor = (typeof splitTo === 'number'); // TODO@Ben ugly split code should benefit from empty group support once available! + const freeGroup = (stacks.groups.length === 1) ? Position.CENTER : Position.RIGHT; + const pinned = EditorOptions.create({ pinned: true }); + // Check for transfer from title control const draggedEditor = TitleControl.getDraggedEditor(); if (draggedEditor) { const isCopy = (e.ctrlKey && !isMacintosh) || (e.altKey && isMacintosh); + + // Copy editor to new location if (isCopy) { - $this.editorService.openEditor(draggedEditor.editor, EditorOptions.create({ pinned: true }), position).done(null, errors.onUnexpectedError); - } else { - const sourcePosition = $this.stacks.positionOfGroup(draggedEditor.group); - $this.editorGroupService.moveEditor(draggedEditor.editor, sourcePosition, position); + if (splitEditor) { + editorService.openEditor(draggedEditor.editor, pinned, freeGroup).then(() => { + if (splitTo !== freeGroup) { + groupService.moveGroup(freeGroup, splitTo); + } + }); + } else { + editorService.openEditor(draggedEditor.editor, pinned, position).done(null, errors.onUnexpectedError); + } + } + + // Move editor to new location + else { + const sourcePosition = stacks.positionOfGroup(draggedEditor.group); + if (splitEditor) { + editorService.openEditor(draggedEditor.editor, pinned, freeGroup).then(() => { + if (splitTo !== freeGroup) { + groupService.moveGroup(freeGroup, splitTo); + } + groupService.moveEditor(draggedEditor.editor, stacks.positionOfGroup(draggedEditor.group), splitTo); + }); + } else { + groupService.moveEditor(draggedEditor.editor, sourcePosition, position); + } } } @@ -783,21 +812,16 @@ export class SideBySideEditorControl implements ISideBySideEditorControl, IVerti if (droppedResources.length) { window.focus(); // make sure this window has focus so that the open call reaches the right window! - if (splitTo === Position.LEFT && position === Position.LEFT && $this.stacks.groups.length === 1) { - $this.editorService.openEditors(droppedResources.map(resource => { return { input: { resource, options: { pinned: true } }, position: Position.CENTER }; })) + // Open all + editorService.openEditors(droppedResources.map(resource => { return { input: { resource, options: { pinned: true } }, position: splitEditor ? freeGroup : position }; })) .then(() => { - $this.editorGroupService.moveGroup(Position.LEFT, Position.CENTER); - $this.editorGroupService.focusGroup(position); + if (splitEditor && splitTo !== freeGroup) { + groupService.moveGroup(freeGroup, splitTo); + } + + groupService.focusGroup(splitEditor ? splitTo : position); }) .done(null, errors.onUnexpectedError); - } - - // Open all - else { - $this.editorService.openEditors(droppedResources.map(resource => { return { input: { resource, options: { pinned: true } }, position }; })) - .then(() => $this.editorGroupService.focusGroup(position)) - .done(null, errors.onUnexpectedError); - } } } } @@ -812,19 +836,27 @@ export class SideBySideEditorControl implements ISideBySideEditorControl, IVerti function positionOverlay(e: DragEvent, groups: number, position: Position): void { const target = e.target; const posXOnOverlay = e.offsetX; + const overlayIsSplit = typeof overlay.getProperty(splitToPropertyKey) === 'number'; const overlayWidth = target.clientWidth; + const splitThreshold = overlayIsSplit ? overlayWidth / 5 : overlayWidth / 10; + const isCopy = (e.ctrlKey && !isMacintosh) || (e.altKey && isMacintosh); if (groups === POSITIONS.length) { return; // do not show split feedback when we already at the maximum } - if (posXOnOverlay + SideBySideEditorControl.SHOW_SPLIT_DROP_FEEDBACK_THRESHOLD > overlayWidth) { + const draggedEditor = TitleControl.getDraggedEditor(); + if (!isCopy && draggedEditor && draggedEditor.group.count === 1) { + return; // do not show split feedback when moving the only one editor of a group + } + + if (posXOnOverlay + splitThreshold > overlayWidth) { overlay.setProperty(splitToPropertyKey, position === Position.LEFT ? Position.CENTER : Position.RIGHT); overlay.style({ left: '50%', width: '50%', }); - } else if (posXOnOverlay < SideBySideEditorControl.SHOW_SPLIT_DROP_FEEDBACK_THRESHOLD) { + } else if (posXOnOverlay < splitThreshold) { overlay.setProperty(splitToPropertyKey, position === Position.LEFT ? Position.LEFT : Position.CENTER); overlay.style({ width: '50%' From 8559fd44f010d8793d695b8896fc67a7f299f16b Mon Sep 17 00:00:00 2001 From: Benjamin Pasero Date: Fri, 17 Jun 2016 11:04:24 +0200 Subject: [PATCH 172/217] stacks: emit move event for groups when a group closes pushing the others to the left --- .../workbench/common/editor/editorStacksModel.ts | 5 ++++- .../test/common/editor/editorStacksModel.test.ts | 15 +++++++++++++++ 2 files changed, 19 insertions(+), 1 deletion(-) diff --git a/src/vs/workbench/common/editor/editorStacksModel.ts b/src/vs/workbench/common/editor/editorStacksModel.ts index 1ab6b5d8c03..f1663615a6f 100644 --- a/src/vs/workbench/common/editor/editorStacksModel.ts +++ b/src/vs/workbench/common/editor/editorStacksModel.ts @@ -822,8 +822,11 @@ export class EditorStacksModel implements IEditorStacksModel { this._groups.splice(index, 1); this.groupToIdentifier[group.id] = void 0; - // Event + // Events this.fireEvent(this._onGroupClosed, group, true); + for (let i = index; i < this._groups.length; i++) { + this.fireEvent(this._onGroupMoved, this._groups[i], true); // send move event for groups to the right that moved to the left into the closed group position + } } public closeGroups(except?: EditorGroup): void { diff --git a/src/vs/workbench/test/common/editor/editorStacksModel.test.ts b/src/vs/workbench/test/common/editor/editorStacksModel.test.ts index 28864d6f511..b0282df59e2 100644 --- a/src/vs/workbench/test/common/editor/editorStacksModel.test.ts +++ b/src/vs/workbench/test/common/editor/editorStacksModel.test.ts @@ -266,6 +266,21 @@ suite('Editor Stacks Model', () => { assert.equal(model.groups.length, 0); }); + test('Groups - Close Group sends move event for others to the right', function () { + const model = create(); + const events = modelListener(model); + + const first = model.openGroup('first'); + model.openGroup('second'); + const third = model.openGroup('third'); + + model.closeGroup(first); + assert.equal(events.moved.length, 2); + + model.closeGroup(third); + assert.equal(events.moved.length, 2); + }); + test('Groups - Move Groups', function () { const model = create(); const events = modelListener(model); From f23877c4edc5f1e71f932de3a9e46665ab309c8b Mon Sep 17 00:00:00 2001 From: Johannes Rieken Date: Fri, 17 Jun 2016 11:23:10 +0200 Subject: [PATCH 173/217] md - differentiate between showPreview and showSource having two distinct commands allows us to have a context menu action in the explorer to show a preview --- extensions/markdown/package.json | 23 ++++++++----- extensions/markdown/package.nls.json | 1 + extensions/markdown/src/extension.ts | 50 +++++++++++++++++++--------- 3 files changed, 51 insertions(+), 23 deletions(-) diff --git a/extensions/markdown/package.json b/extensions/markdown/package.json index 0a9ad0e646e..27d4fa8c058 100644 --- a/extensions/markdown/package.json +++ b/extensions/markdown/package.json @@ -12,8 +12,8 @@ "Languages" ], "activationEvents": [ - "onCommand:extension.previewMarkdown", - "onCommand:extension.previewMarkdownSide" + "onCommand:markdown.showPreview", + "onCommand:markdown.showPreviewToSide" ], "contributes": { "languages": [ @@ -41,7 +41,14 @@ ], "commands": [ { - "command": "extension.previewMarkdown", + "command": "markdown.showPreview", + "title": "%markdown.openPreview%", + "category": "%markdown.category%", + "where": ["explorer/context"], + "when": "markdown" + }, + { + "command": "markdown.showPreview", "title": "%markdown.previewMarkdown.title%", "category": "%markdown.category%", "icon": { @@ -52,6 +59,7 @@ "when": "markdown" }, { + "command": "markdown.showSource", "title": "%markdown.previewMarkdown.title%", "category": "%markdown.category%", "icon": { @@ -59,11 +67,10 @@ "dark": "./media/ViewSource_inverse.svg" }, "where": ["editor/primary"], - "when": { "scheme": "markdown" }, - "command": "extension.previewMarkdown" + "when": { "scheme": "markdown" } }, { - "command": "extension.previewMarkdownSide", + "command": "markdown.showPreviewToSide", "title": "%markdown.previewMarkdownSide.title%", "where": "editor/secondary", "when": "markdown" @@ -71,12 +78,12 @@ ], "keybindings": [ { - "command": "extension.previewMarkdown", + "command": "markdown.showPreview", "key": "shift+ctrl+v", "mac": "shift+cmd+v" }, { - "command": "extension.previewMarkdownSide", + "command": "markdown.showPreviewToSide", "key": "ctrl+k v", "mac": "cmd+k v" } diff --git a/extensions/markdown/package.nls.json b/extensions/markdown/package.nls.json index d41fc234818..8c3b2a994bc 100644 --- a/extensions/markdown/package.nls.json +++ b/extensions/markdown/package.nls.json @@ -1,5 +1,6 @@ { "markdown.category" : "Markdown", + "markdown.openPreview" : "Open Preview", "markdown.previewMarkdown.title" : "Toggle Preview", "markdown.previewMarkdownSide.title" : "Open Preview to the Side" } \ No newline at end of file diff --git a/extensions/markdown/src/extension.ts b/extensions/markdown/src/extension.ts index bc0835469d2..99486ad5451 100644 --- a/extensions/markdown/src/extension.ts +++ b/extensions/markdown/src/extension.ts @@ -27,21 +27,22 @@ export function activate(context: ExtensionContext) { let provider = new MDDocumentContentProvider(context); let registration = vscode.workspace.registerTextDocumentContentProvider('markdown', provider); - let d1 = vscode.commands.registerCommand('extension.previewMarkdown', () => openPreview()); - let d2 = vscode.commands.registerCommand('extension.previewMarkdownSide', () => openPreview(true)); + let d1 = vscode.commands.registerCommand('markdown.showPreview', showPreview); + let d2 = vscode.commands.registerCommand('markdown.showPreviewToSide', uri => showPreview(uri, true)); + let d3 = vscode.commands.registerCommand('markdown.showSource', showSource); - context.subscriptions.push(d1, d2, registration); + context.subscriptions.push(d1, d2, d3, registration); vscode.workspace.onDidSaveTextDocument(document => { if (isMarkdownFile(document)) { - const uri = getMarkdownUri(document); + const uri = getMarkdownUri(document.uri); provider.update(uri); } }); vscode.workspace.onDidChangeTextDocument(event => { if (isMarkdownFile(event.document)) { - const uri = getMarkdownUri(event.document); + const uri = getMarkdownUri(event.document.uri); provider.update(uri); } @@ -61,22 +62,28 @@ function isMarkdownFile(document: vscode.TextDocument) { && document.uri.scheme !== 'markdown'; // prevent processing of own documents } -function getMarkdownUri(document: vscode.TextDocument) { - return document.uri.with({ scheme: 'markdown', path: document.uri.path + '.rendered', query: document.uri.toString() }); +function getMarkdownUri(uri: Uri) { + return uri.with({ scheme: 'markdown', path: uri.path + '.rendered', query: uri.toString() }); } -function openPreview(sideBySide?: boolean): void { - const activeEditor = vscode.window.activeTextEditor; - if (!activeEditor) { - vscode.commands.executeCommand('workbench.action.navigateBack'); +function showPreview(resource?: Uri, sideBySide: boolean = false) { + + if (!(resource instanceof Uri)) { + if (vscode.window.activeTextEditor) { + // we are relaxed and don't check for markdown files + resource = vscode.window.activeTextEditor.document.uri; + } + } + + if (!(resource instanceof Uri)) { + // nothing found that could be shown return; } - let markdownPreviewUri = getMarkdownUri(activeEditor.document); - vscode.commands.executeCommand('vscode.previewHtml', - markdownPreviewUri, + return vscode.commands.executeCommand('vscode.previewHtml', + getMarkdownUri(resource), getViewColumn(sideBySide), - `Preview '${path.basename(activeEditor.document.fileName)}'`); + `Preview '${path.basename(resource.fsPath)}'`); } function getViewColumn(sideBySide): ViewColumn { @@ -99,6 +106,19 @@ function getViewColumn(sideBySide): ViewColumn { return active.viewColumn; } +function showSource(mdUri: Uri) { + const docUri = Uri.parse(mdUri.query); + + for (let editor of vscode.window.visibleTextEditors) { + if (editor.document.uri.toString() === docUri.toString()) { + return vscode.window.showTextDocument(editor.document, editor.viewColumn); + } + } + + return vscode.workspace.openTextDocument(docUri).then(doc => { + return vscode.window.showTextDocument(doc); + }); +} class MDDocumentContentProvider implements TextDocumentContentProvider { private _context: ExtensionContext; From 77ed90567120d275fc232274162a298582e0f781 Mon Sep 17 00:00:00 2001 From: Benjamin Pasero Date: Fri, 17 Jun 2016 11:25:19 +0200 Subject: [PATCH 174/217] fire move event for all groups --- .../common/editor/editorStacksModel.ts | 4 ++- .../common/editor/editorStacksModel.test.ts | 34 +++++++++++++++++-- 2 files changed, 35 insertions(+), 3 deletions(-) diff --git a/src/vs/workbench/common/editor/editorStacksModel.ts b/src/vs/workbench/common/editor/editorStacksModel.ts index f1663615a6f..287e76b2a18 100644 --- a/src/vs/workbench/common/editor/editorStacksModel.ts +++ b/src/vs/workbench/common/editor/editorStacksModel.ts @@ -870,7 +870,9 @@ export class EditorStacksModel implements IEditorStacksModel { this._groups.splice(toIndex, 0, group); // Event - this.fireEvent(this._onGroupMoved, group, true); + for (let i = Math.min(index, toIndex); i <= Math.max(index, toIndex) && i < this._groups.length; i++) { + this.fireEvent(this._onGroupMoved, this._groups[i], true); // send move event for groups to the right that moved to the left into the closed group position + } } private indexOf(group: EditorGroup): number { diff --git a/src/vs/workbench/test/common/editor/editorStacksModel.test.ts b/src/vs/workbench/test/common/editor/editorStacksModel.test.ts index b0282df59e2..c268ae33c7e 100644 --- a/src/vs/workbench/test/common/editor/editorStacksModel.test.ts +++ b/src/vs/workbench/test/common/editor/editorStacksModel.test.ts @@ -308,13 +308,11 @@ suite('Editor Stacks Model', () => { test('Groups - Rename Group', function () { const model = create(); - const events = modelListener(model); const group1 = model.openGroup('first'); const group2 = model.openGroup('second'); model.moveGroup(group1, 1); - assert.equal(events.moved[0], group1); assert.equal(model.groups[0], group2); assert.equal(model.groups[1], group1); @@ -331,6 +329,38 @@ suite('Editor Stacks Model', () => { assert.equal(model.groups[2], group1); }); + test('Groups - Move Group sends move events for all moved groups', function () { + const model = create(); + let events = modelListener(model); + + let group1 = model.openGroup('first'); + let group2 = model.openGroup('second'); + let group3 = model.openGroup('third'); + + model.moveGroup(group1, 1); + assert.equal(events.moved.length, 2); + + model.closeGroups(); + + events = modelListener(model); + group1 = model.openGroup('first'); + group2 = model.openGroup('second'); + group3 = model.openGroup('third'); + + model.moveGroup(group1, 2); + assert.equal(events.moved.length, 3); + + model.closeGroups(); + + events = modelListener(model); + group1 = model.openGroup('first'); + group2 = model.openGroup('second'); + group3 = model.openGroup('third'); + + model.moveGroup(group3, 1); + assert.equal(events.moved.length, 2); + }); + test('Groups - Event Aggregation', function () { const model = create(); From 2cac9dd2fa3f202efcd723f8aeda4b6c6782f78d Mon Sep 17 00:00:00 2001 From: Benjamin Pasero Date: Fri, 17 Jun 2016 11:54:48 +0200 Subject: [PATCH 175/217] more consistent openEditors() behaviour --- src/vs/workbench/browser/workbench.ts | 2 +- .../parts/files/electron-browser/electronFileTracker.ts | 3 ++- 2 files changed, 3 insertions(+), 2 deletions(-) diff --git a/src/vs/workbench/browser/workbench.ts b/src/vs/workbench/browser/workbench.ts index a8e8ea11622..07d83498e13 100644 --- a/src/vs/workbench/browser/workbench.ts +++ b/src/vs/workbench/browser/workbench.ts @@ -241,7 +241,7 @@ export class Workbench implements IPartService { return { input: inputWithOptions.input, options: inputWithOptions.options, - position: Math.min(index, Position.RIGHT) // put any resource > RIGHT to right position + position: Position.LEFT }; }); diff --git a/src/vs/workbench/parts/files/electron-browser/electronFileTracker.ts b/src/vs/workbench/parts/files/electron-browser/electronFileTracker.ts index b1a414925df..94bbb204e8a 100644 --- a/src/vs/workbench/parts/files/electron-browser/electronFileTracker.ts +++ b/src/vs/workbench/parts/files/electron-browser/electronFileTracker.ts @@ -137,10 +137,11 @@ export class FileTracker implements IWorkbenchContribution { } // Otherwise open all + const activeEditor = this.editorService.getActiveEditor(); return this.editorService.openEditors(resources.map((r, index) => { return { input: r, - position: Math.min(index, Position.RIGHT) // put any resource > RIGHT to right position + position: activeEditor ? activeEditor.position : Position.LEFT }; })); }); From a59654e933d6c1c0aa892b4b06c28aa2d0648444 Mon Sep 17 00:00:00 2001 From: isidor Date: Fri, 17 Jun 2016 12:27:08 +0200 Subject: [PATCH 176/217] debug: make toolbar moveable fixes #4580 --- .../parts/debug/browser/debugActionsWidget.ts | 43 ++++++++++++++++++- .../browser/media/debug.contribution.css | 11 ++++- .../parts/debug/browser/media/drag.svg | 8 ++++ 3 files changed, 59 insertions(+), 3 deletions(-) create mode 100644 src/vs/workbench/parts/debug/browser/media/drag.svg diff --git a/src/vs/workbench/parts/debug/browser/debugActionsWidget.ts b/src/vs/workbench/parts/debug/browser/debugActionsWidget.ts index ecb97c63c72..3cd5608d834 100644 --- a/src/vs/workbench/parts/debug/browser/debugActionsWidget.ts +++ b/src/vs/workbench/parts/debug/browser/debugActionsWidget.ts @@ -7,6 +7,8 @@ import lifecycle = require('vs/base/common/lifecycle'); import errors = require('vs/base/common/errors'); import severity from 'vs/base/common/severity'; import builder = require('vs/base/browser/builder'); +import dom = require('vs/base/browser/dom'); +import { StandardMouseEvent } from 'vs/base/browser/mouseEvent'; import actions = require('vs/base/common/actions'); import events = require('vs/base/common/events'); import actionbar = require('vs/base/browser/ui/actionbar/actionbar'); @@ -15,17 +17,20 @@ import wbext = require('vs/workbench/common/contributions'); import debug = require('vs/workbench/parts/debug/common/debug'); import dbgactions = require('vs/workbench/parts/debug/electron-browser/debugActions'); import { IInstantiationService } from 'vs/platform/instantiation/common/instantiation'; +import { IStorageService, StorageScope } from 'vs/platform/storage/common/storage'; import { IMessageService } from 'vs/platform/message/common/message'; import { ITelemetryService } from 'vs/platform/telemetry/common/telemetry'; import IDebugService = debug.IDebugService; const $ = builder.$; +const DEBUG_ACTIONS_WIDGET_POSITION_KEY = 'debug.actionswidgetposition'; export class DebugActionsWidget implements wbext.IWorkbenchContribution { private static ID = 'debug.actionsWidget'; private $el: builder.Builder; + private dragArea: builder.Builder; private toDispose: lifecycle.IDisposable[]; private actionBar: actionbar.ActionBar; private actions: actions.IAction[]; @@ -39,12 +44,18 @@ export class DebugActionsWidget implements wbext.IWorkbenchContribution { @IMessageService private messageService: IMessageService, @ITelemetryService private telemetryService: ITelemetryService, @IDebugService private debugService: IDebugService, - @IInstantiationService private instantiationService: IInstantiationService + @IInstantiationService private instantiationService: IInstantiationService, + @IStorageService private storageService: IStorageService ) { this.$el = $().div().addClass('debug-actions-widget'); + this.dragArea = $().div().addClass('drag-area'); + this.$el.append(this.dragArea); + + const actionBarContainter = $().div().addClass('.action-bar-container'); + this.$el.append(actionBarContainter); this.toDispose = []; - this.actionBar = new actionbar.ActionBar(this.$el, { + this.actionBar = new actionbar.ActionBar(actionBarContainter, { orientation: actionbar.ActionsOrientation.HORIZONTAL }); @@ -53,6 +64,7 @@ export class DebugActionsWidget implements wbext.IWorkbenchContribution { this.hide(); this.isBuilt = false; + this.onResize(); } private registerListeners(): void { @@ -70,6 +82,33 @@ export class DebugActionsWidget implements wbext.IWorkbenchContribution { this.telemetryService.publicLog('workbenchActionExecuted', { id: e.action.id, from: 'debugActionsWidget' }); } })); + $(window).on(dom.EventType.RESIZE, () => this.onResize(), this.toDispose); + + this.dragArea.on(dom.EventType.MOUSE_DOWN, event => { + const $window = $(window); + + $window.on('mousemove', (e: MouseEvent) => { + const mouseMoveEvent = new StandardMouseEvent(e); + this.setXCoordinate(mouseMoveEvent.posx); + }).once('mouseup', (e: MouseEvent) => { + const mouseMoveEvent = new StandardMouseEvent(e); + this.storageService.store(DEBUG_ACTIONS_WIDGET_POSITION_KEY, mouseMoveEvent.posx / window.innerWidth, StorageScope.WORKSPACE); + $window.off('mousemove'); + }); + }); + } + + private onResize(): void { + const x = parseFloat(this.storageService.get(DEBUG_ACTIONS_WIDGET_POSITION_KEY, StorageScope.WORKSPACE, '0.5')) * window.innerWidth; + this.setXCoordinate(x); + } + + private setXCoordinate(x: number): void { + const halfWidgetWidth = this.$el.getHTMLElement().clientWidth / 2; + x = x + halfWidgetWidth - 12; // take into account half the size of the widget + x = Math.max(148, x); // do not allow the widget to overflow on the left + x = Math.min(x, window.innerWidth - halfWidgetWidth); // do not allow the widget to overflow on the right + this.$el.style('left', `${x}px`); } public getId(): string { diff --git a/src/vs/workbench/parts/debug/browser/media/debug.contribution.css b/src/vs/workbench/parts/debug/browser/media/debug.contribution.css index 12a0ebf3d2d..8d683383b77 100644 --- a/src/vs/workbench/parts/debug/browser/media/debug.contribution.css +++ b/src/vs/workbench/parts/debug/browser/media/debug.contribution.css @@ -130,9 +130,18 @@ padding-top: 3px; left: 50%; margin-left: -96px; + display: flex; + padding-left: 7px; } -.monaco-workbench .debug-actions-widget > .monaco-action-bar .action-label { +.monaco-workbench .debug-actions-widget .drag-area { + cursor: -webkit-grabbing; + height: 32px; + width: 10px; + background: url('drag.svg') center center no-repeat; +} + +.monaco-workbench .debug-actions-widget .monaco-action-bar .action-label { width: 32px; height: 32px; margin-right: 0; diff --git a/src/vs/workbench/parts/debug/browser/media/drag.svg b/src/vs/workbench/parts/debug/browser/media/drag.svg new file mode 100644 index 00000000000..7f4145d742b --- /dev/null +++ b/src/vs/workbench/parts/debug/browser/media/drag.svg @@ -0,0 +1,8 @@ + + + + + + + + \ No newline at end of file From 6efb6f15001c22d3e9b1c1ac31c236dc83e2769e Mon Sep 17 00:00:00 2001 From: Benjamin Pasero Date: Fri, 17 Jun 2016 12:49:42 +0200 Subject: [PATCH 177/217] some fixes around untitled files --- src/vs/workbench/common/editor/untitledEditorInput.ts | 2 ++ src/vs/workbench/parts/files/browser/fileTracker.ts | 11 ++++++++--- 2 files changed, 10 insertions(+), 3 deletions(-) diff --git a/src/vs/workbench/common/editor/untitledEditorInput.ts b/src/vs/workbench/common/editor/untitledEditorInput.ts index 63b169ce2d9..a5e88527de7 100644 --- a/src/vs/workbench/common/editor/untitledEditorInput.ts +++ b/src/vs/workbench/common/editor/untitledEditorInput.ts @@ -99,6 +99,8 @@ export class UntitledEditorInput extends AbstractUntitledEditorInput { public revert(): TPromise { this.cachedModel.revert(); + this.dispose(); // a reverted untitled editor is no longer valid, so we dispose it + return TPromise.as(true); } diff --git a/src/vs/workbench/parts/files/browser/fileTracker.ts b/src/vs/workbench/parts/files/browser/fileTracker.ts index 7ebfdbc57bd..b4cebc89496 100644 --- a/src/vs/workbench/parts/files/browser/fileTracker.ts +++ b/src/vs/workbench/parts/files/browser/fileTracker.ts @@ -85,9 +85,14 @@ export class FileTracker implements IWorkbenchContribution { } // If a file becomes dirty but is not opened, we open it in the background - if (!this.stacks.isOpen(e.resource)) { - this.editorService.openEditor({ resource: e.resource, options: { inactive: true } }).done(null, errors.onUnexpectedError); - } + // Since it might be the intent of whoever created the model to show it shortly + // after, we delay this a little bit and check again if the editor has not been + // opened meanwhile + setTimeout(() => { + if (!this.stacks.isOpen(e.resource) && this.textFileService.isDirty(e.resource)) { + this.editorService.openEditor({ resource: e.resource, options: { inactive: true } }).done(null, errors.onUnexpectedError); + } + }, 500); } private onTextFileSaveError(e: TextFileChangeEvent): void { From 4c7717885efd835a24fa33285702f956346548b3 Mon Sep 17 00:00:00 2001 From: Benjamin Pasero Date: Fri, 17 Jun 2016 12:59:24 +0200 Subject: [PATCH 178/217] do not switch file when untitled is opened and explorer gets focu --- src/vs/workbench/parts/files/browser/views/explorerView.ts | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/src/vs/workbench/parts/files/browser/views/explorerView.ts b/src/vs/workbench/parts/files/browser/views/explorerView.ts index 369c87d6f11..d7fa1ed06e7 100644 --- a/src/vs/workbench/parts/files/browser/views/explorerView.ts +++ b/src/vs/workbench/parts/files/browser/views/explorerView.ts @@ -23,6 +23,7 @@ import {FileImportedEvent, RefreshViewExplorerAction, NewFolderAction, NewFileAc import {FileEditorInput} from 'vs/workbench/parts/files/browser/editors/fileEditorInput'; import {FileDragAndDrop, FileFilter, FileSorter, FileController, FileRenderer, FileDataSource, FileViewletState, FileAccessibilityProvider} from 'vs/workbench/parts/files/browser/views/explorerViewer'; import lifecycle = require('vs/base/common/lifecycle'); +import {UntitledEditorInput} from 'vs/workbench/common/editor/untitledEditorInput'; import {IEditor} from 'vs/platform/editor/common/editor'; import {IEditorGroupService} from 'vs/workbench/services/group/common/groupService'; import * as DOM from 'vs/base/browser/dom'; @@ -172,8 +173,8 @@ export class ExplorerView extends CollapsibleViewletView { } } - // Handle closed (convince explorer to not reopen any file when getting visible) - if (!activeInput) { + // Handle closed or untitled file (convince explorer to not reopen any file when getting visible) + if (activeInput instanceof UntitledEditorInput || !activeInput) { this.settings[ExplorerView.MEMENTO_LAST_ACTIVE_FILE_RESOURCE] = void 0; clearFocus = true; } From a7f869b3e189f130d7d059cace366e33877bccc2 Mon Sep 17 00:00:00 2001 From: isidor Date: Fri, 17 Jun 2016 13:04:17 +0200 Subject: [PATCH 179/217] debug: smoothe out the d&d for action bar --- src/vs/workbench/parts/debug/browser/debugActionsWidget.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/vs/workbench/parts/debug/browser/debugActionsWidget.ts b/src/vs/workbench/parts/debug/browser/debugActionsWidget.ts index 3cd5608d834..be03ff13a80 100644 --- a/src/vs/workbench/parts/debug/browser/debugActionsWidget.ts +++ b/src/vs/workbench/parts/debug/browser/debugActionsWidget.ts @@ -105,7 +105,7 @@ export class DebugActionsWidget implements wbext.IWorkbenchContribution { private setXCoordinate(x: number): void { const halfWidgetWidth = this.$el.getHTMLElement().clientWidth / 2; - x = x + halfWidgetWidth - 12; // take into account half the size of the widget + x = x + halfWidgetWidth - 16; // take into account half the size of the widget x = Math.max(148, x); // do not allow the widget to overflow on the left x = Math.min(x, window.innerWidth - halfWidgetWidth); // do not allow the widget to overflow on the right this.$el.style('left', `${x}px`); From d841d1d75d3468bd38839556bcbf8c5737a73cba Mon Sep 17 00:00:00 2001 From: isidor Date: Fri, 17 Jun 2016 15:46:45 +0200 Subject: [PATCH 180/217] debug: double click on variable to set value --- .../workbench/parts/debug/browser/debugViewer.ts | 16 ++++++++++++++++ .../workbench/parts/debug/browser/debugViews.ts | 2 +- 2 files changed, 17 insertions(+), 1 deletion(-) diff --git a/src/vs/workbench/parts/debug/browser/debugViewer.ts b/src/vs/workbench/parts/debug/browser/debugViewer.ts index 18efc7e919f..0f0e6601ef0 100644 --- a/src/vs/workbench/parts/debug/browser/debugViewer.ts +++ b/src/vs/workbench/parts/debug/browser/debugViewer.ts @@ -668,6 +668,22 @@ export class VariablesAccessibilityProvider implements tree.IAccessibilityProvid } } +export class VariablesController extends BaseDebugController { + + protected onLeftClick(tree: tree.ITree, element: any, event: IMouseEvent): boolean { + // double click on primitive value: open input box to be able to set the value + if (element instanceof model.Variable && event.detail === 2) { + const expression = element; + if (expression.reference === 0) { + this.debugService.getViewModel().setSelectedExpression(expression); + } + return true; + } + + return super.onLeftClick(tree, element, event); + } +} + // watch expressions export class WatchExpressionsActionProvider implements renderer.IActionProvider { diff --git a/src/vs/workbench/parts/debug/browser/debugViews.ts b/src/vs/workbench/parts/debug/browser/debugViews.ts index 6bc164fb0a6..da0596e6aed 100644 --- a/src/vs/workbench/parts/debug/browser/debugViews.ts +++ b/src/vs/workbench/parts/debug/browser/debugViews.ts @@ -75,7 +75,7 @@ export class VariablesView extends viewlet.CollapsibleViewletView { dataSource: new viewer.VariablesDataSource(this.debugService), renderer: this.instantiationService.createInstance(viewer.VariablesRenderer), accessibilityProvider: new viewer.VariablesAccessibilityProvider(), - controller: new viewer.BaseDebugController(this.debugService, this.contextMenuService, new viewer.VariablesActionProvider(this.instantiationService)) + controller: new viewer.VariablesController(this.debugService, this.contextMenuService, new viewer.VariablesActionProvider(this.instantiationService)) }, debugTreeOptions(nls.localize('variablesAriaTreeLabel', "Debug Variables"))); const viewModel = this.debugService.getViewModel(); From f58a45aa2f57cbd8cc3ca373220130624bf1c64f Mon Sep 17 00:00:00 2001 From: isidor Date: Fri, 17 Jun 2016 15:58:19 +0200 Subject: [PATCH 181/217] debug: also change variable value on enter --- src/vs/workbench/parts/debug/browser/debugViewer.ts | 13 +++++++++++++ 1 file changed, 13 insertions(+) diff --git a/src/vs/workbench/parts/debug/browser/debugViewer.ts b/src/vs/workbench/parts/debug/browser/debugViewer.ts index 0f0e6601ef0..8f99ea2e99b 100644 --- a/src/vs/workbench/parts/debug/browser/debugViewer.ts +++ b/src/vs/workbench/parts/debug/browser/debugViewer.ts @@ -682,6 +682,19 @@ export class VariablesController extends BaseDebugController { return super.onLeftClick(tree, element, event); } + + protected onEnter(tree: tree.ITree, event: IKeyboardEvent): boolean { + // double click on primitive value: open input box to be able to set the value + const element = tree.getFocus(); + if (element instanceof model.Variable) { + if (element.reference === 0) { + this.debugService.getViewModel().setSelectedExpression(element); + } + return true; + } + + return super.onEnter(tree, event); + } } // watch expressions From 59fdb4a40deba18348bf299c047f14a5087428b2 Mon Sep 17 00:00:00 2001 From: Johannes Rieken Date: Fri, 17 Jun 2016 13:55:55 +0200 Subject: [PATCH 182/217] simpler way to prepare context menu --- .../contextmenu/browser/contextmenu.ts | 71 ++++++++++--------- 1 file changed, 38 insertions(+), 33 deletions(-) diff --git a/src/vs/editor/contrib/contextmenu/browser/contextmenu.ts b/src/vs/editor/contrib/contextmenu/browser/contextmenu.ts index d43874e4507..012f011b6a0 100644 --- a/src/vs/editor/contrib/contextmenu/browser/contextmenu.ts +++ b/src/vs/editor/contrib/contextmenu/browser/contextmenu.ts @@ -8,7 +8,6 @@ import * as nls from 'vs/nls'; import {IAction} from 'vs/base/common/actions'; import {KeyCode, KeyMod, Keybinding} from 'vs/base/common/keyCodes'; import {IDisposable, dispose} from 'vs/base/common/lifecycle'; -import {SortedList} from 'vs/base/common/sortedList'; import {TPromise} from 'vs/base/common/winjs.base'; import * as dom from 'vs/base/browser/dom'; import {IKeyboardEvent} from 'vs/base/browser/keyboardEvent'; @@ -124,47 +123,53 @@ class ContextMenuController implements IEditorContribution { } private _getMenuActions(): IAction[] { - var editorModel = this._editor.getModel(); + const editorModel = this._editor.getModel(); if (!editorModel) { return []; } - var allActions = this._editor.getActions(); - var contributedActions = allActions.filter((action)=>(typeof action.shouldShowInContextMenu === 'function') && action.shouldShowInContextMenu() && action.isSupported()); - - return this._prepareActions(contributedActions); - } - - private _prepareActions(actions:EditorAction[]):IAction[] { - var list = new SortedList>(); - - actions.forEach((action)=>{ - var groups = action.getGroupId().split('/'); - var actionsForGroup = list.getValue(groups[0]); - if (!actionsForGroup) { - actionsForGroup = new SortedList(); - list.add(groups[0], actionsForGroup); + const contributedActions = this._editor.getActions().filter(action => { + if (action instanceof EditorAction) { + return action.shouldShowInContextMenu() && action.isSupported(); } - - actionsForGroup.add(groups[1] || groups[0], action); }); - var sortedAndGroupedActions:IAction[] = []; - var groupIterator = list.getIterator(); - while(groupIterator.moveNext()) { - var group = groupIterator.current.value; - var actionsIterator = group.getIterator(); - while(actionsIterator.moveNext()) { - var action = actionsIterator.current.value; - sortedAndGroupedActions.push(action); - } + return ContextMenuController._prepareActions(contributedActions); + } - if (groupIterator.hasNext()) { - sortedAndGroupedActions.push(new Separator()); - } - } + private static _prepareActions(actions: EditorAction[]): IAction[] { - return sortedAndGroupedActions; + const data = actions.map(action => { + const groupId = action.getGroupId(); + const idx = groupId.indexOf('/'); + const group = idx > 0 + ? groupId.substr(0, idx) + : groupId; + + return { action, group }; + }); + + data.sort((a, b) => { + if (a.group < b.group) { + return -1; + } else if (a.group > b.group) { + return 1; + } else { + return 0; + } + }); + + const result: IAction[] = []; + let lastGroup: string; + data.forEach((value, idx) => { + if (lastGroup && lastGroup !== value.group) { + result.push(new Separator()); + } + result.push(value.action); + lastGroup = value.group; + }); + + return result; } private _doShowContextMenu(actions:IAction[], forcedPosition:IPosition = null): void { From 86e4673905d425f322c773e593c6581bfc5217b0 Mon Sep 17 00:00:00 2001 From: Johannes Rieken Date: Fri, 17 Jun 2016 13:56:44 +0200 Subject: [PATCH 183/217] remove unused sortedList --- src/vs/base/common/sortedList.ts | 256 --------------------- src/vs/base/test/common/sortedList.test.ts | 111 --------- 2 files changed, 367 deletions(-) delete mode 100644 src/vs/base/common/sortedList.ts delete mode 100644 src/vs/base/test/common/sortedList.test.ts diff --git a/src/vs/base/common/sortedList.ts b/src/vs/base/common/sortedList.ts deleted file mode 100644 index c15d6ecbba5..00000000000 --- a/src/vs/base/common/sortedList.ts +++ /dev/null @@ -1,256 +0,0 @@ -/*--------------------------------------------------------------------------------------------- - * Copyright (c) Microsoft Corporation. All rights reserved. - * Licensed under the MIT License. See License.txt in the project root for license information. - *--------------------------------------------------------------------------------------------*/ -'use strict'; - -import Arrays = require('vs/base/common/arrays'); - -export interface IIterator { - current: TValue; - moveNext(): boolean; - hasNext(): boolean; - reset(): void; - dispose(): void; -} - -export interface IIterable { - getIterator(): IIterator; -} - -export interface ISortedList extends IIterable> { - /** - * Number of elements in a sorted list. - * O(1) - */ - count: number; - - /** - * Gets the value associated with the specified key. - * Returns null if there is no value associated with the key. - * O(log n) - */ - getValue(key: TKey): TValue; - - /** - * Gets an iterator over values. - * O(1) - */ - getValues(): IIterator; - - /** - * Gets the value at the specified index. - * Returns null if index is out of bounds. - * O(1) - */ - getValueByIndex(index: number): TValue; - - /** - * Gets the key at the specified index. - * Returns null if index is out of bounds. - * O(1) - */ - getKey(index: number): TKey; - - /** - * Gets an iterator over keys. - * O(1) - */ - getKeys(): IIterator; - - /** - * Returns the zero-based index of the specified key in a SortedList object. - * Returns -1 if the key is not found. - * O(log n) - */ - indexOfKey(key: TKey): number; - - /** - * Adds the specified key and value to the sorted list. - * O(n) - */ - add(key: TKey, value: TValue): void; - - /** - * Removes a value from the sorted list. - * Returns true if the value got removed, false otherwise. - * O(n) - */ - remove(key: TKey): boolean; -} - -export interface KeyValue { - key: TKey; - value: TValue; -} - -export class SortedList implements ISortedList { - - private static DEFAULT_COMPARATOR = function(first: TKey, second: TKey) { - return first < second ? -1 : first > second ? 1 : 0; - }; - - private keys: TKey[]; - private values: TValue[]; - private comparator: (first: TKey, second: TKey) => number; - - constructor(comparator?: (first: TKey, second: TKey) => number) { - this.keys = []; - this.values = []; - this.comparator = comparator || SortedList.DEFAULT_COMPARATOR; - } - - public get count(): number { - return this.keys.length; - } - - public getValueByIndex(index: number): TValue { - if (0 <= index && index < this.values.length) { - return this.values[index]; - } - - return null; - } - - public getKey(index: number): TKey { - if (0 <= index && index < this.keys.length) { - return this.keys[index]; - } - - return null; - } - - public getKeys(): IIterator { - return new ListIterator(this.keys); - } - - public getValue(key: TKey): TValue { - if (!key) { - throw new Error('Key must be defined.'); - } - var indexOfKey = this.indexOfKey(key); - if (indexOfKey >= 0) { - return this.values[indexOfKey]; - } - - return null; - } - - public getValues(): IIterator { - return new ListIterator(this.values); - } - - public indexOfKey(key: TKey): number { - if (!key) { - throw new Error('Key must be defined.'); - } - return Math.max(-1, Arrays.binarySearch(this.keys, key, this.comparator)); - } - - public add(key: TKey, value: TValue): void { - if (!key || !value) { - throw new Error('Key and value must be defined.'); - } - - var position = 0; - while (position < this.keys.length && this.comparator(key, this.keys[position]) > 0) { - position++; - } - - this.keys.splice(position, 0, key); - this.values.splice(position, 0, value); - } - - public remove(key: TKey): boolean { - if (!key) { - throw new Error('Key must be defined.'); - } - var indexOfKey = this.indexOfKey(key); - if (indexOfKey >= 0) { - this.values.splice(indexOfKey, 1); - this.keys.splice(indexOfKey, 1); - } - - return indexOfKey >= 0; - } - - public getIterator(): IIterator> { - return new SortedListIterator(this.keys, this.values); - } -} - -class SortedListIterator implements IIterator> { - private keys: TKey[]; - private values: TValue[]; - private index: number; - - constructor(keys: TKey[], values: TValue[]) { - this.keys = keys; - this.values = values; - this.index = -1; - } - - public get current(): KeyValue { - if (this.index < 0 || this.keys.length < this.index) { - return null; - } - - return { - key: this.keys[this.index], - value: this.values[this.index] - }; - } - - public moveNext(): boolean { - this.index++; - return this.index < this.keys.length; - } - - public hasNext(): boolean { - return this.index + 1 < this.keys.length; - } - - public reset(): void { - this.index = -1; - } - - public dispose(): void { - this.keys = null; - this.values = null; - } -} - -class ListIterator implements IIterator { - private values: TValue[]; - private index: number; - - constructor(values: TValue[]) { - this.values = values; - this.index = -1; - } - - public get current(): TValue { - if (this.index < 0 || this.values.length < this.index) { - return null; - } - - return this.values[this.index]; - } - - public moveNext(): boolean { - this.index++; - return this.index < this.values.length; - } - - public hasNext(): boolean { - return this.index + 1 < this.values.length; - } - - public reset(): void { - this.index = -1; - } - - public dispose(): void { - this.values = null; - } -} \ No newline at end of file diff --git a/src/vs/base/test/common/sortedList.test.ts b/src/vs/base/test/common/sortedList.test.ts deleted file mode 100644 index d4e9a65234a..00000000000 --- a/src/vs/base/test/common/sortedList.test.ts +++ /dev/null @@ -1,111 +0,0 @@ -/*--------------------------------------------------------------------------------------------- - * Copyright (c) Microsoft Corporation. All rights reserved. - * Licensed under the MIT License. See License.txt in the project root for license information. - *--------------------------------------------------------------------------------------------*/ -'use strict'; - -import * as assert from 'assert'; -import SortedList = require('vs/base/common/sortedList'); - -function getCuisineKeys(): string[] { - return ['german', 'swiss', 'french', 'italian', 'english','scotish', 'turksih', 'hungarian', 'serbian', 'swedish', 'russian', - 'portugesse', 'american', 'japenesse', 'chinesse', 'bosnian', 'makedonian', 'libanese', 'mexican', 'thailand']; -} - -function getCuisineValues(): string[] { - return ['beer', 'cheese', 'wine', 'pizza', 'chips', 'whiskey', 'kebab', 'gulash', 'pljeska', 'salmon', 'vodka', - 'shrimp', 'burger', 'susshi', 'sechuan', 'cevapcici', 'burek', 'falafel', 'burito', 'curryduck']; -} - -function shouldThrow(func: (key: any) => any, key: any): void { - try { - func(key); - assert(false); - } catch (e) { - assert(true); - } -} - -var keys = getCuisineKeys(); -var values = getCuisineValues(); - -function getCuisineList(withoutIterator:boolean = false): SortedList.ISortedList { - var result = new SortedList.SortedList(withoutIterator ? null : (first: string, second: string) => { - return first.localeCompare(second); - }); - for (var i = 0; i < keys.length; i++) { - result.add(keys[i], values[i]); - } - - return result; -} - -suite('SortedList', () => { - test('sorted list add', function() { - var sortedList = getCuisineList(); - assert.equal(sortedList.count, keys.length); - - for (var i = 0; i < keys.length; i++) { - assert.equal(sortedList.getValue(keys[i]), values[i]); - assert(sortedList.indexOfKey(keys[i]) >= 0); - assert.notEqual(sortedList.getValueByIndex(i), null); - } - }); - - test('sorted list add with default comparator', function() { - var sortedList = getCuisineList(true /* without comparator */); - assert.equal(sortedList.count, keys.length); - - for (var i = 0; i < keys.length; i++) { - assert.equal(sortedList.getValue(keys[i]), values[i]); - assert(sortedList.indexOfKey(keys[i]) >= 0); - assert.notEqual(sortedList.getValueByIndex(i), null); - } - }); - - test('sorted list remove', function() { - var sortedList = getCuisineList(); - for (var i = 0; i < keys.length; i++) { - assert(sortedList.remove(keys[i])); - } - assert.equal(sortedList.count, 0); - }); - - test('sorted list iterator', function() { - var sortedList = getCuisineList(); - // cast due to TS bug. - var iterator = sortedList.getIterator(); - var elementCount = 0; - while (iterator.moveNext()) { - elementCount++; - assert(keys.indexOf(iterator.current.key) >= 0); - assert(values.indexOf(iterator.current.value) >= 0); - } - assert.equal(elementCount, sortedList.count); - - iterator.reset(); - elementCount = 0; - assert(iterator.hasNext()); - while (iterator.moveNext()) { - elementCount++; - assert(keys.indexOf(iterator.current.key) >= 0); - assert(values.indexOf(iterator.current.value) >= 0); - } - assert(!iterator.hasNext()); - assert.equal(elementCount, sortedList.count); - }); - - test('sorted list bad op', function() { - var sortedList = getCuisineList(); - assert.equal(sortedList.getKey(127), null); - assert.equal(sortedList.getKey(-1), null); - assert.equal(sortedList.getValue('banana'), null); - assert.equal(sortedList.remove('unexistingKey'), false); - assert.equal(sortedList.getValueByIndex(-4), null); - assert.equal(sortedList.getValueByIndex(1114), null); - assert.equal(sortedList.indexOfKey('fakeKey'), -1); - shouldThrow(sortedList.indexOfKey, null); - shouldThrow(sortedList.getValue, null); - shouldThrow(sortedList.remove, null); - }); -}); \ No newline at end of file From 8b46c05dec8c4ba4615ecc8bea686f1f49314f2e Mon Sep 17 00:00:00 2001 From: Benjamin Pasero Date: Fri, 17 Jun 2016 16:15:39 +0200 Subject: [PATCH 184/217] for now do not override Cmd+1/2/3 (for #7647) --- .../browser/parts/editor/editor.contribution.ts | 12 ++++++------ .../workbench/browser/parts/sidebar/sidebarPart.ts | 4 ++-- 2 files changed, 8 insertions(+), 8 deletions(-) diff --git a/src/vs/workbench/browser/parts/editor/editor.contribution.ts b/src/vs/workbench/browser/parts/editor/editor.contribution.ts index b890a243ec6..4714103cc68 100644 --- a/src/vs/workbench/browser/parts/editor/editor.contribution.ts +++ b/src/vs/workbench/browser/parts/editor/editor.contribution.ts @@ -291,10 +291,10 @@ registry.registerWorkbenchAction(new SyncActionDescriptor(CloseOtherEditorsInGro registry.registerWorkbenchAction(new SyncActionDescriptor(CloseEditorsInOtherGroupsAction, CloseEditorsInOtherGroupsAction.ID, CloseEditorsInOtherGroupsAction.LABEL), 'View: Close Editors in Other Groups', category); registry.registerWorkbenchAction(new SyncActionDescriptor(SplitEditorAction, SplitEditorAction.ID, SplitEditorAction.LABEL, { primary: KeyMod.CtrlCmd | KeyCode.US_BACKSLASH }), 'View: Split Editor', category); registry.registerWorkbenchAction(new SyncActionDescriptor(NavigateBetweenGroupsAction, NavigateBetweenGroupsAction.ID, NavigateBetweenGroupsAction.LABEL), 'View: Navigate Between Editor Groups', category); -registry.registerWorkbenchAction(new SyncActionDescriptor(FocusFirstGroupAction, FocusFirstGroupAction.ID, FocusFirstGroupAction.LABEL, { primary: KeyMod.CtrlCmd | KeyCode.KEY_1 }, KbExpr.has('!config.workbench.editor.showTabs')), 'View: Focus Left Editor Group', category); -registry.registerWorkbenchAction(new SyncActionDescriptor(FocusSecondGroupAction, FocusSecondGroupAction.ID, FocusSecondGroupAction.LABEL, { primary: KeyMod.CtrlCmd | KeyCode.KEY_2 }, KbExpr.has('!config.workbench.editor.showTabs')), 'View: Focus Center Editor Group', category); -registry.registerWorkbenchAction(new SyncActionDescriptor(FocusThirdGroupAction, FocusThirdGroupAction.ID, FocusThirdGroupAction.LABEL, { primary: KeyMod.CtrlCmd | KeyCode.KEY_3 }, KbExpr.has('!config.workbench.editor.showTabs')), 'View: Focus Right Editor Group', category); -registry.registerWorkbenchAction(new SyncActionDescriptor(FocusLastEditorInStackAction, FocusLastEditorInStackAction.ID, FocusLastEditorInStackAction.LABEL, { primary: KeyMod.CtrlCmd | KeyCode.KEY_0 }, KbExpr.has('config.workbench.editor.showTabs')), 'View: Focus Last Editor in Group', category); +registry.registerWorkbenchAction(new SyncActionDescriptor(FocusFirstGroupAction, FocusFirstGroupAction.ID, FocusFirstGroupAction.LABEL, { primary: KeyMod.CtrlCmd | KeyCode.KEY_1 }), 'View: Focus Left Editor Group', category); +registry.registerWorkbenchAction(new SyncActionDescriptor(FocusSecondGroupAction, FocusSecondGroupAction.ID, FocusSecondGroupAction.LABEL, { primary: KeyMod.CtrlCmd | KeyCode.KEY_2 }), 'View: Focus Center Editor Group', category); +registry.registerWorkbenchAction(new SyncActionDescriptor(FocusThirdGroupAction, FocusThirdGroupAction.ID, FocusThirdGroupAction.LABEL, { primary: KeyMod.CtrlCmd | KeyCode.KEY_3 }), 'View: Focus Right Editor Group', category); +registry.registerWorkbenchAction(new SyncActionDescriptor(FocusLastEditorInStackAction, FocusLastEditorInStackAction.ID, FocusLastEditorInStackAction.LABEL, { primary: KeyMod.CtrlCmd | KeyMod.Shift | KeyCode.KEY_0 }), 'View: Focus Last Editor in Group', category); registry.registerWorkbenchAction(new SyncActionDescriptor(EvenGroupWidthsAction, EvenGroupWidthsAction.ID, EvenGroupWidthsAction.LABEL), 'View: Even Editor Group Widths', category); registry.registerWorkbenchAction(new SyncActionDescriptor(MaximizeGroupAction, MaximizeGroupAction.ID, MaximizeGroupAction.LABEL), 'View: Maximize Editor Group and Hide Sidebar', category); registry.registerWorkbenchAction(new SyncActionDescriptor(MinimizeOtherGroupsAction, MinimizeOtherGroupsAction.ID, MinimizeOtherGroupsAction.LABEL), 'View: Minimize Other Editor Groups', category); @@ -331,8 +331,8 @@ for (let i = 0; i < 9; i++) { KeybindingsRegistry.registerCommandDesc({ id: 'workbench.action.openEditorAtIndex' + visibleIndex, weight: KeybindingsRegistry.WEIGHT.workbenchContrib(), - when: KbExpr.has('config.workbench.editor.showTabs'), - primary: KeyMod.CtrlCmd | toKeyCode(visibleIndex), + when: void 0, + primary: KeyMod.CtrlCmd | KeyMod.Shift | toKeyCode(visibleIndex), handler: accessor => { const editorService = accessor.get(IWorkbenchEditorService); const editorGroupService = accessor.get(IEditorGroupService); diff --git a/src/vs/workbench/browser/parts/sidebar/sidebarPart.ts b/src/vs/workbench/browser/parts/sidebar/sidebarPart.ts index ede8570b8fd..c2a78d59e54 100644 --- a/src/vs/workbench/browser/parts/sidebar/sidebarPart.ts +++ b/src/vs/workbench/browser/parts/sidebar/sidebarPart.ts @@ -21,7 +21,7 @@ import {IContextMenuService} from 'vs/platform/contextview/browser/contextView'; import {IEventService} from 'vs/platform/event/common/event'; import {IMessageService} from 'vs/platform/message/common/message'; import {ITelemetryService} from 'vs/platform/telemetry/common/telemetry'; -import {IKeybindingService, KbExpr} from 'vs/platform/keybinding/common/keybindingService'; +import {IKeybindingService} from 'vs/platform/keybinding/common/keybindingService'; import {KeyMod, KeyCode} from 'vs/base/common/keyCodes'; import {IInstantiationService} from 'vs/platform/instantiation/common/instantiation'; @@ -129,4 +129,4 @@ export class FocusSideBarAction extends Action { let registry = Registry.as(ActionExtensions.WorkbenchActions); registry.registerWorkbenchAction(new SyncActionDescriptor(FocusSideBarAction, FocusSideBarAction.ID, FocusSideBarAction.LABEL, { primary: KeyMod.CtrlCmd | KeyCode.KEY_0 -}, KbExpr.has('!config.workbench.editor.showTabs')), 'View: Focus into Side Bar', nls.localize('viewCategory', "View")); +}), 'View: Focus into Side Bar', nls.localize('viewCategory', "View")); From e65a6df0132e6a168c8b7818e3912cd4acfd7407 Mon Sep 17 00:00:00 2001 From: Martin Aeschlimann Date: Fri, 17 Jun 2016 16:17:07 +0200 Subject: [PATCH 185/217] fixes #7777: [scss] validation doesn't disable --- extensions/css/server/src/cssLanguageService.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/extensions/css/server/src/cssLanguageService.ts b/extensions/css/server/src/cssLanguageService.ts index 2901f52b261..df699692691 100644 --- a/extensions/css/server/src/cssLanguageService.ts +++ b/extensions/css/server/src/cssLanguageService.ts @@ -43,11 +43,11 @@ export interface LanguageSettings { let cssParser = new Parser(); let cssCompletion = new CSSCompletion(); let cssHover = new CSSHover(); -let cssValidation = new CSSValidation(); let cssNavigation = new CSSNavigation(); let cssCodeActions = new CSSCodeActions(); export function getCSSLanguageService() : LanguageService { + let cssValidation = new CSSValidation(); // an instance per language service return { configure: cssValidation.configure.bind(cssValidation), doValidation: cssValidation.doValidation.bind(cssValidation), From e1e2a2c4666f0cfa15436322dfedf8fc5dd8932f Mon Sep 17 00:00:00 2001 From: Benjamin Pasero Date: Fri, 17 Jun 2016 16:26:44 +0200 Subject: [PATCH 186/217] wtf keybindings --- src/vs/workbench/browser/parts/editor/editor.contribution.ts | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/vs/workbench/browser/parts/editor/editor.contribution.ts b/src/vs/workbench/browser/parts/editor/editor.contribution.ts index 4714103cc68..615198b418e 100644 --- a/src/vs/workbench/browser/parts/editor/editor.contribution.ts +++ b/src/vs/workbench/browser/parts/editor/editor.contribution.ts @@ -294,7 +294,7 @@ registry.registerWorkbenchAction(new SyncActionDescriptor(NavigateBetweenGroupsA registry.registerWorkbenchAction(new SyncActionDescriptor(FocusFirstGroupAction, FocusFirstGroupAction.ID, FocusFirstGroupAction.LABEL, { primary: KeyMod.CtrlCmd | KeyCode.KEY_1 }), 'View: Focus Left Editor Group', category); registry.registerWorkbenchAction(new SyncActionDescriptor(FocusSecondGroupAction, FocusSecondGroupAction.ID, FocusSecondGroupAction.LABEL, { primary: KeyMod.CtrlCmd | KeyCode.KEY_2 }), 'View: Focus Center Editor Group', category); registry.registerWorkbenchAction(new SyncActionDescriptor(FocusThirdGroupAction, FocusThirdGroupAction.ID, FocusThirdGroupAction.LABEL, { primary: KeyMod.CtrlCmd | KeyCode.KEY_3 }), 'View: Focus Right Editor Group', category); -registry.registerWorkbenchAction(new SyncActionDescriptor(FocusLastEditorInStackAction, FocusLastEditorInStackAction.ID, FocusLastEditorInStackAction.LABEL, { primary: KeyMod.CtrlCmd | KeyMod.Shift | KeyCode.KEY_0 }), 'View: Focus Last Editor in Group', category); +registry.registerWorkbenchAction(new SyncActionDescriptor(FocusLastEditorInStackAction, FocusLastEditorInStackAction.ID, FocusLastEditorInStackAction.LABEL, { primary: KeyMod.WinCtrl | KeyCode.KEY_0 }), 'View: Focus Last Editor in Group', category); registry.registerWorkbenchAction(new SyncActionDescriptor(EvenGroupWidthsAction, EvenGroupWidthsAction.ID, EvenGroupWidthsAction.LABEL), 'View: Even Editor Group Widths', category); registry.registerWorkbenchAction(new SyncActionDescriptor(MaximizeGroupAction, MaximizeGroupAction.ID, MaximizeGroupAction.LABEL), 'View: Maximize Editor Group and Hide Sidebar', category); registry.registerWorkbenchAction(new SyncActionDescriptor(MinimizeOtherGroupsAction, MinimizeOtherGroupsAction.ID, MinimizeOtherGroupsAction.LABEL), 'View: Minimize Other Editor Groups', category); @@ -332,7 +332,7 @@ for (let i = 0; i < 9; i++) { id: 'workbench.action.openEditorAtIndex' + visibleIndex, weight: KeybindingsRegistry.WEIGHT.workbenchContrib(), when: void 0, - primary: KeyMod.CtrlCmd | KeyMod.Shift | toKeyCode(visibleIndex), + primary: KeyMod.WinCtrl | toKeyCode(visibleIndex), handler: accessor => { const editorService = accessor.get(IWorkbenchEditorService); const editorGroupService = accessor.get(IEditorGroupService); From 435e89eff062765516d42a649c7d2693b2833363 Mon Sep 17 00:00:00 2001 From: isidor Date: Fri, 17 Jun 2016 16:34:08 +0200 Subject: [PATCH 187/217] revert debug: also change variable value on enter --- src/vs/workbench/parts/debug/browser/debugViewer.ts | 13 ------------- 1 file changed, 13 deletions(-) diff --git a/src/vs/workbench/parts/debug/browser/debugViewer.ts b/src/vs/workbench/parts/debug/browser/debugViewer.ts index 8f99ea2e99b..0f0e6601ef0 100644 --- a/src/vs/workbench/parts/debug/browser/debugViewer.ts +++ b/src/vs/workbench/parts/debug/browser/debugViewer.ts @@ -682,19 +682,6 @@ export class VariablesController extends BaseDebugController { return super.onLeftClick(tree, element, event); } - - protected onEnter(tree: tree.ITree, event: IKeyboardEvent): boolean { - // double click on primitive value: open input box to be able to set the value - const element = tree.getFocus(); - if (element instanceof model.Variable) { - if (element.reference === 0) { - this.debugService.getViewModel().setSelectedExpression(element); - } - return true; - } - - return super.onEnter(tree, event); - } } // watch expressions From faf853a232f6bf0111096dfb8bd8dceba143717a Mon Sep 17 00:00:00 2001 From: Benjamin Pasero Date: Fri, 17 Jun 2016 16:43:49 +0200 Subject: [PATCH 188/217] less hectic overflow updates --- .../browser/parts/editor/media/sidebyside.css | 4 ++ .../parts/editor/sideBySideEditorControl.ts | 45 +++++++++++-------- 2 files changed, 30 insertions(+), 19 deletions(-) diff --git a/src/vs/workbench/browser/parts/editor/media/sidebyside.css b/src/vs/workbench/browser/parts/editor/media/sidebyside.css index 6be7b4f9775..291000feff0 100644 --- a/src/vs/workbench/browser/parts/editor/media/sidebyside.css +++ b/src/vs/workbench/browser/parts/editor/media/sidebyside.css @@ -20,6 +20,10 @@ z-index: 3000000; } +#monaco-workbench-editor-drop-overlay { + opacity: 0; /* initially not visible until moving around */ +} + .vs #monaco-workbench-editor-drop-overlay, .vs .monaco-workbench .editor.empty > .content.dropfeedback { background-color: rgba(51,153,255, 0.18); diff --git a/src/vs/workbench/browser/parts/editor/sideBySideEditorControl.ts b/src/vs/workbench/browser/parts/editor/sideBySideEditorControl.ts index 11071d07b9e..4015b662b0a 100644 --- a/src/vs/workbench/browser/parts/editor/sideBySideEditorControl.ts +++ b/src/vs/workbench/browser/parts/editor/sideBySideEditorControl.ts @@ -841,33 +841,40 @@ export class SideBySideEditorControl implements ISideBySideEditorControl, IVerti const splitThreshold = overlayIsSplit ? overlayWidth / 5 : overlayWidth / 10; const isCopy = (e.ctrlKey && !isMacintosh) || (e.altKey && isMacintosh); + let allowSplit = true; if (groups === POSITIONS.length) { - return; // do not show split feedback when we already at the maximum + allowSplit = false; // do not show split feedback when we already at the maximum } const draggedEditor = TitleControl.getDraggedEditor(); if (!isCopy && draggedEditor && draggedEditor.group.count === 1) { - return; // do not show split feedback when moving the only one editor of a group + allowSplit = false; // do not show split feedback when moving the only one editor of a group } - if (posXOnOverlay + splitThreshold > overlayWidth) { - overlay.setProperty(splitToPropertyKey, position === Position.LEFT ? Position.CENTER : Position.RIGHT); - overlay.style({ - left: '50%', - width: '50%', - }); - } else if (posXOnOverlay < splitThreshold) { - overlay.setProperty(splitToPropertyKey, position === Position.LEFT ? Position.LEFT : Position.CENTER); - overlay.style({ - width: '50%' - }); - } else { - overlay.removeProperty(splitToPropertyKey); - overlay.style({ - left: '0', - width: '100%' - }); + // Compute split decoration + if (allowSplit) { + if (posXOnOverlay + splitThreshold > overlayWidth) { + overlay.setProperty(splitToPropertyKey, position === Position.LEFT ? Position.CENTER : Position.RIGHT); + overlay.style({ + left: '50%', + width: '50%', + }); + } else if (posXOnOverlay < splitThreshold) { + overlay.setProperty(splitToPropertyKey, position === Position.LEFT ? Position.LEFT : Position.CENTER); + overlay.style({ + width: '50%' + }); + } else { + overlay.removeProperty(splitToPropertyKey); + overlay.style({ + left: '0', + width: '100%' + }); + } } + + // Make sure the overlay is visible + overlay.style({ opacity: 1 }); } function createOverlay(target: HTMLElement): void { From ea101fea0995a76647afcad8264a79187c80658e Mon Sep 17 00:00:00 2001 From: kieferrm Date: Fri, 17 Jun 2016 12:26:34 -0700 Subject: [PATCH 189/217] re-contribute configuration option; fixes #7832 --- extensions/markdown/package.json | 13 ++++++++++++- 1 file changed, 12 insertions(+), 1 deletion(-) diff --git a/extensions/markdown/package.json b/extensions/markdown/package.json index 27d4fa8c058..69be3160b00 100644 --- a/extensions/markdown/package.json +++ b/extensions/markdown/package.json @@ -91,7 +91,18 @@ "snippets": [{ "language": "markdown", "path": "./snippets/markdown.json" - }] + }], + "configuration": { + "type": "object", + "title": "Markdown preview configuration", + "properties": { + "markdown.styles": { + "type": "array", + "default" : null, + "description": "A list of URLs or local paths to CSS style sheets to use from the markdown preview." + } + } + } }, "scripts": { "vscode:prepublish": "node ../../node_modules/gulp/bin/gulp.js --gulpfile ../../build/gulpfile.extensions.js compile-extension:markdown ./tsconfig.json" From b48230db20350c095cb1a2916b8a9bc5b95c0ee3 Mon Sep 17 00:00:00 2001 From: kieferrm Date: Fri, 17 Jun 2016 12:43:02 -0700 Subject: [PATCH 190/217] handle allOf at toplevel, fixes #7833 --- src/vs/platform/configuration/common/model.ts | 21 ++++++++++++------- 1 file changed, 14 insertions(+), 7 deletions(-) diff --git a/src/vs/platform/configuration/common/model.ts b/src/vs/platform/configuration/common/model.ts index 699afb648e8..df1cfbc8a8f 100644 --- a/src/vs/platform/configuration/common/model.ts +++ b/src/vs/platform/configuration/common/model.ts @@ -117,16 +117,17 @@ export function consolidate(configMap: { [key: string]: IConfigFile; }): { conte // defaults... -function processDefaultValues(withConfig: (config: configurationRegistry.IConfigurationNode, isTop?: boolean) => void): void { +function processDefaultValues(withConfig: (config: configurationRegistry.IConfigurationNode, isTop?: boolean) => boolean): void { let configurations = (platform.Registry.as(configurationRegistry.Extensions.Configuration)).getConfigurations(); - let visit = (config: configurationRegistry.IConfigurationNode, isFirst: boolean) => { - withConfig(config, isFirst); + let visit = (config: configurationRegistry.IConfigurationNode, level: number) => { + let handled = withConfig(config, level === 0); if (Array.isArray(config.allOf)) { config.allOf.forEach((c) => { - visit(c, false); + // if the config node only contains an `allOf` we treat the `allOf` children as if they were at the top level + visit(c, (!handled && level === 0) ? level : level + 1); }); } }; @@ -142,7 +143,7 @@ function processDefaultValues(withConfig: (config: configurationRegistry.IConfig return c1.order - c2.order; }).forEach((config) => { - visit(config, true); + visit(config, 0); }); } @@ -150,7 +151,7 @@ function processDefaultValues(withConfig: (config: configurationRegistry.IConfig export function getDefaultValues(): any { let ret: any = Object.create(null); - let handleConfig = (config: configurationRegistry.IConfigurationNode, isTop: boolean) => { + let handleConfig = (config: configurationRegistry.IConfigurationNode, isTop: boolean) : boolean => { if (config.properties) { Object.keys(config.properties).forEach((key) => { let prop = config.properties[key]; @@ -160,7 +161,9 @@ export function getDefaultValues(): any { } setNode(ret, key, value); }); + return true; } + return false; }; processDefaultValues(handleConfig); return ret; @@ -172,9 +175,11 @@ export function getDefaultValuesContent(indent: string): string { let result: string[] = []; result.push('{'); - let handleConfig = (config: configurationRegistry.IConfigurationNode, isTop: boolean) => { + let handleConfig = (config: configurationRegistry.IConfigurationNode, isTop: boolean) : boolean => { + let handled = false; if (config.title) { + handled = true; if (isTop) { result.push(''); result.push('//-------- ' + config.title + ' --------'); @@ -184,6 +189,7 @@ export function getDefaultValuesContent(indent: string): string { result.push(''); } if (config.properties) { + handled = true; Object.keys(config.properties).forEach((key) => { let prop = config.properties[key]; @@ -209,6 +215,7 @@ export function getDefaultValuesContent(indent: string): string { result.push(''); }); } + return handled; }; processDefaultValues(handleConfig); From e7f6f45f14103fe3059f1302298406da29a50559 Mon Sep 17 00:00:00 2001 From: Urban Dove Date: Sun, 19 Jun 2016 01:19:40 -0400 Subject: [PATCH 191/217] Add 'vscode' as a keyword in the .desktop file so you can search for vscode not only for code --- resources/linux/code.desktop | 1 + 1 file changed, 1 insertion(+) diff --git a/resources/linux/code.desktop b/resources/linux/code.desktop index d4f065696b1..4e82b76f7a2 100644 --- a/resources/linux/code.desktop +++ b/resources/linux/code.desktop @@ -10,6 +10,7 @@ StartupWMClass=@@NAME_SHORT@@ Categories=Utility;TextEditor;Development;IDE; MimeType=text/plain; Actions=new-window; +Keywords=vscode; [Desktop Action new-window] Name=New Window From 86a6759e6dae5616386c521033105d86fa6cdc27 Mon Sep 17 00:00:00 2001 From: Basarat Ali Syed Date: Sun, 19 Jun 2016 18:22:36 +1000 Subject: [PATCH 192/217] fix : Standalone Monaco text edit validation --- src/vs/editor/browser/standalone/standaloneLanguages.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/vs/editor/browser/standalone/standaloneLanguages.ts b/src/vs/editor/browser/standalone/standaloneLanguages.ts index 2f833db0253..4ddedb0dc5b 100644 --- a/src/vs/editor/browser/standalone/standaloneLanguages.ts +++ b/src/vs/editor/browser/standalone/standaloneLanguages.ts @@ -396,7 +396,7 @@ class SuggestAdapter { let isSingleLine = (editRange.startLineNumber === editRange.endLineNumber); // invalid text edit - if (!isSingleLine || editRange.startColumn !== position.lineNumber) { + if (!isSingleLine || editRange.startLineNumber !== position.lineNumber) { console.warn('INVALID text edit, must be single line and on the same line'); continue; } From 21abbf9ad202f0e694cc38ab289952ee2423184a Mon Sep 17 00:00:00 2001 From: Georgios Kalpakas Date: Sun, 19 Jun 2016 11:47:11 +0300 Subject: [PATCH 193/217] docs(vscode.d.ts): fix typo ("a a" --> "a") --- src/vs/vscode.d.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/vs/vscode.d.ts b/src/vs/vscode.d.ts index 3817db9a13c..93cf6db550b 100644 --- a/src/vs/vscode.d.ts +++ b/src/vs/vscode.d.ts @@ -2630,7 +2630,7 @@ declare namespace vscode { /** * A diagnostics collection is a container that manages a set of * [diagnostics](#Diagnostic). Diagnostics are always scopes to a - * a diagnostics collection and a resource. + * diagnostics collection and a resource. * * To get an instance of a `DiagnosticCollection` use * [createDiagnosticCollection](#languages.createDiagnosticCollection). From b7ee78d6d6afcd2f5ee67792952fa56c5bfd0017 Mon Sep 17 00:00:00 2001 From: Benjamin Pasero Date: Sat, 18 Jun 2016 15:40:01 +0200 Subject: [PATCH 194/217] tabs bugfixing and polish --- src/typings/electron.d.ts | 3 +- .../browser/parts/editor/editorActions.ts | 32 +++++ .../browser/parts/editor/media/sidebyside.css | 1 - .../browser/parts/editor/media/tabstitle.css | 23 ++-- .../parts/editor/sideBySideEditorControl.ts | 121 ++++++++++++------ .../browser/parts/editor/tabsTitleControl.ts | 24 +++- .../browser/parts/editor/titleControl.ts | 91 +++++-------- .../parts/files/browser/fileActions.ts | 16 ++- .../electron-browser/contextmenuService.ts | 2 +- 9 files changed, 187 insertions(+), 126 deletions(-) diff --git a/src/typings/electron.d.ts b/src/typings/electron.d.ts index 1dae7da854f..abd89ba6348 100644 --- a/src/typings/electron.d.ts +++ b/src/typings/electron.d.ts @@ -838,8 +838,9 @@ declare module Electron { * at the current mouse cursor position. * @param x Horizontal coordinate where the menu will be placed. * @param y Vertical coordinate where the menu will be placed. + * @param positioningItem The item to select by default. */ - popup(browserWindow: BrowserWindow, x?: number, y?: number): void; + popup(browserWindow: BrowserWindow, x?: number, y?: number, positioningItem?: number): void; /** * Appends the menuItem to the menu. */ diff --git a/src/vs/workbench/browser/parts/editor/editorActions.ts b/src/vs/workbench/browser/parts/editor/editorActions.ts index fdb21f2092f..8ce3af32df8 100644 --- a/src/vs/workbench/browser/parts/editor/editorActions.ts +++ b/src/vs/workbench/browser/parts/editor/editorActions.ts @@ -970,6 +970,38 @@ export class ShowEditorsInRightGroupAction extends QuickOpenAction { } } +export class ShowEditorsInGroupAction extends Action { + + public static ID = 'workbench.action.showEditorsInGroup'; + public static LABEL = nls.localize('showEditorsInGroup', "Show Editors in Group"); + + constructor( + id: string, + label: string, + @IQuickOpenService private quickOpenService: IQuickOpenService, + @IEditorGroupService private editorGroupService: IEditorGroupService + ) { + super(id, label); + } + + public run(context?: IEditorContext): TPromise { + const stacks = this.editorGroupService.getStacksModel(); + const groupCount = stacks.groups.length; + if (groupCount <= 1 || !context) { + return this.quickOpenService.show(NAVIGATE_ALL_EDITORS_GROUP_PREFIX); + } + + switch (stacks.positionOfGroup(context.group)) { + case Position.CENTER: + return this.quickOpenService.show((groupCount === 2) ? NAVIGATE_IN_RIGHT_GROUP_PREFIX : NAVIGATE_IN_CENTER_GROUP_PREFIX); + case Position.RIGHT: + return this.quickOpenService.show(NAVIGATE_IN_RIGHT_GROUP_PREFIX); + } + + return this.quickOpenService.show(NAVIGATE_IN_LEFT_GROUP_PREFIX); + } +} + export const NAVIGATE_ALL_EDITORS_GROUP_PREFIX = 'edt '; export class ShowAllEditorsAction extends QuickOpenAction { diff --git a/src/vs/workbench/browser/parts/editor/media/sidebyside.css b/src/vs/workbench/browser/parts/editor/media/sidebyside.css index 291000feff0..6856774592e 100644 --- a/src/vs/workbench/browser/parts/editor/media/sidebyside.css +++ b/src/vs/workbench/browser/parts/editor/media/sidebyside.css @@ -16,7 +16,6 @@ position: absolute; left: 0; width: 100%; - height: 100%; z-index: 3000000; } diff --git a/src/vs/workbench/browser/parts/editor/media/tabstitle.css b/src/vs/workbench/browser/parts/editor/media/tabstitle.css index 5a9ceec4949..4ec13f088bf 100644 --- a/src/vs/workbench/browser/parts/editor/media/tabstitle.css +++ b/src/vs/workbench/browser/parts/editor/media/tabstitle.css @@ -11,11 +11,14 @@ .monaco-workbench > .part.editor > .content > .one-editor-container > .title .tabs-container { display: flex; - /*overflow: scroll;*/ background-color: rgba(128, 128, 128, 0.2); height: 35px; } +.monaco-workbench > .part.editor > .content > .one-editor-container > .title .tabs-container.scroll { + overflow: scroll !important; +} + .monaco-workbench > .part.editor > .content > .one-editor-container > .title .tabs-container::-webkit-scrollbar { display: none; } @@ -36,10 +39,6 @@ padding-left: 10px; } -.monaco-workbench > .part.editor > .content > .one-editor-container > .title .tabs-container > .tab:focus { - outline-offset: -2px; -} - .hc-black .monaco-workbench > .part.editor > .content > .one-editor-container > .title.active .tabs-container > .tab.active { border: 1px solid #f38518; } @@ -49,15 +48,19 @@ } .monaco-workbench > .part.editor > .content > .one-editor-container > .title .tabs-container > .tab.active { - border-bottom: 0; + border-bottom-color: transparent; opacity: 1 !important; } -.vs .monaco-workbench > .part.editor > .content > .one-editor-container > .title .tabs-container.dropfeedback, -.vs .monaco-workbench > .part.editor > .content > .one-editor-container > .title .tabs-container > .tab.dropfeedback { +.vs .monaco-workbench > .part.editor > .content > .one-editor-container > .title .tabs-container.dropfeedback { background-color: rgba(51,153,255, 0.18); } +.vs .monaco-workbench > .part.editor > .content > .one-editor-container > .title .tabs-container > .tab.dropfeedback { + background-color: rgba(187, 230, 255, 0.5); + opacity: 1 !important; +} + .vs-dark .monaco-workbench > .part.editor > .content > .one-editor-container > .title .tabs-container.dropfeedback, .vs-dark .monaco-workbench > .part.editor > .content > .one-editor-container > .title .tabs-container > .tab.dropfeedback { background-color: rgba(83, 89, 93, 0.5); @@ -70,10 +73,6 @@ outline-offset: -2px; } -.monaco-workbench > .part.editor > .content > .one-editor-container > .title .tabs-container > .tab.dragged { - opacity: 0.7 !important; -} - /* Tab Close */ .monaco-workbench > .part.editor > .content > .one-editor-container .title .tabs-container > .tab > .tab-close { diff --git a/src/vs/workbench/browser/parts/editor/sideBySideEditorControl.ts b/src/vs/workbench/browser/parts/editor/sideBySideEditorControl.ts index 4015b662b0a..be6d811fc4d 100644 --- a/src/vs/workbench/browser/parts/editor/sideBySideEditorControl.ts +++ b/src/vs/workbench/browser/parts/editor/sideBySideEditorControl.ts @@ -758,6 +758,7 @@ export class SideBySideEditorControl implements ISideBySideEditorControl, IVerti const $this = this; const overlayId = 'monaco-workbench-editor-drop-overlay'; const splitToPropertyKey = 'splitToPosition'; + const stacks = this.editorGroupService.getStacksModel(); let overlay: Builder; function onDrop(e: DragEvent, position: Position, splitTo?: Position): void { @@ -766,7 +767,6 @@ export class SideBySideEditorControl implements ISideBySideEditorControl, IVerti const editorService = $this.editorService; const groupService = $this.editorGroupService; - const stacks = groupService.getStacksModel(); const splitEditor = (typeof splitTo === 'number'); // TODO@Ben ugly split code should benefit from empty group support once available! const freeGroup = (stacks.groups.length === 1) ? Position.CENTER : Position.RIGHT; @@ -784,7 +784,7 @@ export class SideBySideEditorControl implements ISideBySideEditorControl, IVerti if (splitTo !== freeGroup) { groupService.moveGroup(freeGroup, splitTo); } - }); + }).done(null, errors.onUnexpectedError); } else { editorService.openEditor(draggedEditor.editor, pinned, position).done(null, errors.onUnexpectedError); } @@ -794,12 +794,17 @@ export class SideBySideEditorControl implements ISideBySideEditorControl, IVerti else { const sourcePosition = stacks.positionOfGroup(draggedEditor.group); if (splitEditor) { - editorService.openEditor(draggedEditor.editor, pinned, freeGroup).then(() => { - if (splitTo !== freeGroup) { - groupService.moveGroup(freeGroup, splitTo); - } - groupService.moveEditor(draggedEditor.editor, stacks.positionOfGroup(draggedEditor.group), splitTo); - }); + if (draggedEditor.group.count === 1) { + groupService.moveGroup(sourcePosition, splitTo); + } else { + editorService.openEditor(draggedEditor.editor, pinned, freeGroup).then(() => { + if (splitTo !== freeGroup) { + groupService.moveGroup(freeGroup, splitTo); + } + groupService.moveEditor(draggedEditor.editor, stacks.positionOfGroup(draggedEditor.group), splitTo); + }).done(null, errors.onUnexpectedError); + } + } else { groupService.moveEditor(draggedEditor.editor, sourcePosition, position); } @@ -840,39 +845,71 @@ export class SideBySideEditorControl implements ISideBySideEditorControl, IVerti const overlayWidth = target.clientWidth; const splitThreshold = overlayIsSplit ? overlayWidth / 5 : overlayWidth / 10; const isCopy = (e.ctrlKey && !isMacintosh) || (e.altKey && isMacintosh); - - let allowSplit = true; - if (groups === POSITIONS.length) { - allowSplit = false; // do not show split feedback when we already at the maximum - } - const draggedEditor = TitleControl.getDraggedEditor(); - if (!isCopy && draggedEditor && draggedEditor.group.count === 1) { - allowSplit = false; // do not show split feedback when moving the only one editor of a group + + const isOverSplitLeft = posXOnOverlay < splitThreshold; + const isOverSplitRight = posXOnOverlay + splitThreshold > overlayWidth; + + let splitTarget: Position; + + // No splitting if we reached maximum group count + if (groups === POSITIONS.length) { + splitTarget = null; } - // Compute split decoration - if (allowSplit) { - if (posXOnOverlay + splitThreshold > overlayWidth) { - overlay.setProperty(splitToPropertyKey, position === Position.LEFT ? Position.CENTER : Position.RIGHT); - overlay.style({ - left: '50%', - width: '50%', - }); - } else if (posXOnOverlay < splitThreshold) { - overlay.setProperty(splitToPropertyKey, position === Position.LEFT ? Position.LEFT : Position.CENTER); - overlay.style({ - width: '50%' - }); - } else { - overlay.removeProperty(splitToPropertyKey); - overlay.style({ - left: '0', - width: '100%' - }); + // Special splitting if we drag an editor of a group with only one editor + else if (!isCopy && draggedEditor && draggedEditor.group.count === 1) { + const positionOfDraggedEditor = stacks.positionOfGroup(draggedEditor.group); + switch (positionOfDraggedEditor) { + case Position.LEFT: + if (position === Position.CENTER && isOverSplitRight) { + splitTarget = Position.CENTER; // allow to move single editor from LEFT to CENTER + } + break; + case Position.CENTER: + if (position === Position.LEFT && isOverSplitLeft) { + splitTarget = Position.LEFT; // allow to move single editor from CENTER to LEFT + } + break; + default: + splitTarget = null; // splitting not allowed } } + // Any other case, check for mouse position + else { + if (isOverSplitRight) { + splitTarget = (position === Position.LEFT) ? Position.CENTER : Position.RIGHT; + } else if (isOverSplitLeft) { + splitTarget = (position === Position.LEFT) ? Position.LEFT : Position.CENTER; + } + } + + // Apply split target + const canSplit = (typeof splitTarget === 'number'); + if (canSplit) { + overlay.setProperty(splitToPropertyKey, splitTarget); + } else { + overlay.removeProperty(splitToPropertyKey); + } + + // Update overlay styles + if (canSplit && isOverSplitRight) { + overlay.style({ + left: '50%', + width: '50%', + }); + } else if (canSplit && isOverSplitLeft) { + overlay.style({ + width: '50%' + }); + } else { + overlay.style({ + left: '0', + width: '100%' + }); + } + // Make sure the overlay is visible overlay.style({ opacity: 1 }); } @@ -885,7 +922,8 @@ export class SideBySideEditorControl implements ISideBySideEditorControl, IVerti const useTabs = !!$this.configurationService.getConfiguration().workbench.editor.showTabs; overlay = $('div').style({ - top: useTabs ? SideBySideEditorControl.EDITOR_TITLE_HEIGHT + 'px' : 0 + top: useTabs ? SideBySideEditorControl.EDITOR_TITLE_HEIGHT + 'px' : 0, + height: useTabs ? `calc(100% - ${SideBySideEditorControl.EDITOR_TITLE_HEIGHT}px` : '100%' }).id(overlayId); overlay.appendTo(container); @@ -976,7 +1014,8 @@ export class SideBySideEditorControl implements ISideBySideEditorControl, IVerti // Overlay the editor area with a div to be able to capture all mouse events let overlayDiv = $('div').style({ - top: SideBySideEditorControl.EDITOR_TITLE_HEIGHT + 'px' + top: SideBySideEditorControl.EDITOR_TITLE_HEIGHT + 'px', + height: '100%' }).id('monaco-workbench-editor-move-overlay'); overlayDiv.appendTo(this.parent); @@ -1122,8 +1161,12 @@ export class SideBySideEditorControl implements ISideBySideEditorControl, IVerti // Move to valid position if any if (moveTo !== null) { this.editorGroupService.moveGroup(position, moveTo); - this.titleAreaControl[position].refresh(true); - this.titleAreaControl[moveTo].refresh(true); + + // To reduce flickering during this operation we trigger a refresh of all + // title controls right after. + POSITIONS.forEach(p => { + this.titleAreaControl[p].refresh(true); + }); } // Otherwise layout to restore proper positioning diff --git a/src/vs/workbench/browser/parts/editor/tabsTitleControl.ts b/src/vs/workbench/browser/parts/editor/tabsTitleControl.ts index 2e8e005186f..5e304542ca7 100644 --- a/src/vs/workbench/browser/parts/editor/tabsTitleControl.ts +++ b/src/vs/workbench/browser/parts/editor/tabsTitleControl.ts @@ -78,6 +78,14 @@ export class TabsTitleControl extends TitleControl { this.tabsContainer.setAttribute('role', 'tablist'); DOM.addClass(this.tabsContainer, 'tabs-container'); + this.toDispose.push(DOM.addDisposableListener(this.tabsContainer, DOM.EventType.SCROLL, e => { + if (DOM.hasClass(this.tabsContainer, 'scroll')) { + this.scrollbar.updateState({ + scrollLeft: this.tabsContainer.scrollLeft // during DND the container gets scrolled so we need to update the custom scrollbar + }); + } + })); + // Custom Scrollbar this.scrollbar = new ScrollableElement(this.tabsContainer, { horizontal: ScrollbarVisibility.Auto, @@ -87,7 +95,6 @@ export class TabsTitleControl extends TitleControl { canUseTranslate3d: true, horizontalScrollbarSize: 3 }); - // this.tabsContainer.style.overflow = 'scroll'; // custom scrollbar is eager on removing this style but we want it for DND scroll feedback this.scrollbar.onScroll(e => { this.tabsContainer.scrollLeft = e.scrollLeft; @@ -97,6 +104,8 @@ export class TabsTitleControl extends TitleControl { // Drag over this.toDispose.push(DOM.addDisposableListener(this.tabsContainer, DOM.EventType.DRAG_OVER, (e: DragEvent) => { + DOM.addClass(this.tabsContainer, 'scroll'); // enable support to scroll while dragging + const target = e.target; if (target instanceof HTMLElement && target.className.indexOf('tabs-container') === 0) { DOM.addClass(this.tabsContainer, 'dropfeedback'); @@ -106,16 +115,19 @@ export class TabsTitleControl extends TitleControl { // Drag leave this.toDispose.push(DOM.addDisposableListener(this.tabsContainer, DOM.EventType.DRAG_LEAVE, (e: DragEvent) => { DOM.removeClass(this.tabsContainer, 'dropfeedback'); + DOM.removeClass(this.tabsContainer, 'scroll'); })); // Drag end this.toDispose.push(DOM.addDisposableListener(this.tabsContainer, DOM.EventType.DRAG_END, (e: DragEvent) => { DOM.removeClass(this.tabsContainer, 'dropfeedback'); + DOM.removeClass(this.tabsContainer, 'scroll'); })); // Drop onto tabs container this.toDispose.push(DOM.addDisposableListener(this.tabsContainer, DOM.EventType.DROP, (e: DragEvent) => { DOM.removeClass(this.tabsContainer, 'dropfeedback'); + DOM.removeClass(this.tabsContainer, 'scroll'); const target = e.target; if (target instanceof HTMLElement && target.className.indexOf('tabs-container') === 0) { @@ -339,10 +351,7 @@ export class TabsTitleControl extends TitleControl { // Update enablement of certain actions that depend on overflow const isOverflowing = (totalContainerWidth > visibleContainerWidth); - this.showEditorsOfLeftGroup.enabled = isOverflowing; - this.showEditorsOfCenterGroup.enabled = isOverflowing; - this.showEditorsOfRightGroup.enabled = isOverflowing; - this.showAllEditorsAction.enabled = isOverflowing; + this.showEditorsInGroupAction.enabled = isOverflowing; } private hookTabListeners(tab: HTMLElement, identifier: IEditorIdentifier): void { @@ -420,7 +429,6 @@ export class TabsTitleControl extends TitleControl { // Drag start this.tabDisposeables.push(DOM.addDisposableListener(tab, DOM.EventType.DRAG_START, (e: DragEvent) => { - DOM.addClass(tab, 'dragged'); this.onEditorDragStart({ editor, group }); e.dataTransfer.effectAllowed = 'copyMove'; @@ -443,13 +451,15 @@ export class TabsTitleControl extends TitleControl { // Drag end this.tabDisposeables.push(DOM.addDisposableListener(tab, DOM.EventType.DRAG_END, (e: DragEvent) => { - DOM.removeClass(tab, 'dragged'); DOM.removeClass(tab, 'dropfeedback'); + this.onEditorDragEnd(); })); // Drop this.tabDisposeables.push(DOM.addDisposableListener(tab, DOM.EventType.DROP, (e: DragEvent) => { + DOM.removeClass(tab, 'dropfeedback'); + const targetPosition = this.stacks.positionOfGroup(group); const targetIndex = group.indexOf(editor); diff --git a/src/vs/workbench/browser/parts/editor/titleControl.ts b/src/vs/workbench/browser/parts/editor/titleControl.ts index 789fb025af6..1050cf3405e 100644 --- a/src/vs/workbench/browser/parts/editor/titleControl.ts +++ b/src/vs/workbench/browser/parts/editor/titleControl.ts @@ -15,7 +15,7 @@ import DOM = require('vs/base/browser/dom'); import {TPromise} from 'vs/base/common/winjs.base'; import {BaseEditor, IEditorInputActionContext} from 'vs/workbench/browser/parts/editor/baseEditor'; import {RunOnceScheduler} from 'vs/base/common/async'; -import {IEditorStacksModel, IEditorGroup, IEditorIdentifier, EditorInput, IWorkbenchEditorConfiguration} from 'vs/workbench/common/editor'; +import {IEditorStacksModel, IEditorGroup, IEditorIdentifier, EditorInput, IWorkbenchEditorConfiguration, IStacksModelChangeEvent} from 'vs/workbench/common/editor'; import {EventType as BaseEventType} from 'vs/base/common/events'; import {IActionItem, ActionsOrientation, Separator} from 'vs/base/browser/ui/actionbar/actionbar'; import {ToolBar} from 'vs/base/browser/ui/toolbar/toolbar'; @@ -25,14 +25,11 @@ import {Position} from 'vs/platform/editor/common/editor'; import {IConfigurationService} from 'vs/platform/configuration/common/configuration'; import {IEditorGroupService} from 'vs/workbench/services/group/common/groupService'; import {IMessageService, Severity} from 'vs/platform/message/common/message'; -import {QuickOpenAction} from 'vs/workbench/browser/quickopen'; import {StandardMouseEvent} from 'vs/base/browser/mouseEvent'; import {ITelemetryService} from 'vs/platform/telemetry/common/telemetry'; import {IInstantiationService} from 'vs/platform/instantiation/common/instantiation'; import {IKeybindingService} from 'vs/platform/keybinding/common/keybindingService'; -import {ShowEditorsInLeftGroupAction, ShowAllEditorsAction, ShowEditorsInCenterGroupAction, ShowEditorsInRightGroupAction, CloseEditorsInGroupAction, MoveGroupLeftAction, - MoveGroupRightAction, SplitEditorAction, CloseEditorAction, KeepEditorAction, CloseOtherEditorsInGroupAction, CloseRightEditorsInGroupAction} -from 'vs/workbench/browser/parts/editor/editorActions'; +import {CloseEditorsInGroupAction, MoveGroupLeftAction, MoveGroupRightAction, SplitEditorAction, CloseEditorAction, KeepEditorAction, CloseOtherEditorsInGroupAction, CloseRightEditorsInGroupAction, ShowEditorsInGroupAction} from 'vs/workbench/browser/parts/editor/editorActions'; import {IDisposable, dispose} from 'vs/base/common/lifecycle'; export interface IToolbarActions { @@ -62,14 +59,11 @@ export abstract class TitleControl { protected pinEditorAction: KeepEditorAction; protected closeOtherEditorsAction: CloseOtherEditorsInGroupAction; protected closeRightEditorsAction: CloseRightEditorsInGroupAction; - protected showEditorsOfLeftGroup: QuickOpenAction; - protected showEditorsOfCenterGroup: QuickOpenAction; - protected showEditorsOfRightGroup: QuickOpenAction; protected moveGroupLeftAction: MoveGroupLeftAction; protected moveGroupRightAction: MoveGroupRightAction; protected closeEditorsInGroupAction: CloseEditorsInGroupAction; protected splitEditorAction: SplitEditorAction; - protected showAllEditorsAction: ShowAllEditorsAction; + protected showEditorsInGroupAction: ShowEditorsInGroupAction; private previewEditors: boolean; private showTabs: boolean; @@ -115,6 +109,13 @@ export abstract class TitleControl { private registerListeners(): void { this.toDispose.push(this.configurationService.onDidUpdateConfiguration(e => this.onConfigurationUpdated(e.config))); + this.toDispose.push(this.stacks.onModelChanged(e => this.onStacksChanged(e))); + } + + private onStacksChanged(e: IStacksModelChangeEvent): void { + if (e.structural) { + this.updateSplitActionEnablement(); + } } private onConfigurationUpdated(config: IWorkbenchEditorConfiguration): void { @@ -122,37 +123,18 @@ export abstract class TitleControl { this.showTabs = config.workbench.editor.showTabs; } - private updateActionEnablement(): void { + private updateSplitActionEnablement(): void { if (!this.context) { return; } - const group = this.context; const groupCount = this.stacks.groups.length; - // Move group - switch (this.stacks.positionOfGroup(group)) { - case Position.LEFT: - this.moveGroupLeftAction.enabled = false; - this.moveGroupRightAction.enabled = this.stacks.groups.length > 1; - break; - - case Position.CENTER: - this.moveGroupRightAction.enabled = this.stacks.groups.length > 2; - break; - - case Position.RIGHT: - this.moveGroupRightAction.enabled = false; - break; - } - // Split editor this.splitEditorAction.enabled = groupCount < 3; } private onSchedule(): void { - this.updateActionEnablement(); - if (this.refreshScheduled) { this.doRefresh(); } else { @@ -206,15 +188,12 @@ export abstract class TitleControl { this.closeRightEditorsAction = this.instantiationService.createInstance(CloseRightEditorsInGroupAction, CloseRightEditorsInGroupAction.ID, nls.localize('closeRight', "Close to the Right")); this.closeEditorsInGroupAction = this.instantiationService.createInstance(CloseEditorsInGroupAction, CloseEditorsInGroupAction.ID, nls.localize('closeAll', "Close All")); this.pinEditorAction = this.instantiationService.createInstance(KeepEditorAction, KeepEditorAction.ID, nls.localize('keepEditor', "Keep Editor")); - this.showAllEditorsAction = this.instantiationService.createInstance(ShowAllEditorsAction, ShowAllEditorsAction.ID, nls.localize('showEditors', "Show Editors")); + this.showEditorsInGroupAction = this.instantiationService.createInstance(ShowEditorsInGroupAction, ShowEditorsInGroupAction.ID, ShowEditorsInGroupAction.LABEL); this.splitEditorAction = this.instantiationService.createInstance(SplitEditorAction, SplitEditorAction.ID, SplitEditorAction.LABEL); this.moveGroupLeftAction = this.instantiationService.createInstance(MoveGroupLeftAction, MoveGroupLeftAction.ID, nls.localize('moveLeft', "Move Left")); this.moveGroupRightAction = this.instantiationService.createInstance(MoveGroupRightAction, MoveGroupRightAction.ID, nls.localize('moveRight', "Move Right")); - this.showEditorsOfLeftGroup = this.instantiationService.createInstance(ShowEditorsInLeftGroupAction, ShowEditorsInLeftGroupAction.ID, nls.localize('showEditors', "Show Editors")); - this.showEditorsOfCenterGroup = this.instantiationService.createInstance(ShowEditorsInCenterGroupAction, ShowEditorsInCenterGroupAction.ID, nls.localize('showEditors', "Show Editors")); - this.showEditorsOfRightGroup = this.instantiationService.createInstance(ShowEditorsInRightGroupAction, ShowEditorsInRightGroupAction.ID, nls.localize('showEditors', "Show Editors")); - [this.showEditorsOfLeftGroup, this.showEditorsOfCenterGroup, this.showEditorsOfRightGroup, this.showAllEditorsAction].forEach(a => a.class = 'show-group-editors-action'); + this.showEditorsInGroupAction.class = 'show-group-editors-action'; } protected doCreateToolbar(container: HTMLElement): ToolBar { @@ -328,35 +307,30 @@ export abstract class TitleControl { const editor = group.activeEditor; const primary: IAction[] = []; - const groupCount = this.stacks.groups.length; - // Overflow - let overflowAction: Action; - if (groupCount === 1) { - overflowAction = this.showAllEditorsAction; - } else { - switch (this.stacks.positionOfGroup(group)) { - case Position.LEFT: - overflowAction = this.showEditorsOfLeftGroup; - break; - - case Position.CENTER: - overflowAction = (groupCount === 2) ? this.showEditorsOfRightGroup : this.showEditorsOfCenterGroup; - break; - - case Position.RIGHT: - overflowAction = this.showEditorsOfRightGroup; - break; - } - } - - primary.push(overflowAction); + primary.push(this.showEditorsInGroupAction); // Splitting if (editor instanceof EditorInput && editor.supportsSplitEditor()) { primary.push(this.splitEditorAction); } + // Enablement + switch (this.stacks.positionOfGroup(group)) { + case Position.LEFT: + this.moveGroupLeftAction.enabled = false; + this.moveGroupRightAction.enabled = this.stacks.groups.length > 1; + break; + + case Position.CENTER: + this.moveGroupRightAction.enabled = this.stacks.groups.length > 2; + break; + + case Position.RIGHT: + this.moveGroupRightAction.enabled = false; + break; + } + // Return actions const secondary = [ this.moveGroupLeftAction, @@ -423,10 +397,7 @@ export abstract class TitleControl { // Actions [ this.splitEditorAction, - this.showAllEditorsAction, - this.showEditorsOfLeftGroup, - this.showEditorsOfCenterGroup, - this.showEditorsOfRightGroup, + this.showEditorsInGroupAction, this.closeEditorAction, this.closeRightEditorsAction, this.closeOtherEditorsAction, diff --git a/src/vs/workbench/parts/files/browser/fileActions.ts b/src/vs/workbench/parts/files/browser/fileActions.ts index a53028044da..ce8e106df46 100644 --- a/src/vs/workbench/parts/files/browser/fileActions.ts +++ b/src/vs/workbench/parts/files/browser/fileActions.ts @@ -1541,13 +1541,18 @@ export abstract class BaseSaveAllAction extends BaseActionWithErrorReporting { const stacks = this.editorGroupService.getStacksModel(); // Store some properties per untitled file to restore later after save is completed - const mapUntitledToProperties: { [resource: string]: { mime: string; encoding: string; indexInGroups: number[]; } } = Object.create(null); + const mapUntitledToProperties: { [resource: string]: { mime: string; encoding: string; indexInGroups: number[]; activeInGroups: boolean[] } } = Object.create(null); this.textFileService.getDirty() .filter(r => r.scheme === 'untitled') // All untitled resources .map(r => this.untitledEditorService.get(r)) // Mapped to their inputs - .filter(i => !!i) // If possible :) - .forEach(i => { - mapUntitledToProperties[i.getResource().toString()] = { mime: i.getMime(), encoding: i.getEncoding(), indexInGroups: stacks.groups.map(g => g.indexOf(i)) }; + .filter(input => !!input) // If possible :) + .forEach(input => { + mapUntitledToProperties[input.getResource().toString()] = { + mime: input.getMime(), + encoding: input.getEncoding(), + indexInGroups: stacks.groups.map(g => g.indexOf(input)), + activeInGroups: stacks.groups.map(g => g.isActive(input)) + }; }); // Save all @@ -1582,7 +1587,8 @@ export abstract class BaseSaveAllAction extends BaseActionWithErrorReporting { options: { pinned: true, index: indexInGroup, - preserveFocus: true + preserveFocus: true, + inactive: !untitledProps.activeInGroups[index] } }, position: index diff --git a/src/vs/workbench/services/contextview/electron-browser/contextmenuService.ts b/src/vs/workbench/services/contextview/electron-browser/contextmenuService.ts index 953620e6209..d1cd4a990ae 100644 --- a/src/vs/workbench/services/contextview/electron-browser/contextmenuService.ts +++ b/src/vs/workbench/services/contextview/electron-browser/contextmenuService.ts @@ -57,7 +57,7 @@ export class ContextMenuService implements IContextMenuService { x *= zoom; y *= zoom; - menu.popup(remote.getCurrentWindow(), Math.floor(x), Math.floor(y)); + menu.popup(remote.getCurrentWindow(), Math.floor(x), Math.floor(y), -1 /* no item selected by default */); if (delegate.onHide) { delegate.onHide(undefined); } From f8bb4ade94ba5c9401419d3ec1e12fbe8719e0c1 Mon Sep 17 00:00:00 2001 From: Erich Gamma Date: Sun, 19 Jun 2016 20:13:34 +0200 Subject: [PATCH 195/217] Added wrapWithAbbreviation, updateTag, removeTag --- .../editor/contrib/snippet/common/snippet.ts | 14 +-- .../parts/emmet/node/editorAccessor.ts | 35 ++++--- .../parts/emmet/node/emmet.contribution.ts | 17 +++- src/vs/workbench/parts/emmet/node/emmet.d.ts | 62 ++++++------ .../parts/emmet/node/emmetActions.ts | 99 +++++++++++++++++-- 5 files changed, 163 insertions(+), 64 deletions(-) diff --git a/src/vs/editor/contrib/snippet/common/snippet.ts b/src/vs/editor/contrib/snippet/common/snippet.ts index b006e09fd06..a54a4465626 100644 --- a/src/vs/editor/contrib/snippet/common/snippet.ts +++ b/src/vs/editor/contrib/snippet/common/snippet.ts @@ -700,7 +700,7 @@ class InsertSnippetController { } export interface ISnippetController extends editorCommon.IEditorContribution { - run(snippet: CodeSnippet, overwriteBefore: number, overwriteAfter: number): void; + run(snippet: CodeSnippet, overwriteBefore: number, overwriteAfter: number, stripPrefix?:boolean): void; jumpToNextPlaceholder(): void; jumpToPrevPlaceholder(): void; acceptSnippet(): void; @@ -736,7 +736,7 @@ class SnippetController implements ISnippetController { return SnippetController.ID; } - public run(snippet:CodeSnippet, overwriteBefore:number, overwriteAfter:number): void { + public run(snippet:CodeSnippet, overwriteBefore:number, overwriteAfter:number, stripPrefix?:boolean): void { let prevController = this._currentController; this._currentController = null; @@ -744,7 +744,7 @@ class SnippetController implements ISnippetController { // No placeholders => execute for all editor selections this._runForAllSelections(snippet, overwriteBefore, overwriteAfter); } else { - this._runForPrimarySelection(snippet, overwriteBefore, overwriteAfter); + this._runForPrimarySelection(snippet, overwriteBefore, overwriteAfter, stripPrefix); } if (!this._currentController) { @@ -785,12 +785,12 @@ class SnippetController implements ISnippetController { } } - private _runForPrimarySelection(snippet: CodeSnippet, overwriteBefore: number, overwriteAfter: number): void { + private _runForPrimarySelection(snippet: CodeSnippet, overwriteBefore: number, overwriteAfter: number, stripPrefix?:boolean): void { let initialAlternativeVersionId = this._editor.getModel().getAlternativeVersionId(); let edits: editorCommon.IIdentifiedSingleEditOperation[] = []; - let prepared = SnippetController._prepareSnippet(this._editor, this._editor.getSelection(), snippet, overwriteBefore, overwriteAfter); + let prepared = SnippetController._prepareSnippet(this._editor, this._editor.getSelection(), snippet, overwriteBefore, overwriteAfter, stripPrefix); SnippetController._addCommandForSnippet(this._editor.getModel(), prepared.adaptedSnippet, prepared.typeRange, edits); if (edits.length > 0) { @@ -822,7 +822,7 @@ class SnippetController implements ISnippetController { } } - private static _prepareSnippet(editor:editorCommon.ICommonCodeEditor, selection:Selection, snippet:CodeSnippet, overwriteBefore:number, overwriteAfter:number): { typeRange: Range; adaptedSnippet: ICodeSnippet; } { + private static _prepareSnippet(editor:editorCommon.ICommonCodeEditor, selection:Selection, snippet:CodeSnippet, overwriteBefore:number, overwriteAfter:number, stripPrefix?:boolean): { typeRange: Range; adaptedSnippet: ICodeSnippet; } { var model = editor.getModel(); var typeRange = SnippetController._getTypeRangeForSelection(model, selection, overwriteBefore, overwriteAfter); @@ -831,7 +831,7 @@ class SnippetController implements ISnippetController { var nextInSnippet = snippet.lines[0].substr(overwriteBefore); var commonPrefix = strings.commonPrefixLength(nextTextOnLine, nextInSnippet); - if (commonPrefix > 0) { + if (commonPrefix > 0 && !stripPrefix === false) { typeRange = typeRange.setEndPosition(typeRange.endLineNumber, typeRange.endColumn + commonPrefix); } } diff --git a/src/vs/workbench/parts/emmet/node/editorAccessor.ts b/src/vs/workbench/parts/emmet/node/editorAccessor.ts index 4d3b51de4d3..81a3a40c16a 100644 --- a/src/vs/workbench/parts/emmet/node/editorAccessor.ts +++ b/src/vs/workbench/parts/emmet/node/editorAccessor.ts @@ -60,7 +60,7 @@ export class EditorAccessor implements emmet.Editor { } public setCaretPos(pos: number): void { - // + this.createSelection(pos); } public getCurrentLine(): string { @@ -86,29 +86,29 @@ export class EditorAccessor implements emmet.Editor { // shift column by +1 since they are 1 based let range = new Range(startPosition.lineNumber, startPosition.column + 1, endPosition.lineNumber, endPosition.column + 1); - let deletePreviousChars = 0; - if (range.startLineNumber === range.endLineNumber) { - // The snippet will delete - deletePreviousChars = range.endColumn - range.startColumn; - } else { - // We must manually delete - let command = new ReplaceCommand(range, ''); - this.editor.executeCommand('emmet', command); - deletePreviousChars = 0; - } + let command = new ReplaceCommand(range, ''); + this.editor.executeCommand('emmet', command); let snippet = snippets.CodeSnippet.convertExternalSnippet(value, snippets.ExternalSnippetType.EmmetSnippet); let codeSnippet = new snippets.CodeSnippet(snippet); - snippets.getSnippetController(this.editor).run(codeSnippet, deletePreviousChars, 0); + snippets.getSnippetController(this.editor).run(codeSnippet, 0, 0, false); } public getContent(): string { return this.editor.getModel().getValue(); } - public createSelection(start: number, end: number): void { - // + public createSelection(startOffset: number, endOffset?: number): void { + let startPosition = this.getPositionFromOffset(startOffset); + let endPosition = null; + if (!endOffset) { + endPosition = startPosition; + } else { + endPosition = this.getPositionFromOffset(endOffset); + } + let range = new Range(startPosition.lineNumber, startPosition.column + 1, endPosition.lineNumber, endPosition.column + 1); + this.editor.setSelection(range); } public getSyntax(): string { @@ -136,7 +136,12 @@ export class EditorAccessor implements emmet.Editor { } public getSelection(): string { - return ''; + let selection = this.editor.getSelection(); + let model = this.editor.getModel(); + let start = selection.getStartPosition(); + let end = selection.getEndPosition(); + let range = new Range(start.lineNumber, start.column, end.lineNumber, end.column); + return model.getValueInRange(range); } public getFilePath(): string { diff --git a/src/vs/workbench/parts/emmet/node/emmet.contribution.ts b/src/vs/workbench/parts/emmet/node/emmet.contribution.ts index 2cf673e010c..f03f653ac6e 100644 --- a/src/vs/workbench/parts/emmet/node/emmet.contribution.ts +++ b/src/vs/workbench/parts/emmet/node/emmet.contribution.ts @@ -11,7 +11,7 @@ import {CommonEditorRegistry, EditorActionDescriptor} from 'vs/editor/common/edi import {IConfigurationRegistry, Extensions as ConfigurationExtensions} from 'vs/platform/configuration/common/configurationRegistry'; import editorCommon = require('vs/editor/common/editorCommon'); -import {ExpandAbbreviationAction} from './emmetActions'; +import {ExpandAbbreviationAction, WrapWithAbbreviationAction, RemoveTagAction, UpdateTagAction} from './emmetActions'; import {KeybindingsRegistry} from 'vs/platform/keybinding/common/keybindingsRegistry'; import {KeyCode} from 'vs/base/common/keyCodes'; import {KbExpr} from 'vs/platform/keybinding/common/keybindingService'; @@ -21,6 +21,21 @@ CommonEditorRegistry.registerEditorAction(new EditorActionDescriptor(ExpandAbbre nls.localize('expandAbbreviationAction', "Emmet: Expand Abbreviation"), void 0, 'Emmet: Expand Abbreviation')); +CommonEditorRegistry.registerEditorAction(new EditorActionDescriptor(WrapWithAbbreviationAction, + WrapWithAbbreviationAction.ID, + nls.localize('wrapWithAbbreviationAction', + "Emmet: Wrap with Abbreviation"), void 0, 'Emmet: Wrap with Abbreviation')); + +CommonEditorRegistry.registerEditorAction(new EditorActionDescriptor(RemoveTagAction, + RemoveTagAction.ID, + nls.localize('removeTag', + "Emmet: Remove Tag"), void 0, 'Emmet: Remove Tag')); + +CommonEditorRegistry.registerEditorAction(new EditorActionDescriptor(UpdateTagAction, + UpdateTagAction.ID, + nls.localize('updateTag', + "Emmet: Update Tag"), void 0, 'Emmet: Update Tag')); + KeybindingsRegistry.registerCommandRule({ id: ExpandAbbreviationAction.ID, weight: KeybindingsRegistry.WEIGHT.editorContrib(), diff --git a/src/vs/workbench/parts/emmet/node/emmet.d.ts b/src/vs/workbench/parts/emmet/node/emmet.d.ts index 5a5380d64b3..97aa42e38ae 100644 --- a/src/vs/workbench/parts/emmet/node/emmet.d.ts +++ b/src/vs/workbench/parts/emmet/node/emmet.d.ts @@ -13,30 +13,30 @@ declare module 'emmet' { export interface Editor { /** * Returns character indexes of selected text: object with start - * and end properties. If there's no selection, should return + * and end properties. If there's no selection, should return * object with start and end properties referring * to current caret position * @return {Object} * @example * var selection = editor.getSelectionRange(); - * alert(selection.start + ', ' + selection.end); + * alert(selection.start + ', ' + selection.end); */ getSelectionRange(): Range; - + /** * Creates selection from start to end character - * indexes. If end is omitted, this method should place caret + * indexes. If end is omitted, this method should place caret * and start index * @param {Number} start * @param {Number} [end] * @example * editor.createSelection(10, 40); - * + * * //move caret to 15th character * editor.createSelection(15); */ - createSelection(start: number, end: number): void; - + createSelection(start: number, end?: number): void; + /** * Returns current line's start and end indexes as object with start * and end properties @@ -46,72 +46,72 @@ declare module 'emmet' { * alert(range.start + ', ' + range.end); */ getCurrentLineRange(): Range; - + /** * Returns current caret position * @return {Number|null} */ getCaretPos(): number; - + /** * Set new caret position * @param {Number} pos Caret position */ setCaretPos(pos: number): void; - + /** * Returns content of current line * @return {String} */ getCurrentLine(): string; - + /** - * Replace editor's content or it's part (from start to - * end index). If value contains - * caret_placeholder, the editor will put caret into + * Replace editor's content or it's part (from start to + * end index). If value contains + * caret_placeholder, the editor will put caret into * this position. If you skip start and end - * arguments, the whole target's content will be replaced with - * value. - * + * arguments, the whole target's content will be replaced with + * value. + * * If you pass start argument only, - * the value will be placed at start string - * index of current content. - * + * the value will be placed at start string + * index of current content. + * * If you pass start and end arguments, - * the corresponding substring of current target's content will be - * replaced with value. + * the corresponding substring of current target's content will be + * replaced with value. * @param {String} value Content you want to paste * @param {Number} [start] Start index of editor's content * @param {Number} [end] End index of editor's content * @param {Boolean} [no_indent] Do not auto indent value */ replaceContent(value: string, start: number, end: number, no_indent: boolean): void; - + /** * Returns editor's content * @return {String} */ getContent(): string; - + /** * Returns current editor's syntax mode * @return {String} */ getSyntax(): string; - + /** * Returns current output profile name (see profile module). - * In most cases, this method should return null and let + * In most cases, this method should return null and let * Emmet guess best profile name for current syntax and user data. - * In case you’re using advanced editor with access to syntax scopes - * (like Sublime Text 2), you can return syntax name for current scope. + * In case you’re using advanced editor with access to syntax scopes + * (like Sublime Text 2), you can return syntax name for current scope. * For example, you may return `line` profile when editor caret is inside * string of programming language. - * + * * @return {String} */ getProfileName(): string; - + /** * Ask user to enter something * @param {String} title Dialog title @@ -124,7 +124,7 @@ declare module 'emmet' { getFilePath(): string; } - + /** * Runs given action * @param {String} name Action name diff --git a/src/vs/workbench/parts/emmet/node/emmetActions.ts b/src/vs/workbench/parts/emmet/node/emmetActions.ts index 69a204280f9..0b066b726a5 100644 --- a/src/vs/workbench/parts/emmet/node/emmetActions.ts +++ b/src/vs/workbench/parts/emmet/node/emmetActions.ts @@ -10,34 +10,113 @@ import {IEditorActionDescriptorData, ICommonCodeEditor} from 'vs/editor/common/e import {EditorAction} from 'vs/editor/common/editorAction'; import {Behaviour} from 'vs/editor/common/editorActionEnablement'; import {EditorAccessor} from './editorAccessor'; +import {IQuickOpenService, IInputOptions} from 'vs/workbench/services/quickopen/common/quickOpenService'; +import nls = require('vs/nls'); -export class ExpandAbbreviationAction extends EditorAction { - static ID = 'editor.emmet.action.expandAbbreviation'; +export abstract class EmmetEditorAction extends EditorAction { - private editorAccessor: EditorAccessor; + protected static editorAccessor: EditorAccessor; constructor(descriptor: IEditorActionDescriptorData, editor: ICommonCodeEditor) { super(descriptor, editor, Behaviour.TextFocus); - this.editorAccessor = new EditorAccessor(editor); + if (!EmmetEditorAction.editorAccessor) { + EmmetEditorAction.editorAccessor = new EditorAccessor(editor); + } } + abstract runEmmetAction(_module: any); + public run(): TPromise { return new TPromise((c, e) => { require(['emmet'], (_module) => { try { - if (!this.editorAccessor.isEmmetEnabledMode()) { - this.editorAccessor.noExpansionOccurred(); + if (!EmmetEditorAction.editorAccessor.isEmmetEnabledMode()) { + EmmetEditorAction.editorAccessor.noExpansionOccurred(); return; } - if (!_module.run('expand_abbreviation', this.editorAccessor)) { - this.editorAccessor.noExpansionOccurred(); - } + this.runEmmetAction(_module); } catch (err) { // } finally { - this.editorAccessor.flushCache(); + EmmetEditorAction.editorAccessor.flushCache(); } }, e); }); } +} + +export class ExpandAbbreviationAction extends EmmetEditorAction { + static ID = 'editor.emmet.action.expandAbbreviation'; + + constructor(descriptor: IEditorActionDescriptorData, editor: ICommonCodeEditor) { + super(descriptor, editor); + } + + public runEmmetAction(_module) { + if (!_module.run('expand_abbreviation', EmmetEditorAction.editorAccessor)) { + EmmetEditorAction.editorAccessor.noExpansionOccurred(); + } + } +} + +export class RemoveTagAction extends EmmetEditorAction { + static ID = 'editor.emmet.action.removeTag'; + + constructor(descriptor: IEditorActionDescriptorData, editor: ICommonCodeEditor) { + super(descriptor, editor); + } + + public runEmmetAction(_module) { + if (!_module.run('remove_tag', EmmetEditorAction.editorAccessor)) { + EmmetEditorAction.editorAccessor.noExpansionOccurred(); + } + } +} + +export class UpdateTagAction extends EmmetEditorAction { + static ID = 'editor.emmet.action.updateTag'; + + constructor(descriptor: IEditorActionDescriptorData, editor: ICommonCodeEditor, @IQuickOpenService private quickOpenService: IQuickOpenService) { + super(descriptor, editor); + } + + public runEmmetAction(_module) { + let options: IInputOptions = { + prompt: nls.localize('enterTag', "Enter Tag"), + placeHolder: nls.localize('tag', "Tag") + }; + this.quickOpenService.input(options).then(tag => { + this.wrapAbbreviation(_module, tag); + }); + } + + private wrapAbbreviation(_module: any, tag) { + if (!_module.run('update_tag', EmmetEditorAction.editorAccessor, tag)) { + EmmetEditorAction.editorAccessor.noExpansionOccurred(); + } + } +} + +export class WrapWithAbbreviationAction extends EmmetEditorAction { + static ID = 'editor.emmet.action.wrapWithAbbreviation'; + + constructor(descriptor: IEditorActionDescriptorData, editor: ICommonCodeEditor, @IQuickOpenService private quickOpenService: IQuickOpenService) { + super(descriptor, editor); + } + + public runEmmetAction(_module) { + let options: IInputOptions = { + prompt: nls.localize('enterAbbreviation', "Enter Abbreviation"), + placeHolder: nls.localize('abbreviation', "Abbreviation") + }; + this.quickOpenService.input(options).then(abbreviation => { + this.wrapAbbreviation(_module, abbreviation); + }); + } + + private wrapAbbreviation(_module: any, abbreviation) { + if (!_module.run('wrap_with_abbreviation', EmmetEditorAction.editorAccessor, abbreviation)) { + EmmetEditorAction.editorAccessor.noExpansionOccurred(); + } + } } \ No newline at end of file From f416b8e8b4468529d2e19fe0941b2896a3d78732 Mon Sep 17 00:00:00 2001 From: Joao Moreno Date: Mon, 20 Jun 2016 08:46:04 +0200 Subject: [PATCH 196/217] nls fix --- src/vs/workbench/parts/git/browser/gitActions.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/vs/workbench/parts/git/browser/gitActions.ts b/src/vs/workbench/parts/git/browser/gitActions.ts index be7d5d26d25..1b276a31923 100644 --- a/src/vs/workbench/parts/git/browser/gitActions.ts +++ b/src/vs/workbench/parts/git/browser/gitActions.ts @@ -773,7 +773,7 @@ export class InputCommitAction extends GitAction { const status = this.gitService.getModel().getStatus(); - return this.quickOpenService.input({ prompt: 'Commit Message' }) + return this.quickOpenService.input({ prompt: nls.localize('commitMessage', "Commit Message") }) .then(message => message && this.gitService.commit(message, false, status.getIndexStatus().all().length === 0)); } } From 8203a8970d7a8a27b3bee95595446b9c0c0ed8de Mon Sep 17 00:00:00 2001 From: Benjamin Pasero Date: Mon, 20 Jun 2016 09:03:37 +0200 Subject: [PATCH 197/217] fix ui glitch with editor width ratios --- src/vs/workbench/browser/parts/editor/editorPart.ts | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/src/vs/workbench/browser/parts/editor/editorPart.ts b/src/vs/workbench/browser/parts/editor/editorPart.ts index bdae70268ef..7b1d550a557 100644 --- a/src/vs/workbench/browser/parts/editor/editorPart.ts +++ b/src/vs/workbench/browser/parts/editor/editorPart.ts @@ -933,7 +933,11 @@ export class EditorPart extends Part implements IEditorPart, IEditorGroupService // Validate width ratios const positions = rightEditors.length ? 3 : centerEditors.length ? 2 : 1; if (widthRatios.length !== positions) { - widthRatios = void 0; // being taken care of by the layouting + if (!this.getVisibleEditors().length) { + widthRatios = (positions === 3) ? [0.33, 0.33, 0.34] : (positions === 2) ? [0.5, 0.5] : [1]; + } else { + widthRatios = void 0; // being taken care of by the layouting if editors are already open + } } // Open each input respecting the options. Since there can only be one active editor in each From 482f09f28a3df3f40cefdba9f444bfa3ff116471 Mon Sep 17 00:00:00 2001 From: isidor Date: Mon, 20 Jun 2016 09:29:36 +0200 Subject: [PATCH 198/217] open editors: do not allow left / right to expand and collapse groups fixes #7848 --- .../parts/files/browser/views/openEditorsViewer.ts | 9 +++++++++ 1 file changed, 9 insertions(+) diff --git a/src/vs/workbench/parts/files/browser/views/openEditorsViewer.ts b/src/vs/workbench/parts/files/browser/views/openEditorsViewer.ts index bfc700188ee..89ccef4c629 100644 --- a/src/vs/workbench/parts/files/browser/views/openEditorsViewer.ts +++ b/src/vs/workbench/parts/files/browser/views/openEditorsViewer.ts @@ -272,6 +272,15 @@ export class Controller extends treedefaults.DefaultController { return true; } + // Do not allow left / right to expand and collapse groups #7848 + protected onLeft(tree: ITree, event: IKeyboardEvent): boolean { + return true; + } + + protected onRight(tree: ITree, event: IKeyboardEvent): boolean { + return true; + } + protected onEnter(tree: ITree, event: IKeyboardEvent): boolean { var element = tree.getFocus(); From 74683cd2abefb805e9443ee3abc1c16a76ecb193 Mon Sep 17 00:00:00 2001 From: isidor Date: Mon, 20 Jun 2016 09:36:09 +0200 Subject: [PATCH 199/217] open editors: also update dirty indicator when view gets visibe fixes #7861 --- src/vs/workbench/parts/files/browser/views/openEditorsView.ts | 1 + 1 file changed, 1 insertion(+) diff --git a/src/vs/workbench/parts/files/browser/views/openEditorsView.ts b/src/vs/workbench/parts/files/browser/views/openEditorsView.ts index 37431614a3d..026f04aa1b0 100644 --- a/src/vs/workbench/parts/files/browser/views/openEditorsView.ts +++ b/src/vs/workbench/parts/files/browser/views/openEditorsView.ts @@ -138,6 +138,7 @@ export class OpenEditorsView extends AdaptiveCollapsibleViewletView { if (e.compositeId === VIEWLET_ID) { this.fullRefreshNeeded = true; this.structuralTreeUpdate(); + this.updateDirtyIndicator(); } })); } From 3f5b6f8b6475dcbb6b3e8154311938769ff5c119 Mon Sep 17 00:00:00 2001 From: isidor Date: Mon, 20 Jun 2016 09:54:56 +0200 Subject: [PATCH 200/217] debug: pixel math tunings for debu toolbar fixes #7844 --- src/vs/workbench/parts/debug/browser/debugActionsWidget.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/vs/workbench/parts/debug/browser/debugActionsWidget.ts b/src/vs/workbench/parts/debug/browser/debugActionsWidget.ts index be03ff13a80..387a9149cb2 100644 --- a/src/vs/workbench/parts/debug/browser/debugActionsWidget.ts +++ b/src/vs/workbench/parts/debug/browser/debugActionsWidget.ts @@ -107,7 +107,7 @@ export class DebugActionsWidget implements wbext.IWorkbenchContribution { const halfWidgetWidth = this.$el.getHTMLElement().clientWidth / 2; x = x + halfWidgetWidth - 16; // take into account half the size of the widget x = Math.max(148, x); // do not allow the widget to overflow on the left - x = Math.min(x, window.innerWidth - halfWidgetWidth); // do not allow the widget to overflow on the right + x = Math.min(x, window.innerWidth - halfWidgetWidth - 10); // do not allow the widget to overflow on the right this.$el.style('left', `${x}px`); } From 8a4bdea8b17fb0030aa1eec83404edef13f38e6e Mon Sep 17 00:00:00 2001 From: isidor Date: Mon, 20 Jun 2016 09:58:49 +0200 Subject: [PATCH 201/217] debug: polish loading and setting of x coordinate --- .../parts/debug/browser/debugActionsWidget.ts | 16 +++++++++------- 1 file changed, 9 insertions(+), 7 deletions(-) diff --git a/src/vs/workbench/parts/debug/browser/debugActionsWidget.ts b/src/vs/workbench/parts/debug/browser/debugActionsWidget.ts index 387a9149cb2..bdf2fced9f9 100644 --- a/src/vs/workbench/parts/debug/browser/debugActionsWidget.ts +++ b/src/vs/workbench/parts/debug/browser/debugActionsWidget.ts @@ -64,7 +64,6 @@ export class DebugActionsWidget implements wbext.IWorkbenchContribution { this.hide(); this.isBuilt = false; - this.onResize(); } private registerListeners(): void { @@ -82,7 +81,7 @@ export class DebugActionsWidget implements wbext.IWorkbenchContribution { this.telemetryService.publicLog('workbenchActionExecuted', { id: e.action.id, from: 'debugActionsWidget' }); } })); - $(window).on(dom.EventType.RESIZE, () => this.onResize(), this.toDispose); + $(window).on(dom.EventType.RESIZE, () => this.setXCoordinate(), this.toDispose); this.dragArea.on(dom.EventType.MOUSE_DOWN, event => { const $window = $(window); @@ -98,12 +97,14 @@ export class DebugActionsWidget implements wbext.IWorkbenchContribution { }); } - private onResize(): void { - const x = parseFloat(this.storageService.get(DEBUG_ACTIONS_WIDGET_POSITION_KEY, StorageScope.WORKSPACE, '0.5')) * window.innerWidth; - this.setXCoordinate(x); - } + private setXCoordinate(x?: number): void { + if (!this.isVisible) { + return; + } + if (!x) { + x = parseFloat(this.storageService.get(DEBUG_ACTIONS_WIDGET_POSITION_KEY, StorageScope.WORKSPACE, '0.5')) * window.innerWidth; + } - private setXCoordinate(x: number): void { const halfWidgetWidth = this.$el.getHTMLElement().clientWidth / 2; x = x + halfWidgetWidth - 16; // take into account half the size of the widget x = Math.max(148, x); // do not allow the widget to overflow on the left @@ -136,6 +137,7 @@ export class DebugActionsWidget implements wbext.IWorkbenchContribution { this.isVisible = true; this.$el.show(); + this.setXCoordinate(); } private hide(): void { From 10df2938f88a2bcf94e0fcb7f62c1d8f90095628 Mon Sep 17 00:00:00 2001 From: isidor Date: Mon, 20 Jun 2016 11:01:10 +0200 Subject: [PATCH 202/217] Debug toolbar: grab / grabbing cursor fixes #7845 --- src/vs/workbench/parts/debug/browser/debugActionsWidget.ts | 2 ++ .../parts/debug/browser/media/debug.contribution.css | 6 +++++- 2 files changed, 7 insertions(+), 1 deletion(-) diff --git a/src/vs/workbench/parts/debug/browser/debugActionsWidget.ts b/src/vs/workbench/parts/debug/browser/debugActionsWidget.ts index bdf2fced9f9..b5b8b1703c9 100644 --- a/src/vs/workbench/parts/debug/browser/debugActionsWidget.ts +++ b/src/vs/workbench/parts/debug/browser/debugActionsWidget.ts @@ -85,6 +85,7 @@ export class DebugActionsWidget implements wbext.IWorkbenchContribution { this.dragArea.on(dom.EventType.MOUSE_DOWN, event => { const $window = $(window); + this.dragArea.addClass('dragged'); $window.on('mousemove', (e: MouseEvent) => { const mouseMoveEvent = new StandardMouseEvent(e); @@ -92,6 +93,7 @@ export class DebugActionsWidget implements wbext.IWorkbenchContribution { }).once('mouseup', (e: MouseEvent) => { const mouseMoveEvent = new StandardMouseEvent(e); this.storageService.store(DEBUG_ACTIONS_WIDGET_POSITION_KEY, mouseMoveEvent.posx / window.innerWidth, StorageScope.WORKSPACE); + this.dragArea.removeClass('dragged'); $window.off('mousemove'); }); }); diff --git a/src/vs/workbench/parts/debug/browser/media/debug.contribution.css b/src/vs/workbench/parts/debug/browser/media/debug.contribution.css index 8d683383b77..dd878b9d291 100644 --- a/src/vs/workbench/parts/debug/browser/media/debug.contribution.css +++ b/src/vs/workbench/parts/debug/browser/media/debug.contribution.css @@ -135,12 +135,16 @@ } .monaco-workbench .debug-actions-widget .drag-area { - cursor: -webkit-grabbing; + cursor: -webkit-grab; height: 32px; width: 10px; background: url('drag.svg') center center no-repeat; } +.monaco-workbench .debug-actions-widget .drag-area.dragged { + cursor: -webkit-grabbing; +} + .monaco-workbench .debug-actions-widget .monaco-action-bar .action-label { width: 32px; height: 32px; From 6e255b936d9c901fe0ebdf3b18090205ae46123c Mon Sep 17 00:00:00 2001 From: Benjamin Pasero Date: Mon, 20 Jun 2016 13:54:15 +0200 Subject: [PATCH 203/217] fix issue with editor action resolution --- .../workbench/actionBarContributions.ts | 10 +---- .../parts/editor/noTabsTitleControl.ts | 2 +- .../browser/parts/editor/tabsTitleControl.ts | 2 +- .../browser/parts/editor/titleControl.ts | 40 ++++++++++--------- 4 files changed, 26 insertions(+), 28 deletions(-) diff --git a/src/vs/platform/actions/workbench/actionBarContributions.ts b/src/vs/platform/actions/workbench/actionBarContributions.ts index 906dc9496c5..725c6a4aab8 100644 --- a/src/vs/platform/actions/workbench/actionBarContributions.ts +++ b/src/vs/platform/actions/workbench/actionBarContributions.ts @@ -158,16 +158,10 @@ class EditorContributor extends BaseActionBarContributor { return { primary: 'editor/primary', secondary: 'editor/secondary' }; } protected _getResource(context: any): URI { - const {input, position, editor} = context; - if (typeof position !== 'number' || !editor) { - //todo@ben I get called two times with different - //but very similar looking context-objects in case - //an editor is created the first time - return; - } + const {input} = context; if (input instanceof EditorInput) { if (typeof input.getResource === 'function') { - const candidate = context.input.getResource(); + const candidate = input.getResource(); if (candidate instanceof URI) { return candidate; } diff --git a/src/vs/workbench/browser/parts/editor/noTabsTitleControl.ts b/src/vs/workbench/browser/parts/editor/noTabsTitleControl.ts index e95c354baba..499a30b1c88 100644 --- a/src/vs/workbench/browser/parts/editor/noTabsTitleControl.ts +++ b/src/vs/workbench/browser/parts/editor/noTabsTitleControl.ts @@ -186,7 +186,7 @@ export class NoTabsTitleControl extends TitleControl { } // Update Editor Actions Toolbar - const editorActions = this.getEditorActions(group); + const editorActions = this.getEditorActions({group, editor }); const primaryEditorActions = prepareActions(editorActions.primary); if (isActive && editor instanceof EditorInput && editor.supportsSplitEditor()) { primaryEditorActions.push(this.splitEditorAction); diff --git a/src/vs/workbench/browser/parts/editor/tabsTitleControl.ts b/src/vs/workbench/browser/parts/editor/tabsTitleControl.ts index 5e304542ca7..8dded89ab7b 100644 --- a/src/vs/workbench/browser/parts/editor/tabsTitleControl.ts +++ b/src/vs/workbench/browser/parts/editor/tabsTitleControl.ts @@ -521,7 +521,7 @@ export class TabsTitleControl extends TitleControl { // Actions: For active editor if (group.isActive(editor)) { - const editorActions = this.getEditorActions(group); + const editorActions = this.getEditorActions(identifier); if (editorActions.primary.length) { actions.push(new Separator(), ...prepareActions(editorActions.primary)); } diff --git a/src/vs/workbench/browser/parts/editor/titleControl.ts b/src/vs/workbench/browser/parts/editor/titleControl.ts index 1050cf3405e..68be8227519 100644 --- a/src/vs/workbench/browser/parts/editor/titleControl.ts +++ b/src/vs/workbench/browser/parts/editor/titleControl.ts @@ -246,33 +246,35 @@ export abstract class TitleControl { // Check Registry if (!actionItem) { - let actionBarRegistry = Registry.as(Extensions.Actionbar); + const actionBarRegistry = Registry.as(Extensions.Actionbar); actionItem = actionBarRegistry.getActionItemForContext(Scope.EDITOR, { input: editor && editor.input, editor, position }, action); } return actionItem; } - protected getEditorActions(group: IEditorGroup): IToolbarActions { - const position = this.stacks.positionOfGroup(group); - const isActive = this.stacks.isActive(group); + protected getEditorActions(identifier: IEditorIdentifier): IToolbarActions { const primary: IAction[] = []; const secondary: IAction[] = []; - const editor = this.editorService.getVisibleEditors()[position]; - if (isActive && editor instanceof BaseEditor) { - let editorActions = this.mapActionsToEditors[editor.getId()]; + const {group} = identifier; + const position = this.stacks.positionOfGroup(group); + + // Editor actions require the editor control to be there, so we retrieve it via service + const control = this.editorService.getVisibleEditors()[position]; + if (this.stacks.isActive(group) && control instanceof BaseEditor && control.input && typeof control.position === 'number') { + + // Editor Control Actions + let editorActions = this.mapActionsToEditors[control.getId()]; if (!editorActions) { - editorActions = this.getEditorActionsForContext(editor); - this.mapActionsToEditors[editor.getId()] = editorActions; + editorActions = this.getEditorActionsForContext(control); + this.mapActionsToEditors[control.getId()] = editorActions; } - primary.push(...editorActions.primary); secondary.push(...editorActions.secondary); - // Handle Editor Input Actions - let editorInputActions = this.getEditorActionsForContext({ input: editor.input, editor, position: editor.position }); - + // Editor Input Actions + const editorInputActions = this.getEditorActionsForContext({ input: control.input, editor: control, position: control.position }); primary.push(...editorInputActions.primary); secondary.push(...editorInputActions.secondary); } @@ -283,8 +285,8 @@ export abstract class TitleControl { private getEditorActionsForContext(context: BaseEditor): IToolbarActions; private getEditorActionsForContext(context: IEditorInputActionContext): IToolbarActions; private getEditorActionsForContext(context: any): IToolbarActions { - let primaryActions: IAction[] = []; - let secondaryActions: IAction[] = []; + const primaryActions: IAction[] = []; + const secondaryActions: IAction[] = []; // From Editor if (context instanceof BaseEditor) { @@ -293,9 +295,11 @@ export abstract class TitleControl { } // From Contributions - let actionBarRegistry = Registry.as(Extensions.Actionbar); - primaryActions.push(...actionBarRegistry.getActionBarActionsForContext(Scope.EDITOR, context)); - secondaryActions.push(...actionBarRegistry.getSecondaryActionBarActionsForContext(Scope.EDITOR, context)); + else { + const actionBarRegistry = Registry.as(Extensions.Actionbar); + primaryActions.push(...actionBarRegistry.getActionBarActionsForContext(Scope.EDITOR, context)); + secondaryActions.push(...actionBarRegistry.getSecondaryActionBarActionsForContext(Scope.EDITOR, context)); + } return { primary: primaryActions, From 5f5b1cae1082232eeaaff6bd5e35a2e139535bce Mon Sep 17 00:00:00 2001 From: isidor Date: Mon, 20 Jun 2016 14:17:52 +0200 Subject: [PATCH 204/217] debug: add publisher as prefix to custom debug telemetry --- src/vs/workbench/parts/debug/electron-browser/debugService.ts | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/vs/workbench/parts/debug/electron-browser/debugService.ts b/src/vs/workbench/parts/debug/electron-browser/debugService.ts index 4d1a0458c8d..ce69c5164c9 100644 --- a/src/vs/workbench/parts/debug/electron-browser/debugService.ts +++ b/src/vs/workbench/parts/debug/electron-browser/debugService.ts @@ -575,6 +575,7 @@ export class DebugService implements debug.IDebugService { return telemetryInfo; }).then(data => { const { aiKey, type } = this.configurationManager.adapter; + const publisher = this.configurationManager.adapter.extensionDescription.publisher; this.customTelemetryService = null; if (aiKey) { @@ -583,7 +584,7 @@ export class DebugService implements debug.IDebugService { { serverName: 'Debug Telemetry', timeout: 1000 * 60 * 5, - args: [type, JSON.stringify(data), aiKey], + args: [`${ publisher }.${ type }`, JSON.stringify(data), aiKey], env: { ATOM_SHELL_INTERNAL_RUN_AS_NODE: 1, PIPE_LOGGING: 'true', From f81582e1925161700751638e26e85bd6e0048745 Mon Sep 17 00:00:00 2001 From: Alex Dima Date: Mon, 20 Jun 2016 14:21:33 +0200 Subject: [PATCH 205/217] Fixes #7880: Remove conflicting keybindings --- .../contrib/carretOperations/common/carretOperations.ts | 9 +++------ 1 file changed, 3 insertions(+), 6 deletions(-) diff --git a/src/vs/editor/contrib/carretOperations/common/carretOperations.ts b/src/vs/editor/contrib/carretOperations/common/carretOperations.ts index aa21fcca2cd..0dc6eca25d8 100644 --- a/src/vs/editor/contrib/carretOperations/common/carretOperations.ts +++ b/src/vs/editor/contrib/carretOperations/common/carretOperations.ts @@ -5,7 +5,6 @@ 'use strict'; import * as nls from 'vs/nls'; -import {KeyCode, KeyMod} from 'vs/base/common/keyCodes'; import {TPromise} from 'vs/base/common/winjs.base'; import {EditorAction} from 'vs/editor/common/editorAction'; import {ICommand, ICommonCodeEditor, IEditorActionDescriptorData} from 'vs/editor/common/editorCommon'; @@ -54,12 +53,10 @@ class MoveCarretRightAction extends MoveCarretAction { CommonEditorRegistry.registerEditorAction(new EditorActionDescriptor(MoveCarretLeftAction, MoveCarretLeftAction.ID, nls.localize('carret.moveLeft', "Move Carret Left"), { context: ContextKey.EditorTextFocus, - primary: KeyMod.Alt | KeyCode.LeftArrow, - linux: { primary: KeyMod.Alt | KeyCode.LeftArrow } + primary: 0 }, 'Move Carret Left')); CommonEditorRegistry.registerEditorAction(new EditorActionDescriptor(MoveCarretRightAction, MoveCarretRightAction.ID, nls.localize('carret.moveRight', "Move Carret Right"), { context: ContextKey.EditorTextFocus, - primary: KeyMod.Alt | KeyCode.RightArrow, - linux: { primary: KeyMod.Alt | KeyCode.LeftArrow } -}, 'Move Carret Right')); \ No newline at end of file + primary: 0 +}, 'Move Carret Right')); From eaa522ccb1811f534c63f6d285a01a5f83199522 Mon Sep 17 00:00:00 2001 From: Benjamin Pasero Date: Mon, 20 Jun 2016 14:27:00 +0200 Subject: [PATCH 206/217] move conflict resolution into the message (this is a workaround because we do not show primary actions when tabs are enabled) --- .../files/browser/fileActions.contribution.ts | 27 +------- .../parts/files/browser/saveErrorHandler.ts | 62 +++++++++++-------- 2 files changed, 38 insertions(+), 51 deletions(-) diff --git a/src/vs/workbench/parts/files/browser/fileActions.contribution.ts b/src/vs/workbench/parts/files/browser/fileActions.contribution.ts index 2bd671ec5cf..754b65ef604 100644 --- a/src/vs/workbench/parts/files/browser/fileActions.contribution.ts +++ b/src/vs/workbench/parts/files/browser/fileActions.contribution.ts @@ -9,9 +9,7 @@ import {Registry} from 'vs/platform/platform'; import {Action, IAction} from 'vs/base/common/actions'; import {ActionItem, BaseActionItem, Separator} from 'vs/base/browser/ui/actionbar/actionbar'; import {Scope, IActionBarRegistry, Extensions as ActionBarExtensions, ActionBarContributor} from 'vs/workbench/browser/actionBarRegistry'; -import {IEditorInputActionContext, IEditorInputAction, EditorInputActionContributor} from 'vs/workbench/browser/parts/editor/baseEditor'; import {FocusOpenEditorsView, FocusFilesExplorer, GlobalCompareResourcesAction, GlobalNewFileAction, GlobalNewFolderAction, RevertFileAction, SaveFilesAction, SaveAllAction, SaveFileAction, keybindingForAction, MoveFileToTrashAction, TriggerRenameFileAction, PasteFileAction, CopyFileAction, SelectResourceForCompareAction, CompareResourcesAction, NewFolderAction, NewFileAction, OpenToSideAction, ShowActiveFileInExplorer, CollapseExplorerView, RefreshExplorerView} from 'vs/workbench/parts/files/browser/fileActions'; -import {RevertLocalChangesAction, AcceptLocalChangesAction, ConflictResolutionDiffEditorInput} from 'vs/workbench/parts/files/browser/saveErrorHandler'; import {SyncActionDescriptor} from 'vs/platform/actions/common/actions'; import {IWorkbenchActionRegistry, Extensions as ActionExtensions} from 'vs/workbench/common/actionRegistry'; import {IInstantiationService} from 'vs/platform/instantiation/common/instantiation'; @@ -133,35 +131,14 @@ class FilesViewerActionContributor extends ActionBarContributor { } } -class ConflictResolutionActionContributor extends EditorInputActionContributor { - - constructor( @IInstantiationService private instantiationService: IInstantiationService) { - super(); - } - - public hasActionsForEditorInput(context: IEditorInputActionContext): boolean { - return (context.input instanceof ConflictResolutionDiffEditorInput); - } - - public getActionsForEditorInput(context: IEditorInputActionContext): IEditorInputAction[] { - return [ - this.instantiationService.createInstance(AcceptLocalChangesAction), - this.instantiationService.createInstance(RevertLocalChangesAction) - ]; - } -} - // Contribute to Viewers that show Files -let actionBarRegistry = Registry.as(ActionBarExtensions.Actionbar); +const actionBarRegistry = Registry.as(ActionBarExtensions.Actionbar); actionBarRegistry.registerActionBarContributor(Scope.VIEWER, FilesViewerActionContributor); -// Contribute to Conflict Editor Inputs -actionBarRegistry.registerActionBarContributor(Scope.EDITOR, ConflictResolutionActionContributor); - // Contribute Global Actions const category = nls.localize('filesCategory', "Files"); -let registry = Registry.as(ActionExtensions.WorkbenchActions); +const registry = Registry.as(ActionExtensions.WorkbenchActions); registry.registerWorkbenchAction(new SyncActionDescriptor(SaveFileAction, SaveFileAction.ID, SaveFileAction.LABEL, { primary: KeyMod.CtrlCmd | KeyCode.KEY_S }), 'Files: Save', category); registry.registerWorkbenchAction(new SyncActionDescriptor(SaveAllAction, SaveAllAction.ID, SaveAllAction.LABEL), 'Files: Save All', category); registry.registerWorkbenchAction(new SyncActionDescriptor(SaveFilesAction, SaveFilesAction.ID, null /* only for programmatic trigger */), null); diff --git a/src/vs/workbench/parts/files/browser/saveErrorHandler.ts b/src/vs/workbench/parts/files/browser/saveErrorHandler.ts index 0ba2f2adba3..bf973e4cc43 100644 --- a/src/vs/workbench/parts/files/browser/saveErrorHandler.ts +++ b/src/vs/workbench/parts/files/browser/saveErrorHandler.ts @@ -12,10 +12,10 @@ import {Action} from 'vs/base/common/actions'; import URI from 'vs/base/common/uri'; import {EditorModel} from 'vs/workbench/common/editor'; import {guessMimeTypes} from 'vs/base/common/mime'; -import {EditorInputAction} from 'vs/workbench/browser/parts/editor/baseEditor'; import {ResourceEditorInput} from 'vs/workbench/common/editor/resourceEditorInput'; import {DiffEditorInput} from 'vs/workbench/common/editor/diffEditorInput'; import {DiffEditorModel} from 'vs/workbench/common/editor/diffEditorModel'; +import {Position} from 'vs/platform/editor/common/editor'; import {FileEditorInput} from 'vs/workbench/parts/files/browser/editors/fileEditorInput'; import {SaveFileAsAction, RevertFileAction, SaveFileAction} from 'vs/workbench/parts/files/browser/fileActions'; import {IFileService, IFileOperationResult, FileOperationResult} from 'vs/platform/files/common/files'; @@ -67,8 +67,8 @@ export class SaveErrorHandler implements ISaveErrorHandler { // Any other save error else { - let isReadonly = (error).fileOperationResult === FileOperationResult.FILE_READ_ONLY; - let actions: Action[] = []; + const isReadonly = (error).fileOperationResult === FileOperationResult.FILE_READ_ONLY; + const actions: Action[] = []; // Cancel actions.push(CancelAction); @@ -84,7 +84,7 @@ export class SaveErrorHandler implements ISaveErrorHandler { })); } else { actions.push(new Action('workbench.files.action.retry', nls.localize('retry', "Retry"), null, true, () => { - let saveFileAction = this.instantiationService.createInstance(SaveFileAction, SaveFileAction.ID, SaveFileAction.LABEL); + const saveFileAction = this.instantiationService.createInstance(SaveFileAction, SaveFileAction.ID, SaveFileAction.LABEL); saveFileAction.setResource(resource); return saveFileAction.run().then(() => { saveFileAction.dispose(); return true; }); @@ -93,7 +93,7 @@ export class SaveErrorHandler implements ISaveErrorHandler { // Discard actions.push(new Action('workbench.files.action.discard', nls.localize('discard', "Discard"), null, true, () => { - let revertFileAction = this.instantiationService.createInstance(RevertFileAction, RevertFileAction.ID, RevertFileAction.LABEL); + const revertFileAction = this.instantiationService.createInstance(RevertFileAction, RevertFileAction.ID, RevertFileAction.LABEL); revertFileAction.setResource(resource); return revertFileAction.run().then(() => { revertFileAction.dispose(); return true; }); @@ -101,7 +101,7 @@ export class SaveErrorHandler implements ISaveErrorHandler { // Save As actions.push(new Action('workbench.files.action.saveAs', SaveFileAsAction.LABEL, null, true, () => { - let saveAsAction = this.instantiationService.createInstance(SaveFileAsAction, SaveFileAsAction.ID, SaveFileAsAction.LABEL); + const saveAsAction = this.instantiationService.createInstance(SaveFileAsAction, SaveFileAsAction.ID, SaveFileAsAction.LABEL); saveAsAction.setResource(resource); return saveAsAction.run().then(() => { saveAsAction.dispose(); return true; }); @@ -188,7 +188,7 @@ export class FileOnDiskEditorInput extends ResourceEditorInput { return this.fileService.resolveContent(this.fileResource).then(content => { this.lastModified = content.mtime; - let codeEditorModel = this.modelService.getModel(this.resource); + const codeEditorModel = this.modelService.getModel(this.resource); if (!codeEditorModel) { this.modelService.createModel(content.value, this.modeService.getOrCreateMode(this.mime), this.resource); this.createdEditorModel = true; @@ -237,18 +237,24 @@ class ResolveSaveConflictMessage implements IMessageWithAction { this.actions = [ new Action('workbench.files.action.resolveConflict', nls.localize('compareChanges', "Compare"), null, true, () => { if (!this.model.isDisposed()) { - let mime = guessMimeTypes(resource.fsPath).join(', '); - let originalInput = this.instantiationService.createInstance(FileOnDiskEditorInput, resource, mime, paths.basename(resource.fsPath), resource.fsPath); - let modifiedInput = this.instantiationService.createInstance(FileEditorInput, resource, mime, void 0); - let conflictInput = this.instantiationService.createInstance(ConflictResolutionDiffEditorInput, this.model, nls.localize('saveConflictDiffLabel', "{0} - on disk ↔ in {1}", modifiedInput.getName(), this.contextService.getConfiguration().env.appName), nls.localize('resolveSaveConflict', "{0} - Resolve save conflict", modifiedInput.getDescription()), originalInput, modifiedInput); + const mime = guessMimeTypes(resource.fsPath).join(', '); + const originalInput = this.instantiationService.createInstance(FileOnDiskEditorInput, resource, mime, paths.basename(resource.fsPath), resource.fsPath); + const modifiedInput = this.instantiationService.createInstance(FileEditorInput, resource, mime, void 0); + const conflictInput = this.instantiationService.createInstance(ConflictResolutionDiffEditorInput, this.model, nls.localize('saveConflictDiffLabel', "{0} - on disk ↔ in {1}", modifiedInput.getName(), this.contextService.getConfiguration().env.appName), nls.localize('resolveSaveConflict', "{0} - Resolve save conflict", modifiedInput.getDescription()), originalInput, modifiedInput); - return this.editorService.openEditor(conflictInput).then(() => { + return this.editorService.openEditor(conflictInput).then(editor => { // We have to bring the model into conflict resolution mode to prevent subsequent save erros when the user makes edits this.model.setConflictResolutionMode(); // Inform user - this.messageService.show(Severity.Info, nls.localize('userGuide', "Use the actions in the editor tool bar to either **undo** your changes or **overwrite** the content on disk with your changes")); + this.messageService.show(Severity.Info, { + message: nls.localize('userGuide', "Please either select **Revert** to discard your changes or **Overwrite** to replace the content on disk with your changes"), + actions: [ + this.instantiationService.createInstance(AcceptLocalChangesAction, conflictInput, editor.position), + this.instantiationService.createInstance(RevertLocalChangesAction, conflictInput, editor.position) + ] + }); }); } @@ -259,31 +265,33 @@ class ResolveSaveConflictMessage implements IMessageWithAction { } // Accept changes to resolve a conflicting edit -export class AcceptLocalChangesAction extends EditorInputAction { +export class AcceptLocalChangesAction extends Action { private messagesToHide: { (): void; }[]; constructor( + private input: ConflictResolutionDiffEditorInput, + private position: Position, @IMessageService private messageService: IMessageService, @IInstantiationService private instantiationService: IInstantiationService, @IWorkbenchEditorService private editorService: IWorkbenchEditorService ) { - super('workbench.files.action.acceptLocalChanges', nls.localize('acceptLocalChanges', "Use local changes and overwrite disk contents"), 'conflict-editor-action accept-changes'); + super('workbench.files.action.acceptLocalChanges', nls.localize('acceptLocalChanges', "Overwrite"), 'conflict-editor-action accept-changes'); this.messagesToHide = []; } public run(): TPromise { - let conflictInput = this.input; - let model = conflictInput.getModel(); - let localModelValue = model.getValue(); + const conflictInput = this.input; + const model = conflictInput.getModel(); + const localModelValue = model.getValue(); // 1.) Get the diff editor model from cache (resolve(false)) to have access to the mtime of the file we currently show to the left return conflictInput.resolve(false).then((diffModel: DiffEditorModel) => { - let knownLastModified = (conflictInput.originalInput).getLastModified(); + const knownLastModified = (conflictInput.originalInput).getLastModified(); // 2.) Revert the model to get the latest copy from disk and to have access to the mtime of the file now return model.revert().then(() => { - let diskLastModified = model.getLastModifiedTime(); + const diskLastModified = model.getLastModifiedTime(); // 3. a) If we know that the file on the left hand side was not modified meanwhile, restore the user value and trigger a save if (diskLastModified <= knownLastModified) { @@ -300,7 +308,7 @@ export class AcceptLocalChangesAction extends EditorInputAction { } // Reopen file input - let input = this.instantiationService.createInstance(FileEditorInput, model.getResource(), guessMimeTypes(model.getResource().fsPath).join(', '), void 0); + const input = this.instantiationService.createInstance(FileEditorInput, model.getResource(), guessMimeTypes(model.getResource().fsPath).join(', '), void 0); return this.editorService.openEditor(input, null, this.position).then(() => { // Dispose conflict input @@ -329,24 +337,26 @@ export class AcceptLocalChangesAction extends EditorInputAction { } // Revert changes to resolve a conflicting edit -export class RevertLocalChangesAction extends EditorInputAction { +export class RevertLocalChangesAction extends Action { constructor( + private input: ConflictResolutionDiffEditorInput, + private position: Position, @IInstantiationService private instantiationService: IInstantiationService, @IWorkbenchEditorService private editorService: IWorkbenchEditorService ) { - super('workbench.action.files.revert', nls.localize('revertLocalChanges', "Discard local changes and revert to content on disk"), 'conflict-editor-action revert-changes'); + super('workbench.action.files.revert', nls.localize('revertLocalChanges', "Revert"), 'conflict-editor-action revert-changes'); } public run(): TPromise { - let conflictInput = this.input; - let model = conflictInput.getModel(); + const conflictInput = this.input; + const model = conflictInput.getModel(); // Revert on model return model.revert().then(() => { // Reopen file input - let input = this.instantiationService.createInstance(FileEditorInput, model.getResource(), guessMimeTypes(model.getResource().fsPath).join(', '), void 0); + const input = this.instantiationService.createInstance(FileEditorInput, model.getResource(), guessMimeTypes(model.getResource().fsPath).join(', '), void 0); return this.editorService.openEditor(input, null, this.position).then(() => { // Dispose conflict input From d0dc1bdd66cc07415306019810e1914ee39cd408 Mon Sep 17 00:00:00 2001 From: Erich Gamma Date: Mon, 20 Jun 2016 15:06:04 +0200 Subject: [PATCH 207/217] fix for #7882 --- .../parts/emmet/node/emmetActions.ts | 28 +++++++++---------- 1 file changed, 13 insertions(+), 15 deletions(-) diff --git a/src/vs/workbench/parts/emmet/node/emmetActions.ts b/src/vs/workbench/parts/emmet/node/emmetActions.ts index 0b066b726a5..358ae220ebd 100644 --- a/src/vs/workbench/parts/emmet/node/emmetActions.ts +++ b/src/vs/workbench/parts/emmet/node/emmetActions.ts @@ -15,13 +15,11 @@ import nls = require('vs/nls'); export abstract class EmmetEditorAction extends EditorAction { - protected static editorAccessor: EditorAccessor; + protected editorAccessor: EditorAccessor; constructor(descriptor: IEditorActionDescriptorData, editor: ICommonCodeEditor) { super(descriptor, editor, Behaviour.TextFocus); - if (!EmmetEditorAction.editorAccessor) { - EmmetEditorAction.editorAccessor = new EditorAccessor(editor); - } + this.editorAccessor = new EditorAccessor(editor); } abstract runEmmetAction(_module: any); @@ -30,15 +28,15 @@ export abstract class EmmetEditorAction extends EditorAction { return new TPromise((c, e) => { require(['emmet'], (_module) => { try { - if (!EmmetEditorAction.editorAccessor.isEmmetEnabledMode()) { - EmmetEditorAction.editorAccessor.noExpansionOccurred(); + if (!this.editorAccessor.isEmmetEnabledMode()) { + this.editorAccessor.noExpansionOccurred(); return; } this.runEmmetAction(_module); } catch (err) { // } finally { - EmmetEditorAction.editorAccessor.flushCache(); + this.editorAccessor.flushCache(); } }, e); }); @@ -53,8 +51,8 @@ export class ExpandAbbreviationAction extends EmmetEditorAction { } public runEmmetAction(_module) { - if (!_module.run('expand_abbreviation', EmmetEditorAction.editorAccessor)) { - EmmetEditorAction.editorAccessor.noExpansionOccurred(); + if (!_module.run('expand_abbreviation', this.editorAccessor)) { + this.editorAccessor.noExpansionOccurred(); } } } @@ -67,8 +65,8 @@ export class RemoveTagAction extends EmmetEditorAction { } public runEmmetAction(_module) { - if (!_module.run('remove_tag', EmmetEditorAction.editorAccessor)) { - EmmetEditorAction.editorAccessor.noExpansionOccurred(); + if (!_module.run('remove_tag', this.editorAccessor)) { + this.editorAccessor.noExpansionOccurred(); } } } @@ -91,8 +89,8 @@ export class UpdateTagAction extends EmmetEditorAction { } private wrapAbbreviation(_module: any, tag) { - if (!_module.run('update_tag', EmmetEditorAction.editorAccessor, tag)) { - EmmetEditorAction.editorAccessor.noExpansionOccurred(); + if (!_module.run('update_tag', this.editorAccessor, tag)) { + this.editorAccessor.noExpansionOccurred(); } } } @@ -115,8 +113,8 @@ export class WrapWithAbbreviationAction extends EmmetEditorAction { } private wrapAbbreviation(_module: any, abbreviation) { - if (!_module.run('wrap_with_abbreviation', EmmetEditorAction.editorAccessor, abbreviation)) { - EmmetEditorAction.editorAccessor.noExpansionOccurred(); + if (!_module.run('wrap_with_abbreviation', this.editorAccessor, abbreviation)) { + this.editorAccessor.noExpansionOccurred(); } } } \ No newline at end of file From da501b031fbadb68d497821237657ad4aa978e48 Mon Sep 17 00:00:00 2001 From: Andre Weinand Date: Mon, 20 Jun 2016 15:20:30 +0200 Subject: [PATCH 208/217] update node-debug (add variable value support) --- extensions/node-debug/node-debug.azure.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/extensions/node-debug/node-debug.azure.json b/extensions/node-debug/node-debug.azure.json index 01d228a4a17..3be7e95786b 100644 --- a/extensions/node-debug/node-debug.azure.json +++ b/extensions/node-debug/node-debug.azure.json @@ -1,6 +1,6 @@ { "account": "monacobuild", "container": "debuggers", - "zip": "f9803b8/node-debug.zip", + "zip": "babb057/node-debug.zip", "output": "" } From d2f9b29ca3b39bf7a5cac40a54c7a606fc48c216 Mon Sep 17 00:00:00 2001 From: Erich Gamma Date: Mon, 20 Jun 2016 15:51:58 +0200 Subject: [PATCH 209/217] Update TypeScript dependency to ^1.8.10 (1.8.0 produces errors). --- package.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/package.json b/package.json index 9dd9d64c2d1..bf7459e2962 100644 --- a/package.json +++ b/package.json @@ -83,7 +83,7 @@ "sinon": "^1.17.2", "source-map": "^0.4.4", "tslint": "^3.3.0", - "typescript": "^1.8.0", + "typescript": "^1.8.10", "uglify-js": "2.4.8", "underscore": "^1.8.2", "vinyl": "^0.4.5", From c9a739067cebb3e31fc0098a6a564b0cb6a8f575 Mon Sep 17 00:00:00 2001 From: Denis Malinochkin Date: Mon, 20 Jun 2016 17:10:56 +0300 Subject: [PATCH 210/217] Added support Emmet for Sass and Stylus (#7887) --- src/vs/workbench/parts/emmet/node/editorAccessor.ts | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/src/vs/workbench/parts/emmet/node/editorAccessor.ts b/src/vs/workbench/parts/emmet/node/editorAccessor.ts index 81a3a40c16a..1e2abb9d378 100644 --- a/src/vs/workbench/parts/emmet/node/editorAccessor.ts +++ b/src/vs/workbench/parts/emmet/node/editorAccessor.ts @@ -19,7 +19,7 @@ export class EditorAccessor implements emmet.Editor { lineStarts: number[] = null; - emmetSupportedModes = ['html', 'razor', 'css', 'less', 'scss', 'xml', 'xsl', 'jade', 'handlebars', 'ejs', 'hbs', 'jsx', 'tsx', 'erb', 'php', 'twig']; + emmetSupportedModes = ['html', 'razor', 'css', 'less', 'sass', 'scss', 'stylus', 'xml', 'xsl', 'jade', 'handlebars', 'ejs', 'hbs', 'jsx', 'tsx', 'erb', 'php', 'twig']; constructor(editor: ICommonCodeEditor) { this.editor = editor; @@ -121,8 +121,8 @@ export class EditorAccessor implements emmet.Editor { if (/\b(typescriptreact|javascriptreact)\b/.test(syntax)) { // treat like tsx like jsx return 'jsx'; } - if (syntax === 'stylus') { // map stylus to css - return 'css'; + if (syntax === 'sass-indented') { // map sass-indented to sass + return 'sass'; } return syntax; } From eb41d47b260e75944e094ad481e9634431e04327 Mon Sep 17 00:00:00 2001 From: Benjamin Pasero Date: Mon, 20 Jun 2016 17:36:41 +0200 Subject: [PATCH 211/217] delete markdown language from vscode --- build/gulpfile.vscode.js | 2 - src/vs/languages/buildfile.js | 3 - src/vs/languages/languages.main.ts | 1 - .../markdown/common/markdown.contribution.ts | 19 -- src/vs/languages/markdown/common/markdown.ts | 239 ------------------ .../markdown/test/common/markdown.test.ts | 116 --------- 6 files changed, 380 deletions(-) delete mode 100644 src/vs/languages/markdown/common/markdown.contribution.ts delete mode 100644 src/vs/languages/markdown/common/markdown.ts delete mode 100644 src/vs/languages/markdown/test/common/markdown.test.ts diff --git a/build/gulpfile.vscode.js b/build/gulpfile.vscode.js index 4bdfd44987c..67fc67e9fa1 100644 --- a/build/gulpfile.vscode.js +++ b/build/gulpfile.vscode.js @@ -53,7 +53,6 @@ var vscodeResources = [ 'out-build/vs/base/worker/workerMainCompatibility.html', 'out-build/vs/base/worker/workerMain.{js,js.map}', 'out-build/vs/base/browser/ui/octiconLabel/octicons/**', - 'out-build/vs/languages/markdown/common/*.css', 'out-build/vs/workbench/browser/media/*-theme.css', 'out-build/vs/workbench/electron-browser/index.html', 'out-build/vs/workbench/parts/debug/**/*.json', @@ -61,7 +60,6 @@ var vscodeResources = [ 'out-build/vs/workbench/parts/git/**/*.html', 'out-build/vs/workbench/parts/git/**/*.sh', 'out-build/vs/workbench/parts/html/browser/webview.html', - 'out-build/vs/workbench/parts/markdown/**/*.md', 'out-build/vs/workbench/parts/tasks/**/*.json', 'out-build/vs/workbench/parts/terminal/electron-browser/terminalProcess.js', 'out-build/vs/workbench/services/files/**/*.exe', diff --git a/src/vs/languages/buildfile.js b/src/vs/languages/buildfile.js index 8335e4d4fcb..965a3b68c9f 100644 --- a/src/vs/languages/buildfile.js +++ b/src/vs/languages/buildfile.js @@ -65,9 +65,6 @@ exports.collectModules = function(args) { .combine(worker) .define('vs/languages/html/common/htmlWorker', ['vs/languages/lib/common/beautify-html']); - // ---- markdown ------------------------------- - common.define('vs/languages/markdown/common/markdown', ['vs/languages/html/common/html']); - // ---- php ----------------------------------- common.define('vs/languages/php/common/php'); diff --git a/src/vs/languages/languages.main.ts b/src/vs/languages/languages.main.ts index 6b2325b0007..be15b628f86 100644 --- a/src/vs/languages/languages.main.ts +++ b/src/vs/languages/languages.main.ts @@ -8,5 +8,4 @@ import 'vs/languages/handlebars/common/handlebars.contribution'; import 'vs/languages/html/common/html.contribution'; -import 'vs/languages/markdown/common/markdown.contribution'; import 'vs/languages/razor/common/razor.contribution'; diff --git a/src/vs/languages/markdown/common/markdown.contribution.ts b/src/vs/languages/markdown/common/markdown.contribution.ts deleted file mode 100644 index a984f358078..00000000000 --- a/src/vs/languages/markdown/common/markdown.contribution.ts +++ /dev/null @@ -1,19 +0,0 @@ -/*--------------------------------------------------------------------------------------------- - * Copyright (c) Microsoft Corporation. All rights reserved. - * Licensed under the MIT License. See License.txt in the project root for license information. - *--------------------------------------------------------------------------------------------*/ -'use strict'; - -import {ModesRegistry} from 'vs/editor/common/modes/modesRegistry'; - -const register = false; -if (register) { - ModesRegistry.registerCompatMode({ - id: 'markdown', - extensions: ['.md', '.markdown', '.mdown', '.mkdn', '.mkd', '.mdwn', '.mdtxt', '.mdtext'], - aliases: ['Markdown', 'markdown'], - mimetypes: ['text/x-web-markdown'], - moduleId: 'vs/languages/markdown/common/markdown', - ctorName: 'MarkdownMode' - }); -} \ No newline at end of file diff --git a/src/vs/languages/markdown/common/markdown.ts b/src/vs/languages/markdown/common/markdown.ts deleted file mode 100644 index ea7bbf1d308..00000000000 --- a/src/vs/languages/markdown/common/markdown.ts +++ /dev/null @@ -1,239 +0,0 @@ -/*--------------------------------------------------------------------------------------------- - * Copyright (c) Microsoft Corporation. All rights reserved. - * Licensed under the MIT License. See License.txt in the project root for license information. - *--------------------------------------------------------------------------------------------*/ -'use strict'; - -import Types = require('vs/editor/common/modes/monarch/monarchTypes'); -import Compile = require('vs/editor/common/modes/monarch/monarchCompile'); -import Modes = require('vs/editor/common/modes'); -import {htmlTokenTypes} from 'vs/languages/html/common/html'; -import {IModeService} from 'vs/editor/common/services/modeService'; -import {IInstantiationService} from 'vs/platform/instantiation/common/instantiation'; -import {IThreadService} from 'vs/platform/thread/common/thread'; -import {IConfigurationService} from 'vs/platform/configuration/common/configuration'; -import {IEditorWorkerService} from 'vs/editor/common/services/editorWorkerService'; -import {AbstractMode} from 'vs/editor/common/modes/abstractMode'; -import {createTokenizationSupport} from 'vs/editor/common/modes/monarch/monarchLexer'; -import {LanguageConfigurationRegistry, LanguageConfiguration} from 'vs/editor/common/modes/languageConfigurationRegistry'; -import {wireCancellationToken} from 'vs/base/common/async'; - -export const TOKEN_HEADER_LEAD = 'entity.name.tag'; -export const TOKEN_HEADER = 'entity.name.tag'; -export const TOKEN_EXT_HEADER = 'entity.other.attribute-name'; -export const TOKEN_SEPARATOR = 'meta.separator'; -export const TOKEN_QUOTE = 'comment'; -export const TOKEN_LIST = 'keyword'; -export const TOKEN_BLOCK = 'string'; -export const TOKEN_BLOCK_CODE = 'variable.source'; - -export const language = - { - defaultToken: '', - tokenPostfix: '.md', - - // escape codes - control: /[\\`*_\[\]{}()#+\-\.!]/, - noncontrol: /[^\\`*_\[\]{}()#+\-\.!]/, - escapes: /\\(?:@control)/, - - // escape codes for javascript/CSS strings - jsescapes: /\\(?:[btnfr\\"']|[0-7][0-7]?|[0-3][0-7]{2})/, - - // non matched elements - empty: [ - 'area', 'base', 'basefont', 'br', 'col', 'frame', - 'hr', 'img', 'input', 'isindex', 'link', 'meta', 'param' - ], - - tokenizer: { - root: [ - - // headers (with #) - [/^(\s{0,3})(#+)((?:[^\\#]|@escapes)+)((?:#+)?)/, ['white', TOKEN_HEADER_LEAD, TOKEN_HEADER, TOKEN_HEADER]], - - // headers (with =) - [/^\s*(=+|\-+)\s*$/, TOKEN_EXT_HEADER], - - // headers (with ***) - [/^\s*((\*[ ]?)+)\s*$/, TOKEN_SEPARATOR], - - // quote - [/^\s*>+/, TOKEN_QUOTE], - - // list (starting with * or number) - [/^\s*([\*\-+:]|\d+\.)\s/, TOKEN_LIST], - - // code block (4 spaces indent) - [/^(\t|[ ]{4})[^ ].*$/, TOKEN_BLOCK], - - // code block (3 tilde) - [/^\s*~{3}\s*((?:\w|[\/\-#])+)?\s*$/, { token: TOKEN_BLOCK, next: '@codeblock' }], - - // github style code blocks (with backticks and language) - [/^\s*```\s*((?:\w|[\/\-#])+)\s*$/, { token: TOKEN_BLOCK, next: '@codeblockgh', nextEmbedded: '$1' }], - - // github style code blocks (with backticks but no language) - [/^\s*`{3}\s*$/, { token: TOKEN_BLOCK, next: '@codeblock' }], - - // markup within lines - { include: '@linecontent' }, - ], - - codeblock: [ - [/^\s*~{3}\s*$/, { token: TOKEN_BLOCK, next: '@pop' }], - [/^\s*`{3}\s*$/, { token: TOKEN_BLOCK, next: '@pop' }], - [/.*$/, TOKEN_BLOCK_CODE], - ], - - // github style code blocks - codeblockgh: [ - [/```\s*$/, { token: '@rematch', switchTo: '@codeblockghend', nextEmbedded: '@pop' }], - [/[^`]*$/, TOKEN_BLOCK_CODE], - ], - - codeblockghend: [ - [/\s*```/, { token: TOKEN_BLOCK_CODE, next: '@pop' }], - [/./, '@rematch', '@pop'], - ], - - linecontent: [ - - // escapes - [/&\w+;/, 'string.escape'], - [/@escapes/, 'escape'], - - // various markup - [/\b__([^\\_]|@escapes|_(?!_))+__\b/, 'strong'], - [/\*\*([^\\*]|@escapes|\*(?!\*))+\*\*/, 'strong'], - [/\b_[^_]+_\b/, 'emphasis'], - [/\*([^\\*]|@escapes)+\*/, 'emphasis'], - [/`([^\\`]|@escapes)+`/, 'variable'], - - // links - [/\{[^}]+\}/, 'string.target'], - [/(!?\[)((?:[^\]\\]|@escapes)*)(\]\([^\)]+\))/, ['string.link', '', 'string.link']], - [/(!?\[)((?:[^\]\\]|@escapes)*)(\])/, 'string.link'], - - // or html - { include: 'html' }, - ], - - // Note: it is tempting to rather switch to the real HTML mode instead of building our own here - // but currently there is a limitation in Monarch that prevents us from doing it: The opening - // '<' would start the HTML mode, however there is no way to jump 1 character back to let the - // HTML mode also tokenize the opening angle bracket. Thus, even though we could jump to HTML, - // we cannot correctly tokenize it in that mode yet. - html: [ - // html tags - [/<(\w+)\/>/, htmlTokenTypes.getTag('$1')], - [/<(\w+)/, { - cases: { - '@empty': { token: htmlTokenTypes.getTag('$1'), next: '@tag.$1' }, - '@default': { token: htmlTokenTypes.getTag('$1'), bracket: '@open', next: '@tag.$1' } - } - }], - [/<\/(\w+)\s*>/, { token: htmlTokenTypes.getTag('$1'), bracket: '@close' }], - - [//, 'comment', '@pop'], - [/',] - }, - brackets: [['{', '}'], ['[', ']'], ['(', ')'], ['<', '>']], - autoClosingPairs: [] - }; - - public tokenizationSupport: Modes.ITokenizationSupport; - - constructor( - descriptor: Modes.IModeDescriptor, - @IInstantiationService instantiationService: IInstantiationService, - @IThreadService threadService: IThreadService, - @IModeService modeService: IModeService, - @IEditorWorkerService editorWorkerService: IEditorWorkerService, - @IConfigurationService configurationService: IConfigurationService - ) { - super(descriptor.id); - let lexer = Compile.compile(descriptor.id, language); - - this.tokenizationSupport = createTokenizationSupport(modeService, this, lexer); - - LanguageConfigurationRegistry.register(this.getId(), MarkdownMode.LANG_CONFIG); - - Modes.SuggestRegistry.register(this.getId(), { - triggerCharacters: [], - shouldAutotriggerSuggest: false, - provideCompletionItems: (model, position, token) => { - return wireCancellationToken(token, editorWorkerService.textualSuggest(model.uri, position)); - } - }, true); - } -} \ No newline at end of file diff --git a/src/vs/languages/markdown/test/common/markdown.test.ts b/src/vs/languages/markdown/test/common/markdown.test.ts deleted file mode 100644 index e46e0d5b747..00000000000 --- a/src/vs/languages/markdown/test/common/markdown.test.ts +++ /dev/null @@ -1,116 +0,0 @@ -/*--------------------------------------------------------------------------------------------- - * Copyright (c) Microsoft Corporation. All rights reserved. - * Licensed under the MIT License. See License.txt in the project root for license information. - *--------------------------------------------------------------------------------------------*/ -'use strict'; - -import modesUtil = require('vs/editor/test/common/modesUtil'); -import Modes = require('vs/editor/common/modes'); -import {htmlTokenTypes} from 'vs/languages/html/common/html'; -import {MockModeService} from 'vs/editor/test/common/mocks/mockModeService'; -import {NULL_THREAD_SERVICE} from 'vs/platform/test/common/nullThreadService'; -import {IThreadService} from 'vs/platform/thread/common/thread'; -import {IModeService} from 'vs/editor/common/services/modeService'; -import {ServiceCollection} from 'vs/platform/instantiation/common/serviceCollection'; -import {InstantiationService} from 'vs/platform/instantiation/common/instantiationService'; -import {MarkdownMode} from 'vs/languages/markdown/common/markdown'; -import {MockTokenizingMode} from 'vs/editor/test/common/mocks/mockMode'; - -class MarkdownMockModeService extends MockModeService { - isRegisteredMode(mimetypeOrModeId: string): boolean { - if (mimetypeOrModeId === 'javascript') { - return true; - } - if (mimetypeOrModeId === 'css') { - return true; - } - throw new Error('Not implemented'); - } - - getMode(commaSeparatedMimetypesOrCommaSeparatedIds: string): Modes.IMode { - if (commaSeparatedMimetypesOrCommaSeparatedIds === 'javascript') { - return new MockTokenizingMode('js', 'mock-js'); - } - if (commaSeparatedMimetypesOrCommaSeparatedIds === 'css') { - return new MockTokenizingMode('css', 'mock-css'); - } - throw new Error('Not implemented'); - } - - getModeIdForLanguageName(alias:string): string { - if (alias === 'text/javascript') { - return 'javascript'; - } - if (alias === 'text/css') { - return 'css'; - } - console.log(alias); - throw new Error('Not implemented'); - } -} - -suite('Markdown - tokenization', () => { - - var tokenizationSupport: Modes.ITokenizationSupport; - - (function() { - let threadService = NULL_THREAD_SERVICE; - let modeService = new MarkdownMockModeService(); - let services = new ServiceCollection(); - services.set(IThreadService, threadService); - services.set(IModeService, modeService); - let inst = new InstantiationService(services); - threadService.setInstantiationService(inst); - - let mode = new MarkdownMode( - { id: 'markdown' }, - inst, - threadService, - modeService, - null, - null - ); - - tokenizationSupport = mode.tokenizationSupport; - - })(); - - test('', () => { - modesUtil.executeTests(tokenizationSupport, [ - // HTML and embedded content - bug 16912 - [{ - line: 'foo*bar*', - tokens: [ - { startIndex:0, type: htmlTokenTypes.getTag('b.md') }, - { startIndex:3, type: '' }, - { startIndex:6, type: htmlTokenTypes.getTag('b.md') }, - { startIndex:10, type: 'emphasis.md' } - ]}], - - [{ - line: '*bar*', - tokens: [ - { startIndex:0, type: htmlTokenTypes.getTag('b.md') }, - { startIndex:4, type: 'emphasis.md' } - ]}], - - [{ - line: '*bar*', - tokens: [ - { startIndex:0, type: htmlTokenTypes.getTag('script.md') }, - { startIndex:8, type: 'mock-js' }, - { startIndex:20, type: htmlTokenTypes.getTag('script.md') }, - { startIndex:29, type: 'emphasis.md' } - ]}], - - [{ - line: '*bar*', - tokens: [ - { startIndex:0, type: htmlTokenTypes.getTag('style.md') }, - { startIndex:7, type: 'mock-css' }, - { startIndex:30, type: htmlTokenTypes.getTag('style.md') }, - { startIndex:38, type: 'emphasis.md' } - ]}] - ]); - }); -}); From 62f0272219dc72fda5246d330640e6af52a10cd0 Mon Sep 17 00:00:00 2001 From: Andre Weinand Date: Tue, 21 Jun 2016 00:33:12 +0200 Subject: [PATCH 212/217] update node-debug --- extensions/node-debug/node-debug.azure.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/extensions/node-debug/node-debug.azure.json b/extensions/node-debug/node-debug.azure.json index 3be7e95786b..81fcaee940f 100644 --- a/extensions/node-debug/node-debug.azure.json +++ b/extensions/node-debug/node-debug.azure.json @@ -1,6 +1,6 @@ { "account": "monacobuild", "container": "debuggers", - "zip": "babb057/node-debug.zip", + "zip": "1e5cde6/node-debug.zip", "output": "" } From d808ba31a697998f36c9c2cbdfc5f8d8e8b16ca2 Mon Sep 17 00:00:00 2001 From: Benjamin Pasero Date: Tue, 21 Jun 2016 09:58:25 +0200 Subject: [PATCH 213/217] fix issue in restoring editors --- src/vs/workbench/browser/parts/editor/editorPart.ts | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/vs/workbench/browser/parts/editor/editorPart.ts b/src/vs/workbench/browser/parts/editor/editorPart.ts index 7b1d550a557..737653efed8 100644 --- a/src/vs/workbench/browser/parts/editor/editorPart.ts +++ b/src/vs/workbench/browser/parts/editor/editorPart.ts @@ -932,11 +932,11 @@ export class EditorPart extends Part implements IEditorPart, IEditorGroupService // Validate width ratios const positions = rightEditors.length ? 3 : centerEditors.length ? 2 : 1; - if (widthRatios.length !== positions) { + if (!widthRatios || widthRatios.length !== positions) { if (!this.getVisibleEditors().length) { widthRatios = (positions === 3) ? [0.33, 0.33, 0.34] : (positions === 2) ? [0.5, 0.5] : [1]; } else { - widthRatios = void 0; // being taken care of by the layouting if editors are already open + widthRatios = void 0; } } From 4d2350a8250330ae6215f002200ae71efb0c8343 Mon Sep 17 00:00:00 2001 From: Benjamin Pasero Date: Tue, 21 Jun 2016 10:54:53 +0200 Subject: [PATCH 214/217] Keybinding conflict (scrollPageDown, scrollPageUp) (fixes #7047) --- src/vs/editor/common/config/config.ts | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/src/vs/editor/common/config/config.ts b/src/vs/editor/common/config/config.ts index 650fa4dfb6f..d4eee107698 100644 --- a/src/vs/editor/common/config/config.ts +++ b/src/vs/editor/common/config/config.ts @@ -231,10 +231,12 @@ registerCoreCommand(H.ScrollLineDown, { }); registerCoreCommand(H.ScrollPageUp, { - primary: KeyMod.CtrlCmd | KeyCode.PageUp + primary: KeyMod.CtrlCmd | KeyCode.PageUp, + win: { primary: KeyMod.Alt | KeyCode.PageUp } }); registerCoreCommand(H.ScrollPageDown, { - primary: KeyMod.CtrlCmd | KeyCode.PageDown + primary: KeyMod.CtrlCmd | KeyCode.PageDown, + win: { primary: KeyMod.Alt | KeyCode.PageDown } }); registerCoreCommand(H.CursorColumnSelectLeft, { From f555b323a4e6ff97c2e6007722de95f4bb3395c5 Mon Sep 17 00:00:00 2001 From: isidor Date: Tue, 21 Jun 2016 11:34:56 +0200 Subject: [PATCH 215/217] debug: do not show 'canceled' error messages to the user fixes #7906 --- .../workbench/parts/debug/electron-browser/debugService.ts | 5 +++++ src/vs/workbench/parts/debug/node/v8Protocol.ts | 5 ++++- 2 files changed, 9 insertions(+), 1 deletion(-) diff --git a/src/vs/workbench/parts/debug/electron-browser/debugService.ts b/src/vs/workbench/parts/debug/electron-browser/debugService.ts index ce69c5164c9..e7271fea91d 100644 --- a/src/vs/workbench/parts/debug/electron-browser/debugService.ts +++ b/src/vs/workbench/parts/debug/electron-browser/debugService.ts @@ -646,6 +646,11 @@ export class DebugService implements debug.IDebugService { isBuiltin: this.configurationManager.adapter.extensionDescription.isBuiltin }); }).then(undefined, (error: any) => { + if (error instanceof Error && error.message === 'Canceled') { + // Do not show 'canceled' error messages to the user #7906 + return TPromise.as(null); + } + this.telemetryService.publicLog('debugMisconfiguration', { type: configuration ? configuration.type : undefined }); this.setStateAndEmit(debug.State.Inactive); if (this.session) { diff --git a/src/vs/workbench/parts/debug/node/v8Protocol.ts b/src/vs/workbench/parts/debug/node/v8Protocol.ts index 340ec55ef33..e490d102c03 100644 --- a/src/vs/workbench/parts/debug/node/v8Protocol.ts +++ b/src/vs/workbench/parts/debug/node/v8Protocol.ts @@ -6,6 +6,7 @@ import stream = require('stream'); import uuid = require('vs/base/common/uuid'); import { TPromise } from 'vs/base/common/winjs.base'; +import { canceled } from 'vs/base/common/errors'; export abstract class V8Protocol { @@ -41,7 +42,9 @@ export abstract class V8Protocol { } protected send(command: string, args: any): TPromise { + let errorCallback; return new TPromise((completeDispatch, errorDispatch) => { + errorCallback = errorDispatch; this.doSend(command, args, (result: DebugProtocol.Response) => { if (result.success) { completeDispatch(result); @@ -49,7 +52,7 @@ export abstract class V8Protocol { errorDispatch(result); } }); - }); + }, () => errorCallback(canceled())); } private doSend(command: string, args: any, clb: (result: DebugProtocol.Response) => void): void { From ce48b74a5bee9b4a6976afe374401e7b9c7a661a Mon Sep 17 00:00:00 2001 From: isidor Date: Tue, 21 Jun 2016 11:45:34 +0200 Subject: [PATCH 216/217] debug: move set / get expression value logic to super class fixes #7914 --- .../parts/debug/common/debugModel.ts | 33 ++++++++----------- 1 file changed, 14 insertions(+), 19 deletions(-) diff --git a/src/vs/workbench/parts/debug/common/debugModel.ts b/src/vs/workbench/parts/debug/common/debugModel.ts index ae8095d401b..15b79893269 100644 --- a/src/vs/workbench/parts/debug/common/debugModel.ts +++ b/src/vs/workbench/parts/debug/common/debugModel.ts @@ -226,11 +226,12 @@ export class KeyValueOutputElement extends OutputElement { } } -export class ExpressionContainer implements debug.IExpressionContainer { +export abstract class ExpressionContainer implements debug.IExpressionContainer { private children: TPromise; public valueChanged: boolean; public static allValues: { [id: string]: string } = {}; + private _value: string; constructor(public reference: number, private id: string, private cacheChildren: boolean) { this.children = null; @@ -251,20 +252,6 @@ export class ExpressionContainer implements debug.IExpressionContainer { return this.id; } -} - -export class Expression extends ExpressionContainer implements debug.IExpression { - static DEFAULT_VALUE = 'not available'; - - public available: boolean; - private _value: string; - - constructor(public name: string, cacheChildren: boolean, id = uuid.generateUuid()) { - super(0, id, cacheChildren); - this.value = Expression.DEFAULT_VALUE; - this.available = false; - } - public get value(): string { return this._value; } @@ -277,15 +264,23 @@ export class Expression extends ExpressionContainer implements debug.IExpression } } -export class Variable extends ExpressionContainer implements debug.IExpression { +export class Expression extends ExpressionContainer implements debug.IExpression { + static DEFAULT_VALUE = 'not available'; - public value: string; + public available: boolean; + + constructor(public name: string, cacheChildren: boolean, id = uuid.generateUuid()) { + super(0, id, cacheChildren); + this.value = Expression.DEFAULT_VALUE; + this.available = false; + } +} + +export class Variable extends ExpressionContainer implements debug.IExpression { constructor(public parent: debug.IExpressionContainer, reference: number, public name: string, value: string, public available = true) { super(reference, `variable:${ parent.getId() }:${ name }`, true); this.value = massageValue(value); - this.valueChanged = ExpressionContainer.allValues[this.getId()] && ExpressionContainer.allValues[this.getId()] !== value; - ExpressionContainer.allValues[this.getId()] = value; } } From 82fea1b9c18c5f157a8536b7f901ee35422937bd Mon Sep 17 00:00:00 2001 From: Benjamin Pasero Date: Tue, 21 Jun 2016 11:54:35 +0200 Subject: [PATCH 217/217] more explicit navigation in mru stack order --- .../quickopen/browser/quickOpenWidget.ts | 13 +++++-- .../base/parts/quickopen/common/quickOpen.ts | 5 +++ src/vs/code/electron-main/menus.ts | 4 +- .../parts/editor/editor.contribution.ts | 14 +++++-- .../browser/parts/editor/editorActions.ts | 39 +++++++++++++++++-- .../browser/parts/editor/editorPicker.ts | 13 +++++-- .../parts/quickopen/quickOpenController.ts | 6 +-- src/vs/workbench/browser/quickopen.ts | 4 +- 8 files changed, 78 insertions(+), 20 deletions(-) diff --git a/src/vs/base/parts/quickopen/browser/quickOpenWidget.ts b/src/vs/base/parts/quickopen/browser/quickOpenWidget.ts index 8c27201f26e..f8d94989037 100644 --- a/src/vs/base/parts/quickopen/browser/quickOpenWidget.ts +++ b/src/vs/base/parts/quickopen/browser/quickOpenWidget.ts @@ -575,12 +575,19 @@ export class QuickOpenWidget implements IModelProvider { } } - // Finally check for auto focus of second entry + // Check for auto focus of second entry else if (autoFocus.autoFocusSecondEntry) { if (entries.length > 1) { this.tree.focusNth(1); } } + + // Finally check for auto focus of last entry + else if (autoFocus.autoFocusLastEntry) { + if (entries.length > 1) { + this.tree.focusLast(); + } + } } public refresh(input: IModel, autoFocus: IAutoFocus): void { @@ -719,8 +726,8 @@ export class QuickOpenWidget implements IModelProvider { } } - public isQuickNavigating(): boolean { - return !!this.quickNavigateConfiguration; + public getQuickNavigateConfiguration(): IQuickNavigateConfiguration { + return this.quickNavigateConfiguration; } public setPlaceHolder(placeHolder: string): void { diff --git a/src/vs/base/parts/quickopen/common/quickOpen.ts b/src/vs/base/parts/quickopen/common/quickOpen.ts index bc2002d3609..8bbe2285f39 100644 --- a/src/vs/base/parts/quickopen/common/quickOpen.ts +++ b/src/vs/base/parts/quickopen/common/quickOpen.ts @@ -27,6 +27,11 @@ export interface IAutoFocus { */ autoFocusSecondEntry?: boolean; + /** + * If set to true, will automatically select the last entry from the result list. + */ + autoFocusLastEntry?: boolean; + /** * If set to true, will automatically select any entry whose label starts with the search * value. Since some entries to the top might match the query but not on the prefix, this diff --git a/src/vs/code/electron-main/menus.ts b/src/vs/code/electron-main/menus.ts index aaa18e0c357..6a29abf74bb 100644 --- a/src/vs/code/electron-main/menus.ts +++ b/src/vs/code/electron-main/menus.ts @@ -592,12 +592,14 @@ export class VSCodeMenu { let nextEditor = this.createMenuItem(nls.localize({ key: 'miNextEditor', comment: ['&& denotes a mnemonic'] }, "&&Next Editor"), 'workbench.action.nextEditor'); let previousEditor = this.createMenuItem(nls.localize({ key: 'miPreviousEditor', comment: ['&& denotes a mnemonic'] }, "&&Previous Editor"), 'workbench.action.previousEditor'); - let previousEditorInGroup = this.createMenuItem(nls.localize({ key: 'miPreviousEditorInGroup', comment: ['&& denotes a mnemonic'] }, "Previous &&Editor in Group"), 'workbench.action.openPreviousEditorInGroup'); + let nextEditorInGroup = this.createMenuItem(nls.localize({ key: 'miNextEditorInGroup', comment: ['&& denotes a mnemonic'] }, "&&Next Used Editor in Group"), 'workbench.action.openNextRecentlyUsedEditorInGroup'); + let previousEditorInGroup = this.createMenuItem(nls.localize({ key: 'miPreviousEditorInGroup', comment: ['&& denotes a mnemonic'] }, "&&Previous Used Editor in Group"), 'workbench.action.openPreviousRecentlyUsedEditorInGroup'); [ nextEditor, previousEditor, __separator__(), + nextEditorInGroup, previousEditorInGroup ].forEach(item => switchEditorMenu.append(item)); diff --git a/src/vs/workbench/browser/parts/editor/editor.contribution.ts b/src/vs/workbench/browser/parts/editor/editor.contribution.ts index 615198b418e..2ac7fa5f107 100644 --- a/src/vs/workbench/browser/parts/editor/editor.contribution.ts +++ b/src/vs/workbench/browser/parts/editor/editor.contribution.ts @@ -32,9 +32,9 @@ import {KeyMod, KeyCode} from 'vs/base/common/keyCodes'; import {EditorStacksModel} from 'vs/workbench/common/editor/editorStacksModel'; import {CloseEditorsInGroupAction, CloseEditorsInOtherGroupsAction, CloseAllEditorsAction, MoveGroupLeftAction, MoveGroupRightAction, SplitEditorAction, KeepEditorAction, CloseOtherEditorsInGroupAction, OpenToSideAction, NavigateBetweenGroupsAction, FocusFirstGroupAction, FocusSecondGroupAction, FocusThirdGroupAction, EvenGroupWidthsAction, MaximizeGroupAction, MinimizeOtherGroupsAction, FocusPreviousGroup, FocusNextGroup, ShowEditorsInLeftGroupAction, - toEditorQuickOpenEntry, CloseLeftEditorsInGroupAction, CloseRightEditorsInGroupAction, OpenNextEditor, OpenPreviousEditor, NavigateBackwardsAction, NavigateForwardAction, ReopenClosedEditorAction, OpenPreviousEditorInGroupAction, NAVIGATE_IN_LEFT_GROUP_PREFIX, + toEditorQuickOpenEntry, CloseLeftEditorsInGroupAction, CloseRightEditorsInGroupAction, OpenNextEditor, OpenPreviousEditor, NavigateBackwardsAction, NavigateForwardAction, ReopenClosedEditorAction, OpenPreviousRecentlyUsedEditorInGroupAction, NAVIGATE_IN_LEFT_GROUP_PREFIX, GlobalQuickOpenAction, OpenPreviousEditorFromHistoryAction, QuickOpenNavigateNextAction, QuickOpenNavigatePreviousAction, ShowAllEditorsAction, NAVIGATE_ALL_EDITORS_GROUP_PREFIX, ClearEditorHistoryAction, ShowEditorsInCenterGroupAction, - NAVIGATE_IN_CENTER_GROUP_PREFIX, ShowEditorsInRightGroupAction, NAVIGATE_IN_RIGHT_GROUP_PREFIX, RemoveFromEditorHistoryAction, FocusLastEditorInStackAction + NAVIGATE_IN_CENTER_GROUP_PREFIX, ShowEditorsInRightGroupAction, NAVIGATE_IN_RIGHT_GROUP_PREFIX, RemoveFromEditorHistoryAction, FocusLastEditorInStackAction, OpenNextRecentlyUsedEditorInGroupAction } from 'vs/workbench/browser/parts/editor/editorActions'; // Register String Editor @@ -263,12 +263,18 @@ function navigateKeybinding(shift: boolean): IKeybindings { // Register Editor Actions const category = nls.localize('view', "View"); -registry.registerWorkbenchAction(new SyncActionDescriptor(OpenPreviousEditorInGroupAction, OpenPreviousEditorInGroupAction.ID, OpenPreviousEditorInGroupAction.LABEL, { +registry.registerWorkbenchAction(new SyncActionDescriptor(OpenNextRecentlyUsedEditorInGroupAction, OpenNextRecentlyUsedEditorInGroupAction.ID, OpenNextRecentlyUsedEditorInGroupAction.LABEL, { primary: KeyMod.CtrlCmd | KeyCode.Tab, mac: { primary: KeyMod.WinCtrl | KeyCode.Tab } -}), 'Open Previous in Editor Group'); +}), 'Open Next Recently Used Editor in Group'); +registry.registerWorkbenchAction(new SyncActionDescriptor(OpenPreviousRecentlyUsedEditorInGroupAction, OpenPreviousRecentlyUsedEditorInGroupAction.ID, OpenPreviousRecentlyUsedEditorInGroupAction.LABEL, { + primary: KeyMod.CtrlCmd | KeyMod.Shift |  KeyCode.Tab, + mac: { + primary: KeyMod.WinCtrl | KeyMod.Shift |  KeyCode.Tab + } +}), 'Open Previous Recently Used Editor in Group'); registry.registerWorkbenchAction(new SyncActionDescriptor(ShowAllEditorsAction, ShowAllEditorsAction.ID, ShowAllEditorsAction.LABEL, { primary: null, mac: { primary: KeyMod.CtrlCmd | KeyMod.Alt | KeyCode.Tab } }), 'View: Show All Editors', category); registry.registerWorkbenchAction(new SyncActionDescriptor(ShowEditorsInLeftGroupAction, ShowEditorsInLeftGroupAction.ID, ShowEditorsInLeftGroupAction.LABEL), 'View: Show Editors in Left Group', category); registry.registerWorkbenchAction(new SyncActionDescriptor(ShowEditorsInCenterGroupAction, ShowEditorsInCenterGroupAction.ID, ShowEditorsInCenterGroupAction.LABEL), 'View: Show Editors in Center Group', category); diff --git a/src/vs/workbench/browser/parts/editor/editorActions.ts b/src/vs/workbench/browser/parts/editor/editorActions.ts index 8ce3af32df8..1a588852832 100644 --- a/src/vs/workbench/browser/parts/editor/editorActions.ts +++ b/src/vs/workbench/browser/parts/editor/editorActions.ts @@ -1014,10 +1014,7 @@ export class ShowAllEditorsAction extends QuickOpenAction { } } -export class OpenPreviousEditorInGroupAction extends Action { - - public static ID = 'workbench.action.openPreviousEditorInGroup'; - public static LABEL = nls.localize('openPreviousEditorInGroup', "Open Previous in Editor Group"); +export class BaseQuickOpenEditorInGroupAction extends Action { constructor( id: string, @@ -1052,6 +1049,40 @@ export class OpenPreviousEditorInGroupAction extends Action { } } +export class OpenPreviousRecentlyUsedEditorInGroupAction extends BaseQuickOpenEditorInGroupAction { + + public static ID = 'workbench.action.openPreviousRecentlyUsedEditorInGroup'; + public static LABEL = nls.localize('openPreviousEditorInGroup', "Open Previous Recently Used Editor in Group"); + + constructor( + id: string, + label: string, + @IQuickOpenService quickOpenService: IQuickOpenService, + @IKeybindingService keybindingService: IKeybindingService, + @IEditorGroupService editorGroupService: IEditorGroupService, + @IWorkbenchEditorService editorService: IWorkbenchEditorService + ) { + super(id, label, quickOpenService, keybindingService, editorGroupService, editorService); + } +} + +export class OpenNextRecentlyUsedEditorInGroupAction extends BaseQuickOpenEditorInGroupAction { + + public static ID = 'workbench.action.openNextRecentlyUsedEditorInGroup'; + public static LABEL = nls.localize('openNextEditorInGroup', "Open Next Recently Used Editor in Group"); + + constructor( + id: string, + label: string, + @IQuickOpenService quickOpenService: IQuickOpenService, + @IKeybindingService keybindingService: IKeybindingService, + @IEditorGroupService editorGroupService: IEditorGroupService, + @IWorkbenchEditorService editorService: IWorkbenchEditorService + ) { + super(id, label, quickOpenService, keybindingService, editorGroupService, editorService); + } +} + export class GlobalQuickOpenAction extends Action { public static ID = 'workbench.action.quickOpen'; diff --git a/src/vs/workbench/browser/parts/editor/editorPicker.ts b/src/vs/workbench/browser/parts/editor/editorPicker.ts index a504261df5f..5a7a49892e6 100644 --- a/src/vs/workbench/browser/parts/editor/editorPicker.ts +++ b/src/vs/workbench/browser/parts/editor/editorPicker.ts @@ -11,7 +11,7 @@ import labels = require('vs/base/common/labels'); import URI from 'vs/base/common/uri'; import errors = require('vs/base/common/errors'); import strings = require('vs/base/common/strings'); -import {IAutoFocus, Mode, IEntryRunContext} from 'vs/base/parts/quickopen/common/quickOpen'; +import {IAutoFocus, Mode, IEntryRunContext, IQuickNavigateConfiguration} from 'vs/base/parts/quickopen/common/quickOpen'; import {QuickOpenModel, QuickOpenEntry, QuickOpenEntryGroup} from 'vs/base/parts/quickopen/browser/quickOpenModel'; import scorer = require('vs/base/common/scorer'); import {QuickOpenHandler} from 'vs/workbench/browser/quickopen'; @@ -178,8 +178,8 @@ export abstract class EditorGroupPicker extends BaseEditorPicker { return nls.localize('noOpenedEditors', "List of opened editors is currently empty"); } - public getAutoFocus(searchValue: string, isQuickNavigating?: boolean): IAutoFocus { - if (searchValue || !isQuickNavigating) { + public getAutoFocus(searchValue: string, quickNavigateConfiguration: IQuickNavigateConfiguration): IAutoFocus { + if (searchValue || !quickNavigateConfiguration) { return { autoFocusFirstEntry: true }; @@ -191,6 +191,13 @@ export abstract class EditorGroupPicker extends BaseEditorPicker { return super.getAutoFocus(searchValue); } + const isShiftNavigate = (quickNavigateConfiguration && quickNavigateConfiguration.keybindings.some(k => k.hasShift())); + if (isShiftNavigate) { + return { + autoFocusLastEntry: true + }; + } + return { autoFocusFirstEntry: group.count === 1, autoFocusSecondEntry: group.count > 1 diff --git a/src/vs/workbench/browser/parts/quickopen/quickOpenController.ts b/src/vs/workbench/browser/parts/quickopen/quickOpenController.ts index a8c28c53c20..83fb90f2528 100644 --- a/src/vs/workbench/browser/parts/quickopen/quickOpenController.ts +++ b/src/vs/workbench/browser/parts/quickopen/quickOpenController.ts @@ -771,7 +771,7 @@ export class QuickOpenController extends WorkbenchComponent implements IQuickOpe let placeHolderLabel = (typeof canRun === 'string') ? canRun : nls.localize('canNotRunPlaceholder', "This quick open handler can not be used in the current context"); const model = new QuickOpenModel([new PlaceholderQuickOpenEntry(placeHolderLabel)], this.actionProvider); - this.showModel(model, resolvedHandler.getAutoFocus(value, this.quickOpenWidget.isQuickNavigating()), resolvedHandler.getAriaLabel()); + this.showModel(model, resolvedHandler.getAutoFocus(value, this.quickOpenWidget.getQuickNavigateConfiguration()), resolvedHandler.getAriaLabel()); return TPromise.as(null); } @@ -792,9 +792,9 @@ export class QuickOpenController extends WorkbenchComponent implements IQuickOpe if (this.currentResultToken === currentResultToken) { if (!result || !result.entries.length) { const model = new QuickOpenModel([new PlaceholderQuickOpenEntry(resolvedHandler.getEmptyLabel(value))]); - this.showModel(model, resolvedHandler.getAutoFocus(value, this.quickOpenWidget.isQuickNavigating()), resolvedHandler.getAriaLabel()); + this.showModel(model, resolvedHandler.getAutoFocus(value, this.quickOpenWidget.getQuickNavigateConfiguration()), resolvedHandler.getAriaLabel()); } else { - this.showModel(result, resolvedHandler.getAutoFocus(value, this.quickOpenWidget.isQuickNavigating()), resolvedHandler.getAriaLabel()); + this.showModel(result, resolvedHandler.getAutoFocus(value, this.quickOpenWidget.getQuickNavigateConfiguration()), resolvedHandler.getAriaLabel()); } } }); diff --git a/src/vs/workbench/browser/quickopen.ts b/src/vs/workbench/browser/quickopen.ts index 12092bce3ab..e83e4341c1d 100644 --- a/src/vs/workbench/browser/quickopen.ts +++ b/src/vs/workbench/browser/quickopen.ts @@ -14,7 +14,7 @@ import errors = require('vs/base/common/errors'); import {Registry} from 'vs/platform/platform'; import {Action} from 'vs/base/common/actions'; import {KeyMod} from 'vs/base/common/keyCodes'; -import {Mode, IEntryRunContext, IAutoFocus, IModel} from 'vs/base/parts/quickopen/common/quickOpen'; +import {Mode, IEntryRunContext, IAutoFocus, IModel, IQuickNavigateConfiguration} from 'vs/base/parts/quickopen/common/quickOpen'; import {QuickOpenEntry, IHighlight, QuickOpenEntryGroup, QuickOpenModel} from 'vs/base/parts/quickopen/browser/quickOpenModel'; import {EditorOptions, EditorInput} from 'vs/workbench/common/editor'; import {IResourceInput, IEditorInput} from 'vs/platform/editor/common/editor'; @@ -63,7 +63,7 @@ export class QuickOpenHandler { * Indicates if the handler wishes the quick open widget to automatically select the first result entry or an entry * based on a specific prefix match. */ - public getAutoFocus(searchValue: string, isQuickNavigating?: boolean): IAutoFocus { + public getAutoFocus(searchValue: string, quickNavigateConfiguration?: IQuickNavigateConfiguration): IAutoFocus { return {}; }