mirror of
https://github.com/microsoft/vscode.git
synced 2026-09-23 15:24:20 +01:00
electron 5 - bootstrap a nodeless configuration (#68302)
This commit is contained in:
@@ -406,10 +406,10 @@
|
||||
"./vs/workbench/services/extensions/electron-browser/cachedExtensionScanner.ts",
|
||||
"./vs/workbench/services/extensions/electron-browser/extensionHost.ts",
|
||||
"./vs/workbench/services/extensions/electron-browser/extensionHostProfiler.ts",
|
||||
"./vs/workbench/services/extensions/electron-browser/extensionManagementServerService.ts",
|
||||
"./vs/workbench/services/extensions/electron-browser/inactiveExtensionUrlHandler.ts",
|
||||
"./vs/workbench/services/extensions/node/extensionDescriptionRegistry.ts",
|
||||
"./vs/workbench/services/extensions/node/extensionHostProtocol.ts",
|
||||
"./vs/workbench/services/extensions/node/extensionManagementServerService.ts",
|
||||
"./vs/workbench/services/extensions/node/extensionPoints.ts",
|
||||
"./vs/workbench/services/extensions/node/lazyPromise.ts",
|
||||
"./vs/workbench/services/extensions/node/proxyIdentifier.ts",
|
||||
|
||||
+344
-1
@@ -3,6 +3,8 @@
|
||||
* Licensed under the MIT License. See License.txt in the project root for license information.
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
|
||||
import { isString } from 'vs/base/common/types';
|
||||
|
||||
/**
|
||||
* Return a hash value for an object.
|
||||
*/
|
||||
@@ -69,4 +71,345 @@ export class Hasher {
|
||||
this._value = hash(obj, this._value);
|
||||
return this._value;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
//#region SHA1
|
||||
|
||||
export function computeSHA1Hash(value: string): string {
|
||||
const data = encodeToArrayBuffer(value);
|
||||
const hash = new SHA1();
|
||||
|
||||
if (data.byteLength) {
|
||||
hash.update(data);
|
||||
}
|
||||
|
||||
return hash.digest();
|
||||
}
|
||||
|
||||
class SHA1 {
|
||||
|
||||
// Reference: http://en.wikipedia.org/wiki/SHA-1
|
||||
|
||||
private static BLOCK_SIZE = 64; // 512 / 8
|
||||
|
||||
private length: number;
|
||||
private buffer: Uint8Array | null;
|
||||
private bufferDV: DataView | null;
|
||||
private bufferLength: number;
|
||||
|
||||
private bigBlock32: DataView;
|
||||
private h0 = 0x67452301;
|
||||
private h1 = 0xEFCDAB89;
|
||||
private h2 = 0x98BADCFE;
|
||||
private h3 = 0x10325476;
|
||||
private h4 = 0xC3D2E1F0;
|
||||
|
||||
static digest(data: string): string;
|
||||
static digest(data: Uint8Array): string;
|
||||
static digest(data: ArrayBuffer): string;
|
||||
static digest(data: DataView): string;
|
||||
static digest(data: any): string {
|
||||
let sha = new SHA1();
|
||||
sha.update(data);
|
||||
|
||||
return sha.digest();
|
||||
}
|
||||
|
||||
constructor() {
|
||||
this.length = 0;
|
||||
|
||||
this.buffer = new Uint8Array(SHA1.BLOCK_SIZE);
|
||||
this.bufferDV = new DataView(this.buffer.buffer);
|
||||
this.bufferLength = 0;
|
||||
|
||||
this.bigBlock32 = new DataView(new ArrayBuffer(320)); // 80 * 4 = 320;
|
||||
}
|
||||
|
||||
update(data: string): void;
|
||||
update(data: Uint8Array): void;
|
||||
update(data: ArrayBuffer): void;
|
||||
update(data: DataView): void;
|
||||
update(arg: any): void {
|
||||
if (!this.buffer || !this.bufferDV) {
|
||||
throw new Error('Digest already computed.');
|
||||
}
|
||||
|
||||
let data: Uint8Array;
|
||||
|
||||
if (isString(arg)) {
|
||||
data = new Uint8Array(encodeToArrayBuffer(<string>arg));
|
||||
} else if (arg instanceof ArrayBuffer) {
|
||||
data = new Uint8Array(arg);
|
||||
} else if (arg instanceof DataView) {
|
||||
data = new Uint8Array((<DataView>arg).buffer);
|
||||
} else {
|
||||
data = <Uint8Array>arg;
|
||||
}
|
||||
|
||||
let bytesRead = 0, totalBytesRead = 0;
|
||||
|
||||
while (totalBytesRead < data.byteLength) {
|
||||
bytesRead = copy(this.buffer, this.bufferLength, data, totalBytesRead, data.byteLength);
|
||||
|
||||
this.bufferLength += bytesRead;
|
||||
totalBytesRead += bytesRead;
|
||||
|
||||
if (this.bufferLength === SHA1.BLOCK_SIZE) {
|
||||
this.step(this.bufferDV);
|
||||
this.bufferLength = 0;
|
||||
}
|
||||
}
|
||||
|
||||
this.length += totalBytesRead;
|
||||
}
|
||||
|
||||
digest(): string {
|
||||
if (this.buffer) {
|
||||
this.wrapUp();
|
||||
}
|
||||
|
||||
return toHexString(this.h0) + toHexString(this.h1) + toHexString(this.h2) + toHexString(this.h3) + toHexString(this.h4);
|
||||
}
|
||||
|
||||
private wrapUp(): void {
|
||||
if (!this.buffer || !this.bufferDV) {
|
||||
return; // already wrapped up
|
||||
}
|
||||
|
||||
this.buffer[this.bufferLength++] = 0x80;
|
||||
fill(this.buffer, this.bufferLength);
|
||||
|
||||
if (this.bufferLength > 56) {
|
||||
this.step(this.bufferDV);
|
||||
fill(this.buffer);
|
||||
}
|
||||
|
||||
let ml = multiply64(8, this.length);
|
||||
this.bufferDV.setUint32(56, ml[0], false);
|
||||
this.bufferDV.setUint32(60, ml[1], false);
|
||||
|
||||
this.step(this.bufferDV);
|
||||
|
||||
this.buffer = null;
|
||||
this.bufferDV = null;
|
||||
this.bufferLength = -1;
|
||||
}
|
||||
|
||||
private step(data: DataView): void {
|
||||
for (let j = 0; j < 64 /* 16*4 */; j += 4) {
|
||||
this.bigBlock32.setUint32(j, data.getUint32(j, false), false);
|
||||
}
|
||||
|
||||
for (let j = 64; j < 320 /* 80*4 */; j += 4) {
|
||||
this.bigBlock32.setUint32(j, leftRotate((this.bigBlock32.getUint32(j - 12, false) ^ this.bigBlock32.getUint32(j - 32, false) ^ this.bigBlock32.getUint32(j - 56, false) ^ this.bigBlock32.getUint32(j - 64, false)), 1), false);
|
||||
}
|
||||
|
||||
let a = this.h0;
|
||||
let b = this.h1;
|
||||
let c = this.h2;
|
||||
let d = this.h3;
|
||||
let e = this.h4;
|
||||
|
||||
let f: number, k: number;
|
||||
let temp: number;
|
||||
|
||||
for (let j = 0; j < 80; j++) {
|
||||
if (j < 20) {
|
||||
f = (b & c) | ((~b) & d);
|
||||
k = 0x5A827999;
|
||||
} else if (j < 40) {
|
||||
f = b ^ c ^ d;
|
||||
k = 0x6ED9EBA1;
|
||||
} else if (j < 60) {
|
||||
f = (b & c) | (b & d) | (c & d);
|
||||
k = 0x8F1BBCDC;
|
||||
} else {
|
||||
f = b ^ c ^ d;
|
||||
k = 0xCA62C1D6;
|
||||
}
|
||||
|
||||
temp = (leftRotate(a, 5) + f + e + k + this.bigBlock32.getUint32(j * 4, false)) & 0xFFFFFFFF;
|
||||
e = d;
|
||||
d = c;
|
||||
c = leftRotate(b, 30);
|
||||
b = a;
|
||||
a = temp;
|
||||
}
|
||||
|
||||
this.h0 = (this.h0 + a) & 0xFFFFFFFF;
|
||||
this.h1 = (this.h1 + b) & 0xFFFFFFFF;
|
||||
this.h2 = (this.h2 + c) & 0xFFFFFFFF;
|
||||
this.h3 = (this.h3 + d) & 0xFFFFFFFF;
|
||||
this.h4 = (this.h4 + e) & 0xFFFFFFFF;
|
||||
}
|
||||
}
|
||||
|
||||
function leftPad(value: string, length: number, char: string = '0'): string {
|
||||
return new Array(length - value.length + 1).join(char) + value;
|
||||
}
|
||||
|
||||
function toHexString(value: number, bitsize: number = 32): string {
|
||||
return leftPad((value >>> 0).toString(16), bitsize / 4);
|
||||
}
|
||||
|
||||
function leftRotate(value: number, bits: number, totalBits: number = 32): number {
|
||||
|
||||
// delta + bits = totalBits
|
||||
let delta = totalBits - bits;
|
||||
|
||||
// All ones, expect `delta` zeros aligned to the right
|
||||
let mask = ~((1 << delta) - 1);
|
||||
|
||||
// Join (value left-shifted `bits` bits) with (masked value right-shifted `delta` bits)
|
||||
return ((value << bits) | ((mask & value) >>> delta)) >>> 0;
|
||||
}
|
||||
|
||||
function multiply64(a: number, b: number): number[] {
|
||||
/* A1 A0 => A
|
||||
* B1 B0 => B
|
||||
* B0 * A1 B0 * A0
|
||||
* B1 * A1 B1 * A0
|
||||
* C3 C2 C1 C0 => C
|
||||
*/
|
||||
|
||||
let a0 = a & 0xFFFF, a1 = a >>> 16;
|
||||
let b0 = b & 0xFFFF, b1 = b >>> 16;
|
||||
let c0 = 0, c1 = 0, c2 = 0, c3 = 0;
|
||||
|
||||
let x = b0 * a0;
|
||||
c0 += x & 0xFFFF;
|
||||
c1 += x >>> 16;
|
||||
|
||||
x = b0 * a1;
|
||||
c1 += x & 0xFFFF;
|
||||
c2 += x >>> 16;
|
||||
|
||||
x = b1 * a0;
|
||||
c1 += x & 0xFFFF;
|
||||
c2 += x >>> 16;
|
||||
|
||||
c2 += c1 >>> 16;
|
||||
c1 = c1 & 0xFFFF;
|
||||
|
||||
x = b1 * a1;
|
||||
c2 += x & 0xFFFF;
|
||||
c3 += x >>> 16;
|
||||
|
||||
c3 += c2 >>> 16;
|
||||
c2 = c2 & 0xFFFF;
|
||||
|
||||
return [(c3 << 16 | c2) >>> 0, (c1 << 16 | c0) >>> 0];
|
||||
}
|
||||
|
||||
function encodeToArrayBuffer(str: string): ArrayBuffer {
|
||||
let i: number, len: number, length = 0, charCode = 0, trailCharCode = 0, codepoint = 0;
|
||||
|
||||
// First pass, for the size
|
||||
for (i = 0, len = str.length; i < len; i++) {
|
||||
charCode = str.charCodeAt(i);
|
||||
|
||||
// Surrogate pair
|
||||
if (charCode >= 0xD800 && charCode < 0xDC00) {
|
||||
trailCharCode = str.charCodeAt(++i);
|
||||
|
||||
if (!(trailCharCode >= 0xDC00 && trailCharCode < 0xE000)) {
|
||||
throw new Error('Invalid char code');
|
||||
}
|
||||
|
||||
// Code point can be obtained by subtracting 0xD800 and 0xDC00 from both char codes respectively
|
||||
// and joining the 10 least significant bits from each, finally adding 0x10000.
|
||||
codepoint = ((((charCode - 0xD800) & 0x3FF) << 10) | ((trailCharCode - 0xDC00) & 0x3FF)) + 0x10000;
|
||||
|
||||
} else {
|
||||
codepoint = charCode;
|
||||
}
|
||||
|
||||
length += byteSizeInUTF8(codepoint);
|
||||
}
|
||||
|
||||
let result = new ArrayBuffer(length);
|
||||
let view = new Uint8Array(result);
|
||||
let pos = 0;
|
||||
|
||||
// Second pass, for the data
|
||||
for (i = 0, len = str.length; i < len; i++) {
|
||||
charCode = str.charCodeAt(i);
|
||||
|
||||
if (charCode >= 0xD800 && charCode < 0xDC00) {
|
||||
trailCharCode = str.charCodeAt(++i);
|
||||
codepoint = ((((charCode - 0xD800) & 0x3FF) << 10) | ((trailCharCode - 0xDC00) & 0x3FF)) + 0x10000;
|
||||
} else {
|
||||
codepoint = charCode;
|
||||
}
|
||||
|
||||
pos += writeUTF8(codepoint, view, pos);
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
function byteSizeInUTF8(codePoint: number): number {
|
||||
codePoint = codePoint >>> 0;
|
||||
|
||||
if (codePoint < 0x80) {
|
||||
return 1;
|
||||
} else if (codePoint < 0x800) {
|
||||
return 2;
|
||||
} else if (codePoint < 0x10000) {
|
||||
return 3;
|
||||
} else if (codePoint < 0x200000) {
|
||||
return 4;
|
||||
} else if (codePoint < 0x4000000) {
|
||||
return 5;
|
||||
} else if (codePoint < 0x80000000) {
|
||||
return 6;
|
||||
} else {
|
||||
throw new Error('Code point 0x' + toHexString(codePoint) + ' not encodable in UTF8.');
|
||||
}
|
||||
}
|
||||
|
||||
function writeUTF8(codePoint: number, buffer: Uint8Array, pos: number): number {
|
||||
|
||||
// How many bits needed for codePoint
|
||||
let byteSize = byteSizeInUTF8(codePoint);
|
||||
|
||||
// 0xxxxxxx
|
||||
if (byteSize === 1) {
|
||||
buffer[pos] = codePoint;
|
||||
return 1;
|
||||
}
|
||||
|
||||
// 110xxxxx 10xxxxxx
|
||||
// 1110xxxx 10xxxxxx 10xxxxxx
|
||||
// 11110xxx 10xxxxxx 10xxxxxx 10xxxxxx
|
||||
// 111110xx 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx
|
||||
// 1111110x 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx 10xxxxxx
|
||||
|
||||
// first byte
|
||||
buffer[pos] = ((0xFC << (6 - byteSize)) | (codePoint >>> (6 * (byteSize - 1)))) & 0xFF;
|
||||
|
||||
// successive bytes
|
||||
for (let i = 1; i < byteSize; i++) {
|
||||
buffer[pos + i] = (0x80 | (0x3F & (codePoint >>> (6 * (byteSize - i - 1))))) & 0xFF;
|
||||
}
|
||||
|
||||
return byteSize;
|
||||
}
|
||||
|
||||
function copy(dest: Uint8Array, destIndex: number, src: Uint8Array, srcIndex: number, count: number): number {
|
||||
const len = Math.min(dest.byteLength - destIndex, src.byteLength - srcIndex, count);
|
||||
|
||||
for (let i = 0; i < len; i++) {
|
||||
dest[destIndex + i] = src[srcIndex + i];
|
||||
}
|
||||
|
||||
return len;
|
||||
}
|
||||
|
||||
function fill(dest: Uint8Array, index: number = 0, count: number = dest.byteLength, value: number = 0): void {
|
||||
for (let i = 0; i < count; i++) {
|
||||
dest[index + i] = value;
|
||||
}
|
||||
}
|
||||
|
||||
//#endregion
|
||||
@@ -3,7 +3,7 @@
|
||||
* Licensed under the MIT License. See License.txt in the project root for license information.
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
import * as assert from 'assert';
|
||||
import { hash } from 'vs/base/common/hash';
|
||||
import { hash, computeSHA1Hash } from 'vs/base/common/hash';
|
||||
|
||||
suite('Hash', () => {
|
||||
test('string', () => {
|
||||
@@ -43,4 +43,12 @@ suite('Hash', () => {
|
||||
assert.notEqual(hash({ 'foo': 'bar' }), hash({ 'foo': 'bar2' }));
|
||||
assert.notEqual(hash({}), hash([]));
|
||||
});
|
||||
|
||||
test('computeSHA1Hash', () => {
|
||||
assert.equal(computeSHA1Hash(''), 'da39a3ee5e6b4b0d3255bfef95601890afd80709');
|
||||
assert.equal(computeSHA1Hash('hello world'), '2aae6c35c94fcfb415dbe95f408b9ce91ee846ed');
|
||||
assert.equal(computeSHA1Hash('da39a3ee5e6b4b0d3255bfef95601890afd80709'), '10a34637ad661d98ba3344717656fcc76209c2f8');
|
||||
assert.equal(computeSHA1Hash('2aae6c35c94fcfb415dbe95f408b9ce91ee846ed'), 'd6b0d82cea4269b51572b8fab43adcee9fc3cf9a');
|
||||
assert.equal(computeSHA1Hash('öäü_?ß()<>ÖÄÜ'), 'b64beaeff9e317b0193c8e40a2431b210388eba9');
|
||||
});
|
||||
});
|
||||
@@ -16,7 +16,6 @@ import * as os from 'os';
|
||||
import { debounce } from 'vs/base/common/decorators';
|
||||
import * as platform from 'vs/base/common/platform';
|
||||
import { Disposable } from 'vs/base/common/lifecycle';
|
||||
import { Client as ElectronIPCClient } from 'vs/base/parts/ipc/electron-browser/ipc.electron-browser';
|
||||
import { getDelayedChannel } from 'vs/base/parts/ipc/node/ipc';
|
||||
import { connect as connectNet } from 'vs/base/parts/ipc/node/ipc.net';
|
||||
import { ServiceCollection } from 'vs/platform/instantiation/common/serviceCollection';
|
||||
@@ -28,7 +27,8 @@ import { TelemetryAppenderClient } from 'vs/platform/telemetry/node/telemetryIpc
|
||||
import { ITelemetryService } from 'vs/platform/telemetry/common/telemetry';
|
||||
import { InstantiationService } from 'vs/platform/instantiation/common/instantiationService';
|
||||
import { resolveCommonProperties } from 'vs/platform/telemetry/node/commonProperties';
|
||||
import { WindowsChannelClient } from 'vs/platform/windows/node/windowsIpc';
|
||||
import { WindowsService } from 'vs/platform/windows/electron-browser/windowsService';
|
||||
import { MainProcessService, IMainProcessService } from 'vs/platform/ipc/electron-browser/mainProcessService';
|
||||
import { EnvironmentService } from 'vs/platform/environment/node/environmentService';
|
||||
import { IssueReporterModel } from 'vs/code/electron-browser/issue/issueReporterModel';
|
||||
import { IssueReporterData, IssueReporterStyles, IssueType, ISettingsSearchIssueReporterData, IssueReporterFeatures, IssueReporterExtensionData } from 'vs/platform/issue/common/issue';
|
||||
@@ -273,14 +273,14 @@ export class IssueReporter extends Disposable {
|
||||
|
||||
private initServices(configuration: IWindowConfiguration): void {
|
||||
const serviceCollection = new ServiceCollection();
|
||||
const mainProcessClient = new ElectronIPCClient(String(`window${configuration.windowId}`));
|
||||
const mainProcessService = new MainProcessService(configuration.windowId);
|
||||
serviceCollection.set(IMainProcessService, mainProcessService);
|
||||
|
||||
const windowsChannel = mainProcessClient.getChannel('windows');
|
||||
serviceCollection.set(IWindowsService, new WindowsChannelClient(windowsChannel));
|
||||
serviceCollection.set(IWindowsService, new WindowsService(mainProcessService));
|
||||
this.environmentService = new EnvironmentService(configuration, configuration.execPath);
|
||||
|
||||
const logService = createSpdLogService(`issuereporter${configuration.windowId}`, getLogLevel(this.environmentService), this.environmentService.logsPath);
|
||||
const logLevelClient = new LogLevelSetterChannelClient(mainProcessClient.getChannel('loglevel'));
|
||||
const logLevelClient = new LogLevelSetterChannelClient(mainProcessService.getChannel('loglevel'));
|
||||
this.logService = new FollowerLogService(logLevelClient, logService);
|
||||
|
||||
const sharedProcess = (<IWindowsService>serviceCollection.get(IWindowsService)).whenSharedProcessReady()
|
||||
|
||||
@@ -28,7 +28,7 @@ import { TelemetryAppenderChannel } from 'vs/platform/telemetry/node/telemetryIp
|
||||
import { TelemetryService, ITelemetryServiceConfig } from 'vs/platform/telemetry/common/telemetryService';
|
||||
import { AppInsightsAppender } from 'vs/platform/telemetry/node/appInsightsAppender';
|
||||
import { IWindowsService, ActiveWindowManager } from 'vs/platform/windows/common/windows';
|
||||
import { WindowsChannelClient } from 'vs/platform/windows/node/windowsIpc';
|
||||
import { WindowsService } from 'vs/platform/windows/electron-browser/windowsService';
|
||||
import { ipcRenderer } from 'electron';
|
||||
import { createSpdLogService } from 'vs/platform/log/node/spdlogService';
|
||||
import { ILogService, LogLevel } from 'vs/platform/log/common/log';
|
||||
@@ -41,11 +41,13 @@ import { IDialogService } from 'vs/platform/dialogs/common/dialogs';
|
||||
import { IDisposable, dispose, combinedDisposable, toDisposable } from 'vs/base/common/lifecycle';
|
||||
import { DownloadService } from 'vs/platform/download/node/downloadService';
|
||||
import { IDownloadService } from 'vs/platform/download/common/download';
|
||||
import { StaticRouter } from 'vs/base/parts/ipc/node/ipc';
|
||||
import { StaticRouter, IServerChannel, IChannel } from 'vs/base/parts/ipc/node/ipc';
|
||||
import { NodeCachedDataCleaner } from 'vs/code/electron-browser/sharedProcess/contrib/nodeCachedDataCleaner';
|
||||
import { LanguagePackCachedDataCleaner } from 'vs/code/electron-browser/sharedProcess/contrib/languagePackCachedDataCleaner';
|
||||
import { StorageDataCleaner } from 'vs/code/electron-browser/sharedProcess/contrib/storageDataCleaner';
|
||||
import { LogsDataCleaner } from 'vs/code/electron-browser/sharedProcess/contrib/logsDataCleaner';
|
||||
import { IMainProcessService } from 'vs/platform/ipc/electron-browser/mainProcessService';
|
||||
import { ServiceIdentifier } from 'vs/platform/instantiation/common/instantiation';
|
||||
|
||||
export interface ISharedProcessConfiguration {
|
||||
readonly machineId: string;
|
||||
@@ -63,6 +65,20 @@ interface ISharedProcessInitData {
|
||||
|
||||
const eventPrefix = 'monacoworkbench';
|
||||
|
||||
class MainProcessService implements IMainProcessService {
|
||||
constructor(private server: Server, private mainRouter: StaticRouter) { }
|
||||
|
||||
_serviceBrand: ServiceIdentifier<any>;
|
||||
|
||||
getChannel(channelName: string): IChannel {
|
||||
return this.server.getChannel(channelName, this.mainRouter);
|
||||
}
|
||||
|
||||
registerChannel(channelName: string, channel: IServerChannel<string>): void {
|
||||
this.server.registerChannel(channelName, channel);
|
||||
}
|
||||
}
|
||||
|
||||
function main(server: Server, initData: ISharedProcessInitData, configuration: ISharedProcessConfiguration): void {
|
||||
const services = new ServiceCollection();
|
||||
|
||||
@@ -89,8 +105,10 @@ function main(server: Server, initData: ISharedProcessInitData, configuration: I
|
||||
services.set(IRequestService, new SyncDescriptor(RequestService));
|
||||
services.set(IDownloadService, new SyncDescriptor(DownloadService));
|
||||
|
||||
const windowsChannel = server.getChannel('windows', mainRouter);
|
||||
const windowsService = new WindowsChannelClient(windowsChannel);
|
||||
const mainProcessService = new MainProcessService(server, mainRouter);
|
||||
services.set(IMainProcessService, mainProcessService);
|
||||
|
||||
const windowsService = new WindowsService(mainProcessService);
|
||||
services.set(IWindowsService, windowsService);
|
||||
|
||||
const activeWindowManager = new ActiveWindowManager(windowsService);
|
||||
|
||||
@@ -0,0 +1,12 @@
|
||||
<!-- Copyright (C) Microsoft Corporation. All rights reserved. -->
|
||||
<!DOCTYPE html>
|
||||
<html>
|
||||
<head>
|
||||
<meta charset="utf-8" />
|
||||
</head>
|
||||
<body class="monaco-shell vs-dark" aria-label="">
|
||||
</body>
|
||||
|
||||
<!-- Startup via workbench.nodeless.js -->
|
||||
<script src="workbench.nodeless.js"></script>
|
||||
</html>
|
||||
@@ -0,0 +1,38 @@
|
||||
/*---------------------------------------------------------------------------------------------
|
||||
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||
* Licensed under the MIT License. See License.txt in the project root for license information.
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
|
||||
//@ts-check
|
||||
'use strict';
|
||||
|
||||
(function () {
|
||||
|
||||
function loadScript(path, callback) {
|
||||
let script = document.createElement('script');
|
||||
script.onload = callback;
|
||||
script.async = true;
|
||||
script.type = 'text/javascript';
|
||||
script.src = path;
|
||||
document.head.appendChild(script);
|
||||
}
|
||||
|
||||
loadScript('../../../../../src/vs/loader.js', function () {
|
||||
|
||||
// @ts-ignore
|
||||
require.config({
|
||||
baseUrl: 'file:../../../../../out'
|
||||
});
|
||||
|
||||
// @ts-ignore
|
||||
require([
|
||||
'vs/workbench/workbench.nodeless.main',
|
||||
'vs/nls!vs/workbench/workbench.nodeless.main',
|
||||
'vs/css!vs/workbench/workbench.nodeless.main'
|
||||
], function () {
|
||||
|
||||
// @ts-ignore
|
||||
require('vs/workbench/browser/nodeless.main').main().then(undefined, console.error);
|
||||
});
|
||||
});
|
||||
})();
|
||||
@@ -78,6 +78,8 @@ export class CodeWindow extends Disposable implements ICodeWindow {
|
||||
|
||||
private readonly touchBarGroups: Electron.TouchBarSegmentedControl[];
|
||||
|
||||
private nodeless: boolean;
|
||||
|
||||
constructor(
|
||||
config: IWindowCreationOptions,
|
||||
@ILogService private readonly logService: ILogService,
|
||||
@@ -94,6 +96,8 @@ export class CodeWindow extends Disposable implements ICodeWindow {
|
||||
this._readyState = ReadyState.NONE;
|
||||
this.whenReadyCallbacks = [];
|
||||
|
||||
this.nodeless = !!(environmentService.args.nodeless && !environmentService.isBuilt);
|
||||
|
||||
// create browser window
|
||||
this.createBrowserWindow(config);
|
||||
|
||||
@@ -123,7 +127,7 @@ export class CodeWindow extends Disposable implements ICodeWindow {
|
||||
height: this.windowState.height,
|
||||
x: this.windowState.x,
|
||||
y: this.windowState.y,
|
||||
backgroundColor: getBackgroundColor(this.stateService),
|
||||
backgroundColor: this.nodeless ? undefined : getBackgroundColor(this.stateService),
|
||||
minWidth: CodeWindow.MIN_WIDTH,
|
||||
minHeight: CodeWindow.MIN_HEIGHT,
|
||||
show: !isFullscreenOrMaximized,
|
||||
@@ -133,10 +137,14 @@ export class CodeWindow extends Disposable implements ICodeWindow {
|
||||
// want to enforce that Code stays in the foreground. This triggers a disable_hidden_
|
||||
// flag that Electron provides via patch:
|
||||
// https://github.com/electron/libchromiumcontent/blob/master/patches/common/chromium/disable_hidden.patch
|
||||
'backgroundThrottling': false
|
||||
backgroundThrottling: false
|
||||
}
|
||||
};
|
||||
|
||||
if (this.nodeless) {
|
||||
options.webPreferences!.nodeIntegration = false; // simulate Electron 5 behaviour
|
||||
}
|
||||
|
||||
if (isLinux) {
|
||||
options.icon = path.join(this.environmentService.appRoot, 'resources/linux/code.png'); // Windows and Mac are better off using the embedded icon(s)
|
||||
}
|
||||
@@ -188,6 +196,10 @@ export class CodeWindow extends Disposable implements ICodeWindow {
|
||||
}
|
||||
}
|
||||
|
||||
if (this.nodeless) {
|
||||
this._win.webContents.toggleDevTools();
|
||||
}
|
||||
|
||||
this._lastFocusTime = Date.now(); // since we show directly, we need to set the last focus time too
|
||||
}
|
||||
|
||||
@@ -387,7 +399,7 @@ export class CodeWindow extends Disposable implements ICodeWindow {
|
||||
}
|
||||
|
||||
// Window (Un)Maximize
|
||||
this._win.on('maximize', e => {
|
||||
this._win.on('maximize', (e: Event) => {
|
||||
if (this.currentConfig) {
|
||||
this.currentConfig.maximized = true;
|
||||
}
|
||||
@@ -395,7 +407,7 @@ export class CodeWindow extends Disposable implements ICodeWindow {
|
||||
app.emit('browser-window-maximize', e, this._win);
|
||||
});
|
||||
|
||||
this._win.on('unmaximize', e => {
|
||||
this._win.on('unmaximize', (e: Event) => {
|
||||
if (this.currentConfig) {
|
||||
this.currentConfig.maximized = false;
|
||||
}
|
||||
@@ -618,6 +630,10 @@ export class CodeWindow extends Disposable implements ICodeWindow {
|
||||
}
|
||||
|
||||
private doGetUrl(config: object): string {
|
||||
if (this.nodeless) {
|
||||
return `${require.toUrl('vs/code/electron-browser/workbench/workbench.nodeless.html')}?config=${encodeURIComponent(JSON.stringify(config))}`;
|
||||
}
|
||||
|
||||
return `${require.toUrl('vs/code/electron-browser/workbench/workbench.html')}?config=${encodeURIComponent(JSON.stringify(config))}`;
|
||||
}
|
||||
|
||||
|
||||
@@ -42,7 +42,6 @@ import { IProgressRunner, IProgressService } from 'vs/platform/progress/common/p
|
||||
import { ITelemetryInfo, ITelemetryService } from 'vs/platform/telemetry/common/telemetry';
|
||||
import { IWorkspace, IWorkspaceContextService, IWorkspaceFolder, IWorkspaceFoldersChangeEvent, WorkbenchState, WorkspaceFolder } from 'vs/platform/workspace/common/workspace';
|
||||
import { ISingleFolderWorkspaceIdentifier, IWorkspaceIdentifier } from 'vs/platform/workspaces/common/workspaces';
|
||||
import { IAccessibilityService, AccessibilitySupport } from 'vs/platform/accessibility/common/accessibility';
|
||||
import { ILayoutService, IDimension } from 'vs/platform/layout/browser/layoutService';
|
||||
|
||||
export class SimpleModel implements IResolvedTextEditorModel {
|
||||
@@ -218,31 +217,6 @@ export class SimpleNotificationService implements INotificationService {
|
||||
}
|
||||
}
|
||||
|
||||
export class BrowserAccessibilityService implements IAccessibilityService {
|
||||
_serviceBrand: any;
|
||||
|
||||
private _accessibilitySupport = AccessibilitySupport.Unknown;
|
||||
private readonly _onDidChangeAccessibilitySupport = new Emitter<void>();
|
||||
readonly onDidChangeAccessibilitySupport: Event<void> = this._onDidChangeAccessibilitySupport.event;
|
||||
|
||||
alwaysUnderlineAccessKeys(): Promise<boolean> {
|
||||
return Promise.resolve(false);
|
||||
}
|
||||
|
||||
setAccessibilitySupport(accessibilitySupport: AccessibilitySupport): void {
|
||||
if (this._accessibilitySupport === accessibilitySupport) {
|
||||
return;
|
||||
}
|
||||
|
||||
this._accessibilitySupport = accessibilitySupport;
|
||||
this._onDidChangeAccessibilitySupport.fire();
|
||||
}
|
||||
|
||||
getAccessibilitySupport(): AccessibilitySupport {
|
||||
return this._accessibilitySupport;
|
||||
}
|
||||
}
|
||||
|
||||
export class StandaloneCommandService implements ICommandService {
|
||||
_serviceBrand: any;
|
||||
|
||||
|
||||
@@ -13,7 +13,7 @@ import { ModeServiceImpl } from 'vs/editor/common/services/modeServiceImpl';
|
||||
import { IModelService } from 'vs/editor/common/services/modelService';
|
||||
import { ModelServiceImpl } from 'vs/editor/common/services/modelServiceImpl';
|
||||
import { ITextResourceConfigurationService, ITextResourcePropertiesService } from 'vs/editor/common/services/resourceConfiguration';
|
||||
import { SimpleBulkEditService, SimpleConfigurationService, SimpleDialogService, SimpleNotificationService, SimpleProgressService, SimpleResourceConfigurationService, SimpleResourcePropertiesService, SimpleUriLabelService, SimpleWorkspaceContextService, StandaloneCommandService, StandaloneKeybindingService, StandaloneTelemetryService, BrowserAccessibilityService, SimpleLayoutService } from 'vs/editor/standalone/browser/simpleServices';
|
||||
import { SimpleBulkEditService, SimpleConfigurationService, SimpleDialogService, SimpleNotificationService, SimpleProgressService, SimpleResourceConfigurationService, SimpleResourcePropertiesService, SimpleUriLabelService, SimpleWorkspaceContextService, StandaloneCommandService, StandaloneKeybindingService, StandaloneTelemetryService, SimpleLayoutService } from 'vs/editor/standalone/browser/simpleServices';
|
||||
import { StandaloneCodeEditorServiceImpl } from 'vs/editor/standalone/browser/standaloneCodeServiceImpl';
|
||||
import { StandaloneThemeServiceImpl } from 'vs/editor/standalone/browser/standaloneThemeServiceImpl';
|
||||
import { IStandaloneThemeService } from 'vs/editor/standalone/common/standaloneThemeService';
|
||||
@@ -46,6 +46,7 @@ import { IMarkerDecorationsService } from 'vs/editor/common/services/markersDeco
|
||||
import { MarkerDecorationsService } from 'vs/editor/common/services/markerDecorationsServiceImpl';
|
||||
import { ISuggestMemoryService, SuggestMemoryService } from 'vs/editor/contrib/suggest/suggestMemory';
|
||||
import { IAccessibilityService } from 'vs/platform/accessibility/common/accessibility';
|
||||
import { BrowserAccessibilityService } from 'vs/platform/accessibility/common/accessibilityService';
|
||||
import { ILayoutService } from 'vs/platform/layout/browser/layoutService';
|
||||
|
||||
export interface IEditorOverrideServices {
|
||||
@@ -201,7 +202,7 @@ export class DynamicStandaloneServices extends Disposable {
|
||||
|
||||
let contextViewService = ensure(IContextViewService, () => this._register(new ContextViewService(layoutService)));
|
||||
|
||||
ensure(IContextMenuService, () => this._register(new ContextMenuService(domElement, telemetryService, notificationService, contextViewService, keybindingService, themeService)));
|
||||
ensure(IContextMenuService, () => this._register(new ContextMenuService(layoutService, telemetryService, notificationService, contextViewService, keybindingService, themeService)));
|
||||
|
||||
ensure(IMenuService, () => new MenuService(commandService));
|
||||
|
||||
|
||||
@@ -0,0 +1,34 @@
|
||||
/*---------------------------------------------------------------------------------------------
|
||||
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||
* Licensed under the MIT License. See License.txt in the project root for license information.
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
|
||||
import { Emitter, Event } from 'vs/base/common/event';
|
||||
import { IAccessibilityService, AccessibilitySupport } from 'vs/platform/accessibility/common/accessibility';
|
||||
import { Disposable } from 'vs/base/common/lifecycle';
|
||||
|
||||
export class BrowserAccessibilityService extends Disposable implements IAccessibilityService {
|
||||
|
||||
_serviceBrand: any;
|
||||
|
||||
private _accessibilitySupport = AccessibilitySupport.Unknown;
|
||||
private readonly _onDidChangeAccessibilitySupport = new Emitter<void>();
|
||||
readonly onDidChangeAccessibilitySupport: Event<void> = this._onDidChangeAccessibilitySupport.event;
|
||||
|
||||
alwaysUnderlineAccessKeys(): Promise<boolean> {
|
||||
return Promise.resolve(false);
|
||||
}
|
||||
|
||||
setAccessibilitySupport(accessibilitySupport: AccessibilitySupport): void {
|
||||
if (this._accessibilitySupport === accessibilitySupport) {
|
||||
return;
|
||||
}
|
||||
|
||||
this._accessibilitySupport = accessibilitySupport;
|
||||
this._onDidChangeAccessibilitySupport.fire();
|
||||
}
|
||||
|
||||
getAccessibilitySupport(): AccessibilitySupport {
|
||||
return this._accessibilitySupport;
|
||||
}
|
||||
}
|
||||
@@ -12,6 +12,7 @@ import { IContextMenuDelegate } from 'vs/base/browser/contextmenu';
|
||||
import { IThemeService } from 'vs/platform/theme/common/themeService';
|
||||
import { IKeybindingService } from 'vs/platform/keybinding/common/keybinding';
|
||||
import { Disposable } from 'vs/base/common/lifecycle';
|
||||
import { ILayoutService } from 'vs/platform/layout/browser/layoutService';
|
||||
|
||||
export class ContextMenuService extends Disposable implements IContextMenuService {
|
||||
_serviceBrand: any;
|
||||
@@ -22,7 +23,7 @@ export class ContextMenuService extends Disposable implements IContextMenuServic
|
||||
private contextMenuHandler: ContextMenuHandler;
|
||||
|
||||
constructor(
|
||||
container: HTMLElement | null,
|
||||
@ILayoutService layoutService: ILayoutService,
|
||||
@ITelemetryService telemetryService: ITelemetryService,
|
||||
@INotificationService notificationService: INotificationService,
|
||||
@IContextViewService contextViewService: IContextViewService,
|
||||
@@ -31,7 +32,7 @@ export class ContextMenuService extends Disposable implements IContextMenuServic
|
||||
) {
|
||||
super();
|
||||
|
||||
this.contextMenuHandler = this._register(new ContextMenuHandler(container, contextViewService, telemetryService, notificationService, keybindingService, themeService));
|
||||
this.contextMenuHandler = this._register(new ContextMenuHandler(layoutService.container, contextViewService, telemetryService, notificationService, keybindingService, themeService));
|
||||
}
|
||||
|
||||
dispose(): void {
|
||||
|
||||
@@ -4,19 +4,13 @@
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
|
||||
import { URI } from 'vs/base/common/uri';
|
||||
import * as path from 'vs/base/common/path';
|
||||
import * as fs from 'fs';
|
||||
import { IChannel, IServerChannel } from 'vs/base/parts/ipc/node/ipc';
|
||||
import { IServerChannel } from 'vs/base/parts/ipc/node/ipc';
|
||||
import { Event, Emitter } from 'vs/base/common/event';
|
||||
import { IDownloadService } from 'vs/platform/download/common/download';
|
||||
import { mkdirp } from 'vs/base/node/pfs';
|
||||
import { IURITransformer } from 'vs/base/common/uriIpc';
|
||||
import { tmpdir } from 'os';
|
||||
import { generateUuid } from 'vs/base/common/uuid';
|
||||
|
||||
export type UploadResponse = Buffer | string | undefined;
|
||||
type UploadResponse = Buffer | string | undefined;
|
||||
|
||||
export function upload(uri: URI): Event<UploadResponse> {
|
||||
function upload(uri: URI): Event<UploadResponse> {
|
||||
const stream = new Emitter<UploadResponse>();
|
||||
const readstream = fs.createReadStream(uri.fsPath);
|
||||
readstream.on('data', data => stream.fire(data));
|
||||
@@ -41,36 +35,3 @@ export class DownloadServiceChannel implements IServerChannel {
|
||||
throw new Error(`Call not found: ${command}`);
|
||||
}
|
||||
}
|
||||
|
||||
export class DownloadServiceChannelClient implements IDownloadService {
|
||||
|
||||
_serviceBrand: any;
|
||||
|
||||
constructor(private channel: IChannel, private getUriTransformer: () => IURITransformer) { }
|
||||
|
||||
download(from: URI, to: string = path.join(tmpdir(), generateUuid())): Promise<string> {
|
||||
from = this.getUriTransformer().transformOutgoingURI(from);
|
||||
const dirName = path.dirname(to);
|
||||
let out: fs.WriteStream;
|
||||
return new Promise<string>((c, e) => {
|
||||
return mkdirp(dirName)
|
||||
.then(() => {
|
||||
out = fs.createWriteStream(to);
|
||||
out.once('close', () => c(to));
|
||||
out.once('error', e);
|
||||
const uploadStream = this.channel.listen<UploadResponse>('upload', from);
|
||||
const disposable = uploadStream(result => {
|
||||
if (result === undefined) {
|
||||
disposable.dispose();
|
||||
out.end(() => c(to));
|
||||
} else if (Buffer.isBuffer(result)) {
|
||||
out.write(result);
|
||||
} else if (typeof result === 'string') {
|
||||
disposable.dispose();
|
||||
out.end(() => e(result));
|
||||
}
|
||||
});
|
||||
});
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
@@ -3,10 +3,10 @@
|
||||
* Licensed under the MIT License. See License.txt in the project root for license information.
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
|
||||
import { IDisposable, toDisposable, combinedDisposable } from 'vs/base/common/lifecycle';
|
||||
import { IDisposable, toDisposable } from 'vs/base/common/lifecycle';
|
||||
import { IWindowDriver, IElement, WindowDriverChannel, WindowDriverRegistryChannelClient } from 'vs/platform/driver/node/driver';
|
||||
import { IPCClient } from 'vs/base/parts/ipc/node/ipc';
|
||||
import { IInstantiationService } from 'vs/platform/instantiation/common/instantiation';
|
||||
import { IInstantiationService, ServicesAccessor } from 'vs/platform/instantiation/common/instantiation';
|
||||
import { IMainProcessService } from 'vs/platform/ipc/electron-browser/mainProcessService';
|
||||
import { getTopLeftOffset, getClientArea } from 'vs/base/browser/dom';
|
||||
import * as electron from 'electron';
|
||||
import { IWindowService } from 'vs/platform/windows/common/windows';
|
||||
@@ -214,25 +214,24 @@ class WindowDriver implements IWindowDriver {
|
||||
}
|
||||
}
|
||||
|
||||
export async function registerWindowDriver(
|
||||
client: IPCClient,
|
||||
windowId: number,
|
||||
instantiationService: IInstantiationService
|
||||
): Promise<IDisposable> {
|
||||
export async function registerWindowDriver(accessor: ServicesAccessor): Promise<IDisposable> {
|
||||
const instantiationService = accessor.get(IInstantiationService);
|
||||
const mainProcessService = accessor.get(IMainProcessService);
|
||||
const windowService = accessor.get(IWindowService);
|
||||
|
||||
const windowDriver = instantiationService.createInstance(WindowDriver);
|
||||
const windowDriverChannel = new WindowDriverChannel(windowDriver);
|
||||
client.registerChannel('windowDriver', windowDriverChannel);
|
||||
mainProcessService.registerChannel('windowDriver', windowDriverChannel);
|
||||
|
||||
const windowDriverRegistryChannel = client.getChannel('windowDriverRegistry');
|
||||
const windowDriverRegistryChannel = mainProcessService.getChannel('windowDriverRegistry');
|
||||
const windowDriverRegistry = new WindowDriverRegistryChannelClient(windowDriverRegistryChannel);
|
||||
|
||||
await windowDriverRegistry.registerWindowDriver(windowId);
|
||||
await windowDriverRegistry.registerWindowDriver(windowService.getCurrentWindowId());
|
||||
// const options = await windowDriverRegistry.registerWindowDriver(windowId);
|
||||
|
||||
// if (options.verbose) {
|
||||
// windowDriver.openDevTools();
|
||||
// }
|
||||
|
||||
const disposable = toDisposable(() => windowDriverRegistry.reloadWindowDriver(windowId));
|
||||
return combinedDisposable([disposable, client]);
|
||||
return toDisposable(() => windowDriverRegistry.reloadWindowDriver(windowService.getCurrentWindowId()));
|
||||
}
|
||||
|
||||
@@ -69,6 +69,7 @@ export interface ParsedArgs {
|
||||
'driver'?: string;
|
||||
'driver-verbose'?: boolean;
|
||||
remote?: string;
|
||||
'nodeless'?: boolean; // TODO@ben revisit electron5 nodeless support
|
||||
}
|
||||
|
||||
export const IEnvironmentService = createDecorator<IEnvironmentService>('environmentService');
|
||||
|
||||
@@ -91,7 +91,8 @@ export const options: Option[] = [
|
||||
{ id: 'force', type: 'boolean' },
|
||||
{ id: 'trace-category-filter', type: 'string' },
|
||||
{ id: 'trace-options', type: 'string' },
|
||||
{ id: 'prof-code-loading', type: 'boolean' }
|
||||
{ id: 'prof-code-loading', type: 'boolean' },
|
||||
{ id: 'nodeless', type: 'boolean' } // TODO@ben revisit electron5 nodeless support
|
||||
];
|
||||
|
||||
export function parseArgs(args: string[], isOptionSupported = (_: Option) => true): ParsedArgs {
|
||||
|
||||
@@ -0,0 +1,43 @@
|
||||
/*---------------------------------------------------------------------------------------------
|
||||
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||
* Licensed under the MIT License. See License.txt in the project root for license information.
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
|
||||
import { createDecorator, ServiceIdentifier } from 'vs/platform/instantiation/common/instantiation';
|
||||
import { IChannel, IServerChannel } from 'vs/base/parts/ipc/node/ipc';
|
||||
import { Client } from 'vs/base/parts/ipc/electron-browser/ipc.electron-browser';
|
||||
import { Disposable } from 'vs/base/common/lifecycle';
|
||||
|
||||
export const IMainProcessService = createDecorator<IMainProcessService>('mainProcessService');
|
||||
|
||||
export interface IMainProcessService {
|
||||
|
||||
_serviceBrand: ServiceIdentifier<any>;
|
||||
|
||||
getChannel(channelName: string): IChannel;
|
||||
|
||||
registerChannel(channelName: string, channel: IServerChannel<string>): void;
|
||||
}
|
||||
|
||||
export class MainProcessService extends Disposable implements IMainProcessService {
|
||||
|
||||
_serviceBrand: ServiceIdentifier<any>;
|
||||
|
||||
private mainProcessConnection: Client;
|
||||
|
||||
constructor(
|
||||
windowId: number
|
||||
) {
|
||||
super();
|
||||
|
||||
this.mainProcessConnection = this._register(new Client(`window:${windowId}`));
|
||||
}
|
||||
|
||||
getChannel(channelName: string): IChannel {
|
||||
return this.mainProcessConnection.getChannel(channelName);
|
||||
}
|
||||
|
||||
registerChannel(channelName: string, channel: IServerChannel<string>): void {
|
||||
this.mainProcessConnection.registerChannel(channelName, channel);
|
||||
}
|
||||
}
|
||||
+1
-1
@@ -32,7 +32,7 @@ export class SharedProcessService implements ISharedProcessService {
|
||||
@IEnvironmentService environmentService: IEnvironmentService
|
||||
) {
|
||||
this.withSharedProcessConnection = windowsService.whenSharedProcessReady()
|
||||
.then(() => connect(environmentService.sharedIPCHandle, `window:${windowService.getConfiguration().windowId}`));
|
||||
.then(() => connect(environmentService.sharedIPCHandle, `window:${windowService.getCurrentWindowId()}`));
|
||||
}
|
||||
|
||||
getChannel(channelName: string): IChannel {
|
||||
@@ -0,0 +1,28 @@
|
||||
/*---------------------------------------------------------------------------------------------
|
||||
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||
* Licensed under the MIT License. See License.txt in the project root for license information.
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
|
||||
import { IChannel } from 'vs/base/parts/ipc/node/ipc';
|
||||
import { IIssueService, IssueReporterData, ProcessExplorerData } from 'vs/platform/issue/common/issue';
|
||||
import { IMainProcessService } from 'vs/platform/ipc/electron-browser/mainProcessService';
|
||||
import { ServiceIdentifier } from 'vs/platform/instantiation/common/instantiation';
|
||||
|
||||
export class IssueService implements IIssueService {
|
||||
|
||||
_serviceBrand: ServiceIdentifier<any>;
|
||||
|
||||
private channel: IChannel;
|
||||
|
||||
constructor(@IMainProcessService mainProcessService: IMainProcessService) {
|
||||
this.channel = mainProcessService.getChannel('issue');
|
||||
}
|
||||
|
||||
openReporter(data: IssueReporterData): Promise<void> {
|
||||
return this.channel.call('openIssueReporter', data);
|
||||
}
|
||||
|
||||
openProcessExplorer(data: ProcessExplorerData): Promise<void> {
|
||||
return this.channel.call('openProcessExplorer', data);
|
||||
}
|
||||
}
|
||||
@@ -3,9 +3,9 @@
|
||||
* Licensed under the MIT License. See License.txt in the project root for license information.
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
|
||||
import { IChannel, IServerChannel } from 'vs/base/parts/ipc/node/ipc';
|
||||
import { IIssueService, IssueReporterData, ProcessExplorerData } from '../common/issue';
|
||||
import { IServerChannel } from 'vs/base/parts/ipc/node/ipc';
|
||||
import { Event } from 'vs/base/common/event';
|
||||
import { IIssueService } from 'vs/platform/issue/common/issue';
|
||||
|
||||
export class IssueChannel implements IServerChannel {
|
||||
|
||||
@@ -25,19 +25,4 @@ export class IssueChannel implements IServerChannel {
|
||||
|
||||
throw new Error(`Call not found: ${command}`);
|
||||
}
|
||||
}
|
||||
|
||||
export class IssueChannelClient implements IIssueService {
|
||||
|
||||
_serviceBrand: any;
|
||||
|
||||
constructor(private channel: IChannel) { }
|
||||
|
||||
openReporter(data: IssueReporterData): Promise<void> {
|
||||
return this.channel.call('openIssueReporter', data);
|
||||
}
|
||||
|
||||
openProcessExplorer(data: ProcessExplorerData): Promise<void> {
|
||||
return this.channel.call('openProcessExplorer', data);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,74 @@
|
||||
/*---------------------------------------------------------------------------------------------
|
||||
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||
* Licensed under the MIT License. See License.txt in the project root for license information.
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
|
||||
import { Event, Emitter } from 'vs/base/common/event';
|
||||
import { Barrier } from 'vs/base/common/async';
|
||||
import { Disposable } from 'vs/base/common/lifecycle';
|
||||
import { ILifecycleService, BeforeShutdownEvent, WillShutdownEvent, StartupKind, LifecyclePhase, LifecyclePhaseToString } from 'vs/platform/lifecycle/common/lifecycle';
|
||||
import { ILogService } from 'vs/platform/log/common/log';
|
||||
import { mark } from 'vs/base/common/performance';
|
||||
|
||||
export abstract class AbstractLifecycleService extends Disposable implements ILifecycleService {
|
||||
|
||||
_serviceBrand: any;
|
||||
|
||||
protected readonly _onBeforeShutdown = this._register(new Emitter<BeforeShutdownEvent>());
|
||||
get onBeforeShutdown(): Event<BeforeShutdownEvent> { return this._onBeforeShutdown.event; }
|
||||
|
||||
protected readonly _onWillShutdown = this._register(new Emitter<WillShutdownEvent>());
|
||||
get onWillShutdown(): Event<WillShutdownEvent> { return this._onWillShutdown.event; }
|
||||
|
||||
protected readonly _onShutdown = this._register(new Emitter<void>());
|
||||
get onShutdown(): Event<void> { return this._onShutdown.event; }
|
||||
|
||||
protected _startupKind: StartupKind;
|
||||
get startupKind(): StartupKind { return this._startupKind; }
|
||||
|
||||
private _phase: LifecyclePhase = LifecyclePhase.Starting;
|
||||
get phase(): LifecyclePhase { return this._phase; }
|
||||
|
||||
private phaseWhen = new Map<LifecyclePhase, Barrier>();
|
||||
|
||||
constructor(
|
||||
@ILogService protected readonly logService: ILogService
|
||||
) {
|
||||
super();
|
||||
}
|
||||
|
||||
set phase(value: LifecyclePhase) {
|
||||
if (value < this.phase) {
|
||||
throw new Error('Lifecycle cannot go backwards');
|
||||
}
|
||||
|
||||
if (this._phase === value) {
|
||||
return;
|
||||
}
|
||||
|
||||
this.logService.trace(`lifecycle: phase changed (value: ${value})`);
|
||||
|
||||
this._phase = value;
|
||||
mark(`LifecyclePhase/${LifecyclePhaseToString(value)}`);
|
||||
|
||||
const barrier = this.phaseWhen.get(this._phase);
|
||||
if (barrier) {
|
||||
barrier.open();
|
||||
this.phaseWhen.delete(this._phase);
|
||||
}
|
||||
}
|
||||
|
||||
when(phase: LifecyclePhase): Promise<any> {
|
||||
if (phase <= this._phase) {
|
||||
return Promise.resolve();
|
||||
}
|
||||
|
||||
let barrier = this.phaseWhen.get(phase);
|
||||
if (!barrier) {
|
||||
barrier = new Barrier();
|
||||
this.phaseWhen.set(phase, barrier);
|
||||
}
|
||||
|
||||
return barrier.wait();
|
||||
}
|
||||
}
|
||||
@@ -4,50 +4,30 @@
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
|
||||
import { toErrorMessage } from 'vs/base/common/errorMessage';
|
||||
import { ILifecycleService, BeforeShutdownEvent, ShutdownReason, StartupKind, LifecyclePhase, handleVetos, LifecyclePhaseToString, WillShutdownEvent } from 'vs/platform/lifecycle/common/lifecycle';
|
||||
import { ShutdownReason, StartupKind, handleVetos } from 'vs/platform/lifecycle/common/lifecycle';
|
||||
import { IStorageService, StorageScope } from 'vs/platform/storage/common/storage';
|
||||
import { ipcRenderer as ipc } from 'electron';
|
||||
import { Event, Emitter } from 'vs/base/common/event';
|
||||
import { IWindowService } from 'vs/platform/windows/common/windows';
|
||||
import { mark } from 'vs/base/common/performance';
|
||||
import { Barrier } from 'vs/base/common/async';
|
||||
import { ILogService } from 'vs/platform/log/common/log';
|
||||
import { INotificationService } from 'vs/platform/notification/common/notification';
|
||||
import { Disposable } from 'vs/base/common/lifecycle';
|
||||
import { onUnexpectedError } from 'vs/base/common/errors';
|
||||
import { AbstractLifecycleService } from 'vs/platform/lifecycle/common/lifecycleService';
|
||||
|
||||
export class LifecycleService extends Disposable implements ILifecycleService {
|
||||
export class LifecycleService extends AbstractLifecycleService {
|
||||
|
||||
private static readonly LAST_SHUTDOWN_REASON_KEY = 'lifecyle.lastShutdownReason';
|
||||
|
||||
_serviceBrand: any;
|
||||
|
||||
private readonly _onBeforeShutdown = this._register(new Emitter<BeforeShutdownEvent>());
|
||||
get onBeforeShutdown(): Event<BeforeShutdownEvent> { return this._onBeforeShutdown.event; }
|
||||
|
||||
private readonly _onWillShutdown = this._register(new Emitter<WillShutdownEvent>());
|
||||
get onWillShutdown(): Event<WillShutdownEvent> { return this._onWillShutdown.event; }
|
||||
|
||||
private readonly _onShutdown = this._register(new Emitter<void>());
|
||||
get onShutdown(): Event<void> { return this._onShutdown.event; }
|
||||
|
||||
private readonly _startupKind: StartupKind;
|
||||
get startupKind(): StartupKind { return this._startupKind; }
|
||||
|
||||
private _phase: LifecyclePhase = LifecyclePhase.Starting;
|
||||
get phase(): LifecyclePhase { return this._phase; }
|
||||
|
||||
private phaseWhen = new Map<LifecyclePhase, Barrier>();
|
||||
|
||||
private shutdownReason: ShutdownReason;
|
||||
|
||||
constructor(
|
||||
@INotificationService private readonly notificationService: INotificationService,
|
||||
@IWindowService private readonly windowService: IWindowService,
|
||||
@IStorageService private readonly storageService: IStorageService,
|
||||
@ILogService private readonly logService: ILogService
|
||||
@IStorageService readonly storageService: IStorageService,
|
||||
@ILogService readonly logService: ILogService
|
||||
) {
|
||||
super();
|
||||
super(logService);
|
||||
|
||||
this._startupKind = this.resolveStartupKind();
|
||||
|
||||
@@ -148,39 +128,4 @@ export class LifecycleService extends Disposable implements ILifecycleService {
|
||||
onUnexpectedError(err);
|
||||
});
|
||||
}
|
||||
|
||||
set phase(value: LifecyclePhase) {
|
||||
if (value < this.phase) {
|
||||
throw new Error('Lifecycle cannot go backwards');
|
||||
}
|
||||
|
||||
if (this._phase === value) {
|
||||
return;
|
||||
}
|
||||
|
||||
this.logService.trace(`lifecycle: phase changed (value: ${value})`);
|
||||
|
||||
this._phase = value;
|
||||
mark(`LifecyclePhase/${LifecyclePhaseToString(value)}`);
|
||||
|
||||
const barrier = this.phaseWhen.get(this._phase);
|
||||
if (barrier) {
|
||||
barrier.open();
|
||||
this.phaseWhen.delete(this._phase);
|
||||
}
|
||||
}
|
||||
|
||||
when(phase: LifecyclePhase): Promise<any> {
|
||||
if (phase <= this._phase) {
|
||||
return Promise.resolve();
|
||||
}
|
||||
|
||||
let barrier = this.phaseWhen.get(phase);
|
||||
if (!barrier) {
|
||||
barrier = new Barrier();
|
||||
this.phaseWhen.set(phase, barrier);
|
||||
}
|
||||
|
||||
return barrier.wait();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,27 @@
|
||||
/*---------------------------------------------------------------------------------------------
|
||||
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||
* Licensed under the MIT License. See License.txt in the project root for license information.
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
|
||||
import { IChannel } from 'vs/base/parts/ipc/node/ipc';
|
||||
import { Event } from 'vs/base/common/event';
|
||||
import { ILocalizationsService, LanguageType } from 'vs/platform/localizations/common/localizations';
|
||||
import { ISharedProcessService } from 'vs/platform/ipc/electron-browser/sharedProcessService';
|
||||
import { ServiceIdentifier } from 'vs/platform/instantiation/common/instantiation';
|
||||
|
||||
export class LocalizationsService implements ILocalizationsService {
|
||||
|
||||
_serviceBrand: ServiceIdentifier<any>;
|
||||
|
||||
private channel: IChannel;
|
||||
|
||||
constructor(@ISharedProcessService sharedProcessService: ISharedProcessService) {
|
||||
this.channel = sharedProcessService.getChannel('localizations');
|
||||
}
|
||||
|
||||
get onDidLanguagesChange(): Event<void> { return this.channel.listen('onDidLanguagesChange'); }
|
||||
|
||||
getLanguageIds(type?: LanguageType): Promise<string[]> {
|
||||
return this.channel.call('getLanguageIds', type);
|
||||
}
|
||||
}
|
||||
@@ -3,10 +3,9 @@
|
||||
* Licensed under the MIT License. See License.txt in the project root for license information.
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
|
||||
import { IChannel, IServerChannel } from 'vs/base/parts/ipc/node/ipc';
|
||||
import { IServerChannel } from 'vs/base/parts/ipc/node/ipc';
|
||||
import { Event } from 'vs/base/common/event';
|
||||
import { ILocalizationsService, LanguageType } from 'vs/platform/localizations/common/localizations';
|
||||
import { ISharedProcessService } from 'vs/platform/sharedProcess/node/sharedProcessService';
|
||||
import { ILocalizationsService } from 'vs/platform/localizations/common/localizations';
|
||||
|
||||
export class LocalizationsChannel implements IServerChannel {
|
||||
|
||||
@@ -32,20 +31,3 @@ export class LocalizationsChannel implements IServerChannel {
|
||||
throw new Error(`Call not found: ${command}`);
|
||||
}
|
||||
}
|
||||
|
||||
export class LocalizationsChannelClient implements ILocalizationsService {
|
||||
|
||||
_serviceBrand: any;
|
||||
|
||||
private channel: IChannel;
|
||||
|
||||
constructor(@ISharedProcessService sharedProcessService: ISharedProcessService) {
|
||||
this.channel = sharedProcessService.getChannel('localizations');
|
||||
}
|
||||
|
||||
get onDidLanguagesChange(): Event<void> { return this.channel.listen('onDidLanguagesChange'); }
|
||||
|
||||
getLanguageIds(type?: LanguageType): Promise<string[]> {
|
||||
return this.channel.call('getLanguageIds', type);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,24 @@
|
||||
/*---------------------------------------------------------------------------------------------
|
||||
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||
* Licensed under the MIT License. See License.txt in the project root for license information.
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
|
||||
import { IChannel } from 'vs/base/parts/ipc/node/ipc';
|
||||
import { IMenubarService, IMenubarData } from 'vs/platform/menubar/common/menubar';
|
||||
import { IMainProcessService } from 'vs/platform/ipc/electron-browser/mainProcessService';
|
||||
import { ServiceIdentifier } from 'vs/platform/instantiation/common/instantiation';
|
||||
|
||||
export class MenubarService implements IMenubarService {
|
||||
|
||||
_serviceBrand: ServiceIdentifier<any>;
|
||||
|
||||
private channel: IChannel;
|
||||
|
||||
constructor(@IMainProcessService mainProcessService: IMainProcessService) {
|
||||
this.channel = mainProcessService.getChannel('menubar');
|
||||
}
|
||||
|
||||
updateMenubar(windowId: number, menuData: IMenubarData): Promise<void> {
|
||||
return this.channel.call('updateMenubar', [windowId, menuData]);
|
||||
}
|
||||
}
|
||||
@@ -2,8 +2,9 @@
|
||||
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||
* Licensed under the MIT License. See License.txt in the project root for license information.
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
import { IChannel, IServerChannel } from 'vs/base/parts/ipc/node/ipc';
|
||||
import { IMenubarService, IMenubarData } from 'vs/platform/menubar/common/menubar';
|
||||
|
||||
import { IServerChannel } from 'vs/base/parts/ipc/node/ipc';
|
||||
import { IMenubarService } from 'vs/platform/menubar/common/menubar';
|
||||
import { Event } from 'vs/base/common/event';
|
||||
|
||||
export class MenubarChannel implements IServerChannel {
|
||||
@@ -21,15 +22,4 @@ export class MenubarChannel implements IServerChannel {
|
||||
|
||||
throw new Error(`Call not found: ${command}`);
|
||||
}
|
||||
}
|
||||
|
||||
export class MenubarChannelClient implements IMenubarService {
|
||||
|
||||
_serviceBrand: any;
|
||||
|
||||
constructor(private channel: IChannel) { }
|
||||
|
||||
updateMenubar(windowId: number, menuData: IMenubarData): Promise<void> {
|
||||
return this.channel.call('updateMenubar', [windowId, menuData]);
|
||||
}
|
||||
}
|
||||
}
|
||||
+1
-1
@@ -9,7 +9,7 @@ import { IConfigurationService } from 'vs/platform/configuration/common/configur
|
||||
import { Disposable } from 'vs/base/common/lifecycle';
|
||||
import { IEnvironmentService } from 'vs/platform/environment/common/environment';
|
||||
import { IProductService } from 'vs/platform/product/common/product';
|
||||
import { ISharedProcessService } from 'vs/platform/sharedProcess/node/sharedProcessService';
|
||||
import { ISharedProcessService } from 'vs/platform/ipc/electron-browser/sharedProcessService';
|
||||
import { TelemetryAppenderClient } from 'vs/platform/telemetry/node/telemetryIpc';
|
||||
import { ILogService } from 'vs/platform/log/common/log';
|
||||
import { IStorageService } from 'vs/platform/storage/common/storage';
|
||||
@@ -0,0 +1,59 @@
|
||||
/*---------------------------------------------------------------------------------------------
|
||||
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||
* Licensed under the MIT License. See License.txt in the project root for license information.
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
|
||||
import { IChannel } from 'vs/base/parts/ipc/node/ipc';
|
||||
import { Event, Emitter } from 'vs/base/common/event';
|
||||
import { IUpdateService, State } from 'vs/platform/update/common/update';
|
||||
import { IMainProcessService } from 'vs/platform/ipc/electron-browser/mainProcessService';
|
||||
import { ServiceIdentifier } from 'vs/platform/instantiation/common/instantiation';
|
||||
|
||||
export class UpdateService implements IUpdateService {
|
||||
|
||||
_serviceBrand: ServiceIdentifier<any>;
|
||||
|
||||
private _onStateChange = new Emitter<State>();
|
||||
get onStateChange(): Event<State> { return this._onStateChange.event; }
|
||||
|
||||
private _state: State = State.Uninitialized;
|
||||
get state(): State { return this._state; }
|
||||
|
||||
private channel: IChannel;
|
||||
|
||||
constructor(@IMainProcessService mainProcessService: IMainProcessService) {
|
||||
this.channel = mainProcessService.getChannel('update');
|
||||
|
||||
// always set this._state as the state changes
|
||||
this.onStateChange(state => this._state = state);
|
||||
|
||||
this.channel.call<State>('_getInitialState').then(state => {
|
||||
// fire initial state
|
||||
this._onStateChange.fire(state);
|
||||
|
||||
// fire subsequent states as they come in from remote
|
||||
|
||||
this.channel.listen<State>('onStateChange')(state => this._onStateChange.fire(state));
|
||||
});
|
||||
}
|
||||
|
||||
checkForUpdates(context: any): Promise<void> {
|
||||
return this.channel.call('checkForUpdates', context);
|
||||
}
|
||||
|
||||
downloadUpdate(): Promise<void> {
|
||||
return this.channel.call('downloadUpdate');
|
||||
}
|
||||
|
||||
applyUpdate(): Promise<void> {
|
||||
return this.channel.call('applyUpdate');
|
||||
}
|
||||
|
||||
quitAndInstall(): Promise<void> {
|
||||
return this.channel.call('quitAndInstall');
|
||||
}
|
||||
|
||||
isLatestVersion(): Promise<boolean> {
|
||||
return this.channel.call('isLatestVersion');
|
||||
}
|
||||
}
|
||||
@@ -3,9 +3,9 @@
|
||||
* Licensed under the MIT License. See License.txt in the project root for license information.
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
|
||||
import { IChannel, IServerChannel } from 'vs/base/parts/ipc/node/ipc';
|
||||
import { Event, Emitter } from 'vs/base/common/event';
|
||||
import { IUpdateService, State } from 'vs/platform/update/common/update';
|
||||
import { IServerChannel } from 'vs/base/parts/ipc/node/ipc';
|
||||
import { Event } from 'vs/base/common/event';
|
||||
import { IUpdateService } from 'vs/platform/update/common/update';
|
||||
|
||||
export class UpdateChannel implements IServerChannel {
|
||||
|
||||
@@ -31,49 +31,4 @@ export class UpdateChannel implements IServerChannel {
|
||||
|
||||
throw new Error(`Call not found: ${command}`);
|
||||
}
|
||||
}
|
||||
|
||||
export class UpdateChannelClient implements IUpdateService {
|
||||
|
||||
_serviceBrand: any;
|
||||
|
||||
private _onStateChange = new Emitter<State>();
|
||||
get onStateChange(): Event<State> { return this._onStateChange.event; }
|
||||
|
||||
private _state: State = State.Uninitialized;
|
||||
get state(): State { return this._state; }
|
||||
|
||||
constructor(private channel: IChannel) {
|
||||
// always set this._state as the state changes
|
||||
this.onStateChange(state => this._state = state);
|
||||
|
||||
channel.call<State>('_getInitialState').then(state => {
|
||||
// fire initial state
|
||||
this._onStateChange.fire(state);
|
||||
|
||||
// fire subsequent states as they come in from remote
|
||||
|
||||
this.channel.listen<State>('onStateChange')(state => this._onStateChange.fire(state));
|
||||
});
|
||||
}
|
||||
|
||||
checkForUpdates(context: any): Promise<void> {
|
||||
return this.channel.call('checkForUpdates', context);
|
||||
}
|
||||
|
||||
downloadUpdate(): Promise<void> {
|
||||
return this.channel.call('downloadUpdate');
|
||||
}
|
||||
|
||||
applyUpdate(): Promise<void> {
|
||||
return this.channel.call('applyUpdate');
|
||||
}
|
||||
|
||||
quitAndInstall(): Promise<void> {
|
||||
return this.channel.call('quitAndInstall');
|
||||
}
|
||||
|
||||
isLatestVersion(): Promise<boolean> {
|
||||
return this.channel.call('isLatestVersion');
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -8,10 +8,11 @@ import { URI } from 'vs/base/common/uri';
|
||||
import { IDisposable, toDisposable } from 'vs/base/common/lifecycle';
|
||||
import { first } from 'vs/base/common/async';
|
||||
import { values } from 'vs/base/common/map';
|
||||
import { ServiceIdentifier } from 'vs/platform/instantiation/common/instantiation';
|
||||
|
||||
export class URLService implements IURLService {
|
||||
|
||||
_serviceBrand: any;
|
||||
_serviceBrand: ServiceIdentifier<any>;
|
||||
|
||||
private handlers = new Set<IURLHandler>();
|
||||
|
||||
@@ -25,18 +26,3 @@ export class URLService implements IURLService {
|
||||
return toDisposable(() => this.handlers.delete(handler));
|
||||
}
|
||||
}
|
||||
|
||||
export class RelayURLService extends URLService implements IURLHandler {
|
||||
|
||||
constructor(private urlService: IURLService) {
|
||||
super();
|
||||
}
|
||||
|
||||
open(uri: URI): Promise<boolean> {
|
||||
return this.urlService.open(uri);
|
||||
}
|
||||
|
||||
handleURL(uri: URI): Promise<boolean> {
|
||||
return super.open(uri);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,30 @@
|
||||
/*---------------------------------------------------------------------------------------------
|
||||
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||
* Licensed under the MIT License. See License.txt in the project root for license information.
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
|
||||
import { IURLService, IURLHandler } from 'vs/platform/url/common/url';
|
||||
import { URI } from 'vs/base/common/uri';
|
||||
import { IMainProcessService } from 'vs/platform/ipc/electron-browser/mainProcessService';
|
||||
import { URLServiceChannelClient, URLHandlerChannel } from 'vs/platform/url/node/urlIpc';
|
||||
import { URLService } from 'vs/platform/url/common/urlService';
|
||||
|
||||
export class RelayURLService extends URLService implements IURLHandler {
|
||||
private urlService: IURLService;
|
||||
|
||||
constructor(@IMainProcessService mainProcessService: IMainProcessService) {
|
||||
super();
|
||||
|
||||
this.urlService = new URLServiceChannelClient(mainProcessService.getChannel('url'));
|
||||
|
||||
mainProcessService.registerChannel('urlHandler', new URLHandlerChannel(this));
|
||||
}
|
||||
|
||||
open(uri: URI): Promise<boolean> {
|
||||
return this.urlService.open(uri);
|
||||
}
|
||||
|
||||
handleURL(uri: URI): Promise<boolean> {
|
||||
return super.open(uri);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,250 @@
|
||||
/*---------------------------------------------------------------------------------------------
|
||||
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||
* Licensed under the MIT License. See License.txt in the project root for license information.
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
|
||||
import { Event } from 'vs/base/common/event';
|
||||
import { IChannel } from 'vs/base/parts/ipc/node/ipc';
|
||||
import { IWindowsService, INativeOpenDialogOptions, IEnterWorkspaceResult, CrashReporterStartOptions, IMessageBoxResult, MessageBoxOptions, SaveDialogOptions, OpenDialogOptions, IDevToolsOptions, INewWindowOptions, IURIToOpen } from 'vs/platform/windows/common/windows';
|
||||
import { IWorkspaceIdentifier, ISingleFolderWorkspaceIdentifier, reviveWorkspaceIdentifier } from 'vs/platform/workspaces/common/workspaces';
|
||||
import { IRecentlyOpened, IRecent, isRecentWorkspace } from 'vs/platform/history/common/history';
|
||||
import { ISerializableCommandAction } from 'vs/platform/actions/common/actions';
|
||||
import { URI } from 'vs/base/common/uri';
|
||||
import { ParsedArgs } from 'vs/platform/environment/common/environment';
|
||||
import { IMainProcessService } from 'vs/platform/ipc/electron-browser/mainProcessService';
|
||||
|
||||
export class WindowsService implements IWindowsService {
|
||||
|
||||
_serviceBrand: any;
|
||||
|
||||
private channel: IChannel;
|
||||
|
||||
constructor(@IMainProcessService mainProcessService: IMainProcessService) {
|
||||
this.channel = mainProcessService.getChannel('windows');
|
||||
}
|
||||
|
||||
get onWindowOpen(): Event<number> { return this.channel.listen('onWindowOpen'); }
|
||||
get onWindowFocus(): Event<number> { return this.channel.listen('onWindowFocus'); }
|
||||
get onWindowBlur(): Event<number> { return this.channel.listen('onWindowBlur'); }
|
||||
get onWindowMaximize(): Event<number> { return this.channel.listen('onWindowMaximize'); }
|
||||
get onWindowUnmaximize(): Event<number> { return this.channel.listen('onWindowUnmaximize'); }
|
||||
get onRecentlyOpenedChange(): Event<void> { return this.channel.listen('onRecentlyOpenedChange'); }
|
||||
|
||||
pickFileFolderAndOpen(options: INativeOpenDialogOptions): Promise<void> {
|
||||
return this.channel.call('pickFileFolderAndOpen', options);
|
||||
}
|
||||
|
||||
pickFileAndOpen(options: INativeOpenDialogOptions): Promise<void> {
|
||||
return this.channel.call('pickFileAndOpen', options);
|
||||
}
|
||||
|
||||
pickFolderAndOpen(options: INativeOpenDialogOptions): Promise<void> {
|
||||
return this.channel.call('pickFolderAndOpen', options);
|
||||
}
|
||||
|
||||
pickWorkspaceAndOpen(options: INativeOpenDialogOptions): Promise<void> {
|
||||
return this.channel.call('pickWorkspaceAndOpen', options);
|
||||
}
|
||||
|
||||
showMessageBox(windowId: number, options: MessageBoxOptions): Promise<IMessageBoxResult> {
|
||||
return this.channel.call('showMessageBox', [windowId, options]);
|
||||
}
|
||||
|
||||
showSaveDialog(windowId: number, options: SaveDialogOptions): Promise<string> {
|
||||
return this.channel.call('showSaveDialog', [windowId, options]);
|
||||
}
|
||||
|
||||
showOpenDialog(windowId: number, options: OpenDialogOptions): Promise<string[]> {
|
||||
return this.channel.call('showOpenDialog', [windowId, options]);
|
||||
}
|
||||
|
||||
reloadWindow(windowId: number, args?: ParsedArgs): Promise<void> {
|
||||
return this.channel.call('reloadWindow', [windowId, args]);
|
||||
}
|
||||
|
||||
openDevTools(windowId: number, options?: IDevToolsOptions): Promise<void> {
|
||||
return this.channel.call('openDevTools', [windowId, options]);
|
||||
}
|
||||
|
||||
toggleDevTools(windowId: number): Promise<void> {
|
||||
return this.channel.call('toggleDevTools', windowId);
|
||||
}
|
||||
|
||||
closeWorkspace(windowId: number): Promise<void> {
|
||||
return this.channel.call('closeWorkspace', windowId);
|
||||
}
|
||||
|
||||
enterWorkspace(windowId: number, path: URI): Promise<IEnterWorkspaceResult> {
|
||||
return this.channel.call('enterWorkspace', [windowId, path]).then((result: IEnterWorkspaceResult) => {
|
||||
result.workspace = reviveWorkspaceIdentifier(result.workspace);
|
||||
return result;
|
||||
});
|
||||
}
|
||||
|
||||
toggleFullScreen(windowId: number): Promise<void> {
|
||||
return this.channel.call('toggleFullScreen', windowId);
|
||||
}
|
||||
|
||||
setRepresentedFilename(windowId: number, fileName: string): Promise<void> {
|
||||
return this.channel.call('setRepresentedFilename', [windowId, fileName]);
|
||||
}
|
||||
|
||||
addRecentlyOpened(recent: IRecent[]): Promise<void> {
|
||||
return this.channel.call('addRecentlyOpened', recent);
|
||||
}
|
||||
|
||||
removeFromRecentlyOpened(paths: Array<URI>): Promise<void> {
|
||||
return this.channel.call('removeFromRecentlyOpened', paths);
|
||||
}
|
||||
|
||||
clearRecentlyOpened(): Promise<void> {
|
||||
return this.channel.call('clearRecentlyOpened');
|
||||
}
|
||||
|
||||
getRecentlyOpened(windowId: number): Promise<IRecentlyOpened> {
|
||||
return this.channel.call('getRecentlyOpened', windowId)
|
||||
.then((recentlyOpened: IRecentlyOpened) => {
|
||||
recentlyOpened.workspaces.forEach(recent => isRecentWorkspace(recent) ? recent.workspace = reviveWorkspaceIdentifier(recent.workspace) : recent.folderUri = URI.revive(recent.folderUri));
|
||||
recentlyOpened.files.forEach(recent => recent.fileUri = URI.revive(recent.fileUri));
|
||||
return recentlyOpened;
|
||||
});
|
||||
}
|
||||
|
||||
newWindowTab(): Promise<void> {
|
||||
return this.channel.call('newWindowTab');
|
||||
}
|
||||
|
||||
showPreviousWindowTab(): Promise<void> {
|
||||
return this.channel.call('showPreviousWindowTab');
|
||||
}
|
||||
|
||||
showNextWindowTab(): Promise<void> {
|
||||
return this.channel.call('showNextWindowTab');
|
||||
}
|
||||
|
||||
moveWindowTabToNewWindow(): Promise<void> {
|
||||
return this.channel.call('moveWindowTabToNewWindow');
|
||||
}
|
||||
|
||||
mergeAllWindowTabs(): Promise<void> {
|
||||
return this.channel.call('mergeAllWindowTabs');
|
||||
}
|
||||
|
||||
toggleWindowTabsBar(): Promise<void> {
|
||||
return this.channel.call('toggleWindowTabsBar');
|
||||
}
|
||||
|
||||
focusWindow(windowId: number): Promise<void> {
|
||||
return this.channel.call('focusWindow', windowId);
|
||||
}
|
||||
|
||||
closeWindow(windowId: number): Promise<void> {
|
||||
return this.channel.call('closeWindow', windowId);
|
||||
}
|
||||
|
||||
isFocused(windowId: number): Promise<boolean> {
|
||||
return this.channel.call('isFocused', windowId);
|
||||
}
|
||||
|
||||
isMaximized(windowId: number): Promise<boolean> {
|
||||
return this.channel.call('isMaximized', windowId);
|
||||
}
|
||||
|
||||
maximizeWindow(windowId: number): Promise<void> {
|
||||
return this.channel.call('maximizeWindow', windowId);
|
||||
}
|
||||
|
||||
unmaximizeWindow(windowId: number): Promise<void> {
|
||||
return this.channel.call('unmaximizeWindow', windowId);
|
||||
}
|
||||
|
||||
minimizeWindow(windowId: number): Promise<void> {
|
||||
return this.channel.call('minimizeWindow', windowId);
|
||||
}
|
||||
|
||||
onWindowTitleDoubleClick(windowId: number): Promise<void> {
|
||||
return this.channel.call('onWindowTitleDoubleClick', windowId);
|
||||
}
|
||||
|
||||
setDocumentEdited(windowId: number, flag: boolean): Promise<void> {
|
||||
return this.channel.call('setDocumentEdited', [windowId, flag]);
|
||||
}
|
||||
|
||||
quit(): Promise<void> {
|
||||
return this.channel.call('quit');
|
||||
}
|
||||
|
||||
relaunch(options: { addArgs?: string[], removeArgs?: string[] }): Promise<void> {
|
||||
return this.channel.call('relaunch', [options]);
|
||||
}
|
||||
|
||||
whenSharedProcessReady(): Promise<void> {
|
||||
return this.channel.call('whenSharedProcessReady');
|
||||
}
|
||||
|
||||
toggleSharedProcess(): Promise<void> {
|
||||
return this.channel.call('toggleSharedProcess');
|
||||
}
|
||||
|
||||
openWindow(windowId: number, uris: IURIToOpen[], options?: { forceNewWindow?: boolean, forceReuseWindow?: boolean, forceOpenWorkspaceAsFile?: boolean, args?: ParsedArgs }): Promise<void> {
|
||||
return this.channel.call('openWindow', [windowId, uris, options]);
|
||||
}
|
||||
|
||||
openNewWindow(options?: INewWindowOptions): Promise<void> {
|
||||
return this.channel.call('openNewWindow', options);
|
||||
}
|
||||
|
||||
showWindow(windowId: number): Promise<void> {
|
||||
return this.channel.call('showWindow', windowId);
|
||||
}
|
||||
|
||||
getWindows(): Promise<{ id: number; workspace?: IWorkspaceIdentifier; folderUri?: ISingleFolderWorkspaceIdentifier; title: string; filename?: string; }[]> {
|
||||
return this.channel.call<{ id: number; workspace?: IWorkspaceIdentifier; folderUri?: ISingleFolderWorkspaceIdentifier; title: string; filename?: string; }[]>('getWindows').then(result => {
|
||||
for (const win of result) {
|
||||
if (win.folderUri) {
|
||||
win.folderUri = URI.revive(win.folderUri);
|
||||
}
|
||||
if (win.workspace) {
|
||||
win.workspace = reviveWorkspaceIdentifier(win.workspace);
|
||||
}
|
||||
}
|
||||
return result;
|
||||
});
|
||||
}
|
||||
|
||||
getWindowCount(): Promise<number> {
|
||||
return this.channel.call('getWindowCount');
|
||||
}
|
||||
|
||||
log(severity: string, ...messages: string[]): Promise<void> {
|
||||
return this.channel.call('log', [severity, messages]);
|
||||
}
|
||||
|
||||
showItemInFolder(path: URI): Promise<void> {
|
||||
return this.channel.call('showItemInFolder', path);
|
||||
}
|
||||
|
||||
getActiveWindowId(): Promise<number | undefined> {
|
||||
return this.channel.call('getActiveWindowId');
|
||||
}
|
||||
|
||||
openExternal(url: string): Promise<boolean> {
|
||||
return this.channel.call('openExternal', url);
|
||||
}
|
||||
|
||||
startCrashReporter(config: CrashReporterStartOptions): Promise<void> {
|
||||
return this.channel.call('startCrashReporter', config);
|
||||
}
|
||||
|
||||
updateTouchBar(windowId: number, items: ISerializableCommandAction[][]): Promise<void> {
|
||||
return this.channel.call('updateTouchBar', [windowId, items]);
|
||||
}
|
||||
|
||||
openAboutDialog(): Promise<void> {
|
||||
return this.channel.call('openAboutDialog');
|
||||
}
|
||||
|
||||
resolveProxy(windowId: number, url: string): Promise<string | undefined> {
|
||||
return Promise.resolve(this.channel.call('resolveProxy', [windowId, url]));
|
||||
}
|
||||
}
|
||||
@@ -4,13 +4,11 @@
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
|
||||
import { Event } from 'vs/base/common/event';
|
||||
import { IChannel, IServerChannel } from 'vs/base/parts/ipc/node/ipc';
|
||||
import { IWindowsService, INativeOpenDialogOptions, IEnterWorkspaceResult, CrashReporterStartOptions, IMessageBoxResult, MessageBoxOptions, SaveDialogOptions, OpenDialogOptions, IDevToolsOptions, INewWindowOptions, IURIToOpen } from 'vs/platform/windows/common/windows';
|
||||
import { IWorkspaceIdentifier, ISingleFolderWorkspaceIdentifier, reviveWorkspaceIdentifier } from 'vs/platform/workspaces/common/workspaces';
|
||||
import { IRecentlyOpened, isRecentFile, isRecentFolder, IRecent, isRecentWorkspace } from 'vs/platform/history/common/history';
|
||||
import { ISerializableCommandAction } from 'vs/platform/actions/common/actions';
|
||||
import { IServerChannel } from 'vs/base/parts/ipc/node/ipc';
|
||||
import { IWindowsService, IURIToOpen } from 'vs/platform/windows/common/windows';
|
||||
import { reviveWorkspaceIdentifier } from 'vs/platform/workspaces/common/workspaces';
|
||||
import { URI } from 'vs/base/common/uri';
|
||||
import { ParsedArgs } from 'vs/platform/environment/common/environment';
|
||||
import { IRecent, isRecentFile, isRecentFolder } from 'vs/platform/history/common/history';
|
||||
|
||||
export class WindowsChannel implements IServerChannel {
|
||||
|
||||
@@ -108,236 +106,4 @@ export class WindowsChannel implements IServerChannel {
|
||||
|
||||
throw new Error(`Call not found: ${command}`);
|
||||
}
|
||||
}
|
||||
|
||||
export class WindowsChannelClient implements IWindowsService {
|
||||
|
||||
_serviceBrand: any;
|
||||
|
||||
constructor(private channel: IChannel) { }
|
||||
|
||||
get onWindowOpen(): Event<number> { return this.channel.listen('onWindowOpen'); }
|
||||
get onWindowFocus(): Event<number> { return this.channel.listen('onWindowFocus'); }
|
||||
get onWindowBlur(): Event<number> { return this.channel.listen('onWindowBlur'); }
|
||||
get onWindowMaximize(): Event<number> { return this.channel.listen('onWindowMaximize'); }
|
||||
get onWindowUnmaximize(): Event<number> { return this.channel.listen('onWindowUnmaximize'); }
|
||||
get onRecentlyOpenedChange(): Event<void> { return this.channel.listen('onRecentlyOpenedChange'); }
|
||||
|
||||
pickFileFolderAndOpen(options: INativeOpenDialogOptions): Promise<void> {
|
||||
return this.channel.call('pickFileFolderAndOpen', options);
|
||||
}
|
||||
|
||||
pickFileAndOpen(options: INativeOpenDialogOptions): Promise<void> {
|
||||
return this.channel.call('pickFileAndOpen', options);
|
||||
}
|
||||
|
||||
pickFolderAndOpen(options: INativeOpenDialogOptions): Promise<void> {
|
||||
return this.channel.call('pickFolderAndOpen', options);
|
||||
}
|
||||
|
||||
pickWorkspaceAndOpen(options: INativeOpenDialogOptions): Promise<void> {
|
||||
return this.channel.call('pickWorkspaceAndOpen', options);
|
||||
}
|
||||
|
||||
showMessageBox(windowId: number, options: MessageBoxOptions): Promise<IMessageBoxResult> {
|
||||
return this.channel.call('showMessageBox', [windowId, options]);
|
||||
}
|
||||
|
||||
showSaveDialog(windowId: number, options: SaveDialogOptions): Promise<string> {
|
||||
return this.channel.call('showSaveDialog', [windowId, options]);
|
||||
}
|
||||
|
||||
showOpenDialog(windowId: number, options: OpenDialogOptions): Promise<string[]> {
|
||||
return this.channel.call('showOpenDialog', [windowId, options]);
|
||||
}
|
||||
|
||||
reloadWindow(windowId: number, args?: ParsedArgs): Promise<void> {
|
||||
return this.channel.call('reloadWindow', [windowId, args]);
|
||||
}
|
||||
|
||||
openDevTools(windowId: number, options?: IDevToolsOptions): Promise<void> {
|
||||
return this.channel.call('openDevTools', [windowId, options]);
|
||||
}
|
||||
|
||||
toggleDevTools(windowId: number): Promise<void> {
|
||||
return this.channel.call('toggleDevTools', windowId);
|
||||
}
|
||||
|
||||
closeWorkspace(windowId: number): Promise<void> {
|
||||
return this.channel.call('closeWorkspace', windowId);
|
||||
}
|
||||
|
||||
enterWorkspace(windowId: number, path: URI): Promise<IEnterWorkspaceResult> {
|
||||
return this.channel.call('enterWorkspace', [windowId, path]).then((result: IEnterWorkspaceResult) => {
|
||||
result.workspace = reviveWorkspaceIdentifier(result.workspace);
|
||||
return result;
|
||||
});
|
||||
}
|
||||
|
||||
toggleFullScreen(windowId: number): Promise<void> {
|
||||
return this.channel.call('toggleFullScreen', windowId);
|
||||
}
|
||||
|
||||
setRepresentedFilename(windowId: number, fileName: string): Promise<void> {
|
||||
return this.channel.call('setRepresentedFilename', [windowId, fileName]);
|
||||
}
|
||||
|
||||
addRecentlyOpened(recent: IRecent[]): Promise<void> {
|
||||
return this.channel.call('addRecentlyOpened', recent);
|
||||
}
|
||||
|
||||
removeFromRecentlyOpened(paths: Array<URI>): Promise<void> {
|
||||
return this.channel.call('removeFromRecentlyOpened', paths);
|
||||
}
|
||||
|
||||
clearRecentlyOpened(): Promise<void> {
|
||||
return this.channel.call('clearRecentlyOpened');
|
||||
}
|
||||
|
||||
getRecentlyOpened(windowId: number): Promise<IRecentlyOpened> {
|
||||
return this.channel.call('getRecentlyOpened', windowId)
|
||||
.then((recentlyOpened: IRecentlyOpened) => {
|
||||
recentlyOpened.workspaces.forEach(recent => isRecentWorkspace(recent) ? recent.workspace = reviveWorkspaceIdentifier(recent.workspace) : recent.folderUri = URI.revive(recent.folderUri));
|
||||
recentlyOpened.files.forEach(recent => recent.fileUri = URI.revive(recent.fileUri));
|
||||
return recentlyOpened;
|
||||
});
|
||||
}
|
||||
|
||||
newWindowTab(): Promise<void> {
|
||||
return this.channel.call('newWindowTab');
|
||||
}
|
||||
|
||||
showPreviousWindowTab(): Promise<void> {
|
||||
return this.channel.call('showPreviousWindowTab');
|
||||
}
|
||||
|
||||
showNextWindowTab(): Promise<void> {
|
||||
return this.channel.call('showNextWindowTab');
|
||||
}
|
||||
|
||||
moveWindowTabToNewWindow(): Promise<void> {
|
||||
return this.channel.call('moveWindowTabToNewWindow');
|
||||
}
|
||||
|
||||
mergeAllWindowTabs(): Promise<void> {
|
||||
return this.channel.call('mergeAllWindowTabs');
|
||||
}
|
||||
|
||||
toggleWindowTabsBar(): Promise<void> {
|
||||
return this.channel.call('toggleWindowTabsBar');
|
||||
}
|
||||
|
||||
focusWindow(windowId: number): Promise<void> {
|
||||
return this.channel.call('focusWindow', windowId);
|
||||
}
|
||||
|
||||
closeWindow(windowId: number): Promise<void> {
|
||||
return this.channel.call('closeWindow', windowId);
|
||||
}
|
||||
|
||||
isFocused(windowId: number): Promise<boolean> {
|
||||
return this.channel.call('isFocused', windowId);
|
||||
}
|
||||
|
||||
isMaximized(windowId: number): Promise<boolean> {
|
||||
return this.channel.call('isMaximized', windowId);
|
||||
}
|
||||
|
||||
maximizeWindow(windowId: number): Promise<void> {
|
||||
return this.channel.call('maximizeWindow', windowId);
|
||||
}
|
||||
|
||||
unmaximizeWindow(windowId: number): Promise<void> {
|
||||
return this.channel.call('unmaximizeWindow', windowId);
|
||||
}
|
||||
|
||||
minimizeWindow(windowId: number): Promise<void> {
|
||||
return this.channel.call('minimizeWindow', windowId);
|
||||
}
|
||||
|
||||
onWindowTitleDoubleClick(windowId: number): Promise<void> {
|
||||
return this.channel.call('onWindowTitleDoubleClick', windowId);
|
||||
}
|
||||
|
||||
setDocumentEdited(windowId: number, flag: boolean): Promise<void> {
|
||||
return this.channel.call('setDocumentEdited', [windowId, flag]);
|
||||
}
|
||||
|
||||
quit(): Promise<void> {
|
||||
return this.channel.call('quit');
|
||||
}
|
||||
|
||||
relaunch(options: { addArgs?: string[], removeArgs?: string[] }): Promise<void> {
|
||||
return this.channel.call('relaunch', [options]);
|
||||
}
|
||||
|
||||
whenSharedProcessReady(): Promise<void> {
|
||||
return this.channel.call('whenSharedProcessReady');
|
||||
}
|
||||
|
||||
toggleSharedProcess(): Promise<void> {
|
||||
return this.channel.call('toggleSharedProcess');
|
||||
}
|
||||
|
||||
openWindow(windowId: number, uris: IURIToOpen[], options?: { forceNewWindow?: boolean, forceReuseWindow?: boolean, forceOpenWorkspaceAsFile?: boolean, args?: ParsedArgs }): Promise<void> {
|
||||
return this.channel.call('openWindow', [windowId, uris, options]);
|
||||
}
|
||||
|
||||
openNewWindow(options?: INewWindowOptions): Promise<void> {
|
||||
return this.channel.call('openNewWindow', options);
|
||||
}
|
||||
|
||||
showWindow(windowId: number): Promise<void> {
|
||||
return this.channel.call('showWindow', windowId);
|
||||
}
|
||||
|
||||
getWindows(): Promise<{ id: number; workspace?: IWorkspaceIdentifier; folderUri?: ISingleFolderWorkspaceIdentifier; title: string; filename?: string; }[]> {
|
||||
return this.channel.call<{ id: number; workspace?: IWorkspaceIdentifier; folderUri?: ISingleFolderWorkspaceIdentifier; title: string; filename?: string; }[]>('getWindows').then(result => {
|
||||
for (const win of result) {
|
||||
if (win.folderUri) {
|
||||
win.folderUri = URI.revive(win.folderUri);
|
||||
}
|
||||
if (win.workspace) {
|
||||
win.workspace = reviveWorkspaceIdentifier(win.workspace);
|
||||
}
|
||||
}
|
||||
return result;
|
||||
});
|
||||
}
|
||||
|
||||
getWindowCount(): Promise<number> {
|
||||
return this.channel.call('getWindowCount');
|
||||
}
|
||||
|
||||
log(severity: string, ...messages: string[]): Promise<void> {
|
||||
return this.channel.call('log', [severity, messages]);
|
||||
}
|
||||
|
||||
showItemInFolder(path: URI): Promise<void> {
|
||||
return this.channel.call('showItemInFolder', path);
|
||||
}
|
||||
|
||||
getActiveWindowId(): Promise<number | undefined> {
|
||||
return this.channel.call('getActiveWindowId');
|
||||
}
|
||||
|
||||
openExternal(url: string): Promise<boolean> {
|
||||
return this.channel.call('openExternal', url);
|
||||
}
|
||||
|
||||
startCrashReporter(config: CrashReporterStartOptions): Promise<void> {
|
||||
return this.channel.call('startCrashReporter', config);
|
||||
}
|
||||
|
||||
updateTouchBar(windowId: number, items: ISerializableCommandAction[][]): Promise<void> {
|
||||
return this.channel.call('updateTouchBar', [windowId, items]);
|
||||
}
|
||||
|
||||
openAboutDialog(): Promise<void> {
|
||||
return this.channel.call('openAboutDialog');
|
||||
}
|
||||
|
||||
resolveProxy(windowId: number, url: string): Promise<string | undefined> {
|
||||
return Promise.resolve(this.channel.call('resolveProxy', [windowId, url]));
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,33 @@
|
||||
/*---------------------------------------------------------------------------------------------
|
||||
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||
* Licensed under the MIT License. See License.txt in the project root for license information.
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
|
||||
import { IChannel } from 'vs/base/parts/ipc/node/ipc';
|
||||
import { IWorkspacesService, IWorkspaceIdentifier, IWorkspaceFolderCreationData, reviveWorkspaceIdentifier } from 'vs/platform/workspaces/common/workspaces';
|
||||
import { IMainProcessService } from 'vs/platform/ipc/electron-browser/mainProcessService';
|
||||
import { ServiceIdentifier } from 'vs/platform/instantiation/common/instantiation';
|
||||
import { URI } from 'vs/base/common/uri';
|
||||
|
||||
export class WorkspacesService implements IWorkspacesService {
|
||||
|
||||
_serviceBrand: ServiceIdentifier<any>;
|
||||
|
||||
private channel: IChannel;
|
||||
|
||||
constructor(@IMainProcessService mainProcessService: IMainProcessService) {
|
||||
this.channel = mainProcessService.getChannel('workspaces');
|
||||
}
|
||||
|
||||
createUntitledWorkspace(folders?: IWorkspaceFolderCreationData[], remoteAuthority?: string): Promise<IWorkspaceIdentifier> {
|
||||
return this.channel.call('createUntitledWorkspace', [folders, remoteAuthority]).then(reviveWorkspaceIdentifier);
|
||||
}
|
||||
|
||||
deleteUntitledWorkspace(workspaceIdentifier: IWorkspaceIdentifier): Promise<void> {
|
||||
return this.channel.call('deleteUntitledWorkspace', workspaceIdentifier);
|
||||
}
|
||||
|
||||
getWorkspaceIdentifier(configPath: URI): Promise<IWorkspaceIdentifier> {
|
||||
return this.channel.call('getWorkspaceIdentifier', configPath);
|
||||
}
|
||||
}
|
||||
@@ -3,8 +3,8 @@
|
||||
* Licensed under the MIT License. See License.txt in the project root for license information.
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
|
||||
import { IChannel, IServerChannel } from 'vs/base/parts/ipc/node/ipc';
|
||||
import { IWorkspacesService, IWorkspaceIdentifier, IWorkspaceFolderCreationData, IWorkspacesMainService, reviveWorkspaceIdentifier } from 'vs/platform/workspaces/common/workspaces';
|
||||
import { IServerChannel } from 'vs/base/parts/ipc/node/ipc';
|
||||
import { IWorkspaceIdentifier, IWorkspaceFolderCreationData, IWorkspacesMainService } from 'vs/platform/workspaces/common/workspaces';
|
||||
import { URI } from 'vs/base/common/uri';
|
||||
import { Event } from 'vs/base/common/event';
|
||||
|
||||
@@ -45,22 +45,3 @@ export class WorkspacesChannel implements IServerChannel {
|
||||
throw new Error(`Call not found: ${command}`);
|
||||
}
|
||||
}
|
||||
|
||||
export class WorkspacesChannelClient implements IWorkspacesService {
|
||||
|
||||
_serviceBrand: any;
|
||||
|
||||
constructor(private channel: IChannel) { }
|
||||
|
||||
createUntitledWorkspace(folders?: IWorkspaceFolderCreationData[], remoteAuthority?: string): Promise<IWorkspaceIdentifier> {
|
||||
return this.channel.call('createUntitledWorkspace', [folders, remoteAuthority]).then(reviveWorkspaceIdentifier);
|
||||
}
|
||||
|
||||
deleteUntitledWorkspace(workspaceIdentifier: IWorkspaceIdentifier): Promise<void> {
|
||||
return this.channel.call('deleteUntitledWorkspace', workspaceIdentifier);
|
||||
}
|
||||
|
||||
getWorkspaceIdentifier(configPath: URI): Promise<IWorkspaceIdentifier> {
|
||||
return this.channel.call('getWorkspaceIdentifier', configPath);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -0,0 +1,56 @@
|
||||
/*---------------------------------------------------------------------------------------------
|
||||
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||
* Licensed under the MIT License. See License.txt in the project root for license information.
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
|
||||
import { mark } from 'vs/base/common/performance';
|
||||
import { domContentLoaded, addDisposableListener, EventType } from 'vs/base/browser/dom';
|
||||
import { ServiceCollection } from 'vs/platform/instantiation/common/serviceCollection';
|
||||
import { ILogService } from 'vs/platform/log/common/log';
|
||||
import { Disposable } from 'vs/base/common/lifecycle';
|
||||
import { SimpleLogService } from 'vs/workbench/browser/nodeless.simpleservices';
|
||||
import { Workbench } from 'vs/workbench/browser/workbench';
|
||||
|
||||
class CodeRendererMain extends Disposable {
|
||||
|
||||
private workbench: Workbench;
|
||||
|
||||
open(): Promise<void> {
|
||||
const services = this.initServices();
|
||||
|
||||
return domContentLoaded().then(() => {
|
||||
mark('willStartWorkbench');
|
||||
|
||||
// Create Workbench
|
||||
this.workbench = new Workbench(
|
||||
document.body,
|
||||
services.serviceCollection,
|
||||
services.logService
|
||||
);
|
||||
|
||||
// Layout
|
||||
this._register(addDisposableListener(window, EventType.RESIZE, () => this.workbench.layout()));
|
||||
|
||||
// Workbench Lifecycle
|
||||
this._register(this.workbench.onShutdown(() => this.dispose()));
|
||||
|
||||
// Startup
|
||||
this.workbench.startup();
|
||||
});
|
||||
}
|
||||
|
||||
private initServices(): { serviceCollection: ServiceCollection, logService: ILogService } {
|
||||
const serviceCollection = new ServiceCollection();
|
||||
|
||||
const logService = new SimpleLogService();
|
||||
serviceCollection.set(ILogService, logService);
|
||||
|
||||
return { serviceCollection, logService };
|
||||
}
|
||||
}
|
||||
|
||||
export function main(): Promise<void> {
|
||||
const renderer = new CodeRendererMain();
|
||||
|
||||
return renderer.open();
|
||||
}
|
||||
File diff suppressed because it is too large
Load Diff
@@ -57,6 +57,7 @@ export class NotificationsCenter extends Themable {
|
||||
|
||||
private registerListeners(): void {
|
||||
this._register(this.model.onDidNotificationChange(e => this.onDidNotificationChange(e)));
|
||||
this._register(this.layoutService.onLayout(dimension => this.layout(dimension)));
|
||||
}
|
||||
|
||||
get isVisible(): boolean {
|
||||
|
||||
@@ -79,6 +79,9 @@ export class NotificationsToasts extends Themable {
|
||||
|
||||
private registerListeners(): void {
|
||||
|
||||
// Layout
|
||||
this._register(this.layoutService.onLayout(dimension => this.layout(dimension)));
|
||||
|
||||
// Delay some tasks until after we can show notifications
|
||||
this.onCanShowNotifications().then(() => {
|
||||
|
||||
|
||||
@@ -24,7 +24,6 @@ import { SidebarPart } from 'vs/workbench/browser/parts/sidebar/sidebarPart';
|
||||
import { PanelPart } from 'vs/workbench/browser/parts/panel/panelPart';
|
||||
import { IActionBarRegistry, Extensions as ActionBarExtensions } from 'vs/workbench/browser/actions';
|
||||
import { PanelRegistry, Extensions as PanelExtensions } from 'vs/workbench/browser/panel';
|
||||
import { ViewletRegistry, Extensions as ViewletExtensions } from 'vs/workbench/browser/viewlet';
|
||||
import { getServices } from 'vs/platform/instantiation/common/extensions';
|
||||
import { Position, Parts, IWorkbenchLayoutService, ILayoutOptions } from 'vs/workbench/services/layout/browser/layoutService';
|
||||
import { IWorkspaceContextService, WorkbenchState } from 'vs/platform/workspace/common/workspace';
|
||||
@@ -61,6 +60,8 @@ import { IDimension } from 'vs/platform/layout/browser/layoutService';
|
||||
import { Part } from 'vs/workbench/browser/part';
|
||||
import { IStatusbarService } from 'vs/platform/statusbar/common/statusbar';
|
||||
import { IActivityBarService } from 'vs/workbench/services/activityBar/browser/activityBarService';
|
||||
import { coalesce } from 'vs/base/common/arrays';
|
||||
import { InstantiationService } from 'vs/platform/instantiation/common/instantiationService';
|
||||
|
||||
export interface IWorkbenchOptions {
|
||||
hasInitialFilesToOpen: boolean;
|
||||
@@ -90,8 +91,6 @@ enum Storage {
|
||||
|
||||
export class Workbench extends Disposable implements IWorkbenchLayoutService {
|
||||
|
||||
//#region workbench
|
||||
|
||||
_serviceBrand: ServiceIdentifier<any>;
|
||||
|
||||
private readonly _onShutdown = this._register(new Emitter<void>());
|
||||
@@ -100,47 +99,19 @@ export class Workbench extends Disposable implements IWorkbenchLayoutService {
|
||||
private readonly _onWillShutdown = this._register(new Emitter<WillShutdownEvent>());
|
||||
get onWillShutdown(): Event<WillShutdownEvent> { return this._onWillShutdown.event; }
|
||||
|
||||
private previousErrorValue: string;
|
||||
private previousErrorTime = 0;
|
||||
|
||||
private workbench: HTMLElement;
|
||||
|
||||
private restored: boolean;
|
||||
private disposed: boolean;
|
||||
|
||||
private instantiationService: IInstantiationService;
|
||||
private contextService: IWorkspaceContextService;
|
||||
private storageService: IStorageService;
|
||||
private configurationService: IConfigurationService;
|
||||
private environmentService: IEnvironmentService;
|
||||
private logService: ILogService;
|
||||
|
||||
private parts: Map<string, Part> = new Map<string, Part>();
|
||||
private workbench: HTMLElement = document.createElement('div');
|
||||
|
||||
constructor(
|
||||
private parent: HTMLElement,
|
||||
private options: IWorkbenchOptions,
|
||||
private serviceCollection: ServiceCollection,
|
||||
@IInstantiationService instantiationService: IInstantiationService,
|
||||
@IWorkspaceContextService contextService: IWorkspaceContextService,
|
||||
@IStorageService storageService: IStorageService,
|
||||
@IConfigurationService configurationService: IConfigurationService,
|
||||
@IEnvironmentService environmentService: IEnvironmentService,
|
||||
@ILogService logService: ILogService
|
||||
private readonly parent: HTMLElement,
|
||||
private readonly serviceCollection: ServiceCollection,
|
||||
logService: ILogService
|
||||
) {
|
||||
super();
|
||||
|
||||
this.instantiationService = instantiationService;
|
||||
this.contextService = contextService;
|
||||
this.storageService = storageService;
|
||||
this.configurationService = configurationService;
|
||||
this.environmentService = environmentService;
|
||||
this.logService = logService;
|
||||
|
||||
this.registerErrorHandler();
|
||||
this.registerErrorHandler(logService);
|
||||
}
|
||||
|
||||
private registerErrorHandler(): void {
|
||||
private registerErrorHandler(logService: ILogService): void {
|
||||
|
||||
// Listen on unhandled rejection events
|
||||
window.addEventListener('unhandledrejection', (event: PromiseRejectionEvent) => {
|
||||
@@ -153,7 +124,7 @@ export class Workbench extends Disposable implements IWorkbenchLayoutService {
|
||||
});
|
||||
|
||||
// Install handler for unexpected errors
|
||||
setUnexpectedErrorHandler(error => this.handleUnexpectedError(error));
|
||||
setUnexpectedErrorHandler(error => this.handleUnexpectedError(error, logService));
|
||||
|
||||
// Inform user about loading issues from the loader
|
||||
(<any>self).require.config({
|
||||
@@ -165,117 +136,107 @@ export class Workbench extends Disposable implements IWorkbenchLayoutService {
|
||||
});
|
||||
}
|
||||
|
||||
private handleUnexpectedError(error: any): void {
|
||||
const errorMsg = toErrorMessage(error, true);
|
||||
if (!errorMsg) {
|
||||
private previousUnexpectedError: { message: string, time: number } = { message: undefined, time: 0 };
|
||||
private handleUnexpectedError(error: any, logService: ILogService): void {
|
||||
const message = toErrorMessage(error, true);
|
||||
if (!message) {
|
||||
return;
|
||||
}
|
||||
|
||||
const now = Date.now();
|
||||
if (errorMsg === this.previousErrorValue && now - this.previousErrorTime <= 1000) {
|
||||
if (message === this.previousUnexpectedError.message && now - this.previousUnexpectedError.time <= 1000) {
|
||||
return; // Return if error message identical to previous and shorter than 1 second
|
||||
}
|
||||
|
||||
this.previousErrorTime = now;
|
||||
this.previousErrorValue = errorMsg;
|
||||
this.previousUnexpectedError.time = now;
|
||||
this.previousUnexpectedError.message = message;
|
||||
|
||||
// Log it
|
||||
this.logService.error(errorMsg);
|
||||
logService.error(message);
|
||||
}
|
||||
|
||||
startup(): void {
|
||||
startup(): IInstantiationService {
|
||||
try {
|
||||
this.doStartup().then(undefined, error => this.logService.error(toErrorMessage(error, true)));
|
||||
|
||||
// Configure emitter leak warning threshold
|
||||
setGlobalLeakWarningThreshold(175);
|
||||
|
||||
// Setup Intl for comparers
|
||||
setFileNameComparer(new IdleValue(() => {
|
||||
const collator = new Intl.Collator(undefined, { numeric: true, sensitivity: 'base' });
|
||||
return {
|
||||
collator: collator,
|
||||
collatorIsNumeric: collator.resolvedOptions().numeric
|
||||
};
|
||||
}));
|
||||
|
||||
// ARIA
|
||||
setARIAContainer(document.body);
|
||||
|
||||
// Services
|
||||
const instantiationService = this.initServices(this.serviceCollection);
|
||||
|
||||
instantiationService.invokeFunction(accessor => {
|
||||
const lifecycleService = accessor.get(ILifecycleService);
|
||||
const storageService = accessor.get(IStorageService);
|
||||
const configurationService = accessor.get(IConfigurationService);
|
||||
|
||||
// Layout
|
||||
this.initLayout(accessor);
|
||||
|
||||
// Registries
|
||||
this.initRegistries(accessor);
|
||||
|
||||
// Context Keys
|
||||
this._register(instantiationService.createInstance(WorkbenchContextKeysHandler));
|
||||
|
||||
// Register Listeners
|
||||
this.registerListeners(lifecycleService, storageService, configurationService);
|
||||
|
||||
// Render Workbench
|
||||
this.renderWorkbench(instantiationService, accessor.get(INotificationService) as NotificationService, storageService, configurationService);
|
||||
|
||||
// Workbench Layout
|
||||
this.createWorkbenchLayout(instantiationService);
|
||||
|
||||
// Layout
|
||||
this.layout();
|
||||
|
||||
// Restore
|
||||
this.restoreWorkbench(accessor.get(IEditorService), accessor.get(IEditorGroupsService), accessor.get(IViewletService), accessor.get(IPanelService), accessor.get(ILogService), lifecycleService).then(undefined, error => onUnexpectedError(error));
|
||||
});
|
||||
|
||||
return instantiationService;
|
||||
} catch (error) {
|
||||
this.logService.error(toErrorMessage(error, true));
|
||||
onUnexpectedError(error);
|
||||
|
||||
throw error; // rethrow because this is a critical issue we cannot handle properly here
|
||||
}
|
||||
}
|
||||
|
||||
private doStartup(): Promise<void> {
|
||||
|
||||
// Configure emitter leak warning threshold
|
||||
setGlobalLeakWarningThreshold(175);
|
||||
|
||||
// Setup Intl for comparers
|
||||
setFileNameComparer(new IdleValue(() => {
|
||||
const collator = new Intl.Collator(undefined, { numeric: true, sensitivity: 'base' });
|
||||
return {
|
||||
collator: collator,
|
||||
collatorIsNumeric: collator.resolvedOptions().numeric
|
||||
};
|
||||
}));
|
||||
|
||||
// ARIA
|
||||
setARIAContainer(document.body);
|
||||
|
||||
// Warm up font cache information before building up too many dom elements
|
||||
restoreFontInfo(this.storageService);
|
||||
readFontInfo(BareFontInfo.createFromRawSettings(this.configurationService.getValue('editor'), getZoomLevel()));
|
||||
|
||||
// Create Workbench Container
|
||||
this.createWorkbenchContainer();
|
||||
|
||||
// Services
|
||||
this.initServices(this.serviceCollection);
|
||||
|
||||
// Registries
|
||||
this.startRegistries();
|
||||
|
||||
// Context Keys
|
||||
this._register(this.instantiationService.createInstance(WorkbenchContextKeysHandler));
|
||||
|
||||
// Register Listeners
|
||||
this.instantiationService.invokeFunction(accessor => {
|
||||
this.registerListeners(accessor);
|
||||
this.registerLayoutListeners(accessor);
|
||||
});
|
||||
|
||||
// Layout State
|
||||
this.instantiationService.invokeFunction(accessor => this.initLayoutState(accessor));
|
||||
|
||||
// Render Workbench
|
||||
this.renderWorkbench();
|
||||
|
||||
// Workbench Layout
|
||||
this.createWorkbenchLayout();
|
||||
|
||||
// Layout
|
||||
this.layout();
|
||||
|
||||
// Restore
|
||||
return this.instantiationService.invokeFunction(accessor => this.restoreWorkbench(accessor));
|
||||
}
|
||||
|
||||
private createWorkbenchContainer(): void {
|
||||
this.workbench = document.createElement('div');
|
||||
|
||||
const platformClass = isWindows ? 'windows' : isLinux ? 'linux' : 'mac';
|
||||
|
||||
addClasses(this.workbench, 'monaco-workbench', platformClass);
|
||||
addClasses(document.body, platformClass); // used by our fonts
|
||||
}
|
||||
|
||||
private initServices(serviceCollection: ServiceCollection): void {
|
||||
private initServices(serviceCollection: ServiceCollection): IInstantiationService {
|
||||
|
||||
// Layout Service
|
||||
serviceCollection.set(IWorkbenchLayoutService, this);
|
||||
|
||||
//
|
||||
// NOTE: DO NOT ADD ANY OTHER SERVICE INTO THE COLLECTION HERE.
|
||||
// INSTEAD, CONTRIBUTE IT VIA WORKBENCH.MAIN.TS
|
||||
//
|
||||
|
||||
// All Contributed Services
|
||||
const contributedServices = getServices();
|
||||
for (let contributedService of contributedServices) {
|
||||
serviceCollection.set(contributedService.id, contributedService.descriptor);
|
||||
}
|
||||
|
||||
const instantationServie = new InstantiationService(serviceCollection, true);
|
||||
|
||||
// Wrap up
|
||||
this.instantiationService.invokeFunction(accessor => {
|
||||
|
||||
// Signal to lifecycle that services are set
|
||||
instantationServie.invokeFunction(accessor => {
|
||||
const lifecycleService = accessor.get(ILifecycleService);
|
||||
lifecycleService.phase = LifecyclePhase.Ready;
|
||||
|
||||
// TODO@Sandeep TODO@Martin debt around cyclic dependencies
|
||||
// TODO@Ben TODO@Sandeep TODO@Martin debt around cyclic dependencies
|
||||
const fileService = accessor.get(IFileService);
|
||||
const instantiationService = accessor.get(IInstantiationService);
|
||||
const configurationService = accessor.get(IConfigurationService) as any;
|
||||
@@ -292,21 +253,25 @@ export class Workbench extends Disposable implements IWorkbenchLayoutService {
|
||||
if (typeof themeService.acquireFileService === 'function') {
|
||||
themeService.acquireFileService(fileService);
|
||||
}
|
||||
|
||||
// Signal to lifecycle that services are set
|
||||
lifecycleService.phase = LifecyclePhase.Ready;
|
||||
});
|
||||
|
||||
return instantationServie;
|
||||
}
|
||||
|
||||
private startRegistries(): void {
|
||||
this.instantiationService.invokeFunction(accessor => {
|
||||
Registry.as<IActionBarRegistry>(ActionBarExtensions.Actionbar).start(accessor);
|
||||
Registry.as<IWorkbenchContributionsRegistry>(WorkbenchExtensions.Workbench).start(accessor);
|
||||
Registry.as<IEditorInputFactoryRegistry>(EditorExtensions.EditorInputFactories).start(accessor);
|
||||
});
|
||||
private initRegistries(accessor: ServicesAccessor): void {
|
||||
Registry.as<IActionBarRegistry>(ActionBarExtensions.Actionbar).start(accessor);
|
||||
Registry.as<IWorkbenchContributionsRegistry>(WorkbenchExtensions.Workbench).start(accessor);
|
||||
Registry.as<IEditorInputFactoryRegistry>(EditorExtensions.EditorInputFactories).start(accessor);
|
||||
}
|
||||
|
||||
private registerListeners(accessor: ServicesAccessor): void {
|
||||
const lifecycleService = accessor.get(ILifecycleService);
|
||||
const storageService = accessor.get(IStorageService);
|
||||
const configurationService = accessor.get(IConfigurationService);
|
||||
private registerListeners(
|
||||
lifecycleService: ILifecycleService,
|
||||
storageService: IStorageService,
|
||||
configurationService: IConfigurationService
|
||||
): void {
|
||||
|
||||
// Lifecycle
|
||||
this._register(lifecycleService.onWillShutdown(event => this._onWillShutdown.fire(event)));
|
||||
@@ -316,15 +281,15 @@ export class Workbench extends Disposable implements IWorkbenchLayoutService {
|
||||
}));
|
||||
|
||||
// Storage
|
||||
this._register(storageService.onWillSaveState(e => this.saveState(e)));
|
||||
this._register(storageService.onWillSaveState(() => saveFontInfo(storageService)));
|
||||
|
||||
// Configuration changes
|
||||
this._register(configurationService.onDidChangeConfiguration(() => this.setFontAliasing()));
|
||||
this._register(configurationService.onDidChangeConfiguration(() => this.setFontAliasing(configurationService)));
|
||||
}
|
||||
|
||||
private fontAliasing: 'default' | 'antialiased' | 'none' | 'auto';
|
||||
private setFontAliasing() {
|
||||
const aliasing = this.configurationService.getValue<'default' | 'antialiased' | 'none' | 'auto'>(Settings.FONT_ALIASING);
|
||||
private setFontAliasing(configurationService: IConfigurationService) {
|
||||
const aliasing = configurationService.getValue<'default' | 'antialiased' | 'none' | 'auto'>(Settings.FONT_ALIASING);
|
||||
if (this.fontAliasing === aliasing) {
|
||||
return;
|
||||
}
|
||||
@@ -341,100 +306,73 @@ export class Workbench extends Disposable implements IWorkbenchLayoutService {
|
||||
}
|
||||
}
|
||||
|
||||
private renderWorkbench(): void {
|
||||
if (this.state.sideBar.hidden) {
|
||||
addClass(this.workbench, 'nosidebar');
|
||||
}
|
||||
private renderWorkbench(instantiationService: IInstantiationService, notificationService: NotificationService, storageService: IStorageService, configurationService: IConfigurationService): void {
|
||||
|
||||
if (this.state.panel.hidden) {
|
||||
addClass(this.workbench, 'nopanel');
|
||||
}
|
||||
// State specific classes
|
||||
const platformClass = isWindows ? 'windows' : isLinux ? 'linux' : 'mac';
|
||||
const workbenchClasses = coalesce([
|
||||
'monaco-workbench',
|
||||
platformClass,
|
||||
this.state.sideBar.hidden ? 'nosidebar' : undefined,
|
||||
this.state.panel.hidden ? 'nopanel' : undefined,
|
||||
this.state.statusBar.hidden ? 'nostatusbar' : undefined,
|
||||
this.state.fullscreen ? 'fullscreen' : undefined
|
||||
]);
|
||||
|
||||
if (this.state.statusBar.hidden) {
|
||||
addClass(this.workbench, 'nostatusbar');
|
||||
}
|
||||
|
||||
if (this.state.fullscreen) {
|
||||
addClass(this.workbench, 'fullscreen');
|
||||
}
|
||||
addClasses(this.workbench, ...workbenchClasses);
|
||||
addClasses(document.body, platformClass); // used by our fonts
|
||||
|
||||
// Apply font aliasing
|
||||
this.setFontAliasing();
|
||||
this.setFontAliasing(configurationService);
|
||||
|
||||
// Warm up font cache information before building up too many dom elements
|
||||
restoreFontInfo(storageService);
|
||||
readFontInfo(BareFontInfo.createFromRawSettings(configurationService.getValue('editor'), getZoomLevel()));
|
||||
|
||||
// Create Parts
|
||||
this.createTitlebarPart();
|
||||
this.createActivityBarPart();
|
||||
this.createSidebarPart();
|
||||
this.createEditorPart();
|
||||
this.createPanelPart();
|
||||
this.createStatusbarPart();
|
||||
[
|
||||
{ id: Parts.TITLEBAR_PART, role: 'contentinfo', classes: ['titlebar'] },
|
||||
{ id: Parts.ACTIVITYBAR_PART, role: 'navigation', classes: ['activitybar', this.state.sideBar.position === Position.LEFT ? 'left' : 'right'] },
|
||||
{ id: Parts.SIDEBAR_PART, role: 'complementary', classes: ['sidebar', this.state.sideBar.position === Position.LEFT ? 'left' : 'right'] },
|
||||
{ id: Parts.PANEL_PART, role: 'complementary', classes: ['panel', this.state.panel.position === Position.BOTTOM ? 'bottom' : 'right'] },
|
||||
{ id: Parts.EDITOR_PART, role: 'main', classes: ['editor'], options: { restorePreviousState: this.state.editor.restoreEditors } },
|
||||
{ id: Parts.STATUSBAR_PART, role: 'contentinfo', classes: ['statusbar'] }
|
||||
].forEach(({ id, role, classes, options }) => {
|
||||
const partContainer = this.createPart(id, role, classes);
|
||||
|
||||
if (!configurationService.getValue('workbench.useExperimentalGridLayout')) {
|
||||
// TODO@Ben cleanup once moved to grid
|
||||
// Insert all workbench parts at the beginning. Issue #52531
|
||||
// This is primarily for the title bar to allow overriding -webkit-app-region
|
||||
this.workbench.insertBefore(partContainer, this.workbench.lastChild);
|
||||
}
|
||||
|
||||
this.parts.get(id).create(partContainer, options);
|
||||
});
|
||||
|
||||
// Notification Handlers
|
||||
this.instantiationService.invokeFunction(accessor => this.createNotificationsHandlers(accessor));
|
||||
this.createNotificationsHandlers(instantiationService, notificationService);
|
||||
|
||||
// Add Workbench to DOM
|
||||
this.parent.appendChild(this.workbench);
|
||||
}
|
||||
|
||||
private createTitlebarPart(): void {
|
||||
const titlebarContainer = this.createPart(Parts.TITLEBAR_PART, 'contentinfo', 'titlebar');
|
||||
|
||||
this.parts.get(Parts.TITLEBAR_PART).create(titlebarContainer);
|
||||
}
|
||||
|
||||
private createActivityBarPart(): void {
|
||||
const activitybarPartContainer = this.createPart(Parts.ACTIVITYBAR_PART, 'navigation', 'activitybar', this.state.sideBar.position === Position.LEFT ? 'left' : 'right');
|
||||
|
||||
this.parts.get(Parts.ACTIVITYBAR_PART).create(activitybarPartContainer);
|
||||
}
|
||||
|
||||
private createSidebarPart(): void {
|
||||
const sidebarPartContainer = this.createPart(Parts.SIDEBAR_PART, 'complementary', 'sidebar', this.state.sideBar.position === Position.LEFT ? 'left' : 'right');
|
||||
|
||||
this.parts.get(Parts.SIDEBAR_PART).create(sidebarPartContainer);
|
||||
}
|
||||
|
||||
private createPanelPart(): void {
|
||||
const panelPartContainer = this.createPart(Parts.PANEL_PART, 'complementary', 'panel', this.state.panel.position === Position.BOTTOM ? 'bottom' : 'right');
|
||||
|
||||
this.parts.get(Parts.PANEL_PART).create(panelPartContainer);
|
||||
}
|
||||
|
||||
private createEditorPart(): void {
|
||||
const editorContainer = this.createPart(Parts.EDITOR_PART, 'main', 'editor');
|
||||
|
||||
this.parts.get(Parts.EDITOR_PART).create(editorContainer, { restorePreviousState: !this.options.hasInitialFilesToOpen });
|
||||
}
|
||||
|
||||
private createStatusbarPart(): void {
|
||||
const statusbarContainer = this.createPart(Parts.STATUSBAR_PART, 'contentinfo', 'statusbar');
|
||||
|
||||
this.parts.get(Parts.STATUSBAR_PART).create(statusbarContainer);
|
||||
}
|
||||
|
||||
private createPart(id: string, role: string, ...classes: string[]): HTMLElement {
|
||||
private createPart(id: string, role: string, classes: string[]): HTMLElement {
|
||||
const part = document.createElement('div');
|
||||
addClasses(part, 'part', ...classes);
|
||||
part.id = id;
|
||||
part.setAttribute('role', role);
|
||||
|
||||
if (!this.configurationService.getValue('workbench.useExperimentalGridLayout')) {
|
||||
// Insert all workbench parts at the beginning. Issue #52531
|
||||
// This is primarily for the title bar to allow overriding -webkit-app-region
|
||||
this.workbench.insertBefore(part, this.workbench.lastChild);
|
||||
}
|
||||
|
||||
return part;
|
||||
}
|
||||
|
||||
private createNotificationsHandlers(accessor: ServicesAccessor): void {
|
||||
const notificationService = accessor.get(INotificationService) as NotificationService;
|
||||
private createNotificationsHandlers(instantiationService: IInstantiationService, notificationService: NotificationService): void {
|
||||
|
||||
// Instantiate Notification components
|
||||
const notificationsCenter = this._register(this.instantiationService.createInstance(NotificationsCenter, this.workbench, notificationService.model));
|
||||
const notificationsToasts = this._register(this.instantiationService.createInstance(NotificationsToasts, this.workbench, notificationService.model));
|
||||
this._register(this.instantiationService.createInstance(NotificationsAlerts, notificationService.model));
|
||||
const notificationsStatus = this.instantiationService.createInstance(NotificationsStatus, notificationService.model);
|
||||
const notificationsCenter = this._register(instantiationService.createInstance(NotificationsCenter, this.workbench, notificationService.model));
|
||||
const notificationsToasts = this._register(instantiationService.createInstance(NotificationsToasts, this.workbench, notificationService.model));
|
||||
this._register(instantiationService.createInstance(NotificationsAlerts, notificationService.model));
|
||||
const notificationsStatus = instantiationService.createInstance(NotificationsStatus, notificationService.model);
|
||||
|
||||
// Visibility
|
||||
this._register(notificationsCenter.onDidChangeVisibility(() => {
|
||||
@@ -442,23 +380,18 @@ export class Workbench extends Disposable implements IWorkbenchLayoutService {
|
||||
notificationsToasts.update(notificationsCenter.isVisible);
|
||||
}));
|
||||
|
||||
// Layout
|
||||
this._register(this.onLayout(dimension => {
|
||||
notificationsCenter.layout(dimension);
|
||||
notificationsToasts.layout(dimension);
|
||||
}));
|
||||
|
||||
// Register Commands
|
||||
registerNotificationCommands(notificationsCenter, notificationsToasts);
|
||||
}
|
||||
|
||||
private restoreWorkbench(accessor: ServicesAccessor): Promise<void> {
|
||||
const editorService = accessor.get(IEditorService);
|
||||
const editorGroupService = accessor.get(IEditorGroupsService);
|
||||
const viewletService = accessor.get(IViewletService);
|
||||
const panelService = accessor.get(IPanelService);
|
||||
const logService = accessor.get(ILogService);
|
||||
|
||||
private restoreWorkbench(
|
||||
editorService: IEditorService,
|
||||
editorGroupService: IEditorGroupsService,
|
||||
viewletService: IViewletService,
|
||||
panelService: IPanelService,
|
||||
logService: ILogService,
|
||||
lifecycleService: ILifecycleService
|
||||
): Promise<void> {
|
||||
const restorePromises: Promise<any>[] = [];
|
||||
|
||||
// Restore editors
|
||||
@@ -514,52 +447,26 @@ export class Workbench extends Disposable implements IWorkbenchLayoutService {
|
||||
// Emit a warning after 10s if restore does not complete
|
||||
const restoreTimeoutHandle = setTimeout(() => logService.warn('Workbench did not finish loading in 10 seconds, that might be a problem that should be reported.'), 10000);
|
||||
|
||||
let error: Error;
|
||||
return Promise.all(restorePromises)
|
||||
.then(() => clearTimeout(restoreTimeoutHandle))
|
||||
.catch(err => error = err)
|
||||
.finally(() => this.instantiationService.invokeFunction(accessor => this.whenRestored(accessor, error)));
|
||||
.catch(error => onUnexpectedError(error))
|
||||
.finally(() => {
|
||||
|
||||
// Set lifecycle phase to `Restored`
|
||||
lifecycleService.phase = LifecyclePhase.Restored;
|
||||
|
||||
// Set lifecycle phase to `Eventually` after a short delay and when idle (min 2.5sec, max 5sec)
|
||||
setTimeout(() => {
|
||||
this._register(runWhenIdle(() => {
|
||||
lifecycleService.phase = LifecyclePhase.Eventually;
|
||||
}, 2500));
|
||||
}, 2500);
|
||||
|
||||
// Telemetry: startup metrics
|
||||
mark('didStartWorkbench');
|
||||
});
|
||||
}
|
||||
|
||||
private whenRestored(accessor: ServicesAccessor, error?: Error): void {
|
||||
const lifecycleService = accessor.get(ILifecycleService);
|
||||
|
||||
this.restored = true;
|
||||
|
||||
// Set lifecycle phase to `Restored`
|
||||
lifecycleService.phase = LifecyclePhase.Restored;
|
||||
|
||||
// Set lifecycle phase to `Eventually` after a short delay and when
|
||||
// idle (min 2.5sec, max 5sec)
|
||||
setTimeout(() => {
|
||||
this._register(runWhenIdle(() => {
|
||||
lifecycleService.phase = LifecyclePhase.Eventually;
|
||||
}, 2500));
|
||||
}, 2500);
|
||||
|
||||
if (error) {
|
||||
onUnexpectedError(error);
|
||||
}
|
||||
|
||||
// Telemetry: startup metrics
|
||||
mark('didStartWorkbench');
|
||||
}
|
||||
|
||||
private saveState(e: IWillSaveStateEvent): void {
|
||||
|
||||
// Font info
|
||||
saveFontInfo(this.storageService);
|
||||
}
|
||||
|
||||
dispose(): void {
|
||||
super.dispose();
|
||||
|
||||
this.disposed = true;
|
||||
}
|
||||
|
||||
//#endregion
|
||||
|
||||
//#region ILayoutService
|
||||
|
||||
private readonly _onTitleBarVisibilityChange: Emitter<void> = this._register(new Emitter<void>());
|
||||
@@ -576,8 +483,12 @@ export class Workbench extends Disposable implements IWorkbenchLayoutService {
|
||||
|
||||
get container(): HTMLElement { return this.workbench; }
|
||||
|
||||
private parts: Map<string, Part> = new Map<string, Part>();
|
||||
|
||||
private workbenchGrid: Grid<View> | WorkbenchLegacyLayout;
|
||||
|
||||
private disposed: boolean;
|
||||
|
||||
private titleBarPartView: View;
|
||||
private activityBarPartView: View;
|
||||
private sideBarPartView: View;
|
||||
@@ -585,11 +496,18 @@ export class Workbench extends Disposable implements IWorkbenchLayoutService {
|
||||
private editorPartView: View;
|
||||
private statusBarPartView: View;
|
||||
|
||||
private environmentService: IEnvironmentService;
|
||||
private configurationService: IConfigurationService;
|
||||
private lifecycleService: ILifecycleService;
|
||||
private storageService: IStorageService;
|
||||
private windowService: IWindowService;
|
||||
private editorService: IEditorService;
|
||||
private editorGroupService: IEditorGroupsService;
|
||||
private panelService: IPanelService;
|
||||
private titleService: ITitleService;
|
||||
private viewletService: IViewletService;
|
||||
private contextService: IWorkspaceContextService;
|
||||
private backupFileService: IBackupFileService;
|
||||
|
||||
private readonly state = {
|
||||
fullscreen: false,
|
||||
@@ -614,6 +532,7 @@ export class Workbench extends Disposable implements IWorkbenchLayoutService {
|
||||
hidden: false,
|
||||
centered: false,
|
||||
restoreCentered: false,
|
||||
restoreEditors: false,
|
||||
editorsToOpen: undefined as Promise<IResourceEditor[]> | IResourceEditor[]
|
||||
},
|
||||
|
||||
@@ -640,41 +559,57 @@ export class Workbench extends Disposable implements IWorkbenchLayoutService {
|
||||
}
|
||||
};
|
||||
|
||||
registerPart(part: Part): void {
|
||||
this.parts.set(part.getId(), part);
|
||||
private initLayout(accessor: ServicesAccessor) {
|
||||
|
||||
// Services
|
||||
this.environmentService = accessor.get(IEnvironmentService);
|
||||
this.configurationService = accessor.get(IConfigurationService);
|
||||
this.lifecycleService = accessor.get(ILifecycleService);
|
||||
this.windowService = accessor.get(IWindowService);
|
||||
this.contextService = accessor.get(IWorkspaceContextService);
|
||||
this.storageService = accessor.get(IStorageService);
|
||||
|
||||
// Parts
|
||||
this.editorService = accessor.get(IEditorService);
|
||||
this.editorGroupService = accessor.get(IEditorGroupsService);
|
||||
this.panelService = accessor.get(IPanelService);
|
||||
this.viewletService = accessor.get(IViewletService);
|
||||
this.titleService = accessor.get(ITitleService);
|
||||
accessor.get(IStatusbarService); // not used, but called to ensure instantiated
|
||||
accessor.get(IActivityBarService); // not used, but called to ensure instantiated
|
||||
|
||||
// Listeners
|
||||
this.registerLayoutListeners();
|
||||
|
||||
// State
|
||||
this.initLayoutState(accessor.get(ILifecycleService));
|
||||
}
|
||||
|
||||
private registerLayoutListeners(accessor: ServicesAccessor): void {
|
||||
const storageService = accessor.get(IStorageService);
|
||||
const editorService = accessor.get(IEditorService);
|
||||
const configurationService = accessor.get(IConfigurationService);
|
||||
const editorGroupService = accessor.get(IEditorGroupsService);
|
||||
const titleService = accessor.get(ITitleService);
|
||||
const environmentService = accessor.get(IEnvironmentService);
|
||||
private registerLayoutListeners(): void {
|
||||
|
||||
// Storage
|
||||
this._register(storageService.onWillSaveState(e => this.saveLayoutState(e)));
|
||||
this._register(this.storageService.onWillSaveState(e => this.saveLayoutState(e)));
|
||||
|
||||
// Restore editor if hidden and it changes
|
||||
this._register(editorService.onDidVisibleEditorsChange(() => this.setEditorHidden(false)));
|
||||
this._register(editorGroupService.onDidActivateGroup(() => this.setEditorHidden(false)));
|
||||
this._register(this.editorService.onDidVisibleEditorsChange(() => this.setEditorHidden(false)));
|
||||
this._register(this.editorGroupService.onDidActivateGroup(() => this.setEditorHidden(false)));
|
||||
|
||||
// Configuration changes
|
||||
this._register(configurationService.onDidChangeConfiguration(() => this.doUpdateLayoutConfiguration()));
|
||||
this._register(this.configurationService.onDidChangeConfiguration(() => this.doUpdateLayoutConfiguration()));
|
||||
|
||||
// Fullscreen changes
|
||||
this._register(onDidChangeFullscreen(() => this.onFullscreenChanged()));
|
||||
|
||||
// Group changes
|
||||
this._register(editorGroupService.onDidAddGroup(() => this.centerEditorLayout(this.state.editor.centered)));
|
||||
this._register(editorGroupService.onDidRemoveGroup(() => this.centerEditorLayout(this.state.editor.centered)));
|
||||
this._register(this.editorGroupService.onDidAddGroup(() => this.centerEditorLayout(this.state.editor.centered)));
|
||||
this._register(this.editorGroupService.onDidRemoveGroup(() => this.centerEditorLayout(this.state.editor.centered)));
|
||||
|
||||
// Prevent workbench from scrolling #55456
|
||||
this._register(addDisposableListener(this.workbench, EventType.SCROLL, () => this.workbench.scrollTop = 0));
|
||||
|
||||
// Menubar visibility changes
|
||||
if ((isWindows || isLinux) && getTitleBarStyle(configurationService, environmentService) === 'custom') {
|
||||
this._register(titleService.onMenubarVisibilityChange(visible => this.onMenubarToggled(visible)));
|
||||
if ((isWindows || isLinux) && getTitleBarStyle(this.configurationService, this.environmentService) === 'custom') {
|
||||
this._register(this.titleService.onMenubarVisibilityChange(visible => this.onMenubarToggled(visible)));
|
||||
}
|
||||
}
|
||||
|
||||
@@ -784,49 +719,32 @@ export class Workbench extends Disposable implements IWorkbenchLayoutService {
|
||||
}
|
||||
}
|
||||
|
||||
private initLayoutState(accessor: ServicesAccessor): void {
|
||||
const configurationService = accessor.get(IConfigurationService);
|
||||
const storageService = accessor.get(IStorageService);
|
||||
const lifecycleService = accessor.get(ILifecycleService);
|
||||
const contextService = accessor.get(IWorkspaceContextService);
|
||||
const environmentService = accessor.get(IEnvironmentService);
|
||||
|
||||
this.windowService = accessor.get(IWindowService);
|
||||
|
||||
// Ensure all part services are created (TODO@ben revisit this requirement)
|
||||
this.editorService = accessor.get(IEditorService);
|
||||
this.editorGroupService = accessor.get(IEditorGroupsService);
|
||||
this.panelService = accessor.get(IPanelService);
|
||||
this.viewletService = accessor.get(IViewletService);
|
||||
accessor.get(IStatusbarService);
|
||||
accessor.get(ITitleService);
|
||||
accessor.get(IActivityBarService);
|
||||
private initLayoutState(lifecycleService: ILifecycleService): void {
|
||||
|
||||
// Fullscreen
|
||||
this.state.fullscreen = isFullscreen();
|
||||
|
||||
// Menubar visibility
|
||||
this.state.menuBar.visibility = configurationService.getValue<MenuBarVisibility>(Settings.MENUBAR_VISIBLE);
|
||||
this.state.menuBar.visibility = this.configurationService.getValue<MenuBarVisibility>(Settings.MENUBAR_VISIBLE);
|
||||
|
||||
// Activity bar visibility
|
||||
this.state.activityBar.hidden = !configurationService.getValue<string>(Settings.ACTIVITYBAR_VISIBLE);
|
||||
this.state.activityBar.hidden = !this.configurationService.getValue<string>(Settings.ACTIVITYBAR_VISIBLE);
|
||||
|
||||
// Sidebar visibility
|
||||
this.state.sideBar.hidden = storageService.getBoolean(Storage.SIDEBAR_HIDDEN, StorageScope.WORKSPACE, contextService.getWorkbenchState() === WorkbenchState.EMPTY);
|
||||
this.state.sideBar.hidden = this.storageService.getBoolean(Storage.SIDEBAR_HIDDEN, StorageScope.WORKSPACE, this.contextService.getWorkbenchState() === WorkbenchState.EMPTY);
|
||||
|
||||
// Sidebar position
|
||||
this.state.sideBar.position = (configurationService.getValue<string>(Settings.SIDEBAR_POSITION) === 'right') ? Position.RIGHT : Position.LEFT;
|
||||
this.state.sideBar.position = (this.configurationService.getValue<string>(Settings.SIDEBAR_POSITION) === 'right') ? Position.RIGHT : Position.LEFT;
|
||||
|
||||
// Sidebar viewlet
|
||||
if (!this.state.sideBar.hidden) {
|
||||
const viewletRegistry = Registry.as<ViewletRegistry>(ViewletExtensions.Viewlets);
|
||||
|
||||
// Only restore last viewlet if window was reloaded or we are in development mode
|
||||
let viewletToRestore: string;
|
||||
if (!environmentService.isBuilt || lifecycleService.startupKind === StartupKind.ReloadedWindow) {
|
||||
viewletToRestore = storageService.get(SidebarPart.activeViewletSettingsKey, StorageScope.WORKSPACE, viewletRegistry.getDefaultViewletId());
|
||||
if (!this.environmentService.isBuilt || lifecycleService.startupKind === StartupKind.ReloadedWindow) {
|
||||
viewletToRestore = this.storageService.get(SidebarPart.activeViewletSettingsKey, StorageScope.WORKSPACE, this.viewletService.getDefaultViewletId());
|
||||
} else {
|
||||
viewletToRestore = viewletRegistry.getDefaultViewletId();
|
||||
viewletToRestore = this.viewletService.getDefaultViewletId();
|
||||
}
|
||||
|
||||
if (viewletToRestore) {
|
||||
@@ -837,13 +755,13 @@ export class Workbench extends Disposable implements IWorkbenchLayoutService {
|
||||
}
|
||||
|
||||
// Editor centered layout
|
||||
this.state.editor.restoreCentered = storageService.getBoolean(Storage.CENTERED_LAYOUT_ENABLED, StorageScope.WORKSPACE, false);
|
||||
this.state.editor.restoreCentered = this.storageService.getBoolean(Storage.CENTERED_LAYOUT_ENABLED, StorageScope.WORKSPACE, false);
|
||||
|
||||
// Editors to open
|
||||
this.state.editor.editorsToOpen = this.resolveEditorsToOpen(accessor);
|
||||
this.state.editor.editorsToOpen = this.resolveEditorsToOpen();
|
||||
|
||||
// Panel visibility
|
||||
this.state.panel.hidden = storageService.getBoolean(Storage.PANEL_HIDDEN, StorageScope.WORKSPACE, true);
|
||||
this.state.panel.hidden = this.storageService.getBoolean(Storage.PANEL_HIDDEN, StorageScope.WORKSPACE, true);
|
||||
|
||||
// Panel position
|
||||
this.updatePanelPosition();
|
||||
@@ -852,7 +770,7 @@ export class Workbench extends Disposable implements IWorkbenchLayoutService {
|
||||
if (!this.state.panel.hidden) {
|
||||
const panelRegistry = Registry.as<PanelRegistry>(PanelExtensions.Panels);
|
||||
|
||||
let panelToRestore = storageService.get(PanelPart.activePanelSettingsKey, StorageScope.WORKSPACE, panelRegistry.getDefaultPanelId());
|
||||
let panelToRestore = this.storageService.get(PanelPart.activePanelSettingsKey, StorageScope.WORKSPACE, panelRegistry.getDefaultPanelId());
|
||||
if (!panelRegistry.hasPanel(panelToRestore)) {
|
||||
panelToRestore = panelRegistry.getDefaultPanelId(); // fallback to default if panel is unknown
|
||||
}
|
||||
@@ -865,21 +783,21 @@ export class Workbench extends Disposable implements IWorkbenchLayoutService {
|
||||
}
|
||||
|
||||
// Statusbar visibility
|
||||
this.state.statusBar.hidden = !configurationService.getValue<string>(Settings.STATUSBAR_VISIBLE);
|
||||
this.state.statusBar.hidden = !this.configurationService.getValue<string>(Settings.STATUSBAR_VISIBLE);
|
||||
|
||||
// Zen mode enablement
|
||||
this.state.zenMode.restore = storageService.getBoolean(Storage.ZEN_MODE_ENABLED, StorageScope.WORKSPACE, false) && configurationService.getValue(Settings.ZEN_MODE_RESTORE);
|
||||
this.state.zenMode.restore = this.storageService.getBoolean(Storage.ZEN_MODE_ENABLED, StorageScope.WORKSPACE, false) && this.configurationService.getValue(Settings.ZEN_MODE_RESTORE);
|
||||
}
|
||||
|
||||
private resolveEditorsToOpen(accessor: ServicesAccessor): Promise<IResourceEditor[]> | IResourceEditor[] {
|
||||
const configuration = accessor.get(IWindowService).getConfiguration();
|
||||
const configurationService = accessor.get(IConfigurationService);
|
||||
const contextService = accessor.get(IWorkspaceContextService);
|
||||
const editorGroupService = accessor.get(IEditorGroupsService);
|
||||
const backupFileService = accessor.get(IBackupFileService);
|
||||
private resolveEditorsToOpen(): Promise<IResourceEditor[]> | IResourceEditor[] {
|
||||
const configuration = this.windowService.getConfiguration();
|
||||
const hasInitialFilesToOpen = this.hasInitialFilesToOpen();
|
||||
|
||||
// Only restore editors if we are not instructed to open files initially
|
||||
this.state.editor.restoreEditors = !hasInitialFilesToOpen;
|
||||
|
||||
// Files to open, diff or create
|
||||
if (this.options.hasInitialFilesToOpen) {
|
||||
if (hasInitialFilesToOpen) {
|
||||
|
||||
// Files to diff is exclusive
|
||||
const filesToDiff = this.toInputs(configuration.filesToDiff, false);
|
||||
@@ -900,13 +818,13 @@ export class Workbench extends Disposable implements IWorkbenchLayoutService {
|
||||
}
|
||||
|
||||
// Empty workbench
|
||||
else if (contextService.getWorkbenchState() === WorkbenchState.EMPTY && configurationService.inspect('workbench.startupEditor').value === 'newUntitledFile') {
|
||||
const isEmpty = editorGroupService.count === 1 && editorGroupService.activeGroup.count === 0;
|
||||
else if (this.contextService.getWorkbenchState() === WorkbenchState.EMPTY && this.configurationService.inspect('workbench.startupEditor').value === 'newUntitledFile') {
|
||||
const isEmpty = this.editorGroupService.count === 1 && this.editorGroupService.activeGroup.count === 0;
|
||||
if (!isEmpty) {
|
||||
return []; // do not open any empty untitled file if we restored editors from previous session
|
||||
}
|
||||
|
||||
return backupFileService.hasBackups().then(hasBackups => {
|
||||
return this.backupFileService.hasBackups().then(hasBackups => {
|
||||
if (hasBackups) {
|
||||
return []; // do not open any empty untitled file if we have backups to restore
|
||||
}
|
||||
@@ -918,6 +836,15 @@ export class Workbench extends Disposable implements IWorkbenchLayoutService {
|
||||
return [];
|
||||
}
|
||||
|
||||
private hasInitialFilesToOpen(): boolean {
|
||||
const configuration = this.windowService.getConfiguration();
|
||||
|
||||
return !!(
|
||||
(configuration.filesToCreate && configuration.filesToCreate.length > 0) ||
|
||||
(configuration.filesToOpen && configuration.filesToOpen.length > 0) ||
|
||||
(configuration.filesToDiff && configuration.filesToDiff.length > 0));
|
||||
}
|
||||
|
||||
private toInputs(paths: IPath[] | undefined, isNew: boolean): Array<IResourceInput | IUntitledResourceInput> {
|
||||
if (!paths || !paths.length) {
|
||||
return [];
|
||||
@@ -950,8 +877,12 @@ export class Workbench extends Disposable implements IWorkbenchLayoutService {
|
||||
this.state.panel.position = (panelPosition === 'right') ? Position.RIGHT : Position.BOTTOM;
|
||||
}
|
||||
|
||||
registerPart(part: Part): void {
|
||||
this.parts.set(part.getId(), part);
|
||||
}
|
||||
|
||||
isRestored(): boolean {
|
||||
return this.restored;
|
||||
return this.lifecycleService.phase >= LifecyclePhase.Restored;
|
||||
}
|
||||
|
||||
hasFocus(part: Parts): boolean {
|
||||
@@ -1145,7 +1076,7 @@ export class Workbench extends Disposable implements IWorkbenchLayoutService {
|
||||
}
|
||||
}
|
||||
|
||||
private createWorkbenchLayout(): void {
|
||||
private createWorkbenchLayout(instantiationService: IInstantiationService): void {
|
||||
const titleBar = this.parts.get(Parts.TITLEBAR_PART);
|
||||
const editorPart = this.parts.get(Parts.EDITOR_PART);
|
||||
const activityBar = this.parts.get(Parts.ACTIVITYBAR_PART);
|
||||
@@ -1167,7 +1098,7 @@ export class Workbench extends Disposable implements IWorkbenchLayoutService {
|
||||
|
||||
this.workbench.prepend(this.workbenchGrid.element);
|
||||
} else {
|
||||
this.workbenchGrid = this.instantiationService.createInstance(
|
||||
this.workbenchGrid = instantiationService.createInstance(
|
||||
WorkbenchLegacyLayout,
|
||||
this.parent,
|
||||
this.workbench,
|
||||
@@ -1590,5 +1521,11 @@ export class Workbench extends Disposable implements IWorkbenchLayoutService {
|
||||
}
|
||||
}
|
||||
|
||||
dispose(): void {
|
||||
super.dispose();
|
||||
|
||||
this.disposed = true;
|
||||
}
|
||||
|
||||
//#endregion
|
||||
}
|
||||
|
||||
@@ -33,11 +33,11 @@ import { IWindowService } from 'vs/platform/windows/common/windows';
|
||||
import { URLService } from 'vs/platform/url/common/urlService';
|
||||
import { URI } from 'vs/base/common/uri';
|
||||
import { TestConfigurationService } from 'vs/platform/configuration/test/common/testConfigurationService';
|
||||
import { ExtensionManagementServerService } from 'vs/workbench/services/extensions/node/extensionManagementServerService';
|
||||
import { ExtensionManagementServerService } from 'vs/workbench/services/extensions/electron-browser/extensionManagementServerService';
|
||||
import { IRemoteAgentService } from 'vs/workbench/services/remote/node/remoteAgentService';
|
||||
import { RemoteAgentService } from 'vs/workbench/services/remote/electron-browser/remoteAgentServiceImpl';
|
||||
import { ExtensionIdentifier, IExtensionContributions, ExtensionType } from 'vs/platform/extensions/common/extensions';
|
||||
import { ISharedProcessService } from 'vs/platform/sharedProcess/node/sharedProcessService';
|
||||
import { ISharedProcessService } from 'vs/platform/ipc/electron-browser/sharedProcessService';
|
||||
|
||||
suite('ExtensionsActions Test', () => {
|
||||
|
||||
|
||||
+1
-1
@@ -48,7 +48,7 @@ import { IExperimentService } from 'vs/workbench/contrib/experiments/node/experi
|
||||
import { TestExperimentService } from 'vs/workbench/contrib/experiments/test/electron-browser/experimentService.test';
|
||||
import { IStorageService, StorageScope } from 'vs/platform/storage/common/storage';
|
||||
import { ExtensionType } from 'vs/platform/extensions/common/extensions';
|
||||
import { ISharedProcessService } from 'vs/platform/sharedProcess/node/sharedProcessService';
|
||||
import { ISharedProcessService } from 'vs/platform/ipc/electron-browser/sharedProcessService';
|
||||
|
||||
const mockExtensionGallery: IGalleryExtension[] = [
|
||||
aGalleryExtension('MockExtension1', {
|
||||
|
||||
@@ -37,9 +37,9 @@ import { SinonStub } from 'sinon';
|
||||
import { IExperimentService, ExperimentService, ExperimentState, ExperimentActionType } from 'vs/workbench/contrib/experiments/node/experimentService';
|
||||
import { IRemoteAgentService } from 'vs/workbench/services/remote/node/remoteAgentService';
|
||||
import { RemoteAgentService } from 'vs/workbench/services/remote/electron-browser/remoteAgentServiceImpl';
|
||||
import { ExtensionManagementServerService } from 'vs/workbench/services/extensions/node/extensionManagementServerService';
|
||||
import { ExtensionManagementServerService } from 'vs/workbench/services/extensions/electron-browser/extensionManagementServerService';
|
||||
import { ExtensionIdentifier, ExtensionType } from 'vs/platform/extensions/common/extensions';
|
||||
import { ISharedProcessService } from 'vs/platform/sharedProcess/node/sharedProcessService';
|
||||
import { ISharedProcessService } from 'vs/platform/ipc/electron-browser/sharedProcessService';
|
||||
|
||||
|
||||
suite('ExtensionsListView Tests', () => {
|
||||
|
||||
+2
-2
@@ -37,10 +37,10 @@ import { URLService } from 'vs/platform/url/common/urlService';
|
||||
import { URI } from 'vs/base/common/uri';
|
||||
import { CancellationToken } from 'vs/base/common/cancellation';
|
||||
import { ExtensionType } from 'vs/platform/extensions/common/extensions';
|
||||
import { ExtensionManagementServerService } from 'vs/workbench/services/extensions/node/extensionManagementServerService';
|
||||
import { ExtensionManagementServerService } from 'vs/workbench/services/extensions/electron-browser/extensionManagementServerService';
|
||||
import { IRemoteAgentService } from 'vs/workbench/services/remote/node/remoteAgentService';
|
||||
import { RemoteAgentService } from 'vs/workbench/services/remote/electron-browser/remoteAgentServiceImpl';
|
||||
import { ISharedProcessService } from 'vs/platform/sharedProcess/node/sharedProcessService';
|
||||
import { ISharedProcessService } from 'vs/platform/ipc/electron-browser/sharedProcessService';
|
||||
|
||||
suite('ExtensionsWorkbenchServiceTest', () => {
|
||||
|
||||
|
||||
@@ -7,7 +7,7 @@ import * as fs from 'fs';
|
||||
import * as gracefulFs from 'graceful-fs';
|
||||
import { createHash } from 'crypto';
|
||||
import { importEntries, mark } from 'vs/base/common/performance';
|
||||
import { Workbench, IWorkbenchOptions } from 'vs/workbench/browser/workbench';
|
||||
import { Workbench } from 'vs/workbench/browser/workbench';
|
||||
import { ElectronWindow } from 'vs/workbench/electron-browser/window';
|
||||
import { setZoomLevel, setZoomFactor, setFullscreen } from 'vs/base/browser/browser';
|
||||
import { domContentLoaded, addDisposableListener, EventType, scheduleAtNextAnimationFrame } from 'vs/base/browser/dom';
|
||||
@@ -20,27 +20,15 @@ import { ServiceCollection } from 'vs/platform/instantiation/common/serviceColle
|
||||
import { stat } from 'vs/base/node/pfs';
|
||||
import { EnvironmentService } from 'vs/platform/environment/node/environmentService';
|
||||
import { KeyboardMapperFactory } from 'vs/workbench/services/keybinding/electron-browser/keybindingService';
|
||||
import { IWindowConfiguration, IWindowsService, IWindowService } from 'vs/platform/windows/common/windows';
|
||||
import { IWindowConfiguration, IWindowService } from 'vs/platform/windows/common/windows';
|
||||
import { WindowService } from 'vs/platform/windows/electron-browser/windowService';
|
||||
import { WindowsChannelClient } from 'vs/platform/windows/node/windowsIpc';
|
||||
import { IEnvironmentService } from 'vs/platform/environment/common/environment';
|
||||
import { Client as ElectronIPCClient } from 'vs/base/parts/ipc/electron-browser/ipc.electron-browser';
|
||||
import { webFrame } from 'electron';
|
||||
import { UpdateChannelClient } from 'vs/platform/update/node/updateIpc';
|
||||
import { IUpdateService } from 'vs/platform/update/common/update';
|
||||
import { URLHandlerChannel, URLServiceChannelClient } from 'vs/platform/url/node/urlIpc';
|
||||
import { IURLService } from 'vs/platform/url/common/url';
|
||||
import { WorkspacesChannelClient } from 'vs/platform/workspaces/node/workspacesIpc';
|
||||
import { IWorkspacesService, ISingleFolderWorkspaceIdentifier, IWorkspaceInitializationPayload, IMultiFolderWorkspaceInitializationPayload, IEmptyWorkspaceInitializationPayload, ISingleFolderWorkspaceInitializationPayload, reviveWorkspaceIdentifier } from 'vs/platform/workspaces/common/workspaces';
|
||||
import { ISingleFolderWorkspaceIdentifier, IWorkspaceInitializationPayload, IMultiFolderWorkspaceInitializationPayload, IEmptyWorkspaceInitializationPayload, ISingleFolderWorkspaceInitializationPayload, reviveWorkspaceIdentifier } from 'vs/platform/workspaces/common/workspaces';
|
||||
import { createSpdLogService } from 'vs/platform/log/node/spdlogService';
|
||||
import { ConsoleLogService, MultiplexLogService, ILogService } from 'vs/platform/log/common/log';
|
||||
import { StorageService } from 'vs/platform/storage/node/storageService';
|
||||
import { IssueChannelClient } from 'vs/platform/issue/node/issueIpc';
|
||||
import { IIssueService } from 'vs/platform/issue/common/issue';
|
||||
import { LogLevelSetterChannelClient, FollowerLogService } from 'vs/platform/log/node/logIpc';
|
||||
import { RelayURLService } from 'vs/platform/url/common/urlService';
|
||||
import { MenubarChannelClient } from 'vs/platform/menubar/node/menubarIpc';
|
||||
import { IMenubarService } from 'vs/platform/menubar/common/menubar';
|
||||
import { Schemas } from 'vs/base/common/network';
|
||||
import { sanitizeFilePath } from 'vs/base/node/extfs';
|
||||
import { basename } from 'vs/base/common/path';
|
||||
@@ -48,9 +36,9 @@ import { GlobalStorageDatabaseChannelClient } from 'vs/platform/storage/node/sto
|
||||
import { IWorkspaceContextService } from 'vs/platform/workspace/common/workspace';
|
||||
import { IConfigurationService } from 'vs/platform/configuration/common/configuration';
|
||||
import { IStorageService } from 'vs/platform/storage/common/storage';
|
||||
import { InstantiationService } from 'vs/platform/instantiation/common/instantiationService';
|
||||
import { Disposable } from 'vs/base/common/lifecycle';
|
||||
import { registerWindowDriver } from 'vs/platform/driver/electron-browser/driver';
|
||||
import { IMainProcessService, MainProcessService } from 'vs/platform/ipc/electron-browser/mainProcessService';
|
||||
|
||||
class CodeRendererMain extends Disposable {
|
||||
|
||||
@@ -102,47 +90,31 @@ class CodeRendererMain extends Disposable {
|
||||
});
|
||||
}
|
||||
|
||||
private hasInitialFilesToOpen(): boolean {
|
||||
return !!(
|
||||
(this.configuration.filesToCreate && this.configuration.filesToCreate.length > 0) ||
|
||||
(this.configuration.filesToOpen && this.configuration.filesToOpen.length > 0) ||
|
||||
(this.configuration.filesToDiff && this.configuration.filesToDiff.length > 0));
|
||||
}
|
||||
|
||||
open(): Promise<void> {
|
||||
const electronMainClient = this._register(new ElectronIPCClient(`window:${this.configuration.windowId}`));
|
||||
|
||||
return this.initServices(electronMainClient).then(services => {
|
||||
return this.initServices().then(services => {
|
||||
|
||||
return domContentLoaded().then(() => {
|
||||
mark('willStartWorkbench');
|
||||
|
||||
const instantiationService = new InstantiationService(services, true);
|
||||
|
||||
// Create Workbench
|
||||
this.workbench = instantiationService.createInstance(
|
||||
Workbench,
|
||||
document.body,
|
||||
{ hasInitialFilesToOpen: this.hasInitialFilesToOpen() } as IWorkbenchOptions,
|
||||
services
|
||||
);
|
||||
this.workbench = new Workbench(document.body, services.serviceCollection, services.logService);
|
||||
|
||||
// Layout
|
||||
this._register(addDisposableListener(window, EventType.RESIZE, e => this.onWindowResize(e, true)));
|
||||
|
||||
// Workbench Lifecycle
|
||||
this._register(this.workbench.onShutdown(() => this.dispose()));
|
||||
this._register(this.workbench.onWillShutdown(event => event.join((services.get(IStorageService) as StorageService).close())));
|
||||
this._register(this.workbench.onWillShutdown(event => event.join(services.storageService.close())));
|
||||
|
||||
// Startup
|
||||
this.workbench.startup();
|
||||
const instantiationService = this.workbench.startup();
|
||||
|
||||
// Window
|
||||
this._register(instantiationService.createInstance(ElectronWindow));
|
||||
|
||||
// Driver
|
||||
if (this.configuration.driver) {
|
||||
registerWindowDriver(electronMainClient, this.configuration.windowId, instantiationService).then(disposable => this._register(disposable));
|
||||
instantiationService.invokeFunction(accessor => registerWindowDriver(accessor).then(disposable => this._register(disposable)));
|
||||
}
|
||||
|
||||
// Config Exporter
|
||||
@@ -151,12 +123,12 @@ class CodeRendererMain extends Disposable {
|
||||
}
|
||||
|
||||
// Logging
|
||||
instantiationService.invokeFunction(accessor => accessor.get(ILogService).trace('workbench configuration', JSON.stringify(this.configuration)));
|
||||
services.logService.trace('workbench configuration', JSON.stringify(this.configuration));
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
private onWindowResize(e: any, retry: boolean): void {
|
||||
private onWindowResize(e: Event, retry: boolean): void {
|
||||
if (e.target === window) {
|
||||
if (window.document && window.document.body && window.document.body.clientWidth === 0) {
|
||||
// TODO@Ben this is an electron issue on macOS when simple fullscreen is enabled
|
||||
@@ -174,68 +146,44 @@ class CodeRendererMain extends Disposable {
|
||||
}
|
||||
}
|
||||
|
||||
private initServices(electronMainClient: ElectronIPCClient): Promise<ServiceCollection> {
|
||||
private initServices(): Promise<{ serviceCollection: ServiceCollection, logService: ILogService, storageService: StorageService }> {
|
||||
const serviceCollection = new ServiceCollection();
|
||||
|
||||
// Windows Service
|
||||
const windowsChannel = electronMainClient.getChannel('windows');
|
||||
serviceCollection.set(IWindowsService, new WindowsChannelClient(windowsChannel));
|
||||
// Main Process
|
||||
const mainProcessService = this._register(new MainProcessService(this.configuration.windowId));
|
||||
serviceCollection.set(IMainProcessService, mainProcessService);
|
||||
|
||||
// Window
|
||||
serviceCollection.set(IWindowService, new SyncDescriptor(WindowService, [this.configuration]));
|
||||
|
||||
// Update Service
|
||||
const updateChannel = electronMainClient.getChannel('update');
|
||||
serviceCollection.set(IUpdateService, new SyncDescriptor(UpdateChannelClient, [updateChannel]));
|
||||
|
||||
// URL Service
|
||||
const urlChannel = electronMainClient.getChannel('url');
|
||||
const mainUrlService = new URLServiceChannelClient(urlChannel);
|
||||
const urlService = new RelayURLService(mainUrlService);
|
||||
serviceCollection.set(IURLService, urlService);
|
||||
|
||||
// URLHandler Service
|
||||
const urlHandlerChannel = new URLHandlerChannel(urlService);
|
||||
electronMainClient.registerChannel('urlHandler', urlHandlerChannel);
|
||||
|
||||
// Issue Service
|
||||
const issueChannel = electronMainClient.getChannel('issue');
|
||||
serviceCollection.set(IIssueService, new SyncDescriptor(IssueChannelClient, [issueChannel]));
|
||||
|
||||
// Menubar Service
|
||||
const menubarChannel = electronMainClient.getChannel('menubar');
|
||||
serviceCollection.set(IMenubarService, new SyncDescriptor(MenubarChannelClient, [menubarChannel]));
|
||||
|
||||
// Workspaces Service
|
||||
const workspacesChannel = electronMainClient.getChannel('workspaces');
|
||||
serviceCollection.set(IWorkspacesService, new WorkspacesChannelClient(workspacesChannel));
|
||||
|
||||
// Environment
|
||||
const environmentService = new EnvironmentService(this.configuration, this.configuration.execPath);
|
||||
serviceCollection.set(IEnvironmentService, environmentService);
|
||||
|
||||
// Log
|
||||
const logService = this._register(this.createLogService(electronMainClient, environmentService));
|
||||
const logService = this._register(this.createLogService(mainProcessService, environmentService));
|
||||
serviceCollection.set(ILogService, logService);
|
||||
|
||||
// Resolve a workspace payload that we can get the workspace ID from
|
||||
return this.resolveWorkspaceInitializationPayload(environmentService).then(payload => {
|
||||
return this.resolveWorkspaceInitializationPayload(environmentService).then(payload => Promise.all([
|
||||
this.createWorkspaceService(payload, environmentService, logService).then(service => {
|
||||
|
||||
return Promise.all([
|
||||
// Workspace
|
||||
serviceCollection.set(IWorkspaceContextService, service);
|
||||
|
||||
// Create and initialize workspace/configuration service
|
||||
this.createWorkspaceService(payload, environmentService, logService),
|
||||
// Configuration
|
||||
serviceCollection.set(IConfigurationService, service);
|
||||
|
||||
// Create and initialize storage service
|
||||
this.createStorageService(payload, environmentService, logService, electronMainClient)
|
||||
]).then(services => {
|
||||
serviceCollection.set(IWorkspaceContextService, services[0]);
|
||||
serviceCollection.set(IConfigurationService, services[0]);
|
||||
serviceCollection.set(IStorageService, services[1]);
|
||||
return service;
|
||||
}),
|
||||
|
||||
return serviceCollection;
|
||||
});
|
||||
});
|
||||
this.createStorageService(payload, environmentService, logService, mainProcessService).then(service => {
|
||||
|
||||
// Storage
|
||||
serviceCollection.set(IStorageService, service);
|
||||
|
||||
return service;
|
||||
})
|
||||
]).then(services => ({ serviceCollection, logService, storageService: services[1] })));
|
||||
}
|
||||
|
||||
private resolveWorkspaceInitializationPayload(environmentService: EnvironmentService): Promise<IWorkspaceInitializationPayload> {
|
||||
@@ -319,8 +267,8 @@ class CodeRendererMain extends Disposable {
|
||||
});
|
||||
}
|
||||
|
||||
private createStorageService(payload: IWorkspaceInitializationPayload, environmentService: IEnvironmentService, logService: ILogService, electronMainClient: ElectronIPCClient): Promise<StorageService> {
|
||||
const globalStorageDatabase = new GlobalStorageDatabaseChannelClient(electronMainClient.getChannel('storage'));
|
||||
private createStorageService(payload: IWorkspaceInitializationPayload, environmentService: IEnvironmentService, logService: ILogService, mainProcessService: IMainProcessService): Promise<StorageService> {
|
||||
const globalStorageDatabase = new GlobalStorageDatabaseChannelClient(mainProcessService.getChannel('storage'));
|
||||
const storageService = new StorageService(globalStorageDatabase, logService, environmentService);
|
||||
|
||||
return storageService.initialize(payload).then(() => storageService, error => {
|
||||
@@ -331,11 +279,11 @@ class CodeRendererMain extends Disposable {
|
||||
});
|
||||
}
|
||||
|
||||
private createLogService(electronMainClient: ElectronIPCClient, environmentService: IEnvironmentService): ILogService {
|
||||
private createLogService(mainProcessService: IMainProcessService, environmentService: IEnvironmentService): ILogService {
|
||||
const spdlogService = createSpdLogService(`renderer${this.configuration.windowId}`, this.configuration.logLevel, environmentService.logsPath);
|
||||
const consoleLogService = new ConsoleLogService(this.configuration.logLevel);
|
||||
const logService = new MultiplexLogService([consoleLogService, spdlogService]);
|
||||
const logLevelClient = new LogLevelSetterChannelClient(electronMainClient.getChannel('loglevel'));
|
||||
const logLevelClient = new LogLevelSetterChannelClient(mainProcessService.getChannel('loglevel'));
|
||||
|
||||
return new FollowerLogService(logLevelClient, logService);
|
||||
}
|
||||
|
||||
@@ -22,7 +22,7 @@ import * as browser from 'vs/base/browser/browser';
|
||||
import { ICommandService } from 'vs/platform/commands/common/commands';
|
||||
import { IResourceInput } from 'vs/platform/editor/common/editor';
|
||||
import { KeyboardMapperFactory } from 'vs/workbench/services/keybinding/electron-browser/keybindingService';
|
||||
import { ipcRenderer as ipc, webFrame, crashReporter } from 'electron';
|
||||
import { ipcRenderer as ipc, webFrame, crashReporter, Event } from 'electron';
|
||||
import { IWorkspaceEditingService } from 'vs/workbench/services/workspace/common/workspaceEditing';
|
||||
import { IMenuService, MenuId, IMenu, MenuItemAction, ICommandAction } from 'vs/platform/actions/common/actions';
|
||||
import { IContextKeyService } from 'vs/platform/contextkey/common/contextkey';
|
||||
@@ -57,8 +57,6 @@ const TextInputActions: IAction[] = [
|
||||
|
||||
export class ElectronWindow extends Disposable {
|
||||
|
||||
private static readonly closeWhenEmptyConfigurationKey = 'window.closeWhenEmpty';
|
||||
|
||||
private touchBarMenu?: IMenu;
|
||||
private touchBarUpdater: RunOnceScheduler;
|
||||
private touchBarDisposables: IDisposable[];
|
||||
@@ -116,7 +114,7 @@ export class ElectronWindow extends Disposable {
|
||||
});
|
||||
|
||||
// Support runAction event
|
||||
ipc.on('vscode:runAction', (event: any, request: IRunActionInWindowRequest) => {
|
||||
ipc.on('vscode:runAction', (event: Event, request: IRunActionInWindowRequest) => {
|
||||
const args: any[] = request.args || [];
|
||||
|
||||
// If we run an action from the touchbar, we fill in the currently active resource
|
||||
@@ -147,29 +145,27 @@ export class ElectronWindow extends Disposable {
|
||||
});
|
||||
|
||||
// Support runKeybinding event
|
||||
ipc.on('vscode:runKeybinding', (event: any, request: IRunKeybindingInWindowRequest) => {
|
||||
ipc.on('vscode:runKeybinding', (event: Event, request: IRunKeybindingInWindowRequest) => {
|
||||
if (document.activeElement) {
|
||||
this.keybindingService.dispatchByUserSettingsLabel(request.userSettingsLabel, document.activeElement);
|
||||
}
|
||||
});
|
||||
|
||||
// Error reporting from main
|
||||
ipc.on('vscode:reportError', (event: any, error: string) => {
|
||||
ipc.on('vscode:reportError', (event: Event, error: string) => {
|
||||
if (error) {
|
||||
const errorParsed = JSON.parse(error);
|
||||
errorParsed.mainProcess = true;
|
||||
errors.onUnexpectedError(errorParsed);
|
||||
errors.onUnexpectedError(JSON.parse(error));
|
||||
}
|
||||
});
|
||||
|
||||
// Support openFiles event for existing and new files
|
||||
ipc.on('vscode:openFiles', (event: any, request: IOpenFileRequest) => this.onOpenFiles(request));
|
||||
ipc.on('vscode:openFiles', (event: Event, request: IOpenFileRequest) => this.onOpenFiles(request));
|
||||
|
||||
// Support addFolders event if we have a workspace opened
|
||||
ipc.on('vscode:addFolders', (event: any, request: IAddFoldersRequest) => this.onAddFoldersRequest(request));
|
||||
ipc.on('vscode:addFolders', (event: Event, request: IAddFoldersRequest) => this.onAddFoldersRequest(request));
|
||||
|
||||
// Message support
|
||||
ipc.on('vscode:showInfoMessage', (event: any, message: string) => {
|
||||
ipc.on('vscode:showInfoMessage', (event: Event, message: string) => {
|
||||
this.notificationService.info(message);
|
||||
});
|
||||
|
||||
@@ -211,7 +207,7 @@ export class ElectronWindow extends Disposable {
|
||||
});
|
||||
|
||||
// keyboard layout changed event
|
||||
ipc.on('vscode:accessibilitySupportChanged', (event: any, accessibilitySupportEnabled: boolean) => {
|
||||
ipc.on('vscode:accessibilitySupportChanged', (event: Event, accessibilitySupportEnabled: boolean) => {
|
||||
this.accessibilityService.setAccessibilitySupport(accessibilitySupportEnabled ? AccessibilitySupport.Enabled : AccessibilitySupport.Disabled);
|
||||
});
|
||||
|
||||
@@ -247,7 +243,7 @@ export class ElectronWindow extends Disposable {
|
||||
// or setting is disabled. Also enabled when running with --wait from the command line.
|
||||
const visibleEditors = this.editorService.visibleControls;
|
||||
if (visibleEditors.length === 0 && this.contextService.getWorkbenchState() === WorkbenchState.EMPTY && !this.environmentService.isExtensionDevelopment) {
|
||||
const closeWhenEmpty = this.configurationService.getValue<boolean>(ElectronWindow.closeWhenEmptyConfigurationKey);
|
||||
const closeWhenEmpty = this.configurationService.getValue<boolean>('window.closeWhenEmpty');
|
||||
if (closeWhenEmpty || this.environmentService.args.wait) {
|
||||
this.closeEmptyWindowScheduler.schedule();
|
||||
}
|
||||
@@ -316,7 +312,7 @@ export class ElectronWindow extends Disposable {
|
||||
|
||||
// Handle window.open() calls
|
||||
const $this = this;
|
||||
(<any>window).open = function (url: string, target: string, features: string, replace: boolean): any {
|
||||
window.open = function (url: string, target: string, features: string, replace: boolean): Window | null {
|
||||
$this.windowsService.openExternal(url);
|
||||
|
||||
return null;
|
||||
|
||||
@@ -25,6 +25,7 @@ import { IEnvironmentService } from 'vs/platform/environment/common/environment'
|
||||
import { ContextMenuService as HTMLContextMenuService } from 'vs/platform/contextview/browser/contextMenuService';
|
||||
import { IThemeService } from 'vs/platform/theme/common/themeService';
|
||||
import { registerSingleton } from 'vs/platform/instantiation/common/extensions';
|
||||
import { ILayoutService } from 'vs/platform/layout/browser/layoutService';
|
||||
|
||||
export class ContextMenuService extends Disposable implements IContextMenuService {
|
||||
|
||||
@@ -41,13 +42,14 @@ export class ContextMenuService extends Disposable implements IContextMenuServic
|
||||
@IConfigurationService configurationService: IConfigurationService,
|
||||
@IEnvironmentService environmentService: IEnvironmentService,
|
||||
@IContextViewService contextViewService: IContextViewService,
|
||||
@IThemeService themeService: IThemeService
|
||||
@IThemeService themeService: IThemeService,
|
||||
@ILayoutService layoutService: ILayoutService
|
||||
) {
|
||||
super();
|
||||
|
||||
// Custom context menu: Linux/Windows if custom title is enabled
|
||||
if (!isMacintosh && getTitleBarStyle(configurationService, environmentService) === 'custom') {
|
||||
this.impl = new HTMLContextMenuService(null, telemetryService, notificationService, contextViewService, keybindingService, themeService);
|
||||
this.impl = new HTMLContextMenuService(layoutService, telemetryService, notificationService, contextViewService, keybindingService, themeService);
|
||||
}
|
||||
|
||||
// Native context menu: otherwise
|
||||
|
||||
@@ -23,7 +23,7 @@ import { WORKSPACE_EXTENSION } from 'vs/platform/workspaces/common/workspaces';
|
||||
import { REMOTE_HOST_SCHEME } from 'vs/platform/remote/common/remoteHosts';
|
||||
import { IConfigurationService } from 'vs/platform/configuration/common/configuration';
|
||||
import { registerSingleton } from 'vs/platform/instantiation/common/extensions';
|
||||
import { ISharedProcessService } from 'vs/platform/sharedProcess/node/sharedProcessService';
|
||||
import { ISharedProcessService } from 'vs/platform/ipc/electron-browser/sharedProcessService';
|
||||
import { DialogChannel } from 'vs/platform/dialogs/node/dialogIpc';
|
||||
|
||||
interface IMassagedMessageBoxOptions {
|
||||
|
||||
+1
-1
@@ -11,7 +11,7 @@ import { ExtensionManagementChannelClient } from 'vs/platform/extensionManagemen
|
||||
import { IRemoteAgentService } from 'vs/workbench/services/remote/node/remoteAgentService';
|
||||
import { REMOTE_HOST_SCHEME } from 'vs/platform/remote/common/remoteHosts';
|
||||
import { IChannel } from 'vs/base/parts/ipc/node/ipc';
|
||||
import { ISharedProcessService } from 'vs/platform/sharedProcess/node/sharedProcessService';
|
||||
import { ISharedProcessService } from 'vs/platform/ipc/electron-browser/sharedProcessService';
|
||||
import { registerSingleton } from 'vs/platform/instantiation/common/extensions';
|
||||
|
||||
const localExtensionManagementServerAuthority: string = 'vscode-local';
|
||||
@@ -4,6 +4,8 @@
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
|
||||
import { createDecorator } from 'vs/platform/instantiation/common/instantiation';
|
||||
import { registerSingleton } from 'vs/platform/instantiation/common/extensions';
|
||||
import { computeSHA1Hash } from 'vs/base/common/hash';
|
||||
|
||||
export const IHashService = createDecorator<IHashService>('hashService');
|
||||
|
||||
@@ -14,4 +16,15 @@ export interface IHashService {
|
||||
* Produce a SHA1 hash of the provided content.
|
||||
*/
|
||||
createSHA1(content: string): string;
|
||||
}
|
||||
}
|
||||
|
||||
export class HashService implements IHashService {
|
||||
|
||||
_serviceBrand: any;
|
||||
|
||||
createSHA1(content: string): string {
|
||||
return computeSHA1Hash(content);
|
||||
}
|
||||
}
|
||||
|
||||
registerSingleton(IHashService, HashService, true);
|
||||
@@ -81,7 +81,7 @@ import { Part } from 'vs/workbench/browser/part';
|
||||
import { IPanelService } from 'vs/workbench/services/panel/common/panelService';
|
||||
import { IPanel } from 'vs/workbench/common/panel';
|
||||
import { IBadge } from 'vs/workbench/services/activity/common/activity';
|
||||
import { ISharedProcessService } from 'vs/platform/sharedProcess/node/sharedProcessService';
|
||||
import { ISharedProcessService } from 'vs/platform/ipc/electron-browser/sharedProcessService';
|
||||
|
||||
export function createFileInput(instantiationService: IInstantiationService, resource: URI): FileEditorInput {
|
||||
return instantiationService.createInstance(FileEditorInput, resource, undefined);
|
||||
|
||||
@@ -22,7 +22,7 @@ import 'vs/workbench/electron-browser/main';
|
||||
import 'vs/workbench/browser/actions/layoutActions';
|
||||
import 'vs/workbench/browser/actions/listCommands';
|
||||
import 'vs/workbench/browser/actions/navigationActions';
|
||||
import 'vs/workbench/browser/parts/quickopen/quickopenActions';
|
||||
import 'vs/workbench/browser/parts/quickopen/quickOpenActions';
|
||||
import 'vs/workbench/browser/parts/quickinput/quickInputActions';
|
||||
|
||||
//#endregion
|
||||
@@ -72,12 +72,26 @@ import { RequestService } from 'vs/platform/request/electron-browser/requestServ
|
||||
import { LifecycleService } from 'vs/platform/lifecycle/electron-browser/lifecycleService';
|
||||
import { ILifecycleService } from 'vs/platform/lifecycle/common/lifecycle';
|
||||
import { ILocalizationsService } from 'vs/platform/localizations/common/localizations';
|
||||
import { LocalizationsChannelClient } from 'vs/platform/localizations/node/localizationsIpc';
|
||||
import { ISharedProcessService, SharedProcessService } from 'vs/platform/sharedProcess/node/sharedProcessService';
|
||||
import { LocalizationsService } from 'vs/platform/localizations/electron-browser/localizationsService';
|
||||
import { ISharedProcessService, SharedProcessService } from 'vs/platform/ipc/electron-browser/sharedProcessService';
|
||||
import { RemoteAuthorityResolverService } from 'vs/platform/remote/electron-browser/remoteAuthorityResolverService';
|
||||
import { IRemoteAuthorityResolverService } from 'vs/platform/remote/common/remoteAuthorityResolver';
|
||||
import { ITelemetryService } from 'vs/platform/telemetry/common/telemetry';
|
||||
import { TelemetryService } from 'vs/platform/telemetry/node/telemetryService';
|
||||
import { TelemetryService } from 'vs/platform/telemetry/electron-browser/telemetryService';
|
||||
import { IProductService } from 'vs/platform/product/common/product';
|
||||
import { ProductService } from 'vs/platform/product/node/productService';
|
||||
import { IWindowsService } from 'vs/platform/windows/common/windows';
|
||||
import { WindowsService } from 'vs/platform/windows/electron-browser/windowsService';
|
||||
import { IUpdateService } from 'vs/platform/update/common/update';
|
||||
import { UpdateService } from 'vs/platform/update/electron-browser/updateService';
|
||||
import { IIssueService } from 'vs/platform/issue/common/issue';
|
||||
import { IssueService } from 'vs/platform/issue/electron-browser/issueService';
|
||||
import { IWorkspacesService } from 'vs/platform/workspaces/common/workspaces';
|
||||
import { WorkspacesService } from 'vs/platform/workspaces/electron-browser/workspacesService';
|
||||
import { IMenubarService } from 'vs/platform/menubar/common/menubar';
|
||||
import { MenubarService } from 'vs/platform/menubar/electron-browser/menubarService';
|
||||
import { IURLService } from 'vs/platform/url/common/url';
|
||||
import { RelayURLService } from 'vs/platform/url/electron-browser/urlService';
|
||||
|
||||
import 'vs/workbench/services/bulkEdit/browser/bulkEditService';
|
||||
import 'vs/workbench/services/integrity/node/integrityService';
|
||||
@@ -114,7 +128,7 @@ import 'vs/workbench/services/extensions/electron-browser/extensionService';
|
||||
import 'vs/workbench/services/contextmenu/electron-browser/contextmenuService';
|
||||
import 'vs/workbench/services/extensionManagement/node/multiExtensionManagement';
|
||||
import 'vs/workbench/services/label/common/labelService';
|
||||
import 'vs/workbench/services/extensions/node/extensionManagementServerService';
|
||||
import 'vs/workbench/services/extensions/electron-browser/extensionManagementServerService';
|
||||
import 'vs/workbench/services/remote/electron-browser/remoteAgentServiceImpl';
|
||||
import 'vs/workbench/services/notification/common/notificationService';
|
||||
|
||||
@@ -135,11 +149,17 @@ registerSingleton(IContextViewService, ContextViewService, true);
|
||||
registerSingleton(IExtensionGalleryService, ExtensionGalleryService, true);
|
||||
registerSingleton(IRequestService, RequestService, true);
|
||||
registerSingleton(ILifecycleService, LifecycleService);
|
||||
registerSingleton(ILocalizationsService, LocalizationsChannelClient);
|
||||
registerSingleton(ILocalizationsService, LocalizationsService);
|
||||
registerSingleton(ISharedProcessService, SharedProcessService, true);
|
||||
registerSingleton(IRemoteAuthorityResolverService, RemoteAuthorityResolverService, true);
|
||||
registerSingleton(ITelemetryService, TelemetryService);
|
||||
registerSingleton(IProductService, ProductService, true);
|
||||
registerSingleton(IWindowsService, WindowsService);
|
||||
registerSingleton(IUpdateService, UpdateService);
|
||||
registerSingleton(IIssueService, IssueService);
|
||||
registerSingleton(IWorkspacesService, WorkspacesService);
|
||||
registerSingleton(IMenubarService, MenubarService);
|
||||
registerSingleton(IURLService, RelayURLService);
|
||||
|
||||
//#endregion
|
||||
|
||||
@@ -296,7 +316,5 @@ import 'vs/workbench/contrib/codeinset/electron-browser/codeInset.contribution';
|
||||
|
||||
// Issues
|
||||
import 'vs/workbench/contrib/issue/electron-browser/issue.contribution';
|
||||
import { IProductService } from 'vs/platform/product/common/product';
|
||||
import { ProductService } from 'vs/platform/product/node/productService';
|
||||
|
||||
//#endregion
|
||||
|
||||
@@ -0,0 +1,9 @@
|
||||
/*---------------------------------------------------------------------------------------------
|
||||
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||
* Licensed under the MIT License. See License.txt in the project root for license information.
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
|
||||
/* NOTE: THIS FILE WILL BE OVERWRITTEN DURING BUILD TIME, DO NOT EDIT */
|
||||
|
||||
div.monaco.main.css {
|
||||
}
|
||||
@@ -0,0 +1,8 @@
|
||||
/*---------------------------------------------------------------------------------------------
|
||||
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||
* Licensed under the MIT License. See License.txt in the project root for license information.
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
|
||||
// NOTE: THIS FILE WILL BE OVERWRITTEN DURING BUILD TIME, DO NOT EDIT
|
||||
|
||||
define([], {});
|
||||
@@ -0,0 +1,325 @@
|
||||
/*---------------------------------------------------------------------------------------------
|
||||
* Copyright (c) Microsoft Corporation. All rights reserved.
|
||||
* Licensed under the MIT License. See License.txt in the project root for license information.
|
||||
*--------------------------------------------------------------------------------------------*/
|
||||
|
||||
//#region --- workbench/editor core
|
||||
|
||||
import 'vs/editor/editor.all';
|
||||
|
||||
// import 'vs/workbench/api/electron-browser/extensionHost.contribution';
|
||||
|
||||
// import 'vs/workbench/electron-browser/main.contribution';
|
||||
import 'vs/workbench/browser/workbench.contribution';
|
||||
|
||||
import 'vs/workbench/browser/nodeless.main';
|
||||
|
||||
//#endregion
|
||||
|
||||
|
||||
//#region --- workbench actions
|
||||
|
||||
import 'vs/workbench/browser/actions/layoutActions';
|
||||
import 'vs/workbench/browser/actions/listCommands';
|
||||
import 'vs/workbench/browser/actions/navigationActions';
|
||||
import 'vs/workbench/browser/parts/quickopen/quickOpenActions';
|
||||
import 'vs/workbench/browser/parts/quickinput/quickInputActions';
|
||||
|
||||
//#endregion
|
||||
|
||||
|
||||
//#region --- API Extension Points
|
||||
|
||||
import 'vs/workbench/api/common/menusExtensionPoint';
|
||||
import 'vs/workbench/api/common/configurationExtensionPoint';
|
||||
import 'vs/workbench/api/browser/viewsExtensionPoint';
|
||||
|
||||
//#endregion
|
||||
|
||||
|
||||
//#region --- workbench services
|
||||
import { registerSingleton } from 'vs/platform/instantiation/common/extensions';
|
||||
import { IMenuService } from 'vs/platform/actions/common/actions';
|
||||
import { MenuService } from 'vs/platform/actions/common/menuService';
|
||||
import { IListService, ListService } from 'vs/platform/list/browser/listService';
|
||||
import { OpenerService } from 'vs/editor/browser/services/openerService';
|
||||
import { IOpenerService } from 'vs/platform/opener/common/opener';
|
||||
import { IEditorWorkerService } from 'vs/editor/common/services/editorWorkerService';
|
||||
import { EditorWorkerServiceImpl } from 'vs/editor/common/services/editorWorkerServiceImpl';
|
||||
import { MarkerDecorationsService } from 'vs/editor/common/services/markerDecorationsServiceImpl';
|
||||
import { IMarkerDecorationsService } from 'vs/editor/common/services/markersDecorationService';
|
||||
import { IMarkerService } from 'vs/platform/markers/common/markers';
|
||||
import { MarkerService } from 'vs/platform/markers/common/markerService';
|
||||
// import { IDownloadService } from 'vs/platform/download/common/download';
|
||||
// import { DownloadService } from 'vs/platform/download/node/downloadService';
|
||||
// import { IClipboardService } from 'vs/platform/clipboard/common/clipboardService';
|
||||
// import { ClipboardService } from 'vs/platform/clipboard/electron-browser/clipboardService';
|
||||
import { ContextKeyService } from 'vs/platform/contextkey/browser/contextKeyService';
|
||||
import { IContextKeyService } from 'vs/platform/contextkey/common/contextkey';
|
||||
import { IModelService } from 'vs/editor/common/services/modelService';
|
||||
import { ModelServiceImpl } from 'vs/editor/common/services/modelServiceImpl';
|
||||
import { ITextResourceConfigurationService } from 'vs/editor/common/services/resourceConfiguration';
|
||||
import { TextResourceConfigurationService } from 'vs/editor/common/services/resourceConfigurationImpl';
|
||||
import { IAccessibilityService } from 'vs/platform/accessibility/common/accessibility';
|
||||
import { BrowserAccessibilityService } from 'vs/platform/accessibility/common/accessibilityService';
|
||||
import { IExtensionEnablementService } from 'vs/platform/extensionManagement/common/extensionManagement';
|
||||
import { ExtensionEnablementService } from 'vs/platform/extensionManagement/common/extensionEnablementService';
|
||||
import { IContextViewService, IContextMenuService } from 'vs/platform/contextview/browser/contextView';
|
||||
import { ContextMenuService } from 'vs/platform/contextview/browser/contextMenuService';
|
||||
import { ContextViewService } from 'vs/platform/contextview/browser/contextViewService';
|
||||
// import { ExtensionGalleryService } from 'vs/platform/extensionManagement/node/extensionGalleryService';
|
||||
// import { IRequestService } from 'vs/platform/request/node/request';
|
||||
// import { RequestService } from 'vs/platform/request/electron-browser/requestService';
|
||||
// import { LifecycleService } from 'vs/platform/lifecycle/electron-browser/lifecycleService';
|
||||
// import { ILifecycleService } from 'vs/platform/lifecycle/common/lifecycle';
|
||||
// import { ILocalizationsService } from 'vs/platform/localizations/common/localizations';
|
||||
// import { LocalizationsService } from 'vs/platform/localizations/electron-browser/localizationsService';
|
||||
// import { ISharedProcessService, SharedProcessService } from 'vs/platform/ipc/electron-browser/sharedProcessService';
|
||||
// import { RemoteAuthorityResolverService } from 'vs/platform/remote/electron-browser/remoteAuthorityResolverService';
|
||||
// import { IRemoteAuthorityResolverService } from 'vs/platform/remote/common/remoteAuthorityResolver';
|
||||
// import { ITelemetryService } from 'vs/platform/telemetry/common/telemetry';
|
||||
// import { TelemetryService } from 'vs/platform/telemetry/electron-browser/telemetryService';
|
||||
// import { IProductService } from 'vs/platform/product/common/product';
|
||||
// import { ProductService } from 'vs/platform/product/node/productService';
|
||||
// import { IWindowsService } from 'vs/platform/windows/common/windows';
|
||||
// import { WindowsService } from 'vs/platform/windows/electron-browser/windowsService';
|
||||
// import { IUpdateService } from 'vs/platform/update/common/update';
|
||||
// import { UpdateService } from 'vs/platform/update/electron-browser/updateService';
|
||||
// import { IIssueService } from 'vs/platform/issue/common/issue';
|
||||
// import { IssueService } from 'vs/platform/issue/electron-browser/issueService';
|
||||
// import { IWorkspacesService } from 'vs/platform/workspaces/common/workspaces';
|
||||
// import { WorkspacesService } from 'vs/platform/workspaces/electron-browser/workspacesService';
|
||||
// import { IMenubarService } from 'vs/platform/menubar/common/menubar';
|
||||
// import { MenubarService } from 'vs/platform/menubar/electron-browser/menubarService';
|
||||
// import { IURLService } from 'vs/platform/url/common/url';
|
||||
// import { RelayURLService } from 'vs/platform/url/electron-browser/urlService';
|
||||
|
||||
import 'vs/workbench/browser/nodeless.simpleservices';
|
||||
|
||||
import 'vs/workbench/services/bulkEdit/browser/bulkEditService';
|
||||
// import 'vs/workbench/services/integrity/node/integrityService';
|
||||
import 'vs/workbench/services/keybinding/common/keybindingEditing';
|
||||
import 'vs/workbench/services/hash/common/hashService';
|
||||
// import 'vs/workbench/services/textMate/electron-browser/textMateService';
|
||||
import 'vs/workbench/services/configurationResolver/browser/configurationResolverService';
|
||||
// import 'vs/workbench/services/workspace/node/workspaceEditingService';
|
||||
// import 'vs/workbench/services/extensions/electron-browser/inactiveExtensionUrlHandler';
|
||||
import 'vs/workbench/services/decorations/browser/decorationsService';
|
||||
// import 'vs/workbench/services/search/node/searchService';
|
||||
import 'vs/workbench/services/progress/browser/progressService2';
|
||||
import 'vs/workbench/services/editor/browser/codeEditorService';
|
||||
// import 'vs/workbench/services/broadcast/electron-browser/broadcastService';
|
||||
import 'vs/workbench/services/preferences/browser/preferencesService';
|
||||
// import 'vs/workbench/services/output/node/outputChannelModelService';
|
||||
// import 'vs/workbench/services/configuration/node/jsonEditingService';
|
||||
import 'vs/workbench/services/textmodelResolver/common/textModelResolverService';
|
||||
import 'vs/workbench/services/textfile/common/textFileService';
|
||||
// import 'vs/workbench/services/dialogs/electron-browser/dialogService';
|
||||
// import 'vs/workbench/services/backup/node/backupFileService';
|
||||
import 'vs/workbench/services/editor/browser/editorService';
|
||||
import 'vs/workbench/services/history/browser/history';
|
||||
// import 'vs/workbench/services/files/node/remoteFileService';
|
||||
import 'vs/workbench/services/activity/browser/activityService';
|
||||
import 'vs/workbench/browser/parts/views/views';
|
||||
// import 'vs/workbench/services/keybinding/electron-browser/keybindingService';
|
||||
import 'vs/workbench/services/untitled/common/untitledEditorService';
|
||||
// import 'vs/workbench/services/textfile/node/textResourcePropertiesService';
|
||||
import 'vs/workbench/services/mode/common/workbenchModeService';
|
||||
import 'vs/workbench/services/commands/common/commandService';
|
||||
import 'vs/workbench/services/themes/browser/workbenchThemeService';
|
||||
// import 'vs/workbench/services/extensions/electron-browser/extensionService';
|
||||
// import 'vs/workbench/services/contextmenu/electron-browser/contextmenuService';
|
||||
// import 'vs/workbench/services/extensionManagement/node/multiExtensionManagement';
|
||||
import 'vs/workbench/services/label/common/labelService';
|
||||
// import 'vs/workbench/services/extensions/electron-browser/extensionManagementServerService';
|
||||
// import 'vs/workbench/services/remote/electron-browser/remoteAgentServiceImpl';
|
||||
import 'vs/workbench/services/notification/common/notificationService';
|
||||
|
||||
registerSingleton(IMenuService, MenuService, true);
|
||||
registerSingleton(IListService, ListService, true);
|
||||
registerSingleton(IOpenerService, OpenerService, true);
|
||||
registerSingleton(IEditorWorkerService, EditorWorkerServiceImpl);
|
||||
registerSingleton(IMarkerDecorationsService, MarkerDecorationsService);
|
||||
registerSingleton(IMarkerService, MarkerService, true);
|
||||
// registerSingleton(IDownloadService, DownloadService, true);
|
||||
// registerSingleton(IClipboardService, ClipboardService, true);
|
||||
registerSingleton(IContextKeyService, ContextKeyService);
|
||||
registerSingleton(IModelService, ModelServiceImpl, true);
|
||||
registerSingleton(ITextResourceConfigurationService, TextResourceConfigurationService);
|
||||
registerSingleton(IAccessibilityService, BrowserAccessibilityService, true);
|
||||
registerSingleton(IExtensionEnablementService, ExtensionEnablementService, true);
|
||||
registerSingleton(IContextViewService, ContextViewService, true);
|
||||
// registerSingleton(IExtensionGalleryService, ExtensionGalleryService, true);
|
||||
// registerSingleton(IRequestService, RequestService, true);
|
||||
// registerSingleton(ILifecycleService, LifecycleService);
|
||||
// registerSingleton(ILocalizationsService, LocalizationsService);
|
||||
// registerSingleton(ISharedProcessService, SharedProcessService, true);
|
||||
// registerSingleton(IRemoteAuthorityResolverService, RemoteAuthorityResolverService, true);
|
||||
// registerSingleton(ITelemetryService, TelemetryService);
|
||||
// registerSingleton(IProductService, ProductService, true);
|
||||
// registerSingleton(IWindowsService, WindowsService);
|
||||
// registerSingleton(IUpdateService, UpdateService);
|
||||
// registerSingleton(IIssueService, IssueService);
|
||||
// registerSingleton(IWorkspacesService, WorkspacesService);
|
||||
// registerSingleton(IMenubarService, MenubarService);
|
||||
// registerSingleton(IURLService, RelayURLService);
|
||||
|
||||
registerSingleton(IContextMenuService, ContextMenuService);
|
||||
|
||||
//#endregion
|
||||
|
||||
//#region --- workbench parts
|
||||
|
||||
import 'vs/workbench/browser/parts/quickinput/quickInput';
|
||||
import 'vs/workbench/browser/parts/quickopen/quickOpenController';
|
||||
import 'vs/workbench/browser/parts/titlebar/titlebarPart';
|
||||
import 'vs/workbench/browser/parts/editor/editorPart';
|
||||
import 'vs/workbench/browser/parts/activitybar/activitybarPart';
|
||||
import 'vs/workbench/browser/parts/panel/panelPart';
|
||||
import 'vs/workbench/browser/parts/sidebar/sidebarPart';
|
||||
import 'vs/workbench/browser/parts/statusbar/statusbarPart';
|
||||
|
||||
//#endregion
|
||||
|
||||
//#region --- workbench contributions
|
||||
|
||||
// Telemetry
|
||||
import 'vs/workbench/contrib/telemetry/browser/telemetry.contribution';
|
||||
|
||||
// Localizations
|
||||
// import 'vs/workbench/contrib/localizations/browser/localizations.contribution';
|
||||
|
||||
// Preferences
|
||||
// import 'vs/workbench/contrib/preferences/electron-browser/preferences.contribution';
|
||||
import 'vs/workbench/contrib/preferences/browser/keybindingsEditorContribution';
|
||||
|
||||
// Logs
|
||||
import 'vs/workbench/contrib/logs/common/logs.contribution';
|
||||
|
||||
// Quick Open Handlers
|
||||
import 'vs/workbench/contrib/quickopen/browser/quickopen.contribution';
|
||||
|
||||
// Explorer
|
||||
import 'vs/workbench/contrib/files/browser/explorerViewlet';
|
||||
import 'vs/workbench/contrib/files/browser/fileActions.contribution';
|
||||
import 'vs/workbench/contrib/files/browser/files.contribution';
|
||||
|
||||
// Backup
|
||||
import 'vs/workbench/contrib/backup/common/backup.contribution';
|
||||
|
||||
// Stats
|
||||
// import 'vs/workbench/contrib/stats/node/stats.contribution';
|
||||
|
||||
// Rapid Render Splash
|
||||
// import 'vs/workbench/contrib/splash/electron-browser/partsSplash.contribution';
|
||||
|
||||
// Search
|
||||
import 'vs/workbench/contrib/search/browser/search.contribution';
|
||||
import 'vs/workbench/contrib/search/browser/searchView';
|
||||
import 'vs/workbench/contrib/search/browser/openAnythingHandler';
|
||||
|
||||
// SCM
|
||||
import 'vs/workbench/contrib/scm/browser/scm.contribution';
|
||||
import 'vs/workbench/contrib/scm/browser/scmViewlet';
|
||||
|
||||
// Debug
|
||||
// import 'vs/workbench/contrib/debug/electron-browser/debug.contribution';
|
||||
// import 'vs/workbench/contrib/debug/browser/debugQuickOpen';
|
||||
// import 'vs/workbench/contrib/debug/electron-browser/repl';
|
||||
// import 'vs/workbench/contrib/debug/browser/debugViewlet';
|
||||
|
||||
// Markers
|
||||
import 'vs/workbench/contrib/markers/browser/markers.contribution';
|
||||
|
||||
// Comments
|
||||
// import 'vs/workbench/contrib/comments/electron-browser/comments.contribution';
|
||||
|
||||
// URL Support
|
||||
import 'vs/workbench/contrib/url/common/url.contribution';
|
||||
|
||||
// Webview
|
||||
// import 'vs/workbench/contrib/webview/electron-browser/webview.contribution';
|
||||
|
||||
// Extensions Management
|
||||
// import 'vs/workbench/contrib/extensions/electron-browser/extensions.contribution';
|
||||
// import 'vs/workbench/contrib/extensions/browser/extensionsQuickOpen';
|
||||
// import 'vs/workbench/contrib/extensions/electron-browser/extensionsViewlet';
|
||||
|
||||
// Output Panel
|
||||
import 'vs/workbench/contrib/output/browser/output.contribution';
|
||||
import 'vs/workbench/contrib/output/browser/outputPanel';
|
||||
|
||||
// Terminal
|
||||
// import 'vs/workbench/contrib/terminal/browser/terminal.contribution';
|
||||
// import 'vs/workbench/contrib/terminal/electron-browser/terminal.contribution';
|
||||
// import 'vs/workbench/contrib/terminal/browser/terminalQuickOpen';
|
||||
// import 'vs/workbench/contrib/terminal/browser/terminalPanel';
|
||||
|
||||
// Relauncher
|
||||
// import 'vs/workbench/contrib/relauncher/electron-browser/relauncher.contribution';
|
||||
|
||||
// Tasks
|
||||
// import 'vs/workbench/contrib/tasks/electron-browser/task.contribution';
|
||||
|
||||
// Emmet
|
||||
import 'vs/workbench/contrib/emmet/browser/emmet.contribution';
|
||||
|
||||
// CodeEditor Contributions
|
||||
import 'vs/workbench/contrib/codeEditor/browser/codeEditor.contribution';
|
||||
// import 'vs/workbench/contrib/codeEditor/electron-browser/codeEditor.contribution';
|
||||
|
||||
// Execution
|
||||
// import 'vs/workbench/contrib/externalTerminal/electron-browser/externalTerminal.contribution';
|
||||
|
||||
// Snippets
|
||||
import 'vs/workbench/contrib/snippets/browser/snippets.contribution';
|
||||
import 'vs/workbench/contrib/snippets/browser/snippetsService';
|
||||
import 'vs/workbench/contrib/snippets/browser/insertSnippet';
|
||||
import 'vs/workbench/contrib/snippets/browser/configureSnippets';
|
||||
import 'vs/workbench/contrib/snippets/browser/tabCompletion';
|
||||
|
||||
// Formatter Help
|
||||
import 'vs/workbench/contrib/format/browser/format.contribution';
|
||||
|
||||
// Send a Smile
|
||||
// import 'vs/workbench/contrib/feedback/electron-browser/feedback.contribution';
|
||||
|
||||
// Update
|
||||
// import 'vs/workbench/contrib/update/electron-browser/update.contribution';
|
||||
|
||||
// Surveys
|
||||
// import 'vs/workbench/contrib/surveys/electron-browser/nps.contribution';
|
||||
// import 'vs/workbench/contrib/surveys/electron-browser/languageSurveys.contribution';
|
||||
|
||||
// Performance
|
||||
// import 'vs/workbench/contrib/performance/electron-browser/performance.contribution';
|
||||
|
||||
// CLI
|
||||
// import 'vs/workbench/contrib/cli/node/cli.contribution';
|
||||
|
||||
// Themes Support
|
||||
import 'vs/workbench/contrib/themes/browser/themes.contribution';
|
||||
// import 'vs/workbench/contrib/themes/test/electron-browser/themes.test.contribution';
|
||||
|
||||
// Watermark
|
||||
import 'vs/workbench/contrib/watermark/browser/watermark';
|
||||
|
||||
// Welcome
|
||||
import 'vs/workbench/contrib/welcome/walkThrough/browser/walkThrough.contribution';
|
||||
// import 'vs/workbench/contrib/welcome/gettingStarted/electron-browser/gettingStarted.contribution';
|
||||
import 'vs/workbench/contrib/welcome/overlay/browser/welcomeOverlay';
|
||||
import 'vs/workbench/contrib/welcome/page/browser/welcomePage.contribution';
|
||||
|
||||
// Outline
|
||||
import 'vs/workbench/contrib/outline/browser/outline.contribution';
|
||||
|
||||
// Experiments
|
||||
// import 'vs/workbench/contrib/experiments/electron-browser/experiments.contribution';
|
||||
|
||||
// Code Insets
|
||||
// import 'vs/workbench/contrib/codeinset/electron-browser/codeInset.contribution';
|
||||
|
||||
// Issues
|
||||
// import 'vs/workbench/contrib/issue/electron-browser/issue.contribution';
|
||||
|
||||
//#endregion
|
||||
Reference in New Issue
Block a user