未验证 提交 8eb77a14 编写于 作者: S Sandeep Somavarapu 提交者: GitHub

Merge pull request #49365 from Microsoft/sandy081/compositebar

Enhance Composite bar
......@@ -591,11 +591,13 @@ export class ActionBar implements IActionRunner {
if (index === null || index < 0 || index >= this.actionsList.children.length) {
this.actionsList.appendChild(actionItemElement);
this.items.push(item);
} else {
this.actionsList.insertBefore(actionItemElement, this.actionsList.children[index++]);
this.actionsList.insertBefore(actionItemElement, this.actionsList.children[index]);
this.items.splice(index, 0, item);
index++;
}
this.items.push(item);
});
}
......
......@@ -173,7 +173,8 @@ class ViewsContainersExtensionHandler implements IWorkbenchContribution {
id,
descriptor.title,
cssClass,
order
order,
descriptor.icon
);
viewletRegistry.registerViewlet(viewletDescriptor);
......
......@@ -7,12 +7,10 @@
import 'vs/css!./media/activitybarpart';
import * as nls from 'vs/nls';
import { TPromise } from 'vs/base/common/winjs.base';
import { illegalArgument } from 'vs/base/common/errors';
import { $ } from 'vs/base/browser/builder';
import { Action } from 'vs/base/common/actions';
import { ActionsOrientation, ActionBar, Separator } from 'vs/base/browser/ui/actionbar/actionbar';
import { GlobalActivityExtensions, IGlobalActivityRegistry } from 'vs/workbench/common/activity';
import { ActionsOrientation, ActionBar } from 'vs/base/browser/ui/actionbar/actionbar';
import { GlobalActivityExtensions, IGlobalActivityRegistry, IActivity } from 'vs/workbench/common/activity';
import { Registry } from 'vs/platform/registry/common/platform';
import { Part } from 'vs/workbench/browser/part';
import { GlobalActivityActionItem, GlobalActivityAction, ViewletActivityAction, ToggleViewletAction } from 'vs/workbench/browser/parts/activitybar/activitybarActions';
......@@ -20,22 +18,29 @@ import { IViewletService } from 'vs/workbench/services/viewlet/browser/viewlet';
import { IBadge } from 'vs/workbench/services/activity/common/activity';
import { IPartService, Parts, Position as SideBarPosition } from 'vs/workbench/services/part/common/partService';
import { IInstantiationService } from 'vs/platform/instantiation/common/instantiation';
import { IContextMenuService } from 'vs/platform/contextview/browser/contextView';
import { StandardMouseEvent } from 'vs/base/browser/mouseEvent';
import { dispose, IDisposable, toDisposable } from 'vs/base/common/lifecycle';
import { IDisposable, toDisposable } from 'vs/base/common/lifecycle';
import { ToggleActivityBarVisibilityAction } from 'vs/workbench/browser/actions/toggleActivityBarVisibility';
import { IThemeService } from 'vs/platform/theme/common/themeService';
import { ACTIVITY_BAR_BACKGROUND, ACTIVITY_BAR_BORDER, ACTIVITY_BAR_FOREGROUND, ACTIVITY_BAR_BADGE_BACKGROUND, ACTIVITY_BAR_BADGE_FOREGROUND, ACTIVITY_BAR_DRAG_AND_DROP_BACKGROUND } from 'vs/workbench/common/theme';
import { contrastBorder } from 'vs/platform/theme/common/colorRegistry';
import { CompositeBar } from 'vs/workbench/browser/parts/compositebar/compositeBar';
import { ToggleCompositePinnedAction } from 'vs/workbench/browser/parts/compositebar/compositeBarActions';
import { ToggleCompositePinnedAction, ICompositeBar } from 'vs/workbench/browser/parts/compositebar/compositeBarActions';
import { ViewLocation, ViewsRegistry } from 'vs/workbench/common/views';
import { ViewletDescriptor } from 'vs/workbench/browser/viewlet';
import { Dimension } from 'vs/base/browser/dom';
import { Dimension, createCSSRule } from 'vs/base/browser/dom';
import { IStorageService, StorageScope } from 'vs/platform/storage/common/storage';
import { IExtensionService } from 'vs/workbench/services/extensions/common/extensions';
import { ITelemetryService } from 'vs/platform/telemetry/common/telemetry';
interface IPlaceholderComposite {
id: string;
iconUrl: string;
}
export class ActivitybarPart extends Part {
private static readonly PINNED_VIEWLETS = 'workbench.activity.pinnedViewlets';
private static readonly PLACEHOLDER_VIEWLETS = 'workbench.activity.placeholderViewlets';
private static readonly COLORS = {
backgroundColor: ACTIVITY_BAR_FOREGROUND,
badgeBackground: ACTIVITY_BAR_BADGE_BACKGROUND,
......@@ -51,37 +56,53 @@ export class ActivitybarPart extends Part {
private globalActionBar: ActionBar;
private globalActivityIdToActions: { [globalActivityId: string]: GlobalActivityAction; };
private placeholderComposites: IPlaceholderComposite[] = [];
private extensionsRegistrationCompleted: boolean = false;
private compositeBar: CompositeBar;
private compositeActions: { [compositeId: string]: { activityAction: ViewletActivityAction, pinnedAction: ToggleCompositePinnedAction } };
constructor(
id: string,
@IViewletService private viewletService: IViewletService,
@IContextMenuService private contextMenuService: IContextMenuService,
@IInstantiationService private instantiationService: IInstantiationService,
@IPartService private partService: IPartService,
@IThemeService themeService: IThemeService
@IThemeService themeService: IThemeService,
@IStorageService private storageService: IStorageService,
@IExtensionService extensionService: IExtensionService,
) {
super(id, { hasTitle: false }, themeService);
this.globalActivityIdToActions = Object.create(null);
this.placeholderComposites = JSON.parse(this.storageService.get(ActivitybarPart.PLACEHOLDER_VIEWLETS, StorageScope.GLOBAL, '[]'));
this.compositeActions = Object.create(null);
this.compositeBar = this.instantiationService.createInstance(CompositeBar, {
icon: true,
storageId: ActivitybarPart.PINNED_VIEWLETS,
orientation: ActionsOrientation.VERTICAL,
composites: this.viewletService.getViewlets(),
openComposite: (compositeId: string) => this.viewletService.openViewlet(compositeId, true),
getActivityAction: (compositeId: string) => this.instantiationService.createInstance(ViewletActivityAction, this.viewletService.getViewlet(compositeId)),
getCompositePinnedAction: (compositeId: string) => new ToggleCompositePinnedAction(this.viewletService.getViewlet(compositeId), this.compositeBar),
getActivityAction: (compositeId: string) => this.getCompositeActions(compositeId).activityAction,
getCompositePinnedAction: (compositeId: string) => this.getCompositeActions(compositeId).pinnedAction,
getOnCompositeClickAction: (compositeId: string) => this.instantiationService.createInstance(ToggleViewletAction, this.viewletService.getViewlet(compositeId)),
getContextMenuActions: () => [this.instantiationService.createInstance(ToggleActivityBarVisibilityAction, ToggleActivityBarVisibilityAction.ID, nls.localize('hideActivitBar', "Hide Activity Bar"))],
getDefaultCompositeId: () => this.viewletService.getDefaultViewletId(),
hidePart: () => this.partService.setSideBarHidden(true),
compositeSize: 50,
colors: ActivitybarPart.COLORS,
overflowActionSize: ActivitybarPart.ACTION_HEIGHT
});
this.registerListeners();
this.updateCompositebar();
this.updatePlaceholderComposites();
extensionService.onDidRegisterExtensions(() => this.onDidRegisterExtensions());
}
private onDidRegisterExtensions(): void {
this.extensionsRegistrationCompleted = true;
this.removeNotExistingPlaceholderComposites();
this.updateCompositebar();
}
private registerListeners(): void {
......@@ -95,12 +116,11 @@ export class ActivitybarPart extends Part {
// Deactivate viewlet action on close
this.toUnbind.push(this.viewletService.onDidViewletClose(viewlet => this.compositeBar.deactivateComposite(viewlet.getId())));
this.toUnbind.push(this.compositeBar.onDidContextMenu(e => this.showContextMenu(e)));
this.toUnbind.push(this.viewletService.onDidViewletEnablementChange(({ id, enabled }) => {
if (enabled) {
this.compositeBar.addComposite(this.viewletService.getViewlet(id), true);
} else {
this.compositeBar.removeComposite(id);
this.removeComposite(id);
}
}));
}
......@@ -160,22 +180,6 @@ export class ActivitybarPart extends Part {
container.style('border-left-color', !isPositionLeft ? borderColor : null);
}
private showContextMenu(e: MouseEvent): void {
const event = new StandardMouseEvent(e);
const actions: Action[] = this.viewletService.getViewlets()
.filter(viewlet => this.canShow(viewlet))
.map(viewlet => this.instantiationService.createInstance(ToggleCompositePinnedAction, viewlet, this.compositeBar));
actions.push(new Separator());
actions.push(this.instantiationService.createInstance(ToggleActivityBarVisibilityAction, ToggleActivityBarVisibilityAction.ID, nls.localize('hideActivitBar', "Hide Activity Bar")));
this.contextMenuService.showContextMenu({
getAnchor: () => { return { x: event.posx, y: event.posy }; },
getActions: () => TPromise.as(actions),
onHide: () => dispose(actions)
});
}
private createGlobalActivityActionBar(container: HTMLElement): void {
const activityRegistry = Registry.as<IGlobalActivityRegistry>(GlobalActivityExtensions);
const descriptors = activityRegistry.getActivities();
......@@ -197,19 +201,93 @@ export class ActivitybarPart extends Part {
});
}
private getCompositeActions(compositeId: string): { activityAction: ViewletActivityAction, pinnedAction: ToggleCompositePinnedAction } {
let compositeActions = this.compositeActions[compositeId];
if (!compositeActions) {
const viewlet = this.viewletService.getViewlet(compositeId);
if (viewlet) {
compositeActions = {
activityAction: this.instantiationService.createInstance(ViewletActivityAction, viewlet),
pinnedAction: new ToggleCompositePinnedAction(viewlet, this.compositeBar)
};
} else {
const placeHolderComposite = this.placeholderComposites.filter(c => c.id === compositeId)[0];
compositeActions = {
activityAction: this.instantiationService.createInstance(PlaceHolderViewletActivityAction, compositeId, placeHolderComposite.iconUrl),
pinnedAction: new PlaceHolderToggleCompositePinnedAction(compositeId, this.compositeBar)
};
}
this.compositeActions[compositeId] = compositeActions;
}
return compositeActions;
}
private updateCompositebar(): void {
const viewlets = this.viewletService.getViewlets();
for (const viewlet of viewlets) {
const canShow = this.canShow(viewlet);
if (canShow) {
const hasPlaceholder = this.placeholderComposites.some(c => c.id === viewlet.id);
// Add the composite if it has views registered or
// If it was existing before and the extensions registration is not yet completed.
if (this.hasRegisteredViews(viewlet)
|| (hasPlaceholder && !this.extensionsRegistrationCompleted)
) {
this.compositeBar.addComposite(viewlet, false);
// Pin it by default if it is new => it does not has a placeholder
if (!hasPlaceholder) {
this.compositeBar.pin(viewlet.id);
}
this.enableCompositeActions(viewlet);
const activeViewlet = this.viewletService.getActiveViewlet();
if (activeViewlet && activeViewlet.getId() === viewlet.id) {
this.compositeBar.pin(viewlet.id);
this.compositeBar.activateComposite(viewlet.id);
}
} else {
this.compositeBar.removeComposite(viewlet.id);
this.removeComposite(viewlet.id);
}
}
}
private updatePlaceholderComposites(): void {
const viewlets = this.viewletService.getViewlets();
for (const { id } of this.placeholderComposites) {
if (viewlets.every(viewlet => viewlet.id !== id)) {
this.compositeBar.addComposite({ id, name: id, order: void 0 }, false);
}
}
}
private canShow(viewlet: ViewletDescriptor): boolean {
private removeNotExistingPlaceholderComposites(): void {
const viewlets = this.viewletService.getViewlets();
for (const { id } of this.placeholderComposites) {
if (viewlets.every(viewlet => viewlet.id !== id)) {
this.removeComposite(id);
}
}
}
private removeComposite(compositeId: string): void {
this.compositeBar.removeComposite(compositeId);
const compositeActions = this.compositeActions[compositeId];
if (compositeActions) {
compositeActions.activityAction.dispose();
compositeActions.pinnedAction.dispose();
delete this.compositeActions[compositeId];
}
}
private enableCompositeActions(viewlet: ViewletDescriptor): void {
const { activityAction, pinnedAction } = this.getCompositeActions(viewlet.id);
if (activityAction instanceof PlaceHolderViewletActivityAction) {
activityAction.enable(viewlet);
}
if (pinnedAction instanceof PlaceHolderToggleCompositePinnedAction) {
pinnedAction.enable(viewlet);
}
}
private hasRegisteredViews(viewlet: ViewletDescriptor): boolean {
const viewLocation = ViewLocation.get(viewlet.id);
if (viewLocation) {
return ViewsRegistry.getViews(viewLocation).length > 0;
......@@ -245,6 +323,8 @@ export class ActivitybarPart extends Part {
}
public shutdown(): void {
const state = this.viewletService.getViewlets().filter(viewlet => this.hasRegisteredViews(viewlet)).map(viewlet => ({ id: viewlet.id, iconUrl: viewlet.iconUrl }));
this.storageService.store(ActivitybarPart.PLACEHOLDER_VIEWLETS, JSON.stringify(state), StorageScope.GLOBAL);
this.compositeBar.shutdown();
super.shutdown();
}
......@@ -262,4 +342,43 @@ export class ActivitybarPart extends Part {
super.dispose();
}
}
class PlaceHolderViewletActivityAction extends ViewletActivityAction {
constructor(
id: string, iconUrl: string,
@IViewletService viewletService: IViewletService,
@IPartService partService: IPartService,
@ITelemetryService telemetryService: ITelemetryService
) {
super({ id, name: id, cssClass: `extensionViewlet-placeholder-${id.replace(/\./g, '-')}` }, viewletService, partService, telemetryService);
// Generate Placeholder CSS to show the icon in the activity bar
const iconClass = `.monaco-workbench > .activitybar .monaco-action-bar .action-label.${this.class}`;
createCSSRule(iconClass, `-webkit-mask: url('${iconUrl}') no-repeat 50% 50%`);
this.enabled = false;
}
enable(activity: IActivity): void {
this.label = activity.name;
this.class = activity.cssClass;
this.enabled = true;
}
}
class PlaceHolderToggleCompositePinnedAction extends ToggleCompositePinnedAction {
constructor(
id: string, compositeBar: ICompositeBar
) {
super({ id, name: id, cssClass: void 0 }, compositeBar);
this.enabled = false;
}
enable(activity: IActivity): void {
this.label = activity.name;
this.enabled = true;
}
}
\ No newline at end of file
......@@ -445,6 +445,9 @@ export class CompositeActionItem extends ActivityActionItem {
public render(container: HTMLElement): void {
super.render(container);
this._updateChecked();
this._updateEnabled();
this.$container.on('contextmenu', e => {
dom.EventHelper.stop(e, true);
......@@ -564,11 +567,13 @@ export class CompositeActionItem extends ActivityActionItem {
protected _updateClass(): void {
if (this.cssClass) {
this.$badge.removeClass(this.cssClass);
this.$label.removeClass(this.cssClass);
}
this.cssClass = this.getAction().class;
this.$badge.addClass(this.cssClass);
if (this.cssClass) {
this.$label.addClass(this.cssClass);
}
}
protected _updateChecked(): void {
......
......@@ -5,7 +5,7 @@
import 'vs/css!./media/panelpart';
import { TPromise } from 'vs/base/common/winjs.base';
import { IAction, Action } from 'vs/base/common/actions';
import { IAction } from 'vs/base/common/actions';
import { Event } from 'vs/base/common/event';
import { $ } from 'vs/base/browser/builder';
import { Registry } from 'vs/platform/registry/common/platform';
......@@ -20,17 +20,17 @@ import { IContextMenuService } from 'vs/platform/contextview/browser/contextView
import { ITelemetryService } from 'vs/platform/telemetry/common/telemetry';
import { IKeybindingService } from 'vs/platform/keybinding/common/keybinding';
import { IInstantiationService } from 'vs/platform/instantiation/common/instantiation';
import { ClosePanelAction, TogglePanelPositionAction, PanelActivityAction, ToggleMaximizedPanelAction } from 'vs/workbench/browser/parts/panel/panelActions';
import { ClosePanelAction, TogglePanelPositionAction, PanelActivityAction, ToggleMaximizedPanelAction, TogglePanelAction } from 'vs/workbench/browser/parts/panel/panelActions';
import { IThemeService, registerThemingParticipant, ITheme, ICssStyleCollector } from 'vs/platform/theme/common/themeService';
import { PANEL_BACKGROUND, PANEL_BORDER, PANEL_ACTIVE_TITLE_FOREGROUND, PANEL_INACTIVE_TITLE_FOREGROUND, PANEL_ACTIVE_TITLE_BORDER, PANEL_DRAG_AND_DROP_BACKGROUND } from 'vs/workbench/common/theme';
import { activeContrastBorder, focusBorder, contrastBorder, editorBackground, badgeBackground, badgeForeground } from 'vs/platform/theme/common/colorRegistry';
import { CompositeBar } from 'vs/workbench/browser/parts/compositebar/compositeBar';
import { ToggleCompositePinnedAction } from 'vs/workbench/browser/parts/compositebar/compositeBarActions';
import { StandardMouseEvent } from 'vs/base/browser/mouseEvent';
import { dispose, IDisposable } from 'vs/base/common/lifecycle';
import { IBadge } from 'vs/workbench/services/activity/common/activity';
import { INotificationService } from 'vs/platform/notification/common/notification';
import { Dimension } from 'vs/base/browser/dom';
import { localize } from 'vs/nls';
import { IDisposable } from 'vs/base/common/lifecycle';
export class PanelPart extends CompositePart<Panel> implements IPanelService {
......@@ -42,6 +42,7 @@ export class PanelPart extends CompositePart<Panel> implements IPanelService {
private blockOpeningPanel: boolean;
private compositeBar: CompositeBar;
private compositeActions: { [compositeId: string]: { activityAction: PanelActivityAction, pinnedAction: ToggleCompositePinnedAction } };
private dimension: Dimension;
constructor(
......@@ -74,17 +75,19 @@ export class PanelPart extends CompositePart<Panel> implements IPanelService {
{ hasTitle: true }
);
this.compositeActions = Object.create(null);
this.compositeBar = this.instantiationService.createInstance(CompositeBar, {
icon: false,
storageId: PanelPart.PINNED_PANELS,
orientation: ActionsOrientation.HORIZONTAL,
composites: this.getPanels(),
openComposite: (compositeId: string) => this.openPanel(compositeId, true),
getActivityAction: (compositeId: string) => this.instantiationService.createInstance(PanelActivityAction, this.getPanel(compositeId)),
getCompositePinnedAction: (compositeId: string) => new ToggleCompositePinnedAction(this.getPanel(compositeId), this.compositeBar),
getActivityAction: (compositeId: string) => this.getCompositeActions(compositeId).activityAction,
getCompositePinnedAction: (compositeId: string) => this.getCompositeActions(compositeId).pinnedAction,
getOnCompositeClickAction: (compositeId: string) => this.instantiationService.createInstance(PanelActivityAction, this.getPanel(compositeId)),
getContextMenuActions: () => [this.instantiationService.createInstance(TogglePanelAction, TogglePanelAction.ID, localize('hidePanel', "Hide Panel"))],
getDefaultCompositeId: () => Registry.as<PanelRegistry>(PanelExtensions.Panels).getDefaultPanelId(),
hidePart: () => this.partService.setPanelHidden(true),
compositeSize: 0,
overflowActionSize: 44,
colors: {
backgroundColor: PANEL_BACKGROUND,
......@@ -94,6 +97,9 @@ export class PanelPart extends CompositePart<Panel> implements IPanelService {
}
});
this.toUnbind.push(this.compositeBar);
for (const panel of this.getPanels()) {
this.compositeBar.addComposite(panel, false);
}
this.registerListeners();
}
......@@ -108,7 +114,6 @@ export class PanelPart extends CompositePart<Panel> implements IPanelService {
// Need to relayout composite bar since different panels have different action bar width
this.layoutCompositeBar();
}));
this.toUnbind.push(this.compositeBar.onDidContextMenu(e => this.showContextMenu(e)));
// Deactivate panel action on close
this.toUnbind.push(this.onDidPanelClose(panel => this.compositeBar.deactivateComposite(panel.getId())));
......@@ -160,17 +165,6 @@ export class PanelPart extends CompositePart<Panel> implements IPanelService {
return this.getPanels().filter(p => p.id === panelId).pop();
}
private showContextMenu(e: MouseEvent): void {
const event = new StandardMouseEvent(e);
const actions: Action[] = this.getPanels().map(panel => this.instantiationService.createInstance(ToggleCompositePinnedAction, panel, this.compositeBar));
this.contextMenuService.showContextMenu({
getAnchor: () => { return { x: event.posx, y: event.posy }; },
getActions: () => TPromise.as(actions),
onHide: () => dispose(actions)
});
}
public getPanels(): PanelDescriptor[] {
return Registry.as<PanelRegistry>(PanelExtensions.Panels).getPanels()
.filter(p => p.enabled)
......@@ -184,7 +178,7 @@ export class PanelPart extends CompositePart<Panel> implements IPanelService {
if (enabled) {
this.compositeBar.addComposite(descriptor, true);
} else {
this.compositeBar.removeComposite(id);
this.removeComposite(id);
}
}
}
......@@ -259,6 +253,28 @@ export class PanelPart extends CompositePart<Panel> implements IPanelService {
}
}
private getCompositeActions(compositeId: string): { activityAction: PanelActivityAction, pinnedAction: ToggleCompositePinnedAction } {
let compositeActions = this.compositeActions[compositeId];
if (!compositeActions) {
compositeActions = {
activityAction: this.instantiationService.createInstance(PanelActivityAction, this.getPanel(compositeId)),
pinnedAction: new ToggleCompositePinnedAction(this.getPanel(compositeId), this.compositeBar)
};
this.compositeActions[compositeId] = compositeActions;
}
return compositeActions;
}
private removeComposite(compositeId: string): void {
this.compositeBar.removeComposite(compositeId);
const compositeActions = this.compositeActions[compositeId];
if (compositeActions) {
compositeActions.activityAction.dispose();
compositeActions.pinnedAction.dispose();
delete this.compositeActions[compositeId];
}
}
private getToolbarWidth(): number {
const activePanel = this.getActivePanel();
if (!activePanel) {
......
......@@ -54,13 +54,13 @@ export class ViewletDescriptor extends CompositeDescriptor<Viewlet> {
name: string,
cssClass?: string,
order?: number,
private _extensionId?: string
private _iconUrl?: string
) {
super(ctor, id, name, cssClass, order, id);
}
public get extensionId(): string {
return this._extensionId;
public get iconUrl(): string {
return this._iconUrl;
}
}
......
......@@ -49,6 +49,10 @@ export class OutputPanel extends AbstractTextResourceEditor {
return OUTPUT_PANEL_ID;
}
public getTitle(): string {
return nls.localize('output', "Output");
}
public getActions(): IAction[] {
if (!this.actions) {
this.actions = [
......
......@@ -4,17 +4,17 @@
*--------------------------------------------------------------------------------------------*/
'use strict';
import { TPromise, ValueCallback } from 'vs/base/common/winjs.base';
import { TPromise } from 'vs/base/common/winjs.base';
import { IViewlet } from 'vs/workbench/common/viewlet';
import { IViewletService } from 'vs/workbench/services/viewlet/browser/viewlet';
import { Event, Emitter } from 'vs/base/common/event';
import { SidebarPart } from 'vs/workbench/browser/parts/sidebar/sidebarPart';
import { Registry } from 'vs/platform/registry/common/platform';
import { ViewletDescriptor, ViewletRegistry, Extensions as ViewletExtensions } from 'vs/workbench/browser/viewlet';
import { IExtensionService } from 'vs/workbench/services/extensions/common/extensions';
import { IProgressService } from 'vs/platform/progress/common/progress';
import { IContextKeyService, RawContextKey, IContextKey } from 'vs/platform/contextkey/common/contextkey';
import { dispose, IDisposable } from 'vs/base/common/lifecycle';
import { IExtensionService } from 'vs/workbench/services/extensions/common/extensions';
const ActiveViewletContextId = 'activeViewlet';
export const ActiveViewletContext = new RawContextKey<string>(ActiveViewletContextId, '');
......@@ -26,9 +26,6 @@ export class ViewletService implements IViewletService {
private sidebarPart: SidebarPart;
private viewletRegistry: ViewletRegistry;
private extensionViewlets: ViewletDescriptor[];
private extensionViewletsLoaded: TPromise<void>;
private extensionViewletsLoadedPromiseComplete: ValueCallback;
private activeViewletContextKey: IContextKey<string>;
private _onDidViewletEnable = new Emitter<{ id: string, enabled: boolean }>();
private disposables: IDisposable[] = [];
......@@ -40,8 +37,8 @@ export class ViewletService implements IViewletService {
constructor(
sidebarPart: SidebarPart,
@IExtensionService private extensionService: IExtensionService,
@IContextKeyService contextKeyService: IContextKeyService
@IContextKeyService contextKeyService: IContextKeyService,
@IExtensionService private extensionService: IExtensionService
) {
this.sidebarPart = sidebarPart;
this.viewletRegistry = Registry.as<ViewletRegistry>(ViewletExtensions.Viewlets);
......@@ -50,8 +47,6 @@ export class ViewletService implements IViewletService {
this.onDidViewletOpen(this._onDidViewletOpen, this, this.disposables);
this.onDidViewletClose(this._onDidViewletClose, this, this.disposables);
this.loadExtensionViewlets();
}
private _onDidViewletOpen(viewlet: IViewlet): void {
......@@ -66,25 +61,6 @@ export class ViewletService implements IViewletService {
}
}
private loadExtensionViewlets(): void {
this.extensionViewlets = [];
this.extensionViewletsLoaded = new TPromise<void>(c => {
this.extensionViewletsLoadedPromiseComplete = c;
});
this.extensionService.whenInstalledExtensionsRegistered().then(() => {
const viewlets = this.viewletRegistry.getViewlets();
viewlets.forEach(v => {
if (!!v.extensionId) {
this.extensionViewlets.push(v);
}
});
this.extensionViewletsLoadedPromiseComplete(void 0);
});
}
public setViewletEnablement(id: string, enabled: boolean): void {
const descriptor = this.getBuiltInViewlets().filter(desc => desc.id === id).pop();
if (descriptor && descriptor.enabled !== enabled) {
......@@ -94,23 +70,11 @@ export class ViewletService implements IViewletService {
}
public openViewlet(id: string, focus?: boolean): TPromise<IViewlet> {
// Built in viewlets do not need to wait for extensions to be loaded
const builtInViewletIds = this.getBuiltInViewlets().map(v => v.id);
const isBuiltInViewlet = builtInViewletIds.indexOf(id) !== -1;
if (isBuiltInViewlet) {
if (this.getViewlet(id)) {
return this.sidebarPart.openViewlet(id, focus);
}
// Extension viewlets need to be loaded first which can take time
return this.extensionViewletsLoaded.then(() => {
if (this.viewletRegistry.getViewlet(id)) {
return this.sidebarPart.openViewlet(id, focus);
}
// Fallback to default viewlet if extension viewlet is still not found (e.g. uninstalled)
return this.sidebarPart.openViewlet(this.getDefaultViewletId(), focus);
});
return this.extensionService.whenInstalledExtensionsRegistered()
.then(() => this.sidebarPart.openViewlet(id, focus));
}
public getActiveViewlet(): IViewlet {
......@@ -118,15 +82,12 @@ export class ViewletService implements IViewletService {
}
public getViewlets(): ViewletDescriptor[] {
const builtInViewlets = this.getBuiltInViewlets();
const viewlets = builtInViewlets.concat(this.extensionViewlets);
return viewlets.filter(v => v.enabled);
return this.getBuiltInViewlets()
.filter(v => v.enabled);
}
private getBuiltInViewlets(): ViewletDescriptor[] {
return this.viewletRegistry.getViewlets()
.filter(viewlet => !viewlet.extensionId)
.sort((v1, v2) => v1.order - v2.order);
}
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册