bt-sensors-plugin-sk 1.2.0-beta.0.1.5 → 1.2.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/BTSensor.js +52 -17
- package/README.md +184 -78
- package/Screenshot 2025-06-12 at 9.33.57/342/200/257AM.png +0 -0
- package/index.js +44 -51
- package/package.json +7 -6
- package/plugin_defaults.json +14 -5
- package/public/159.js +2 -1
- package/public/681.js +14 -0
- package/public/{239.js.LICENSE.txt → 681.js.LICENSE.txt} +9 -0
- package/public/847.js +1 -0
- package/public/main.js +1 -1
- package/public/remoteEntry.js +1 -1
- package/sensor_classes/ATC.js +22 -1
- package/sensor_classes/BlackListedDevice.js +10 -7
- package/sensor_classes/GobiusCTankMeter.js +18 -1
- package/sensor_classes/JBDBMS.js +75 -51
- package/sensor_classes/RenogyRoverClient.js +0 -1
- package/sensor_classes/ShellySBMO003Z.js +4 -0
- package/sensor_classes/ShenzhenLiOnBMS.js +177 -0
- package/sensor_classes/Victron/VictronConstants.js +17 -32
- package/sensor_classes/Victron/VictronImages.js +8 -0
- package/sensor_classes/Victron/VictronSensor.js +27 -3
- package/sensor_classes/VictronBatteryMonitor.js +4 -0
- package/sensor_classes/VictronSolarCharger.js +1 -0
- package/sensor_classes/XiaomiMiBeacon.js +5 -0
- package/src/components/PluginConfigurationPanel.js +145 -60
- package/webpack.config.js +1 -1
- package/public/239.js +0 -14
- package/public/778.js +0 -2
- /package/public/{778.js.LICENSE.txt → 159.js.LICENSE.txt} +0 -0
|
@@ -1,24 +1,8 @@
|
|
|
1
|
-
|
|
1
|
+
const Images = require('./VictronImages.js')
|
|
2
|
+
|
|
3
|
+
const VC=
|
|
4
|
+
{
|
|
2
5
|
|
|
3
|
-
/*Device State?
|
|
4
|
-
0x00: Off
|
|
5
|
-
0x01: Low Power Mode,
|
|
6
|
-
0x02: Fault,
|
|
7
|
-
0x03: Bulk,
|
|
8
|
-
0x04: Absorption,
|
|
9
|
-
0x05: Float,
|
|
10
|
-
0x06: Storage,
|
|
11
|
-
0x07: Equalize,
|
|
12
|
-
0x08: Passthru,
|
|
13
|
-
0x09: Inverting,
|
|
14
|
-
0x0A: Assisting,
|
|
15
|
-
0x0B: Power Supply Mode,
|
|
16
|
-
0x0C-0xFA: Reserved,
|
|
17
|
-
0xFB: Test,
|
|
18
|
-
0xFC: Hub-1,
|
|
19
|
-
0xFD-0xFE: Reserved,
|
|
20
|
-
0xFF: Not Available
|
|
21
|
-
*/
|
|
22
6
|
OperationMode: new Map([
|
|
23
7
|
[0, 'OFF'],
|
|
24
8
|
[1, 'LOW_POWER'],
|
|
@@ -73,9 +57,9 @@ module.exports = {
|
|
|
73
57
|
[8, 'WATER_HEATER']
|
|
74
58
|
]),
|
|
75
59
|
MODEL_ID_MAP :{
|
|
76
|
-
0x203: "BMV-700",
|
|
77
|
-
0x204: "BMV-702",
|
|
78
|
-
0x205: "BMV-700H",
|
|
60
|
+
0x203: {name: "BMV-700",image: Images.bmv},
|
|
61
|
+
0x204: {name: "BMV-702",image: Images.bmv},
|
|
62
|
+
0x205: {name: "BMV-700H",image: Images.bmv},
|
|
79
63
|
0x0300: "BlueSolar MPPT 70|15",
|
|
80
64
|
0xA040: "BlueSolar MPPT 75|50",
|
|
81
65
|
0xA041: "BlueSolar MPPT 150|35",
|
|
@@ -207,12 +191,12 @@ module.exports = {
|
|
|
207
191
|
0xA346: "Phoenix Smart IP43 Charger 24|16 (1+1)",
|
|
208
192
|
0xA347: "Phoenix Smart IP43 Charger 24|16 (3)",
|
|
209
193
|
0xA350: "Phoenix Smart IP43 Charger 12|50 (1+1) 120-240V A350",
|
|
210
|
-
0xA381: "BMV-712 Smart",
|
|
211
|
-
0xA382: "BMV-710H Smart",
|
|
212
|
-
0xA383: "BMV-712 Smart Rev2",
|
|
213
|
-
0xA389: "SmartShunt 500A/50mV",
|
|
214
|
-
0xA38A: "SmartShunt 1000A/50mV",
|
|
215
|
-
0xA38B: "SmartShunt 2000A/50mV",
|
|
194
|
+
0xA381: {name: "BMV-712 Smart", image: Images.bmv},
|
|
195
|
+
0xA382: {name: "BMV-710H Smart", image: Images.bmv},
|
|
196
|
+
0xA383: {name: "BMV-712 Smart Rev2", image: Images.bmv},
|
|
197
|
+
0xA389: {name:"SmartShunt 500A/50mV",image: Images.shunt},
|
|
198
|
+
0xA38A: {name:"SmartShunt 1000A/50mV",image: Images.shunt},
|
|
199
|
+
0xA38B: {name:"SmartShunt 2000A/50mV",image: Images.shunt},
|
|
216
200
|
0xA3A4: "Smart Battery Sense",
|
|
217
201
|
0xA3A5: "Smart Battery Sense",
|
|
218
202
|
0xA3B0: "Smart Battery Protect",
|
|
@@ -239,7 +223,7 @@ module.exports = {
|
|
|
239
223
|
0xA3E6: "Lynx Smart BMS 1000",
|
|
240
224
|
0x2780: "Victron Multiplus II 12/3000/120-50 2x120V",
|
|
241
225
|
0xC00A: "Cerbo GX",
|
|
242
|
-
0xC030: "SmartShunt IP65 500A/50mV",
|
|
226
|
+
0xC030: {name:"SmartShunt IP65 500A/50mV",image: Images.shunt},
|
|
243
227
|
0xeba0: "Smart Lithium Battery",
|
|
244
228
|
|
|
245
229
|
},
|
|
@@ -249,6 +233,7 @@ AuxMode:{
|
|
|
249
233
|
TEMPERATURE: 2,
|
|
250
234
|
DISABLED: 3
|
|
251
235
|
},
|
|
236
|
+
|
|
252
237
|
ChargerError:new Map()
|
|
253
238
|
.set(0,"NO_ERROR")
|
|
254
239
|
.set(1,"TEMPERATURE_BATTERY_HIGH")
|
|
@@ -330,6 +315,6 @@ OffReasons : new Map([
|
|
|
330
315
|
[0x00000080, 'ENGINE_SHUTDOWN'],
|
|
331
316
|
[0x00000081, 'ENGINE_SHUTDOWN_AND_INPUT_VOLTAGE_LOCKOUT'],
|
|
332
317
|
[0x00000100, 'ANALYSING_INPUT_VOLTAGE']
|
|
333
|
-
])
|
|
334
|
-
|
|
318
|
+
])
|
|
335
319
|
}
|
|
320
|
+
module.exports = VC
|
|
@@ -1,6 +1,8 @@
|
|
|
1
|
+
const VC = require( './VictronConstants.js');
|
|
2
|
+
const Images = require('./VictronImages.js')
|
|
3
|
+
|
|
1
4
|
const BTSensor = require("../../BTSensor.js");
|
|
2
5
|
const crypto = require('node:crypto');
|
|
3
|
-
const VC = require('./VictronConstants.js');
|
|
4
6
|
function sleep(x) {
|
|
5
7
|
return new Promise((resolve) => {
|
|
6
8
|
setTimeout(() => {
|
|
@@ -59,12 +61,21 @@ function sleep(x) {
|
|
|
59
61
|
}
|
|
60
62
|
)
|
|
61
63
|
this.model_id=this.getManufacturerData(0x2e1)?.readUInt16LE(2)??"Unknown"
|
|
64
|
+
this._schema.title = this.getName()
|
|
62
65
|
}
|
|
63
66
|
alarmReason(alarmValue){
|
|
64
67
|
return this.constructor.AlarmReason[alarmValue]
|
|
65
68
|
}
|
|
66
69
|
getModelName(){
|
|
67
|
-
|
|
70
|
+
const m = VC.MODEL_ID_MAP[this.model_id]
|
|
71
|
+
if(m) {
|
|
72
|
+
if(typeof m == 'string' || m instanceof String ) {
|
|
73
|
+
return m
|
|
74
|
+
} else {
|
|
75
|
+
return m.name
|
|
76
|
+
}
|
|
77
|
+
}
|
|
78
|
+
return this.constructor.name+" (Model ID:"+this.model_id+")"
|
|
68
79
|
}
|
|
69
80
|
|
|
70
81
|
decrypt(data){
|
|
@@ -110,7 +121,20 @@ function sleep(x) {
|
|
|
110
121
|
throw new Error( "GATT Connection unimplemented for "+this.getDisplayName())
|
|
111
122
|
}
|
|
112
123
|
|
|
113
|
-
|
|
124
|
+
getImage(){
|
|
125
|
+
const m = VC.MODEL_ID_MAP[this.model_id]
|
|
126
|
+
if (m && m.image)
|
|
127
|
+
return m.image
|
|
128
|
+
else
|
|
129
|
+
return Images.generic
|
|
130
|
+
}
|
|
131
|
+
|
|
132
|
+
getDescription(){
|
|
133
|
+
//return `<img src="https://www.victronenergy.com/_next/image?url=https%3A%2F%2Fwww.victronenergy.com%2Fupload%2Fproducts%2FSmartShunt%2520500_nw.png&w=1080&q=70"" height="150" object-fit="cover" ></img>`
|
|
134
|
+
|
|
135
|
+
|
|
136
|
+
return `<img src="../bt-sensors-plugin-sk/images/${this.getImage()}" height="300" object-fit="cover" ></img>`
|
|
137
|
+
}
|
|
114
138
|
|
|
115
139
|
}
|
|
116
140
|
module.exports=VictronSensor
|
|
@@ -195,6 +195,10 @@ class VictronBatteryMonitor extends VictronSensor{
|
|
|
195
195
|
return "To use the GATT connection the SignalK server computer and the Smart Shunt must first be paired."
|
|
196
196
|
}
|
|
197
197
|
|
|
198
|
+
getDescription(){
|
|
199
|
+
return super.getDescription()
|
|
200
|
+
}
|
|
201
|
+
|
|
198
202
|
async stopListening(){
|
|
199
203
|
super.stopListening()
|
|
200
204
|
for (var c of this.characteristics){
|
|
@@ -97,6 +97,11 @@ class XiaomiMiBeacon extends BTSensor{
|
|
|
97
97
|
this.emit("humidity", buffer.readUInt8(2)/100)
|
|
98
98
|
this.emitData("voltage",buffer,3);
|
|
99
99
|
}
|
|
100
|
+
|
|
101
|
+
getDescription(){
|
|
102
|
+
return `<div><p><img src="../bt-sensors-plugin-sk/images/LYWSD03MMC-Device.jpg" alt=LYWSD03MMC image" style="float: left; margin-right: 10px;" /> The LYWSD03MMC temperature and humidity sensor is an inexpensive environmental sensor from Xiaomi Inc. <p> WARNING: If you use the GATT connection, you won't need an encrypytion//bind key to get your data but the energy cost of maintaining a GATT connection is high and will drain your battery in about 2 weeks of persistent use. Instead follow the instructions <a href=https://github.com/PiotrMachowski/Xiaomi-cloud-tokens-extractor/?tab=readme-ov-file#linux--home-assistant-in-ssh--web-terminal target="_blank">here</a> to get your device's encryption key.<div>`
|
|
103
|
+
}
|
|
104
|
+
|
|
100
105
|
getManufacturer(){
|
|
101
106
|
return "Xiaomi Inc."
|
|
102
107
|
}
|
|
@@ -1,9 +1,12 @@
|
|
|
1
1
|
import Form from '@rjsf/core' ;
|
|
2
2
|
import validator from '@rjsf/validator-ajv8';
|
|
3
|
-
import React from
|
|
3
|
+
import React from "react";
|
|
4
|
+
import ReactHtmlParser from 'react-html-parser';
|
|
5
|
+
|
|
4
6
|
import {useEffect, useState} from 'react'
|
|
5
7
|
|
|
6
|
-
import {Button, Grid} from '@material-ui/core';
|
|
8
|
+
import {Button, Grid } from '@material-ui/core';
|
|
9
|
+
import { makeStyles } from '@material-ui/core/styles';
|
|
7
10
|
|
|
8
11
|
import { SignalCellular0Bar, SignalCellular1Bar, SignalCellular2Bar, SignalCellular3Bar, SignalCellular4Bar, SignalCellularConnectedNoInternet0Bar } from '@material-ui/icons';
|
|
9
12
|
|
|
@@ -12,30 +15,62 @@ const log = (type) => console.log.bind(console, type);
|
|
|
12
15
|
import ListGroup from 'react-bootstrap/ListGroup';
|
|
13
16
|
import Tabs from 'react-bootstrap/Tabs';
|
|
14
17
|
import Tab from 'react-bootstrap/Tab';
|
|
18
|
+
|
|
15
19
|
import { ListGroupItem } from 'react-bootstrap';
|
|
16
20
|
|
|
17
21
|
import ProgressBar from 'react-bootstrap/ProgressBar';
|
|
18
22
|
|
|
19
|
-
|
|
20
23
|
var _sensorMap, _sensorDomains={}, _sensorList={}
|
|
21
24
|
|
|
22
|
-
export default (props)
|
|
25
|
+
export default function BTConfig (props) {
|
|
23
26
|
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
27
|
+
const _uiSchema= {
|
|
28
|
+
"ui:options": {label: false},
|
|
29
|
+
'title': { 'ui:widget': 'hidden' }
|
|
30
|
+
}
|
|
31
|
+
|
|
32
|
+
const baseUISchema =
|
|
33
|
+
{
|
|
34
|
+
"ui:field": "LayoutGridField",
|
|
35
|
+
"ui:layoutGrid": {
|
|
36
|
+
"ui:row":[
|
|
37
|
+
{
|
|
38
|
+
"ui:row": {
|
|
39
|
+
"className": "row",
|
|
40
|
+
"children": [
|
|
41
|
+
{
|
|
42
|
+
"ui:columns": {
|
|
43
|
+
"className": "col-xs-4",
|
|
44
|
+
"children": [
|
|
45
|
+
"adapter",
|
|
46
|
+
"transport",
|
|
47
|
+
"duplicateData",
|
|
48
|
+
"discoveryTimeout",
|
|
49
|
+
"discoveryInterval"
|
|
50
|
+
]
|
|
51
|
+
}
|
|
52
|
+
}
|
|
53
|
+
]
|
|
54
|
+
}
|
|
55
|
+
}
|
|
56
|
+
]
|
|
57
|
+
}
|
|
33
58
|
}
|
|
59
|
+
|
|
60
|
+
const useStyles = makeStyles((theme) => ({
|
|
61
|
+
root: {
|
|
62
|
+
'& > *': {
|
|
63
|
+
margin: theme.spacing(1),
|
|
64
|
+
},
|
|
65
|
+
},
|
|
66
|
+
}));
|
|
67
|
+
|
|
34
68
|
const [baseSchema, setBaseSchema] = useState({})
|
|
69
|
+
|
|
35
70
|
const [baseData, setBaseData] = useState({})
|
|
36
71
|
|
|
37
72
|
const [schema, setSchema] = useState({})
|
|
38
|
-
const [ uiSchema, setUISchema] = useState(
|
|
73
|
+
const [ uiSchema, setUISchema] = useState(_uiSchema )
|
|
39
74
|
const [sensorList, setSensorList] = useState([])
|
|
40
75
|
|
|
41
76
|
const [sensorData, setSensorData] = useState()
|
|
@@ -49,11 +84,12 @@ export default (props) => {
|
|
|
49
84
|
|
|
50
85
|
const [pluginState, setPluginState ] = useState("unknown")
|
|
51
86
|
const [error, setError ] = useState()
|
|
87
|
+
const classes = useStyles();
|
|
52
88
|
|
|
53
|
-
|
|
89
|
+
|
|
54
90
|
function sendJSONData(cmd, data){
|
|
55
91
|
|
|
56
|
-
console.log(`sending ${cmd}`)
|
|
92
|
+
console.log(`sending ${cmd}`)
|
|
57
93
|
console.log(data)
|
|
58
94
|
const headers = new Headers();
|
|
59
95
|
headers.append("Content-Type", "application/json");
|
|
@@ -67,11 +103,19 @@ export default (props) => {
|
|
|
67
103
|
|
|
68
104
|
async function fetchJSONData(path){
|
|
69
105
|
console.log(`fetching ${path}`)
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
106
|
+
var result
|
|
107
|
+
try {
|
|
108
|
+
result = fetch(`/plugins/bt-sensors-plugin-sk/${path}`, {
|
|
109
|
+
credentials: 'include'
|
|
110
|
+
})
|
|
111
|
+
} catch (e) {
|
|
112
|
+
result=
|
|
113
|
+
{
|
|
114
|
+
status: 500,
|
|
115
|
+
statusText: e.toString()
|
|
116
|
+
}
|
|
117
|
+
}
|
|
118
|
+
return result
|
|
75
119
|
}
|
|
76
120
|
|
|
77
121
|
async function getSensors(){
|
|
@@ -82,6 +126,9 @@ export default (props) => {
|
|
|
82
126
|
}
|
|
83
127
|
const json = await response.json()
|
|
84
128
|
console.log(json)
|
|
129
|
+
//for (let i=0;i<json.length;i++){
|
|
130
|
+
// json[i].schema.htmlDescription=<div>{ReactHtmlParser(json[i].schema.htmlDescription)}<p></p></div>
|
|
131
|
+
//}
|
|
85
132
|
return json
|
|
86
133
|
|
|
87
134
|
}
|
|
@@ -100,17 +147,18 @@ export default (props) => {
|
|
|
100
147
|
console.log("getBaseData")
|
|
101
148
|
const response = await fetchJSONData("getBaseData")
|
|
102
149
|
if (response.status!=200){
|
|
103
|
-
throw new Error(`Unable get base data: ${response.statusText} (${response.status}) `)
|
|
150
|
+
throw new Error(`Unable to get base data: ${response.statusText} (${response.status}) `)
|
|
104
151
|
}
|
|
105
152
|
const json = await response.json()
|
|
106
153
|
console.log(json)
|
|
154
|
+
json.schema.htmlDescription=<div>{ReactHtmlParser(json.schema.htmlDescription)}<p></p></div>
|
|
107
155
|
return json
|
|
108
156
|
}
|
|
109
157
|
async function getProgress(){
|
|
110
158
|
console.log("getProgress")
|
|
111
159
|
const response = await fetchJSONData("getProgress")
|
|
112
160
|
if (response.status!=200){
|
|
113
|
-
throw new Error(`Unable get
|
|
161
|
+
throw new Error(`Unable to get progress: ${response.statusText} (${response.status}) `)
|
|
114
162
|
}
|
|
115
163
|
const json = await response.json()
|
|
116
164
|
console.log(json)
|
|
@@ -163,14 +211,13 @@ export default (props) => {
|
|
|
163
211
|
sendJSONData("updateBaseData", data).then( (response )=>{
|
|
164
212
|
if (response.status != 200) {
|
|
165
213
|
setError(new Error(`Unable to update base data: ${response.statusText} (${response.status})`))
|
|
166
|
-
} else {
|
|
214
|
+
} /*else {
|
|
167
215
|
getProgress().then((json)=>{
|
|
168
216
|
setProgress(json)
|
|
169
217
|
}).catch((e)=>{
|
|
170
218
|
setError(e)
|
|
171
219
|
})
|
|
172
|
-
|
|
173
|
-
}
|
|
220
|
+
}*/
|
|
174
221
|
})
|
|
175
222
|
}
|
|
176
223
|
|
|
@@ -221,6 +268,7 @@ export default (props) => {
|
|
|
221
268
|
|
|
222
269
|
if (_sensorMap.has(json.mac)) {
|
|
223
270
|
let sensor = _sensorMap.get(json.mac)
|
|
271
|
+
|
|
224
272
|
Object.assign(sensor.info, json )
|
|
225
273
|
setSensorMap(new Map ( _sensorMap ))
|
|
226
274
|
}
|
|
@@ -372,66 +420,72 @@ useEffect(()=>{
|
|
|
372
420
|
|
|
373
421
|
return Object.keys(_sensorList).map((domain)=> {return getTab(domain)})
|
|
374
422
|
}
|
|
423
|
+
// <div style={{paddingBottom: 20}} class="d-flex flex-wrap justify-content-start align-items-start">
|
|
424
|
+
// <div class="d-flex flex-column" >
|
|
425
|
+
|
|
375
426
|
function getTab(key){
|
|
376
427
|
var title = key.slice(key.charAt(0)==="_"?1:0)
|
|
377
428
|
|
|
378
429
|
return <Tab eventKey={key} title={title.charAt(0).toUpperCase()+title.slice(1) }>
|
|
379
430
|
|
|
380
|
-
<div style={{paddingBottom: 20}} class="d-flex flex-wrap justify-content-start align-items-start">
|
|
381
431
|
<ListGroup style={{ maxHeight: '300px', overflowY: 'auto' }}>
|
|
382
432
|
{getSensorList(key)}
|
|
383
433
|
</ListGroup>
|
|
434
|
+
|
|
384
435
|
|
|
385
|
-
|
|
436
|
+
</Tab>
|
|
437
|
+
}
|
|
386
438
|
|
|
387
|
-
|
|
388
|
-
|
|
389
|
-
|
|
390
|
-
|
|
391
|
-
onChange={(e) => {
|
|
392
|
-
const s = sensorMap.get(e.formData.mac_address)
|
|
393
|
-
s._changesMade=true
|
|
394
|
-
setSensorData(e.formData)
|
|
395
|
-
}
|
|
396
|
-
}
|
|
397
|
-
onSubmit={({ formData }, e) => {
|
|
398
|
-
console.log(formData)
|
|
399
|
-
updateSensorData(formData)
|
|
400
|
-
setSchema({})
|
|
401
|
-
alert("Changes saved")
|
|
402
|
-
}}
|
|
403
|
-
onError={log('errors')}
|
|
404
|
-
formData={sensorData}>
|
|
405
|
-
<div>
|
|
406
|
-
<Grid direction="row" style={{spacing:5}}>
|
|
407
|
-
<Button type='submit' color="primary" variant="contained">Save</Button>
|
|
408
|
-
<Button variant="contained" onClick={()=>{undoChanges(sensorData.mac_address)}}>Undo</Button>
|
|
409
|
-
<Button variant="contained" color="secondary" onClick={(e)=>confirmDelete(sensorData.mac_address)}>Delete</Button>
|
|
439
|
+
|
|
440
|
+
function openInNewTab (url) {
|
|
441
|
+
window.open(url, "_blank", "noreferrer");
|
|
442
|
+
}
|
|
410
443
|
|
|
444
|
+
function CustomFieldTemplate(props) {
|
|
445
|
+
const { id, classNames, style, label, help, required, description, errors, children } = props;
|
|
446
|
+
return (
|
|
447
|
+
<div className={classNames} style={style}>
|
|
448
|
+
<Grid container xs={12} direction="row" spacing="1">
|
|
449
|
+
<Grid item xs={1} sm container direction="column">
|
|
450
|
+
<Grid item ><label htmlFor={id}>{label}{required ? '*' : null}</label></Grid>
|
|
451
|
+
<Grid item> {description}</Grid>
|
|
452
|
+
</Grid>
|
|
453
|
+
<Grid item>{children}</Grid>
|
|
411
454
|
</Grid>
|
|
412
|
-
|
|
413
|
-
|
|
414
|
-
|
|
455
|
+
{errors}
|
|
456
|
+
{help}
|
|
415
457
|
</div>
|
|
416
|
-
|
|
417
|
-
|
|
418
|
-
}
|
|
458
|
+
);
|
|
459
|
+
}
|
|
419
460
|
|
|
420
461
|
if (pluginState=="stopped" || pluginState=="unknown")
|
|
421
|
-
return (<
|
|
462
|
+
return (<h3>Enable plugin to see configuration</h3>)
|
|
422
463
|
else
|
|
423
464
|
return(
|
|
424
465
|
|
|
425
466
|
<div>
|
|
467
|
+
<div className={classes.root}>
|
|
468
|
+
|
|
469
|
+
<Button variant="contained" onClick={()=>{openInNewTab("https://github.com/naugehyde/bt-sensors-plugin-sk/tree/1.2.0-beta#configuration")}}>Documentation</Button>
|
|
470
|
+
<Button variant="contained" onClick={()=>{openInNewTab("https://github.com/naugehyde/bt-sensors-plugin-sk/issues/new/choose")}}>Report Issue</Button>
|
|
471
|
+
<Button variant="contained" onClick={()=>{openInNewTab("https://discord.com/channels/1170433917761892493/1295425963466952725" )}}>Discord Thread</Button>
|
|
472
|
+
<p></p>
|
|
473
|
+
<p></p>
|
|
474
|
+
</div>
|
|
475
|
+
<hr style={{"width":"100%","height":"1px","color":"gray","background-color":"gray","text-align":"left","margin-left":0}}></hr>
|
|
476
|
+
|
|
426
477
|
{error?<h2 style="color: red;">{error}</h2>:""}
|
|
427
478
|
<Form
|
|
428
479
|
schema={baseSchema}
|
|
429
480
|
validator={validator}
|
|
481
|
+
uiSchema={baseUISchema}
|
|
430
482
|
onChange={(e) => setBaseData(e.formData)}
|
|
431
483
|
onSubmit={ ({ formData }, e) => { updateBaseData(formData); setSchema({}) } }
|
|
484
|
+
|
|
432
485
|
onError={log('errors')}
|
|
433
486
|
formData={baseData}
|
|
434
487
|
/>
|
|
488
|
+
<hr style={{"width":"100%","height":"1px","color":"gray","background-color":"gray","text-align":"left","margin-left":0}}></hr>
|
|
435
489
|
<p></p>
|
|
436
490
|
<p></p>
|
|
437
491
|
{ (progress.deviceCount<progress.totalDevices)?
|
|
@@ -439,16 +493,47 @@ useEffect(()=>{
|
|
|
439
493
|
now={progress.progress}
|
|
440
494
|
/>:""
|
|
441
495
|
}
|
|
442
|
-
<h2>{`${sensorMap.size>0?"Bluetooth Devices - Select to configure" :""}`}</h2>
|
|
443
|
-
<h2>{`${sensorMap.size>0?"(* = sensor has unsaved changes)" :""}`}</h2>
|
|
444
496
|
<p></p>
|
|
445
497
|
<Tabs
|
|
446
498
|
defaultActiveKey="_configured"
|
|
447
499
|
id="domain-tabs"
|
|
448
500
|
className="mb-3"
|
|
501
|
+
onClick={()=>{setSchema({})}}
|
|
449
502
|
>
|
|
450
503
|
{getTabs()}
|
|
451
504
|
</Tabs>
|
|
505
|
+
<div style= {{ paddingLeft: 10, paddingTop: 10, display: (Object.keys(schema).length==0)? "none" :"" }}>
|
|
506
|
+
<Grid container direction="column" style={{spacing:5}}>
|
|
507
|
+
<Grid item><h2>{schema?.title}</h2><p></p></Grid>
|
|
508
|
+
<Grid item>{ReactHtmlParser(schema?.htmlDescription)}</Grid>
|
|
509
|
+
</Grid>
|
|
510
|
+
|
|
511
|
+
<Form
|
|
512
|
+
schema={schema}
|
|
513
|
+
validator={validator}
|
|
514
|
+
uiSchema={uiSchema}
|
|
515
|
+
onChange={(e) => {
|
|
516
|
+
const s = sensorMap.get(e.formData.mac_address)
|
|
517
|
+
s._changesMade=true
|
|
518
|
+
setSensorData(e.formData)
|
|
519
|
+
}
|
|
520
|
+
}
|
|
521
|
+
onSubmit={({ formData }, e) => {
|
|
522
|
+
updateSensorData(formData)
|
|
523
|
+
setSchema({})
|
|
524
|
+
alert("Changes saved")
|
|
525
|
+
}}
|
|
526
|
+
onError={log('errors')}
|
|
527
|
+
formData={sensorData}>
|
|
528
|
+
<div className={classes.root}>
|
|
529
|
+
<Button type='submit' color="primary" variant="contained">Save</Button>
|
|
530
|
+
<Button variant="contained" onClick={()=>{undoChanges(sensorData.mac_address)}}>Undo</Button>
|
|
531
|
+
<Button variant="contained" color="secondary" onClick={(e)=>confirmDelete(sensorData.mac_address)}>Delete</Button>
|
|
532
|
+
</div>
|
|
533
|
+
</Form>
|
|
534
|
+
|
|
535
|
+
|
|
536
|
+
</div>
|
|
452
537
|
</div>
|
|
453
538
|
)
|
|
454
539
|
|
package/webpack.config.js
CHANGED
|
@@ -4,7 +4,7 @@ const path = require('path');
|
|
|
4
4
|
const { ModuleFederationPlugin } = require('webpack').container;
|
|
5
5
|
const { WatchIgnorePlugin } = require('webpack')
|
|
6
6
|
|
|
7
|
-
require('@signalk/server-admin-ui-dependencies')
|
|
7
|
+
//require('@signalk/server-admin-ui-dependencies')
|
|
8
8
|
|
|
9
9
|
const packageJson = require('./package')
|
|
10
10
|
|