From 2e77bd0cb1098e1a4a451e92a8678952ab3e24a3 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Torkel=20=C3=96degaard?= Date: Tue, 10 Oct 2017 17:57:53 +0200 Subject: [PATCH] grid: progress on react grid --- public/app/core/directives/dash_edit_link.js | 2 +- public/app/features/dashboard/PanelModel.ts | 15 +++++------ public/app/features/dashboard/all.js | 1 + .../app/features/dashboard/dashboard_ctrl.ts | 14 +++------- .../dashboard/dashgrid/DashboardGrid.tsx | 27 ++++++++++++++----- .../dashboard/dashgrid/PanelContainer.ts | 3 --- .../features/dashboard/dashnav/dashnav.html | 2 +- .../app/features/dashboard/dashnav/dashnav.ts | 8 ++++++ public/app/features/dashboard/model.ts | 11 +++++++- .../features/dashboard/partials/settings.html | 26 +++++++++--------- public/app/features/panel/panel_ctrl.ts | 2 +- public/sass/_variables.dark.scss | 6 ++--- public/sass/_variables.light.scss | 6 ++--- public/sass/components/_modals.scss | 2 +- 14 files changed, 74 insertions(+), 51 deletions(-) diff --git a/public/app/core/directives/dash_edit_link.js b/public/app/core/directives/dash_edit_link.js index a3bac58945c..02c7d55b99e 100644 --- a/public/app/core/directives/dash_edit_link.js +++ b/public/app/core/directives/dash_edit_link.js @@ -123,7 +123,7 @@ function ($, angular, coreModule, _) { }, 10); } - scope.$watch("dashboardViewState.state.editview", function(newValue, oldValue) { + scope.$watch("ctrl.dashboardViewState.state.editview", function(newValue, oldValue) { if (newValue) { showEditorPane(null, {editview: newValue}); } else if (oldValue) { diff --git a/public/app/features/dashboard/PanelModel.ts b/public/app/features/dashboard/PanelModel.ts index 592c21f29fe..f5455dee5ca 100644 --- a/public/app/features/dashboard/PanelModel.ts +++ b/public/app/features/dashboard/PanelModel.ts @@ -8,7 +8,6 @@ export interface GridPos { } const notPersistedProperties: {[str: string]: boolean} = { - "model": true, "events": true, }; @@ -19,26 +18,26 @@ export class PanelModel { title: string; events: Emitter; - constructor(private model) { + constructor(model) { + this.events = new Emitter(); + // copy properties from persisted model for (var property in model) { this[property] = model[property]; } - - this.events = new Emitter(); } getSaveModel() { - this.model = {}; + const model: any = {}; for (var property in this) { if (notPersistedProperties[property] || !this.hasOwnProperty(property)) { - console.log('PanelModel.getSaveModel() skiping property', property); continue; } - this.model[property] = this[property]; + model[property] = this[property]; } - return this.model; + + return model; } updateGridPos(newPos: GridPos) { diff --git a/public/app/features/dashboard/all.js b/public/app/features/dashboard/all.js index 93368e401a5..3871dc3ff85 100644 --- a/public/app/features/dashboard/all.js +++ b/public/app/features/dashboard/all.js @@ -25,6 +25,7 @@ define([ './repeat_option/repeat_option', './dashgrid/DashboardGrid', './dashgrid/PanelLoader', + './row/add_panel', './acl/acl', './folder_picker/picker', './folder_modal/folder' diff --git a/public/app/features/dashboard/dashboard_ctrl.ts b/public/app/features/dashboard/dashboard_ctrl.ts index 98015d666af..02c2825a844 100644 --- a/public/app/features/dashboard/dashboard_ctrl.ts +++ b/public/app/features/dashboard/dashboard_ctrl.ts @@ -3,12 +3,12 @@ import config from 'app/core/config'; import coreModule from 'app/core/core_module'; import {PanelContainer} from './dashgrid/PanelContainer'; import {DashboardModel} from './model'; -import {PanelModel} from './PanelModel'; export class DashboardCtrl implements PanelContainer { dashboard: DashboardModel; dashboardViewState: any; loadedFallbackDashboard: boolean; + editTab: number; /** @ngInject */ constructor( @@ -27,6 +27,9 @@ export class DashboardCtrl implements PanelContainer { // can't use controllerAs on route yet $scope.ctrl = this; + // TODO: break out settings view to separate view & controller + this.editTab = 0; + // funcs called from React component bindings and needs this binding this.getPanelContainer = this.getPanelContainer.bind(this); } @@ -116,15 +119,6 @@ export class DashboardCtrl implements PanelContainer { return this.panelLoader; } - getPanels() { - return this.dashboard.panels; - } - - panelPossitionUpdated(panel: PanelModel) { - //console.log('panel pos updated', panel); - //this.$rootScope.$broadcast('render'); - } - timezoneChanged() { this.$rootScope.$broadcast("refresh"); } diff --git a/public/app/features/dashboard/dashgrid/DashboardGrid.tsx b/public/app/features/dashboard/dashgrid/DashboardGrid.tsx index 93b02c82395..ca819739048 100644 --- a/public/app/features/dashboard/dashgrid/DashboardGrid.tsx +++ b/public/app/features/dashboard/dashgrid/DashboardGrid.tsx @@ -3,13 +3,14 @@ import coreModule from 'app/core/core_module'; import ReactGridLayout from 'react-grid-layout'; import {CELL_HEIGHT, CELL_VMARGIN} from '../model'; import {DashboardPanel} from './DashboardPanel'; +import {DashboardModel} from '../model'; import {PanelContainer} from './PanelContainer'; import {PanelModel} from '../PanelModel'; import sizeMe from 'react-sizeme'; const COLUMN_COUNT = 12; -function GridWrapper({size, layout, onLayoutChange, children}) { +function GridWrapper({size, layout, onLayoutChange, children, onResize}) { if (size.width === 0) { console.log('size is zero!'); } @@ -30,6 +31,7 @@ function GridWrapper({size, layout, onLayoutChange, children}) { rowHeight={CELL_HEIGHT} draggableHandle=".grid-drag-handle" layout={layout} + onResize={onResize} onLayoutChange={onLayoutChange}> {children} @@ -45,20 +47,25 @@ export interface DashboardGridProps { export class DashboardGrid extends React.Component { gridToPanelMap: any; panelContainer: PanelContainer; + dashboard: DashboardModel; panelMap: {[id: string]: PanelModel}; constructor(props) { super(props); this.panelContainer = this.props.getPanelContainer(); this.onLayoutChange = this.onLayoutChange.bind(this); + this.onResize = this.onResize.bind(this); + + // subscribe to dashboard events + this.dashboard = this.panelContainer.getDashboard(); + this.dashboard.on('panel-added', this.panelAdded.bind(this)); } buildLayout() { const layout = []; - const panels = this.panelContainer.getPanels(); this.panelMap = {}; - for (let panel of panels) { + for (let panel of this.dashboard.panels) { let stringId = panel.id.toString(); this.panelMap[stringId] = panel; @@ -85,11 +92,18 @@ export class DashboardGrid extends React.Component { } } + panelAdded() { + this.forceUpdate(); + } + + onResize(layout, oldItem, newItem) { + this.panelMap[newItem.i].updateGridPos(newItem); + } + renderPanels() { - const panels = this.panelContainer.getPanels(); const panelElements = []; - for (let panel of panels) { + for (let panel of this.dashboard.panels) { panelElements.push(
@@ -101,8 +115,9 @@ export class DashboardGrid extends React.Component { } render() { + console.log('DashboardGrid.render()'); return ( - + {this.renderPanels()} ); diff --git a/public/app/features/dashboard/dashgrid/PanelContainer.ts b/public/app/features/dashboard/dashgrid/PanelContainer.ts index 352e771cb41..39f589f44eb 100644 --- a/public/app/features/dashboard/dashgrid/PanelContainer.ts +++ b/public/app/features/dashboard/dashgrid/PanelContainer.ts @@ -1,11 +1,8 @@ -import {PanelModel} from '../PanelModel'; import {DashboardModel}  from '../model'; import {PanelLoader} from './PanelLoader'; export interface PanelContainer { - getPanels(): PanelModel[]; getPanelLoader(): PanelLoader; getDashboard(): DashboardModel; - panelPossitionUpdated(panel: PanelModel); } diff --git a/public/app/features/dashboard/dashnav/dashnav.html b/public/app/features/dashboard/dashnav/dashnav.html index fd1ee180248..e350bc33caa 100644 --- a/public/app/features/dashboard/dashnav/dashnav.html +++ b/public/app/features/dashboard/dashnav/dashnav.html @@ -70,7 +70,7 @@ diff --git a/public/app/features/dashboard/dashnav/dashnav.ts b/public/app/features/dashboard/dashnav/dashnav.ts index 182c722b739..b197c48c649 100644 --- a/public/app/features/dashboard/dashnav/dashnav.ts +++ b/public/app/features/dashboard/dashnav/dashnav.ts @@ -145,6 +145,14 @@ export class DashNavCtrl { this.$rootScope.appEvent('show-dash-search'); } + addPanel() { + this.dashboard.addPanel({ + type: 'graph', + gridPos: {x: 0, y: 0, w: 6, h: 5}, + title: 'New Graph', + }); + } + navItemClicked(navItem, evt) { if (navItem.clickHandler) { navItem.clickHandler(); diff --git a/public/app/features/dashboard/model.ts b/public/app/features/dashboard/model.ts index c467868c789..4ab7dfbec59 100644 --- a/public/app/features/dashboard/model.ts +++ b/public/app/features/dashboard/model.ts @@ -180,7 +180,8 @@ export class DashboardModel { addPanel(panel) { panel.id = this.getNextPanelId(); - this.panels.push(panel); + this.panels.unshift(new PanelModel(panel)); + this.events.emit('panel-added', panel); } removePanel(panel, ask?) { @@ -282,6 +283,14 @@ export class DashboardModel { } } + on(eventName, callback) { + this.events.on(eventName, callback); + } + + off(eventName, callback?) { + this.events.off(eventName, callback); + } + cycleGraphTooltip() { this.graphTooltip = (this.graphTooltip + 1) % 3; } diff --git a/public/app/features/dashboard/partials/settings.html b/public/app/features/dashboard/partials/settings.html index 8c7af5d70cd..6a8f4792f72 100644 --- a/public/app/features/dashboard/partials/settings.html +++ b/public/app/features/dashboard/partials/settings.html @@ -5,7 +5,7 @@
-
+
Details
- +
- +
- +
-
@@ -51,19 +51,19 @@
- +
@@ -79,7 +79,7 @@
- +
@@ -90,7 +90,7 @@
- +
diff --git a/public/app/features/panel/panel_ctrl.ts b/public/app/features/panel/panel_ctrl.ts index 8d927d79b53..35ced744378 100644 --- a/public/app/features/panel/panel_ctrl.ts +++ b/public/app/features/panel/panel_ctrl.ts @@ -178,7 +178,7 @@ export class PanelCtrl { this.calculatePanelHeight(); this.$timeout(() => { this.render(); - }); + }, 100); } duplicate() { diff --git a/public/sass/_variables.dark.scss b/public/sass/_variables.dark.scss index 52761e4bfc6..7eea87b2009 100644 --- a/public/sass/_variables.dark.scss +++ b/public/sass/_variables.dark.scss @@ -105,9 +105,9 @@ $tight-form-bg: $dark-3; $tight-form-func-bg: #333; $tight-form-func-highlight-bg: #444; -$modal-background: $black; -$code-tag-bg: $gray-1; -$code-tag-border: lighten($code-tag-bg, 2%); +$modal-backdrop-bg: $dark-3; +$code-tag-bg: $gray-1; +$code-tag-border: lighten($code-tag-bg, 2%); // Lists diff --git a/public/sass/_variables.light.scss b/public/sass/_variables.light.scss index 1e48d515c4d..1bb58532d67 100644 --- a/public/sass/_variables.light.scss +++ b/public/sass/_variables.light.scss @@ -112,9 +112,9 @@ $tight-form-bg: $gray-6; $tight-form-func-bg: $gray-5; $tight-form-func-highlight-bg: $gray-6; -$modal-background: $body-bg; -$code-tag-bg: $gray-6; -$code-tag-border: darken($code-tag-bg, 3%); +$modal-backdrop-bg: $body-bg; +$code-tag-bg: $gray-6; +$code-tag-border: darken($code-tag-bg, 3%); // Lists $grafanaListBackground: $gray-6; diff --git a/public/sass/components/_modals.scss b/public/sass/components/_modals.scss index 2525f104aa7..14713fbda74 100644 --- a/public/sass/components/_modals.scss +++ b/public/sass/components/_modals.scss @@ -10,7 +10,7 @@ bottom: 0; left: 0; z-index: $zindex-modal-backdrop; - background-color: $black; + background-color: $modal-backdrop-bg; } .modal-backdrop,