mirror of
https://github.com/fhem/fhem-mirror.git
synced 2025-01-31 12:49:34 +00:00
see changed file for changes
git-svn-id: https://svn.fhem.de/fhem/trunk@3346 2b470e98-0d58-463d-a4d8-8e2adae1ed80
This commit is contained in:
parent
92b6fc3cd7
commit
504586dcfe
@ -1,3 +1,6 @@
|
||||
Update vom 27.6.2013
|
||||
* "Database Tables" können jetzt über Zeit und Parameter konkretisiert werden
|
||||
* Bug aus Zeitsprüngen entfernt, damit zwischen Monatswechsel Datum korrekt angezeigt wird
|
||||
Update vom 01.5.2013
|
||||
* Performance Verbesserungen der Charts
|
||||
* Statistikberechnungen nach ZoomIn hinzugefügt
|
||||
|
@ -270,14 +270,15 @@ UPD 2013-03-02_01:53:05 770 www/frontend/app/resources/icons/database_refresh.pn
|
||||
UPD 2013-03-02_01:53:05 524 www/frontend/app/resources/icons/resultset_last.png
|
||||
UPD 2013-04-03_07:27:17 733 www/frontend/app/resources/icons/add.png
|
||||
UPD 2013-04-03_07:27:17 389 www/frontend/app/resources/icons/resultset_previous.png
|
||||
UPD 2013-05-01_05:09:36 2154 www/frontend/app/app.js
|
||||
UPD 2013-06-27_09:34:38 2201 www/frontend/app/app.js
|
||||
UPD 2013-05-01_05:10:56 27200 www/frontend/app/view/LineChartPanel.js
|
||||
UPD 2013-04-28_02:00:20 1205 www/frontend/app/view/ChartGridPanel.js
|
||||
UPD 2013-04-03_07:26:40 15793 www/frontend/app/view/DevicePanel.js
|
||||
UPD 2013-05-01_05:10:56 8782 www/frontend/app/view/Viewport.js
|
||||
UPD 2013-04-01_07:05:14 2476 www/frontend/app/view/TableDataGridPanel.js
|
||||
UPD 2013-05-01_05:10:42 76820 www/frontend/app/controller/ChartController.js
|
||||
UPD 2013-05-01_05:10:42 13004 www/frontend/app/controller/MainController.js
|
||||
UPD 2013-06-27_09:35:22 10042 www/frontend/app/view/TableDataGridPanel.js
|
||||
UPD 2013-06-27_09:34:51 77454 www/frontend/app/controller/ChartController.js
|
||||
UPD 2013-06-27_09:34:52 13004 www/frontend/app/controller/MainController.js
|
||||
UPD 2013-06-27_09:34:52 5414 www/frontend/app/controller/TableDataController.js
|
||||
UPD 2013-04-01_07:04:35 202 www/frontend/app/model/ReadingsModel.js
|
||||
UPD 2013-04-01_07:04:36 338 www/frontend/app/model/SavedChartsModel.js
|
||||
UPD 2013-04-01_07:04:34 11535 www/frontend/app/model/ChartModel.js
|
||||
@ -286,5 +287,5 @@ UPD 2013-04-01_07:04:34 685 www/frontend/app/model/TableDataModel.js
|
||||
UPD 2013-04-01_07:04:54 432 www/frontend/app/store/ChartStore.js
|
||||
UPD 2013-04-01_07:04:54 451 www/frontend/app/store/SavedChartsStore.js
|
||||
UPD 2013-04-01_07:04:54 426 www/frontend/app/store/ReadingsStore.js
|
||||
UPD 2013-04-01_07:04:54 1048 www/frontend/app/store/TableDataStore.js
|
||||
UPD 2013-06-27_09:35:10 657 www/frontend/app/store/TableDataStore.js
|
||||
UPD 2013-04-27_06:11:13 439 www/frontend/app/store/DeviceStore.js
|
@ -18,7 +18,8 @@ Ext.application({
|
||||
|
||||
controllers: [
|
||||
'FHEM.controller.MainController',
|
||||
'FHEM.controller.ChartController'
|
||||
'FHEM.controller.ChartController',
|
||||
'FHEM.controller.TableDataController'
|
||||
],
|
||||
|
||||
launch: function() {
|
||||
|
@ -1124,21 +1124,30 @@ Ext.define('FHEM.controller.ChartController', {
|
||||
me.minY2Value = 9999999;
|
||||
|
||||
var starttime = me.getStarttimepicker().getValue(),
|
||||
dbstarttime = Ext.Date.format(starttime, 'Y-m-d H:i:s'),
|
||||
endtime = me.getEndtimepicker().getValue(),
|
||||
dbendtime = Ext.Date.format(endtime, 'Y-m-d H:i:s');
|
||||
dynamicradio = Ext.ComponentQuery.query('radiogroup[name=dynamictime]')[0];
|
||||
|
||||
if(!Ext.isEmpty(starttime) && !Ext.isEmpty(endtime)) {
|
||||
var timediff = Ext.Date.getElapsed(starttime, endtime);
|
||||
if(btn.name === "stepback") {
|
||||
me.getEndtimepicker().setValue(starttime);
|
||||
var newstarttime = Ext.Date.add(starttime, Ext.Date.MILLI, -timediff);
|
||||
me.getStarttimepicker().setValue(newstarttime);
|
||||
if (dynamicradio.getValue().rb === "month") {
|
||||
me.getEndtimepicker().setValue(Ext.Date.getLastDateOfMonth(Ext.Date.add(endtime, Ext.Date.MONTH, -1)));
|
||||
me.getStarttimepicker().setValue(Ext.Date.add(starttime, Ext.Date.MONTH, -1));
|
||||
} else {
|
||||
me.getEndtimepicker().setValue(starttime);
|
||||
var newstarttime = Ext.Date.add(starttime, Ext.Date.MILLI, -timediff);
|
||||
me.getStarttimepicker().setValue(newstarttime);
|
||||
}
|
||||
me.requestChartData(true);
|
||||
} else if (btn.name === "stepforward") {
|
||||
me.getStarttimepicker().setValue(endtime);
|
||||
var newendtime = Ext.Date.add(endtime, Ext.Date.MILLI, timediff);
|
||||
me.getEndtimepicker().setValue(newendtime);
|
||||
if (dynamicradio.getValue().rb === "month") {
|
||||
me.getEndtimepicker().setValue(Ext.Date.getLastDateOfMonth(Ext.Date.add(endtime, Ext.Date.MONTH, +1)));
|
||||
me.getStarttimepicker().setValue(Ext.Date.add(starttime, Ext.Date.MONTH, +1));
|
||||
} else {
|
||||
me.getStarttimepicker().setValue(endtime);
|
||||
var newendtime = Ext.Date.add(endtime, Ext.Date.MILLI, timediff);
|
||||
me.getEndtimepicker().setValue(newendtime);
|
||||
}
|
||||
me.requestChartData(true);
|
||||
}
|
||||
}
|
||||
|
@ -93,7 +93,7 @@ Ext.define('FHEM.controller.MainController', {
|
||||
|
||||
if (Ext.isDefined(FHEM.version)) {
|
||||
var sp = this.getStatustextfield();
|
||||
sp.setText(FHEM.version + "; Frontend Version: 0.7 - 2013-05-01");
|
||||
sp.setText(FHEM.version + "; Frontend Version: 0.8 - 2013-06-27");
|
||||
}
|
||||
|
||||
//setup west accordion / treepanel
|
||||
|
@ -0,0 +1,137 @@
|
||||
/**
|
||||
* The Controller handling Table Data retrieval
|
||||
*/
|
||||
Ext.define('FHEM.controller.TableDataController', {
|
||||
extend: 'Ext.app.Controller',
|
||||
requires: [
|
||||
'FHEM.view.TableDataGridPanel'
|
||||
],
|
||||
|
||||
refs: [
|
||||
{
|
||||
selector: 'button[name=applytablefilter]',
|
||||
ref: 'applytablefilterbtn' //this.getApplytablefilterbtn()
|
||||
}
|
||||
],
|
||||
|
||||
/**
|
||||
* init function to register listeners
|
||||
*/
|
||||
init: function() {
|
||||
this.control({
|
||||
'button[name=applytablefilter]': {
|
||||
click: this.filterTableData
|
||||
}
|
||||
});
|
||||
},
|
||||
|
||||
/**
|
||||
* function handling the filtering of tabledata, preparing querystring
|
||||
*/
|
||||
filterTableData: function() {
|
||||
|
||||
var me = this,
|
||||
devicecombo = Ext.ComponentQuery.query('combo[name=tddevicecombo]')[0],
|
||||
readingscombo = Ext.ComponentQuery.query('combo[name=tdreadingscombo]')[0],
|
||||
checkedradio = Ext.ComponentQuery.query('radiogroup[name=tddynamictime]')[0],
|
||||
starttimepicker = Ext.ComponentQuery.query('datefield[name=tdstarttimepicker]')[0],
|
||||
endtimepicker = Ext.ComponentQuery.query('datefield[name=tdendtimepicker]')[0],
|
||||
gridpanel = Ext.ComponentQuery.query('gridpanel[name=tabledatagridpanel]')[0];
|
||||
|
||||
//check if timerange or dynamic time should be used
|
||||
checkedradio.eachBox(function(box, idx){
|
||||
var date = new Date();
|
||||
if (box.checked) {
|
||||
if (box.inputValue === "year") {
|
||||
starttime = Ext.Date.parse(date.getUTCFullYear() + "-01-01", "Y-m-d");
|
||||
endtime = Ext.Date.parse(date.getUTCFullYear() + 1 + "-01-01", "Y-m-d");
|
||||
} else if (box.inputValue === "month") {
|
||||
starttime = Ext.Date.getFirstDateOfMonth(date);
|
||||
endtime = Ext.Date.getLastDateOfMonth(date);
|
||||
} else if (box.inputValue === "week") {
|
||||
date.setHours(0);
|
||||
date.setMinutes(0);
|
||||
date.setSeconds(0);
|
||||
//monday starts with 0 till sat with 5, sund with -1
|
||||
var dayoffset = date.getDay() - 1,
|
||||
monday,
|
||||
nextmonday;
|
||||
if (dayoffset >= 0) {
|
||||
monday = Ext.Date.add(date, Ext.Date.DAY, -dayoffset);
|
||||
} else {
|
||||
//we have a sunday
|
||||
monday = Ext.Date.add(date, Ext.Date.DAY, -6);
|
||||
}
|
||||
nextmonday = Ext.Date.add(monday, Ext.Date.DAY, 7);
|
||||
|
||||
starttime = monday;
|
||||
endtime = nextmonday;
|
||||
} else if (box.inputValue === "day") {
|
||||
date.setHours(0);
|
||||
date.setMinutes(0);
|
||||
date.setSeconds(0);
|
||||
starttime = date;
|
||||
endtime = Ext.Date.add(date, Ext.Date.DAY, 1);
|
||||
} else if (box.inputValue === "hour") {
|
||||
date.setMinutes(0);
|
||||
date.setSeconds(0);
|
||||
starttime = date;
|
||||
endtime = Ext.Date.add(date, Ext.Date.HOUR, 1);
|
||||
} else {
|
||||
Ext.Msg.alert("Error", "Could not setup the dynamic time.");
|
||||
}
|
||||
dbstarttime = Ext.Date.format(starttime, 'Y-m-d_H:i:s');
|
||||
dbendtime = Ext.Date.format(endtime, 'Y-m-d_H:i:s');
|
||||
|
||||
starttimepicker.setValue(starttime);
|
||||
endtimepicker.setValue(endtime);
|
||||
} else {
|
||||
dbstarttime = Ext.Date.format(starttimepicker.getValue(), 'Y-m-d_H:i:s');
|
||||
dbendtime = Ext.Date.format(endtimepicker.getValue(), 'Y-m-d_H:i:s');
|
||||
}
|
||||
});
|
||||
|
||||
if (Ext.isEmpty(dbstarttime) || Ext.isEmpty(dbendtime)) {
|
||||
Ext.Msg.alert("Error", "Please select a timerange first!");
|
||||
} else {
|
||||
//cleanup store
|
||||
gridpanel.getStore().clearData();
|
||||
|
||||
var firststart = true;
|
||||
|
||||
gridpanel.getStore().on("beforeprefetch", function(store, operation, eOpts) {
|
||||
|
||||
var url = '../../../fhem?cmd=get+' + FHEM.dblogname + '+-+webchart+' + dbstarttime + '+' + dbendtime + '+';
|
||||
if (!Ext.isEmpty(devicecombo.getValue())) {
|
||||
url += devicecombo.getValue();
|
||||
} else {
|
||||
url += '""';
|
||||
}
|
||||
|
||||
url += '+getTableData+""+';
|
||||
if (!Ext.isEmpty(readingscombo.rawValue)) {
|
||||
url += readingscombo.rawValue;
|
||||
} else {
|
||||
url += '""';
|
||||
}
|
||||
url += '+""+""+';
|
||||
if (firststart) {
|
||||
url += "0+";
|
||||
firststart = false;
|
||||
} else {
|
||||
url += operation.start + "+";
|
||||
}
|
||||
url += operation.limit + "&XHR=1"
|
||||
|
||||
if (operation.request) {
|
||||
operation.request.url = url;
|
||||
}
|
||||
|
||||
store.proxy.url = url;
|
||||
});
|
||||
gridpanel.getStore().load();
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
});
|
@ -5,10 +5,10 @@ Ext.define('FHEM.store.TableDataStore', {
|
||||
extend: 'Ext.data.Store',
|
||||
model: 'FHEM.model.TableDataModel',
|
||||
buffered: true,
|
||||
trailingBufferZone: 200,
|
||||
leadingBufferZone: 200,
|
||||
trailingBufferZone: 1000,
|
||||
leadingBufferZone: 1000,
|
||||
//remoteGroup: true,
|
||||
pageSize: 200,
|
||||
pageSize: 1000,
|
||||
proxy: {
|
||||
type: 'ajax',
|
||||
method: 'POST',
|
||||
@ -19,12 +19,5 @@ Ext.define('FHEM.store.TableDataStore', {
|
||||
totalProperty: 'totalCount'
|
||||
}
|
||||
},
|
||||
autoLoad: true,
|
||||
listeners: {
|
||||
beforeprefetch: function(store, operation) {
|
||||
//override stores url to contain start and limit params in our needed notation
|
||||
store.proxy.url = '../../../fhem?cmd=get+' + FHEM.dblogname + '+-+webchart+""+""+""';
|
||||
store.proxy.url += '+getTableData+""+""+""+""+' + operation.start +'+' + operation.limit +'&XHR=1';
|
||||
}
|
||||
}
|
||||
autoLoad: false
|
||||
});
|
@ -17,56 +17,192 @@ Ext.define('FHEM.view.TableDataGridPanel', {
|
||||
|
||||
var me = this;
|
||||
|
||||
var tablestore = Ext.create('FHEM.store.TableDataStore');
|
||||
|
||||
me.items = [
|
||||
{
|
||||
xtype: 'panel',
|
||||
items: [
|
||||
{
|
||||
xtype: 'fieldset',
|
||||
title: 'Configure Database Query',
|
||||
items: [
|
||||
{
|
||||
xtype: 'displayfield',
|
||||
value: 'The configuration of the Databasequery will follow here...'
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
xtype: 'gridpanel',
|
||||
height: 400,
|
||||
collapsible: true,
|
||||
store: tablestore,
|
||||
width: '100%',
|
||||
loadMask: true,
|
||||
selModel: {
|
||||
pruneRemoved: false
|
||||
},
|
||||
multiSelect: true,
|
||||
viewConfig: {
|
||||
trackOver: false
|
||||
},
|
||||
verticalScroller:{
|
||||
//trailingBufferZone: 20, // Keep 200 records buffered in memory behind scroll
|
||||
//leadingBufferZone: 50 // Keep 5000 records buffered in memory ahead of scroll
|
||||
},
|
||||
columns: [
|
||||
{ text: 'TIMESTAMP', dataIndex: 'TIMESTAMP' },
|
||||
{ text: 'DEVICE', dataIndex: 'DEVICE' },
|
||||
{ text: 'TYPE', dataIndex: 'TYPE' },
|
||||
{ text: 'EVENT', dataIndex: 'EVENT' },
|
||||
{ text: 'READING', dataIndex: 'READING' },
|
||||
{ text: 'VALUE', dataIndex: 'VALUE' },
|
||||
{ text: 'UNIT', dataIndex: 'UNIT' }
|
||||
]
|
||||
}
|
||||
]
|
||||
}
|
||||
];
|
||||
|
||||
me.callParent(arguments);
|
||||
|
||||
me.tablestore = Ext.create('FHEM.store.TableDataStore');
|
||||
|
||||
me.devicestore = Ext.create('FHEM.store.DeviceStore', {
|
||||
proxy: {
|
||||
type: 'ajax',
|
||||
noCache: false,
|
||||
method: 'POST',
|
||||
url: '../../../fhem?cmd=get+' + FHEM.dblogname + '+-+webchart+""+""+""+getdevices&XHR=1',
|
||||
reader: {
|
||||
type: 'json',
|
||||
root: 'data',
|
||||
totalProperty: 'totalCount'
|
||||
}
|
||||
},
|
||||
autoLoad: true
|
||||
});
|
||||
|
||||
me.on("afterlayout", function() {
|
||||
|
||||
me.add(
|
||||
{
|
||||
xtype: 'fieldset',
|
||||
title: 'Configure Database Query',
|
||||
maxHeight: 150,
|
||||
items: [
|
||||
{
|
||||
xtype: 'fieldset',
|
||||
layout: 'column',
|
||||
defaults: {
|
||||
margin: '5 5 5 10'
|
||||
},
|
||||
items: [
|
||||
{
|
||||
xtype: 'combobox',
|
||||
name: 'tddevicecombo',
|
||||
fieldLabel: 'Select Device',
|
||||
labelWidth: 90,
|
||||
store: me.devicestore,
|
||||
allowBlank: false,
|
||||
queryMode: 'local',
|
||||
displayField: 'DEVICE',
|
||||
valueField: 'DEVICE',
|
||||
listeners: {
|
||||
select: function(combo) {
|
||||
var device = combo.getValue(),
|
||||
readingscombo = combo.up().down('combobox[name=tdreadingscombo]'),
|
||||
readingsstore = readingscombo.getStore(),
|
||||
readingsproxy = readingsstore.getProxy();
|
||||
|
||||
readingsproxy.url = '../../../fhem?cmd=get+' + FHEM.dblogname + '+-+webchart+""+""+' + device + '+getreadings&XHR=1';
|
||||
readingsstore.load();
|
||||
readingscombo.setDisabled(false);
|
||||
}
|
||||
}
|
||||
},
|
||||
{
|
||||
xtype: 'combobox',
|
||||
name: 'tdreadingscombo',
|
||||
fieldLabel: 'Select Reading',
|
||||
allowBlank: false,
|
||||
disabled: true,
|
||||
labelWidth: 90,
|
||||
inputWidth: 110,
|
||||
store: Ext.create('FHEM.store.ReadingsStore', {
|
||||
proxy: {
|
||||
type: 'ajax',
|
||||
method: 'POST',
|
||||
url: '../../../fhem?cmd=get+' + FHEM.dblogname + '+-+webchart+""+""+-+getreadings&XHR=1',
|
||||
reader: {
|
||||
type: 'json',
|
||||
root: 'data',
|
||||
totalProperty: 'totalCount'
|
||||
}
|
||||
},
|
||||
autoLoad: false
|
||||
}),
|
||||
displayField: 'READING',
|
||||
valueField: 'READING'
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
xtype: 'fieldset',
|
||||
layout: 'column',
|
||||
title: 'Select Timerange',
|
||||
defaults: {
|
||||
margin: '0 0 0 10'
|
||||
},
|
||||
items: [
|
||||
{
|
||||
xtype: 'radiofield',
|
||||
fieldLabel: 'Timerange',
|
||||
labelWidth: 60,
|
||||
name: 'tdrb',
|
||||
checked: true,
|
||||
inputValue: 'timerange',
|
||||
listeners: {
|
||||
change: function(tdrb, newval, oldval) {
|
||||
if (newval === false) {
|
||||
tdrb.up().down('datefield[name=tdstarttimepicker]').setDisabled(true);
|
||||
tdrb.up().down('datefield[name=tdendtimepicker]').setDisabled(true);
|
||||
} else {
|
||||
tdrb.up().down('datefield[name=tdstarttimepicker]').setDisabled(false);
|
||||
tdrb.up().down('datefield[name=tdendtimepicker]').setDisabled(false);
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
{
|
||||
xtype: 'datefield',
|
||||
name: 'tdstarttimepicker',
|
||||
format: 'Y-m-d H:i:s',
|
||||
fieldLabel: 'Starttime',
|
||||
allowBlank: false,
|
||||
labelWidth: 70
|
||||
},
|
||||
{
|
||||
xtype: 'datefield',
|
||||
name: 'tdendtimepicker',
|
||||
format: 'Y-m-d H:i:s',
|
||||
fieldLabel: 'Endtime',
|
||||
allowBlank: false,
|
||||
labelWidth: 70
|
||||
},
|
||||
{
|
||||
xtype: 'radiogroup',
|
||||
name: 'tddynamictime',
|
||||
fieldLabel: 'or select a dynamic time',
|
||||
labelWidth: 140,
|
||||
allowBlank: true,
|
||||
defaults: {
|
||||
labelWidth: 42,
|
||||
padding: "0 25px 0 0",
|
||||
checked: false
|
||||
},
|
||||
items: [
|
||||
{ fieldLabel: 'yearly', name: 'tdrb', inputValue: 'year' },
|
||||
{ fieldLabel: 'monthly', name: 'tdrb', inputValue: 'month' },
|
||||
{ fieldLabel: 'weekly', name: 'tdrb', inputValue: 'week' },
|
||||
{ fieldLabel: 'daily', name: 'tdrb', inputValue: 'day' },
|
||||
{ fieldLabel: 'hourly', name: 'tdrb', inputValue: 'hour' }
|
||||
]
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
xtype: 'button',
|
||||
text: 'Apply Filter',
|
||||
name: 'applytablefilter',
|
||||
width: '120'
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
xtype: 'gridpanel',
|
||||
maxHeight: me.up().getHeight() - 290,
|
||||
name: 'tabledatagridpanel',
|
||||
store: me.tablestore,
|
||||
width: '100%',
|
||||
loadMask: true,
|
||||
selModel: {
|
||||
pruneRemoved: false
|
||||
},
|
||||
multiSelect: true,
|
||||
viewConfig: {
|
||||
trackOver: false
|
||||
},
|
||||
verticalScroller:{
|
||||
//trailingBufferZone: 20, // Keep 200 records buffered in memory behind scroll
|
||||
//leadingBufferZone: 50 // Keep 5000 records buffered in memory ahead of scroll
|
||||
},
|
||||
columns: [
|
||||
{ text: 'TIMESTAMP', dataIndex: 'TIMESTAMP', width: 240, sortable: false },
|
||||
{ text: 'DEVICE', dataIndex: 'DEVICE', width: '10%', sortable: false },
|
||||
{ text: 'TYPE', dataIndex: 'TYPE', width: '7%', sortable: false },
|
||||
{ text: 'EVENT', dataIndex: 'EVENT', width: '20%', sortable: false },
|
||||
{ text: 'READING', dataIndex: 'READING', width: '12%', sortable: false },
|
||||
{ text: 'VALUE', dataIndex: 'VALUE', width: '20%', sortable: false },
|
||||
{ text: 'UNIT', dataIndex: 'UNIT', width: '5%', sortable: false }
|
||||
]
|
||||
}
|
||||
);
|
||||
}, me, {single: true});
|
||||
|
||||
}
|
||||
|
||||
});
|
||||
|
Loading…
Reference in New Issue
Block a user