scmMenus.ts 5.1 KB
Newer Older
J
Joao Moreno 已提交
1 2 3 4 5 6 7 8
/*---------------------------------------------------------------------------------------------
 *  Copyright (c) Microsoft Corporation. All rights reserved.
 *  Licensed under the MIT License. See License.txt in the project root for license information.
 *--------------------------------------------------------------------------------------------*/

'use strict';

import 'vs/css!./media/scmViewlet';
J
Joao Moreno 已提交
9 10
import { localize } from 'vs/nls';
import { TPromise } from 'vs/base/common/winjs.base';
J
Joao Moreno 已提交
11
import Event, { Emitter } from 'vs/base/common/event';
J
Joao Moreno 已提交
12
import { IDisposable, dispose, empty as EmptyDisposable, toDisposable } from 'vs/base/common/lifecycle';
J
Joao Moreno 已提交
13
import { IContextKeyService } from 'vs/platform/contextkey/common/contextkey';
J
Joao Moreno 已提交
14
import { IMenuService, MenuId } from 'vs/platform/actions/common/actions';
J
Joao Moreno 已提交
15
import { IAction, Action } from 'vs/base/common/actions';
J
Joao Moreno 已提交
16
import { fillInActions } from 'vs/platform/actions/browser/menuItemActionItem';
J
Joao Moreno 已提交
17 18
import { ContextSubMenu } from 'vs/platform/contextview/browser/contextView';
import { Separator } from 'vs/base/browser/ui/actionbar/actionbar';
J
Joao Moreno 已提交
19
import { ISCMService, ISCMProvider, ISCMResource, ISCMResourceGroup } from 'vs/workbench/services/scm/common/scm';
J
Joao Moreno 已提交
20
import { getSCMResourceContextKey } from './scmUtil';
J
Joao Moreno 已提交
21

J
Joao Moreno 已提交
22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40
class SwitchProviderAction extends Action {

	get checked(): boolean {
		return this.scmService.activeProvider === this.provider;
	}

	constructor(
		private provider: ISCMProvider,
		@ISCMService private scmService: ISCMService
	) {
		super('scm.switchProvider', provider.label, '', true);
	}

	run(): TPromise<void> {
		this.scmService.activeProvider = this.provider;
		return TPromise.as(null);
	}
}

J
Joao Moreno 已提交
41 42
export class SCMMenus implements IDisposable {

J
Joao Moreno 已提交
43
	private disposables: IDisposable[] = [];
J
Joao Moreno 已提交
44

J
Joao Moreno 已提交
45 46 47
	private titleDisposable: IDisposable = EmptyDisposable;
	private titleActions: IAction[] = [];
	private titleSecondaryActions: IAction[] = [];
J
Joao Moreno 已提交
48 49 50

	private _onDidChangeTitle = new Emitter<void>();
	get onDidChangeTitle(): Event<void> { return this._onDidChangeTitle.event; }
J
Joao Moreno 已提交
51 52 53

	constructor(
		@IContextKeyService private contextKeyService: IContextKeyService,
J
Joao Moreno 已提交
54
		@ISCMService private scmService: ISCMService,
J
Joao Moreno 已提交
55 56
		@IMenuService private menuService: IMenuService
	) {
J
Joao Moreno 已提交
57 58 59 60 61 62 63 64 65 66 67 68 69 70
		this.setActiveProvider(this.scmService.activeProvider);
		this.scmService.onDidChangeProvider(this.setActiveProvider, this, this.disposables);
	}

	private setActiveProvider(activeProvider: ISCMProvider | undefined): void {
		if (this.titleDisposable) {
			this.titleDisposable.dispose();
			this.titleDisposable = EmptyDisposable;
		}

		if (!activeProvider) {
			return;
		}

J
Joao Moreno 已提交
71
		const titleMenu = this.menuService.createMenu(MenuId.SCMTitle, this.contextKeyService);
J
Joao Moreno 已提交
72 73 74 75
		const updateActions = () => {
			this.titleActions = [];
			this.titleSecondaryActions = [];
			fillInActions(titleMenu, null, { primary: this.titleActions, secondary: this.titleSecondaryActions });
J
Joao Moreno 已提交
76
			this._onDidChangeTitle.fire();
J
Joao Moreno 已提交
77 78
		};

J
Joao Moreno 已提交
79 80 81 82 83 84 85 86 87
		const listener = titleMenu.onDidChange(updateActions);
		updateActions();

		this.titleDisposable = toDisposable(() => {
			listener.dispose();
			titleMenu.dispose();
			this.titleActions = [];
			this.titleSecondaryActions = [];
		});
J
Joao Moreno 已提交
88 89
	}

J
Joao Moreno 已提交
90 91
	getTitleActions(): IAction[] {
		return this.titleActions;
J
Joao Moreno 已提交
92 93
	}

J
Joao Moreno 已提交
94
	getTitleSecondaryActions(): IAction[] {
J
Joao Moreno 已提交
95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112
		const providerSwitchActions = this.scmService.providers
			.map(p => new SwitchProviderAction(p, this.scmService));

		let result = [];

		if (this.titleSecondaryActions.length > 0) {
			result = result.concat(this.titleSecondaryActions);
		}

		if (result.length > 0 && providerSwitchActions.length > 0) {
			result.push(new Separator());
		}

		if (providerSwitchActions.length > 0) {
			result.push(new ContextSubMenu(localize('switch provider', "Switch SCM Provider..."), providerSwitchActions));
		}

		return result;
J
Joao Moreno 已提交
113 114
	}

J
Joao Moreno 已提交
115
	getResourceGroupActions(group: ISCMResourceGroup): IAction[] {
116
		return this.getActions(MenuId.SCMResourceGroupContext, group).primary;
J
Joao Moreno 已提交
117 118 119
	}

	getResourceGroupContextActions(group: ISCMResourceGroup): IAction[] {
120
		return this.getActions(MenuId.SCMResourceGroupContext, group).secondary;
J
Joao Moreno 已提交
121 122
	}

J
Joao Moreno 已提交
123
	getResourceActions(resource: ISCMResource): IAction[] {
124
		return this.getActions(MenuId.SCMResourceContext, resource).primary;
J
Joao Moreno 已提交
125 126
	}

J
Joao Moreno 已提交
127
	getResourceContextActions(resource: ISCMResource): IAction[] {
128
		return this.getActions(MenuId.SCMResourceContext, resource).secondary;
J
Joao Moreno 已提交
129 130 131 132
	}

	private static readonly NoActions = { primary: [], secondary: [] };

133
	private getActions(menuId: MenuId, resource: ISCMResourceGroup | ISCMResource): { primary: IAction[]; secondary: IAction[]; } {
J
Joao Moreno 已提交
134
		if (!this.scmService.activeProvider) {
J
Joao Moreno 已提交
135
			return SCMMenus.NoActions;
J
Joao Moreno 已提交
136 137
		}

J
Joao Moreno 已提交
138
		const contextKeyService = this.contextKeyService.createScoped();
J
Joao Moreno 已提交
139
		contextKeyService.createKey('scmResourceGroup', getSCMResourceContextKey(resource));
J
Joao Moreno 已提交
140

J
Joao Moreno 已提交
141
		const menu = this.menuService.createMenu(menuId, contextKeyService);
J
Joao Moreno 已提交
142 143 144
		const primary = [];
		const secondary = [];
		const result = { primary, secondary };
145
		fillInActions(menu, { arg: resource.uri, shouldForwardArgs: true }, result, g => g === 'inline');
J
Joao Moreno 已提交
146

J
Joao Moreno 已提交
147
		menu.dispose();
J
Joao Moreno 已提交
148 149
		contextKeyService.dispose();

J
Joao Moreno 已提交
150 151 152
		return result;
	}

J
Joao Moreno 已提交
153 154 155 156
	dispose(): void {
		this.disposables = dispose(this.disposables);
	}
}