mirror of
https://github.com/ckaczor/azuredatastudio.git
synced 2026-04-05 03:20:29 -04:00
Merge from vscode 313ede61cbad8f9dc748907b3384e059ddddb79a (#7436)
* Merge from vscode 313ede61cbad8f9dc748907b3384e059ddddb79a * fix strict null checks
This commit is contained in:
2
.yarnrc
2
.yarnrc
@@ -1,3 +1,3 @@
|
|||||||
disturl "https://atom.io/download/electron"
|
disturl "https://atom.io/download/electron"
|
||||||
target "6.0.9"
|
target "4.2.10"
|
||||||
runtime "electron"
|
runtime "electron"
|
||||||
|
|||||||
@@ -48,7 +48,7 @@ declare namespace monaco.editor {
|
|||||||
#include(vs/editor/standalone/common/standaloneThemeService): BuiltinTheme, IStandaloneThemeData, IColors
|
#include(vs/editor/standalone/common/standaloneThemeService): BuiltinTheme, IStandaloneThemeData, IColors
|
||||||
#include(vs/editor/common/modes/supports/tokenization): ITokenThemeRule
|
#include(vs/editor/common/modes/supports/tokenization): ITokenThemeRule
|
||||||
#include(vs/editor/common/services/webWorker): MonacoWebWorker, IWebWorkerOptions
|
#include(vs/editor/common/services/webWorker): MonacoWebWorker, IWebWorkerOptions
|
||||||
#include(vs/editor/standalone/browser/standaloneCodeEditor): IActionDescriptor, IEditorConstructionOptions, IDiffEditorConstructionOptions, IStandaloneCodeEditor, IStandaloneDiffEditor
|
#include(vs/editor/standalone/browser/standaloneCodeEditor): IActionDescriptor, IStandaloneEditorConstructionOptions, IDiffEditorConstructionOptions, IStandaloneCodeEditor, IStandaloneDiffEditor
|
||||||
export interface ICommandHandler {
|
export interface ICommandHandler {
|
||||||
(...args: any[]): void;
|
(...args: any[]): void;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -6,7 +6,7 @@
|
|||||||
"git": {
|
"git": {
|
||||||
"name": "chromium",
|
"name": "chromium",
|
||||||
"repositoryUrl": "https://chromium.googlesource.com/chromium/src",
|
"repositoryUrl": "https://chromium.googlesource.com/chromium/src",
|
||||||
"commitHash": "91f08db83c2ce8c722ddf0911ead8f7c473bedfa"
|
"commitHash": "c6a08e5368de4352903e702cde750b33239a50ab"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"licenseDetail": [
|
"licenseDetail": [
|
||||||
@@ -40,7 +40,7 @@
|
|||||||
"SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE."
|
"SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE."
|
||||||
],
|
],
|
||||||
"isOnlyProductionDependency": true,
|
"isOnlyProductionDependency": true,
|
||||||
"version": "76.0.3809.146"
|
"version": "69.0.3497.128"
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"component": {
|
"component": {
|
||||||
@@ -48,11 +48,11 @@
|
|||||||
"git": {
|
"git": {
|
||||||
"name": "nodejs",
|
"name": "nodejs",
|
||||||
"repositoryUrl": "https://github.com/nodejs/node",
|
"repositoryUrl": "https://github.com/nodejs/node",
|
||||||
"commitHash": "64219741218aa87e259cf8257596073b8e747f0a"
|
"commitHash": "8c70b2084ce5f76ea1e3b3c4ccdeee4483fe338b"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"isOnlyProductionDependency": true,
|
"isOnlyProductionDependency": true,
|
||||||
"version": "12.4.0"
|
"version": "10.11.0"
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"component": {
|
"component": {
|
||||||
@@ -60,12 +60,12 @@
|
|||||||
"git": {
|
"git": {
|
||||||
"name": "electron",
|
"name": "electron",
|
||||||
"repositoryUrl": "https://github.com/electron/electron",
|
"repositoryUrl": "https://github.com/electron/electron",
|
||||||
"commitHash": "407747b48c47cdeed156a73dde1c47609470c95a"
|
"commitHash": "4e4c7527c63fcf27dffaeb58bde996b8d859c0ed"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"isOnlyProductionDependency": true,
|
"isOnlyProductionDependency": true,
|
||||||
"license": "MIT",
|
"license": "MIT",
|
||||||
"version": "6.0.9"
|
"version": "4.2.10"
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"component": {
|
"component": {
|
||||||
@@ -98,11 +98,11 @@
|
|||||||
"git": {
|
"git": {
|
||||||
"name": "vscode-octicons-font",
|
"name": "vscode-octicons-font",
|
||||||
"repositoryUrl": "https://github.com/Microsoft/vscode-octicons-font",
|
"repositoryUrl": "https://github.com/Microsoft/vscode-octicons-font",
|
||||||
"commitHash": "415cd5b42ab699b6b46c0bf011ada0a2ae50bfb4"
|
"commitHash": "4cbf2bd35cf0084eabd47d322cc58339fd7743cf"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"license": "MIT",
|
"license": "MIT",
|
||||||
"version": "1.3.1"
|
"version": "1.3.2"
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
"component": {
|
"component": {
|
||||||
|
|||||||
@@ -1268,7 +1268,7 @@ export class CommandCenter {
|
|||||||
|
|
||||||
if (pick === saveAndCommit) {
|
if (pick === saveAndCommit) {
|
||||||
await Promise.all(documents.map(d => d.save()));
|
await Promise.all(documents.map(d => d.save()));
|
||||||
await repository.add(documents.map(d => d.uri));
|
await repository.add([]);
|
||||||
} else if (pick !== commit) {
|
} else if (pick !== commit) {
|
||||||
return false; // do not commit on cancel
|
return false; // do not commit on cancel
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -10,8 +10,8 @@ import { xhr, XHRResponse, getErrorStatusDescription } from 'request-light';
|
|||||||
|
|
||||||
const localize = nls.loadMessageBundle();
|
const localize = nls.loadMessageBundle();
|
||||||
|
|
||||||
import { workspace, window, languages, commands, ExtensionContext, extensions, Uri, LanguageConfiguration, Diagnostic, StatusBarAlignment, TextEditor } from 'vscode';
|
import { workspace, window, languages, commands, ExtensionContext, extensions, Uri, LanguageConfiguration, Diagnostic, StatusBarAlignment, TextEditor, TextDocument, FormattingOptions, CancellationToken, ProviderResult, TextEdit, Range, Disposable } from 'vscode';
|
||||||
import { LanguageClient, LanguageClientOptions, RequestType, ServerOptions, TransportKind, NotificationType, DidChangeConfigurationNotification, HandleDiagnosticsSignature, ResponseError } from 'vscode-languageclient';
|
import { LanguageClient, LanguageClientOptions, RequestType, ServerOptions, TransportKind, NotificationType, DidChangeConfigurationNotification, HandleDiagnosticsSignature, ResponseError, DocumentRangeFormattingParams, DocumentRangeFormattingRequest } from 'vscode-languageclient';
|
||||||
import TelemetryReporter from 'vscode-extension-telemetry';
|
import TelemetryReporter from 'vscode-extension-telemetry';
|
||||||
|
|
||||||
import { hash } from './utils/hash';
|
import { hash } from './utils/hash';
|
||||||
@@ -65,6 +65,8 @@ export function activate(context: ExtensionContext) {
|
|||||||
|
|
||||||
let toDispose = context.subscriptions;
|
let toDispose = context.subscriptions;
|
||||||
|
|
||||||
|
let rangeFormatting: Disposable | undefined = undefined;
|
||||||
|
|
||||||
let packageInfo = getPackageInfo(context);
|
let packageInfo = getPackageInfo(context);
|
||||||
telemetryReporter = packageInfo && new TelemetryReporter(packageInfo.name, packageInfo.version, packageInfo.aiKey);
|
telemetryReporter = packageInfo && new TelemetryReporter(packageInfo.name, packageInfo.version, packageInfo.aiKey);
|
||||||
|
|
||||||
@@ -101,7 +103,8 @@ export function activate(context: ExtensionContext) {
|
|||||||
// Register the server for json documents
|
// Register the server for json documents
|
||||||
documentSelector,
|
documentSelector,
|
||||||
initializationOptions: {
|
initializationOptions: {
|
||||||
handledSchemaProtocols: ['file'] // language server only loads file-URI. Fetching schemas with other protocols ('http'...) are made on the client.
|
handledSchemaProtocols: ['file'], // language server only loads file-URI. Fetching schemas with other protocols ('http'...) are made on the client.
|
||||||
|
provideFormatter: false // tell the server to not provide formatting capability and ignore the `json.format.enable` setting.
|
||||||
},
|
},
|
||||||
synchronize: {
|
synchronize: {
|
||||||
// Synchronize the setting section 'json' to the server
|
// Synchronize the setting section 'json' to the server
|
||||||
@@ -224,10 +227,13 @@ export function activate(context: ExtensionContext) {
|
|||||||
extensions.onDidChange(_ => {
|
extensions.onDidChange(_ => {
|
||||||
client.sendNotification(SchemaAssociationNotification.type, getSchemaAssociation(context));
|
client.sendNotification(SchemaAssociationNotification.type, getSchemaAssociation(context));
|
||||||
});
|
});
|
||||||
|
|
||||||
|
// manually register / deregister format provider based on the `html.format.enable` setting avoiding issues with late registration. See #71652.
|
||||||
|
updateFormatterRegistration();
|
||||||
|
toDispose.push({ dispose: () => rangeFormatting && rangeFormatting.dispose() });
|
||||||
|
toDispose.push(workspace.onDidChangeConfiguration(e => e.affectsConfiguration('html.format.enable') && updateFormatterRegistration()));
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
let languageConfiguration: LanguageConfiguration = {
|
let languageConfiguration: LanguageConfiguration = {
|
||||||
wordPattern: /("(?:[^\\\"]*(?:\\.)?)*"?)|[^\s{}\[\],:]+/,
|
wordPattern: /("(?:[^\\\"]*(?:\\.)?)*"?)|[^\s{}\[\],:]+/,
|
||||||
indentationRules: {
|
indentationRules: {
|
||||||
@@ -237,8 +243,35 @@ export function activate(context: ExtensionContext) {
|
|||||||
};
|
};
|
||||||
languages.setLanguageConfiguration('json', languageConfiguration);
|
languages.setLanguageConfiguration('json', languageConfiguration);
|
||||||
languages.setLanguageConfiguration('jsonc', languageConfiguration);
|
languages.setLanguageConfiguration('jsonc', languageConfiguration);
|
||||||
|
|
||||||
|
function updateFormatterRegistration() {
|
||||||
|
const formatEnabled = workspace.getConfiguration().get('json.format.enable');
|
||||||
|
if (!formatEnabled && rangeFormatting) {
|
||||||
|
rangeFormatting.dispose();
|
||||||
|
rangeFormatting = undefined;
|
||||||
|
} else if (formatEnabled && !rangeFormatting) {
|
||||||
|
rangeFormatting = languages.registerDocumentRangeFormattingEditProvider(documentSelector, {
|
||||||
|
provideDocumentRangeFormattingEdits(document: TextDocument, range: Range, options: FormattingOptions, token: CancellationToken): ProviderResult<TextEdit[]> {
|
||||||
|
let params: DocumentRangeFormattingParams = {
|
||||||
|
textDocument: client.code2ProtocolConverter.asTextDocumentIdentifier(document),
|
||||||
|
range: client.code2ProtocolConverter.asRange(range),
|
||||||
|
options: client.code2ProtocolConverter.asFormattingOptions(options)
|
||||||
|
};
|
||||||
|
return client.sendRequest(DocumentRangeFormattingRequest.type, params, token).then(
|
||||||
|
client.protocol2CodeConverter.asTextEdits,
|
||||||
|
(error) => {
|
||||||
|
client.logFailedRequest(DocumentRangeFormattingRequest.type, error);
|
||||||
|
return Promise.resolve([]);
|
||||||
|
}
|
||||||
|
);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
export function deactivate(): Promise<any> {
|
export function deactivate(): Promise<any> {
|
||||||
return telemetryReporter ? telemetryReporter.dispose() : Promise.resolve(null);
|
return telemetryReporter ? telemetryReporter.dispose() : Promise.resolve(null);
|
||||||
}
|
}
|
||||||
@@ -286,7 +319,6 @@ function getSettings(): Settings {
|
|||||||
proxyStrictSSL: httpSettings.get('proxyStrictSSL')
|
proxyStrictSSL: httpSettings.get('proxyStrictSSL')
|
||||||
},
|
},
|
||||||
json: {
|
json: {
|
||||||
format: workspace.getConfiguration('json').get('format'),
|
|
||||||
schemas: [],
|
schemas: [],
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -104,7 +104,7 @@
|
|||||||
"dependencies": {
|
"dependencies": {
|
||||||
"request-light": "^0.2.4",
|
"request-light": "^0.2.4",
|
||||||
"vscode-extension-telemetry": "0.1.1",
|
"vscode-extension-telemetry": "0.1.1",
|
||||||
"vscode-languageclient": "^5.3.0-next.6",
|
"vscode-languageclient": "^6.0.0-next.1",
|
||||||
"vscode-nls": "^4.1.1"
|
"vscode-nls": "^4.1.1"
|
||||||
},
|
},
|
||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
|
|||||||
@@ -12,7 +12,7 @@ The JSON Language server provides language-specific smarts for editing, validati
|
|||||||
|
|
||||||
The JSON language server supports requests on documents of language id `json` and `jsonc`.
|
The JSON language server supports requests on documents of language id `json` and `jsonc`.
|
||||||
- `json` documents are parsed and validated following the [JSON specification](https://tools.ietf.org/html/rfc7159).
|
- `json` documents are parsed and validated following the [JSON specification](https://tools.ietf.org/html/rfc7159).
|
||||||
- `jsonc` documents additionally accept single line (`//`) and multi-line comments (`/* ... */`) and accepts trailing commas. JSONC is a VSCode specific file format, intended for VSCode configuration files, without any aspirations to define a new common file format.
|
- `jsonc` documents additionally accept single line (`//`) and multi-line comments (`/* ... */`). JSONC is a VSCode specific file format, intended for VSCode configuration files, without any aspirations to define a new common file format.
|
||||||
|
|
||||||
The server implements the following capabilities of the language server protocol:
|
The server implements the following capabilities of the language server protocol:
|
||||||
|
|
||||||
@@ -40,6 +40,13 @@ The JSON language server has the following dependencies on the client's capabili
|
|||||||
|
|
||||||
## Configuration
|
## Configuration
|
||||||
|
|
||||||
|
### Initialization options
|
||||||
|
|
||||||
|
The client can send the following initialization options to the server:
|
||||||
|
|
||||||
|
- `provideFormatter: boolean | undefined`. If defined, the value defines wheter the server provides the `documentRangeFormattingProvider` capability on initialization. If undefined, the setting `json.format.enable` is used to determined wheter formatting is provided. The formatter will then be registered through dynamic registration. If the client does not support dynamic registration, no formatter will be available.
|
||||||
|
- `handledSchemaProtocols`: The URI schemas handles by the server. See section `Schema configuration` below.
|
||||||
|
|
||||||
### Settings
|
### Settings
|
||||||
|
|
||||||
Clients may send a `workspace/didChangeConfiguration` notification to notify the server of settings changes.
|
Clients may send a `workspace/didChangeConfiguration` notification to notify the server of settings changes.
|
||||||
@@ -51,7 +58,7 @@ The server supports the following settings:
|
|||||||
|
|
||||||
- json
|
- json
|
||||||
- `format`
|
- `format`
|
||||||
- `enable`: Whether the server should register the formatting support. This option is only applicable if the client supports *dynamicRegistration* for *rangeFormatting*
|
- `enable`: Whether the server should register the formatting support. This option is only applicable if the client supports *dynamicRegistration* for *rangeFormatting* and `initializationOptions.provideFormatter` is not defined.
|
||||||
- `schema`: Configures association of file names to schema URL or schemas and/or associations of schema URL to schema content.
|
- `schema`: Configures association of file names to schema URL or schemas and/or associations of schema URL to schema content.
|
||||||
- `fileMatch`: an array or file names or paths (separated by `/`). `*` can be used as a wildcard.
|
- `fileMatch`: an array or file names or paths (separated by `/`). `*` can be used as a wildcard.
|
||||||
- `url`: The URL of the schema, optional when also a schema is provided.
|
- `url`: The URL of the schema, optional when also a schema is provided.
|
||||||
|
|||||||
@@ -14,8 +14,8 @@
|
|||||||
"dependencies": {
|
"dependencies": {
|
||||||
"jsonc-parser": "^2.1.1",
|
"jsonc-parser": "^2.1.1",
|
||||||
"request-light": "^0.2.4",
|
"request-light": "^0.2.4",
|
||||||
"vscode-json-languageservice": "^3.3.4",
|
"vscode-json-languageservice": "^3.3.5",
|
||||||
"vscode-languageserver": "^5.3.0-next.8",
|
"vscode-languageserver": "^6.0.0-next.1",
|
||||||
"vscode-nls": "^4.1.1",
|
"vscode-nls": "^4.1.1",
|
||||||
"vscode-uri": "^2.0.3"
|
"vscode-uri": "^2.0.3"
|
||||||
},
|
},
|
||||||
|
|||||||
@@ -114,7 +114,7 @@ const documents: TextDocuments = new TextDocuments();
|
|||||||
documents.listen(connection);
|
documents.listen(connection);
|
||||||
|
|
||||||
let clientSnippetSupport = false;
|
let clientSnippetSupport = false;
|
||||||
let clientDynamicRegisterSupport = false;
|
let dynamicFormatterRegistration = false;
|
||||||
let foldingRangeLimit = Number.MAX_VALUE;
|
let foldingRangeLimit = Number.MAX_VALUE;
|
||||||
let hierarchicalDocumentSymbolSupport = false;
|
let hierarchicalDocumentSymbolSupport = false;
|
||||||
|
|
||||||
@@ -144,7 +144,7 @@ connection.onInitialize((params: InitializeParams): InitializeResult => {
|
|||||||
}
|
}
|
||||||
|
|
||||||
clientSnippetSupport = getClientCapability('textDocument.completion.completionItem.snippetSupport', false);
|
clientSnippetSupport = getClientCapability('textDocument.completion.completionItem.snippetSupport', false);
|
||||||
clientDynamicRegisterSupport = getClientCapability('workspace.symbol.dynamicRegistration', false);
|
dynamicFormatterRegistration = getClientCapability('textDocument.rangeFormatting.dynamicRegistration', false) && (params.initializationOptions.provideFormatter === undefined);
|
||||||
foldingRangeLimit = getClientCapability('textDocument.foldingRange.rangeLimit', Number.MAX_VALUE);
|
foldingRangeLimit = getClientCapability('textDocument.foldingRange.rangeLimit', Number.MAX_VALUE);
|
||||||
hierarchicalDocumentSymbolSupport = getClientCapability('textDocument.documentSymbol.hierarchicalDocumentSymbolSupport', false);
|
hierarchicalDocumentSymbolSupport = getClientCapability('textDocument.documentSymbol.hierarchicalDocumentSymbolSupport', false);
|
||||||
const capabilities: ServerCapabilities = {
|
const capabilities: ServerCapabilities = {
|
||||||
@@ -156,7 +156,8 @@ connection.onInitialize((params: InitializeParams): InitializeResult => {
|
|||||||
documentRangeFormattingProvider: false,
|
documentRangeFormattingProvider: false,
|
||||||
colorProvider: {},
|
colorProvider: {},
|
||||||
foldingRangeProvider: true,
|
foldingRangeProvider: true,
|
||||||
selectionRangeProvider: true
|
selectionRangeProvider: true,
|
||||||
|
documentFormattingProvider: params.initializationOptions.provideFormatter === true
|
||||||
};
|
};
|
||||||
|
|
||||||
return { capabilities };
|
return { capabilities };
|
||||||
@@ -195,7 +196,7 @@ connection.onDidChangeConfiguration((change) => {
|
|||||||
updateConfiguration();
|
updateConfiguration();
|
||||||
|
|
||||||
// dynamically enable & disable the formatter
|
// dynamically enable & disable the formatter
|
||||||
if (clientDynamicRegisterSupport) {
|
if (dynamicFormatterRegistration) {
|
||||||
const enableFormatter = settings && settings.json && settings.json.format && settings.json.format.enable;
|
const enableFormatter = settings && settings.json && settings.json.format && settings.json.format.enable;
|
||||||
if (enableFormatter) {
|
if (enableFormatter) {
|
||||||
if (!formatterRegistration) {
|
if (!formatterRegistration) {
|
||||||
|
|||||||
@@ -73,42 +73,41 @@ request-light@^0.2.4:
|
|||||||
https-proxy-agent "^2.2.1"
|
https-proxy-agent "^2.2.1"
|
||||||
vscode-nls "^4.0.0"
|
vscode-nls "^4.0.0"
|
||||||
|
|
||||||
vscode-json-languageservice@^3.3.4:
|
vscode-json-languageservice@^3.3.5:
|
||||||
version "3.3.4"
|
version "3.3.5"
|
||||||
resolved "https://registry.yarnpkg.com/vscode-json-languageservice/-/vscode-json-languageservice-3.3.4.tgz#4ff67580491d3a5dc469f4a78643f20adff0278d"
|
resolved "https://registry.yarnpkg.com/vscode-json-languageservice/-/vscode-json-languageservice-3.3.5.tgz#e222e8391beeb23cfa40cf17fd57d1594d295fc7"
|
||||||
integrity sha512-/nuI4uDBfxyVyeGtBdYwP/tIaXYKOoymUOSozYKLzsmrDmu555gZpzc11LrARa96z92wSaa5hfjTtNMAoM2mxw==
|
integrity sha512-Le6SG5aRdrRc5jVeVMRkYbGH9rrVaZHCW0Oa8zCFQ0T8viUud9qdZ29lSv5NPNLwTB8mn4pYucFyyEPM2YWvLA==
|
||||||
dependencies:
|
dependencies:
|
||||||
jsonc-parser "^2.1.1"
|
jsonc-parser "^2.1.1"
|
||||||
vscode-languageserver-types "^3.15.0-next.2"
|
vscode-languageserver-types "^3.15.0-next.5"
|
||||||
vscode-nls "^4.1.1"
|
vscode-nls "^4.1.1"
|
||||||
vscode-uri "^2.0.3"
|
vscode-uri "^2.0.3"
|
||||||
|
|
||||||
vscode-jsonrpc@^4.1.0-next.2:
|
vscode-jsonrpc@^5.0.0-next.2:
|
||||||
version "4.1.0-next.2"
|
version "5.0.0-next.2"
|
||||||
resolved "https://registry.yarnpkg.com/vscode-jsonrpc/-/vscode-jsonrpc-4.1.0-next.2.tgz#3bd318910a48e631742b290975386e3dae685be3"
|
resolved "https://registry.yarnpkg.com/vscode-jsonrpc/-/vscode-jsonrpc-5.0.0-next.2.tgz#a44bc03f67069e53f8d8beb88b96c0cacbfefbca"
|
||||||
integrity sha512-GsBLjP9DxQ42yl1mW9GEIlnSc0+R8mfzhaebwmmTPEJjezD5SPoAo3DFrIAFZha9yvQ1nzZfZlhtVpGQmgxtXg==
|
integrity sha512-Q3/jabZUNviCG9hhF6hHWjhrABevPF9mv0aiE2j8BYCAP2k+aHTpjMyk+04MzaAqWYwXdQuZkLSbcYCCqbzJLg==
|
||||||
|
|
||||||
vscode-languageserver-protocol@^3.15.0-next.6:
|
vscode-languageserver-protocol@^3.15.0-next.9:
|
||||||
version "3.15.0-next.6"
|
version "3.15.0-next.9"
|
||||||
resolved "https://registry.yarnpkg.com/vscode-languageserver-protocol/-/vscode-languageserver-protocol-3.15.0-next.6.tgz#a8aeb7e7dd65da8216b386db59494cdfd3215d92"
|
resolved "https://registry.yarnpkg.com/vscode-languageserver-protocol/-/vscode-languageserver-protocol-3.15.0-next.9.tgz#e768256bd5b580b25bfbc8099bc03bc4c42ebf30"
|
||||||
integrity sha512-/yDpYlWyNs26mM23mT73xmOFsh1iRfgZfBdHmfAxwDKwpQKLoOSqVidtYfxlK/pD3IEKGcAVnT4WXTsguxxAMQ==
|
integrity sha512-b9PAxouMmtsLEe8ZjbIMPb7wRWPhckGfgjwZLmp/dWnaAuRPYtY3lGO0/rNbLc3jKIqCVlnEyYVFKalzDAzj0g==
|
||||||
dependencies:
|
dependencies:
|
||||||
vscode-jsonrpc "^4.1.0-next.2"
|
vscode-jsonrpc "^5.0.0-next.2"
|
||||||
vscode-languageserver-types "^3.15.0-next.2"
|
vscode-languageserver-types "^3.15.0-next.5"
|
||||||
|
|
||||||
vscode-languageserver-types@^3.15.0-next.2:
|
vscode-languageserver-types@^3.15.0-next.5:
|
||||||
version "3.15.0-next.2"
|
version "3.15.0-next.5"
|
||||||
resolved "https://registry.yarnpkg.com/vscode-languageserver-types/-/vscode-languageserver-types-3.15.0-next.2.tgz#a0601332cdaafac21931f497bb080cfb8d73f254"
|
resolved "https://registry.yarnpkg.com/vscode-languageserver-types/-/vscode-languageserver-types-3.15.0-next.5.tgz#863d711bf47b338ff5e63ae19fb20d4fcd4d713b"
|
||||||
integrity sha512-2JkrMWWUi2rlVLSo9OFR2PIGUzdiowEM8NgNYiwLKnXTjpwpjjIrJbNNxDik7Rv4oo9KtikcFQZKXbrKilL/MQ==
|
integrity sha512-7hrELhTeWieUgex3+6692KjCkcmO/+V/bFItM5MHGcBotzwmjEuXjapLLYTYhIspuJ1ibRSik5MhX5YwLpsPiw==
|
||||||
|
|
||||||
vscode-languageserver@^5.3.0-next.8:
|
vscode-languageserver@^6.0.0-next.1:
|
||||||
version "5.3.0-next.8"
|
version "6.0.0-next.1"
|
||||||
resolved "https://registry.yarnpkg.com/vscode-languageserver/-/vscode-languageserver-5.3.0-next.8.tgz#12a4adf60374dbb93e153e08bdca5525f9b2029f"
|
resolved "https://registry.yarnpkg.com/vscode-languageserver/-/vscode-languageserver-6.0.0-next.1.tgz#4d71886d4a17d22eafc61b3a5fbf84e8e27c191f"
|
||||||
integrity sha512-6vUb96wsRfrFqndril3gct/FBCSc24OxFZ2iz7kuEuXvLaIcEVOcSZIqQK8oFN7PdbAIaa9nnIpKSy4Yd15cIw==
|
integrity sha512-LSF6bXoFeXfMPRNyqzI3yFX/kD2DzXBemqvyj1kDWNVraiWttm4xKF4YXsvJ7Z3s9sVt/Dpu3CFU3w61PGNZMg==
|
||||||
dependencies:
|
dependencies:
|
||||||
vscode-languageserver-protocol "^3.15.0-next.6"
|
vscode-languageserver-protocol "^3.15.0-next.9"
|
||||||
vscode-textbuffer "^1.0.0"
|
vscode-textbuffer "^1.0.0"
|
||||||
vscode-uri "^1.0.6"
|
|
||||||
|
|
||||||
vscode-nls@^4.0.0:
|
vscode-nls@^4.0.0:
|
||||||
version "4.0.0"
|
version "4.0.0"
|
||||||
@@ -125,11 +124,6 @@ vscode-textbuffer@^1.0.0:
|
|||||||
resolved "https://registry.yarnpkg.com/vscode-textbuffer/-/vscode-textbuffer-1.0.0.tgz#1faee638c8e0e4131c8d5c353993a1874acda086"
|
resolved "https://registry.yarnpkg.com/vscode-textbuffer/-/vscode-textbuffer-1.0.0.tgz#1faee638c8e0e4131c8d5c353993a1874acda086"
|
||||||
integrity sha512-zPaHo4urgpwsm+PrJWfNakolRpryNja18SUip/qIIsfhuEqEIPEXMxHOlFPjvDC4JgTaimkncNW7UMXRJTY6ow==
|
integrity sha512-zPaHo4urgpwsm+PrJWfNakolRpryNja18SUip/qIIsfhuEqEIPEXMxHOlFPjvDC4JgTaimkncNW7UMXRJTY6ow==
|
||||||
|
|
||||||
vscode-uri@^1.0.6:
|
|
||||||
version "1.0.6"
|
|
||||||
resolved "https://registry.yarnpkg.com/vscode-uri/-/vscode-uri-1.0.6.tgz#6b8f141b0bbc44ad7b07e94f82f168ac7608ad4d"
|
|
||||||
integrity sha512-sLI2L0uGov3wKVb9EB+vIQBl9tVP90nqRvxSoJ35vI3NjxE8jfsE5DSOhWgSunHSZmKS4OCi2jrtfxK7uyp2ww==
|
|
||||||
|
|
||||||
vscode-uri@^2.0.3:
|
vscode-uri@^2.0.3:
|
||||||
version "2.0.3"
|
version "2.0.3"
|
||||||
resolved "https://registry.yarnpkg.com/vscode-uri/-/vscode-uri-2.0.3.tgz#25e5f37f552fbee3cec7e5f80cef8469cefc6543"
|
resolved "https://registry.yarnpkg.com/vscode-uri/-/vscode-uri-2.0.3.tgz#25e5f37f552fbee3cec7e5f80cef8469cefc6543"
|
||||||
|
|||||||
@@ -101,10 +101,10 @@ semver@^5.3.0:
|
|||||||
resolved "https://registry.yarnpkg.com/semver/-/semver-5.5.0.tgz#dc4bbc7a6ca9d916dee5d43516f0092b58f7b8ab"
|
resolved "https://registry.yarnpkg.com/semver/-/semver-5.5.0.tgz#dc4bbc7a6ca9d916dee5d43516f0092b58f7b8ab"
|
||||||
integrity sha512-4SJ3dm0WAwWy/NVeioZh5AntkdJoWKxHxcmyP622fOkgHa4z3R0TdBJICINyaSDE6uNwVc8gZr+ZinwZAH4xIA==
|
integrity sha512-4SJ3dm0WAwWy/NVeioZh5AntkdJoWKxHxcmyP622fOkgHa4z3R0TdBJICINyaSDE6uNwVc8gZr+ZinwZAH4xIA==
|
||||||
|
|
||||||
semver@^5.5.0:
|
semver@^6.3.0:
|
||||||
version "5.5.1"
|
version "6.3.0"
|
||||||
resolved "https://registry.yarnpkg.com/semver/-/semver-5.5.1.tgz#7dfdd8814bdb7cabc7be0fb1d734cfb66c940477"
|
resolved "https://registry.yarnpkg.com/semver/-/semver-6.3.0.tgz#ee0a64c8af5e8ceea67687b133761e1becbd1d3d"
|
||||||
integrity sha512-PqpAxfrEhlSUWge8dwIp4tZnQ25DIOthpiaHNIthsjEFQD6EvqUKUDM7L8O2rShkFccYo1VjJR0coWfNkCubRw==
|
integrity sha512-b39TBaTSfV6yBrapU89p5fKekE2m/NwnDocOVruQFS1/veMgdzuPcnOM34M6CwxW8jH/lxEa5rBoDeUwu5HHTw==
|
||||||
|
|
||||||
vscode-extension-telemetry@0.1.1:
|
vscode-extension-telemetry@0.1.1:
|
||||||
version "0.1.1"
|
version "0.1.1"
|
||||||
@@ -113,31 +113,31 @@ vscode-extension-telemetry@0.1.1:
|
|||||||
dependencies:
|
dependencies:
|
||||||
applicationinsights "1.0.8"
|
applicationinsights "1.0.8"
|
||||||
|
|
||||||
vscode-jsonrpc@^4.1.0-next.2:
|
vscode-jsonrpc@^5.0.0-next.2:
|
||||||
version "4.1.0-next.2"
|
version "5.0.0-next.2"
|
||||||
resolved "https://registry.yarnpkg.com/vscode-jsonrpc/-/vscode-jsonrpc-4.1.0-next.2.tgz#3bd318910a48e631742b290975386e3dae685be3"
|
resolved "https://registry.yarnpkg.com/vscode-jsonrpc/-/vscode-jsonrpc-5.0.0-next.2.tgz#a44bc03f67069e53f8d8beb88b96c0cacbfefbca"
|
||||||
integrity sha512-GsBLjP9DxQ42yl1mW9GEIlnSc0+R8mfzhaebwmmTPEJjezD5SPoAo3DFrIAFZha9yvQ1nzZfZlhtVpGQmgxtXg==
|
integrity sha512-Q3/jabZUNviCG9hhF6hHWjhrABevPF9mv0aiE2j8BYCAP2k+aHTpjMyk+04MzaAqWYwXdQuZkLSbcYCCqbzJLg==
|
||||||
|
|
||||||
vscode-languageclient@^5.3.0-next.6:
|
vscode-languageclient@^6.0.0-next.1:
|
||||||
version "5.3.0-next.6"
|
version "6.0.0-next.1"
|
||||||
resolved "https://registry.yarnpkg.com/vscode-languageclient/-/vscode-languageclient-5.3.0-next.6.tgz#35e74882781158e8b111911c0953869d3df08777"
|
resolved "https://registry.yarnpkg.com/vscode-languageclient/-/vscode-languageclient-6.0.0-next.1.tgz#deca1743afd20da092e04e40ef73cedbbd978455"
|
||||||
integrity sha512-DxT8+gkenjCjJV6ArcP75/AQfx6HP6m6kHIbacPCpffMeoE1YMLKj6ZixA9J87yr0fMtBmqumLmDeGe7MIF2bw==
|
integrity sha512-eJ9VjLFNINArgRzLbQ11YlWry7dM93GEODkQBXTRfrSypksiO9qSGr4SHhWgxxP26p4FRSpzc/17+N+Egnnchg==
|
||||||
dependencies:
|
dependencies:
|
||||||
semver "^5.5.0"
|
semver "^6.3.0"
|
||||||
vscode-languageserver-protocol "^3.15.0-next.6"
|
vscode-languageserver-protocol "^3.15.0-next.9"
|
||||||
|
|
||||||
vscode-languageserver-protocol@^3.15.0-next.6:
|
vscode-languageserver-protocol@^3.15.0-next.9:
|
||||||
version "3.15.0-next.6"
|
version "3.15.0-next.9"
|
||||||
resolved "https://registry.yarnpkg.com/vscode-languageserver-protocol/-/vscode-languageserver-protocol-3.15.0-next.6.tgz#a8aeb7e7dd65da8216b386db59494cdfd3215d92"
|
resolved "https://registry.yarnpkg.com/vscode-languageserver-protocol/-/vscode-languageserver-protocol-3.15.0-next.9.tgz#e768256bd5b580b25bfbc8099bc03bc4c42ebf30"
|
||||||
integrity sha512-/yDpYlWyNs26mM23mT73xmOFsh1iRfgZfBdHmfAxwDKwpQKLoOSqVidtYfxlK/pD3IEKGcAVnT4WXTsguxxAMQ==
|
integrity sha512-b9PAxouMmtsLEe8ZjbIMPb7wRWPhckGfgjwZLmp/dWnaAuRPYtY3lGO0/rNbLc3jKIqCVlnEyYVFKalzDAzj0g==
|
||||||
dependencies:
|
dependencies:
|
||||||
vscode-jsonrpc "^4.1.0-next.2"
|
vscode-jsonrpc "^5.0.0-next.2"
|
||||||
vscode-languageserver-types "^3.15.0-next.2"
|
vscode-languageserver-types "^3.15.0-next.5"
|
||||||
|
|
||||||
vscode-languageserver-types@^3.15.0-next.2:
|
vscode-languageserver-types@^3.15.0-next.5:
|
||||||
version "3.15.0-next.2"
|
version "3.15.0-next.5"
|
||||||
resolved "https://registry.yarnpkg.com/vscode-languageserver-types/-/vscode-languageserver-types-3.15.0-next.2.tgz#a0601332cdaafac21931f497bb080cfb8d73f254"
|
resolved "https://registry.yarnpkg.com/vscode-languageserver-types/-/vscode-languageserver-types-3.15.0-next.5.tgz#863d711bf47b338ff5e63ae19fb20d4fcd4d713b"
|
||||||
integrity sha512-2JkrMWWUi2rlVLSo9OFR2PIGUzdiowEM8NgNYiwLKnXTjpwpjjIrJbNNxDik7Rv4oo9KtikcFQZKXbrKilL/MQ==
|
integrity sha512-7hrELhTeWieUgex3+6692KjCkcmO/+V/bFItM5MHGcBotzwmjEuXjapLLYTYhIspuJ1ibRSik5MhX5YwLpsPiw==
|
||||||
|
|
||||||
vscode-nls@^4.0.0:
|
vscode-nls@^4.0.0:
|
||||||
version "4.0.0"
|
version "4.0.0"
|
||||||
|
|||||||
@@ -171,8 +171,7 @@
|
|||||||
},
|
},
|
||||||
{
|
{
|
||||||
"scope": [
|
"scope": [
|
||||||
"meta.preprocessor",
|
"meta.preprocessor"
|
||||||
"keyword.control.directive"
|
|
||||||
],
|
],
|
||||||
"settings": {
|
"settings": {
|
||||||
"foreground": "#569cd6"
|
"foreground": "#569cd6"
|
||||||
|
|||||||
@@ -169,8 +169,7 @@
|
|||||||
},
|
},
|
||||||
{
|
{
|
||||||
"scope": [
|
"scope": [
|
||||||
"meta.preprocessor",
|
"meta.preprocessor"
|
||||||
"keyword.control.directive"
|
|
||||||
],
|
],
|
||||||
"settings": {
|
"settings": {
|
||||||
"foreground": "#0000ff"
|
"foreground": "#0000ff"
|
||||||
|
|||||||
@@ -1,3 +1,3 @@
|
|||||||
disturl "http://nodejs.org/dist"
|
disturl "http://nodejs.org/dist"
|
||||||
target "12.4.0"
|
target "10.11.0"
|
||||||
runtime "node"
|
runtime "node"
|
||||||
|
|||||||
@@ -2,7 +2,7 @@
|
|||||||
Name=@@NAME_LONG@@ - URL Handler
|
Name=@@NAME_LONG@@ - URL Handler
|
||||||
Comment=Azure Data Studio
|
Comment=Azure Data Studio
|
||||||
GenericName=Text Editor
|
GenericName=Text Editor
|
||||||
Exec=@@EXEC@@ --no-sandbox --open-url %U
|
Exec=@@EXEC@@ --open-url %U
|
||||||
Icon=@@ICON@@
|
Icon=@@ICON@@
|
||||||
Type=Application
|
Type=Application
|
||||||
NoDisplay=true
|
NoDisplay=true
|
||||||
|
|||||||
@@ -2,7 +2,7 @@
|
|||||||
Name=@@NAME_LONG@@
|
Name=@@NAME_LONG@@
|
||||||
Comment=Data Management Tool that enables you to work with SQL Server, Azure SQL DB and SQL DW from Windows, macOS and Linux.
|
Comment=Data Management Tool that enables you to work with SQL Server, Azure SQL DB and SQL DW from Windows, macOS and Linux.
|
||||||
GenericName=Text Editor
|
GenericName=Text Editor
|
||||||
Exec=@@EXEC@@ --no-sandbox --unity-launch %F
|
Exec=@@EXEC@@ --unity-launch %F
|
||||||
Icon=@@ICON@@
|
Icon=@@ICON@@
|
||||||
Type=Application
|
Type=Application
|
||||||
StartupNotify=false
|
StartupNotify=false
|
||||||
@@ -14,5 +14,5 @@ Keywords=azuredatastudio;
|
|||||||
|
|
||||||
[Desktop Action new-empty-window]
|
[Desktop Action new-empty-window]
|
||||||
Name=New Empty Window
|
Name=New Empty Window
|
||||||
Exec=@@EXEC@@ --no-sandbox --new-window %F
|
Exec=@@EXEC@@ --new-window %F
|
||||||
Icon=@@ICON@@
|
Icon=@@ICON@@
|
||||||
|
|||||||
@@ -8,7 +8,7 @@ if [[ "$OSTYPE" == "darwin"* ]]; then
|
|||||||
else
|
else
|
||||||
ROOT=$(dirname $(dirname $(readlink -f $0)))
|
ROOT=$(dirname $(dirname $(readlink -f $0)))
|
||||||
VSCODEUSERDATADIR=`mktemp -d 2>/dev/null`
|
VSCODEUSERDATADIR=`mktemp -d 2>/dev/null`
|
||||||
LINUX_NO_SANDBOX="--no-sandbox" # Electron 6 introduces a chrome-sandbox that requires root to run. This can fail. Disable sandbox via --no-sandbox.
|
LINUX_NO_SANDBOX=""
|
||||||
fi
|
fi
|
||||||
|
|
||||||
cd $ROOT
|
cd $ROOT
|
||||||
|
|||||||
@@ -34,5 +34,5 @@ else
|
|||||||
cd $ROOT ; \
|
cd $ROOT ; \
|
||||||
ELECTRON_ENABLE_LOGGING=1 \
|
ELECTRON_ENABLE_LOGGING=1 \
|
||||||
"$CODE" \
|
"$CODE" \
|
||||||
test/electron/index.js --no-sandbox "$@" # Electron 6 introduces a chrome-sandbox that requires root to run. This can fail. Disable sandbox via --no-sandbox.
|
test/electron/index.js "$@"
|
||||||
fi
|
fi
|
||||||
|
|||||||
18
src/bootstrap.js
vendored
18
src/bootstrap.js
vendored
@@ -21,7 +21,6 @@ process.on('SIGPIPE', () => {
|
|||||||
//#endregion
|
//#endregion
|
||||||
|
|
||||||
//#region Add support for redirecting the loading of node modules
|
//#region Add support for redirecting the loading of node modules
|
||||||
|
|
||||||
exports.injectNodeModuleLookupPath = function (injectPath) {
|
exports.injectNodeModuleLookupPath = function (injectPath) {
|
||||||
if (!injectPath) {
|
if (!injectPath) {
|
||||||
throw new Error('Missing injectPath');
|
throw new Error('Missing injectPath');
|
||||||
@@ -37,8 +36,10 @@ exports.injectNodeModuleLookupPath = function (injectPath) {
|
|||||||
const originalResolveLookupPaths = Module._resolveLookupPaths;
|
const originalResolveLookupPaths = Module._resolveLookupPaths;
|
||||||
|
|
||||||
// @ts-ignore
|
// @ts-ignore
|
||||||
Module._resolveLookupPaths = function (moduleName, parent) {
|
Module._resolveLookupPaths = function (moduleName, parent, newReturn) {
|
||||||
const paths = originalResolveLookupPaths(moduleName, parent);
|
const result = originalResolveLookupPaths(moduleName, parent, newReturn);
|
||||||
|
|
||||||
|
const paths = newReturn ? result : result[1];
|
||||||
for (let i = 0, len = paths.length; i < len; i++) {
|
for (let i = 0, len = paths.length; i < len; i++) {
|
||||||
if (paths[i] === nodeModulesPath) {
|
if (paths[i] === nodeModulesPath) {
|
||||||
paths.splice(i, 0, injectPath);
|
paths.splice(i, 0, injectPath);
|
||||||
@@ -46,7 +47,7 @@ exports.injectNodeModuleLookupPath = function (injectPath) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return paths;
|
return result;
|
||||||
};
|
};
|
||||||
};
|
};
|
||||||
//#endregion
|
//#endregion
|
||||||
@@ -70,10 +71,11 @@ exports.enableASARSupport = function (nodeModulesPath) {
|
|||||||
|
|
||||||
// @ts-ignore
|
// @ts-ignore
|
||||||
const originalResolveLookupPaths = Module._resolveLookupPaths;
|
const originalResolveLookupPaths = Module._resolveLookupPaths;
|
||||||
|
|
||||||
// @ts-ignore
|
// @ts-ignore
|
||||||
Module._resolveLookupPaths = function (request, parent) {
|
Module._resolveLookupPaths = function (request, parent, newReturn) {
|
||||||
const paths = originalResolveLookupPaths(request, parent);
|
const result = originalResolveLookupPaths(request, parent, newReturn);
|
||||||
|
|
||||||
|
const paths = newReturn ? result : result[1];
|
||||||
for (let i = 0, len = paths.length; i < len; i++) {
|
for (let i = 0, len = paths.length; i < len; i++) {
|
||||||
if (paths[i] === NODE_MODULES_PATH) {
|
if (paths[i] === NODE_MODULES_PATH) {
|
||||||
paths.splice(i, 0, NODE_MODULES_ASAR_PATH);
|
paths.splice(i, 0, NODE_MODULES_ASAR_PATH);
|
||||||
@@ -81,7 +83,7 @@ exports.enableASARSupport = function (nodeModulesPath) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return paths;
|
return result;
|
||||||
};
|
};
|
||||||
};
|
};
|
||||||
//#endregion
|
//#endregion
|
||||||
|
|||||||
@@ -17,7 +17,7 @@ const paths = require('./paths');
|
|||||||
// @ts-ignore
|
// @ts-ignore
|
||||||
const product = require('../product.json');
|
const product = require('../product.json');
|
||||||
// @ts-ignore
|
// @ts-ignore
|
||||||
const { app, protocol } = require('electron');
|
const app = require('electron').app;
|
||||||
|
|
||||||
// Enable portable support
|
// Enable portable support
|
||||||
const portable = bootstrap.configurePortable();
|
const portable = bootstrap.configurePortable();
|
||||||
@@ -33,11 +33,6 @@ app.setPath('userData', userDataPath);
|
|||||||
// Update cwd based on environment and platform
|
// Update cwd based on environment and platform
|
||||||
setCurrentWorkingDirectory();
|
setCurrentWorkingDirectory();
|
||||||
|
|
||||||
// Register custom schemes with privileges
|
|
||||||
protocol.registerSchemesAsPrivileged([
|
|
||||||
{ scheme: 'vscode-resource', privileges: { secure: true, supportFetchAPI: true, corsEnabled: true } }
|
|
||||||
]);
|
|
||||||
|
|
||||||
// Global app listeners
|
// Global app listeners
|
||||||
registerListeners();
|
registerListeners();
|
||||||
|
|
||||||
|
|||||||
12
src/sql/workbench/browser/enablePreviewFeatures.ts
Normal file
12
src/sql/workbench/browser/enablePreviewFeatures.ts
Normal file
@@ -0,0 +1,12 @@
|
|||||||
|
/*---------------------------------------------------------------------------------------------
|
||||||
|
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||||
|
* Licensed under the Source EULA. See License.txt in the project root for license information.
|
||||||
|
*--------------------------------------------------------------------------------------------*/
|
||||||
|
|
||||||
|
import { AbstractEnablePreviewFeatures } from 'sql/workbench/common/enablePreviewFeatures';
|
||||||
|
|
||||||
|
export class BrowserEnablePreviewFeatures extends AbstractEnablePreviewFeatures {
|
||||||
|
protected async getWindowCount(): Promise<number> {
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -11,7 +11,7 @@ import { onUnexpectedError } from 'vs/base/common/errors';
|
|||||||
import { IConfigurationService } from 'vs/platform/configuration/common/configuration';
|
import { IConfigurationService } from 'vs/platform/configuration/common/configuration';
|
||||||
import { IHostService } from 'vs/workbench/services/host/browser/host';
|
import { IHostService } from 'vs/workbench/services/host/browser/host';
|
||||||
|
|
||||||
export class EnablePreviewFeatures implements IWorkbenchContribution {
|
export abstract class AbstractEnablePreviewFeatures implements IWorkbenchContribution {
|
||||||
|
|
||||||
private static ENABLE_PREVIEW_FEATURES_SHOWN = 'workbench.enablePreviewFeaturesShown';
|
private static ENABLE_PREVIEW_FEATURES_SHOWN = 'workbench.enablePreviewFeaturesShown';
|
||||||
|
|
||||||
@@ -22,12 +22,12 @@ export class EnablePreviewFeatures implements IWorkbenchContribution {
|
|||||||
@IConfigurationService configurationService: IConfigurationService
|
@IConfigurationService configurationService: IConfigurationService
|
||||||
) {
|
) {
|
||||||
let previewFeaturesEnabled = configurationService.getValue('workbench')['enablePreviewFeatures'];
|
let previewFeaturesEnabled = configurationService.getValue('workbench')['enablePreviewFeatures'];
|
||||||
if (previewFeaturesEnabled || storageService.get(EnablePreviewFeatures.ENABLE_PREVIEW_FEATURES_SHOWN, StorageScope.GLOBAL)) {
|
if (previewFeaturesEnabled || storageService.get(AbstractEnablePreviewFeatures.ENABLE_PREVIEW_FEATURES_SHOWN, StorageScope.GLOBAL)) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
Promise.all([
|
Promise.all([
|
||||||
hostService.hasFocus,
|
hostService.hasFocus,
|
||||||
hostService.windowCount
|
this.getWindowCount()
|
||||||
]).then(([focused, count]) => {
|
]).then(([focused, count]) => {
|
||||||
if (!focused && count > 1) {
|
if (!focused && count > 1) {
|
||||||
return null;
|
return null;
|
||||||
@@ -42,7 +42,7 @@ export class EnablePreviewFeatures implements IWorkbenchContribution {
|
|||||||
label: localize('enablePreviewFeatures.yes', "Yes"),
|
label: localize('enablePreviewFeatures.yes', "Yes"),
|
||||||
run: () => {
|
run: () => {
|
||||||
configurationService.updateValue('workbench.enablePreviewFeatures', true);
|
configurationService.updateValue('workbench.enablePreviewFeatures', true);
|
||||||
storageService.store(EnablePreviewFeatures.ENABLE_PREVIEW_FEATURES_SHOWN, true, StorageScope.GLOBAL);
|
storageService.store(AbstractEnablePreviewFeatures.ENABLE_PREVIEW_FEATURES_SHOWN, true, StorageScope.GLOBAL);
|
||||||
}
|
}
|
||||||
}, {
|
}, {
|
||||||
label: localize('enablePreviewFeatures.no', "No"),
|
label: localize('enablePreviewFeatures.no', "No"),
|
||||||
@@ -53,7 +53,7 @@ export class EnablePreviewFeatures implements IWorkbenchContribution {
|
|||||||
label: localize('enablePreviewFeatures.never', "No, don't show again"),
|
label: localize('enablePreviewFeatures.never', "No, don't show again"),
|
||||||
run: () => {
|
run: () => {
|
||||||
configurationService.updateValue('workbench.enablePreviewFeatures', false);
|
configurationService.updateValue('workbench.enablePreviewFeatures', false);
|
||||||
storageService.store(EnablePreviewFeatures.ENABLE_PREVIEW_FEATURES_SHOWN, true, StorageScope.GLOBAL);
|
storageService.store(AbstractEnablePreviewFeatures.ENABLE_PREVIEW_FEATURES_SHOWN, true, StorageScope.GLOBAL);
|
||||||
},
|
},
|
||||||
isSecondary: true
|
isSecondary: true
|
||||||
}]
|
}]
|
||||||
@@ -61,4 +61,6 @@ export class EnablePreviewFeatures implements IWorkbenchContribution {
|
|||||||
})
|
})
|
||||||
.then(null, onUnexpectedError);
|
.then(null, onUnexpectedError);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
protected abstract getWindowCount(): Promise<number>;
|
||||||
}
|
}
|
||||||
|
|||||||
27
src/sql/workbench/electron-browser/enablePreviewFeatures.ts
Normal file
27
src/sql/workbench/electron-browser/enablePreviewFeatures.ts
Normal file
@@ -0,0 +1,27 @@
|
|||||||
|
/*---------------------------------------------------------------------------------------------
|
||||||
|
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||||
|
* Licensed under the Source EULA. See License.txt in the project root for license information.
|
||||||
|
*--------------------------------------------------------------------------------------------*/
|
||||||
|
|
||||||
|
import { AbstractEnablePreviewFeatures } from 'sql/workbench/common/enablePreviewFeatures';
|
||||||
|
import { IStorageService } from 'vs/platform/storage/common/storage';
|
||||||
|
import { INotificationService } from 'vs/platform/notification/common/notification';
|
||||||
|
import { IHostService } from 'vs/workbench/services/host/browser/host';
|
||||||
|
import { IConfigurationService } from 'vs/platform/configuration/common/configuration';
|
||||||
|
import { IElectronService } from 'vs/platform/electron/node/electron';
|
||||||
|
|
||||||
|
export class NativeEnablePreviewFeatures extends AbstractEnablePreviewFeatures {
|
||||||
|
|
||||||
|
constructor(
|
||||||
|
@IStorageService storageService: IStorageService,
|
||||||
|
@INotificationService notificationService: INotificationService,
|
||||||
|
@IHostService hostService: IHostService,
|
||||||
|
@IConfigurationService configurationService: IConfigurationService,
|
||||||
|
@IElectronService private readonly electronService: IElectronService
|
||||||
|
) {
|
||||||
|
super(storageService, notificationService, hostService, configurationService);
|
||||||
|
}
|
||||||
|
protected getWindowCount(): Promise<number> {
|
||||||
|
return this.electronService.getWindowCount();
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -138,7 +138,7 @@ registerAction({
|
|||||||
await workspaceEditingService.addFolders(folders.map(folder => ({ uri: folder })));
|
await workspaceEditingService.addFolders(folders.map(folder => ({ uri: folder })));
|
||||||
await viewletService.openViewlet(viewletService.getDefaultViewletId(), true);
|
await viewletService.openViewlet(viewletService.getDefaultViewletId(), true);
|
||||||
if (options.forceNewWindow) {
|
if (options.forceNewWindow) {
|
||||||
return hostService.openInWindow([{ folderUri: folders[0] }], { forceNewWindow: options.forceNewWindow });
|
return hostService.openWindow([{ folderUri: folders[0] }], { forceNewWindow: options.forceNewWindow });
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
return hostService.reload();
|
return hostService.reload();
|
||||||
|
|||||||
@@ -4,10 +4,10 @@
|
|||||||
*--------------------------------------------------------------------------------------------*/
|
*--------------------------------------------------------------------------------------------*/
|
||||||
|
|
||||||
import { Registry } from 'vs/platform/registry/common/platform';
|
import { Registry } from 'vs/platform/registry/common/platform';
|
||||||
import { OpenWelcomePageInBrowser } from './openWebsite';
|
|
||||||
import { IWorkbenchContributionsRegistry, Extensions as WorkbenchExtensions } from 'vs/workbench/common/contributions';
|
import { IWorkbenchContributionsRegistry, Extensions as WorkbenchExtensions } from 'vs/workbench/common/contributions';
|
||||||
import { LifecyclePhase } from 'vs/platform/lifecycle/common/lifecycle';
|
import { LifecyclePhase } from 'vs/platform/lifecycle/common/lifecycle';
|
||||||
|
import { BrowserEnablePreviewFeatures } from 'sql/workbench/browser/enablePreviewFeatures';
|
||||||
|
|
||||||
Registry
|
Registry
|
||||||
.as<IWorkbenchContributionsRegistry>(WorkbenchExtensions.Workbench)
|
.as<IWorkbenchContributionsRegistry>(WorkbenchExtensions.Workbench)
|
||||||
.registerWorkbenchContribution(OpenWelcomePageInBrowser, LifecyclePhase.Restored);
|
.registerWorkbenchContribution(BrowserEnablePreviewFeatures, LifecyclePhase.Eventually);
|
||||||
@@ -0,0 +1,13 @@
|
|||||||
|
/*---------------------------------------------------------------------------------------------
|
||||||
|
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||||
|
* Licensed under the Source EULA. See License.txt in the project root for license information.
|
||||||
|
*--------------------------------------------------------------------------------------------*/
|
||||||
|
|
||||||
|
import { Registry } from 'vs/platform/registry/common/platform';
|
||||||
|
import { IWorkbenchContributionsRegistry, Extensions as WorkbenchExtensions } from 'vs/workbench/common/contributions';
|
||||||
|
import { LifecyclePhase } from 'vs/platform/lifecycle/common/lifecycle';
|
||||||
|
import { NativeEnablePreviewFeatures } from 'sql/workbench/electron-browser/enablePreviewFeatures';
|
||||||
|
|
||||||
|
Registry
|
||||||
|
.as<IWorkbenchContributionsRegistry>(WorkbenchExtensions.Workbench)
|
||||||
|
.registerWorkbenchContribution(NativeEnablePreviewFeatures, LifecyclePhase.Eventually);
|
||||||
@@ -14,7 +14,7 @@
|
|||||||
"./sql/azdata.d.ts",
|
"./sql/azdata.d.ts",
|
||||||
"./sql/azdata.proposed.d.ts",
|
"./sql/azdata.proposed.d.ts",
|
||||||
"./vs/base/**/*.ts",
|
"./vs/base/**/*.ts",
|
||||||
"./vs/platform/**/*.ts",
|
// "./vs/platform/**/*.ts",
|
||||||
"./sql/base/**/*.ts",
|
"./sql/base/**/*.ts",
|
||||||
"./sql/editor/**/*.ts",
|
"./sql/editor/**/*.ts",
|
||||||
"./sql/platform/angularEventing/**/*.ts",
|
"./sql/platform/angularEventing/**/*.ts",
|
||||||
|
|||||||
1737
src/typings/electron.d.ts
vendored
1737
src/typings/electron.d.ts
vendored
File diff suppressed because it is too large
Load Diff
@@ -9,7 +9,7 @@ import { onUnexpectedError } from 'vs/base/common/errors';
|
|||||||
import { IMarkdownString, parseHrefAndDimensions, removeMarkdownEscapes } from 'vs/base/common/htmlContent';
|
import { IMarkdownString, parseHrefAndDimensions, removeMarkdownEscapes } from 'vs/base/common/htmlContent';
|
||||||
import { defaultGenerator } from 'vs/base/common/idGenerator';
|
import { defaultGenerator } from 'vs/base/common/idGenerator';
|
||||||
import * as marked from 'vs/base/common/marked/marked';
|
import * as marked from 'vs/base/common/marked/marked';
|
||||||
import * as insane from 'vs/base/common/insane/insane';
|
import { insane } from 'vs/base/common/insane/insane';
|
||||||
import { parse } from 'vs/base/common/marshalling';
|
import { parse } from 'vs/base/common/marshalling';
|
||||||
import { cloneAndChange } from 'vs/base/common/objects';
|
import { cloneAndChange } from 'vs/base/common/objects';
|
||||||
import { escape } from 'vs/base/common/strings';
|
import { escape } from 'vs/base/common/strings';
|
||||||
|
|||||||
@@ -152,34 +152,48 @@ export class StandardWheelEvent {
|
|||||||
this.deltaX = deltaX;
|
this.deltaX = deltaX;
|
||||||
|
|
||||||
if (e) {
|
if (e) {
|
||||||
let e1 = <IWebKitMouseWheelEvent><any>e;
|
if (e.type === 'wheel') {
|
||||||
let e2 = <IGeckoMouseWheelEvent><any>e;
|
|
||||||
|
|
||||||
// vertical delta scroll
|
// Modern wheel event
|
||||||
if (typeof e1.wheelDeltaY !== 'undefined') {
|
// https://developer.mozilla.org/en-US/docs/Web/API/WheelEvent
|
||||||
this.deltaY = e1.wheelDeltaY / 120;
|
const ev = <WheelEvent><unknown>e;
|
||||||
} else if (typeof e2.VERTICAL_AXIS !== 'undefined' && e2.axis === e2.VERTICAL_AXIS) {
|
|
||||||
this.deltaY = -e2.detail / 3;
|
|
||||||
} else {
|
|
||||||
this.deltaY = -e.deltaY / 40;
|
|
||||||
}
|
|
||||||
|
|
||||||
// horizontal delta scroll
|
if (ev.deltaMode === ev.DOM_DELTA_LINE) {
|
||||||
if (typeof e1.wheelDeltaX !== 'undefined') {
|
// the deltas are expressed in lines
|
||||||
if (browser.isSafari && platform.isWindows) {
|
this.deltaY = -e.deltaY;
|
||||||
this.deltaX = - (e1.wheelDeltaX / 120);
|
this.deltaX = -e.deltaX;
|
||||||
} else {
|
} else {
|
||||||
this.deltaX = e1.wheelDeltaX / 120;
|
this.deltaY = -e.deltaY / 40;
|
||||||
|
this.deltaX = -e.deltaX / 40;
|
||||||
}
|
}
|
||||||
} else if (typeof e2.HORIZONTAL_AXIS !== 'undefined' && e2.axis === e2.HORIZONTAL_AXIS) {
|
|
||||||
this.deltaX = -e.detail / 3;
|
|
||||||
} else {
|
|
||||||
this.deltaX = -e.deltaX / 40;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Assume a vertical scroll if nothing else worked
|
} else {
|
||||||
if (this.deltaY === 0 && this.deltaX === 0 && e.wheelDelta) {
|
// Old (deprecated) wheel events
|
||||||
this.deltaY = e.wheelDelta / 120;
|
let e1 = <IWebKitMouseWheelEvent><any>e;
|
||||||
|
let e2 = <IGeckoMouseWheelEvent><any>e;
|
||||||
|
|
||||||
|
// vertical delta scroll
|
||||||
|
if (typeof e1.wheelDeltaY !== 'undefined') {
|
||||||
|
this.deltaY = e1.wheelDeltaY / 120;
|
||||||
|
} else if (typeof e2.VERTICAL_AXIS !== 'undefined' && e2.axis === e2.VERTICAL_AXIS) {
|
||||||
|
this.deltaY = -e2.detail / 3;
|
||||||
|
}
|
||||||
|
|
||||||
|
// horizontal delta scroll
|
||||||
|
if (typeof e1.wheelDeltaX !== 'undefined') {
|
||||||
|
if (browser.isSafari && platform.isWindows) {
|
||||||
|
this.deltaX = - (e1.wheelDeltaX / 120);
|
||||||
|
} else {
|
||||||
|
this.deltaX = e1.wheelDeltaX / 120;
|
||||||
|
}
|
||||||
|
} else if (typeof e2.HORIZONTAL_AXIS !== 'undefined' && e2.axis === e2.HORIZONTAL_AXIS) {
|
||||||
|
this.deltaX = -e.detail / 3;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Assume a vertical scroll if nothing else worked
|
||||||
|
if (this.deltaY === 0 && this.deltaX === 0 && e.wheelDelta) {
|
||||||
|
this.deltaY = e.wheelDelta / 120;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -86,15 +86,21 @@ export class Gesture extends Disposable {
|
|||||||
this._register(DomUtils.addDisposableListener(document, 'touchmove', (e: TouchEvent) => this.onTouchMove(e)));
|
this._register(DomUtils.addDisposableListener(document, 'touchmove', (e: TouchEvent) => this.onTouchMove(e)));
|
||||||
}
|
}
|
||||||
|
|
||||||
public static addTarget(element: HTMLElement): void {
|
public static addTarget(element: HTMLElement): IDisposable {
|
||||||
if (!Gesture.isTouchDevice()) {
|
if (!Gesture.isTouchDevice()) {
|
||||||
return;
|
return Disposable.None;
|
||||||
}
|
}
|
||||||
if (!Gesture.INSTANCE) {
|
if (!Gesture.INSTANCE) {
|
||||||
Gesture.INSTANCE = new Gesture();
|
Gesture.INSTANCE = new Gesture();
|
||||||
}
|
}
|
||||||
|
|
||||||
Gesture.INSTANCE.targets.push(element);
|
Gesture.INSTANCE.targets.push(element);
|
||||||
|
|
||||||
|
return {
|
||||||
|
dispose: () => {
|
||||||
|
Gesture.INSTANCE.targets = Gesture.INSTANCE.targets.filter(t => t !== element);
|
||||||
|
}
|
||||||
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
@memoize
|
@memoize
|
||||||
|
|||||||
@@ -103,7 +103,7 @@ export class BaseActionViewItem extends Disposable implements IActionViewItem {
|
|||||||
|
|
||||||
render(container: HTMLElement): void {
|
render(container: HTMLElement): void {
|
||||||
this.element = container;
|
this.element = container;
|
||||||
Gesture.addTarget(container);
|
this._register(Gesture.addTarget(container));
|
||||||
|
|
||||||
const enableDragging = this.options && this.options.draggable;
|
const enableDragging = this.options && this.options.draggable;
|
||||||
if (enableDragging) {
|
if (enableDragging) {
|
||||||
|
|||||||
@@ -63,7 +63,7 @@ export class Button extends Disposable {
|
|||||||
|
|
||||||
container.appendChild(this._element);
|
container.appendChild(this._element);
|
||||||
|
|
||||||
Gesture.addTarget(this._element);
|
this._register(Gesture.addTarget(this._element));
|
||||||
|
|
||||||
[DOM.EventType.CLICK, EventType.Tap].forEach(eventType => {
|
[DOM.EventType.CLICK, EventType.Tap].forEach(eventType => {
|
||||||
this._register(DOM.addDisposableListener(this._element, eventType, e => {
|
this._register(DOM.addDisposableListener(this._element, eventType, e => {
|
||||||
|
|||||||
@@ -83,7 +83,7 @@ export class BaseDropdown extends ActionRunner {
|
|||||||
this._register(cleanupFn);
|
this._register(cleanupFn);
|
||||||
}
|
}
|
||||||
|
|
||||||
Gesture.addTarget(this._label);
|
this._register(Gesture.addTarget(this._label));
|
||||||
}
|
}
|
||||||
|
|
||||||
get element(): HTMLElement {
|
get element(): HTMLElement {
|
||||||
|
|||||||
@@ -236,7 +236,7 @@ export class ListView<T> implements ISpliceable<T>, IDisposable {
|
|||||||
|
|
||||||
this.rowsContainer = document.createElement('div');
|
this.rowsContainer = document.createElement('div');
|
||||||
this.rowsContainer.className = 'monaco-list-rows';
|
this.rowsContainer.className = 'monaco-list-rows';
|
||||||
Gesture.addTarget(this.rowsContainer);
|
this.disposables.add(Gesture.addTarget(this.rowsContainer));
|
||||||
|
|
||||||
this.scrollableElement = this.disposables.add(new ScrollableElement(this.rowsContainer, {
|
this.scrollableElement = this.disposables.add(new ScrollableElement(this.rowsContainer, {
|
||||||
alwaysConsumeMouseWheel: true,
|
alwaysConsumeMouseWheel: true,
|
||||||
|
|||||||
@@ -542,7 +542,7 @@ export class MouseController<T> implements IDisposable {
|
|||||||
list.onContextMenu(this.onContextMenu, this, this.disposables);
|
list.onContextMenu(this.onContextMenu, this, this.disposables);
|
||||||
list.onMouseDblClick(this.onDoubleClick, this, this.disposables);
|
list.onMouseDblClick(this.onDoubleClick, this, this.disposables);
|
||||||
list.onTouchStart(this.onMouseDown, this, this.disposables);
|
list.onTouchStart(this.onMouseDown, this, this.disposables);
|
||||||
Gesture.addTarget(list.getHTMLElement());
|
this.disposables.add(Gesture.addTarget(list.getHTMLElement()));
|
||||||
}
|
}
|
||||||
|
|
||||||
list.onMouseClick(this.onPointer, this, this.disposables);
|
list.onMouseClick(this.onPointer, this, this.disposables);
|
||||||
|
|||||||
@@ -398,7 +398,7 @@ class BaseMenuActionViewItem extends BaseActionViewItem {
|
|||||||
EventHelper.stop(e, true);
|
EventHelper.stop(e, true);
|
||||||
this.onClick(e);
|
this.onClick(e);
|
||||||
}));
|
}));
|
||||||
}, 50);
|
}, 100);
|
||||||
|
|
||||||
this._register(this.runOnceToEnableMouseUp);
|
this._register(this.runOnceToEnableMouseUp);
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -238,7 +238,7 @@ export class MenuBar extends Disposable {
|
|||||||
}
|
}
|
||||||
}));
|
}));
|
||||||
|
|
||||||
Gesture.addTarget(buttonElement);
|
this._register(Gesture.addTarget(buttonElement));
|
||||||
this._register(DOM.addDisposableListener(buttonElement, EventType.Tap, (e: GestureEvent) => {
|
this._register(DOM.addDisposableListener(buttonElement, EventType.Tap, (e: GestureEvent) => {
|
||||||
// Ignore this touch if the menu is touched
|
// Ignore this touch if the menu is touched
|
||||||
if (this.isOpen && this.focusedMenu && this.focusedMenu.holder && DOM.isAncestor(e.initialTarget as HTMLElement, this.focusedMenu.holder)) {
|
if (this.isOpen && this.focusedMenu && this.focusedMenu.holder && DOM.isAncestor(e.initialTarget as HTMLElement, this.focusedMenu.holder)) {
|
||||||
@@ -322,7 +322,7 @@ export class MenuBar extends Disposable {
|
|||||||
}
|
}
|
||||||
}));
|
}));
|
||||||
|
|
||||||
Gesture.addTarget(buttonElement);
|
this._register(Gesture.addTarget(buttonElement));
|
||||||
this._register(DOM.addDisposableListener(buttonElement, EventType.Tap, (e: GestureEvent) => {
|
this._register(DOM.addDisposableListener(buttonElement, EventType.Tap, (e: GestureEvent) => {
|
||||||
// Ignore this touch if the menu is touched
|
// Ignore this touch if the menu is touched
|
||||||
if (this.isOpen && this.focusedMenu && this.focusedMenu.holder && DOM.isAncestor(e.initialTarget as HTMLElement, this.focusedMenu.holder)) {
|
if (this.isOpen && this.focusedMenu && this.focusedMenu.holder && DOM.isAncestor(e.initialTarget as HTMLElement, this.focusedMenu.holder)) {
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
@font-face {
|
@font-face {
|
||||||
font-family: "octicons";
|
font-family: "octicons";
|
||||||
src: url("./octicons.ttf?628f71ee09945d25ba5fceb0c17f7b0f") format("truetype");
|
src: url("./octicons.ttf?1829db8570ee0fa5a4bef3bb41d5f62e") format("truetype");
|
||||||
}
|
}
|
||||||
|
|
||||||
.octicon, .mega-octicon {
|
.octicon, .mega-octicon {
|
||||||
|
|||||||
Binary file not shown.
@@ -139,7 +139,7 @@ export class Sash extends Disposable {
|
|||||||
this._register(domEvent(this.el, 'mousedown')(this.onMouseDown, this));
|
this._register(domEvent(this.el, 'mousedown')(this.onMouseDown, this));
|
||||||
this._register(domEvent(this.el, 'dblclick')(this.onMouseDoubleClick, this));
|
this._register(domEvent(this.el, 'dblclick')(this.onMouseDoubleClick, this));
|
||||||
|
|
||||||
Gesture.addTarget(this.el);
|
this._register(Gesture.addTarget(this.el));
|
||||||
this._register(domEvent(this.el, EventType.Start)(this.onTouchStart, this));
|
this._register(domEvent(this.el, EventType.Start)(this.onTouchStart, this));
|
||||||
|
|
||||||
if (isIPad) {
|
if (isIPad) {
|
||||||
|
|||||||
@@ -23,7 +23,10 @@ export class MarkdownString implements IMarkdownString {
|
|||||||
|
|
||||||
appendText(value: string): MarkdownString {
|
appendText(value: string): MarkdownString {
|
||||||
// escape markdown syntax tokens: http://daringfireball.net/projects/markdown/syntax#backslash
|
// escape markdown syntax tokens: http://daringfireball.net/projects/markdown/syntax#backslash
|
||||||
this.value += value.replace(/[\\`*_{}[\]()#+\-.!]/g, '\\$&');
|
this.value += value
|
||||||
|
.replace(/[\\`*_{}[\]()#+\-.!]/g, '\\$&')
|
||||||
|
.replace('\n', '\n\n');
|
||||||
|
|
||||||
return this;
|
return this;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
8
src/vs/base/common/insane/insane.d.ts
vendored
8
src/vs/base/common/insane/insane.d.ts
vendored
@@ -3,11 +3,7 @@
|
|||||||
* Licensed under the Source EULA. See License.txt in the project root for license information.
|
* Licensed under the Source EULA. See License.txt in the project root for license information.
|
||||||
*--------------------------------------------------------------------------------------------*/
|
*--------------------------------------------------------------------------------------------*/
|
||||||
|
|
||||||
export as namespace insane;
|
export function insane(
|
||||||
|
|
||||||
export = insane;
|
|
||||||
|
|
||||||
declare function insane(
|
|
||||||
html: string,
|
html: string,
|
||||||
options?: {
|
options?: {
|
||||||
readonly allowedSchemes?: readonly string[],
|
readonly allowedSchemes?: readonly string[],
|
||||||
@@ -16,5 +12,3 @@ declare function insane(
|
|||||||
},
|
},
|
||||||
strict?: boolean,
|
strict?: boolean,
|
||||||
): string;
|
): string;
|
||||||
|
|
||||||
declare namespace insane { }
|
|
||||||
|
|||||||
@@ -21,11 +21,7 @@ IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
|
|||||||
CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
// ESM-comment-begin
|
let __insane_func;
|
||||||
let __insane_exports;
|
|
||||||
// ESM-comment-end
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
(function () { function r(e, n, t) { function o(i, f) { if (!n[i]) { if (!e[i]) { var c = "function" == typeof require && require; if (!f && c) return c(i, !0); if (u) return u(i, !0); var a = new Error("Cannot find module '" + i + "'"); throw a.code = "MODULE_NOT_FOUND", a } var p = n[i] = { exports: {} }; e[i][0].call(p.exports, function (r) { var n = e[i][1][r]; return o(n || r) }, p, p.exports, r, e, n, t) } return n[i].exports } for (var u = "function" == typeof require && require, i = 0; i < t.length; i++)o(t[i]); return o } return r })()({
|
(function () { function r(e, n, t) { function o(i, f) { if (!n[i]) { if (!e[i]) { var c = "function" == typeof require && require; if (!f && c) return c(i, !0); if (u) return u(i, !0); var a = new Error("Cannot find module '" + i + "'"); throw a.code = "MODULE_NOT_FOUND", a } var p = n[i] = { exports: {} }; e[i][0].call(p.exports, function (r) { var n = e[i][1][r]; return o(n || r) }, p, p.exports, r, e, n, t) } return n[i].exports } for (var u = "function" == typeof require && require, i = 0; i < t.length; i++)o(t[i]); return o } return r })()({
|
||||||
1: [function (require, module, exports) {
|
1: [function (require, module, exports) {
|
||||||
@@ -92,7 +88,7 @@ let __insane_exports;
|
|||||||
|
|
||||||
insane.defaults = defaults;
|
insane.defaults = defaults;
|
||||||
module.exports = insane;
|
module.exports = insane;
|
||||||
__insane_exports = insane;
|
__insane_func = insane;
|
||||||
|
|
||||||
}, { "./defaults": 2, "./parser": 7, "./sanitizer": 8, "assignment": 6, "he": 9 }], 5: [function (require, module, exports) {
|
}, { "./defaults": 2, "./parser": 7, "./sanitizer": 8, "assignment": 6, "he": 9 }], 5: [function (require, module, exports) {
|
||||||
'use strict';
|
'use strict';
|
||||||
@@ -469,10 +465,10 @@ let __insane_exports;
|
|||||||
}, {}]
|
}, {}]
|
||||||
}, {}, [4]);
|
}, {}, [4]);
|
||||||
|
|
||||||
// BEGIN MONACOCHANGE
|
|
||||||
// __marked_exports = marked;
|
|
||||||
// }).call(this);
|
|
||||||
|
|
||||||
// ESM-comment-begin
|
// ESM-comment-begin
|
||||||
define(function() { return __insane_exports; });
|
define(function() { return { insane: __insane_func }; });
|
||||||
// ESM-comment-end
|
// ESM-comment-end
|
||||||
|
|
||||||
|
// ESM-uncomment-begin
|
||||||
|
// export var insane = __insane_func;
|
||||||
|
// ESM-uncomment-end
|
||||||
|
|||||||
@@ -92,7 +92,10 @@ class RemoteAuthoritiesImpl {
|
|||||||
return this._delegate(uri);
|
return this._delegate(uri);
|
||||||
}
|
}
|
||||||
const authority = uri.authority;
|
const authority = uri.authority;
|
||||||
const host = this._hosts[authority];
|
let host = this._hosts[authority];
|
||||||
|
if (host.indexOf(':') !== -1) {
|
||||||
|
host = `[${host}]`;
|
||||||
|
}
|
||||||
const port = this._ports[authority];
|
const port = this._ports[authority];
|
||||||
const connectionToken = this._connectionTokens[authority];
|
const connectionToken = this._connectionTokens[authority];
|
||||||
return URI.from({
|
return URI.from({
|
||||||
|
|||||||
@@ -3,7 +3,7 @@
|
|||||||
* Licensed under the Source EULA. See License.txt in the project root for license information.
|
* Licensed under the Source EULA. See License.txt in the project root for license information.
|
||||||
*--------------------------------------------------------------------------------------------*/
|
*--------------------------------------------------------------------------------------------*/
|
||||||
|
|
||||||
import { Menu, MenuItem, BrowserWindow, ipcMain, IpcMainEvent } from 'electron';
|
import { Menu, MenuItem, BrowserWindow, ipcMain, Event as IpcMainEvent } from 'electron';
|
||||||
import { ISerializableContextMenuItem, CONTEXT_MENU_CLOSE_CHANNEL, CONTEXT_MENU_CHANNEL, IPopupOptions } from 'vs/base/parts/contextmenu/common/contextmenu';
|
import { ISerializableContextMenuItem, CONTEXT_MENU_CLOSE_CHANNEL, CONTEXT_MENU_CHANNEL, IPopupOptions } from 'vs/base/parts/contextmenu/common/contextmenu';
|
||||||
|
|
||||||
export function registerContextMenuListener(): void {
|
export function registerContextMenuListener(): void {
|
||||||
|
|||||||
@@ -437,6 +437,7 @@ export class TreeView extends HeightMap {
|
|||||||
private shouldInvalidateDropReaction: boolean;
|
private shouldInvalidateDropReaction: boolean;
|
||||||
private currentDropTargets: ViewItem[] | null = null;
|
private currentDropTargets: ViewItem[] | null = null;
|
||||||
private currentDropDisposable: Lifecycle.IDisposable = Lifecycle.Disposable.None;
|
private currentDropDisposable: Lifecycle.IDisposable = Lifecycle.Disposable.None;
|
||||||
|
private gestureDisposable: Lifecycle.IDisposable = Lifecycle.Disposable.None;
|
||||||
private dragAndDropScrollInterval: number | null = null;
|
private dragAndDropScrollInterval: number | null = null;
|
||||||
private dragAndDropScrollTimeout: number | null = null;
|
private dragAndDropScrollTimeout: number | null = null;
|
||||||
private dragAndDropMouseY: number | null = null;
|
private dragAndDropMouseY: number | null = null;
|
||||||
@@ -523,7 +524,7 @@ export class TreeView extends HeightMap {
|
|||||||
this.wrapper.style.msTouchAction = 'none';
|
this.wrapper.style.msTouchAction = 'none';
|
||||||
this.wrapper.style.msContentZooming = 'none';
|
this.wrapper.style.msContentZooming = 'none';
|
||||||
} else {
|
} else {
|
||||||
Touch.Gesture.addTarget(this.wrapper);
|
this.gestureDisposable = Touch.Gesture.addTarget(this.wrapper);
|
||||||
}
|
}
|
||||||
|
|
||||||
this.rowsContainer = document.createElement('div');
|
this.rowsContainer = document.createElement('div');
|
||||||
@@ -1681,6 +1682,7 @@ export class TreeView extends HeightMap {
|
|||||||
if (this.context.cache) {
|
if (this.context.cache) {
|
||||||
this.context.cache.dispose();
|
this.context.cache.dispose();
|
||||||
}
|
}
|
||||||
|
this.gestureDisposable.dispose();
|
||||||
|
|
||||||
super.dispose();
|
super.dispose();
|
||||||
}
|
}
|
||||||
|
|||||||
19
src/vs/base/test/common/markdownString.test.ts
Normal file
19
src/vs/base/test/common/markdownString.test.ts
Normal file
@@ -0,0 +1,19 @@
|
|||||||
|
/*---------------------------------------------------------------------------------------------
|
||||||
|
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||||
|
* Licensed under the Source EULA. See License.txt in the project root for license information.
|
||||||
|
*--------------------------------------------------------------------------------------------*/
|
||||||
|
|
||||||
|
import * as assert from 'assert';
|
||||||
|
import { MarkdownString } from 'vs/base/common/htmlContent';
|
||||||
|
|
||||||
|
suite('markdownString', () => {
|
||||||
|
|
||||||
|
test('escape', () => {
|
||||||
|
|
||||||
|
const mds = new MarkdownString();
|
||||||
|
|
||||||
|
mds.appendText('# foo\n*bar*');
|
||||||
|
|
||||||
|
assert.equal(mds.value, '\\# foo\n\n\\*bar\\*');
|
||||||
|
});
|
||||||
|
});
|
||||||
@@ -27,6 +27,7 @@ function getWorker(workerId: string, label: string): Worker | Promise<Worker> {
|
|||||||
throw new Error(`You must define a function MonacoEnvironment.getWorkerUrl or MonacoEnvironment.getWorker`);
|
throw new Error(`You must define a function MonacoEnvironment.getWorkerUrl or MonacoEnvironment.getWorker`);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// ESM-comment-begin
|
||||||
export function getWorkerBootstrapUrl(scriptPath: string, label: string): string {
|
export function getWorkerBootstrapUrl(scriptPath: string, label: string): string {
|
||||||
if (/^(http:)|(https:)|(file:)/.test(scriptPath)) {
|
if (/^(http:)|(https:)|(file:)/.test(scriptPath)) {
|
||||||
const currentUrl = String(window.location);
|
const currentUrl = String(window.location);
|
||||||
@@ -43,6 +44,7 @@ export function getWorkerBootstrapUrl(scriptPath: string, label: string): string
|
|||||||
}
|
}
|
||||||
return scriptPath + '#' + label;
|
return scriptPath + '#' + label;
|
||||||
}
|
}
|
||||||
|
// ESM-comment-end
|
||||||
|
|
||||||
function isPromiseLike<T>(obj: any): obj is PromiseLike<T> {
|
function isPromiseLike<T>(obj: any): obj is PromiseLike<T> {
|
||||||
if (typeof obj.then === 'function') {
|
if (typeof obj.then === 'function') {
|
||||||
|
|||||||
@@ -3,7 +3,7 @@
|
|||||||
* Licensed under the Source EULA. See License.txt in the project root for license information.
|
* Licensed under the Source EULA. See License.txt in the project root for license information.
|
||||||
*--------------------------------------------------------------------------------------------*/
|
*--------------------------------------------------------------------------------------------*/
|
||||||
|
|
||||||
import { app, ipcMain as ipc, systemPreferences, shell, Event, contentTracing, protocol, powerMonitor, IpcMainEvent } from 'electron';
|
import { app, ipcMain as ipc, systemPreferences, shell, Event, contentTracing, protocol, powerMonitor, Event as IpcMainEvent, BrowserWindow } from 'electron';
|
||||||
import { IProcessEnvironment, isWindows, isMacintosh } from 'vs/base/common/platform';
|
import { IProcessEnvironment, isWindows, isMacintosh } from 'vs/base/common/platform';
|
||||||
import { WindowsManager } from 'vs/code/electron-main/windows';
|
import { WindowsManager } from 'vs/code/electron-main/windows';
|
||||||
import { OpenContext, IWindowOpenable } from 'vs/platform/windows/common/windows';
|
import { OpenContext, IWindowOpenable } from 'vs/platform/windows/common/windows';
|
||||||
@@ -78,6 +78,8 @@ import { IElectronService } from 'vs/platform/electron/node/electron';
|
|||||||
import { ElectronMainService } from 'vs/platform/electron/electron-main/electronMainService';
|
import { ElectronMainService } from 'vs/platform/electron/electron-main/electronMainService';
|
||||||
import { ISharedProcessMainService, SharedProcessMainService } from 'vs/platform/ipc/electron-main/sharedProcessMainService';
|
import { ISharedProcessMainService, SharedProcessMainService } from 'vs/platform/ipc/electron-main/sharedProcessMainService';
|
||||||
import { assign } from 'vs/base/common/objects';
|
import { assign } from 'vs/base/common/objects';
|
||||||
|
import { IDialogMainService, DialogMainService } from 'vs/platform/dialogs/electron-main/dialogs';
|
||||||
|
import { withNullAsUndefined } from 'vs/base/common/types';
|
||||||
|
|
||||||
export class CodeApplication extends Disposable {
|
export class CodeApplication extends Disposable {
|
||||||
|
|
||||||
@@ -85,6 +87,7 @@ export class CodeApplication extends Disposable {
|
|||||||
private static readonly TRUE_MACHINE_ID_KEY = 'telemetry.trueMachineId';
|
private static readonly TRUE_MACHINE_ID_KEY = 'telemetry.trueMachineId';
|
||||||
|
|
||||||
private windowsMainService: IWindowsMainService | undefined;
|
private windowsMainService: IWindowsMainService | undefined;
|
||||||
|
private dialogMainService: IDialogMainService | undefined;
|
||||||
|
|
||||||
constructor(
|
constructor(
|
||||||
private readonly mainIpcServer: Server,
|
private readonly mainIpcServer: Server,
|
||||||
@@ -381,8 +384,7 @@ export class CodeApplication extends Disposable {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Setup Auth Handler
|
// Setup Auth Handler
|
||||||
const authHandler = appInstantiationService.createInstance(ProxyAuthHandler);
|
this._register(new ProxyAuthHandler());
|
||||||
this._register(authHandler);
|
|
||||||
|
|
||||||
// Open Windows
|
// Open Windows
|
||||||
const windows = appInstantiationService.invokeFunction(accessor => this.openFirstWindow(accessor, electronIpcServer, sharedProcessClient));
|
const windows = appInstantiationService.invokeFunction(accessor => this.openFirstWindow(accessor, electronIpcServer, sharedProcessClient));
|
||||||
@@ -449,6 +451,7 @@ export class CodeApplication extends Disposable {
|
|||||||
}
|
}
|
||||||
|
|
||||||
services.set(IWindowsMainService, new SyncDescriptor(WindowsManager, [machineId, this.userEnv]));
|
services.set(IWindowsMainService, new SyncDescriptor(WindowsManager, [machineId, this.userEnv]));
|
||||||
|
services.set(IDialogMainService, new SyncDescriptor(DialogMainService));
|
||||||
services.set(ISharedProcessMainService, new SyncDescriptor(SharedProcessMainService, [sharedProcess]));
|
services.set(ISharedProcessMainService, new SyncDescriptor(SharedProcessMainService, [sharedProcess]));
|
||||||
services.set(ILaunchMainService, new SyncDescriptor(LaunchMainService));
|
services.set(ILaunchMainService, new SyncDescriptor(LaunchMainService));
|
||||||
|
|
||||||
@@ -503,13 +506,13 @@ export class CodeApplication extends Disposable {
|
|||||||
|
|
||||||
contentTracing.stopRecording(join(homedir(), `${product.applicationName}-${Math.random().toString(16).slice(-4)}.trace.txt`), path => {
|
contentTracing.stopRecording(join(homedir(), `${product.applicationName}-${Math.random().toString(16).slice(-4)}.trace.txt`), path => {
|
||||||
if (!timeout) {
|
if (!timeout) {
|
||||||
if (this.windowsMainService) {
|
if (this.dialogMainService) {
|
||||||
this.windowsMainService.showMessageBox({
|
this.dialogMainService.showMessageBox({
|
||||||
type: 'info',
|
type: 'info',
|
||||||
message: localize('trace.message', "Successfully created trace."),
|
message: localize('trace.message', "Successfully created trace."),
|
||||||
detail: localize('trace.detail', "Please create an issue and manually attach the following file:\n{0}", path),
|
detail: localize('trace.detail', "Please create an issue and manually attach the following file:\n{0}", path),
|
||||||
buttons: [localize('trace.ok', "Ok")]
|
buttons: [localize('trace.ok', "Ok")]
|
||||||
}, this.windowsMainService.getLastActiveWindow());
|
}, withNullAsUndefined(BrowserWindow.getFocusedWindow()));
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
this.logService.info(`Tracing: data recorded (after 30s timeout) to ${path}`);
|
this.logService.info(`Tracing: data recorded (after 30s timeout) to ${path}`);
|
||||||
@@ -580,6 +583,7 @@ export class CodeApplication extends Disposable {
|
|||||||
|
|
||||||
// Propagate to clients
|
// Propagate to clients
|
||||||
const windowsMainService = this.windowsMainService = accessor.get(IWindowsMainService);
|
const windowsMainService = this.windowsMainService = accessor.get(IWindowsMainService);
|
||||||
|
this.dialogMainService = accessor.get(IDialogMainService);
|
||||||
|
|
||||||
// Create a URL handler to open file URIs in the active window
|
// Create a URL handler to open file URIs in the active window
|
||||||
const environmentService = accessor.get(IEnvironmentService);
|
const environmentService = accessor.get(IEnvironmentService);
|
||||||
|
|||||||
@@ -4,8 +4,7 @@
|
|||||||
*--------------------------------------------------------------------------------------------*/
|
*--------------------------------------------------------------------------------------------*/
|
||||||
|
|
||||||
import { localize } from 'vs/nls';
|
import { localize } from 'vs/nls';
|
||||||
import { IDisposable, dispose } from 'vs/base/common/lifecycle';
|
import { Disposable } from 'vs/base/common/lifecycle';
|
||||||
import { IWindowsMainService } from 'vs/platform/windows/electron-main/windows';
|
|
||||||
import { Event } from 'vs/base/common/event';
|
import { Event } from 'vs/base/common/event';
|
||||||
import { BrowserWindow, app, AuthInfo, WebContents, Event as ElectronEvent } from 'electron';
|
import { BrowserWindow, app, AuthInfo, WebContents, Event as ElectronEvent } from 'electron';
|
||||||
|
|
||||||
@@ -22,18 +21,21 @@ type Credentials = {
|
|||||||
password: string;
|
password: string;
|
||||||
};
|
};
|
||||||
|
|
||||||
export class ProxyAuthHandler {
|
export class ProxyAuthHandler extends Disposable {
|
||||||
|
|
||||||
_serviceBrand: undefined;
|
_serviceBrand: undefined;
|
||||||
|
|
||||||
private retryCount = 0;
|
private retryCount = 0;
|
||||||
private disposables: IDisposable[] = [];
|
|
||||||
|
|
||||||
constructor(
|
constructor() {
|
||||||
@IWindowsMainService private readonly windowsMainService: IWindowsMainService
|
super();
|
||||||
) {
|
|
||||||
|
this.registerListeners();
|
||||||
|
}
|
||||||
|
|
||||||
|
private registerListeners(): void {
|
||||||
const onLogin = Event.fromNodeEventEmitter<LoginEvent>(app, 'login', (event, webContents, req, authInfo, cb) => ({ event, webContents, req, authInfo, cb }));
|
const onLogin = Event.fromNodeEventEmitter<LoginEvent>(app, 'login', (event, webContents, req, authInfo, cb) => ({ event, webContents, req, authInfo, cb }));
|
||||||
onLogin(this.onLogin, this, this.disposables);
|
this._register(onLogin(this.onLogin, this));
|
||||||
}
|
}
|
||||||
|
|
||||||
private onLogin({ event, authInfo, cb }: LoginEvent): void {
|
private onLogin({ event, authInfo, cb }: LoginEvent): void {
|
||||||
@@ -61,10 +63,9 @@ export class ProxyAuthHandler {
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
const focusedWindow = this.windowsMainService.getFocusedWindow();
|
const focusedWindow = BrowserWindow.getFocusedWindow();
|
||||||
|
|
||||||
if (focusedWindow) {
|
if (focusedWindow) {
|
||||||
opts.parent = focusedWindow.win;
|
opts.parent = focusedWindow;
|
||||||
opts.modal = true;
|
opts.modal = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -89,8 +90,4 @@ export class ProxyAuthHandler {
|
|||||||
win.close();
|
win.close();
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
dispose(): void {
|
|
||||||
this.disposables = dispose(this.disposables);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -7,7 +7,7 @@ import { assign } from 'vs/base/common/objects';
|
|||||||
import { memoize } from 'vs/base/common/decorators';
|
import { memoize } from 'vs/base/common/decorators';
|
||||||
import { IEnvironmentService } from 'vs/platform/environment/common/environment';
|
import { IEnvironmentService } from 'vs/platform/environment/common/environment';
|
||||||
import { BrowserWindow, ipcMain } from 'electron';
|
import { BrowserWindow, ipcMain } from 'electron';
|
||||||
import { ISharedProcess } from 'vs/platform/windows/electron-main/windows';
|
import { ISharedProcess } from 'vs/platform/ipc/electron-main/sharedProcessMainService';
|
||||||
import { Barrier } from 'vs/base/common/async';
|
import { Barrier } from 'vs/base/common/async';
|
||||||
import { ILogService } from 'vs/platform/log/common/log';
|
import { ILogService } from 'vs/platform/log/common/log';
|
||||||
import { ILifecycleMainService } from 'vs/platform/lifecycle/electron-main/lifecycleMainService';
|
import { ILifecycleMainService } from 'vs/platform/lifecycle/electron-main/lifecycleMainService';
|
||||||
|
|||||||
@@ -561,7 +561,7 @@ export class CodeWindow extends Disposable implements ICodeWindow {
|
|||||||
autoDetectHighContrast = false;
|
autoDetectHighContrast = false;
|
||||||
}
|
}
|
||||||
windowConfiguration.highContrast = isWindows && autoDetectHighContrast && systemPreferences.isInvertedColorScheme();
|
windowConfiguration.highContrast = isWindows && autoDetectHighContrast && systemPreferences.isInvertedColorScheme();
|
||||||
windowConfiguration.accessibilitySupport = app.accessibilitySupportEnabled;
|
windowConfiguration.accessibilitySupport = app.isAccessibilitySupportEnabled();
|
||||||
|
|
||||||
// Title style related
|
// Title style related
|
||||||
windowConfiguration.maximized = this._win.isMaximized();
|
windowConfiguration.maximized = this._win.isMaximized();
|
||||||
|
|||||||
@@ -4,7 +4,7 @@
|
|||||||
*--------------------------------------------------------------------------------------------*/
|
*--------------------------------------------------------------------------------------------*/
|
||||||
|
|
||||||
import * as fs from 'fs';
|
import * as fs from 'fs';
|
||||||
import { basename, normalize, join, dirname } from 'vs/base/common/path';
|
import { basename, normalize, join, } from 'vs/base/common/path';
|
||||||
import { localize } from 'vs/nls';
|
import { localize } from 'vs/nls';
|
||||||
import * as arrays from 'vs/base/common/arrays';
|
import * as arrays from 'vs/base/common/arrays';
|
||||||
import { assign, mixin } from 'vs/base/common/objects';
|
import { assign, mixin } from 'vs/base/common/objects';
|
||||||
@@ -13,34 +13,36 @@ import { IEmptyWindowBackupInfo } from 'vs/platform/backup/node/backup';
|
|||||||
import { IEnvironmentService, ParsedArgs } from 'vs/platform/environment/common/environment';
|
import { IEnvironmentService, ParsedArgs } from 'vs/platform/environment/common/environment';
|
||||||
import { IStateService } from 'vs/platform/state/node/state';
|
import { IStateService } from 'vs/platform/state/node/state';
|
||||||
import { CodeWindow, defaultWindowState } from 'vs/code/electron-main/window';
|
import { CodeWindow, defaultWindowState } from 'vs/code/electron-main/window';
|
||||||
import { ipcMain as ipc, screen, BrowserWindow, dialog, systemPreferences, FileFilter, shell, MessageBoxReturnValue, MessageBoxOptions, SaveDialogOptions, SaveDialogReturnValue, OpenDialogOptions, OpenDialogReturnValue, Display } from 'electron';
|
import { ipcMain as ipc, screen, BrowserWindow, systemPreferences, MessageBoxOptions, Display } from 'electron';
|
||||||
import { parseLineAndColumnAware } from 'vs/code/node/paths';
|
import { parseLineAndColumnAware } from 'vs/code/node/paths';
|
||||||
import { ILifecycleMainService, UnloadReason, LifecycleMainService, LifecycleMainPhase } from 'vs/platform/lifecycle/electron-main/lifecycleMainService';
|
import { ILifecycleMainService, UnloadReason, LifecycleMainService, LifecycleMainPhase } from 'vs/platform/lifecycle/electron-main/lifecycleMainService';
|
||||||
import { IConfigurationService } from 'vs/platform/configuration/common/configuration';
|
import { IConfigurationService } from 'vs/platform/configuration/common/configuration';
|
||||||
import { ILogService } from 'vs/platform/log/common/log';
|
import { ILogService } from 'vs/platform/log/common/log';
|
||||||
import { IWindowSettings, OpenContext, IPath, IWindowConfiguration, IPathsToWaitFor, isFileToOpen, isWorkspaceToOpen, isFolderToOpen, IWindowOpenable, IOpenEmptyWindowOptions } from 'vs/platform/windows/common/windows';
|
import { IWindowSettings, OpenContext, IPath, IWindowConfiguration, IPathsToWaitFor, isFileToOpen, isWorkspaceToOpen, isFolderToOpen, IWindowOpenable, IOpenEmptyWindowOptions, IAddFoldersRequest } from 'vs/platform/windows/common/windows';
|
||||||
import { INativeOpenDialogOptions } from 'vs/platform/dialogs/node/dialogs';
|
import { INativeOpenDialogOptions } from 'vs/platform/dialogs/node/dialogs';
|
||||||
import { getLastActiveWindow, findBestWindowOrFolderForFile, findWindowOnWorkspace, findWindowOnExtensionDevelopmentPath, findWindowOnWorkspaceOrFolderUri } from 'vs/code/node/windowsFinder';
|
import { getLastActiveWindow, findBestWindowOrFolderForFile, findWindowOnWorkspace, findWindowOnExtensionDevelopmentPath, findWindowOnWorkspaceOrFolderUri } from 'vs/platform/windows/node/window';
|
||||||
import { Event as CommonEvent, Emitter } from 'vs/base/common/event';
|
import { Event as CommonEvent, Emitter } from 'vs/base/common/event';
|
||||||
import product from 'vs/platform/product/common/product';
|
import product from 'vs/platform/product/common/product';
|
||||||
import { ITelemetryService, ITelemetryData } from 'vs/platform/telemetry/common/telemetry';
|
import { ITelemetryService, ITelemetryData } from 'vs/platform/telemetry/common/telemetry';
|
||||||
import { IWindowsMainService, IOpenConfiguration, IWindowsCountChangedEvent, ICodeWindow, IWindowState as ISingleWindowState, WindowMode } from 'vs/platform/windows/electron-main/windows';
|
import { IWindowsMainService, IOpenConfiguration, IWindowsCountChangedEvent, ICodeWindow, IWindowState as ISingleWindowState, WindowMode } from 'vs/platform/windows/electron-main/windows';
|
||||||
import { IWorkspacesHistoryMainService } from 'vs/platform/workspaces/electron-main/workspacesHistoryMainService';
|
import { IWorkspacesHistoryMainService } from 'vs/platform/workspaces/electron-main/workspacesHistoryMainService';
|
||||||
import { IProcessEnvironment, isMacintosh, isWindows } from 'vs/base/common/platform';
|
import { IProcessEnvironment, isMacintosh, isWindows } from 'vs/base/common/platform';
|
||||||
import { IWorkspaceIdentifier, WORKSPACE_FILTER, isSingleFolderWorkspaceIdentifier, hasWorkspaceFileExtension, IEnterWorkspaceResult, IRecent } from 'vs/platform/workspaces/common/workspaces';
|
import { IWorkspaceIdentifier, isSingleFolderWorkspaceIdentifier, hasWorkspaceFileExtension, IRecent } from 'vs/platform/workspaces/common/workspaces';
|
||||||
import { IInstantiationService } from 'vs/platform/instantiation/common/instantiation';
|
import { IInstantiationService } from 'vs/platform/instantiation/common/instantiation';
|
||||||
import { mnemonicButtonLabel } from 'vs/base/common/labels';
|
import { mnemonicButtonLabel } from 'vs/base/common/labels';
|
||||||
import { Schemas } from 'vs/base/common/network';
|
import { Schemas } from 'vs/base/common/network';
|
||||||
import { normalizeNFC } from 'vs/base/common/normalization';
|
|
||||||
import { URI } from 'vs/base/common/uri';
|
import { URI } from 'vs/base/common/uri';
|
||||||
import { Queue } from 'vs/base/common/async';
|
import { dirExists } from 'vs/base/node/pfs';
|
||||||
import { exists, dirExists } from 'vs/base/node/pfs';
|
import { getComparisonKey, isEqual, normalizePath, originalFSPath, hasTrailingPathSeparator, removeTrailingPathSeparator } from 'vs/base/common/resources';
|
||||||
import { getComparisonKey, isEqual, normalizePath, basename as resourcesBasename, originalFSPath, hasTrailingPathSeparator, removeTrailingPathSeparator } from 'vs/base/common/resources';
|
|
||||||
import { getRemoteAuthority } from 'vs/platform/remote/common/remoteHosts';
|
import { getRemoteAuthority } from 'vs/platform/remote/common/remoteHosts';
|
||||||
import { restoreWindowsState, WindowsStateStorageData, getWindowsStateStoreData } from 'vs/code/electron-main/windowsStateStorage';
|
import { restoreWindowsState, WindowsStateStorageData, getWindowsStateStoreData } from 'vs/code/electron-main/windowsStateStorage';
|
||||||
import { getWorkspaceIdentifier, IWorkspacesMainService } from 'vs/platform/workspaces/electron-main/workspacesMainService';
|
import { getWorkspaceIdentifier, IWorkspacesMainService } from 'vs/platform/workspaces/electron-main/workspacesMainService';
|
||||||
import { once } from 'vs/base/common/functional';
|
import { once } from 'vs/base/common/functional';
|
||||||
import { Disposable } from 'vs/base/common/lifecycle';
|
import { Disposable } from 'vs/base/common/lifecycle';
|
||||||
|
import { IDialogMainService } from 'vs/platform/dialogs/electron-main/dialogs';
|
||||||
|
import { withNullAsUndefined } from 'vs/base/common/types';
|
||||||
|
import { isWindowsDriveLetter, toSlashes } from 'vs/base/common/extpath';
|
||||||
|
import { CharCode } from 'vs/base/common/charCode';
|
||||||
|
|
||||||
const enum WindowError {
|
const enum WindowError {
|
||||||
UNRESPONSIVE = 1,
|
UNRESPONSIVE = 1,
|
||||||
@@ -167,9 +169,6 @@ export class WindowsManager extends Disposable implements IWindowsMainService {
|
|||||||
private readonly windowsState: IWindowsState;
|
private readonly windowsState: IWindowsState;
|
||||||
private lastClosedWindowState?: IWindowState;
|
private lastClosedWindowState?: IWindowState;
|
||||||
|
|
||||||
private readonly dialogs: Dialogs;
|
|
||||||
private readonly workspacesManager: WorkspacesManager;
|
|
||||||
|
|
||||||
private readonly _onWindowReady = this._register(new Emitter<ICodeWindow>());
|
private readonly _onWindowReady = this._register(new Emitter<ICodeWindow>());
|
||||||
readonly onWindowReady: CommonEvent<ICodeWindow> = this._onWindowReady.event;
|
readonly onWindowReady: CommonEvent<ICodeWindow> = this._onWindowReady.event;
|
||||||
|
|
||||||
@@ -194,7 +193,8 @@ export class WindowsManager extends Disposable implements IWindowsMainService {
|
|||||||
@IConfigurationService private readonly configurationService: IConfigurationService,
|
@IConfigurationService private readonly configurationService: IConfigurationService,
|
||||||
@IWorkspacesHistoryMainService private readonly workspacesHistoryMainService: IWorkspacesHistoryMainService,
|
@IWorkspacesHistoryMainService private readonly workspacesHistoryMainService: IWorkspacesHistoryMainService,
|
||||||
@IWorkspacesMainService private readonly workspacesMainService: IWorkspacesMainService,
|
@IWorkspacesMainService private readonly workspacesMainService: IWorkspacesMainService,
|
||||||
@IInstantiationService private readonly instantiationService: IInstantiationService
|
@IInstantiationService private readonly instantiationService: IInstantiationService,
|
||||||
|
@IDialogMainService private readonly dialogMainService: IDialogMainService
|
||||||
) {
|
) {
|
||||||
super();
|
super();
|
||||||
|
|
||||||
@@ -203,9 +203,6 @@ export class WindowsManager extends Disposable implements IWindowsMainService {
|
|||||||
this.windowsState.openedWindows = [];
|
this.windowsState.openedWindows = [];
|
||||||
}
|
}
|
||||||
|
|
||||||
this.dialogs = new Dialogs(stateService, this);
|
|
||||||
this.workspacesManager = new WorkspacesManager(workspacesMainService, backupMainService, this);
|
|
||||||
|
|
||||||
this.lifecycleMainService.when(LifecycleMainPhase.Ready).then(() => this.registerListeners());
|
this.lifecycleMainService.when(LifecycleMainPhase.Ready).then(() => this.registerListeners());
|
||||||
this.lifecycleMainService.when(LifecycleMainPhase.AfterWindowOpen).then(() => this.installWindowsMutex());
|
this.lifecycleMainService.when(LifecycleMainPhase.AfterWindowOpen).then(() => this.installWindowsMutex());
|
||||||
}
|
}
|
||||||
@@ -260,6 +257,11 @@ export class WindowsManager extends Disposable implements IWindowsMainService {
|
|||||||
this.lastClosedWindowState = undefined;
|
this.lastClosedWindowState = undefined;
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
|
// Signal a window is ready after having entered a workspace
|
||||||
|
this._register(this.workspacesMainService.onWorkspaceEntered(event => {
|
||||||
|
this._onWindowReady.fire(event.window);
|
||||||
|
}));
|
||||||
}
|
}
|
||||||
|
|
||||||
// Note that onBeforeShutdown() and onBeforeWindowClose() are fired in different order depending on the OS:
|
// Note that onBeforeShutdown() and onBeforeWindowClose() are fired in different order depending on the OS:
|
||||||
@@ -380,12 +382,6 @@ export class WindowsManager extends Disposable implements IWindowsMainService {
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
async openExternal(url: string): Promise<boolean> {
|
|
||||||
shell.openExternal(url);
|
|
||||||
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
open(openConfig: IOpenConfiguration): ICodeWindow[] {
|
open(openConfig: IOpenConfiguration): ICodeWindow[] {
|
||||||
this.logService.trace('windowsManager#open');
|
this.logService.trace('windowsManager#open');
|
||||||
openConfig = this.validateOpenConfig(openConfig);
|
openConfig = this.validateOpenConfig(openConfig);
|
||||||
@@ -776,7 +772,9 @@ export class WindowsManager extends Disposable implements IWindowsMainService {
|
|||||||
private doAddFoldersToExistingWindow(window: ICodeWindow, foldersToAdd: URI[]): ICodeWindow {
|
private doAddFoldersToExistingWindow(window: ICodeWindow, foldersToAdd: URI[]): ICodeWindow {
|
||||||
window.focus(); // make sure window has focus
|
window.focus(); // make sure window has focus
|
||||||
|
|
||||||
window.sendWhenReady('vscode:addFolders', { foldersToAdd });
|
const request: IAddFoldersRequest = { foldersToAdd };
|
||||||
|
|
||||||
|
window.sendWhenReady('vscode:addFolders', request);
|
||||||
|
|
||||||
return window;
|
return window;
|
||||||
}
|
}
|
||||||
@@ -862,7 +860,8 @@ export class WindowsManager extends Disposable implements IWindowsMainService {
|
|||||||
path.label = pathToOpen.label;
|
path.label = pathToOpen.label;
|
||||||
pathsToOpen.push(path);
|
pathsToOpen.push(path);
|
||||||
} else {
|
} else {
|
||||||
const uri = resourceFromURIToOpen(pathToOpen);
|
const uri = this.resourceFromURIToOpen(pathToOpen);
|
||||||
|
|
||||||
// Warn about the invalid URI or path
|
// Warn about the invalid URI or path
|
||||||
let message, detail;
|
let message, detail;
|
||||||
if (uri.scheme === Schemas.file) {
|
if (uri.scheme === Schemas.file) {
|
||||||
@@ -881,7 +880,7 @@ export class WindowsManager extends Disposable implements IWindowsMainService {
|
|||||||
noLink: true
|
noLink: true
|
||||||
};
|
};
|
||||||
|
|
||||||
this.dialogs.showMessageBox(options, this.getFocusedWindow());
|
this.dialogMainService.showMessageBox(options, withNullAsUndefined(BrowserWindow.getFocusedWindow()));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
return pathsToOpen;
|
return pathsToOpen;
|
||||||
@@ -1011,10 +1010,12 @@ export class WindowsManager extends Disposable implements IWindowsMainService {
|
|||||||
this.logService.error(`Invalid URI input string, scheme missing: ${arg}`);
|
this.logService.error(`Invalid URI input string, scheme missing: ${arg}`);
|
||||||
return undefined;
|
return undefined;
|
||||||
}
|
}
|
||||||
|
|
||||||
return uri;
|
return uri;
|
||||||
} catch (e) {
|
} catch (e) {
|
||||||
this.logService.error(`Invalid URI input string: ${arg}, ${e.message}`);
|
this.logService.error(`Invalid URI input string: ${arg}, ${e.message}`);
|
||||||
}
|
}
|
||||||
|
|
||||||
return undefined;
|
return undefined;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1023,7 +1024,7 @@ export class WindowsManager extends Disposable implements IWindowsMainService {
|
|||||||
return undefined;
|
return undefined;
|
||||||
}
|
}
|
||||||
|
|
||||||
let uri = resourceFromURIToOpen(toOpen);
|
let uri = this.resourceFromURIToOpen(toOpen);
|
||||||
if (uri.scheme === Schemas.file) {
|
if (uri.scheme === Schemas.file) {
|
||||||
return this.parsePath(uri.fsPath, options, isFileToOpen(toOpen));
|
return this.parsePath(uri.fsPath, options, isFileToOpen(toOpen));
|
||||||
}
|
}
|
||||||
@@ -1050,6 +1051,7 @@ export class WindowsManager extends Disposable implements IWindowsMainService {
|
|||||||
remoteAuthority
|
remoteAuthority
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
return {
|
return {
|
||||||
fileUri: uri,
|
fileUri: uri,
|
||||||
remoteAuthority
|
remoteAuthority
|
||||||
@@ -1071,6 +1073,18 @@ export class WindowsManager extends Disposable implements IWindowsMainService {
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private resourceFromURIToOpen(openable: IWindowOpenable): URI {
|
||||||
|
if (isWorkspaceToOpen(openable)) {
|
||||||
|
return openable.workspaceUri;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (isFolderToOpen(openable)) {
|
||||||
|
return openable.folderUri;
|
||||||
|
}
|
||||||
|
|
||||||
|
return openable.fileUri;
|
||||||
|
}
|
||||||
|
|
||||||
private parsePath(anyPath: string, options: IPathParseOptions, forceOpenWorkspaceAsFile?: boolean): IPathToOpen | undefined {
|
private parsePath(anyPath: string, options: IPathParseOptions, forceOpenWorkspaceAsFile?: boolean): IPathToOpen | undefined {
|
||||||
if (!anyPath) {
|
if (!anyPath) {
|
||||||
return undefined;
|
return undefined;
|
||||||
@@ -1086,11 +1100,36 @@ export class WindowsManager extends Disposable implements IWindowsMainService {
|
|||||||
anyPath = parsedPath.path;
|
anyPath = parsedPath.path;
|
||||||
}
|
}
|
||||||
|
|
||||||
// open remote if either specified in the cli even if it is a local file. TODO@aeschli: Future idea: resolve in remote host context.
|
// open remote if either specified in the cli even if it is a local file.
|
||||||
const remoteAuthority = options.remoteAuthority;
|
const remoteAuthority = options.remoteAuthority;
|
||||||
|
|
||||||
const candidate = normalize(anyPath);
|
if (remoteAuthority) {
|
||||||
|
// assume it's a folder or workspace file
|
||||||
|
|
||||||
|
const first = anyPath.charCodeAt(0);
|
||||||
|
// make absolute
|
||||||
|
if (first !== CharCode.Slash) {
|
||||||
|
if (isWindowsDriveLetter(first) && anyPath.charCodeAt(anyPath.charCodeAt(1)) === CharCode.Colon) {
|
||||||
|
anyPath = toSlashes(anyPath);
|
||||||
|
}
|
||||||
|
anyPath = '/' + anyPath;
|
||||||
|
}
|
||||||
|
|
||||||
|
const uri = URI.from({ scheme: Schemas.vscodeRemote, authority: remoteAuthority, path: anyPath });
|
||||||
|
|
||||||
|
if (hasWorkspaceFileExtension(anyPath)) {
|
||||||
|
if (forceOpenWorkspaceAsFile) {
|
||||||
|
return { fileUri: uri, remoteAuthority };
|
||||||
|
}
|
||||||
|
return { workspace: getWorkspaceIdentifier(uri), remoteAuthority };
|
||||||
|
}
|
||||||
|
return { folderUri: uri, remoteAuthority };
|
||||||
|
}
|
||||||
|
|
||||||
|
let candidate = normalize(anyPath);
|
||||||
|
|
||||||
try {
|
try {
|
||||||
|
|
||||||
const candidateStat = fs.statSync(candidate);
|
const candidateStat = fs.statSync(candidate);
|
||||||
if (candidateStat.isFile()) {
|
if (candidateStat.isFile()) {
|
||||||
|
|
||||||
@@ -1185,7 +1224,7 @@ export class WindowsManager extends Disposable implements IWindowsMainService {
|
|||||||
return { openFolderInNewWindow: !!openFolderInNewWindow, openFilesInNewWindow };
|
return { openFolderInNewWindow: !!openFolderInNewWindow, openFilesInNewWindow };
|
||||||
}
|
}
|
||||||
|
|
||||||
openExtensionDevelopmentHostWindow(extensionDevelopmentPath: string[], openConfig: IOpenConfiguration): void {
|
openExtensionDevelopmentHostWindow(extensionDevelopmentPath: string[], openConfig: IOpenConfiguration): ICodeWindow[] {
|
||||||
|
|
||||||
// Reload an existing extension development host window on the same path
|
// Reload an existing extension development host window on the same path
|
||||||
// We currently do not allow more than one extension development window
|
// We currently do not allow more than one extension development window
|
||||||
@@ -1195,7 +1234,7 @@ export class WindowsManager extends Disposable implements IWindowsMainService {
|
|||||||
this.reload(existingWindow, openConfig.cli);
|
this.reload(existingWindow, openConfig.cli);
|
||||||
existingWindow.focus(); // make sure it gets focus and is restored
|
existingWindow.focus(); // make sure it gets focus and is restored
|
||||||
|
|
||||||
return;
|
return [existingWindow];
|
||||||
}
|
}
|
||||||
let folderUris = openConfig.cli['folder-uri'] || [];
|
let folderUris = openConfig.cli['folder-uri'] || [];
|
||||||
let fileUris = openConfig.cli['file-uri'] || [];
|
let fileUris = openConfig.cli['file-uri'] || [];
|
||||||
@@ -1286,7 +1325,8 @@ export class WindowsManager extends Disposable implements IWindowsMainService {
|
|||||||
noRecentEntry: true,
|
noRecentEntry: true,
|
||||||
waitMarkerFileURI: openConfig.waitMarkerFileURI
|
waitMarkerFileURI: openConfig.waitMarkerFileURI
|
||||||
};
|
};
|
||||||
this.open(openArgs);
|
|
||||||
|
return this.open(openArgs);
|
||||||
}
|
}
|
||||||
|
|
||||||
private openInBrowserWindow(options: IOpenBrowserWindowOptions): ICodeWindow {
|
private openInBrowserWindow(options: IOpenBrowserWindowOptions): ICodeWindow {
|
||||||
@@ -1580,23 +1620,6 @@ export class WindowsManager extends Disposable implements IWindowsMainService {
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
async enterWorkspace(win: ICodeWindow, path: URI): Promise<IEnterWorkspaceResult | undefined> {
|
|
||||||
const result = await this.workspacesManager.enterWorkspace(win, path);
|
|
||||||
|
|
||||||
return result ? this.doEnterWorkspace(win, result) : undefined;
|
|
||||||
}
|
|
||||||
|
|
||||||
private doEnterWorkspace(win: ICodeWindow, result: IEnterWorkspaceResult): IEnterWorkspaceResult {
|
|
||||||
|
|
||||||
// Mark as recently opened
|
|
||||||
this.workspacesHistoryMainService.addRecentlyOpened([{ workspace: result.workspace }]);
|
|
||||||
|
|
||||||
// Trigger Eevent to indicate load of workspace into window
|
|
||||||
this._onWindowReady.fire(win);
|
|
||||||
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
focusLastActive(cli: ParsedArgs, context: OpenContext): ICodeWindow {
|
focusLastActive(cli: ParsedArgs, context: OpenContext): ICodeWindow {
|
||||||
const lastActive = this.getLastActiveWindow();
|
const lastActive = this.getLastActiveWindow();
|
||||||
if (lastActive) {
|
if (lastActive) {
|
||||||
@@ -1613,7 +1636,7 @@ export class WindowsManager extends Disposable implements IWindowsMainService {
|
|||||||
return getLastActiveWindow(WindowsManager.WINDOWS);
|
return getLastActiveWindow(WindowsManager.WINDOWS);
|
||||||
}
|
}
|
||||||
|
|
||||||
getLastActiveWindowForAuthority(remoteAuthority: string | undefined): ICodeWindow | undefined {
|
private getLastActiveWindowForAuthority(remoteAuthority: string | undefined): ICodeWindow | undefined {
|
||||||
return getLastActiveWindow(WindowsManager.WINDOWS.filter(window => window.remoteAuthority === remoteAuthority));
|
return getLastActiveWindow(WindowsManager.WINDOWS.filter(window => window.remoteAuthority === remoteAuthority));
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1623,13 +1646,11 @@ export class WindowsManager extends Disposable implements IWindowsMainService {
|
|||||||
if (cli && (cli.remote !== remote)) {
|
if (cli && (cli.remote !== remote)) {
|
||||||
cli = { ...cli, remote };
|
cli = { ...cli, remote };
|
||||||
}
|
}
|
||||||
const forceReuseWindow = options && options.reuse;
|
|
||||||
const forceNewWindow = !forceReuseWindow;
|
|
||||||
return this.open({ context, cli, forceEmpty: true, forceNewWindow, forceReuseWindow });
|
|
||||||
}
|
|
||||||
|
|
||||||
openNewTabbedWindow(context: OpenContext): ICodeWindow[] {
|
const forceReuseWindow = options && options.forceReuseWindow;
|
||||||
return this.open({ context, cli: this.environmentService.args, forceNewTabbedWindow: true, forceEmpty: true });
|
const forceNewWindow = !forceReuseWindow;
|
||||||
|
|
||||||
|
return this.open({ context, cli, forceEmpty: true, forceNewWindow, forceReuseWindow });
|
||||||
}
|
}
|
||||||
|
|
||||||
waitForWindowCloseOrLoad(windowId: number): Promise<void> {
|
waitForWindowCloseOrLoad(windowId: number): Promise<void> {
|
||||||
@@ -1666,7 +1687,7 @@ export class WindowsManager extends Disposable implements IWindowsMainService {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
getFocusedWindow(): ICodeWindow | undefined {
|
private getFocusedWindow(): ICodeWindow | undefined {
|
||||||
const win = BrowserWindow.getFocusedWindow();
|
const win = BrowserWindow.getFocusedWindow();
|
||||||
if (win) {
|
if (win) {
|
||||||
return this.getWindowById(win.id);
|
return this.getWindowById(win.id);
|
||||||
@@ -1710,14 +1731,14 @@ export class WindowsManager extends Disposable implements IWindowsMainService {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Show Dialog
|
// Show Dialog
|
||||||
this.dialogs.showMessageBox({
|
this.dialogMainService.showMessageBox({
|
||||||
title: product.nameLong,
|
title: product.nameLong,
|
||||||
type: 'warning',
|
type: 'warning',
|
||||||
buttons: [mnemonicButtonLabel(localize({ key: 'reopen', comment: ['&& denotes a mnemonic'] }, "&&Reopen")), mnemonicButtonLabel(localize({ key: 'wait', comment: ['&& denotes a mnemonic'] }, "&&Keep Waiting")), mnemonicButtonLabel(localize({ key: 'close', comment: ['&& denotes a mnemonic'] }, "&&Close"))],
|
buttons: [mnemonicButtonLabel(localize({ key: 'reopen', comment: ['&& denotes a mnemonic'] }, "&&Reopen")), mnemonicButtonLabel(localize({ key: 'wait', comment: ['&& denotes a mnemonic'] }, "&&Keep Waiting")), mnemonicButtonLabel(localize({ key: 'close', comment: ['&& denotes a mnemonic'] }, "&&Close"))],
|
||||||
message: localize('appStalled', "The window is no longer responding"),
|
message: localize('appStalled', "The window is no longer responding"),
|
||||||
detail: localize('appStalledDetail', "You can reopen or close the window or keep waiting."),
|
detail: localize('appStalledDetail', "You can reopen or close the window or keep waiting."),
|
||||||
noLink: true
|
noLink: true
|
||||||
}, window).then(result => {
|
}, window.win).then(result => {
|
||||||
if (!window.win) {
|
if (!window.win) {
|
||||||
return; // Return early if the window has been going down already
|
return; // Return early if the window has been going down already
|
||||||
}
|
}
|
||||||
@@ -1733,14 +1754,14 @@ export class WindowsManager extends Disposable implements IWindowsMainService {
|
|||||||
|
|
||||||
// Crashed
|
// Crashed
|
||||||
else {
|
else {
|
||||||
this.dialogs.showMessageBox({
|
this.dialogMainService.showMessageBox({
|
||||||
title: product.nameLong,
|
title: product.nameLong,
|
||||||
type: 'warning',
|
type: 'warning',
|
||||||
buttons: [mnemonicButtonLabel(localize({ key: 'reopen', comment: ['&& denotes a mnemonic'] }, "&&Reopen")), mnemonicButtonLabel(localize({ key: 'close', comment: ['&& denotes a mnemonic'] }, "&&Close"))],
|
buttons: [mnemonicButtonLabel(localize({ key: 'reopen', comment: ['&& denotes a mnemonic'] }, "&&Reopen")), mnemonicButtonLabel(localize({ key: 'close', comment: ['&& denotes a mnemonic'] }, "&&Close"))],
|
||||||
message: localize('appCrashed', "The window has crashed"),
|
message: localize('appCrashed', "The window has crashed"),
|
||||||
detail: localize('appCrashedDetail', "We are sorry for the inconvenience! You can reopen the window to continue where you left off."),
|
detail: localize('appCrashedDetail', "We are sorry for the inconvenience! You can reopen the window to continue where you left off."),
|
||||||
noLink: true
|
noLink: true
|
||||||
}, window).then(result => {
|
}, window.win).then(result => {
|
||||||
if (!window.win) {
|
if (!window.win) {
|
||||||
return; // Return early if the window has been going down already
|
return; // Return early if the window has been going down already
|
||||||
}
|
}
|
||||||
@@ -1770,8 +1791,7 @@ export class WindowsManager extends Disposable implements IWindowsMainService {
|
|||||||
}
|
}
|
||||||
|
|
||||||
async pickFileFolderAndOpen(options: INativeOpenDialogOptions, win?: ICodeWindow): Promise<void> {
|
async pickFileFolderAndOpen(options: INativeOpenDialogOptions, win?: ICodeWindow): Promise<void> {
|
||||||
const title = localize('open', "Open");
|
const paths = await this.dialogMainService.pickFileFolder(options);
|
||||||
const paths = await this.dialogs.pick({ ...options, pickFolders: true, pickFiles: true, title });
|
|
||||||
if (paths) {
|
if (paths) {
|
||||||
this.sendPickerTelemetry(paths, options.telemetryEventName || 'openFileFolder', options.telemetryExtraData);
|
this.sendPickerTelemetry(paths, options.telemetryEventName || 'openFileFolder', options.telemetryExtraData);
|
||||||
const urisToOpen = await Promise.all(paths.map(async path => {
|
const urisToOpen = await Promise.all(paths.map(async path => {
|
||||||
@@ -1790,8 +1810,7 @@ export class WindowsManager extends Disposable implements IWindowsMainService {
|
|||||||
}
|
}
|
||||||
|
|
||||||
async pickFolderAndOpen(options: INativeOpenDialogOptions, win?: ICodeWindow): Promise<void> {
|
async pickFolderAndOpen(options: INativeOpenDialogOptions, win?: ICodeWindow): Promise<void> {
|
||||||
const title = localize('openFolder', "Open Folder");
|
const paths = await this.dialogMainService.pickFolder(options);
|
||||||
const paths = await this.dialogs.pick({ ...options, pickFolders: true, title });
|
|
||||||
if (paths) {
|
if (paths) {
|
||||||
this.sendPickerTelemetry(paths, options.telemetryEventName || 'openFolder', options.telemetryExtraData);
|
this.sendPickerTelemetry(paths, options.telemetryEventName || 'openFolder', options.telemetryExtraData);
|
||||||
this.open({
|
this.open({
|
||||||
@@ -1805,8 +1824,7 @@ export class WindowsManager extends Disposable implements IWindowsMainService {
|
|||||||
}
|
}
|
||||||
|
|
||||||
async pickFileAndOpen(options: INativeOpenDialogOptions, win?: ICodeWindow): Promise<void> {
|
async pickFileAndOpen(options: INativeOpenDialogOptions, win?: ICodeWindow): Promise<void> {
|
||||||
const title = localize('openFile', "Open File");
|
const paths = await this.dialogMainService.pickFile(options);
|
||||||
const paths = await this.dialogs.pick({ ...options, pickFiles: true, title });
|
|
||||||
if (paths) {
|
if (paths) {
|
||||||
this.sendPickerTelemetry(paths, options.telemetryEventName || 'openFile', options.telemetryExtraData);
|
this.sendPickerTelemetry(paths, options.telemetryEventName || 'openFile', options.telemetryExtraData);
|
||||||
this.open({
|
this.open({
|
||||||
@@ -1820,10 +1838,7 @@ export class WindowsManager extends Disposable implements IWindowsMainService {
|
|||||||
}
|
}
|
||||||
|
|
||||||
async pickWorkspaceAndOpen(options: INativeOpenDialogOptions, win?: ICodeWindow): Promise<void> {
|
async pickWorkspaceAndOpen(options: INativeOpenDialogOptions, win?: ICodeWindow): Promise<void> {
|
||||||
const title = localize('openWorkspaceTitle', "Open Workspace");
|
const paths = await this.dialogMainService.pickWorkspace(options);
|
||||||
const buttonLabel = mnemonicButtonLabel(localize({ key: 'openWorkspace', comment: ['&& denotes a mnemonic'] }, "&&Open"));
|
|
||||||
const filters = WORKSPACE_FILTER;
|
|
||||||
const paths = await this.dialogs.pick({ ...options, pickFiles: true, title, filters, buttonLabel });
|
|
||||||
if (paths) {
|
if (paths) {
|
||||||
this.sendPickerTelemetry(paths, options.telemetryEventName || 'openWorkspace', options.telemetryExtraData);
|
this.sendPickerTelemetry(paths, options.telemetryEventName || 'openWorkspace', options.telemetryExtraData);
|
||||||
this.open({
|
this.open({
|
||||||
@@ -1838,7 +1853,6 @@ export class WindowsManager extends Disposable implements IWindowsMainService {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private sendPickerTelemetry(paths: string[], telemetryEventName: string, telemetryExtraData?: ITelemetryData) {
|
private sendPickerTelemetry(paths: string[], telemetryEventName: string, telemetryExtraData?: ITelemetryData) {
|
||||||
|
|
||||||
const numberOfPaths = paths ? paths.length : 0;
|
const numberOfPaths = paths ? paths.length : 0;
|
||||||
|
|
||||||
// Telemetry
|
// Telemetry
|
||||||
@@ -1850,18 +1864,6 @@ export class WindowsManager extends Disposable implements IWindowsMainService {
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
showMessageBox(options: MessageBoxOptions, win?: ICodeWindow): Promise<MessageBoxReturnValue> {
|
|
||||||
return this.dialogs.showMessageBox(options, win);
|
|
||||||
}
|
|
||||||
|
|
||||||
showSaveDialog(options: SaveDialogOptions, win?: ICodeWindow): Promise<SaveDialogReturnValue> {
|
|
||||||
return this.dialogs.showSaveDialog(options, win);
|
|
||||||
}
|
|
||||||
|
|
||||||
showOpenDialog(options: OpenDialogOptions, win?: ICodeWindow): Promise<OpenDialogReturnValue> {
|
|
||||||
return this.dialogs.showOpenDialog(options, win);
|
|
||||||
}
|
|
||||||
|
|
||||||
quit(): void {
|
quit(): void {
|
||||||
|
|
||||||
// If the user selected to exit from an extension development host window, do not quit, but just
|
// If the user selected to exit from an extension development host window, do not quit, but just
|
||||||
@@ -1879,240 +1881,3 @@ export class WindowsManager extends Disposable implements IWindowsMainService {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
interface IInternalNativeOpenDialogOptions extends INativeOpenDialogOptions {
|
|
||||||
|
|
||||||
pickFolders?: boolean;
|
|
||||||
pickFiles?: boolean;
|
|
||||||
|
|
||||||
title: string;
|
|
||||||
buttonLabel?: string;
|
|
||||||
filters?: FileFilter[];
|
|
||||||
}
|
|
||||||
|
|
||||||
class Dialogs {
|
|
||||||
|
|
||||||
private static readonly workingDirPickerStorageKey = 'pickerWorkingDir';
|
|
||||||
|
|
||||||
private readonly mapWindowToDialogQueue: Map<number, Queue<void>>;
|
|
||||||
private readonly noWindowDialogQueue: Queue<void>;
|
|
||||||
|
|
||||||
constructor(
|
|
||||||
private readonly stateService: IStateService,
|
|
||||||
private readonly windowsMainService: IWindowsMainService
|
|
||||||
) {
|
|
||||||
this.mapWindowToDialogQueue = new Map<number, Queue<void>>();
|
|
||||||
this.noWindowDialogQueue = new Queue<void>();
|
|
||||||
}
|
|
||||||
|
|
||||||
async pick(options: IInternalNativeOpenDialogOptions, win?: ICodeWindow): Promise<string[] | undefined> {
|
|
||||||
|
|
||||||
// Ensure dialog options
|
|
||||||
const dialogOptions: OpenDialogOptions = {
|
|
||||||
title: options.title,
|
|
||||||
buttonLabel: options.buttonLabel,
|
|
||||||
filters: options.filters
|
|
||||||
};
|
|
||||||
|
|
||||||
// Ensure defaultPath
|
|
||||||
dialogOptions.defaultPath = options.defaultPath || this.stateService.getItem<string>(Dialogs.workingDirPickerStorageKey);
|
|
||||||
|
|
||||||
|
|
||||||
// Ensure properties
|
|
||||||
if (typeof options.pickFiles === 'boolean' || typeof options.pickFolders === 'boolean') {
|
|
||||||
dialogOptions.properties = undefined; // let it override based on the booleans
|
|
||||||
|
|
||||||
if (options.pickFiles && options.pickFolders) {
|
|
||||||
dialogOptions.properties = ['multiSelections', 'openDirectory', 'openFile', 'createDirectory'];
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!dialogOptions.properties) {
|
|
||||||
dialogOptions.properties = ['multiSelections', options.pickFolders ? 'openDirectory' : 'openFile', 'createDirectory'];
|
|
||||||
}
|
|
||||||
|
|
||||||
if (isMacintosh) {
|
|
||||||
dialogOptions.properties.push('treatPackageAsDirectory'); // always drill into .app files
|
|
||||||
}
|
|
||||||
|
|
||||||
// Show Dialog
|
|
||||||
const windowToUse = win || this.windowsMainService.getFocusedWindow();
|
|
||||||
|
|
||||||
const result = await this.showOpenDialog(dialogOptions, windowToUse);
|
|
||||||
if (result && result.filePaths && result.filePaths.length > 0) {
|
|
||||||
|
|
||||||
// Remember path in storage for next time
|
|
||||||
this.stateService.setItem(Dialogs.workingDirPickerStorageKey, dirname(result.filePaths[0]));
|
|
||||||
|
|
||||||
return result.filePaths;
|
|
||||||
}
|
|
||||||
|
|
||||||
return undefined; // {{SQL CARBON EDIT}} @anthonydresser strict-null-check
|
|
||||||
}
|
|
||||||
|
|
||||||
private getDialogQueue(window?: ICodeWindow): Queue<any> {
|
|
||||||
if (!window) {
|
|
||||||
return this.noWindowDialogQueue;
|
|
||||||
}
|
|
||||||
|
|
||||||
let windowDialogQueue = this.mapWindowToDialogQueue.get(window.id);
|
|
||||||
if (!windowDialogQueue) {
|
|
||||||
windowDialogQueue = new Queue<any>();
|
|
||||||
this.mapWindowToDialogQueue.set(window.id, windowDialogQueue);
|
|
||||||
}
|
|
||||||
|
|
||||||
return windowDialogQueue;
|
|
||||||
}
|
|
||||||
|
|
||||||
showMessageBox(options: MessageBoxOptions, window?: ICodeWindow): Promise<MessageBoxReturnValue> {
|
|
||||||
return this.getDialogQueue(window).queue(async () => {
|
|
||||||
if (window) {
|
|
||||||
return dialog.showMessageBox(window.win, options);
|
|
||||||
}
|
|
||||||
|
|
||||||
return dialog.showMessageBox(options);
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
showSaveDialog(options: SaveDialogOptions, window?: ICodeWindow): Promise<SaveDialogReturnValue> {
|
|
||||||
|
|
||||||
function normalizePath(path: string | undefined): string | undefined {
|
|
||||||
if (path && isMacintosh) {
|
|
||||||
path = normalizeNFC(path); // normalize paths returned from the OS
|
|
||||||
}
|
|
||||||
|
|
||||||
return path;
|
|
||||||
}
|
|
||||||
|
|
||||||
return this.getDialogQueue(window).queue(async () => {
|
|
||||||
let result: SaveDialogReturnValue;
|
|
||||||
if (window) {
|
|
||||||
result = await dialog.showSaveDialog(window.win, options);
|
|
||||||
} else {
|
|
||||||
result = await dialog.showSaveDialog(options);
|
|
||||||
}
|
|
||||||
|
|
||||||
result.filePath = normalizePath(result.filePath);
|
|
||||||
|
|
||||||
return result;
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
showOpenDialog(options: OpenDialogOptions, window?: ICodeWindow): Promise<OpenDialogReturnValue> {
|
|
||||||
|
|
||||||
function normalizePaths(paths: string[] | undefined): string[] | undefined {
|
|
||||||
if (paths && paths.length > 0 && isMacintosh) {
|
|
||||||
paths = paths.map(path => normalizeNFC(path)); // normalize paths returned from the OS
|
|
||||||
}
|
|
||||||
|
|
||||||
return paths;
|
|
||||||
}
|
|
||||||
|
|
||||||
return this.getDialogQueue(window).queue(async () => {
|
|
||||||
|
|
||||||
// Ensure the path exists (if provided)
|
|
||||||
if (options.defaultPath) {
|
|
||||||
const pathExists = await exists(options.defaultPath);
|
|
||||||
if (!pathExists) {
|
|
||||||
options.defaultPath = undefined;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// Show dialog
|
|
||||||
let result: OpenDialogReturnValue;
|
|
||||||
if (window) {
|
|
||||||
result = await dialog.showOpenDialog(window.win, options);
|
|
||||||
} else {
|
|
||||||
result = await dialog.showOpenDialog(options);
|
|
||||||
}
|
|
||||||
|
|
||||||
result.filePaths = normalizePaths(result.filePaths);
|
|
||||||
|
|
||||||
return result;
|
|
||||||
});
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
class WorkspacesManager {
|
|
||||||
|
|
||||||
constructor(
|
|
||||||
private readonly workspacesMainService: IWorkspacesMainService,
|
|
||||||
private readonly backupMainService: IBackupMainService,
|
|
||||||
private readonly windowsMainService: IWindowsMainService,
|
|
||||||
) { }
|
|
||||||
|
|
||||||
async enterWorkspace(window: ICodeWindow, path: URI): Promise<IEnterWorkspaceResult | null> {
|
|
||||||
if (!window || !window.win || !window.isReady) {
|
|
||||||
return null; // return early if the window is not ready or disposed
|
|
||||||
}
|
|
||||||
|
|
||||||
const isValid = await this.isValidTargetWorkspacePath(window, path);
|
|
||||||
if (!isValid) {
|
|
||||||
return null; // return early if the workspace is not valid
|
|
||||||
}
|
|
||||||
|
|
||||||
return this.doOpenWorkspace(window, getWorkspaceIdentifier(path));
|
|
||||||
}
|
|
||||||
|
|
||||||
private async isValidTargetWorkspacePath(window: ICodeWindow, path?: URI): Promise<boolean> {
|
|
||||||
if (!path) {
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (window.openedWorkspace && isEqual(window.openedWorkspace.configPath, path)) {
|
|
||||||
return false; // window is already opened on a workspace with that path
|
|
||||||
}
|
|
||||||
|
|
||||||
// Prevent overwriting a workspace that is currently opened in another window
|
|
||||||
if (findWindowOnWorkspace(this.windowsMainService.getWindows(), getWorkspaceIdentifier(path))) {
|
|
||||||
const options: MessageBoxOptions = {
|
|
||||||
title: product.nameLong,
|
|
||||||
type: 'info',
|
|
||||||
buttons: [localize('ok', "OK")],
|
|
||||||
message: localize('workspaceOpenedMessage', "Unable to save workspace '{0}'", resourcesBasename(path)),
|
|
||||||
detail: localize('workspaceOpenedDetail', "The workspace is already opened in another window. Please close that window first and then try again."),
|
|
||||||
noLink: true
|
|
||||||
};
|
|
||||||
|
|
||||||
await this.windowsMainService.showMessageBox(options, this.windowsMainService.getFocusedWindow());
|
|
||||||
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
return true; // OK
|
|
||||||
}
|
|
||||||
|
|
||||||
private doOpenWorkspace(window: ICodeWindow, workspace: IWorkspaceIdentifier): IEnterWorkspaceResult {
|
|
||||||
window.focus();
|
|
||||||
|
|
||||||
// Register window for backups and migrate current backups over
|
|
||||||
let backupPath: string | undefined;
|
|
||||||
if (!window.config.extensionDevelopmentPath) {
|
|
||||||
backupPath = this.backupMainService.registerWorkspaceBackupSync({ workspace, remoteAuthority: window.remoteAuthority }, window.config.backupPath);
|
|
||||||
}
|
|
||||||
|
|
||||||
// if the window was opened on an untitled workspace, delete it.
|
|
||||||
if (window.openedWorkspace && this.workspacesMainService.isUntitledWorkspace(window.openedWorkspace)) {
|
|
||||||
this.workspacesMainService.deleteUntitledWorkspaceSync(window.openedWorkspace);
|
|
||||||
}
|
|
||||||
|
|
||||||
// Update window configuration properly based on transition to workspace
|
|
||||||
window.config.folderUri = undefined;
|
|
||||||
window.config.workspace = workspace;
|
|
||||||
window.config.backupPath = backupPath;
|
|
||||||
|
|
||||||
return { workspace, backupPath };
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
function resourceFromURIToOpen(openable: IWindowOpenable): URI {
|
|
||||||
if (isWorkspaceToOpen(openable)) {
|
|
||||||
return openable.workspaceUri;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (isFolderToOpen(openable)) {
|
|
||||||
return openable.folderUri;
|
|
||||||
}
|
|
||||||
|
|
||||||
return openable.fileUri;
|
|
||||||
}
|
|
||||||
|
|||||||
@@ -35,12 +35,15 @@ export function restoreWindowsState(data: WindowsStateStorageData | undefined):
|
|||||||
if (windowsState.lastActiveWindow) {
|
if (windowsState.lastActiveWindow) {
|
||||||
result.lastActiveWindow = restoreWindowState(windowsState.lastActiveWindow);
|
result.lastActiveWindow = restoreWindowState(windowsState.lastActiveWindow);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (windowsState.lastPluginDevelopmentHostWindow) {
|
if (windowsState.lastPluginDevelopmentHostWindow) {
|
||||||
result.lastPluginDevelopmentHostWindow = restoreWindowState(windowsState.lastPluginDevelopmentHostWindow);
|
result.lastPluginDevelopmentHostWindow = restoreWindowState(windowsState.lastPluginDevelopmentHostWindow);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (Array.isArray(windowsState.openedWindows)) {
|
if (Array.isArray(windowsState.openedWindows)) {
|
||||||
result.openedWindows = windowsState.openedWindows.map(windowState => restoreWindowState(windowState));
|
result.openedWindows = windowsState.openedWindows.map(windowState => restoreWindowState(windowState));
|
||||||
}
|
}
|
||||||
|
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -49,9 +52,11 @@ function restoreWindowState(windowState: ISerializedWindowState): IWindowState {
|
|||||||
if (windowState.backupPath) {
|
if (windowState.backupPath) {
|
||||||
result.backupPath = windowState.backupPath;
|
result.backupPath = windowState.backupPath;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (windowState.remoteAuthority) {
|
if (windowState.remoteAuthority) {
|
||||||
result.remoteAuthority = windowState.remoteAuthority;
|
result.remoteAuthority = windowState.remoteAuthority;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (windowState.folder) {
|
if (windowState.folder) {
|
||||||
result.folderUri = URI.parse(windowState.folder);
|
result.folderUri = URI.parse(windowState.folder);
|
||||||
} else if (windowState.folderUri) {
|
} else if (windowState.folderUri) {
|
||||||
@@ -59,11 +64,13 @@ function restoreWindowState(windowState: ISerializedWindowState): IWindowState {
|
|||||||
} else if (windowState.folderPath) {
|
} else if (windowState.folderPath) {
|
||||||
result.folderUri = URI.file(windowState.folderPath);
|
result.folderUri = URI.file(windowState.folderPath);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (windowState.workspaceIdentifier) {
|
if (windowState.workspaceIdentifier) {
|
||||||
result.workspace = { id: windowState.workspaceIdentifier.id, configPath: URI.parse(windowState.workspaceIdentifier.configURIPath) };
|
result.workspace = { id: windowState.workspaceIdentifier.id, configPath: URI.parse(windowState.workspaceIdentifier.configURIPath) };
|
||||||
} else if (windowState.workspace) {
|
} else if (windowState.workspace) {
|
||||||
result.workspace = { id: windowState.workspace.id, configPath: URI.file(windowState.workspace.configPath) };
|
result.workspace = { id: windowState.workspace.id, configPath: URI.file(windowState.workspace.configPath) };
|
||||||
}
|
}
|
||||||
|
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -3,19 +3,18 @@
|
|||||||
* Licensed under the Source EULA. See License.txt in the project root for license information.
|
* Licensed under the Source EULA. See License.txt in the project root for license information.
|
||||||
*--------------------------------------------------------------------------------------------*/
|
*--------------------------------------------------------------------------------------------*/
|
||||||
|
|
||||||
|
import * as os from 'os';
|
||||||
|
import * as fs from 'fs';
|
||||||
import { spawn, ChildProcess, SpawnOptions } from 'child_process';
|
import { spawn, ChildProcess, SpawnOptions } from 'child_process';
|
||||||
import { buildHelpMessage, buildVersionMessage, addArg, createWaitMarkerFile, OPTIONS } from 'vs/platform/environment/node/argv';
|
import { buildHelpMessage, buildVersionMessage, addArg, createWaitMarkerFile, OPTIONS } from 'vs/platform/environment/node/argv';
|
||||||
import { parseCLIProcessArgv } from 'vs/platform/environment/node/argvHelper';
|
import { parseCLIProcessArgv } from 'vs/platform/environment/node/argvHelper';
|
||||||
import { ParsedArgs } from 'vs/platform/environment/common/environment';
|
import { ParsedArgs } from 'vs/platform/environment/common/environment';
|
||||||
import product from 'vs/platform/product/common/product';
|
import product from 'vs/platform/product/common/product';
|
||||||
import * as paths from 'vs/base/common/path';
|
import * as paths from 'vs/base/common/path';
|
||||||
import * as os from 'os';
|
|
||||||
import * as fs from 'fs';
|
|
||||||
import { whenDeleted, writeFileSync } from 'vs/base/node/pfs';
|
import { whenDeleted, writeFileSync } from 'vs/base/node/pfs';
|
||||||
import { findFreePort, randomPort } from 'vs/base/node/ports';
|
import { findFreePort, randomPort } from 'vs/base/node/ports';
|
||||||
import { resolveTerminalEncoding } from 'vs/base/node/encoding';
|
import { resolveTerminalEncoding } from 'vs/base/node/encoding';
|
||||||
import * as iconv from 'iconv-lite';
|
import { isWindows } from 'vs/base/common/platform';
|
||||||
import { isWindows, isLinux } from 'vs/base/common/platform';
|
|
||||||
import { ProfilingSession, Target } from 'v8-inspect-profiler';
|
import { ProfilingSession, Target } from 'v8-inspect-profiler';
|
||||||
import { isString } from 'vs/base/common/types';
|
import { isString } from 'vs/base/common/types';
|
||||||
|
|
||||||
@@ -179,7 +178,8 @@ export async function main(argv: string[]): Promise<any> {
|
|||||||
if (!stdinFileError) {
|
if (!stdinFileError) {
|
||||||
|
|
||||||
// Pipe into tmp file using terminals encoding
|
// Pipe into tmp file using terminals encoding
|
||||||
resolveTerminalEncoding(verbose).then(encoding => {
|
resolveTerminalEncoding(verbose).then(async encoding => {
|
||||||
|
const iconv = await import('iconv-lite');
|
||||||
const converterStream = iconv.decodeStream(encoding);
|
const converterStream = iconv.decodeStream(encoding);
|
||||||
process.stdin.pipe(converterStream).pipe(stdinFileStream);
|
process.stdin.pipe(converterStream).pipe(stdinFileStream);
|
||||||
});
|
});
|
||||||
@@ -360,10 +360,6 @@ export async function main(argv: string[]): Promise<any> {
|
|||||||
options['stdio'] = 'ignore';
|
options['stdio'] = 'ignore';
|
||||||
}
|
}
|
||||||
|
|
||||||
if (isLinux) {
|
|
||||||
addArg(argv, '--no-sandbox'); // Electron 6 introduces a chrome-sandbox that requires root to run. This can fail. Disable sandbox via --no-sandbox
|
|
||||||
}
|
|
||||||
|
|
||||||
const child = spawn(process.execPath, argv.slice(2), options);
|
const child = spawn(process.execPath, argv.slice(2), options);
|
||||||
|
|
||||||
if (args.wait && waitMarkerFilePath) {
|
if (args.wait && waitMarkerFilePath) {
|
||||||
|
|||||||
@@ -1,131 +0,0 @@
|
|||||||
/*---------------------------------------------------------------------------------------------
|
|
||||||
* Copyright (c) Microsoft Corporation. All rights reserved.
|
|
||||||
* Licensed under the Source EULA. See License.txt in the project root for license information.
|
|
||||||
*--------------------------------------------------------------------------------------------*/
|
|
||||||
|
|
||||||
import * as platform from 'vs/base/common/platform';
|
|
||||||
import * as extpath from 'vs/base/common/extpath';
|
|
||||||
import { OpenContext } from 'vs/platform/windows/common/windows';
|
|
||||||
import { IWorkspaceIdentifier, IResolvedWorkspace, ISingleFolderWorkspaceIdentifier, isSingleFolderWorkspaceIdentifier, isWorkspaceIdentifier } from 'vs/platform/workspaces/common/workspaces';
|
|
||||||
import { URI } from 'vs/base/common/uri';
|
|
||||||
import { isEqual, isEqualOrParent } from 'vs/base/common/resources';
|
|
||||||
|
|
||||||
export interface ISimpleWindow {
|
|
||||||
openedWorkspace?: IWorkspaceIdentifier;
|
|
||||||
openedFolderUri?: URI;
|
|
||||||
|
|
||||||
extensionDevelopmentPath?: string[];
|
|
||||||
lastFocusTime: number;
|
|
||||||
}
|
|
||||||
|
|
||||||
export interface IBestWindowOrFolderOptions<W extends ISimpleWindow> {
|
|
||||||
windows: W[];
|
|
||||||
newWindow: boolean;
|
|
||||||
context: OpenContext;
|
|
||||||
fileUri?: URI;
|
|
||||||
userHome?: string;
|
|
||||||
codeSettingsFolder?: string;
|
|
||||||
localWorkspaceResolver: (workspace: IWorkspaceIdentifier) => IResolvedWorkspace | null;
|
|
||||||
}
|
|
||||||
|
|
||||||
export function findBestWindowOrFolderForFile<W extends ISimpleWindow>({ windows, newWindow, context, fileUri, localWorkspaceResolver: workspaceResolver }: IBestWindowOrFolderOptions<W>): W | undefined {
|
|
||||||
if (!newWindow && fileUri && (context === OpenContext.DESKTOP || context === OpenContext.CLI || context === OpenContext.DOCK)) {
|
|
||||||
const windowOnFilePath = findWindowOnFilePath(windows, fileUri, workspaceResolver);
|
|
||||||
if (windowOnFilePath) {
|
|
||||||
return windowOnFilePath;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return !newWindow ? getLastActiveWindow(windows) : undefined;
|
|
||||||
}
|
|
||||||
|
|
||||||
function findWindowOnFilePath<W extends ISimpleWindow>(windows: W[], fileUri: URI, localWorkspaceResolver: (workspace: IWorkspaceIdentifier) => IResolvedWorkspace | null): W | null {
|
|
||||||
|
|
||||||
// First check for windows with workspaces that have a parent folder of the provided path opened
|
|
||||||
for (const window of windows) {
|
|
||||||
const workspace = window.openedWorkspace;
|
|
||||||
if (workspace) {
|
|
||||||
const resolvedWorkspace = localWorkspaceResolver(workspace);
|
|
||||||
if (resolvedWorkspace) {
|
|
||||||
// workspace could be resolved: It's in the local file system
|
|
||||||
if (resolvedWorkspace.folders.some(folder => isEqualOrParent(fileUri, folder.uri))) {
|
|
||||||
return window;
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
// use the config path instead
|
|
||||||
if (isEqualOrParent(fileUri, workspace.configPath)) {
|
|
||||||
return window;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// Then go with single folder windows that are parent of the provided file path
|
|
||||||
const singleFolderWindowsOnFilePath = windows.filter(window => window.openedFolderUri && isEqualOrParent(fileUri, window.openedFolderUri));
|
|
||||||
if (singleFolderWindowsOnFilePath.length) {
|
|
||||||
return singleFolderWindowsOnFilePath.sort((a, b) => -(a.openedFolderUri!.path.length - b.openedFolderUri!.path.length))[0];
|
|
||||||
}
|
|
||||||
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
export function getLastActiveWindow<W extends ISimpleWindow>(windows: W[]): W | undefined {
|
|
||||||
const lastFocusedDate = Math.max.apply(Math, windows.map(window => window.lastFocusTime));
|
|
||||||
|
|
||||||
return windows.filter(window => window.lastFocusTime === lastFocusedDate)[0];
|
|
||||||
}
|
|
||||||
|
|
||||||
export function findWindowOnWorkspace<W extends ISimpleWindow>(windows: W[], workspace: (IWorkspaceIdentifier | ISingleFolderWorkspaceIdentifier)): W | null {
|
|
||||||
if (isSingleFolderWorkspaceIdentifier(workspace)) {
|
|
||||||
for (const window of windows) {
|
|
||||||
// match on folder
|
|
||||||
if (isSingleFolderWorkspaceIdentifier(workspace)) {
|
|
||||||
if (window.openedFolderUri && isEqual(window.openedFolderUri, workspace)) {
|
|
||||||
return window;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
} else if (isWorkspaceIdentifier(workspace)) {
|
|
||||||
for (const window of windows) {
|
|
||||||
// match on workspace
|
|
||||||
if (window.openedWorkspace && window.openedWorkspace.id === workspace.id) {
|
|
||||||
return window;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
export function findWindowOnExtensionDevelopmentPath<W extends ISimpleWindow>(windows: W[], extensionDevelopmentPaths: string[]): W | null {
|
|
||||||
|
|
||||||
const matches = (uriString: string): boolean => {
|
|
||||||
return extensionDevelopmentPaths.some(p => extpath.isEqual(p, uriString, !platform.isLinux /* ignorecase */));
|
|
||||||
};
|
|
||||||
|
|
||||||
for (const window of windows) {
|
|
||||||
// match on extension development path. The path can be one or more paths or uri strings, using paths.isEqual is not 100% correct but good enough
|
|
||||||
const currPaths = window.extensionDevelopmentPath;
|
|
||||||
if (currPaths && currPaths.some(p => matches(p))) {
|
|
||||||
return window;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
export function findWindowOnWorkspaceOrFolderUri<W extends ISimpleWindow>(windows: W[], uri: URI | undefined): W | null {
|
|
||||||
if (!uri) {
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
for (const window of windows) {
|
|
||||||
// check for workspace config path
|
|
||||||
if (window.openedWorkspace && isEqual(window.openedWorkspace.configPath, uri)) {
|
|
||||||
return window;
|
|
||||||
}
|
|
||||||
|
|
||||||
// check for folder path
|
|
||||||
if (window.openedFolderUri && isEqual(window.openedFolderUri, uri)) {
|
|
||||||
return window;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
@@ -1 +0,0 @@
|
|||||||
{}
|
|
||||||
@@ -11,7 +11,7 @@ import * as platform from 'vs/base/common/platform';
|
|||||||
import { CharWidthRequest, CharWidthRequestType, readCharWidths } from 'vs/editor/browser/config/charWidthReader';
|
import { CharWidthRequest, CharWidthRequestType, readCharWidths } from 'vs/editor/browser/config/charWidthReader';
|
||||||
import { ElementSizeObserver } from 'vs/editor/browser/config/elementSizeObserver';
|
import { ElementSizeObserver } from 'vs/editor/browser/config/elementSizeObserver';
|
||||||
import { CommonEditorConfiguration, IEnvConfiguration } from 'vs/editor/common/config/commonEditorConfig';
|
import { CommonEditorConfiguration, IEnvConfiguration } from 'vs/editor/common/config/commonEditorConfig';
|
||||||
import { IEditorOptions, EditorOption } from 'vs/editor/common/config/editorOptions';
|
import { EditorOption, IEditorConstructionOptions } from 'vs/editor/common/config/editorOptions';
|
||||||
import { BareFontInfo, FontInfo } from 'vs/editor/common/config/fontInfo';
|
import { BareFontInfo, FontInfo } from 'vs/editor/common/config/fontInfo';
|
||||||
import { IDimension } from 'vs/editor/common/editorCommon';
|
import { IDimension } from 'vs/editor/common/editorCommon';
|
||||||
import { IAccessibilityService } from 'vs/platform/accessibility/common/accessibility';
|
import { IAccessibilityService } from 'vs/platform/accessibility/common/accessibility';
|
||||||
@@ -310,13 +310,13 @@ export class Configuration extends CommonEditorConfiguration {
|
|||||||
|
|
||||||
constructor(
|
constructor(
|
||||||
isSimpleWidget: boolean,
|
isSimpleWidget: boolean,
|
||||||
options: IEditorOptions,
|
options: IEditorConstructionOptions,
|
||||||
referenceDomElement: HTMLElement | null = null,
|
referenceDomElement: HTMLElement | null = null,
|
||||||
private readonly accessibilityService: IAccessibilityService
|
private readonly accessibilityService: IAccessibilityService
|
||||||
) {
|
) {
|
||||||
super(isSimpleWidget, options);
|
super(isSimpleWidget, options);
|
||||||
|
|
||||||
this._elementSizeObserver = this._register(new ElementSizeObserver(referenceDomElement, () => this._onReferenceDomElementSizeChanged()));
|
this._elementSizeObserver = this._register(new ElementSizeObserver(referenceDomElement, options.dimension, () => this._onReferenceDomElementSizeChanged()));
|
||||||
|
|
||||||
this._register(CSSBasedConfiguration.INSTANCE.onDidChange(() => this._onCSSBasedConfigurationChanged()));
|
this._register(CSSBasedConfiguration.INSTANCE.onDidChange(() => this._onCSSBasedConfigurationChanged()));
|
||||||
|
|
||||||
|
|||||||
@@ -14,14 +14,14 @@ export class ElementSizeObserver extends Disposable {
|
|||||||
private width: number;
|
private width: number;
|
||||||
private height: number;
|
private height: number;
|
||||||
|
|
||||||
constructor(referenceDomElement: HTMLElement | null, changeCallback: () => void) {
|
constructor(referenceDomElement: HTMLElement | null, dimension: IDimension | undefined, changeCallback: () => void) {
|
||||||
super();
|
super();
|
||||||
this.referenceDomElement = referenceDomElement;
|
this.referenceDomElement = referenceDomElement;
|
||||||
this.changeCallback = changeCallback;
|
this.changeCallback = changeCallback;
|
||||||
this.measureReferenceDomElementToken = -1;
|
this.measureReferenceDomElementToken = -1;
|
||||||
this.width = -1;
|
this.width = -1;
|
||||||
this.height = -1;
|
this.height = -1;
|
||||||
this.measureReferenceDomElement(false);
|
this.measureReferenceDomElement(false, dimension);
|
||||||
}
|
}
|
||||||
|
|
||||||
public dispose(): void {
|
public dispose(): void {
|
||||||
@@ -75,4 +75,4 @@ export class ElementSizeObserver extends Disposable {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -190,7 +190,7 @@ class TouchHandler extends MouseHandler {
|
|||||||
constructor(context: ViewContext, viewController: ViewController, viewHelper: IPointerHandlerHelper) {
|
constructor(context: ViewContext, viewController: ViewController, viewHelper: IPointerHandlerHelper) {
|
||||||
super(context, viewController, viewHelper);
|
super(context, viewController, viewHelper);
|
||||||
|
|
||||||
Gesture.addTarget(this.viewHelper.linesContentDomNode);
|
this._register(Gesture.addTarget(this.viewHelper.linesContentDomNode));
|
||||||
|
|
||||||
this._register(dom.addDisposableListener(this.viewHelper.linesContentDomNode, EventType.Tap, (e) => this.onTap(e)));
|
this._register(dom.addDisposableListener(this.viewHelper.linesContentDomNode, EventType.Tap, (e) => this.onTap(e)));
|
||||||
this._register(dom.addDisposableListener(this.viewHelper.linesContentDomNode, EventType.Change, (e) => this.onChange(e)));
|
this._register(dom.addDisposableListener(this.viewHelper.linesContentDomNode, EventType.Change, (e) => this.onChange(e)));
|
||||||
|
|||||||
@@ -152,6 +152,10 @@ export class TextAreaHandler extends ViewPart {
|
|||||||
this.textArea.setAttribute('aria-haspopup', 'false');
|
this.textArea.setAttribute('aria-haspopup', 'false');
|
||||||
this.textArea.setAttribute('aria-autocomplete', 'both');
|
this.textArea.setAttribute('aria-autocomplete', 'both');
|
||||||
|
|
||||||
|
if (platform.isWeb && options.get(EditorOption.readOnly)) {
|
||||||
|
this.textArea.setAttribute('readonly', 'true');
|
||||||
|
}
|
||||||
|
|
||||||
this.textAreaCover = createFastDomNode(document.createElement('div'));
|
this.textAreaCover = createFastDomNode(document.createElement('div'));
|
||||||
this.textAreaCover.setPosition('absolute');
|
this.textAreaCover.setPosition('absolute');
|
||||||
|
|
||||||
@@ -395,6 +399,14 @@ export class TextAreaHandler extends ViewPart {
|
|||||||
this._copyWithSyntaxHighlighting = options.get(EditorOption.copyWithSyntaxHighlighting);
|
this._copyWithSyntaxHighlighting = options.get(EditorOption.copyWithSyntaxHighlighting);
|
||||||
this.textArea.setAttribute('aria-label', this._getAriaLabel(options));
|
this.textArea.setAttribute('aria-label', this._getAriaLabel(options));
|
||||||
|
|
||||||
|
if (platform.isWeb && e.hasChanged(EditorOption.readOnly)) {
|
||||||
|
if (options.get(EditorOption.readOnly)) {
|
||||||
|
this.textArea.setAttribute('readonly', 'true');
|
||||||
|
} else {
|
||||||
|
this.textArea.removeAttribute('readonly');
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
if (e.hasChanged(EditorOption.accessibilitySupport)) {
|
if (e.hasChanged(EditorOption.accessibilitySupport)) {
|
||||||
this._textAreaInput.writeScreenReaderContent('strategy changed');
|
this._textAreaInput.writeScreenReaderContent('strategy changed');
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -29,6 +29,7 @@ import { registerThemingParticipant } from 'vs/platform/theme/common/themeServic
|
|||||||
import { ModelDecorationMinimapOptions } from 'vs/editor/common/model/textModel';
|
import { ModelDecorationMinimapOptions } from 'vs/editor/common/model/textModel';
|
||||||
import { Selection } from 'vs/editor/common/core/selection';
|
import { Selection } from 'vs/editor/common/core/selection';
|
||||||
import { Color } from 'vs/base/common/color';
|
import { Color } from 'vs/base/common/color';
|
||||||
|
import { GestureEvent, EventType, Gesture } from 'vs/base/browser/touch';
|
||||||
|
|
||||||
function getMinimapLineHeight(renderMinimap: RenderMinimap): number {
|
function getMinimapLineHeight(renderMinimap: RenderMinimap): number {
|
||||||
if (renderMinimap === RenderMinimap.Large) {
|
if (renderMinimap === RenderMinimap.Large) {
|
||||||
@@ -208,6 +209,10 @@ class MinimapLayout {
|
|||||||
return Math.round(desiredSliderPosition / this._computedSliderRatio);
|
return Math.round(desiredSliderPosition / this._computedSliderRatio);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public getDesiredScrollTopFromTouchLocation(pageY: number): number {
|
||||||
|
return Math.round((pageY - this.sliderHeight / 2) / this._computedSliderRatio);
|
||||||
|
}
|
||||||
|
|
||||||
public static create(
|
public static create(
|
||||||
options: MinimapOptions,
|
options: MinimapOptions,
|
||||||
viewportStartLineNumber: number,
|
viewportStartLineNumber: number,
|
||||||
@@ -451,12 +456,17 @@ export class Minimap extends ViewPart {
|
|||||||
private readonly _mouseDownListener: IDisposable;
|
private readonly _mouseDownListener: IDisposable;
|
||||||
private readonly _sliderMouseMoveMonitor: GlobalMouseMoveMonitor<IStandardMouseMoveEventData>;
|
private readonly _sliderMouseMoveMonitor: GlobalMouseMoveMonitor<IStandardMouseMoveEventData>;
|
||||||
private readonly _sliderMouseDownListener: IDisposable;
|
private readonly _sliderMouseDownListener: IDisposable;
|
||||||
|
private readonly _gestureDisposable: IDisposable;
|
||||||
|
private readonly _sliderTouchStartListener: IDisposable;
|
||||||
|
private readonly _sliderTouchMoveListener: IDisposable;
|
||||||
|
private readonly _sliderTouchEndListener: IDisposable;
|
||||||
|
|
||||||
private _options: MinimapOptions;
|
private _options: MinimapOptions;
|
||||||
private _lastRenderData: RenderData | null;
|
private _lastRenderData: RenderData | null;
|
||||||
private _selections: Selection[] = [];
|
private _selections: Selection[] = [];
|
||||||
private _selectionColor: Color | undefined;
|
private _selectionColor: Color | undefined;
|
||||||
private _renderDecorations: boolean = false;
|
private _renderDecorations: boolean = false;
|
||||||
|
private _gestureInProgress: boolean = false;
|
||||||
private _buffers: MinimapBuffers | null;
|
private _buffers: MinimapBuffers | null;
|
||||||
|
|
||||||
constructor(context: ViewContext) {
|
constructor(context: ViewContext) {
|
||||||
@@ -566,12 +576,50 @@ export class Minimap extends ViewPart {
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
|
this._gestureDisposable = Gesture.addTarget(this._domNode.domNode);
|
||||||
|
this._sliderTouchStartListener = dom.addDisposableListener(this._domNode.domNode, EventType.Start, (e: GestureEvent) => {
|
||||||
|
e.preventDefault();
|
||||||
|
e.stopPropagation();
|
||||||
|
if (this._lastRenderData) {
|
||||||
|
this._slider.toggleClassName('active', true);
|
||||||
|
this._gestureInProgress = true;
|
||||||
|
this.scrollDueToTouchEvent(e);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
this._sliderTouchMoveListener = dom.addStandardDisposableListener(this._domNode.domNode, EventType.Change, (e: GestureEvent) => {
|
||||||
|
e.preventDefault();
|
||||||
|
e.stopPropagation();
|
||||||
|
if (this._lastRenderData && this._gestureInProgress) {
|
||||||
|
this.scrollDueToTouchEvent(e);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
this._sliderTouchEndListener = dom.addStandardDisposableListener(this._domNode.domNode, EventType.End, (e: GestureEvent) => {
|
||||||
|
e.preventDefault();
|
||||||
|
e.stopPropagation();
|
||||||
|
this._gestureInProgress = false;
|
||||||
|
this._slider.toggleClassName('active', false);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
private scrollDueToTouchEvent(touch: GestureEvent) {
|
||||||
|
const startY = this._domNode.domNode.getBoundingClientRect().top;
|
||||||
|
const scrollTop = this._lastRenderData!.renderedLayout.getDesiredScrollTopFromTouchLocation(touch.pageY - startY);
|
||||||
|
this._context.viewLayout.setScrollPositionNow({
|
||||||
|
scrollTop: scrollTop
|
||||||
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
public dispose(): void {
|
public dispose(): void {
|
||||||
this._mouseDownListener.dispose();
|
this._mouseDownListener.dispose();
|
||||||
this._sliderMouseMoveMonitor.dispose();
|
this._sliderMouseMoveMonitor.dispose();
|
||||||
this._sliderMouseDownListener.dispose();
|
this._sliderMouseDownListener.dispose();
|
||||||
|
this._gestureDisposable.dispose();
|
||||||
|
this._sliderTouchStartListener.dispose();
|
||||||
|
this._sliderTouchMoveListener.dispose();
|
||||||
|
this._sliderTouchEndListener.dispose();
|
||||||
super.dispose();
|
super.dispose();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -23,7 +23,7 @@ import { ICodeEditorService } from 'vs/editor/browser/services/codeEditorService
|
|||||||
import { ICommandDelegate } from 'vs/editor/browser/view/viewController';
|
import { ICommandDelegate } from 'vs/editor/browser/view/viewController';
|
||||||
import { IContentWidgetData, IOverlayWidgetData, View } from 'vs/editor/browser/view/viewImpl';
|
import { IContentWidgetData, IOverlayWidgetData, View } from 'vs/editor/browser/view/viewImpl';
|
||||||
import { ViewOutgoingEvents } from 'vs/editor/browser/view/viewOutgoingEvents';
|
import { ViewOutgoingEvents } from 'vs/editor/browser/view/viewOutgoingEvents';
|
||||||
import { ConfigurationChangedEvent, EditorLayoutInfo, IEditorOptions, EditorOption, IComputedEditorOptions, FindComputedEditorOptionValueById } from 'vs/editor/common/config/editorOptions';
|
import { ConfigurationChangedEvent, EditorLayoutInfo, IEditorOptions, EditorOption, IComputedEditorOptions, FindComputedEditorOptionValueById, IEditorConstructionOptions } from 'vs/editor/common/config/editorOptions';
|
||||||
import { Cursor, CursorStateChangedEvent } from 'vs/editor/common/controller/cursor';
|
import { Cursor, CursorStateChangedEvent } from 'vs/editor/common/controller/cursor';
|
||||||
import { CursorColumns, ICursors } from 'vs/editor/common/controller/cursorCommon';
|
import { CursorColumns, ICursors } from 'vs/editor/common/controller/cursorCommon';
|
||||||
import { ICursorPositionChangedEvent, ICursorSelectionChangedEvent } from 'vs/editor/common/controller/cursorEvents';
|
import { ICursorPositionChangedEvent, ICursorSelectionChangedEvent } from 'vs/editor/common/controller/cursorEvents';
|
||||||
@@ -236,7 +236,7 @@ export class CodeEditorWidget extends Disposable implements editorBrowser.ICodeE
|
|||||||
|
|
||||||
constructor(
|
constructor(
|
||||||
domElement: HTMLElement,
|
domElement: HTMLElement,
|
||||||
options: IEditorOptions,
|
options: IEditorConstructionOptions,
|
||||||
codeEditorWidgetOptions: ICodeEditorWidgetOptions,
|
codeEditorWidgetOptions: ICodeEditorWidgetOptions,
|
||||||
@IInstantiationService instantiationService: IInstantiationService,
|
@IInstantiationService instantiationService: IInstantiationService,
|
||||||
@ICodeEditorService codeEditorService: ICodeEditorService,
|
@ICodeEditorService codeEditorService: ICodeEditorService,
|
||||||
@@ -329,7 +329,7 @@ export class CodeEditorWidget extends Disposable implements editorBrowser.ICodeE
|
|||||||
this._codeEditorService.addCodeEditor(this);
|
this._codeEditorService.addCodeEditor(this);
|
||||||
}
|
}
|
||||||
|
|
||||||
protected _createConfiguration(options: IEditorOptions, accessibilityService: IAccessibilityService): editorCommon.IConfiguration {
|
protected _createConfiguration(options: IEditorConstructionOptions, accessibilityService: IAccessibilityService): editorCommon.IConfiguration {
|
||||||
return new Configuration(this.isSimpleWidget, options, this._domElement, accessibilityService);
|
return new Configuration(this.isSimpleWidget, options, this._domElement, accessibilityService);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -12,6 +12,7 @@ import { USUAL_WORD_SEPARATORS } from 'vs/editor/common/model/wordHelper';
|
|||||||
import { AccessibilitySupport } from 'vs/platform/accessibility/common/accessibility';
|
import { AccessibilitySupport } from 'vs/platform/accessibility/common/accessibility';
|
||||||
import { isObject } from 'vs/base/common/types';
|
import { isObject } from 'vs/base/common/types';
|
||||||
import { IConfigurationPropertySchema } from 'vs/platform/configuration/common/configurationRegistry';
|
import { IConfigurationPropertySchema } from 'vs/platform/configuration/common/configurationRegistry';
|
||||||
|
import { IDimension } from 'vs/editor/common/editorCommon';
|
||||||
|
|
||||||
//#region typed options
|
//#region typed options
|
||||||
|
|
||||||
@@ -516,6 +517,13 @@ export interface IEditorOptions {
|
|||||||
showUnused?: boolean;
|
showUnused?: boolean;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
export interface IEditorConstructionOptions extends IEditorOptions {
|
||||||
|
/**
|
||||||
|
* The initial editor dimension (to avoid measuring the container).
|
||||||
|
*/
|
||||||
|
dimension?: IDimension;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Configuration options for the diff editor.
|
* Configuration options for the diff editor.
|
||||||
*/
|
*/
|
||||||
|
|||||||
@@ -280,6 +280,8 @@ export interface IEditor {
|
|||||||
/**
|
/**
|
||||||
* Instructs the editor to remeasure its container. This method should
|
* Instructs the editor to remeasure its container. This method should
|
||||||
* be called when the container of the editor gets resized.
|
* be called when the container of the editor gets resized.
|
||||||
|
*
|
||||||
|
* If a dimension is passed in, the passed in value will be used.
|
||||||
*/
|
*/
|
||||||
layout(dimension?: IDimension): void;
|
layout(dimension?: IDimension): void;
|
||||||
|
|
||||||
|
|||||||
@@ -922,7 +922,7 @@ export interface DocumentSymbol {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* The document symbol provider interface defines the contract between extensions and
|
* The document symbol provider interface defines the contract between extensions and
|
||||||
* the [go to symbol](https://code.visualstudio.com/docs/editor/editingevolved#_goto-symbol)-feature.
|
* the [go to symbol](https://code.visualstudio.com/docs/editor/editingevolved#_go-to-symbol)-feature.
|
||||||
*/
|
*/
|
||||||
export interface DocumentSymbolProvider {
|
export interface DocumentSymbolProvider {
|
||||||
|
|
||||||
|
|||||||
@@ -14,7 +14,7 @@ import { ScrollType, IEditorContribution } from 'vs/editor/common/editorCommon';
|
|||||||
import { ITextModel } from 'vs/editor/common/model';
|
import { ITextModel } from 'vs/editor/common/model';
|
||||||
import { registerEditorAction, registerEditorContribution, ServicesAccessor, EditorAction, registerInstantiatedEditorAction } from 'vs/editor/browser/editorExtensions';
|
import { registerEditorAction, registerEditorContribution, ServicesAccessor, EditorAction, registerInstantiatedEditorAction } from 'vs/editor/browser/editorExtensions';
|
||||||
import { ICodeEditor, IEditorMouseEvent, MouseTargetType } from 'vs/editor/browser/editorBrowser';
|
import { ICodeEditor, IEditorMouseEvent, MouseTargetType } from 'vs/editor/browser/editorBrowser';
|
||||||
import { FoldingModel, setCollapseStateAtLevel, CollapseMemento, setCollapseStateLevelsDown, setCollapseStateLevelsUp, setCollapseStateForMatchingLines, setCollapseStateForType } from 'vs/editor/contrib/folding/foldingModel';
|
import { FoldingModel, setCollapseStateAtLevel, CollapseMemento, setCollapseStateLevelsDown, setCollapseStateLevelsUp, setCollapseStateForMatchingLines, setCollapseStateForType, toggleCollapseState } from 'vs/editor/contrib/folding/foldingModel';
|
||||||
import { FoldingDecorationProvider } from './foldingDecorations';
|
import { FoldingDecorationProvider } from './foldingDecorations';
|
||||||
import { FoldingRegions, FoldingRegion } from './foldingRanges';
|
import { FoldingRegions, FoldingRegion } from './foldingRanges';
|
||||||
import { EditorContextKeys } from 'vs/editor/common/editorContextKeys';
|
import { EditorContextKeys } from 'vs/editor/common/editorContextKeys';
|
||||||
@@ -656,6 +656,30 @@ class FoldAction extends FoldingAction<FoldingArguments> {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
class ToggleFoldAction extends FoldingAction<void> {
|
||||||
|
|
||||||
|
constructor() {
|
||||||
|
super({
|
||||||
|
id: 'editor.toggleFold',
|
||||||
|
label: nls.localize('toggleFoldAction.label', "Toggle Fold"),
|
||||||
|
alias: 'Toggle Fold',
|
||||||
|
precondition: CONTEXT_FOLDING_ENABLED,
|
||||||
|
kbOpts: {
|
||||||
|
kbExpr: EditorContextKeys.editorTextFocus,
|
||||||
|
primary: KeyChord(KeyMod.CtrlCmd | KeyCode.KEY_K, KeyMod.CtrlCmd | KeyCode.KEY_K),
|
||||||
|
weight: KeybindingWeight.EditorContrib
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
invoke(_foldingController: FoldingController, foldingModel: FoldingModel, editor: ICodeEditor): void {
|
||||||
|
let selectedLines = this.getSelectedLines(editor);
|
||||||
|
toggleCollapseState(foldingModel, 1, selectedLines);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
class FoldRecursivelyAction extends FoldingAction<void> {
|
class FoldRecursivelyAction extends FoldingAction<void> {
|
||||||
|
|
||||||
constructor() {
|
constructor() {
|
||||||
@@ -842,6 +866,7 @@ registerEditorAction(UnfoldAllAction);
|
|||||||
registerEditorAction(FoldAllBlockCommentsAction);
|
registerEditorAction(FoldAllBlockCommentsAction);
|
||||||
registerEditorAction(FoldAllRegionsAction);
|
registerEditorAction(FoldAllRegionsAction);
|
||||||
registerEditorAction(UnfoldAllRegionsAction);
|
registerEditorAction(UnfoldAllRegionsAction);
|
||||||
|
registerEditorAction(ToggleFoldAction);
|
||||||
|
|
||||||
for (let i = 1; i <= 7; i++) {
|
for (let i = 1; i <= 7; i++) {
|
||||||
registerInstantiatedEditorAction(
|
registerInstantiatedEditorAction(
|
||||||
|
|||||||
@@ -242,6 +242,26 @@ export class FoldingModel {
|
|||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Collapse or expand the regions at the given locations
|
||||||
|
* @param levels The number of levels. Use 1 to only impact the regions at the location, use Number.MAX_VALUE for all levels.
|
||||||
|
* @param lineNumbers the location of the regions to collapse or expand, or if not set, all regions in the model.
|
||||||
|
*/
|
||||||
|
export function toggleCollapseState(foldingModel: FoldingModel, levels: number, lineNumbers: number[]) {
|
||||||
|
let toToggle: FoldingRegion[] = [];
|
||||||
|
for (let lineNumber of lineNumbers) {
|
||||||
|
let region = foldingModel.getRegionAtLine(lineNumber);
|
||||||
|
if (region) {
|
||||||
|
const doCollapse = !region.isCollapsed;
|
||||||
|
toToggle.push(region);
|
||||||
|
if (levels > 1) {
|
||||||
|
let regionsInside = foldingModel.getRegionsInside(region, (r, level: number) => r.isCollapsed !== doCollapse && level < levels);
|
||||||
|
toToggle.push(...regionsInside);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
foldingModel.toggleCollapseState(toToggle);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|||||||
@@ -37,7 +37,7 @@
|
|||||||
margin: 8px 0;
|
margin: 8px 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
.monaco-editor-hover p > code {
|
.monaco-editor-hover code {
|
||||||
font-family: var(--monaco-monospace-font);
|
font-family: var(--monaco-monospace-font);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -53,7 +53,7 @@
|
|||||||
padding-left: 20px;
|
padding-left: 20px;
|
||||||
}
|
}
|
||||||
|
|
||||||
.monaco-editor .suggest-widget > .details p > code {
|
.monaco-editor .suggest-widget > .details p code {
|
||||||
font-family: var(--monaco-monospace-font);
|
font-family: var(--monaco-monospace-font);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -21,7 +21,7 @@ import { Selection } from 'vs/editor/common/core/selection';
|
|||||||
import { IEditorContribution } from 'vs/editor/common/editorCommon';
|
import { IEditorContribution } from 'vs/editor/common/editorCommon';
|
||||||
import { EditorContextKeys } from 'vs/editor/common/editorContextKeys';
|
import { EditorContextKeys } from 'vs/editor/common/editorContextKeys';
|
||||||
import { ToggleTabFocusModeAction } from 'vs/editor/contrib/toggleTabFocusMode/toggleTabFocusMode';
|
import { ToggleTabFocusModeAction } from 'vs/editor/contrib/toggleTabFocusMode/toggleTabFocusMode';
|
||||||
import { IEditorConstructionOptions } from 'vs/editor/standalone/browser/standaloneCodeEditor';
|
import { IStandaloneEditorConstructionOptions } from 'vs/editor/standalone/browser/standaloneCodeEditor';
|
||||||
import { IContextKey, IContextKeyService, RawContextKey } from 'vs/platform/contextkey/common/contextkey';
|
import { IContextKey, IContextKeyService, RawContextKey } from 'vs/platform/contextkey/common/contextkey';
|
||||||
import { IInstantiationService, ServicesAccessor } from 'vs/platform/instantiation/common/instantiation';
|
import { IInstantiationService, ServicesAccessor } from 'vs/platform/instantiation/common/instantiation';
|
||||||
import { IKeybindingService } from 'vs/platform/keybinding/common/keybinding';
|
import { IKeybindingService } from 'vs/platform/keybinding/common/keybinding';
|
||||||
@@ -164,7 +164,7 @@ class AccessibilityHelpWidget extends Widget implements IOverlayWidget {
|
|||||||
if (e.equals(KeyMod.CtrlCmd | KeyCode.KEY_H)) {
|
if (e.equals(KeyMod.CtrlCmd | KeyCode.KEY_H)) {
|
||||||
alert(AccessibilityHelpNLS.openingDocs);
|
alert(AccessibilityHelpNLS.openingDocs);
|
||||||
|
|
||||||
let url = (<IEditorConstructionOptions>this._editor.getRawOptions()).accessibilityHelpUrl;
|
let url = (<IStandaloneEditorConstructionOptions>this._editor.getRawOptions()).accessibilityHelpUrl;
|
||||||
if (typeof url === 'undefined') {
|
if (typeof url === 'undefined') {
|
||||||
url = 'https://go.microsoft.com/fwlink/?linkid=852450';
|
url = 'https://go.microsoft.com/fwlink/?linkid=852450';
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -10,7 +10,7 @@ import { ICodeEditor, IDiffEditor } from 'vs/editor/browser/editorBrowser';
|
|||||||
import { ICodeEditorService } from 'vs/editor/browser/services/codeEditorService';
|
import { ICodeEditorService } from 'vs/editor/browser/services/codeEditorService';
|
||||||
import { CodeEditorWidget } from 'vs/editor/browser/widget/codeEditorWidget';
|
import { CodeEditorWidget } from 'vs/editor/browser/widget/codeEditorWidget';
|
||||||
import { DiffEditorWidget } from 'vs/editor/browser/widget/diffEditorWidget';
|
import { DiffEditorWidget } from 'vs/editor/browser/widget/diffEditorWidget';
|
||||||
import { IDiffEditorOptions, IEditorOptions } from 'vs/editor/common/config/editorOptions';
|
import { IDiffEditorOptions, IEditorOptions, IEditorConstructionOptions } from 'vs/editor/common/config/editorOptions';
|
||||||
import { InternalEditorAction } from 'vs/editor/common/editorAction';
|
import { InternalEditorAction } from 'vs/editor/common/editorAction';
|
||||||
import { IModelChangedEvent } from 'vs/editor/common/editorCommon';
|
import { IModelChangedEvent } from 'vs/editor/common/editorCommon';
|
||||||
import { ITextModel } from 'vs/editor/common/model';
|
import { ITextModel } from 'vs/editor/common/model';
|
||||||
@@ -79,7 +79,7 @@ export interface IActionDescriptor {
|
|||||||
/**
|
/**
|
||||||
* The options to create an editor.
|
* The options to create an editor.
|
||||||
*/
|
*/
|
||||||
export interface IEditorConstructionOptions extends IEditorOptions {
|
export interface IStandaloneEditorConstructionOptions extends IEditorConstructionOptions {
|
||||||
/**
|
/**
|
||||||
* The initial model associated with this code editor.
|
* The initial model associated with this code editor.
|
||||||
*/
|
*/
|
||||||
@@ -158,7 +158,7 @@ export class StandaloneCodeEditor extends CodeEditorWidget implements IStandalon
|
|||||||
|
|
||||||
constructor(
|
constructor(
|
||||||
domElement: HTMLElement,
|
domElement: HTMLElement,
|
||||||
options: IEditorConstructionOptions,
|
options: IStandaloneEditorConstructionOptions,
|
||||||
@IInstantiationService instantiationService: IInstantiationService,
|
@IInstantiationService instantiationService: IInstantiationService,
|
||||||
@ICodeEditorService codeEditorService: ICodeEditorService,
|
@ICodeEditorService codeEditorService: ICodeEditorService,
|
||||||
@ICommandService commandService: ICommandService,
|
@ICommandService commandService: ICommandService,
|
||||||
@@ -287,7 +287,7 @@ export class StandaloneEditor extends StandaloneCodeEditor implements IStandalon
|
|||||||
|
|
||||||
constructor(
|
constructor(
|
||||||
domElement: HTMLElement,
|
domElement: HTMLElement,
|
||||||
options: IEditorConstructionOptions | undefined,
|
options: IStandaloneEditorConstructionOptions | undefined,
|
||||||
toDispose: IDisposable,
|
toDispose: IDisposable,
|
||||||
@IInstantiationService instantiationService: IInstantiationService,
|
@IInstantiationService instantiationService: IInstantiationService,
|
||||||
@ICodeEditorService codeEditorService: ICodeEditorService,
|
@ICodeEditorService codeEditorService: ICodeEditorService,
|
||||||
|
|||||||
@@ -24,7 +24,7 @@ import { IWebWorkerOptions, MonacoWebWorker, createWebWorker as actualCreateWebW
|
|||||||
import * as standaloneEnums from 'vs/editor/common/standalone/standaloneEnums';
|
import * as standaloneEnums from 'vs/editor/common/standalone/standaloneEnums';
|
||||||
import { Colorizer, IColorizerElementOptions, IColorizerOptions } from 'vs/editor/standalone/browser/colorizer';
|
import { Colorizer, IColorizerElementOptions, IColorizerOptions } from 'vs/editor/standalone/browser/colorizer';
|
||||||
import { SimpleEditorModelResolverService } from 'vs/editor/standalone/browser/simpleServices';
|
import { SimpleEditorModelResolverService } from 'vs/editor/standalone/browser/simpleServices';
|
||||||
import { IDiffEditorConstructionOptions, IEditorConstructionOptions, IStandaloneCodeEditor, IStandaloneDiffEditor, StandaloneDiffEditor, StandaloneEditor } from 'vs/editor/standalone/browser/standaloneCodeEditor';
|
import { IDiffEditorConstructionOptions, IStandaloneEditorConstructionOptions, IStandaloneCodeEditor, IStandaloneDiffEditor, StandaloneDiffEditor, StandaloneEditor } from 'vs/editor/standalone/browser/standaloneCodeEditor';
|
||||||
import { DynamicStandaloneServices, IEditorOverrideServices, StaticServices } from 'vs/editor/standalone/browser/standaloneServices';
|
import { DynamicStandaloneServices, IEditorOverrideServices, StaticServices } from 'vs/editor/standalone/browser/standaloneServices';
|
||||||
import { IStandaloneThemeData, IStandaloneThemeService } from 'vs/editor/standalone/common/standaloneThemeService';
|
import { IStandaloneThemeData, IStandaloneThemeService } from 'vs/editor/standalone/common/standaloneThemeService';
|
||||||
import { ICommandService } from 'vs/platform/commands/common/commands';
|
import { ICommandService } from 'vs/platform/commands/common/commands';
|
||||||
@@ -68,7 +68,7 @@ function withAllStandaloneServices<T extends editorCommon.IEditor>(domElement: H
|
|||||||
* `domElement` should be empty (not contain other dom nodes).
|
* `domElement` should be empty (not contain other dom nodes).
|
||||||
* The editor will read the size of `domElement`.
|
* The editor will read the size of `domElement`.
|
||||||
*/
|
*/
|
||||||
export function create(domElement: HTMLElement, options?: IEditorConstructionOptions, override?: IEditorOverrideServices): IStandaloneCodeEditor {
|
export function create(domElement: HTMLElement, options?: IStandaloneEditorConstructionOptions, override?: IEditorOverrideServices): IStandaloneCodeEditor {
|
||||||
return withAllStandaloneServices(domElement, override || {}, (services) => {
|
return withAllStandaloneServices(domElement, override || {}, (services) => {
|
||||||
return new StandaloneEditor(
|
return new StandaloneEditor(
|
||||||
domElement,
|
domElement,
|
||||||
|
|||||||
@@ -29,7 +29,7 @@ import { TestThemeService } from 'vs/platform/theme/test/common/testThemeService
|
|||||||
export class TestCodeEditor extends CodeEditorWidget implements editorBrowser.ICodeEditor {
|
export class TestCodeEditor extends CodeEditorWidget implements editorBrowser.ICodeEditor {
|
||||||
|
|
||||||
//#region testing overrides
|
//#region testing overrides
|
||||||
protected _createConfiguration(options: editorOptions.IEditorOptions): editorCommon.IConfiguration {
|
protected _createConfiguration(options: editorOptions.IEditorConstructionOptions): editorCommon.IConfiguration {
|
||||||
return new TestConfiguration(options);
|
return new TestConfiguration(options);
|
||||||
}
|
}
|
||||||
protected _createView(viewModel: ViewModel, cursor: Cursor): [View, boolean] {
|
protected _createView(viewModel: ViewModel, cursor: Cursor): [View, boolean] {
|
||||||
|
|||||||
15
src/vs/monaco.d.ts
vendored
15
src/vs/monaco.d.ts
vendored
@@ -813,7 +813,7 @@ declare namespace monaco.editor {
|
|||||||
* `domElement` should be empty (not contain other dom nodes).
|
* `domElement` should be empty (not contain other dom nodes).
|
||||||
* The editor will read the size of `domElement`.
|
* The editor will read the size of `domElement`.
|
||||||
*/
|
*/
|
||||||
export function create(domElement: HTMLElement, options?: IEditorConstructionOptions, override?: IEditorOverrideServices): IStandaloneCodeEditor;
|
export function create(domElement: HTMLElement, options?: IStandaloneEditorConstructionOptions, override?: IEditorOverrideServices): IStandaloneCodeEditor;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Emitted when an editor is created.
|
* Emitted when an editor is created.
|
||||||
@@ -1051,7 +1051,7 @@ declare namespace monaco.editor {
|
|||||||
/**
|
/**
|
||||||
* The options to create an editor.
|
* The options to create an editor.
|
||||||
*/
|
*/
|
||||||
export interface IEditorConstructionOptions extends IEditorOptions {
|
export interface IStandaloneEditorConstructionOptions extends IEditorConstructionOptions {
|
||||||
/**
|
/**
|
||||||
* The initial model associated with this code editor.
|
* The initial model associated with this code editor.
|
||||||
*/
|
*/
|
||||||
@@ -2061,6 +2061,8 @@ declare namespace monaco.editor {
|
|||||||
/**
|
/**
|
||||||
* Instructs the editor to remeasure its container. This method should
|
* Instructs the editor to remeasure its container. This method should
|
||||||
* be called when the container of the editor gets resized.
|
* be called when the container of the editor gets resized.
|
||||||
|
*
|
||||||
|
* If a dimension is passed in, the passed in value will be used.
|
||||||
*/
|
*/
|
||||||
layout(dimension?: IDimension): void;
|
layout(dimension?: IDimension): void;
|
||||||
/**
|
/**
|
||||||
@@ -2918,6 +2920,13 @@ declare namespace monaco.editor {
|
|||||||
showUnused?: boolean;
|
showUnused?: boolean;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
export interface IEditorConstructionOptions extends IEditorOptions {
|
||||||
|
/**
|
||||||
|
* The initial editor dimension (to avoid measuring the container).
|
||||||
|
*/
|
||||||
|
dimension?: IDimension;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Configuration options for the diff editor.
|
* Configuration options for the diff editor.
|
||||||
*/
|
*/
|
||||||
@@ -5131,7 +5140,7 @@ declare namespace monaco.languages {
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* The document symbol provider interface defines the contract between extensions and
|
* The document symbol provider interface defines the contract between extensions and
|
||||||
* the [go to symbol](https://code.visualstudio.com/docs/editor/editingevolved#_goto-symbol)-feature.
|
* the [go to symbol](https://code.visualstudio.com/docs/editor/editingevolved#_go-to-symbol)-feature.
|
||||||
*/
|
*/
|
||||||
export interface DocumentSymbolProvider {
|
export interface DocumentSymbolProvider {
|
||||||
displayName?: string;
|
displayName?: string;
|
||||||
|
|||||||
@@ -8,6 +8,7 @@ import { IAuthTokenService, AuthTokenStatus } from 'vs/platform/auth/common/auth
|
|||||||
import { ICredentialsService } from 'vs/platform/credentials/common/credentials';
|
import { ICredentialsService } from 'vs/platform/credentials/common/credentials';
|
||||||
import { Disposable } from 'vs/base/common/lifecycle';
|
import { Disposable } from 'vs/base/common/lifecycle';
|
||||||
import { IProductService } from 'vs/platform/product/common/productService';
|
import { IProductService } from 'vs/platform/product/common/productService';
|
||||||
|
import { IConfigurationService } from 'vs/platform/configuration/common/configuration';
|
||||||
|
|
||||||
const SERVICE_NAME = 'VS Code';
|
const SERVICE_NAME = 'VS Code';
|
||||||
const ACCOUNT = 'MyAccount';
|
const ACCOUNT = 'MyAccount';
|
||||||
@@ -23,9 +24,10 @@ export class AuthTokenService extends Disposable implements IAuthTokenService {
|
|||||||
constructor(
|
constructor(
|
||||||
@ICredentialsService private readonly credentialsService: ICredentialsService,
|
@ICredentialsService private readonly credentialsService: ICredentialsService,
|
||||||
@IProductService productService: IProductService,
|
@IProductService productService: IProductService,
|
||||||
|
@IConfigurationService configurationService: IConfigurationService,
|
||||||
) {
|
) {
|
||||||
super();
|
super();
|
||||||
if (productService.settingsSyncStoreUrl) {
|
if (productService.settingsSyncStoreUrl && configurationService.getValue('configurationSync.enableAuth')) {
|
||||||
this._status = AuthTokenStatus.Inactive;
|
this._status = AuthTokenStatus.Inactive;
|
||||||
this.getToken().then(token => {
|
this.getToken().then(token => {
|
||||||
if (token) {
|
if (token) {
|
||||||
|
|||||||
211
src/vs/platform/dialogs/electron-main/dialogs.ts
Normal file
211
src/vs/platform/dialogs/electron-main/dialogs.ts
Normal file
@@ -0,0 +1,211 @@
|
|||||||
|
/*---------------------------------------------------------------------------------------------
|
||||||
|
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||||
|
* Licensed under the Source EULA. See License.txt in the project root for license information.
|
||||||
|
*--------------------------------------------------------------------------------------------*/
|
||||||
|
|
||||||
|
import { createDecorator } from 'vs/platform/instantiation/common/instantiation';
|
||||||
|
import { MessageBoxOptions, SaveDialogOptions, OpenDialogOptions, dialog, FileFilter, BrowserWindow } from 'electron';
|
||||||
|
import { Queue } from 'vs/base/common/async';
|
||||||
|
import { IStateService } from 'vs/platform/state/node/state';
|
||||||
|
import { isMacintosh } from 'vs/base/common/platform';
|
||||||
|
import { dirname } from 'vs/base/common/path';
|
||||||
|
import { normalizeNFC } from 'vs/base/common/normalization';
|
||||||
|
import { exists } from 'vs/base/node/pfs';
|
||||||
|
import { INativeOpenDialogOptions, MessageBoxReturnValue, SaveDialogReturnValue, OpenDialogReturnValue } from 'vs/platform/dialogs/node/dialogs';
|
||||||
|
import { withNullAsUndefined } from 'vs/base/common/types';
|
||||||
|
import { localize } from 'vs/nls';
|
||||||
|
import { WORKSPACE_FILTER } from 'vs/platform/workspaces/common/workspaces';
|
||||||
|
import { mnemonicButtonLabel } from 'vs/base/common/labels';
|
||||||
|
|
||||||
|
export const IDialogMainService = createDecorator<IDialogMainService>('dialogMainService');
|
||||||
|
|
||||||
|
export interface IDialogMainService {
|
||||||
|
|
||||||
|
_serviceBrand: undefined;
|
||||||
|
|
||||||
|
pickFileFolder(options: INativeOpenDialogOptions, window?: BrowserWindow): Promise<string[] | undefined>;
|
||||||
|
pickFolder(options: INativeOpenDialogOptions, window?: BrowserWindow): Promise<string[] | undefined>;
|
||||||
|
pickFile(options: INativeOpenDialogOptions, window?: BrowserWindow): Promise<string[] | undefined>;
|
||||||
|
pickWorkspace(options: INativeOpenDialogOptions, window?: BrowserWindow): Promise<string[] | undefined>;
|
||||||
|
|
||||||
|
showMessageBox(options: MessageBoxOptions, window?: BrowserWindow): Promise<MessageBoxReturnValue>;
|
||||||
|
showSaveDialog(options: SaveDialogOptions, window?: BrowserWindow): Promise<SaveDialogReturnValue>;
|
||||||
|
showOpenDialog(options: OpenDialogOptions, window?: BrowserWindow): Promise<OpenDialogReturnValue>;
|
||||||
|
}
|
||||||
|
|
||||||
|
interface IInternalNativeOpenDialogOptions extends INativeOpenDialogOptions {
|
||||||
|
pickFolders?: boolean;
|
||||||
|
pickFiles?: boolean;
|
||||||
|
|
||||||
|
title: string;
|
||||||
|
buttonLabel?: string;
|
||||||
|
filters?: FileFilter[];
|
||||||
|
}
|
||||||
|
|
||||||
|
export class DialogMainService implements IDialogMainService {
|
||||||
|
|
||||||
|
_serviceBrand: undefined;
|
||||||
|
|
||||||
|
private static readonly workingDirPickerStorageKey = 'pickerWorkingDir';
|
||||||
|
|
||||||
|
private readonly mapWindowToDialogQueue: Map<number, Queue<void>>;
|
||||||
|
private readonly noWindowDialogQueue: Queue<void>;
|
||||||
|
|
||||||
|
constructor(
|
||||||
|
@IStateService private readonly stateService: IStateService
|
||||||
|
) {
|
||||||
|
this.mapWindowToDialogQueue = new Map<number, Queue<void>>();
|
||||||
|
this.noWindowDialogQueue = new Queue<void>();
|
||||||
|
}
|
||||||
|
|
||||||
|
pickFileFolder(options: INativeOpenDialogOptions, window?: BrowserWindow): Promise<string[] | undefined> {
|
||||||
|
return this.doPick({ ...options, pickFolders: true, pickFiles: true, title: localize('open', "Open") }, window);
|
||||||
|
}
|
||||||
|
|
||||||
|
pickFolder(options: INativeOpenDialogOptions, window?: BrowserWindow): Promise<string[] | undefined> {
|
||||||
|
return this.doPick({ ...options, pickFolders: true, title: localize('openFolder', "Open Folder") }, window);
|
||||||
|
}
|
||||||
|
|
||||||
|
pickFile(options: INativeOpenDialogOptions, window?: BrowserWindow): Promise<string[] | undefined> {
|
||||||
|
return this.doPick({ ...options, pickFiles: true, title: localize('openFile', "Open File") }, window);
|
||||||
|
}
|
||||||
|
|
||||||
|
pickWorkspace(options: INativeOpenDialogOptions, window?: BrowserWindow): Promise<string[] | undefined> {
|
||||||
|
const title = localize('openWorkspaceTitle', "Open Workspace");
|
||||||
|
const buttonLabel = mnemonicButtonLabel(localize({ key: 'openWorkspace', comment: ['&& denotes a mnemonic'] }, "&&Open"));
|
||||||
|
const filters = WORKSPACE_FILTER;
|
||||||
|
|
||||||
|
return this.doPick({ ...options, pickFiles: true, title, filters, buttonLabel }, window);
|
||||||
|
}
|
||||||
|
|
||||||
|
private async doPick(options: IInternalNativeOpenDialogOptions, window?: BrowserWindow): Promise<string[] | undefined> {
|
||||||
|
|
||||||
|
// Ensure dialog options
|
||||||
|
const dialogOptions: OpenDialogOptions = {
|
||||||
|
title: options.title,
|
||||||
|
buttonLabel: options.buttonLabel,
|
||||||
|
filters: options.filters
|
||||||
|
};
|
||||||
|
|
||||||
|
// Ensure defaultPath
|
||||||
|
dialogOptions.defaultPath = options.defaultPath || this.stateService.getItem<string>(DialogMainService.workingDirPickerStorageKey);
|
||||||
|
|
||||||
|
|
||||||
|
// Ensure properties
|
||||||
|
if (typeof options.pickFiles === 'boolean' || typeof options.pickFolders === 'boolean') {
|
||||||
|
dialogOptions.properties = undefined; // let it override based on the booleans
|
||||||
|
|
||||||
|
if (options.pickFiles && options.pickFolders) {
|
||||||
|
dialogOptions.properties = ['multiSelections', 'openDirectory', 'openFile', 'createDirectory'];
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!dialogOptions.properties) {
|
||||||
|
dialogOptions.properties = ['multiSelections', options.pickFolders ? 'openDirectory' : 'openFile', 'createDirectory'];
|
||||||
|
}
|
||||||
|
|
||||||
|
if (isMacintosh) {
|
||||||
|
dialogOptions.properties.push('treatPackageAsDirectory'); // always drill into .app files
|
||||||
|
}
|
||||||
|
|
||||||
|
// Show Dialog
|
||||||
|
const windowToUse = window || BrowserWindow.getFocusedWindow();
|
||||||
|
|
||||||
|
const result = await this.showOpenDialog(dialogOptions, withNullAsUndefined(windowToUse));
|
||||||
|
if (result && result.filePaths && result.filePaths.length > 0) {
|
||||||
|
|
||||||
|
// Remember path in storage for next time
|
||||||
|
this.stateService.setItem(DialogMainService.workingDirPickerStorageKey, dirname(result.filePaths[0]));
|
||||||
|
|
||||||
|
return result.filePaths;
|
||||||
|
}
|
||||||
|
|
||||||
|
return undefined; // {{SQL CARBON EDIT}} strict-null-check
|
||||||
|
}
|
||||||
|
|
||||||
|
private getDialogQueue(window?: BrowserWindow): Queue<any> {
|
||||||
|
if (!window) {
|
||||||
|
return this.noWindowDialogQueue;
|
||||||
|
}
|
||||||
|
|
||||||
|
let windowDialogQueue = this.mapWindowToDialogQueue.get(window.id);
|
||||||
|
if (!windowDialogQueue) {
|
||||||
|
windowDialogQueue = new Queue<any>();
|
||||||
|
this.mapWindowToDialogQueue.set(window.id, windowDialogQueue);
|
||||||
|
}
|
||||||
|
|
||||||
|
return windowDialogQueue;
|
||||||
|
}
|
||||||
|
|
||||||
|
showMessageBox(options: MessageBoxOptions, window?: BrowserWindow): Promise<MessageBoxReturnValue> {
|
||||||
|
return this.getDialogQueue(window).queue(async () => {
|
||||||
|
return new Promise(resolve => {
|
||||||
|
if (window) {
|
||||||
|
return dialog.showMessageBox(window, options, (response, checkboxChecked) => resolve({ response, checkboxChecked }));
|
||||||
|
}
|
||||||
|
|
||||||
|
return dialog.showMessageBox(options);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
showSaveDialog(options: SaveDialogOptions, window?: BrowserWindow): Promise<SaveDialogReturnValue> {
|
||||||
|
|
||||||
|
function normalizePath(path: string | undefined): string | undefined {
|
||||||
|
if (path && isMacintosh) {
|
||||||
|
path = normalizeNFC(path); // normalize paths returned from the OS
|
||||||
|
}
|
||||||
|
|
||||||
|
return path;
|
||||||
|
}
|
||||||
|
|
||||||
|
return this.getDialogQueue(window).queue(async () => {
|
||||||
|
return new Promise<SaveDialogReturnValue>(resolve => {
|
||||||
|
if (window) {
|
||||||
|
dialog.showSaveDialog(window, options, filePath => resolve({ filePath }));
|
||||||
|
} else {
|
||||||
|
dialog.showSaveDialog(options, filePath => resolve({ filePath }));
|
||||||
|
}
|
||||||
|
}).then(result => {
|
||||||
|
result.filePath = normalizePath(result.filePath);
|
||||||
|
|
||||||
|
return result;
|
||||||
|
});
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
showOpenDialog(options: OpenDialogOptions, window?: BrowserWindow): Promise<OpenDialogReturnValue> {
|
||||||
|
|
||||||
|
function normalizePaths(paths: string[] | undefined): string[] | undefined {
|
||||||
|
if (paths && paths.length > 0 && isMacintosh) {
|
||||||
|
paths = paths.map(path => normalizeNFC(path)); // normalize paths returned from the OS
|
||||||
|
}
|
||||||
|
|
||||||
|
return paths;
|
||||||
|
}
|
||||||
|
|
||||||
|
return this.getDialogQueue(window).queue(async () => {
|
||||||
|
|
||||||
|
// Ensure the path exists (if provided)
|
||||||
|
if (options.defaultPath) {
|
||||||
|
const pathExists = await exists(options.defaultPath);
|
||||||
|
if (!pathExists) {
|
||||||
|
options.defaultPath = undefined;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Show dialog
|
||||||
|
return new Promise<OpenDialogReturnValue>(resolve => {
|
||||||
|
if (window) {
|
||||||
|
dialog.showOpenDialog(window, options, filePaths => resolve({ filePaths }));
|
||||||
|
} else {
|
||||||
|
dialog.showOpenDialog(options, filePaths => resolve({ filePaths }));
|
||||||
|
}
|
||||||
|
}).then(result => {
|
||||||
|
result.filePaths = normalizePaths(result.filePaths);
|
||||||
|
|
||||||
|
return result;
|
||||||
|
});
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -13,3 +13,16 @@ export interface INativeOpenDialogOptions {
|
|||||||
telemetryEventName?: string;
|
telemetryEventName?: string;
|
||||||
telemetryExtraData?: ITelemetryData;
|
telemetryExtraData?: ITelemetryData;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
export interface MessageBoxReturnValue {
|
||||||
|
response: number;
|
||||||
|
checkboxChecked: boolean;
|
||||||
|
}
|
||||||
|
|
||||||
|
export interface SaveDialogReturnValue {
|
||||||
|
filePath?: string;
|
||||||
|
}
|
||||||
|
|
||||||
|
export interface OpenDialogReturnValue {
|
||||||
|
filePaths?: string[];
|
||||||
|
}
|
||||||
|
|||||||
@@ -5,16 +5,17 @@
|
|||||||
|
|
||||||
import { Event } from 'vs/base/common/event';
|
import { Event } from 'vs/base/common/event';
|
||||||
import { IWindowsMainService } from 'vs/platform/windows/electron-main/windows';
|
import { IWindowsMainService } from 'vs/platform/windows/electron-main/windows';
|
||||||
import { MessageBoxOptions, MessageBoxReturnValue, shell, OpenDevToolsOptions, SaveDialogOptions, SaveDialogReturnValue, OpenDialogOptions, OpenDialogReturnValue, CrashReporterStartOptions, crashReporter, Menu, BrowserWindow, app } from 'electron';
|
import { MessageBoxOptions, shell, OpenDevToolsOptions, SaveDialogOptions, OpenDialogOptions, CrashReporterStartOptions, crashReporter, Menu, BrowserWindow, app } from 'electron';
|
||||||
import { INativeOpenInWindowOptions } from 'vs/platform/windows/node/window';
|
import { INativeOpenWindowOptions } from 'vs/platform/windows/node/window';
|
||||||
import { ILifecycleMainService } from 'vs/platform/lifecycle/electron-main/lifecycleMainService';
|
import { ILifecycleMainService } from 'vs/platform/lifecycle/electron-main/lifecycleMainService';
|
||||||
import { IOpenedWindow, OpenContext, IWindowOpenable, IOpenEmptyWindowOptions } from 'vs/platform/windows/common/windows';
|
import { IOpenedWindow, OpenContext, IWindowOpenable, IOpenEmptyWindowOptions } from 'vs/platform/windows/common/windows';
|
||||||
import { INativeOpenDialogOptions } from 'vs/platform/dialogs/node/dialogs';
|
import { INativeOpenDialogOptions, MessageBoxReturnValue, SaveDialogReturnValue, OpenDialogReturnValue } from 'vs/platform/dialogs/node/dialogs';
|
||||||
import { isMacintosh, IProcessEnvironment } from 'vs/base/common/platform';
|
import { isMacintosh, IProcessEnvironment } from 'vs/base/common/platform';
|
||||||
import { IElectronService } from 'vs/platform/electron/node/electron';
|
import { IElectronService } from 'vs/platform/electron/node/electron';
|
||||||
import { ISerializableCommandAction } from 'vs/platform/actions/common/actions';
|
import { ISerializableCommandAction } from 'vs/platform/actions/common/actions';
|
||||||
import { IEnvironmentService, ParsedArgs } from 'vs/platform/environment/common/environment';
|
import { IEnvironmentService, ParsedArgs } from 'vs/platform/environment/common/environment';
|
||||||
import { AddFirstParameterToFunctions } from 'vs/base/common/types';
|
import { AddFirstParameterToFunctions } from 'vs/base/common/types';
|
||||||
|
import { IDialogMainService } from 'vs/platform/dialogs/electron-main/dialogs';
|
||||||
|
|
||||||
export class ElectronMainService implements AddFirstParameterToFunctions<IElectronService, Promise<any> /* only methods, not events */, number /* window ID */> {
|
export class ElectronMainService implements AddFirstParameterToFunctions<IElectronService, Promise<any> /* only methods, not events */, number /* window ID */> {
|
||||||
|
|
||||||
@@ -22,6 +23,7 @@ export class ElectronMainService implements AddFirstParameterToFunctions<IElectr
|
|||||||
|
|
||||||
constructor(
|
constructor(
|
||||||
@IWindowsMainService private readonly windowsMainService: IWindowsMainService,
|
@IWindowsMainService private readonly windowsMainService: IWindowsMainService,
|
||||||
|
@IDialogMainService private readonly dialogMainService: IDialogMainService,
|
||||||
@ILifecycleMainService private readonly lifecycleMainService: ILifecycleMainService,
|
@ILifecycleMainService private readonly lifecycleMainService: ILifecycleMainService,
|
||||||
@IEnvironmentService private readonly environmentService: IEnvironmentService
|
@IEnvironmentService private readonly environmentService: IEnvironmentService
|
||||||
) {
|
) {
|
||||||
@@ -61,7 +63,7 @@ export class ElectronMainService implements AddFirstParameterToFunctions<IElectr
|
|||||||
}
|
}
|
||||||
|
|
||||||
async getActiveWindowId(windowId: number): Promise<number | undefined> {
|
async getActiveWindowId(windowId: number): Promise<number | undefined> {
|
||||||
const activeWindow = this.windowsMainService.getFocusedWindow() || this.windowsMainService.getLastActiveWindow();
|
const activeWindow = BrowserWindow.getFocusedWindow() || this.windowsMainService.getLastActiveWindow();
|
||||||
if (activeWindow) {
|
if (activeWindow) {
|
||||||
return activeWindow.id;
|
return activeWindow.id;
|
||||||
}
|
}
|
||||||
@@ -69,11 +71,17 @@ export class ElectronMainService implements AddFirstParameterToFunctions<IElectr
|
|||||||
return undefined;
|
return undefined;
|
||||||
}
|
}
|
||||||
|
|
||||||
async openEmptyWindow(windowId: number, options?: IOpenEmptyWindowOptions): Promise<void> {
|
openWindow(windowId: number, options?: IOpenEmptyWindowOptions): Promise<void>;
|
||||||
this.windowsMainService.openEmptyWindow(OpenContext.API, options);
|
openWindow(windowId: number, toOpen: IWindowOpenable[], options?: INativeOpenWindowOptions): Promise<void>;
|
||||||
|
openWindow(windowId: number, arg1?: IOpenEmptyWindowOptions | IWindowOpenable[], arg2?: INativeOpenWindowOptions): Promise<void> {
|
||||||
|
if (Array.isArray(arg1)) {
|
||||||
|
return this.doOpenWindow(windowId, arg1, arg2);
|
||||||
|
}
|
||||||
|
|
||||||
|
return this.doOpenEmptyWindow(windowId, arg1);
|
||||||
}
|
}
|
||||||
|
|
||||||
async openInWindow(windowId: number, toOpen: IWindowOpenable[], options: INativeOpenInWindowOptions = Object.create(null)): Promise<void> {
|
private async doOpenWindow(windowId: number, toOpen: IWindowOpenable[], options: INativeOpenWindowOptions = Object.create(null)): Promise<void> {
|
||||||
if (toOpen.length > 0) {
|
if (toOpen.length > 0) {
|
||||||
this.windowsMainService.open({
|
this.windowsMainService.open({
|
||||||
context: OpenContext.API,
|
context: OpenContext.API,
|
||||||
@@ -91,6 +99,10 @@ export class ElectronMainService implements AddFirstParameterToFunctions<IElectr
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private async doOpenEmptyWindow(windowId: number, options?: IOpenEmptyWindowOptions): Promise<void> {
|
||||||
|
this.windowsMainService.openEmptyWindow(OpenContext.API, options);
|
||||||
|
}
|
||||||
|
|
||||||
async toggleFullScreen(windowId: number): Promise<void> {
|
async toggleFullScreen(windowId: number): Promise<void> {
|
||||||
const window = this.windowsMainService.getWindowById(windowId);
|
const window = this.windowsMainService.getWindowById(windowId);
|
||||||
if (window) {
|
if (window) {
|
||||||
@@ -164,15 +176,24 @@ export class ElectronMainService implements AddFirstParameterToFunctions<IElectr
|
|||||||
//#region Dialog
|
//#region Dialog
|
||||||
|
|
||||||
async showMessageBox(windowId: number, options: MessageBoxOptions): Promise<MessageBoxReturnValue> {
|
async showMessageBox(windowId: number, options: MessageBoxOptions): Promise<MessageBoxReturnValue> {
|
||||||
return this.windowsMainService.showMessageBox(options, this.windowsMainService.getWindowById(windowId));
|
return this.dialogMainService.showMessageBox(options, this.toBrowserWindow(windowId));
|
||||||
}
|
}
|
||||||
|
|
||||||
async showSaveDialog(windowId: number, options: SaveDialogOptions): Promise<SaveDialogReturnValue> {
|
async showSaveDialog(windowId: number, options: SaveDialogOptions): Promise<SaveDialogReturnValue> {
|
||||||
return this.windowsMainService.showSaveDialog(options, this.windowsMainService.getWindowById(windowId));
|
return this.dialogMainService.showSaveDialog(options, this.toBrowserWindow(windowId));
|
||||||
}
|
}
|
||||||
|
|
||||||
async showOpenDialog(windowId: number, options: OpenDialogOptions): Promise<OpenDialogReturnValue> {
|
async showOpenDialog(windowId: number, options: OpenDialogOptions): Promise<OpenDialogReturnValue> {
|
||||||
return this.windowsMainService.showOpenDialog(options, this.windowsMainService.getWindowById(windowId));
|
return this.dialogMainService.showOpenDialog(options, this.toBrowserWindow(windowId));
|
||||||
|
}
|
||||||
|
|
||||||
|
private toBrowserWindow(windowId: number): BrowserWindow | undefined {
|
||||||
|
const window = this.windowsMainService.getWindowById(windowId);
|
||||||
|
if (window) {
|
||||||
|
return window.win;
|
||||||
|
}
|
||||||
|
|
||||||
|
return undefined;
|
||||||
}
|
}
|
||||||
|
|
||||||
async pickFileFolderAndOpen(windowId: number, options: INativeOpenDialogOptions): Promise<void> {
|
async pickFileFolderAndOpen(windowId: number, options: INativeOpenDialogOptions): Promise<void> {
|
||||||
@@ -214,7 +235,9 @@ export class ElectronMainService implements AddFirstParameterToFunctions<IElectr
|
|||||||
}
|
}
|
||||||
|
|
||||||
async openExternal(windowId: number, url: string): Promise<boolean> {
|
async openExternal(windowId: number, url: string): Promise<boolean> {
|
||||||
return this.windowsMainService.openExternal(url);
|
shell.openExternal(url);
|
||||||
|
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
async updateTouchBar(windowId: number, items: ISerializableCommandAction[][]): Promise<void> {
|
async updateTouchBar(windowId: number, items: ISerializableCommandAction[][]): Promise<void> {
|
||||||
@@ -229,7 +252,7 @@ export class ElectronMainService implements AddFirstParameterToFunctions<IElectr
|
|||||||
//#region macOS Touchbar
|
//#region macOS Touchbar
|
||||||
|
|
||||||
async newWindowTab(): Promise<void> {
|
async newWindowTab(): Promise<void> {
|
||||||
this.windowsMainService.openNewTabbedWindow(OpenContext.API);
|
this.windowsMainService.open({ context: OpenContext.API, cli: this.environmentService.args, forceNewTabbedWindow: true, forceEmpty: true });
|
||||||
}
|
}
|
||||||
|
|
||||||
async showPreviousWindowTab(): Promise<void> {
|
async showPreviousWindowTab(): Promise<void> {
|
||||||
@@ -267,7 +290,7 @@ export class ElectronMainService implements AddFirstParameterToFunctions<IElectr
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
async closeWorkpsace(windowId: number): Promise<void> {
|
async closeWorkspace(windowId: number): Promise<void> {
|
||||||
const window = this.windowsMainService.getWindowById(windowId);
|
const window = this.windowsMainService.getWindowById(windowId);
|
||||||
if (window) {
|
if (window) {
|
||||||
return this.windowsMainService.closeWorkspace(window);
|
return this.windowsMainService.closeWorkspace(window);
|
||||||
|
|||||||
@@ -4,14 +4,14 @@
|
|||||||
*--------------------------------------------------------------------------------------------*/
|
*--------------------------------------------------------------------------------------------*/
|
||||||
|
|
||||||
import { Event } from 'vs/base/common/event';
|
import { Event } from 'vs/base/common/event';
|
||||||
import { MessageBoxOptions, MessageBoxReturnValue, OpenDevToolsOptions, SaveDialogOptions, OpenDialogOptions, OpenDialogReturnValue, SaveDialogReturnValue, CrashReporterStartOptions } from 'electron';
|
import { MessageBoxOptions, OpenDevToolsOptions, SaveDialogOptions, OpenDialogOptions, CrashReporterStartOptions } from 'electron';
|
||||||
import { createDecorator } from 'vs/platform/instantiation/common/instantiation';
|
import { createDecorator } from 'vs/platform/instantiation/common/instantiation';
|
||||||
import { IWindowOpenable, IOpenEmptyWindowOptions, IOpenedWindow } from 'vs/platform/windows/common/windows';
|
import { IWindowOpenable, IOpenEmptyWindowOptions, IOpenedWindow } from 'vs/platform/windows/common/windows';
|
||||||
import { INativeOpenDialogOptions } from 'vs/platform/dialogs/node/dialogs';
|
import { INativeOpenDialogOptions, MessageBoxReturnValue, SaveDialogReturnValue, OpenDialogReturnValue } from 'vs/platform/dialogs/node/dialogs';
|
||||||
import { ISerializableCommandAction } from 'vs/platform/actions/common/actions';
|
import { ISerializableCommandAction } from 'vs/platform/actions/common/actions';
|
||||||
import { ParsedArgs } from 'vscode-minimist';
|
import { ParsedArgs } from 'vscode-minimist';
|
||||||
import { IProcessEnvironment } from 'vs/base/common/platform';
|
import { IProcessEnvironment } from 'vs/base/common/platform';
|
||||||
import { INativeOpenInWindowOptions } from 'vs/platform/windows/node/window';
|
import { INativeOpenWindowOptions } from 'vs/platform/windows/node/window';
|
||||||
|
|
||||||
export const IElectronService = createDecorator<IElectronService>('electronService');
|
export const IElectronService = createDecorator<IElectronService>('electronService');
|
||||||
|
|
||||||
@@ -33,8 +33,8 @@ export interface IElectronService {
|
|||||||
getWindowCount(): Promise<number>;
|
getWindowCount(): Promise<number>;
|
||||||
getActiveWindowId(): Promise<number | undefined>;
|
getActiveWindowId(): Promise<number | undefined>;
|
||||||
|
|
||||||
openEmptyWindow(options?: IOpenEmptyWindowOptions): Promise<void>;
|
openWindow(options?: IOpenEmptyWindowOptions): Promise<void>;
|
||||||
openInWindow(toOpen: IWindowOpenable[], options?: INativeOpenInWindowOptions): Promise<void>;
|
openWindow(toOpen: IWindowOpenable[], options?: INativeOpenWindowOptions): Promise<void>;
|
||||||
|
|
||||||
toggleFullScreen(): Promise<void>;
|
toggleFullScreen(): Promise<void>;
|
||||||
|
|
||||||
@@ -76,7 +76,7 @@ export interface IElectronService {
|
|||||||
// Lifecycle
|
// Lifecycle
|
||||||
relaunch(options?: { addArgs?: string[], removeArgs?: string[] }): Promise<void>;
|
relaunch(options?: { addArgs?: string[], removeArgs?: string[] }): Promise<void>;
|
||||||
reload(): Promise<void>;
|
reload(): Promise<void>;
|
||||||
closeWorkpsace(): Promise<void>;
|
closeWorkspace(): Promise<void>;
|
||||||
closeWindow(): Promise<void>;
|
closeWindow(): Promise<void>;
|
||||||
quit(): Promise<void>;
|
quit(): Promise<void>;
|
||||||
|
|
||||||
|
|||||||
@@ -4,7 +4,6 @@
|
|||||||
*--------------------------------------------------------------------------------------------*/
|
*--------------------------------------------------------------------------------------------*/
|
||||||
|
|
||||||
import { createDecorator } from 'vs/platform/instantiation/common/instantiation';
|
import { createDecorator } from 'vs/platform/instantiation/common/instantiation';
|
||||||
import { ISharedProcess } from 'vs/platform/windows/electron-main/windows';
|
|
||||||
|
|
||||||
export const ISharedProcessMainService = createDecorator<ISharedProcessMainService>('sharedProcessMainService');
|
export const ISharedProcessMainService = createDecorator<ISharedProcessMainService>('sharedProcessMainService');
|
||||||
|
|
||||||
@@ -15,6 +14,12 @@ export interface ISharedProcessMainService {
|
|||||||
whenSharedProcessReady(): Promise<void>;
|
whenSharedProcessReady(): Promise<void>;
|
||||||
toggleSharedProcessWindow(): Promise<void>;
|
toggleSharedProcessWindow(): Promise<void>;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
export interface ISharedProcess {
|
||||||
|
whenReady(): Promise<void>;
|
||||||
|
toggle(): void;
|
||||||
|
}
|
||||||
|
|
||||||
export class SharedProcessMainService implements ISharedProcessMainService {
|
export class SharedProcessMainService implements ISharedProcessMainService {
|
||||||
|
|
||||||
_serviceBrand: undefined;
|
_serviceBrand: undefined;
|
||||||
|
|||||||
@@ -7,15 +7,16 @@ import { localize } from 'vs/nls';
|
|||||||
import * as objects from 'vs/base/common/objects';
|
import * as objects from 'vs/base/common/objects';
|
||||||
import { parseArgs, OPTIONS } from 'vs/platform/environment/node/argv';
|
import { parseArgs, OPTIONS } from 'vs/platform/environment/node/argv';
|
||||||
import { IIssueService, IssueReporterData, IssueReporterFeatures, ProcessExplorerData } from 'vs/platform/issue/node/issue';
|
import { IIssueService, IssueReporterData, IssueReporterFeatures, ProcessExplorerData } from 'vs/platform/issue/node/issue';
|
||||||
import { BrowserWindow, ipcMain, screen, dialog, IpcMainEvent, Display } from 'electron';
|
import { BrowserWindow, ipcMain, screen, Event as IpcMainEvent, Display, shell } from 'electron';
|
||||||
import { ILaunchMainService } from 'vs/platform/launch/electron-main/launchMainService';
|
import { ILaunchMainService } from 'vs/platform/launch/electron-main/launchMainService';
|
||||||
import { PerformanceInfo, isRemoteDiagnosticError } from 'vs/platform/diagnostics/common/diagnostics';
|
import { PerformanceInfo, isRemoteDiagnosticError } from 'vs/platform/diagnostics/common/diagnostics';
|
||||||
import { IDiagnosticsService } from 'vs/platform/diagnostics/node/diagnosticsService';
|
import { IDiagnosticsService } from 'vs/platform/diagnostics/node/diagnosticsService';
|
||||||
import { IEnvironmentService } from 'vs/platform/environment/common/environment';
|
import { IEnvironmentService } from 'vs/platform/environment/common/environment';
|
||||||
import { isMacintosh, IProcessEnvironment } from 'vs/base/common/platform';
|
import { isMacintosh, IProcessEnvironment } from 'vs/base/common/platform';
|
||||||
import { ILogService } from 'vs/platform/log/common/log';
|
import { ILogService } from 'vs/platform/log/common/log';
|
||||||
import { IWindowState, IWindowsMainService } from 'vs/platform/windows/electron-main/windows';
|
import { IWindowState } from 'vs/platform/windows/electron-main/windows';
|
||||||
import { listProcesses } from 'vs/base/node/ps';
|
import { listProcesses } from 'vs/base/node/ps';
|
||||||
|
import { IDialogMainService } from 'vs/platform/dialogs/electron-main/dialogs';
|
||||||
|
|
||||||
const DEFAULT_BACKGROUND_COLOR = '#1E1E1E';
|
const DEFAULT_BACKGROUND_COLOR = '#1E1E1E';
|
||||||
|
|
||||||
@@ -33,7 +34,7 @@ export class IssueMainService implements IIssueService {
|
|||||||
@ILaunchMainService private readonly launchMainService: ILaunchMainService,
|
@ILaunchMainService private readonly launchMainService: ILaunchMainService,
|
||||||
@ILogService private readonly logService: ILogService,
|
@ILogService private readonly logService: ILogService,
|
||||||
@IDiagnosticsService private readonly diagnosticsService: IDiagnosticsService,
|
@IDiagnosticsService private readonly diagnosticsService: IDiagnosticsService,
|
||||||
@IWindowsMainService private readonly windowsMainService: IWindowsMainService
|
@IDialogMainService private readonly dialogMainService: IDialogMainService
|
||||||
) {
|
) {
|
||||||
this.registerListeners();
|
this.registerListeners();
|
||||||
}
|
}
|
||||||
@@ -89,7 +90,7 @@ export class IssueMainService implements IIssueService {
|
|||||||
};
|
};
|
||||||
|
|
||||||
if (this._issueWindow) {
|
if (this._issueWindow) {
|
||||||
dialog.showMessageBox(this._issueWindow, messageOptions)
|
this.dialogMainService.showMessageBox(messageOptions, this._issueWindow)
|
||||||
.then(result => {
|
.then(result => {
|
||||||
event.sender.send('vscode:issueReporterClipboardResponse', result.response === 0);
|
event.sender.send('vscode:issueReporterClipboardResponse', result.response === 0);
|
||||||
});
|
});
|
||||||
@@ -113,7 +114,7 @@ export class IssueMainService implements IIssueService {
|
|||||||
};
|
};
|
||||||
|
|
||||||
if (this._issueWindow) {
|
if (this._issueWindow) {
|
||||||
dialog.showMessageBox(this._issueWindow, messageOptions)
|
this.dialogMainService.showMessageBox(messageOptions, this._issueWindow)
|
||||||
.then(result => {
|
.then(result => {
|
||||||
if (result.response === 0) {
|
if (result.response === 0) {
|
||||||
if (this._issueWindow) {
|
if (this._issueWindow) {
|
||||||
@@ -146,7 +147,7 @@ export class IssueMainService implements IIssueService {
|
|||||||
});
|
});
|
||||||
|
|
||||||
ipcMain.on('vscode:openExternal', (_: unknown, arg: string) => {
|
ipcMain.on('vscode:openExternal', (_: unknown, arg: string) => {
|
||||||
this.windowsMainService.openExternal(arg);
|
shell.openExternal(arg);
|
||||||
});
|
});
|
||||||
|
|
||||||
ipcMain.on('vscode:closeIssueReporter', (event: IpcMainEvent) => {
|
ipcMain.on('vscode:closeIssueReporter', (event: IpcMainEvent) => {
|
||||||
|
|||||||
@@ -141,6 +141,7 @@ export class LaunchMainService implements ILaunchMainService {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Open new Window
|
||||||
if (openNewWindow) {
|
if (openNewWindow) {
|
||||||
usedWindows = this.windowsMainService.open({
|
usedWindows = this.windowsMainService.open({
|
||||||
context,
|
context,
|
||||||
@@ -150,8 +151,18 @@ export class LaunchMainService implements ILaunchMainService {
|
|||||||
forceEmpty: true,
|
forceEmpty: true,
|
||||||
waitMarkerFileURI
|
waitMarkerFileURI
|
||||||
});
|
});
|
||||||
} else {
|
}
|
||||||
usedWindows = [this.windowsMainService.focusLastActive(args, context)];
|
|
||||||
|
// Focus existing window or open if none opened
|
||||||
|
else {
|
||||||
|
const lastActive = this.windowsMainService.getLastActiveWindow();
|
||||||
|
if (lastActive) {
|
||||||
|
lastActive.focus();
|
||||||
|
|
||||||
|
usedWindows = [lastActive];
|
||||||
|
} else {
|
||||||
|
usedWindows = this.windowsMainService.open({ context, cli: args, forceEmpty: true });
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -216,7 +227,7 @@ export class LaunchMainService implements ILaunchMainService {
|
|||||||
mainPID: process.pid,
|
mainPID: process.pid,
|
||||||
mainArguments: process.argv.slice(1),
|
mainArguments: process.argv.slice(1),
|
||||||
windows,
|
windows,
|
||||||
screenReader: !!app.accessibilitySupportEnabled,
|
screenReader: !!app.isAccessibilitySupportEnabled(),
|
||||||
gpuFeatureStatus: app.getGPUFeatureStatus()
|
gpuFeatureStatus: app.getGPUFeatureStatus()
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -87,4 +87,10 @@ export class BufferLogService extends AbstractLogService implements ILogService
|
|||||||
this._logger.dispose();
|
this._logger.dispose();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
flush(): void {
|
||||||
|
if (this._logger) {
|
||||||
|
this._logger.flush();
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -78,8 +78,7 @@ export class FileLogService extends AbstractLogService implements ILogService {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
flush(): Promise<void> {
|
flush(): void {
|
||||||
return this.queue.queue(() => Promise.resolve());
|
|
||||||
}
|
}
|
||||||
|
|
||||||
log(level: LogLevel, args: any[]): void {
|
log(level: LogLevel, args: any[]): void {
|
||||||
|
|||||||
@@ -41,6 +41,11 @@ export interface ILogger extends IDisposable {
|
|||||||
warn(message: string, ...args: any[]): void;
|
warn(message: string, ...args: any[]): void;
|
||||||
error(message: string | Error, ...args: any[]): void;
|
error(message: string | Error, ...args: any[]): void;
|
||||||
critical(message: string | Error, ...args: any[]): void;
|
critical(message: string | Error, ...args: any[]): void;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* An operation to flush the contents. Can be synchronous.
|
||||||
|
*/
|
||||||
|
flush(): void;
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface ILogService extends ILogger {
|
export interface ILogService extends ILogger {
|
||||||
@@ -69,6 +74,7 @@ export abstract class AbstractLogService extends Disposable {
|
|||||||
getLevel(): LogLevel {
|
getLevel(): LogLevel {
|
||||||
return this.level;
|
return this.level;
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
export class ConsoleLogMainService extends AbstractLogService implements ILogService {
|
export class ConsoleLogMainService extends AbstractLogService implements ILogService {
|
||||||
@@ -145,6 +151,11 @@ export class ConsoleLogMainService extends AbstractLogService implements ILogSer
|
|||||||
dispose(): void {
|
dispose(): void {
|
||||||
// noop
|
// noop
|
||||||
}
|
}
|
||||||
|
|
||||||
|
flush(): void {
|
||||||
|
// noop
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
export class ConsoleLogService extends AbstractLogService implements ILogService {
|
export class ConsoleLogService extends AbstractLogService implements ILogService {
|
||||||
@@ -192,7 +203,13 @@ export class ConsoleLogService extends AbstractLogService implements ILogService
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
dispose(): void { }
|
dispose(): void {
|
||||||
|
// noop
|
||||||
|
}
|
||||||
|
|
||||||
|
flush(): void {
|
||||||
|
// noop
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
export class ConsoleLogInMainService extends AbstractLogService implements ILogService {
|
export class ConsoleLogInMainService extends AbstractLogService implements ILogService {
|
||||||
@@ -240,7 +257,13 @@ export class ConsoleLogInMainService extends AbstractLogService implements ILogS
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
dispose(): void { }
|
dispose(): void {
|
||||||
|
// noop
|
||||||
|
}
|
||||||
|
|
||||||
|
flush(): void {
|
||||||
|
// noop
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
export class MultiplexLogService extends AbstractLogService implements ILogService {
|
export class MultiplexLogService extends AbstractLogService implements ILogService {
|
||||||
@@ -296,6 +319,12 @@ export class MultiplexLogService extends AbstractLogService implements ILogServi
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
flush(): void {
|
||||||
|
for (const logService of this.logServices) {
|
||||||
|
logService.flush();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
dispose(): void {
|
dispose(): void {
|
||||||
for (const logService of this.logServices) {
|
for (const logService of this.logServices) {
|
||||||
logService.dispose();
|
logService.dispose();
|
||||||
@@ -346,6 +375,10 @@ export class DelegatedLogService extends Disposable implements ILogService {
|
|||||||
critical(message: string | Error, ...args: any[]): void {
|
critical(message: string | Error, ...args: any[]): void {
|
||||||
this.logService.critical(message, ...args);
|
this.logService.critical(message, ...args);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
flush(): void {
|
||||||
|
this.logService.flush();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
export class NullLogService implements ILogService {
|
export class NullLogService implements ILogService {
|
||||||
@@ -360,6 +393,7 @@ export class NullLogService implements ILogService {
|
|||||||
error(message: string | Error, ...args: any[]): void { }
|
error(message: string | Error, ...args: any[]): void { }
|
||||||
critical(message: string | Error, ...args: any[]): void { }
|
critical(message: string | Error, ...args: any[]): void { }
|
||||||
dispose(): void { }
|
dispose(): void { }
|
||||||
|
flush(): void { }
|
||||||
}
|
}
|
||||||
|
|
||||||
export function getLogLevel(environmentService: IEnvironmentService): LogLevel {
|
export function getLogLevel(environmentService: IEnvironmentService): LogLevel {
|
||||||
|
|||||||
@@ -32,7 +32,7 @@ export class LoggerService extends Disposable implements ILoggerService {
|
|||||||
if (resource.scheme === Schemas.file) {
|
if (resource.scheme === Schemas.file) {
|
||||||
const baseName = basename(resource);
|
const baseName = basename(resource);
|
||||||
const ext = extname(resource);
|
const ext = extname(resource);
|
||||||
logger = new SpdLogService(baseName.substring(0, baseName.length - ext.length), dirname(resource).path, this.logService.getLevel());
|
logger = new SpdLogService(baseName.substring(0, baseName.length - ext.length), dirname(resource).fsPath, this.logService.getLevel());
|
||||||
} else {
|
} else {
|
||||||
logger = this.instantiationService.createInstance(FileLogService, basename(resource), resource, this.logService.getLevel());
|
logger = this.instantiationService.createInstance(FileLogService, basename(resource), resource, this.logService.getLevel());
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -30,7 +30,7 @@ interface ILog {
|
|||||||
message: string;
|
message: string;
|
||||||
}
|
}
|
||||||
|
|
||||||
function log(logger: spdlog.RotatingLogger, level: LogLevel, message: string, sync: boolean): void {
|
function log(logger: spdlog.RotatingLogger, level: LogLevel, message: string): void {
|
||||||
switch (level) {
|
switch (level) {
|
||||||
case LogLevel.Trace: logger.trace(message); break;
|
case LogLevel.Trace: logger.trace(message); break;
|
||||||
case LogLevel.Debug: logger.debug(message); break;
|
case LogLevel.Debug: logger.debug(message); break;
|
||||||
@@ -40,9 +40,6 @@ function log(logger: spdlog.RotatingLogger, level: LogLevel, message: string, sy
|
|||||||
case LogLevel.Critical: logger.critical(message); break;
|
case LogLevel.Critical: logger.critical(message); break;
|
||||||
default: throw new Error('Invalid log level');
|
default: throw new Error('Invalid log level');
|
||||||
}
|
}
|
||||||
if (sync) {
|
|
||||||
logger.flush();
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
export class SpdLogService extends AbstractLogService implements ILogService {
|
export class SpdLogService extends AbstractLogService implements ILogService {
|
||||||
@@ -53,7 +50,7 @@ export class SpdLogService extends AbstractLogService implements ILogService {
|
|||||||
private _loggerCreationPromise: Promise<void> | undefined = undefined;
|
private _loggerCreationPromise: Promise<void> | undefined = undefined;
|
||||||
private _logger: spdlog.RotatingLogger | undefined;
|
private _logger: spdlog.RotatingLogger | undefined;
|
||||||
|
|
||||||
constructor(private readonly name: string, private readonly logsFolder: string, level: LogLevel, private readonly sync: boolean = false) {
|
constructor(private readonly name: string, private readonly logsFolder: string, level: LogLevel) {
|
||||||
super();
|
super();
|
||||||
this.setLevel(level);
|
this.setLevel(level);
|
||||||
this._createSpdLogLogger();
|
this._createSpdLogLogger();
|
||||||
@@ -72,7 +69,7 @@ export class SpdLogService extends AbstractLogService implements ILogService {
|
|||||||
this._logger = logger;
|
this._logger = logger;
|
||||||
this._logger.setLevel(this.getLevel());
|
this._logger.setLevel(this.getLevel());
|
||||||
for (const { level, message } of this.buffer) {
|
for (const { level, message } of this.buffer) {
|
||||||
log(this._logger, level, message, this.sync);
|
log(this._logger, level, message);
|
||||||
}
|
}
|
||||||
this.buffer = [];
|
this.buffer = [];
|
||||||
}
|
}
|
||||||
@@ -83,7 +80,7 @@ export class SpdLogService extends AbstractLogService implements ILogService {
|
|||||||
|
|
||||||
private _log(level: LogLevel, message: string): void {
|
private _log(level: LogLevel, message: string): void {
|
||||||
if (this._logger) {
|
if (this._logger) {
|
||||||
log(this._logger, level, message, this.sync);
|
log(this._logger, level, message);
|
||||||
} else if (this.getLevel() <= level) {
|
} else if (this.getLevel() <= level) {
|
||||||
this.buffer.push({ level, message });
|
this.buffer.push({ level, message });
|
||||||
}
|
}
|
||||||
@@ -132,6 +129,14 @@ export class SpdLogService extends AbstractLogService implements ILogService {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
flush(): void {
|
||||||
|
if (this._logger) {
|
||||||
|
this._logger.flush();
|
||||||
|
} else if (this._loggerCreationPromise) {
|
||||||
|
this._loggerCreationPromise.then(() => this.flush());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
dispose(): void {
|
dispose(): void {
|
||||||
if (this._logger) {
|
if (this._logger) {
|
||||||
this.disposeLogger();
|
this.disposeLogger();
|
||||||
|
|||||||
@@ -6,7 +6,7 @@
|
|||||||
import * as nls from 'vs/nls';
|
import * as nls from 'vs/nls';
|
||||||
import { isMacintosh, language } from 'vs/base/common/platform';
|
import { isMacintosh, language } from 'vs/base/common/platform';
|
||||||
import { IEnvironmentService } from 'vs/platform/environment/common/environment';
|
import { IEnvironmentService } from 'vs/platform/environment/common/environment';
|
||||||
import { app, shell, Menu, MenuItem, BrowserWindow, MenuItemConstructorOptions, WebContents, Event, KeyboardEvent } from 'electron';
|
import { app, shell, Menu, MenuItem, BrowserWindow, MenuItemConstructorOptions, WebContents, Event, Event as KeyboardEvent } from 'electron';
|
||||||
import { OpenContext, IRunActionInWindowRequest, getTitleBarStyle, IRunKeybindingInWindowRequest, IWindowOpenable } from 'vs/platform/windows/common/windows';
|
import { OpenContext, IRunActionInWindowRequest, getTitleBarStyle, IRunKeybindingInWindowRequest, IWindowOpenable } from 'vs/platform/windows/common/windows';
|
||||||
import { IConfigurationService } from 'vs/platform/configuration/common/configuration';
|
import { IConfigurationService } from 'vs/platform/configuration/common/configuration';
|
||||||
import { ITelemetryService } from 'vs/platform/telemetry/common/telemetry';
|
import { ITelemetryService } from 'vs/platform/telemetry/common/telemetry';
|
||||||
@@ -368,13 +368,13 @@ export class Menubar {
|
|||||||
const servicesMenu = new Menu();
|
const servicesMenu = new Menu();
|
||||||
const services = new MenuItem({ label: nls.localize('mServices', "Services"), role: 'services', submenu: servicesMenu });
|
const services = new MenuItem({ label: nls.localize('mServices', "Services"), role: 'services', submenu: servicesMenu });
|
||||||
const hide = new MenuItem({ label: nls.localize('mHide', "Hide {0}", product.nameLong), role: 'hide', accelerator: 'Command+H' });
|
const hide = new MenuItem({ label: nls.localize('mHide', "Hide {0}", product.nameLong), role: 'hide', accelerator: 'Command+H' });
|
||||||
const hideOthers = new MenuItem({ label: nls.localize('mHideOthers', "Hide Others"), role: 'hideOthers', accelerator: 'Command+Alt+H' });
|
const hideOthers = new MenuItem({ label: nls.localize('mHideOthers', "Hide Others"), role: 'hideothers', accelerator: 'Command+Alt+H' });
|
||||||
const showAll = new MenuItem({ label: nls.localize('mShowAll', "Show All"), role: 'unhide' });
|
const showAll = new MenuItem({ label: nls.localize('mShowAll', "Show All"), role: 'unhide' });
|
||||||
const quit = new MenuItem(this.likeAction('workbench.action.quit', {
|
const quit = new MenuItem(this.likeAction('workbench.action.quit', {
|
||||||
label: nls.localize('miQuit', "Quit {0}", product.nameLong), click: () => {
|
label: nls.localize('miQuit', "Quit {0}", product.nameLong), click: () => {
|
||||||
if (
|
if (
|
||||||
this.windowsMainService.getWindowCount() === 0 || // allow to quit when no more windows are open
|
this.windowsMainService.getWindowCount() === 0 || // allow to quit when no more windows are open
|
||||||
!!this.windowsMainService.getFocusedWindow() || // allow to quit when window has focus (fix for https://github.com/Microsoft/vscode/issues/39191)
|
!!BrowserWindow.getFocusedWindow() || // allow to quit when window has focus (fix for https://github.com/Microsoft/vscode/issues/39191)
|
||||||
this.windowsMainService.getLastActiveWindow()!.isMinimized() // allow to quit when window has no focus but is minimized (https://github.com/Microsoft/vscode/issues/63000)
|
this.windowsMainService.getLastActiveWindow()!.isMinimized() // allow to quit when window has no focus but is minimized (https://github.com/Microsoft/vscode/issues/63000)
|
||||||
) {
|
) {
|
||||||
this.windowsMainService.quit();
|
this.windowsMainService.quit();
|
||||||
@@ -557,7 +557,7 @@ export class Menubar {
|
|||||||
label: this.mnemonicLabel(nls.localize('miCheckForUpdates', "Check for &&Updates...")), click: () => setTimeout(() => {
|
label: this.mnemonicLabel(nls.localize('miCheckForUpdates', "Check for &&Updates...")), click: () => setTimeout(() => {
|
||||||
this.reportMenuActionTelemetry('CheckForUpdate');
|
this.reportMenuActionTelemetry('CheckForUpdate');
|
||||||
|
|
||||||
const focusedWindow = this.windowsMainService.getFocusedWindow();
|
const focusedWindow = BrowserWindow.getFocusedWindow();
|
||||||
const context = focusedWindow ? { windowId: focusedWindow.id } : null;
|
const context = focusedWindow ? { windowId: focusedWindow.id } : null;
|
||||||
this.updateService.checkForUpdates(context);
|
this.updateService.checkForUpdates(context);
|
||||||
}, 0)
|
}, 0)
|
||||||
@@ -697,15 +697,16 @@ export class Menubar {
|
|||||||
|
|
||||||
private makeContextAwareClickHandler(click: () => void, contextSpecificHandlers: IMenuItemClickHandler): () => void {
|
private makeContextAwareClickHandler(click: () => void, contextSpecificHandlers: IMenuItemClickHandler): () => void {
|
||||||
return () => {
|
return () => {
|
||||||
|
|
||||||
// No Active Window
|
// No Active Window
|
||||||
const activeWindow = this.windowsMainService.getFocusedWindow();
|
const activeWindow = BrowserWindow.getFocusedWindow();
|
||||||
if (!activeWindow) {
|
if (!activeWindow) {
|
||||||
return contextSpecificHandlers.inNoWindow();
|
return contextSpecificHandlers.inNoWindow();
|
||||||
}
|
}
|
||||||
|
|
||||||
// DevTools focused
|
// DevTools focused
|
||||||
if (activeWindow.win.webContents.isDevToolsFocused()) {
|
if (activeWindow.webContents.isDevToolsFocused()) {
|
||||||
return contextSpecificHandlers.inDevTools(activeWindow.win.webContents.devToolsWebContents);
|
return contextSpecificHandlers.inDevTools(activeWindow.webContents.devToolsWebContents);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Finally execute command in Window
|
// Finally execute command in Window
|
||||||
@@ -719,14 +720,15 @@ export class Menubar {
|
|||||||
// https://github.com/Microsoft/vscode/issues/11928
|
// https://github.com/Microsoft/vscode/issues/11928
|
||||||
// Still allow to run when the last active window is minimized though for
|
// Still allow to run when the last active window is minimized though for
|
||||||
// https://github.com/Microsoft/vscode/issues/63000
|
// https://github.com/Microsoft/vscode/issues/63000
|
||||||
let activeWindow = this.windowsMainService.getFocusedWindow();
|
let activeBrowserWindow = BrowserWindow.getFocusedWindow();
|
||||||
if (!activeWindow) {
|
if (!activeBrowserWindow) {
|
||||||
const lastActiveWindow = this.windowsMainService.getLastActiveWindow();
|
const lastActiveWindow = this.windowsMainService.getLastActiveWindow();
|
||||||
if (lastActiveWindow && lastActiveWindow.isMinimized()) {
|
if (lastActiveWindow && lastActiveWindow.isMinimized()) {
|
||||||
activeWindow = lastActiveWindow;
|
activeBrowserWindow = lastActiveWindow.win;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
const activeWindow = activeBrowserWindow ? this.windowsMainService.getWindowById(activeBrowserWindow.id) : undefined;
|
||||||
if (activeWindow) {
|
if (activeWindow) {
|
||||||
this.logService.trace('menubar#runActionInRenderer', invocation);
|
this.logService.trace('menubar#runActionInRenderer', invocation);
|
||||||
|
|
||||||
|
|||||||
@@ -27,7 +27,7 @@ export function extractLocalHostUriMetaDataForPortMapping(uri: URI): { address:
|
|||||||
if (uri.scheme !== 'http' && uri.scheme !== 'https') {
|
if (uri.scheme !== 'http' && uri.scheme !== 'https') {
|
||||||
return undefined;
|
return undefined;
|
||||||
}
|
}
|
||||||
const localhostMatch = /^(localhost|127\.0\.0\.1):(\d+)$/.exec(uri.authority);
|
const localhostMatch = /^(localhost|127\.0\.0\.1|0\.0\.0\.0):(\d+)$/.exec(uri.authority);
|
||||||
if (!localhostMatch) {
|
if (!localhostMatch) {
|
||||||
return undefined;
|
return undefined;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -70,6 +70,7 @@ class TestableLogService extends AbstractLogService implements ILogService {
|
|||||||
}
|
}
|
||||||
|
|
||||||
dispose(): void { }
|
dispose(): void { }
|
||||||
|
flush(): void { }
|
||||||
}
|
}
|
||||||
|
|
||||||
suite('AIAdapter', () => {
|
suite('AIAdapter', () => {
|
||||||
@@ -198,4 +199,4 @@ suite('AIAdapter', () => {
|
|||||||
}
|
}
|
||||||
}]));
|
}]));
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -63,6 +63,12 @@ export function registerConfiguration(): IDisposable {
|
|||||||
$ref: ignoredSettingsSchemaId,
|
$ref: ignoredSettingsSchemaId,
|
||||||
additionalProperties: true,
|
additionalProperties: true,
|
||||||
uniqueItems: true
|
uniqueItems: true
|
||||||
|
},
|
||||||
|
'configurationSync.enableAuth': {
|
||||||
|
'type': 'boolean',
|
||||||
|
description: localize('configurationSync.enableAuth', "Enables authentication and requires VS Code restart when changed"),
|
||||||
|
'default': false,
|
||||||
|
'scope': ConfigurationScope.APPLICATION
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -44,4 +44,8 @@ export class UserDataSyncLogService extends AbstractLogService implements IUserD
|
|||||||
this.logger.critical(message, ...args);
|
this.logger.critical(message, ...args);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
flush(): void {
|
||||||
|
this.logger.flush();
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -131,27 +131,32 @@ export class UserDataAutoSync extends Disposable {
|
|||||||
@IAuthTokenService private readonly authTokenService: IAuthTokenService,
|
@IAuthTokenService private readonly authTokenService: IAuthTokenService,
|
||||||
) {
|
) {
|
||||||
super();
|
super();
|
||||||
this.updateEnablement();
|
this.updateEnablement(false);
|
||||||
this.sync(true);
|
this._register(Event.any<any>(authTokenService.onDidChangeStatus, userDataSyncService.onDidChangeStatus)(() => this.updateEnablement(true)));
|
||||||
this._register(Event.any<any>(authTokenService.onDidChangeStatus, userDataSyncService.onDidChangeStatus)(() => this.updateEnablement()));
|
this._register(Event.filter(this.configurationService.onDidChangeConfiguration, e => e.affectsConfiguration('configurationSync.enable'))(() => this.updateEnablement(true)));
|
||||||
this._register(Event.filter(this.configurationService.onDidChangeConfiguration, e => e.affectsConfiguration('configurationSync.enable'))(() => this.updateEnablement()));
|
|
||||||
|
|
||||||
// Sync immediately if there is a local change.
|
// Sync immediately if there is a local change.
|
||||||
this._register(Event.debounce(this.userDataSyncService.onDidChangeLocal, () => undefined, 500)(() => this.sync(false)));
|
this._register(Event.debounce(this.userDataSyncService.onDidChangeLocal, () => undefined, 500)(() => this.sync(false)));
|
||||||
}
|
}
|
||||||
|
|
||||||
private updateEnablement(): void {
|
private updateEnablement(stopIfDisabled: boolean): void {
|
||||||
const enabled = this.isSyncEnabled();
|
const enabled = this.isSyncEnabled();
|
||||||
if (this.enabled !== enabled) {
|
if (this.enabled === enabled) {
|
||||||
this.enabled = enabled;
|
return;
|
||||||
if (this.enabled) {
|
}
|
||||||
this.userDataSyncLogService.info('Syncing configuration started');
|
|
||||||
this.sync(true);
|
this.enabled = enabled;
|
||||||
} else {
|
if (this.enabled) {
|
||||||
|
this.userDataSyncLogService.info('Syncing configuration started');
|
||||||
|
this.sync(true);
|
||||||
|
return;
|
||||||
|
} else {
|
||||||
|
if (stopIfDisabled) {
|
||||||
this.userDataSyncService.stop();
|
this.userDataSyncService.stop();
|
||||||
this.userDataSyncLogService.info('Syncing configuration stopped.');
|
this.userDataSyncLogService.info('Syncing configuration stopped.');
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private async sync(loop: boolean): Promise<void> {
|
private async sync(loop: boolean): Promise<void> {
|
||||||
|
|||||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user