mirror of
https://github.com/ckaczor/azuredatastudio.git
synced 2026-02-01 01:25:38 -05:00
* Initial work of adding tab in the dashboard (#526) * refactor dashboard to have the home tab * formatting * fix grid layout issue * fix initailize issue in database dashboard * Add action bar to the panel and add close tab to the dashboard (#562) * add action bar to the panel and add close tab to the dashboard * formatting * Tab contribution (#564) * added contrib * disabled edit for extensions; fixed new name for insights contrib * fix merge issue * move file * formatting * fix builds * moving imports * Expand on tab contrib (#581) * added contrib * disabled edit for extensions; fixed new name for insights contrib * fix merge issue * move file * formatting * fix builds * adding to contrib * updated contrib * format * moving imports * updated contribution to map to current design * implemented actually using provider and edition filtering * Refactor and fix issues in close tab and add the placeholder for pin tab (#588) * refactor and fix issues in close tab and add the placeholder for pin tab * formatting * remove the redundant code * add clear all tabs in dashboard page init * Initial work for adding a feature tab dialog (#594) * initial work for add new dashboard tab * formatting * fix add panel action issue * fix breaking change * fix issues and tab and panels * formatting * minor fix * address comments * Add tab status to add extension tab dialog (#610) * add tab status to add extension tab dialog * add tab status to add extension tab dialog * rename add feature tab action * address comments * Webview widget (#618) * getting closer * webview widget now works * fix problem with rerendering webview * formatting * ensure that webview only shows up for extensions * formatting * comments * fix more compile issues * Change dashboard page init (#640) * changed init of serverpage * formatting * Webview tab (#638) * getting closer * webview widget now works * fix problem with rerendering webview * formatting * ensure that webview only shows up for extensions * formatting * comments * fix more compile issues * refacting stuff * added inital webview tab * piped through messaging and tested * Implement pin/unpin feature and always on tabs (#629) * implement pin/unpin feature * fix issue where insight can't be loaded after reopen * fix tab look and feel * implement always show tabs * make AddFeatureTabAction to track always show and pinned tabs * formatting * make dashboard tabs looks like the UX design * load always show before pinned tab * fix regression in panel for restore and connection dialog * fix merge conflict * don't worry about no widgets if its a webview (#656) * expose the dashboard server info when a webview is rendering (#644) * Fix few issues in dashboard command center (#655) * fix reloading insight wigets and create new tab when there is no extension * show possible tabIDs in the setting file * formatting * address comment * fix import name * fixes problem with size of webview widget being wrong (#654) * Refactor tab contribution to support content type (#685) * refactor tab contribution to support content type * formatting * address comment * fix rendering tab issue (#694) * Add layout option to panel for supporting horizontal and vertical navigation bar (#700) * Add left navigation panel for inner tab in the dashboard * add layout option in panel * remove panel option in dashboard Page
176 lines
5.3 KiB
TypeScript
176 lines
5.3 KiB
TypeScript
/*---------------------------------------------------------------------------------------------
|
|
* Copyright (c) Microsoft Corporation. All rights reserved.
|
|
* Licensed under the Source EULA. See License.txt in the project root for license information.
|
|
*--------------------------------------------------------------------------------------------*/
|
|
|
|
import { IThemable } from 'vs/platform/theme/common/styler';
|
|
import * as objects from 'sql/base/common/objects';
|
|
import Event, { Emitter } from 'vs/base/common/event';
|
|
import { Dimension, $, Builder } from 'vs/base/browser/builder';
|
|
import { EventType } from 'vs/base/browser/dom';
|
|
import { IAction } from 'vs/base/common/actions';
|
|
import { IActionOptions, ActionBar } from 'vs/base/browser/ui/actionbar/actionbar';
|
|
import { StandardKeyboardEvent } from 'vs/base/browser/keyboardEvent';
|
|
import { KeyCode } from 'vs/base/common/keyCodes';
|
|
import './panelStyles';
|
|
import { Disposable } from 'vs/base/common/lifecycle';
|
|
|
|
export interface IPanelStyles {
|
|
|
|
}
|
|
|
|
export interface IPanelView {
|
|
render(container: HTMLElement): void;
|
|
layout(dimension: Dimension): void;
|
|
}
|
|
|
|
export interface IPanelTab {
|
|
title: string;
|
|
identifier: string;
|
|
view: IPanelView;
|
|
}
|
|
|
|
interface IInternalPanelTab extends IPanelTab {
|
|
header: Builder;
|
|
label: Builder;
|
|
}
|
|
|
|
export type PanelTabIdentifier = string;
|
|
|
|
export class TabbedPanel extends Disposable implements IThemable {
|
|
private _tabMap = new Map<PanelTabIdentifier, IInternalPanelTab>();
|
|
private _shownTab: PanelTabIdentifier;
|
|
public readonly headersize = 35;
|
|
private $header: Builder;
|
|
private $tabList: Builder;
|
|
private $body: Builder;
|
|
private $parent: Builder;
|
|
private _actionbar: ActionBar;
|
|
private _currentDimensions: Dimension;
|
|
private _collapsed = false;
|
|
|
|
private _onTabChange = new Emitter<PanelTabIdentifier>();
|
|
public onTabChange: Event<PanelTabIdentifier> = this._onTabChange.event;
|
|
|
|
constructor(private container: HTMLElement) {
|
|
super();
|
|
this.$parent = this._register($('.tabbedPanel'));
|
|
this.$parent.appendTo(container);
|
|
this.$header = $('.composite.title');
|
|
this.$tabList = $('.tabList');
|
|
this.$tabList.style('height', this.headersize + 'px');
|
|
this.$header.append(this.$tabList);
|
|
let actionbarcontainer = $('.title-actions');
|
|
this._actionbar = new ActionBar(actionbarcontainer);
|
|
this.$header.append(actionbarcontainer);
|
|
this.$parent.append(this.$header);
|
|
this.$body = $('tabBody');
|
|
this.$parent.append(this.$body);
|
|
}
|
|
|
|
public pushTab(tab: IPanelTab): PanelTabIdentifier {
|
|
let internalTab = objects.clone(tab) as IInternalPanelTab;
|
|
this._tabMap.set(tab.identifier, internalTab);
|
|
this._createTab(internalTab);
|
|
if (!this._shownTab) {
|
|
this.showTab(tab.identifier);
|
|
}
|
|
return tab.identifier as PanelTabIdentifier;
|
|
}
|
|
|
|
public pushAction(arg: IAction | IAction[], options: IActionOptions = {}): void {
|
|
this._actionbar.push(arg, options);
|
|
}
|
|
|
|
public set actionBarContext(context: any) {
|
|
this._actionbar.context = context;
|
|
}
|
|
|
|
private _createTab(tab: IInternalPanelTab): void {
|
|
let tabHeaderElement = $('.tab-header');
|
|
tabHeaderElement.attr('tabindex', '0');
|
|
let tabElement = $('.tab');
|
|
tabHeaderElement.append(tabElement);
|
|
let tabLabel = $('a.tabLabel');
|
|
tabLabel.safeInnerHtml(tab.title);
|
|
tabElement.append(tabLabel);
|
|
tabHeaderElement.on(EventType.CLICK, e => this.showTab(tab.identifier));
|
|
tabHeaderElement.on(EventType.KEY_DOWN, (e: KeyboardEvent) => {
|
|
let event = new StandardKeyboardEvent(e);
|
|
if (event.equals(KeyCode.Enter)) {
|
|
this.showTab(tab.identifier);
|
|
e.stopImmediatePropagation();
|
|
}
|
|
});
|
|
this.$tabList.append(tabHeaderElement);
|
|
tab.header = tabHeaderElement;
|
|
tab.label = tabLabel;
|
|
}
|
|
|
|
public showTab(id: PanelTabIdentifier): void {
|
|
if (this._shownTab && this._shownTab === id) {
|
|
return;
|
|
}
|
|
|
|
if (this._shownTab) {
|
|
this._tabMap.get(this._shownTab).label.removeClass('active');
|
|
this._tabMap.get(this._shownTab).header.removeClass('active');
|
|
}
|
|
|
|
this._shownTab = id;
|
|
this.$body.clearChildren();
|
|
let tab = this._tabMap.get(this._shownTab);
|
|
tab.label.addClass('active');
|
|
tab.header.addClass('active');
|
|
tab.view.render(this.$body.getHTMLElement());
|
|
this._onTabChange.fire(id);
|
|
if (this._currentDimensions) {
|
|
this._layoutCurrentTab(new Dimension(this._currentDimensions.width, this._currentDimensions.height - this.headersize));
|
|
}
|
|
}
|
|
|
|
public removeTab(tab: PanelTabIdentifier) {
|
|
this._tabMap.get(tab).header.destroy();
|
|
this._tabMap.delete(tab);
|
|
}
|
|
|
|
public style(styles: IPanelStyles): void {
|
|
|
|
}
|
|
|
|
public layout(dimension: Dimension): void {
|
|
this._currentDimensions = dimension;
|
|
this.$header.style('width', dimension.width + 'px');
|
|
this.$body.style('width', dimension.width + 'px');
|
|
this.$body.style('height', (dimension.height - this.headersize) + 'px');
|
|
this._layoutCurrentTab(new Dimension(dimension.width, dimension.height - this.headersize));
|
|
}
|
|
|
|
private _layoutCurrentTab(dimension: Dimension): void {
|
|
if (this._shownTab) {
|
|
this._tabMap.get(this._shownTab).view.layout(dimension);
|
|
}
|
|
}
|
|
|
|
public focus(): void {
|
|
|
|
}
|
|
|
|
public set collapsed(val: boolean) {
|
|
if (val === this._collapsed) {
|
|
return;
|
|
}
|
|
|
|
this._collapsed = val === false ? false : true;
|
|
if (this.collapsed) {
|
|
this.$body.offDOM();
|
|
} else {
|
|
this.$parent.append(this.$body);
|
|
}
|
|
}
|
|
|
|
public get collapsed(): boolean {
|
|
return this._collapsed;
|
|
}
|
|
}
|