aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAnton Tananaev <anton.tananaev@gmail.com>2017-09-14 22:59:54 +1200
committerGitHub <noreply@github.com>2017-09-14 22:59:54 +1200
commitca960df40e15d7bfb88d2e0e41a269d4b069058c (patch)
tree0b41508a3f856700c353e5a5082c6ea829f13d43
parent4193ac77fd9f0da264284a6f73601963995554c8 (diff)
parentbe47d612285d484e2d0a2aa43174fb8e36acd816 (diff)
downloadtrackermap-web-ca960df40e15d7bfb88d2e0e41a269d4b069058c.tar.gz
trackermap-web-ca960df40e15d7bfb88d2e0e41a269d4b069058c.tar.bz2
trackermap-web-ca960df40e15d7bfb88d2e0e41a269d4b069058c.zip
Merge pull request #585 from Abyss777/saved_commands
Implement Saved Commands
-rw-r--r--web/app/Application.js6
-rw-r--r--web/app/AttributeFormatter.js7
-rw-r--r--web/app/controller/Root.js2
-rw-r--r--web/app/model/Command.js6
-rw-r--r--web/app/model/KnownCommand.js3
-rw-r--r--web/app/model/Server.js3
-rw-r--r--web/app/model/User.js3
-rw-r--r--web/app/store/AllCommandTypes.js (renamed from web/app/view/permissions/DeviceGeofences.js)31
-rw-r--r--web/app/store/AllCommands.js30
-rw-r--r--web/app/store/Commands.js30
-rw-r--r--web/app/store/DeviceCommands.js32
-rw-r--r--web/app/view/SettingsMenu.js6
-rw-r--r--web/app/view/SettingsMenuController.js11
-rw-r--r--web/app/view/dialog/BaseEditController.js2
-rw-r--r--web/app/view/dialog/Command.js69
-rw-r--r--web/app/view/dialog/SavedCommand.js82
-rw-r--r--web/app/view/dialog/SavedCommandController.js (renamed from web/app/view/dialog/CommandController.js)49
-rw-r--r--web/app/view/dialog/SendCommand.js104
-rw-r--r--web/app/view/dialog/SendCommandController.js96
-rw-r--r--web/app/view/dialog/Server.js6
-rw-r--r--web/app/view/dialog/User.js8
-rw-r--r--web/app/view/dialog/UserController.js1
-rw-r--r--web/app/view/edit/Devices.js41
-rw-r--r--web/app/view/edit/DevicesController.js45
-rw-r--r--web/app/view/edit/Groups.js8
-rw-r--r--web/app/view/edit/GroupsController.js31
-rw-r--r--web/app/view/edit/SavedCommands.js (renamed from web/app/view/permissions/GroupAttributes.js)46
-rw-r--r--web/app/view/edit/SavedCommandsController.js (renamed from web/app/view/permissions/GroupGeofences.js)25
-rw-r--r--web/app/view/edit/Users.js8
-rw-r--r--web/app/view/edit/UsersController.js45
-rw-r--r--web/app/view/permissions/Calendars.js (renamed from web/app/view/permissions/UserCalendars.js)4
-rw-r--r--web/app/view/permissions/ComputedAttributes.js (renamed from web/app/view/permissions/UserAttributes.js)4
-rw-r--r--web/app/view/permissions/DeviceDrivers.js44
-rw-r--r--web/app/view/permissions/Devices.js (renamed from web/app/view/permissions/UserDevices.js)4
-rw-r--r--web/app/view/permissions/Drivers.js (renamed from web/app/view/permissions/UserDrivers.js)4
-rw-r--r--web/app/view/permissions/Geofences.js (renamed from web/app/view/permissions/UserGeofences.js)4
-rw-r--r--web/app/view/permissions/GroupDrivers.js44
-rw-r--r--web/app/view/permissions/Groups.js (renamed from web/app/view/permissions/UserGroups.js)4
-rw-r--r--web/app/view/permissions/SavedCommands.js (renamed from web/app/view/permissions/DeviceAttributes.js)21
-rw-r--r--web/app/view/permissions/Users.js (renamed from web/app/view/permissions/UserUsers.js)4
-rw-r--r--web/l10n/en.json4
41 files changed, 652 insertions, 325 deletions
diff --git a/web/app/Application.js b/web/app/Application.js
index dee3889b..d2ce3c8f 100644
--- a/web/app/Application.js
+++ b/web/app/Application.js
@@ -96,7 +96,11 @@ Ext.define('Traccar.Application', {
'Drivers',
'AllDrivers',
'KnownCommands',
- 'VolumeUnits'
+ 'VolumeUnits',
+ 'AllCommandTypes',
+ 'Commands',
+ 'AllCommands',
+ 'DeviceCommands'
],
controllers: [
diff --git a/web/app/AttributeFormatter.js b/web/app/AttributeFormatter.js
index 8a9e3dca..289aff91 100644
--- a/web/app/AttributeFormatter.js
+++ b/web/app/AttributeFormatter.js
@@ -130,6 +130,11 @@ Ext.define('Traccar.AttributeFormatter', {
return null;
},
+ commandTypeFormatter: function (value) {
+ var name = Strings['command' + value.charAt(0).toUpperCase() + value.slice(1)];
+ return name ? name : value;
+ },
+
defaultFormatter: function (value) {
if (typeof value === 'number') {
return Number(value.toFixed(Traccar.Style.numberPrecision));
@@ -175,6 +180,8 @@ Ext.define('Traccar.AttributeFormatter', {
return this.volumeFormatter;
case 'driverUniqueId':
return this.driverUniqueIdFormatter;
+ case 'commandType':
+ return this.commandTypeFormatter;
default:
return this.defaultFormatter;
}
diff --git a/web/app/controller/Root.js b/web/app/controller/Root.js
index acdd4018..64227aa0 100644
--- a/web/app/controller/Root.js
+++ b/web/app/controller/Root.js
@@ -111,6 +111,8 @@ Ext.define('Traccar.controller.Root', {
Ext.getStore('Geofences').load();
Ext.getStore('Calendars').load();
Ext.getStore('ComputedAttributes').load();
+ Ext.getStore('AllCommandTypes').load();
+ Ext.getStore('Commands').load();
this.initReportEventTypesStore();
Ext.getStore('ServerAttributes').loadData(Ext.getStore('CommonDeviceAttributes').getData().items, true);
diff --git a/web/app/model/Command.js b/web/app/model/Command.js
index 789c3647..f64d2a4b 100644
--- a/web/app/model/Command.js
+++ b/web/app/model/Command.js
@@ -20,6 +20,12 @@ Ext.define('Traccar.model.Command', {
identifier: 'negative',
fields: [{
+ name: 'id',
+ type: 'int'
+ }, {
+ name: 'description',
+ type: 'string'
+ }, {
name: 'deviceId',
type: 'int'
}, {
diff --git a/web/app/model/KnownCommand.js b/web/app/model/KnownCommand.js
index 08213020..06610e32 100644
--- a/web/app/model/KnownCommand.js
+++ b/web/app/model/KnownCommand.js
@@ -25,8 +25,7 @@ Ext.define('Traccar.model.KnownCommand', {
}, {
name: 'name',
convert: function (v, rec) {
- var name = Strings['command' + rec.get('type').charAt(0).toUpperCase() + rec.get('type').slice(1)];
- return name ? name : rec.get('type');
+ return Traccar.AttributeFormatter.getFormatter('commandType')(rec.get('type'));
},
depends: ['type']
}, {
diff --git a/web/app/model/Server.js b/web/app/model/Server.js
index b8a88756..da1618bf 100644
--- a/web/app/model/Server.js
+++ b/web/app/model/Server.js
@@ -32,6 +32,9 @@ Ext.define('Traccar.model.Server', {
name: 'deviceReadonly',
type: 'boolean'
}, {
+ name: 'limitCommands',
+ type: 'boolean'
+ }, {
name: 'map',
type: 'string'
}, {
diff --git a/web/app/model/User.js b/web/app/model/User.js
index c47a8d16..e8771b9b 100644
--- a/web/app/model/User.js
+++ b/web/app/model/User.js
@@ -75,6 +75,9 @@ Ext.define('Traccar.model.User', {
name: 'deviceReadonly',
type: 'boolean'
}, {
+ name: 'limitCommands',
+ type: 'boolean'
+ }, {
name: 'token',
type: 'string'
}, {
diff --git a/web/app/view/permissions/DeviceGeofences.js b/web/app/store/AllCommandTypes.js
index c16bceda..aac9d599 100644
--- a/web/app/view/permissions/DeviceGeofences.js
+++ b/web/app/store/AllCommandTypes.js
@@ -1,5 +1,6 @@
/*
- * Copyright 2016 - 2017 Anton Tananaev (anton@traccar.org)
+ * Copyright 2017 Anton Tananaev (anton@traccar.org)
+ * Copyright 2017 Andrey Kunitsyn (andrey@traccar.org)
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
@@ -15,23 +16,17 @@
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
-Ext.define('Traccar.view.permissions.DeviceGeofences', {
- extend: 'Traccar.view.permissions.Base',
- xtype: 'deviceGeofencesView',
+Ext.define('Traccar.store.AllCommandTypes', {
+ extend: 'Ext.data.Store',
+ model: 'Traccar.model.KnownCommand',
- requires: [
- 'Ext.grid.filters.Filters'
- ],
-
- plugins: 'gridfilters',
-
- columns: {
- items: [{
- text: Strings.sharedName,
- dataIndex: 'name',
- flex: 1,
- minWidth: Traccar.Style.columnWidthNormal,
- filter: 'string'
- }]
+ proxy: {
+ type: 'rest',
+ url: 'api/commandtypes',
+ listeners: {
+ 'exception': function (proxy, response) {
+ Traccar.app.showError(response);
+ }
+ }
}
});
diff --git a/web/app/store/AllCommands.js b/web/app/store/AllCommands.js
new file mode 100644
index 00000000..7f5e1253
--- /dev/null
+++ b/web/app/store/AllCommands.js
@@ -0,0 +1,30 @@
+/*
+ * Copyright 2017 Anton Tananaev (anton@traccar.org)
+ * Copyright 2017 Andrey Kunitsyn (andrey@traccar.org)
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+Ext.define('Traccar.store.AllCommands', {
+ extend: 'Ext.data.Store',
+ model: 'Traccar.model.Command',
+
+ proxy: {
+ type: 'rest',
+ url: 'api/commands',
+ extraParams: {
+ all: true
+ }
+ }
+});
diff --git a/web/app/store/Commands.js b/web/app/store/Commands.js
new file mode 100644
index 00000000..3e5b7604
--- /dev/null
+++ b/web/app/store/Commands.js
@@ -0,0 +1,30 @@
+/*
+ * Copyright 2017 Anton Tananaev (anton@traccar.org)
+ * Copyright 2017 Andrey Kunitsyn (andrey@traccar.org)
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+Ext.define('Traccar.store.Commands', {
+ extend: 'Ext.data.Store',
+ model: 'Traccar.model.Command',
+
+ proxy: {
+ type: 'rest',
+ url: 'api/commands',
+ writer: {
+ writeAllFields: true
+ }
+ }
+});
diff --git a/web/app/store/DeviceCommands.js b/web/app/store/DeviceCommands.js
new file mode 100644
index 00000000..7233b3ba
--- /dev/null
+++ b/web/app/store/DeviceCommands.js
@@ -0,0 +1,32 @@
+/*
+ * Copyright 2017 Anton Tananaev (anton@traccar.org)
+ * Copyright 2017 Andrey Kunitsyn (andrey@traccar.org)
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+Ext.define('Traccar.store.DeviceCommands', {
+ extend: 'Ext.data.Store',
+ model: 'Traccar.model.Command',
+
+ proxy: {
+ type: 'rest',
+ url: 'api/commands/send',
+ listeners: {
+ 'exception': function (proxy, response) {
+ Traccar.app.showError(response);
+ }
+ }
+ }
+});
diff --git a/web/app/view/SettingsMenu.js b/web/app/view/SettingsMenu.js
index 7fb76361..9ef12a3c 100644
--- a/web/app/view/SettingsMenu.js
+++ b/web/app/view/SettingsMenu.js
@@ -97,6 +97,12 @@ Ext.define('Traccar.view.SettingsMenu', {
handler: 'onCalendarsClick',
reference: 'settingsCalendarsButton'
}, {
+ hidden: true,
+ text: Strings.sharedSavedCommands,
+ glyph: 'xf093@FontAwesome',
+ handler: 'onCommandsClick',
+ reference: 'settingsCommandsButton'
+ }, {
text: Strings.loginLogout,
glyph: 'xf08b@FontAwesome',
handler: 'onLogoutClick'
diff --git a/web/app/view/SettingsMenuController.js b/web/app/view/SettingsMenuController.js
index 5968a537..caa57a67 100644
--- a/web/app/view/SettingsMenuController.js
+++ b/web/app/view/SettingsMenuController.js
@@ -32,6 +32,7 @@ Ext.define('Traccar.view.SettingsMenuController', {
'Traccar.view.Statistics',
'Traccar.view.dialog.DeviceDistance',
'Traccar.view.edit.Calendars',
+ 'Traccar.view.edit.SavedCommands',
'Traccar.view.BaseWindow'
],
@@ -58,6 +59,7 @@ Ext.define('Traccar.view.SettingsMenuController', {
Traccar.app.getBooleanAttributePreference('ui.disableCalendars'));
this.lookupReference('settingsDriversButton').setHidden(
Traccar.app.getVehicleFeaturesDisabled() || Traccar.app.getBooleanAttributePreference('ui.disableDrivers'));
+ this.lookupReference('settingsCommandsButton').setHidden(Traccar.app.getPreference('limitCommands', false));
}
if (admin || !deviceReadonly && !readonly) {
this.lookupReference('settingsComputedAttributesButton').setHidden(
@@ -159,6 +161,15 @@ Ext.define('Traccar.view.SettingsMenuController', {
}).show();
},
+ onCommandsClick: function () {
+ Ext.create('Traccar.view.BaseWindow', {
+ title: Strings.sharedSavedCommands,
+ items: {
+ xtype: 'savedCommandsView'
+ }
+ }).show();
+ },
+
onLogoutClick: function () {
Ext.create('Traccar.view.dialog.LoginController').logout();
}
diff --git a/web/app/view/dialog/BaseEditController.js b/web/app/view/dialog/BaseEditController.js
index f58b6cb7..91379e2d 100644
--- a/web/app/view/dialog/BaseEditController.js
+++ b/web/app/view/dialog/BaseEditController.js
@@ -43,7 +43,7 @@ Ext.define('Traccar.view.dialog.BaseEditController', {
} else {
record.save();
}
- button.up('window').close();
+ this.closeView();
},
showAttributesView: function (button) {
diff --git a/web/app/view/dialog/Command.js b/web/app/view/dialog/Command.js
deleted file mode 100644
index ce5b75b8..00000000
--- a/web/app/view/dialog/Command.js
+++ /dev/null
@@ -1,69 +0,0 @@
-/*
- * Copyright 2015 - 2017 Anton Tananaev (anton@traccar.org)
- *
- * This program is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program. If not, see <http://www.gnu.org/licenses/>.
- */
-
-Ext.define('Traccar.view.dialog.Command', {
- extend: 'Traccar.view.dialog.Base',
-
- requires: [
- 'Traccar.view.dialog.CommandController'
- ],
-
- controller: 'command',
- title: Strings.commandTitle,
-
- items: {
- xtype: 'form',
- listeners: {
- validitychange: 'onValidityChange'
- },
- items: [{
- xtype: 'checkboxfield',
- name: 'textChannel',
- reference: 'textChannelCheckBox',
- inputValue: true,
- uncheckedValue: false,
- fieldLabel: Strings.notificationSms,
- listeners: {
- change: 'onTextChannelChange'
- }
- }, {
- xtype: 'combobox',
- name: 'type',
- reference: 'commandType',
- fieldLabel: Strings.sharedType,
- store: 'CommandTypes',
- displayField: 'name',
- valueField: 'type',
- editable: false,
- listeners: {
- select: 'onSelect'
- }
- }, {
- xtype: 'fieldcontainer',
- reference: 'parameters'
- }]
- },
-
- buttons: [{
- text: Strings.commandSend,
- reference: 'sendButton',
- handler: 'onSendClick'
- }, {
- text: Strings.sharedCancel,
- handler: 'closeView'
- }]
-});
diff --git a/web/app/view/dialog/SavedCommand.js b/web/app/view/dialog/SavedCommand.js
new file mode 100644
index 00000000..4759143a
--- /dev/null
+++ b/web/app/view/dialog/SavedCommand.js
@@ -0,0 +1,82 @@
+/*
+ * Copyright 2015 - 2017 Anton Tananaev (anton@traccar.org)
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+Ext.define('Traccar.view.dialog.SavedCommand', {
+ extend: 'Traccar.view.dialog.BaseEdit',
+
+ requires: [
+ 'Traccar.view.dialog.SavedCommandController'
+ ],
+
+ controller: 'savedCommand',
+ title: Strings.sharedSavedCommand,
+
+ items: [{
+ xtype: 'form',
+ listeners: {
+ validitychange: 'onValidityChange'
+ },
+ items: [{
+ xtype: 'fieldset',
+ title: Strings.sharedRequired,
+ items: [{
+ xtype: 'textfield',
+ name: 'description',
+ fieldLabel: Strings.sharedDescription
+ }, {
+ xtype: 'checkboxfield',
+ name: 'textChannel',
+ inputValue: true,
+ uncheckedValue: false,
+ fieldLabel: Strings.notificationSms
+ }, {
+ xtype: 'combobox',
+ name: 'type',
+ reference: 'commandType',
+ fieldLabel: Strings.sharedType,
+ store: 'AllCommandTypes',
+ queryMode: 'local',
+ displayField: 'name',
+ valueField: 'type',
+ editable: false,
+ allowBlank: false,
+ listeners: {
+ change: 'onTypeChange'
+ }
+ }, {
+ xtype: 'fieldcontainer',
+ reference: 'parameters'
+ }]
+ }]
+ }],
+
+ buttons: [{
+ glyph: 'xf00c@FontAwesome',
+ reference: 'saveButton',
+ tooltip: Strings.sharedSave,
+ tooltipType: 'title',
+ minWidth: 0,
+ disabled: true,
+ handler: 'onSaveClick'
+ }, {
+ glyph: 'xf00d@FontAwesome',
+ tooltip: Strings.sharedCancel,
+ tooltipType: 'title',
+ minWidth: 0,
+ handler: 'closeView'
+ }]
+});
diff --git a/web/app/view/dialog/CommandController.js b/web/app/view/dialog/SavedCommandController.js
index 0687f670..37c56603 100644
--- a/web/app/view/dialog/CommandController.js
+++ b/web/app/view/dialog/SavedCommandController.js
@@ -15,18 +15,19 @@
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
-Ext.define('Traccar.view.dialog.CommandController', {
- extend: 'Ext.app.ViewController',
- alias: 'controller.command',
+Ext.define('Traccar.view.dialog.SavedCommandController', {
+ extend: 'Traccar.view.dialog.BaseEditController',
+ alias: 'controller.savedCommand',
defaultFieldConfig: {
allowBlank: false
},
- onSelect: function (selected) {
- var i, config, command, parameters, parameter;
+ onTypeChange: function (combo, newValue) {
+ var i, config, command, parameters, parameter, record;
+ record = combo.up('window').down('form').getRecord();
this.lookupReference('parameters').removeAll();
- command = Ext.getStore('KnownCommands').getById(selected.getValue());
+ command = Ext.getStore('KnownCommands').getById(newValue);
if (command && command.get('parameters')) {
parameters = command.get('parameters');
for (i = 0; i < parameters.length; i++) {
@@ -34,6 +35,10 @@ Ext.define('Traccar.view.dialog.CommandController', {
config = Ext.clone(this.defaultFieldConfig);
config.key = parameter.get('key');
config.fieldLabel = parameter.get('name');
+ if (record.get('attributes')) {
+ config.value = record.get('attributes')[parameter.get('key')];
+ }
+ config.disabled = combo.isDisabled();
switch (parameter.get('valueType')) {
case 'number':
config.xtype = 'customNumberField';
@@ -67,8 +72,8 @@ Ext.define('Traccar.view.dialog.CommandController', {
}
},
- onSendClick: function (button) {
- var i, record, form, parameters, attributes = {};
+ fillAttributes: function (button) {
+ var i, form, record, parameters, attributes = {};
form = button.up('window').down('form');
form.updateRecord();
@@ -80,31 +85,15 @@ Ext.define('Traccar.view.dialog.CommandController', {
}
record.set('attributes', attributes);
-
- Ext.Ajax.request({
- scope: this,
- url: 'api/commands',
- jsonData: record.getData(),
- callback: this.onSendResult
- });
- },
-
- onValidityChange: function (form, valid) {
- this.lookupReference('sendButton').setDisabled(!valid);
},
- onTextChannelChange: function (checkbox, newValue) {
- var typesStore = this.lookupReference('commandType').getStore();
- typesStore.getProxy().setExtraParam('textChannel', newValue);
- typesStore.reload();
+ onSaveClick: function (button) {
+ this.fillAttributes(button);
+ this.callParent(arguments);
},
- onSendResult: function (options, success, response) {
- if (success) {
- this.closeView();
- Traccar.app.showToast(Strings.commandSent);
- } else {
- Traccar.app.showError(response);
- }
+ onValidityChange: function (form, valid) {
+ this.lookupReference('saveButton').setDisabled(!valid);
}
+
});
diff --git a/web/app/view/dialog/SendCommand.js b/web/app/view/dialog/SendCommand.js
new file mode 100644
index 00000000..f4224bec
--- /dev/null
+++ b/web/app/view/dialog/SendCommand.js
@@ -0,0 +1,104 @@
+/*
+ * Copyright 2017 Anton Tananaev (anton@traccar.org)
+ * Copyright 2017 Andrey Kunitsyn (andrey@traccar.org)
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+Ext.define('Traccar.view.dialog.SendCommand', {
+ extend: 'Traccar.view.dialog.Base',
+
+ requires: [
+ 'Traccar.view.dialog.SendCommandController'
+ ],
+
+ controller: 'sendCommand',
+ title: Strings.commandTitle,
+
+ items: [{
+ xtype: 'combobox',
+ reference: 'commandsComboBox',
+ fieldLabel: Strings.deviceCommand,
+ displayField: 'description',
+ valueField: 'id',
+ store: 'DeviceCommands',
+ queryMode: 'local',
+ editable: false,
+ allowBlank: false,
+ listeners: {
+ select: 'onCommandSelect'
+ }
+ }, {
+ xtype: 'form',
+ listeners: {
+ validitychange: 'onValidityChange'
+ },
+ items: [{
+ xtype: 'fieldset',
+ reference: 'newCommandFields',
+ disabled: true,
+ items: [{
+ xtype: 'checkboxfield',
+ name: 'textChannel',
+ reference: 'textChannelCheckBox',
+ inputValue: true,
+ uncheckedValue: false,
+ fieldLabel: Strings.notificationSms,
+ listeners: {
+ change: 'onTextChannelChange'
+ }
+ }, {
+ xtype: 'combobox',
+ name: 'type',
+ reference: 'commandType',
+ fieldLabel: Strings.sharedType,
+ store: 'CommandTypes',
+ displayField: 'name',
+ valueField: 'type',
+ editable: false,
+ allowBlank: false,
+ listeners: {
+ change: 'onTypeChange'
+ }
+ }, {
+ xtype: 'fieldcontainer',
+ reference: 'parameters'
+ }]
+ }]
+ }],
+
+ buttons: [{
+ glyph: 'xf093@FontAwesome',
+ text: Strings.sharedSavedCommands,
+ reference: 'linkButton',
+ handler: 'onLinkCommands',
+ hidden: true
+ }, {
+ xtype: 'tbfill'
+ }, {
+ glyph: 'xf093@FontAwesome',
+ tooltip: Strings.sharedSend,
+ tooltipType: 'title',
+ minWidth: 0,
+ disabled: true,
+ reference: 'sendButton',
+ handler: 'onSendClick'
+ }, {
+ glyph: 'xf00d@FontAwesome',
+ tooltip: Strings.sharedCancel,
+ tooltipType: 'title',
+ minWidth: 0,
+ handler: 'closeView'
+ }]
+});
diff --git a/web/app/view/dialog/SendCommandController.js b/web/app/view/dialog/SendCommandController.js
new file mode 100644
index 00000000..0e9442ab
--- /dev/null
+++ b/web/app/view/dialog/SendCommandController.js
@@ -0,0 +1,96 @@
+/*
+ * Copyright 2017 Anton Tananaev (anton@traccar.org)
+ * Copyright 2017 Andrey Kunitsyn (andrey@traccar.org)
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+Ext.define('Traccar.view.dialog.SendCommandController', {
+ extend: 'Traccar.view.dialog.SavedCommandController',
+ alias: 'controller.sendCommand',
+
+ requires: [
+ 'Traccar.view.permissions.SavedCommands'
+ ],
+
+ init: function () {
+ this.lookupReference('linkButton').setHidden(Traccar.app.getPreference('limitCommands', false));
+ },
+
+ onSendClick: function (button) {
+ var record;
+ this.fillAttributes(button);
+ record = button.up('window').down('form').getRecord();
+
+ Ext.Ajax.request({
+ scope: this,
+ url: 'api/commands/send',
+ jsonData: record.getData(),
+ callback: this.onSendResult
+ });
+ },
+
+ onValidityChange: function (form, valid) {
+ this.lookupReference('sendButton').setDisabled(!valid ||
+ this.lookupReference('commandsComboBox').getValue() === null);
+ },
+
+ onTextChannelChange: function (checkbox, newValue) {
+ var typesStore = this.lookupReference('commandType').getStore();
+ typesStore.getProxy().setExtraParam('textChannel', newValue);
+ typesStore.reload();
+ },
+
+ onCommandSelect: function (selected) {
+ var record, form, command = selected.getStore().getById(selected.getValue());
+ command.set('deviceId', this.getView().deviceId);
+ form = selected.up('window').down('form');
+ record = form.getRecord();
+ form.loadRecord(command);
+ if (record && command.get('type') === record.get('type')) {
+ this.onTypeChange(this.lookupReference('commandType'), command.get('type'));
+ }
+
+ this.lookupReference('newCommandFields').setDisabled(command.getId() !== 0);
+ this.lookupReference('textChannelCheckBox').setDisabled(command.getId() !== 0 || !this.getView().online);
+ this.lookupReference('sendButton').setDisabled(command.getId() === 0);
+ },
+
+ onLinkCommands: function () {
+ Ext.create('Traccar.view.BaseWindow', {
+ title: Strings.sharedSavedCommands,
+ items: {
+ xtype: 'linkSavedCommandsView',
+ baseObjectName: 'deviceId',
+ linkObjectName: 'commandId',
+ storeName: 'Commands',
+ baseObject: this.getView().deviceId
+ }
+ }).show();
+ },
+
+ onSendResult: function (options, success, response) {
+ if (success) {
+ this.closeView();
+ Traccar.app.showToast(Strings.commandSent);
+ } else {
+ Traccar.app.showError(response);
+ }
+ },
+
+ closeView: function () {
+ this.lookupReference('commandsComboBox').getStore().removeAll();
+ this.callParent(arguments);
+ }
+});
diff --git a/web/app/view/dialog/Server.js b/web/app/view/dialog/Server.js
index b6343f3c..1fe2184c 100644
--- a/web/app/view/dialog/Server.js
+++ b/web/app/view/dialog/Server.js
@@ -107,6 +107,12 @@ Ext.define('Traccar.view.dialog.Server', {
uncheckedValue: false,
name: 'deviceReadonly',
fieldLabel: Strings.userDeviceReadonly
+ }, {
+ xtype: 'checkboxfield',
+ inputValue: true,
+ uncheckedValue: false,
+ name: 'limitCommands',
+ fieldLabel: Strings.userLimitCommands
}]
}]
},
diff --git a/web/app/view/dialog/User.js b/web/app/view/dialog/User.js
index 43990a54..36bccfeb 100644
--- a/web/app/view/dialog/User.js
+++ b/web/app/view/dialog/User.js
@@ -133,6 +133,14 @@ Ext.define('Traccar.view.dialog.User', {
disabled: true,
reference: 'deviceReadonlyField'
}, {
+ xtype: 'checkboxfield',
+ inputValue: true,
+ uncheckedValue: false,
+ name: 'limitCommands',
+ fieldLabel: Strings.userLimitCommands,
+ disabled: true,
+ reference: 'limitCommandsField'
+ }, {
xtype: 'datefield',
name: 'expirationTime',
fieldLabel: Strings.userExpirationTime,
diff --git a/web/app/view/dialog/UserController.js b/web/app/view/dialog/UserController.js
index 89b0bc83..6f2c03a1 100644
--- a/web/app/view/dialog/UserController.js
+++ b/web/app/view/dialog/UserController.js
@@ -30,6 +30,7 @@ Ext.define('Traccar.view.dialog.UserController', {
this.lookupReference('disabledField').setDisabled(false);
this.lookupReference('expirationTimeField').setDisabled(false);
this.lookupReference('deviceReadonlyField').setDisabled(false);
+ this.lookupReference('limitCommandsField').setDisabled(false);
}
},
diff --git a/web/app/view/edit/Devices.js b/web/app/view/edit/Devices.js
index 4fdcab00..5ec452b8 100644
--- a/web/app/view/edit/Devices.js
+++ b/web/app/view/edit/Devices.js
@@ -37,67 +37,54 @@ Ext.define('Traccar.view.edit.Devices', {
tbar: {
componentCls: 'toolbar-header-style',
+ defaults: {
+ xtype: 'button',
+ disabled: true,
+ tooltipType: 'title'
+ },
items: [{
xtype: 'tbtext',
html: Strings.deviceTitle,
baseCls: 'x-panel-header-title-default'
}, {
- xtype: 'tbfill'
+ xtype: 'tbfill',
+ disabled: false
}, {
- xtype: 'button',
- disabled: true,
handler: 'onAddClick',
reference: 'toolbarAddButton',
glyph: 'xf067@FontAwesome',
- tooltip: Strings.sharedAdd,
- tooltipType: 'title'
+ tooltip: Strings.sharedAdd
}, {
- xtype: 'button',
- disabled: true,
handler: 'onEditClick',
reference: 'toolbarEditButton',
glyph: 'xf040@FontAwesome',
- tooltip: Strings.sharedEdit,
- tooltipType: 'title'
+ tooltip: Strings.sharedEdit
}, {
- xtype: 'button',
- disabled: true,
handler: 'onRemoveClick',
reference: 'toolbarRemoveButton',
glyph: 'xf00d@FontAwesome',
- tooltip: Strings.sharedRemove,
- tooltipType: 'title'
+ tooltip: Strings.sharedRemove
}, {
- xtype: 'button',
- disabled: true,
handler: 'onGeofencesClick',
reference: 'toolbarGeofencesButton',
glyph: 'xf21d@FontAwesome',
- tooltip: Strings.sharedGeofences,
- tooltipType: 'title'
+ tooltip: Strings.sharedGeofences
}, {
- xtype: 'button',
- disabled: true,
handler: 'onAttributesClick',
reference: 'toolbarAttributesButton',
glyph: 'xf0ae@FontAwesome',
- tooltip: Strings.sharedComputedAttributes,
- tooltipType: 'title'
+ tooltip: Strings.sharedComputedAttributes
}, {
xtype: 'button',
- disabled: true,
handler: 'onDriversClick',
reference: 'toolbarDriversButton',
glyph: 'xf2c2@FontAwesome',
- tooltip: Strings.sharedDrivers,
- tooltipType: 'title'
+ tooltip: Strings.sharedDrivers
}, {
- disabled: true,
handler: 'onCommandClick',
reference: 'deviceCommandButton',
glyph: 'xf093@FontAwesome',
- tooltip: Strings.deviceCommand,
- tooltipType: 'title'
+ tooltip: Strings.deviceCommand
}]
},
diff --git a/web/app/view/edit/DevicesController.js b/web/app/view/edit/DevicesController.js
index df75b1d4..915f724a 100644
--- a/web/app/view/edit/DevicesController.js
+++ b/web/app/view/edit/DevicesController.js
@@ -20,11 +20,12 @@ Ext.define('Traccar.view.edit.DevicesController', {
alias: 'controller.devices',
requires: [
- 'Traccar.view.dialog.Command',
+ 'Traccar.view.dialog.SendCommand',
'Traccar.view.dialog.Device',
- 'Traccar.view.permissions.DeviceGeofences',
- 'Traccar.view.permissions.DeviceAttributes',
- 'Traccar.view.permissions.DeviceDrivers',
+ 'Traccar.view.permissions.Geofences',
+ 'Traccar.view.permissions.ComputedAttributes',
+ 'Traccar.view.permissions.Drivers',
+ 'Traccar.view.permissions.SavedCommands',
'Traccar.view.BaseWindow',
'Traccar.model.Device',
'Traccar.model.Command'
@@ -76,7 +77,7 @@ Ext.define('Traccar.view.edit.DevicesController', {
Ext.create('Traccar.view.BaseWindow', {
title: Strings.sharedGeofences,
items: {
- xtype: 'deviceGeofencesView',
+ xtype: 'linkGeofencesView',
baseObjectName: 'deviceId',
linkObjectName: 'geofenceId',
storeName: 'Geofences',
@@ -90,7 +91,7 @@ Ext.define('Traccar.view.edit.DevicesController', {
Ext.create('Traccar.view.BaseWindow', {
title: Strings.sharedComputedAttributes,
items: {
- xtype: 'deviceAttributesView',
+ xtype: 'linkComputedAttributesView',
baseObjectName: 'deviceId',
linkObjectName: 'attributeId',
storeName: 'ComputedAttributes',
@@ -104,7 +105,7 @@ Ext.define('Traccar.view.edit.DevicesController', {
Ext.create('Traccar.view.BaseWindow', {
title: Strings.sharedDrivers,
items: {
- xtype: 'deviceDriversView',
+ xtype: 'linkDriversView',
baseObjectName: 'deviceId',
linkObjectName: 'driverId',
storeName: 'Drivers',
@@ -114,22 +115,30 @@ Ext.define('Traccar.view.edit.DevicesController', {
},
onCommandClick: function () {
- var device, deviceId, command, dialog, typesStore, online;
+ var device, deviceId, dialog, typesStore, online, commandsStore;
device = this.getView().getSelectionModel().getSelection()[0];
online = device.get('status') === 'online';
deviceId = device.get('id');
- command = Ext.create('Traccar.model.Command');
- command.set('deviceId', deviceId);
- command.set('textChannel', !online);
-
- dialog = Ext.create('Traccar.view.dialog.Command');
-
- typesStore = dialog.lookupReference('commandType').getStore();
- typesStore.getProxy().setExtraParam('deviceId', deviceId);
+ dialog = Ext.create('Traccar.view.dialog.SendCommand');
+ dialog.deviceId = deviceId;
+ dialog.online = online;
+
+ commandsStore = dialog.lookupReference('commandsComboBox').getStore();
+ commandsStore.getProxy().setExtraParam('deviceId', deviceId);
+ if (!Traccar.app.getPreference('limitCommands', false)) {
+ commandsStore.add({
+ id: 0,
+ description: Strings.sharedNew,
+ textChannel: !online
+ });
+ typesStore = dialog.lookupReference('commandType').getStore();
+ typesStore.getProxy().setExtraParam('deviceId', deviceId);
+ }
+ commandsStore.load({
+ addRecords: true
+ });
- dialog.down('form').loadRecord(command);
- dialog.lookupReference('textChannelCheckBox').setDisabled(!online);
dialog.show();
},
diff --git a/web/app/view/edit/Groups.js b/web/app/view/edit/Groups.js
index deb797f1..05c5723d 100644
--- a/web/app/view/edit/Groups.js
+++ b/web/app/view/edit/Groups.js
@@ -57,6 +57,14 @@ Ext.define('Traccar.view.edit.Groups', {
glyph: 'xf2c2@FontAwesome',
tooltip: Strings.sharedDrivers,
tooltipType: 'title'
+ }, {
+ xtype: 'button',
+ disabled: true,
+ handler: 'onCommandsClick',
+ reference: 'toolbarCommandsButton',
+ glyph: 'xf093@FontAwesome',
+ tooltip: Strings.sharedSavedCommands,
+ tooltipType: 'title'
}]
},
diff --git a/web/app/view/edit/GroupsController.js b/web/app/view/edit/GroupsController.js
index be26cc93..872fea4a 100644
--- a/web/app/view/edit/GroupsController.js
+++ b/web/app/view/edit/GroupsController.js
@@ -21,9 +21,10 @@ Ext.define('Traccar.view.edit.GroupsController', {
requires: [
'Traccar.view.dialog.Group',
- 'Traccar.view.permissions.GroupGeofences',
- 'Traccar.view.permissions.GroupAttributes',
- 'Traccar.view.permissions.GroupDrivers',
+ 'Traccar.view.permissions.Geofences',
+ 'Traccar.view.permissions.ComputedAttributes',
+ 'Traccar.view.permissions.Drivers',
+ 'Traccar.view.permissions.SavedCommands',
'Traccar.view.BaseWindow',
'Traccar.model.Group'
],
@@ -37,6 +38,7 @@ Ext.define('Traccar.view.edit.GroupsController', {
Traccar.app.getVehicleFeaturesDisabled() || Traccar.app.getBooleanAttributePreference('ui.disableDrivers'));
this.lookupReference('toolbarAttributesButton').setHidden(
Traccar.app.getBooleanAttributePreference('ui.disableComputedAttributes'));
+ this.lookupReference('toolbarCommandsButton').setHidden(Traccar.app.getPreference('limitCommands', false));
},
onGeofencesClick: function () {
@@ -46,7 +48,7 @@ Ext.define('Traccar.view.edit.GroupsController', {
Ext.create('Traccar.view.BaseWindow', {
title: Strings.sharedGeofences,
items: {
- xtype: 'groupGeofencesView',
+ xtype: 'linkGeofencesView',
baseObjectName: 'groupId',
linkObjectName: 'geofenceId',
storeName: admin ? 'AllGeofences' : 'Geofences',
@@ -62,7 +64,7 @@ Ext.define('Traccar.view.edit.GroupsController', {
Ext.create('Traccar.view.BaseWindow', {
title: Strings.sharedComputedAttributes,
items: {
- xtype: 'groupAttributesView',
+ xtype: 'linkComputedAttributesView',
baseObjectName: 'groupId',
linkObjectName: 'attributeId',
storeName: admin ? 'AllComputedAttributes' : 'ComputedAttributes',
@@ -78,7 +80,7 @@ Ext.define('Traccar.view.edit.GroupsController', {
Ext.create('Traccar.view.BaseWindow', {
title: Strings.sharedDrivers,
items: {
- xtype: 'groupDriversView',
+ xtype: 'linkDriversView',
baseObjectName: 'groupId',
linkObjectName: 'driverId',
storeName: admin ? 'AllDrivers' : 'Drivers',
@@ -87,11 +89,28 @@ Ext.define('Traccar.view.edit.GroupsController', {
}).show();
},
+ onCommandsClick: function () {
+ var admin, group;
+ admin = Traccar.app.getUser().get('admin');
+ group = this.getView().getSelectionModel().getSelection()[0];
+ Ext.create('Traccar.view.BaseWindow', {
+ title: Strings.sharedSavedCommands,
+ items: {
+ xtype: 'linkSavedCommandsView',
+ baseObjectName: 'groupId',
+ linkObjectName: 'commandId',
+ storeName: admin ? 'AllCommands' : 'Commands',
+ baseObject: group.getId()
+ }
+ }).show();
+ },
+
onSelectionChange: function (selection, selected) {
var disabled = selected.length === 0;
this.lookupReference('toolbarGeofencesButton').setDisabled(disabled);
this.lookupReference('toolbarAttributesButton').setDisabled(disabled);
this.lookupReference('toolbarDriversButton').setDisabled(disabled);
+ this.lookupReference('toolbarCommandsButton').setDisabled(disabled);
this.callParent(arguments);
}
});
diff --git a/web/app/view/permissions/GroupAttributes.js b/web/app/view/edit/SavedCommands.js
index 4db8b244..869fbf9a 100644
--- a/web/app/view/permissions/GroupAttributes.js
+++ b/web/app/view/edit/SavedCommands.js
@@ -16,34 +16,52 @@
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
-Ext.define('Traccar.view.permissions.GroupAttributes', {
- extend: 'Traccar.view.permissions.Base',
- xtype: 'groupAttributesView',
+Ext.define('Traccar.view.edit.SavedCommands', {
+ extend: 'Ext.grid.Panel',
+ xtype: 'savedCommandsView',
requires: [
- 'Ext.grid.filters.Filters'
+ 'Ext.grid.filters.Filters',
+ 'Traccar.view.edit.SavedCommandsController',
+ 'Traccar.view.edit.Toolbar'
],
+ plugins: 'gridfilters',
+
+ controller: 'savedCommands',
+ store: 'Commands',
+
+ tbar: {
+ xtype: 'editToolbar'
+ },
+
+ listeners: {
+ selectionchange: 'onSelectionChange'
+ },
+
columns: {
+ defaults: {
+ flex: 1,
+ minWidth: Traccar.Style.columnWidthNormal
+ },
items: [{
text: Strings.sharedDescription,
dataIndex: 'description',
- flex: 1,
- minWidth: Traccar.Style.columnWidthNormal,
filter: 'string'
}, {
- text: Strings.sharedAttribute,
- dataIndex: 'attribute',
- flex: 1,
- minWidth: Traccar.Style.columnWidthNormal,
+ text: Strings.sharedType,
+ dataIndex: 'type',
filter: {
type: 'list',
+ idField: 'type',
labelField: 'name',
- store: 'PositionAttributes'
+ store: 'AllCommandTypes'
},
- renderer: function (value) {
- return Ext.getStore('PositionAttributes').getAttributeName(value);
- }
+ renderer: Traccar.AttributeFormatter.getFormatter('commandType')
+ }, {
+ text: Strings.notificationSms,
+ dataIndex: 'textChannel',
+ filter: 'boolean'
}]
}
});
diff --git a/web/app/view/permissions/GroupGeofences.js b/web/app/view/edit/SavedCommandsController.js
index f365e356..989aeabf 100644
--- a/web/app/view/permissions/GroupGeofences.js
+++ b/web/app/view/edit/SavedCommandsController.js
@@ -1,5 +1,6 @@
/*
- * Copyright 2016 - 2017 Anton Tananaev (anton@traccar.org)
+ * Copyright 2017 Anton Tananaev (anton@traccar.org)
+ * Copyright 2017 Andrey Kunitsyn (andrey@traccar.org)
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
@@ -15,23 +16,17 @@
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
-Ext.define('Traccar.view.permissions.GroupGeofences', {
- extend: 'Traccar.view.permissions.Base',
- xtype: 'groupGeofencesView',
+Ext.define('Traccar.view.edit.SavedCommandsController', {
+ extend: 'Traccar.view.edit.ToolbarController',
+ alias: 'controller.savedCommands',
requires: [
- 'Ext.grid.filters.Filters'
+ 'Traccar.view.dialog.SavedCommand',
+ 'Traccar.model.Command'
],
- plugins: 'gridfilters',
+ objectModel: 'Traccar.model.Command',
+ objectDialog: 'Traccar.view.dialog.SavedCommand',
+ removeTitle: Strings.sharedSavedCommand
- columns: {
- items: [{
- text: Strings.sharedName,
- dataIndex: 'name',
- flex: 1,
- minWidth: Traccar.Style.columnWidthNormal,
- filter: 'string'
- }]
- }
});
diff --git a/web/app/view/edit/Users.js b/web/app/view/edit/Users.js
index bb121be2..c77ba49b 100644
--- a/web/app/view/edit/Users.js
+++ b/web/app/view/edit/Users.js
@@ -90,6 +90,14 @@ Ext.define('Traccar.view.edit.Users', {
glyph: 'xf2c2@FontAwesome',
tooltip: Strings.sharedDrivers,
tooltipType: 'title'
+ }, {
+ xtype: 'button',
+ disabled: true,
+ handler: 'onCommandsClick',
+ reference: 'userCommandsButton',
+ glyph: 'xf093@FontAwesome',
+ tooltip: Strings.sharedSavedCommands,
+ tooltipType: 'title'
}]
},
diff --git a/web/app/view/edit/UsersController.js b/web/app/view/edit/UsersController.js
index 3bc7d1c4..f710ed24 100644
--- a/web/app/view/edit/UsersController.js
+++ b/web/app/view/edit/UsersController.js
@@ -22,13 +22,14 @@ Ext.define('Traccar.view.edit.UsersController', {
requires: [
'Traccar.view.dialog.User',
- 'Traccar.view.permissions.UserDevices',
- 'Traccar.view.permissions.UserGroups',
- 'Traccar.view.permissions.UserGeofences',
- 'Traccar.view.permissions.UserCalendars',
- 'Traccar.view.permissions.UserUsers',
- 'Traccar.view.permissions.UserAttributes',
- 'Traccar.view.permissions.UserDrivers',
+ 'Traccar.view.permissions.Devices',
+ 'Traccar.view.permissions.Groups',
+ 'Traccar.view.permissions.Geofences',
+ 'Traccar.view.permissions.Calendars',
+ 'Traccar.view.permissions.Users',
+ 'Traccar.view.permissions.ComputedAttributes',
+ 'Traccar.view.permissions.Drivers',
+ 'Traccar.view.permissions.SavedCommands',
'Traccar.view.Notifications',
'Traccar.view.BaseWindow',
'Traccar.model.User'
@@ -47,6 +48,7 @@ Ext.define('Traccar.view.edit.UsersController', {
Traccar.app.getBooleanAttributePreference('ui.disableComputedAttributes'));
this.lookupReference('userCalendarsButton').setHidden(
Traccar.app.getBooleanAttributePreference('ui.disableCalendars'));
+ this.lookupReference('userCommandsButton').setHidden(Traccar.app.getPreference('limitCommands', false));
},
onEditClick: function () {
@@ -78,7 +80,7 @@ Ext.define('Traccar.view.edit.UsersController', {
Ext.create('Traccar.view.BaseWindow', {
title: Strings.deviceTitle,
items: {
- xtype: 'userDevicesView',
+ xtype: 'linkDevicesView',
baseObjectName: 'userId',
linkObjectName: 'deviceId',
storeName: 'AllDevices',
@@ -93,7 +95,7 @@ Ext.define('Traccar.view.edit.UsersController', {
Ext.create('Traccar.view.BaseWindow', {
title: Strings.settingsGroups,
items: {
- xtype: 'userGroupsView',
+ xtype: 'linkGroupsView',
baseObjectName: 'userId',
linkObjectName: 'groupId',
storeName: 'AllGroups',
@@ -108,7 +110,7 @@ Ext.define('Traccar.view.edit.UsersController', {
Ext.create('Traccar.view.BaseWindow', {
title: Strings.sharedGeofences,
items: {
- xtype: 'userGeofencesView',
+ xtype: 'linkGeofencesView',
baseObjectName: 'userId',
linkObjectName: 'geofenceId',
storeName: 'AllGeofences',
@@ -134,7 +136,7 @@ Ext.define('Traccar.view.edit.UsersController', {
Ext.create('Traccar.view.BaseWindow', {
title: Strings.sharedCalendars,
items: {
- xtype: 'userCalendarsView',
+ xtype: 'linkCalendarsView',
baseObjectName: 'userId',
linkObjectName: 'calendarId',
storeName: 'AllCalendars',
@@ -149,7 +151,7 @@ Ext.define('Traccar.view.edit.UsersController', {
Ext.create('Traccar.view.BaseWindow', {
title: Strings.settingsUsers,
items: {
- xtype: 'userUsersView',
+ xtype: 'linkUsersView',
baseObjectName: 'userId',
linkObjectName: 'managedUserId',
storeName: 'Users',
@@ -163,7 +165,7 @@ Ext.define('Traccar.view.edit.UsersController', {
Ext.create('Traccar.view.BaseWindow', {
title: Strings.sharedComputedAttributes,
items: {
- xtype: 'userAttributesView',
+ xtype: 'linkComputedAttributesView',
baseObjectName: 'userId',
linkObjectName: 'attributeId',
storeName: 'AllComputedAttributes',
@@ -178,7 +180,7 @@ Ext.define('Traccar.view.edit.UsersController', {
Ext.create('Traccar.view.BaseWindow', {
title: Strings.sharedDrivers,
items: {
- xtype: 'userDriversView',
+ xtype: 'linkDriversView',
baseObjectName: 'userId',
linkObjectName: 'driverId',
storeName: 'AllDrivers',
@@ -188,6 +190,20 @@ Ext.define('Traccar.view.edit.UsersController', {
}).show();
},
+ onCommandsClick: function () {
+ var user = this.getView().getSelectionModel().getSelection()[0];
+ Ext.create('Traccar.view.BaseWindow', {
+ title: Strings.sharedSavedCommands,
+ items: {
+ xtype: 'linkSavedCommandsView',
+ baseObjectName: 'userId',
+ linkObjectName: 'commandId',
+ storeName: 'AllCommands',
+ linkStoreName: 'Commands',
+ baseObject: user.getId()
+ }
+ }).show();
+ },
onSelectionChange: function (selection, selected) {
var disabled = selected.length === 0;
@@ -198,6 +214,7 @@ Ext.define('Traccar.view.edit.UsersController', {
this.lookupReference('userCalendarsButton').setDisabled(disabled);
this.lookupReference('userAttributesButton').setDisabled(disabled);
this.lookupReference('userDriversButton').setDisabled(disabled);
+ this.lookupReference('userCommandsButton').setDisabled(disabled);
this.lookupReference('userUsersButton').setDisabled(disabled || selected[0].get('userLimit') === 0);
this.callParent(arguments);
}
diff --git a/web/app/view/permissions/UserCalendars.js b/web/app/view/permissions/Calendars.js
index 54ecfc22..ff2796bb 100644
--- a/web/app/view/permissions/UserCalendars.js
+++ b/web/app/view/permissions/Calendars.js
@@ -16,9 +16,9 @@
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
-Ext.define('Traccar.view.permissions.UserCalendars', {
+Ext.define('Traccar.view.permissions.Calendars', {
extend: 'Traccar.view.permissions.Base',
- xtype: 'userCalendarsView',
+ xtype: 'linkCalendarsView',
requires: [
'Ext.grid.filters.Filters'
diff --git a/web/app/view/permissions/UserAttributes.js b/web/app/view/permissions/ComputedAttributes.js
index a0a385ee..800717ce 100644
--- a/web/app/view/permissions/UserAttributes.js
+++ b/web/app/view/permissions/ComputedAttributes.js
@@ -16,9 +16,9 @@
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
-Ext.define('Traccar.view.permissions.UserAttributes', {
+Ext.define('Traccar.view.permissions.ComputedAttributes', {
extend: 'Traccar.view.permissions.Base',
- xtype: 'userAttributesView',
+ xtype: 'linkComputedAttributesView',
requires: [
'Ext.grid.filters.Filters'
diff --git a/web/app/view/permissions/DeviceDrivers.js b/web/app/view/permissions/DeviceDrivers.js
deleted file mode 100644
index d3aa20b6..00000000
--- a/web/app/view/permissions/DeviceDrivers.js
+++ /dev/null
@@ -1,44 +0,0 @@
-/*
- * Copyright 2017 Anton Tananaev (anton@traccar.org)
- * Copyright 2017 Andrey Kunitsyn (andrey@traccar.org)
- *
- * This program is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program. If not, see <http://www.gnu.org/licenses/>.
- */
-
-Ext.define('Traccar.view.permissions.DeviceDrivers', {
- extend: 'Traccar.view.permissions.Base',
- xtype: 'deviceDriversView',
-
- requires: [
- 'Ext.grid.filters.Filters'
- ],
-
- plugins: 'gridfilters',
-
- columns: {
- items: [{
- text: Strings.sharedName,
- dataIndex: 'name',
- flex: 1,
- minWidth: Traccar.Style.columnWidthNormal,
- filter: 'string'
- }, {
- text: Strings.deviceIdentifier,
- dataIndex: 'uniqueId',
- flex: 1,
- minWidth: Traccar.Style.columnWidthNormal,
- filter: 'string'
- }]
- }
-});
diff --git a/web/app/view/permissions/UserDevices.js b/web/app/view/permissions/Devices.js
index a9bb65b7..4cadafe4 100644
--- a/web/app/view/permissions/UserDevices.js
+++ b/web/app/view/permissions/Devices.js
@@ -15,9 +15,9 @@
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
-Ext.define('Traccar.view.permissions.UserDevices', {
+Ext.define('Traccar.view.permissions.Devices', {
extend: 'Traccar.view.permissions.Base',
- xtype: 'userDevicesView',
+ xtype: 'linkDevicesView',
requires: [
'Ext.grid.filters.Filters',
diff --git a/web/app/view/permissions/UserDrivers.js b/web/app/view/permissions/Drivers.js
index 8f88ddd8..f0ea2890 100644
--- a/web/app/view/permissions/UserDrivers.js
+++ b/web/app/view/permissions/Drivers.js
@@ -16,9 +16,9 @@
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
-Ext.define('Traccar.view.permissions.UserDrivers', {
+Ext.define('Traccar.view.permissions.Drivers', {
extend: 'Traccar.view.permissions.Base',
- xtype: 'userDriversView',
+ xtype: 'linkDriversView',
requires: [
'Ext.grid.filters.Filters'
diff --git a/web/app/view/permissions/UserGeofences.js b/web/app/view/permissions/Geofences.js
index 436a2a6a..84135d3b 100644
--- a/web/app/view/permissions/UserGeofences.js
+++ b/web/app/view/permissions/Geofences.js
@@ -15,9 +15,9 @@
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
-Ext.define('Traccar.view.permissions.UserGeofences', {
+Ext.define('Traccar.view.permissions.Geofences', {
extend: 'Traccar.view.permissions.Base',
- xtype: 'userGeofencesView',
+ xtype: 'linkGeofencesView',
requires: [
'Ext.grid.filters.Filters'
diff --git a/web/app/view/permissions/GroupDrivers.js b/web/app/view/permissions/GroupDrivers.js
deleted file mode 100644
index 61aa10ad..00000000
--- a/web/app/view/permissions/GroupDrivers.js
+++ /dev/null
@@ -1,44 +0,0 @@
-/*
- * Copyright 2017 Anton Tananaev (anton@traccar.org)
- * Copyright 2017 Andrey Kunitsyn (andrey@traccar.org)
- *
- * This program is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program. If not, see <http://www.gnu.org/licenses/>.
- */
-
-Ext.define('Traccar.view.permissions.GroupDrivers', {
- extend: 'Traccar.view.permissions.Base',
- xtype: 'groupDriversView',
-
- requires: [
- 'Ext.grid.filters.Filters'
- ],
-
- plugins: 'gridfilters',
-
- columns: {
- items: [{
- text: Strings.sharedName,
- dataIndex: 'name',
- flex: 1,
- minWidth: Traccar.Style.columnWidthNormal,
- filter: 'string'
- }, {
- text: Strings.deviceIdentifier,
- dataIndex: 'uniqueId',
- flex: 1,
- minWidth: Traccar.Style.columnWidthNormal,
- filter: 'string'
- }]
- }
-});
diff --git a/web/app/view/permissions/UserGroups.js b/web/app/view/permissions/Groups.js
index bc24201c..d3cad98e 100644
--- a/web/app/view/permissions/UserGroups.js
+++ b/web/app/view/permissions/Groups.js
@@ -15,9 +15,9 @@
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
-Ext.define('Traccar.view.permissions.UserGroups', {
+Ext.define('Traccar.view.permissions.Groups', {
extend: 'Traccar.view.permissions.Base',
- xtype: 'userGroupsView',
+ xtype: 'linkGroupsView',
requires: [
'Ext.grid.filters.Filters',
diff --git a/web/app/view/permissions/DeviceAttributes.js b/web/app/view/permissions/SavedCommands.js
index c7755f09..106fad52 100644
--- a/web/app/view/permissions/DeviceAttributes.js
+++ b/web/app/view/permissions/SavedCommands.js
@@ -16,9 +16,9 @@
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
-Ext.define('Traccar.view.permissions.DeviceAttributes', {
+Ext.define('Traccar.view.permissions.SavedCommands', {
extend: 'Traccar.view.permissions.Base',
- xtype: 'deviceAttributesView',
+ xtype: 'linkSavedCommandsView',
requires: [
'Ext.grid.filters.Filters'
@@ -34,18 +34,23 @@ Ext.define('Traccar.view.permissions.DeviceAttributes', {
minWidth: Traccar.Style.columnWidthNormal,
filter: 'string'
}, {
- text: Strings.sharedAttribute,
- dataIndex: 'attribute',
+ text: Strings.sharedType,
+ dataIndex: 'type',
flex: 1,
minWidth: Traccar.Style.columnWidthNormal,
filter: {
type: 'list',
+ idField: 'type',
labelField: 'name',
- store: 'PositionAttributes'
+ store: 'AllCommandTypes'
},
- renderer: function (value) {
- return Ext.getStore('PositionAttributes').getAttributeName(value);
- }
+ renderer: Traccar.AttributeFormatter.getFormatter('commandType')
+ }, {
+ text: Strings.notificationSms,
+ dataIndex: 'textChannel',
+ flex: 1,
+ minWidth: Traccar.Style.columnWidthNormal,
+ filter: 'boolean'
}]
}
});
diff --git a/web/app/view/permissions/UserUsers.js b/web/app/view/permissions/Users.js
index c5980c2f..66cf5d62 100644
--- a/web/app/view/permissions/UserUsers.js
+++ b/web/app/view/permissions/Users.js
@@ -16,9 +16,9 @@
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
-Ext.define('Traccar.view.permissions.UserUsers', {
+Ext.define('Traccar.view.permissions.Users', {
extend: 'Traccar.view.permissions.Base',
- xtype: 'userUsersView',
+ xtype: 'linkUsersView',
columns: {
items: [{
diff --git a/web/l10n/en.json b/web/l10n/en.json
index 35b15224..aeb20ddc 100644
--- a/web/l10n/en.json
+++ b/web/l10n/en.json
@@ -69,6 +69,9 @@
"sharedTypeBoolean": "Boolean",
"sharedTimezone": "Timezone",
"sharedInfoTitle": "Info",
+ "sharedSavedCommand": "Saved Command",
+ "sharedSavedCommands": "Saved Commands",
+ "sharedNew": "New…",
"attributeSpeedLimit": "Speed Limit",
"attributeReportIgnoreOdometer": "Report: Ignore Odometer",
"attributeMaintenanceStart": "Maintenance: Start",
@@ -109,6 +112,7 @@
"userDeviceLimit": "Device Limit",
"userUserLimit": "User Limit",
"userDeviceReadonly": "Device Readonly",
+ "userLimitCommands": "Limit Commands",
"userToken": "Token",
"loginTitle": "Login",
"loginLanguage": "Language",