@haydendonald/node-red-contrib-hass-stuff 0.0.1
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/LICENSE +5 -0
- package/README.md +544 -0
- package/dist/Connections/connectionsConfigNode.html +21 -0
- package/dist/Connections/connectionsConfigNode.js +330 -0
- package/dist/Connections/connectionsNode.html +30 -0
- package/dist/Connections/connectionsNode.js +17 -0
- package/dist/Connections/connectionsTypes.js +11 -0
- package/dist/LightControl/lightControlConfigNode.html +109 -0
- package/dist/LightControl/lightControlConfigNode.js +311 -0
- package/dist/LightControl/lightControlNode.html +30 -0
- package/dist/LightControl/lightControlNode.js +18 -0
- package/dist/LightControl/lightControlTypes.js +20 -0
- package/dist/baseConfigNode.js +24 -0
- package/dist/baseNode.js +5 -0
- package/dist/utility.js +19 -0
- package/package.json +36 -0
|
@@ -0,0 +1,330 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
const baseConfigNode_1 = require("../baseConfigNode");
|
|
3
|
+
const connectionsTypes_1 = require("./connectionsTypes");
|
|
4
|
+
const utility_1 = require("../utility");
|
|
5
|
+
module.exports = function ConnectionsConfigNode(RED) {
|
|
6
|
+
const register = function (config) {
|
|
7
|
+
RED.nodes.createNode(this, config);
|
|
8
|
+
(0, baseConfigNode_1.assignBaseConfigNode)(this);
|
|
9
|
+
const self = this;
|
|
10
|
+
self.hassAPICallbacks = {};
|
|
11
|
+
self.hassActionCallbacks = {};
|
|
12
|
+
self.hassCurrentStateCallbacks = {};
|
|
13
|
+
self.hassGetEntitiesCallbacks = {};
|
|
14
|
+
self.hassEventReadyCallbacks = {};
|
|
15
|
+
self.hassEventCallbacks = {};
|
|
16
|
+
self.hassEventCallServiceCallbacks = {};
|
|
17
|
+
self.hassEventStateChangeCallbacks = {};
|
|
18
|
+
self.sendHASSAPI = function (protocol, method, path, callback, params, data, results) {
|
|
19
|
+
const callbackId = callback ? (0, utility_1.generateRandomId)(Object.keys(self.hassAPICallbacks)) : undefined;
|
|
20
|
+
const msg = {
|
|
21
|
+
topic: connectionsTypes_1.Topics.API,
|
|
22
|
+
callbackId,
|
|
23
|
+
payload: {
|
|
24
|
+
protocol,
|
|
25
|
+
method,
|
|
26
|
+
path,
|
|
27
|
+
data,
|
|
28
|
+
params,
|
|
29
|
+
results
|
|
30
|
+
}
|
|
31
|
+
};
|
|
32
|
+
self.sendMsg(msg);
|
|
33
|
+
//Add our callback for when a response comes back in
|
|
34
|
+
if (callbackId && callback) {
|
|
35
|
+
self.hassAPICallbacks[callbackId] = callback;
|
|
36
|
+
}
|
|
37
|
+
};
|
|
38
|
+
self.sendHASSAction = function (action, target, data, callback) {
|
|
39
|
+
const callbackId = callback ? (0, utility_1.generateRandomId)(Object.keys(self.hassActionCallbacks)) : undefined;
|
|
40
|
+
const msg = {
|
|
41
|
+
topic: connectionsTypes_1.Topics.ACTION,
|
|
42
|
+
callbackId,
|
|
43
|
+
payload: {
|
|
44
|
+
action,
|
|
45
|
+
target,
|
|
46
|
+
data
|
|
47
|
+
}
|
|
48
|
+
};
|
|
49
|
+
self.sendMsg(msg);
|
|
50
|
+
//Add our callback for when a response comes back in
|
|
51
|
+
if (callbackId && callback) {
|
|
52
|
+
self.hassActionCallbacks[callbackId] = callback;
|
|
53
|
+
}
|
|
54
|
+
};
|
|
55
|
+
self.getHASSEntityState = function (entityId, callback) {
|
|
56
|
+
const callbackId = callback ? (0, utility_1.generateRandomId)(Object.keys(self.hassCurrentStateCallbacks)) : undefined;
|
|
57
|
+
const msg = {
|
|
58
|
+
topic: connectionsTypes_1.Topics.STATE,
|
|
59
|
+
callbackId,
|
|
60
|
+
payload: {
|
|
61
|
+
entityId
|
|
62
|
+
}
|
|
63
|
+
};
|
|
64
|
+
self.sendMsg(msg);
|
|
65
|
+
//Add our callback for when a response comes back in
|
|
66
|
+
if (callbackId && callback) {
|
|
67
|
+
self.hassCurrentStateCallbacks[callbackId] = callback;
|
|
68
|
+
}
|
|
69
|
+
};
|
|
70
|
+
self.getHASSEntities = function (rules, callback) {
|
|
71
|
+
const callbackId = callback ? (0, utility_1.generateRandomId)(Object.keys(self.hassGetEntitiesCallbacks)) : undefined;
|
|
72
|
+
const msg = {
|
|
73
|
+
topic: connectionsTypes_1.Topics.GET_ENTITIES,
|
|
74
|
+
callbackId,
|
|
75
|
+
payload: {
|
|
76
|
+
rules
|
|
77
|
+
}
|
|
78
|
+
};
|
|
79
|
+
self.sendMsg(msg);
|
|
80
|
+
//Add our callback for when a response comes back in
|
|
81
|
+
if (callbackId && callback) {
|
|
82
|
+
self.hassGetEntitiesCallbacks[callbackId] = callback;
|
|
83
|
+
}
|
|
84
|
+
};
|
|
85
|
+
self.addHASSEntity = function (entityId, data, callback) {
|
|
86
|
+
self.sendHASSAPI("http", "post", "/api/states/" + entityId, callback, undefined, data);
|
|
87
|
+
};
|
|
88
|
+
self.addHASSInputBoolean = function (options) {
|
|
89
|
+
let currentState = options.state || "unknown";
|
|
90
|
+
const entityId = options.id ? options.id : (0, utility_1.getEntityId)("input_boolean", options.friendlyName);
|
|
91
|
+
const data = (state) => {
|
|
92
|
+
return {
|
|
93
|
+
state: state || "unknown",
|
|
94
|
+
attributes: {
|
|
95
|
+
friendly_name: options.friendlyName
|
|
96
|
+
}
|
|
97
|
+
};
|
|
98
|
+
};
|
|
99
|
+
//Add the input boolean to HASS
|
|
100
|
+
self.getHASSEntities([{ property: "entity_id", logic: "is", value: entityId }], (entities) => {
|
|
101
|
+
if (entities.length > 1) {
|
|
102
|
+
self.error(`Found more than 1 entity for ${entityId}`);
|
|
103
|
+
return;
|
|
104
|
+
}
|
|
105
|
+
const previousState = entities.length == 1 ? entities[0].state : "unknown";
|
|
106
|
+
self.addHASSEntity(entityId, data(options.state || previousState), options.creationCallback ? (response) => {
|
|
107
|
+
options.creationCallback(response.payload.state, response);
|
|
108
|
+
} : undefined);
|
|
109
|
+
});
|
|
110
|
+
//Assign the changed callback if set
|
|
111
|
+
if (options.changedCallback) {
|
|
112
|
+
self.hassEventCallServiceCallbacks[entityId] = function (domain, service, serviceData) {
|
|
113
|
+
if (domain == "input_boolean" && (serviceData === null || serviceData === void 0 ? void 0 : serviceData.entity_id) == entityId) {
|
|
114
|
+
let state = currentState;
|
|
115
|
+
if (service == "turn_on") {
|
|
116
|
+
state = "on";
|
|
117
|
+
}
|
|
118
|
+
else if (service == "turn_off") {
|
|
119
|
+
state = "off";
|
|
120
|
+
}
|
|
121
|
+
else if (service == "toggle") {
|
|
122
|
+
state = state === "on" ? "off" : "on";
|
|
123
|
+
}
|
|
124
|
+
currentState = state;
|
|
125
|
+
//Tell HASS that the button was pressed
|
|
126
|
+
self.sendHASSAPI("http", "post", "/api/states/" + entityId, undefined, undefined, data(currentState));
|
|
127
|
+
options.changedCallback(currentState, serviceData);
|
|
128
|
+
}
|
|
129
|
+
};
|
|
130
|
+
}
|
|
131
|
+
};
|
|
132
|
+
self.addHASSButton = function (options) {
|
|
133
|
+
var _a;
|
|
134
|
+
const entityId = (_a = options.id) !== null && _a !== void 0 ? _a : (0, utility_1.getEntityId)("button", options.friendlyName);
|
|
135
|
+
const data = (state) => {
|
|
136
|
+
return {
|
|
137
|
+
state: state || "unknown",
|
|
138
|
+
attributes: {
|
|
139
|
+
friendly_name: options.friendlyName
|
|
140
|
+
}
|
|
141
|
+
};
|
|
142
|
+
};
|
|
143
|
+
//Add the button to HASS
|
|
144
|
+
self.getHASSEntities([{ property: "entity_id", logic: "is", value: entityId }], (entities) => {
|
|
145
|
+
if (entities.length > 1) {
|
|
146
|
+
self.error(`Found more than 1 entity for ${entityId}`);
|
|
147
|
+
return;
|
|
148
|
+
}
|
|
149
|
+
const previousState = entities.length == 1 ? entities[0].state : "unknown";
|
|
150
|
+
self.addHASSEntity(entityId, data(options.state || previousState), options.creationCallback ? (response) => {
|
|
151
|
+
options.creationCallback(response.payload.state, response);
|
|
152
|
+
} : undefined);
|
|
153
|
+
});
|
|
154
|
+
//Assign the pressed callback if set
|
|
155
|
+
if (options.pressedCallback) {
|
|
156
|
+
self.hassEventCallServiceCallbacks[entityId] = function (domain, service, serviceData) {
|
|
157
|
+
if (domain == "button" && service == "press" && (serviceData === null || serviceData === void 0 ? void 0 : serviceData.entity_id) == entityId) {
|
|
158
|
+
const state = new Date();
|
|
159
|
+
//Tell HASS that the button was pressed
|
|
160
|
+
self.sendHASSAPI("http", "post", "/api/states/" + entityId, undefined, undefined, data(state));
|
|
161
|
+
options.pressedCallback(state, serviceData);
|
|
162
|
+
}
|
|
163
|
+
};
|
|
164
|
+
}
|
|
165
|
+
};
|
|
166
|
+
self.addHASSScene = function (options) {
|
|
167
|
+
const entityId = options.id || (0, utility_1.getEntityId)("scene", options.friendlyName);
|
|
168
|
+
const data = (state) => {
|
|
169
|
+
return {
|
|
170
|
+
state: state || "unknown",
|
|
171
|
+
attributes: {
|
|
172
|
+
friendly_name: options.friendlyName
|
|
173
|
+
}
|
|
174
|
+
};
|
|
175
|
+
};
|
|
176
|
+
//Add the scene to HASS
|
|
177
|
+
self.getHASSEntities([{ property: "entity_id", logic: "is", value: entityId }], (entities) => {
|
|
178
|
+
if (entities.length > 1) {
|
|
179
|
+
self.error(`Found more than 1 entity for ${entityId}`);
|
|
180
|
+
return;
|
|
181
|
+
}
|
|
182
|
+
const previousState = entities.length == 1 ? entities[0].state : "unknown";
|
|
183
|
+
self.addHASSEntity(entityId, data(options.state || previousState), options.creationCallback ? (response) => {
|
|
184
|
+
options.creationCallback(response.payload.state, response);
|
|
185
|
+
} : undefined);
|
|
186
|
+
});
|
|
187
|
+
//Assign the activated callback if set
|
|
188
|
+
if (options.activatedCallback) {
|
|
189
|
+
self.hassEventCallServiceCallbacks[entityId] = function (domain, service, serviceData) {
|
|
190
|
+
if (domain == "scene" && service == "turn_on") {
|
|
191
|
+
const entities = typeof serviceData.entity_id == "string" ? [serviceData.entity_id] : serviceData.entity_id;
|
|
192
|
+
if (!entities.includes(entityId)) {
|
|
193
|
+
return;
|
|
194
|
+
}
|
|
195
|
+
const state = new Date();
|
|
196
|
+
//Tell HASS that the scene was activated
|
|
197
|
+
self.sendHASSAPI("http", "post", "/api/states/" + entityId, undefined, undefined, data(state));
|
|
198
|
+
options.activatedCallback(state, serviceData);
|
|
199
|
+
}
|
|
200
|
+
};
|
|
201
|
+
}
|
|
202
|
+
};
|
|
203
|
+
self.addHASSSelect = function (options) {
|
|
204
|
+
const entityId = options.id || (0, utility_1.getEntityId)("select", options.friendlyName);
|
|
205
|
+
const data = (state) => {
|
|
206
|
+
return {
|
|
207
|
+
state: state || "unknown",
|
|
208
|
+
attributes: {
|
|
209
|
+
friendly_name: options.friendlyName,
|
|
210
|
+
options: options.options
|
|
211
|
+
}
|
|
212
|
+
};
|
|
213
|
+
};
|
|
214
|
+
//Add the select to HASS
|
|
215
|
+
self.getHASSEntities([{ property: "entity_id", logic: "is", value: entityId }], (entities) => {
|
|
216
|
+
if (entities.length > 1) {
|
|
217
|
+
self.error(`Found more than 1 entity for ${entityId}`);
|
|
218
|
+
return;
|
|
219
|
+
}
|
|
220
|
+
const previousState = entities.length == 1 ? entities[0].state : "unknown";
|
|
221
|
+
self.addHASSEntity(entityId, data(options.state || previousState), options.creationCallback ? (response) => {
|
|
222
|
+
options.creationCallback(response.payload.state, response);
|
|
223
|
+
} : undefined);
|
|
224
|
+
});
|
|
225
|
+
//Assign the activated callback if set
|
|
226
|
+
if (options.activatedCallback) {
|
|
227
|
+
self.hassEventCallServiceCallbacks[entityId] = function (domain, service, serviceData) {
|
|
228
|
+
if (domain == "select") {
|
|
229
|
+
const entities = typeof serviceData.entity_id == "string" ? [serviceData.entity_id] : serviceData.entity_id;
|
|
230
|
+
if (!entities.includes(entityId)) {
|
|
231
|
+
return;
|
|
232
|
+
}
|
|
233
|
+
if (service == "select_option") {
|
|
234
|
+
self.sendHASSAPI("http", "post", "/api/states/" + entityId, undefined, undefined, data(serviceData.option));
|
|
235
|
+
options.activatedCallback(serviceData.option, serviceData);
|
|
236
|
+
}
|
|
237
|
+
else if (service == "select_first") {
|
|
238
|
+
self.sendHASSAPI("http", "post", "/api/states/" + entityId, undefined, undefined, data(options.options[0] || "unknown"));
|
|
239
|
+
options.activatedCallback(options.options[0] || "unknown", serviceData);
|
|
240
|
+
}
|
|
241
|
+
else if (service == "select_last") {
|
|
242
|
+
self.sendHASSAPI("http", "post", "/api/states/" + entityId, undefined, undefined, data(options.options[options.options.length - 1] || "unknown"));
|
|
243
|
+
options.activatedCallback(options.options[options.options.length - 1] || "unknown", serviceData);
|
|
244
|
+
}
|
|
245
|
+
else if (service == "select_previous" || service == "select_next") {
|
|
246
|
+
self.getHASSEntityState(entityId, (currentState) => {
|
|
247
|
+
let index = options.options.indexOf(currentState);
|
|
248
|
+
if (service == "select_previous") {
|
|
249
|
+
index = index - 1;
|
|
250
|
+
if (index < 0 && serviceData.cycle) {
|
|
251
|
+
index = options.options.length - 1;
|
|
252
|
+
}
|
|
253
|
+
if (index < 0 && !serviceData.cycle) {
|
|
254
|
+
index = 0;
|
|
255
|
+
}
|
|
256
|
+
}
|
|
257
|
+
else if (service == "select_next") {
|
|
258
|
+
index = index + 1;
|
|
259
|
+
if (index >= options.options.length && serviceData.cycle) {
|
|
260
|
+
index = 0;
|
|
261
|
+
}
|
|
262
|
+
if (index >= options.options.length && !serviceData.cycle) {
|
|
263
|
+
index = options.options.length - 1;
|
|
264
|
+
}
|
|
265
|
+
}
|
|
266
|
+
self.sendHASSAPI("http", "post", "/api/states/" + entityId, undefined, undefined, data(options.options[index] || "unknown"));
|
|
267
|
+
options.activatedCallback(options.options[index] || "unknown", serviceData);
|
|
268
|
+
});
|
|
269
|
+
}
|
|
270
|
+
}
|
|
271
|
+
};
|
|
272
|
+
}
|
|
273
|
+
};
|
|
274
|
+
self.handleCallback = function (callbacks, callbackId, ...args) {
|
|
275
|
+
var _a;
|
|
276
|
+
//This is a specific callback id
|
|
277
|
+
if (callbackId) {
|
|
278
|
+
(_a = callbacks[callbackId]) === null || _a === void 0 ? void 0 : _a.call(callbacks, ...args);
|
|
279
|
+
delete callbacks[callbackId];
|
|
280
|
+
return;
|
|
281
|
+
}
|
|
282
|
+
//Send to everyone
|
|
283
|
+
for (const id of Object.keys(callbacks)) {
|
|
284
|
+
if (callbacks[id]) {
|
|
285
|
+
callbacks[id](...args);
|
|
286
|
+
}
|
|
287
|
+
}
|
|
288
|
+
};
|
|
289
|
+
self.msgReceived = function (msg, senderIds) {
|
|
290
|
+
const payload = msg.payload;
|
|
291
|
+
//Handle based on the topic
|
|
292
|
+
switch (msg.topic) {
|
|
293
|
+
case connectionsTypes_1.Topics.API: {
|
|
294
|
+
self.handleCallback(self.hassAPICallbacks, msg.callbackId, msg);
|
|
295
|
+
break;
|
|
296
|
+
}
|
|
297
|
+
case connectionsTypes_1.Topics.EVENT: {
|
|
298
|
+
if (msg.event_type == "home_assistant_client" && msg.payload == "ready") {
|
|
299
|
+
self.handleCallback(self.hassEventReadyCallbacks, msg.callbackId, msg);
|
|
300
|
+
}
|
|
301
|
+
if (payload) {
|
|
302
|
+
switch (payload.event_type) {
|
|
303
|
+
case "call_service":
|
|
304
|
+
self.handleCallback(self.hassEventCallServiceCallbacks, msg.callbackId, payload.event.domain, payload.event.service, payload.event.service_data);
|
|
305
|
+
break;
|
|
306
|
+
case "state_changed":
|
|
307
|
+
self.handleCallback(self.hassEventStateChangeCallbacks, msg.callbackId, payload.event.entity_id, payload.event.old_state, payload.event.new_state);
|
|
308
|
+
break;
|
|
309
|
+
}
|
|
310
|
+
}
|
|
311
|
+
self.handleCallback(self.hassEventCallbacks, msg.callbackId, msg);
|
|
312
|
+
break;
|
|
313
|
+
}
|
|
314
|
+
case connectionsTypes_1.Topics.ACTION: {
|
|
315
|
+
self.handleCallback(self.hassActionCallbacks, msg.callbackId, payload.action, payload.target, payload.data);
|
|
316
|
+
break;
|
|
317
|
+
}
|
|
318
|
+
case connectionsTypes_1.Topics.STATE: {
|
|
319
|
+
self.handleCallback(self.hassCurrentStateCallbacks, msg.callbackId, payload, msg);
|
|
320
|
+
break;
|
|
321
|
+
}
|
|
322
|
+
case connectionsTypes_1.Topics.GET_ENTITIES: {
|
|
323
|
+
self.handleCallback(self.hassGetEntitiesCallbacks, msg.callbackId, payload);
|
|
324
|
+
break;
|
|
325
|
+
}
|
|
326
|
+
}
|
|
327
|
+
};
|
|
328
|
+
};
|
|
329
|
+
RED.nodes.registerType("connections-config-node", register);
|
|
330
|
+
};
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
<script type="text/javascript" id="node-connections-node">
|
|
2
|
+
RED.nodes.registerType("connections-node", {
|
|
3
|
+
category: "HASS Stuff",
|
|
4
|
+
color: "#ffcc00",
|
|
5
|
+
inputs: 1,
|
|
6
|
+
outputs: 1,
|
|
7
|
+
icon: "bulb.svg",
|
|
8
|
+
defaults: {
|
|
9
|
+
name: { value: "" },
|
|
10
|
+
connectionsConfigNode: { value: '', type: "connections-config-node", required: true }
|
|
11
|
+
},
|
|
12
|
+
label: function () {
|
|
13
|
+
return this.name || "Connections"
|
|
14
|
+
}
|
|
15
|
+
});
|
|
16
|
+
</script>
|
|
17
|
+
|
|
18
|
+
|
|
19
|
+
<script type="text/html" data-template-name="connections-node">
|
|
20
|
+
<div class="form-row">
|
|
21
|
+
<label for="node-input-name"><i class="fa fa-tag"></i> Name</label>
|
|
22
|
+
<input type="text" id="node-input-name" placeholder="Name">
|
|
23
|
+
</div>
|
|
24
|
+
<div class="form-row">
|
|
25
|
+
<label for="node-input-connectionsConfigNode">Config</label>
|
|
26
|
+
<input type="text" id="node-input-connectionsConfigNode" />
|
|
27
|
+
</div>
|
|
28
|
+
</script>
|
|
29
|
+
<script type="text/html" data-help-name="connections-node">
|
|
30
|
+
</script>
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
const baseNode_1 = require("../baseNode");
|
|
3
|
+
module.exports = function ConnectionsNode(RED) {
|
|
4
|
+
function register(config) {
|
|
5
|
+
RED.nodes.createNode(this, config);
|
|
6
|
+
(0, baseNode_1.assignBaseNode)(this);
|
|
7
|
+
const connectionsConfigNode = RED.nodes.getNode(config.connectionsConfigNode);
|
|
8
|
+
//When a config node wants to send a message to the output
|
|
9
|
+
connectionsConfigNode.addMsgCallback(this.id, (msg) => {
|
|
10
|
+
this.send(msg);
|
|
11
|
+
});
|
|
12
|
+
this.on("input", (msg, send, done) => {
|
|
13
|
+
connectionsConfigNode.msgReceived(msg, [this.id]);
|
|
14
|
+
});
|
|
15
|
+
}
|
|
16
|
+
RED.nodes.registerType("connections-node", register);
|
|
17
|
+
};
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.Topics = void 0;
|
|
4
|
+
var Topics;
|
|
5
|
+
(function (Topics) {
|
|
6
|
+
Topics["API"] = "api";
|
|
7
|
+
Topics["EVENT"] = "event";
|
|
8
|
+
Topics["STATE"] = "state";
|
|
9
|
+
Topics["ACTION"] = "action";
|
|
10
|
+
Topics["GET_ENTITIES"] = "get_entities";
|
|
11
|
+
})(Topics = exports.Topics || (exports.Topics = {}));
|
|
@@ -0,0 +1,109 @@
|
|
|
1
|
+
<script type="text/javascript" id="node-light-control-config-node">
|
|
2
|
+
RED.nodes.registerType("light-control-config-node", {
|
|
3
|
+
category: "config",
|
|
4
|
+
defaults: {
|
|
5
|
+
name: { value: "" },
|
|
6
|
+
connectionsConfigNode: { value: "", type: "connections-config-node", required: true },
|
|
7
|
+
groupEntityId: { value: "", required: true, default: "light.example" },
|
|
8
|
+
nightModeEntityId: { value: "", required: false, default: "input_boolean.example" },
|
|
9
|
+
entitiesOffAtNight: { value: "", required: false, default: "light.example1,light.example2" },
|
|
10
|
+
concentrateSettings: { value: "", required: true, default: "concentrate 100" },
|
|
11
|
+
readSettings: { value: "", required: true, default: "read 100" },
|
|
12
|
+
relaxSettings: { value: "", required: true, default: "relax 100" },
|
|
13
|
+
restSettings: { value: "", required: true, default: "rest 100" },
|
|
14
|
+
nightLightSettings: { value: "", required: true, default: "nightLight 100" },
|
|
15
|
+
nightSettings: { value: "", required: true, default: "nightLight 30" },
|
|
16
|
+
},
|
|
17
|
+
label: function () {
|
|
18
|
+
return this.name || "Light Control Config"
|
|
19
|
+
}
|
|
20
|
+
});
|
|
21
|
+
</script>
|
|
22
|
+
|
|
23
|
+
<script type="text/html" data-template-name="light-control-config-node">
|
|
24
|
+
<div class="form-row">
|
|
25
|
+
<h2>Basic configuration</h2>
|
|
26
|
+
</div>
|
|
27
|
+
<div class="form-row">
|
|
28
|
+
<label for="node-config-input-name"><i class="fa fa-tag"></i> Name</label>
|
|
29
|
+
<input type="text" id="node-config-input-name" placeholder="Name">
|
|
30
|
+
</div>
|
|
31
|
+
<div class="form-row">
|
|
32
|
+
<label for="node-config-input-connectionsConfigNode">Config</label>
|
|
33
|
+
<input type="text" id="node-config-input-connectionsConfigNode" />
|
|
34
|
+
</div>
|
|
35
|
+
<div class="form-row">
|
|
36
|
+
<label style="font-weight: bold;" for="node-config-input-groupEntityId">Group Entity ID</label>
|
|
37
|
+
<p>The entity ID of the light group to control.</p>
|
|
38
|
+
<input type="text" id="node-config-input-groupEntityId" />
|
|
39
|
+
</div>
|
|
40
|
+
<div class="form-row">
|
|
41
|
+
<label style="font-weight: bold;" for="node-config-input-nightModeEntityId">Night Mode Entity ID</label>
|
|
42
|
+
<p>The entity ID of the input_boolean that controls night mode. Empty to disable</p>
|
|
43
|
+
<input type="text" id="node-config-input-nightModeEntityId" />
|
|
44
|
+
</div>
|
|
45
|
+
<div class="form-row">
|
|
46
|
+
<label style="font-weight: bold;" for="node-config-input-entitiesOffAtNight">Entities Off At Night</label>
|
|
47
|
+
<p>Comma-separated list of entities to turn off during night mode. Empty to disable</p>
|
|
48
|
+
<input type="text" id="node-config-input-entitiesOffAtNight" />
|
|
49
|
+
</div>
|
|
50
|
+
<div class="form-row">
|
|
51
|
+
<hr>
|
|
52
|
+
<h2>Scene definitions</h2>
|
|
53
|
+
<p>
|
|
54
|
+
The following settings define what the scenes should do. They follow the syntax of [scene] [brightnessPercent]
|
|
55
|
+
where scene is the scene name, if the same as below values will use the
|
|
56
|
+
<a style="font-weight: bold;" href="https://github.com/basnijholt/adaptive-lighting">Adaptive Lighting HACS plugin</a>
|
|
57
|
+
otherwise will send to scene.apply. The brightnessPercent is the brightness percentage to set
|
|
58
|
+
</p>
|
|
59
|
+
<ul>
|
|
60
|
+
<li>rest</li>
|
|
61
|
+
<li>relax</li>
|
|
62
|
+
<li>concentrate</li>
|
|
63
|
+
<li>energize</li>
|
|
64
|
+
<li>coolBright</li>
|
|
65
|
+
<li>bright</li>
|
|
66
|
+
<li>dimmed</li>
|
|
67
|
+
<li>nightLight</li>
|
|
68
|
+
<li>sleepy</li>
|
|
69
|
+
<li>paintedSky</li>
|
|
70
|
+
<li>rollingHills</li>
|
|
71
|
+
<li>sailingAway</li>
|
|
72
|
+
<li>sunFlare</li>
|
|
73
|
+
</ul>
|
|
74
|
+
</div>
|
|
75
|
+
|
|
76
|
+
<div class="form-row">
|
|
77
|
+
<label style="font-weight: bold;" for="node-config-input-concentrateSettings">Concentrate Settings</label>
|
|
78
|
+
<p>The scene to use for the concentrate scene [scene] [brightnessPercent]</p>
|
|
79
|
+
<input type="text" id="node-config-input-concentrateSettings" />
|
|
80
|
+
</div>
|
|
81
|
+
<div class="form-row">
|
|
82
|
+
<label style="font-weight: bold;" for="node-config-input-readSettings">Read Settings</label>
|
|
83
|
+
<p>The scene to use for the read scene [scene] [brightnessPercent]</p>
|
|
84
|
+
<input type="text" id="node-config-input-readSettings" />
|
|
85
|
+
</div>
|
|
86
|
+
<div class="form-row">
|
|
87
|
+
<label style="font-weight: bold;" for="node-config-input-relaxSettings">Relax Settings</label>
|
|
88
|
+
<p>The scene to use for the relax scene [scene] [brightnessPercent]</p>
|
|
89
|
+
<input type="text" id="node-config-input-relaxSettings" />
|
|
90
|
+
</div>
|
|
91
|
+
<div class="form-row">
|
|
92
|
+
<label style="font-weight: bold;" for="node-config-input-restSettings">Rest Settings</label>
|
|
93
|
+
<p>The scene to use for the rest scene [scene] [brightnessPercent]</p>
|
|
94
|
+
<input type="text" id="node-config-input-restSettings" />
|
|
95
|
+
</div>
|
|
96
|
+
<div class="form-row">
|
|
97
|
+
<label style="font-weight: bold;" for="node-config-input-nightLightSettings">Night Light Settings</label>
|
|
98
|
+
<p>The scene to use for the night light scene [scene] [brightnessPercent]</p>
|
|
99
|
+
<input type="text" id="node-config-input-nightLightSettings" />
|
|
100
|
+
</div>
|
|
101
|
+
<div class="form-row">
|
|
102
|
+
<label style="font-weight: bold;" for="node-config-input-nightSettings">Night Settings</label>
|
|
103
|
+
<p>The scene to use for the night light scene [scene] [brightnessPercent]</p>
|
|
104
|
+
<input type="text" id="node-config-input-nightSettings" />
|
|
105
|
+
</div>
|
|
106
|
+
</script>
|
|
107
|
+
|
|
108
|
+
<script type="text/html" data-help-name="light-control-config-node">
|
|
109
|
+
</script>
|