mirror of
https://github.com/ckaczor/azuredatastudio.git
synced 2026-01-19 01:25:36 -05:00
Fix few dashboard panel issues (#801)
* home tab is shown by default when the dashboard is opened * add scroll bar when tab list is overflow * fix regression in other tab panels * address comments
This commit is contained in:
@@ -29,6 +29,8 @@ panel {
|
||||
padding: 0;
|
||||
justify-content: flex-start;
|
||||
line-height: 35px;
|
||||
white-space: nowrap;
|
||||
flex: 1;
|
||||
}
|
||||
|
||||
.tabbedPanel .tabList .tab {
|
||||
@@ -61,7 +63,7 @@ panel {
|
||||
}
|
||||
|
||||
.composite.title .title-actions {
|
||||
flex: 1;
|
||||
flex: 1 1 auto;
|
||||
}
|
||||
|
||||
.tab > .tabLabel.active {
|
||||
@@ -87,6 +89,10 @@ panel {
|
||||
height: 100%;
|
||||
}
|
||||
|
||||
.tabbedPanel.vertical .tabList {
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.tabbedPanel > .tab-content {
|
||||
flex: 1;
|
||||
position: relative;
|
||||
@@ -98,4 +104,9 @@ panel {
|
||||
|
||||
.tabbedPanel.horizontal > .title > .tabList {
|
||||
flex-flow: row;
|
||||
}
|
||||
|
||||
.tabbedPanel > .title > .monaco-scrollable-element {
|
||||
flex: 0 1 auto;
|
||||
width: inherit;
|
||||
}
|
||||
@@ -13,6 +13,10 @@ import { ActionBar } from 'vs/base/browser/ui/actionbar/actionbar';
|
||||
import { Action } from 'vs/base/common/actions';
|
||||
import * as types from 'vs/base/common/types';
|
||||
import { mixin } from 'vs/base/common/objects';
|
||||
import { ScrollableElement } from 'vs/base/browser/ui/scrollbar/scrollableElement';
|
||||
import { ScrollbarVisibility } from 'vs/base/common/scrollable';
|
||||
import { addDisposableListener, EventType } from 'vs/base/browser/dom';
|
||||
import { Disposable } from 'vs/base/common/lifecycle';
|
||||
|
||||
export interface IPanelOptions {
|
||||
/**
|
||||
@@ -40,9 +44,10 @@ let idPool = 0;
|
||||
@Component({
|
||||
selector: 'panel',
|
||||
template: `
|
||||
|
||||
<div class="tabbedPanel fullsize" #tabbedPanel>
|
||||
<div *ngIf="!options.showTabsWhenOne ? _tabs.length !== 1 : true" class="composite title">
|
||||
<div class="tabList">
|
||||
<div *ngIf="!options.showTabsWhenOne ? _tabs.length !== 1 : true" class="composite title" #titleContainer>
|
||||
<div class="tabList" #tabList>
|
||||
<div *ngFor="let tab of _tabs">
|
||||
<tab-header [tab]="tab" (onSelectTab)='selectTab($event)' (onCloseTab)='closeTab($event)'> </tab-header>
|
||||
</div>
|
||||
@@ -60,7 +65,7 @@ let idPool = 0;
|
||||
</div>
|
||||
`
|
||||
})
|
||||
export class PanelComponent implements AfterContentInit, OnInit, OnChanges, OnDestroy, AfterViewInit {
|
||||
export class PanelComponent extends Disposable implements AfterContentInit, OnInit, OnChanges, OnDestroy, AfterViewInit {
|
||||
@Input() public options: IPanelOptions;
|
||||
@Input() public actions: Array<Action>;
|
||||
@ContentChildren(TabComponent) private _tabs: QueryList<TabComponent>;
|
||||
@@ -72,10 +77,15 @@ export class PanelComponent implements AfterContentInit, OnInit, OnChanges, OnDe
|
||||
private _activeTab: TabComponent;
|
||||
private _actionbar: ActionBar;
|
||||
private _mru: TabComponent[];
|
||||
private _scrollableElement: ScrollableElement;
|
||||
|
||||
@ViewChild('panelActionbar', { read: ElementRef }) private _actionbarRef: ElementRef;
|
||||
@ViewChild('tabbedPanel', { read: ElementRef }) private _tabbedPanelRef: ElementRef;
|
||||
constructor( @Inject(forwardRef(() => NgZone)) private _zone: NgZone) { }
|
||||
@ViewChild('titleContainer', { read: ElementRef }) private _titleContainer: ElementRef;
|
||||
@ViewChild('tabList', { read: ElementRef }) private _tabList: ElementRef;
|
||||
constructor( @Inject(forwardRef(() => NgZone)) private _zone: NgZone) {
|
||||
super();
|
||||
}
|
||||
|
||||
ngOnInit(): void {
|
||||
this.options = mixin(this.options || {}, defaultOptions, false);
|
||||
@@ -90,6 +100,39 @@ export class PanelComponent implements AfterContentInit, OnInit, OnChanges, OnDe
|
||||
}
|
||||
|
||||
ngAfterViewInit(): void {
|
||||
let container = this._titleContainer.nativeElement as HTMLElement;
|
||||
let tabList = this._tabList.nativeElement as HTMLElement;
|
||||
container.removeChild(tabList);
|
||||
|
||||
this._scrollableElement = new ScrollableElement(tabList, {
|
||||
horizontal: ScrollbarVisibility.Auto,
|
||||
vertical: ScrollbarVisibility.Hidden,
|
||||
scrollYToX: true,
|
||||
useShadows: false,
|
||||
horizontalScrollbarSize: 3
|
||||
});
|
||||
|
||||
this._scrollableElement.onScroll(e => {
|
||||
tabList.scrollLeft = e.scrollLeft;
|
||||
});
|
||||
|
||||
container.insertBefore(this._scrollableElement.getDomNode(), container.firstChild);
|
||||
|
||||
this._scrollableElement.setScrollDimensions({
|
||||
width: tabList.offsetWidth,
|
||||
scrollWidth: tabList.scrollWidth
|
||||
});
|
||||
|
||||
this._register(addDisposableListener(window, EventType.RESIZE, () => {
|
||||
// Todo: Need to set timeout because we have to make sure that the grids have already rearraged before the getContentHeight gets called.
|
||||
setTimeout(() => {
|
||||
this._scrollableElement.setScrollDimensions({
|
||||
width: tabList.offsetWidth,
|
||||
scrollWidth: tabList.scrollWidth
|
||||
});
|
||||
}, 100);
|
||||
}));
|
||||
|
||||
if (this.options.layout === NavigationBarLayout.horizontal) {
|
||||
(<HTMLElement>this._tabbedPanelRef.nativeElement).classList.add(horizontalLayout);
|
||||
} else {
|
||||
|
||||
@@ -174,7 +174,7 @@ export abstract class DashboardPage extends Disposable implements OnDestroy {
|
||||
}));
|
||||
|
||||
this._tabsDispose.push(this.dashboardService.onAddNewTabs(e => {
|
||||
this.loadNewTabs(e);
|
||||
this.loadNewTabs(e, true);
|
||||
}));
|
||||
}
|
||||
|
||||
@@ -188,7 +188,7 @@ export abstract class DashboardPage extends Disposable implements OnDestroy {
|
||||
this.dashboardService.writeSettings([this.context, 'tabs'].join('.'), writeableConfig, target);
|
||||
}
|
||||
|
||||
private loadNewTabs(dashboardTabs: IDashboardTab[]) {
|
||||
private loadNewTabs(dashboardTabs: IDashboardTab[], openLastTab: boolean = false) {
|
||||
if (dashboardTabs && dashboardTabs.length > 0) {
|
||||
let selectedTabs = dashboardTabs.map(v => {
|
||||
let container = dashboardHelper.getDashboardContainer(v.container);
|
||||
@@ -226,10 +226,12 @@ export abstract class DashboardPage extends Disposable implements OnDestroy {
|
||||
return config;
|
||||
});
|
||||
|
||||
// put this immediately on the stack so that is ran *after* the tab is rendered
|
||||
setTimeout(() => {
|
||||
this._panel.selectTab(selectedTabs.pop().id);
|
||||
});
|
||||
if (openLastTab) {
|
||||
// put this immediately on the stack so that is ran *after* the tab is rendered
|
||||
setTimeout(() => {
|
||||
this._panel.selectTab(selectedTabs.pop().id);
|
||||
});
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -9,12 +9,12 @@ panel.dashboard-panel > .tabbedPanel {
|
||||
box-sizing: border-box;
|
||||
}
|
||||
|
||||
panel.dashboard-panel > .tabbedPanel > .title > .tabList .tab-header .tab > .tabLabel.active {
|
||||
panel.dashboard-panel > .tabbedPanel > .title > .monaco-scrollable-element > .tabList .tab-header .tab > .tabLabel.active {
|
||||
border-bottom: 0px solid;
|
||||
}
|
||||
|
||||
panel.dashboard-panel > .tabbedPanel > .title > .title-actions,
|
||||
panel.dashboard-panel > .tabbedPanel > .title > .tabList .tab-header {
|
||||
panel.dashboard-panel > .tabbedPanel > .title > .monaco-scrollable-element > .tabList .tab-header {
|
||||
box-sizing: border-box;
|
||||
border: 1px solid transparent;
|
||||
}
|
||||
@@ -15,21 +15,22 @@ registerThemingParticipant((theme: ITheme, collector: ICssStyleCollector) => {
|
||||
const tabActiveForeground = theme.getColor(TAB_ACTIVE_FOREGROUND);
|
||||
if (tabActiveBackground || tabActiveForeground) {
|
||||
collector.addRule(`
|
||||
panel.dashboard-panel > .tabbedPanel > .title > .tabList .tab:hover .tabLabel,
|
||||
panel.dashboard-panel > .tabbedPanel > .title > .tabList .tab .tabLabel.active {
|
||||
panel.dashboard-panel > .tabbedPanel > .title > .monaco-scrollable-element > .tabList .tab:hover .tabLabel,
|
||||
panel.dashboard-panel > .tabbedPanel > .title > .monaco-scrollable-element > .tabList .tab .tabLabel.active {
|
||||
color: ${tabActiveForeground};
|
||||
border-bottom: 0px solid;
|
||||
}
|
||||
|
||||
panel.dashboard-panel > .tabbedPanel > .title > .tabList .tab-header.active {
|
||||
panel.dashboard-panel > .tabbedPanel > .title > .monaco-scrollable-element > .tabList .tab-header.active {
|
||||
background-color: ${tabActiveBackground};
|
||||
outline-color: ${tabActiveBackground};
|
||||
}
|
||||
|
||||
panel.dashboard-panel > .tabbedPanel.horizontal > .title > .tabList .tab-header.active {
|
||||
panel.dashboard-panel > .tabbedPanel.horizontal > .title > .monaco-scrollable-element > .tabList .tab-header.active {
|
||||
border-bottom-color: transparent;
|
||||
}
|
||||
|
||||
panel.dashboard-panel > .tabbedPanel.vertical > .title > .tabList .tab-header.active {
|
||||
panel.dashboard-panel > .tabbedPanel.vertical > .title > .monaco-scrollable-element > .tabList .tab-header.active {
|
||||
border-right-color: transparent;
|
||||
}
|
||||
`);
|
||||
@@ -38,7 +39,7 @@ registerThemingParticipant((theme: ITheme, collector: ICssStyleCollector) => {
|
||||
const activeTabBorderColor = theme.getColor(TAB_ACTIVE_BORDER);
|
||||
if (activeTabBorderColor) {
|
||||
collector.addRule(`
|
||||
panel.dashboard-panel > .tabbedPanel > .title > .tabList .tab-header.active {
|
||||
panel.dashboard-panel > .tabbedPanel > .title > .monaco-scrollable-element > .tabList .tab-header.active {
|
||||
box-shadow: ${activeTabBorderColor} 0 -1px inset;
|
||||
}
|
||||
`);
|
||||
@@ -49,11 +50,11 @@ registerThemingParticipant((theme: ITheme, collector: ICssStyleCollector) => {
|
||||
const tabInactiveForeground = theme.getColor(TAB_INACTIVE_FOREGROUND);
|
||||
if (tabInactiveBackground || tabInactiveForeground) {
|
||||
collector.addRule(`
|
||||
panel.dashboard-panel > .tabbedPanel > .title > .tabList .tab .tabLabel {
|
||||
panel.dashboard-panel > .tabbedPanel > .title > .monaco-scrollable-element > .tabList .tab .tabLabel {
|
||||
color: ${tabInactiveForeground};
|
||||
}
|
||||
|
||||
panel.dashboard-panel > .tabbedPanel > .title > .tabList .tab-header {
|
||||
panel.dashboard-panel > .tabbedPanel > .title > .monaco-scrollable-element > .tabList .tab-header {
|
||||
background-color: ${tabInactiveBackground};
|
||||
}
|
||||
`);
|
||||
@@ -73,18 +74,10 @@ registerThemingParticipant((theme: ITheme, collector: ICssStyleCollector) => {
|
||||
const tabBoarder = theme.getColor(TAB_BORDER);
|
||||
if (tabBoarder) {
|
||||
collector.addRule(`
|
||||
panel.dashboard-panel > .tabbedPanel > .title > .tabList .tab-header {
|
||||
panel.dashboard-panel > .tabbedPanel > .title > .monaco-scrollable-element > .tabList .tab-header {
|
||||
border-right-color: ${tabBoarder};
|
||||
border-bottom-color: ${tabBoarder};
|
||||
}
|
||||
|
||||
panel.dashboard-panel > .tabbedPanel.horizontal > .title > .title-actions {
|
||||
border-bottom-color: ${tabBoarder};
|
||||
}
|
||||
|
||||
panel.dashboard-panel > .tabbedPanel.vertical > .title > .title-actions {
|
||||
border-right-color: ${tabBoarder};
|
||||
}
|
||||
`);
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user