node-red-contrib-knx-ultimate 2.5.0 → 3.0.0-beta1

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.
Files changed (150) hide show
  1. package/.eslintrc.json +3 -2
  2. package/CHANGELOG.md +13 -0
  3. package/README.md +2 -1
  4. package/{KNXEngine → _JS_KNXEngine}/README.md +7 -7
  5. package/{KNXEngine → _JS_KNXEngine}/index.js +1 -1
  6. package/{KNXEngine → _JS_KNXEngine}/sample.js +5 -5
  7. package/{KNXEngine → _JS_KNXEngine}/sampleSecure.js +1 -1
  8. package/{KNXEngine → _JS_KNXEngine}/src/KNXClient.js +3 -3
  9. package/_JS_KNXEngine/src/dptlib/dpt60002.js +101 -0
  10. package/{KNXEngine → _JS_KNXEngine}/src/protocol/KNXConnectResponse.js +2 -0
  11. package/{KNXEngine → _JS_KNXEngine}/src/protocol/KNXConstants.js +1 -0
  12. package/nodes/commonFunctions.js +3 -3
  13. package/nodes/hue-config.html +2 -0
  14. package/nodes/knxUltimate-config.html +2 -0
  15. package/nodes/knxUltimate-config.js +226 -223
  16. package/nodes/knxUltimate.html +123 -56
  17. package/nodes/knxUltimate.js +100 -60
  18. package/nodes/knxUltimateAlerter.html +7 -12
  19. package/nodes/knxUltimateAlerter.js +2 -2
  20. package/nodes/knxUltimateGarageDoorBarrierOpener.html +7 -12
  21. package/nodes/knxUltimateGarageDoorBarrierOpener.js +2 -2
  22. package/nodes/knxUltimateGlobalContext.html +2 -0
  23. package/nodes/knxUltimateHueBattery.html +11 -14
  24. package/nodes/knxUltimateHueButton.html +27 -22
  25. package/nodes/knxUltimateHueButton.js +1 -1
  26. package/nodes/knxUltimateHueContactSensor.html +12 -8
  27. package/nodes/knxUltimateHueLight.html +32 -26
  28. package/nodes/knxUltimateHueLight.js +43 -6
  29. package/nodes/knxUltimateHueLightSensor.html +11 -14
  30. package/nodes/knxUltimateHueMotion.html +11 -14
  31. package/nodes/knxUltimateHueScene.html +24 -19
  32. package/nodes/knxUltimateHueScene.js +2 -1
  33. package/nodes/knxUltimateHueTapDial.html +11 -14
  34. package/nodes/knxUltimateHueTemperatureSensor.html +11 -14
  35. package/nodes/knxUltimateHueZigbeeConnectivity.html +11 -14
  36. package/nodes/knxUltimateLoadControl.html +4 -11
  37. package/nodes/knxUltimateLoadControl.js +1 -1
  38. package/nodes/knxUltimateLogger.html +3 -1
  39. package/nodes/knxUltimateSceneController.html +14 -15
  40. package/nodes/knxUltimateViewer.html +2 -0
  41. package/nodes/knxUltimateViewer.js +1 -1
  42. package/nodes/knxUltimateWatchDog.html +3 -1
  43. package/nodes/utils/payloadManipulation.js +49 -1
  44. package/nodes/utils/utils.js +4 -0
  45. package/package.json +4 -3
  46. package/resources/htmlUtils.js +27 -0
  47. /package/{KNXEngine → _JS_KNXEngine}/CHANGELOG.md +0 -0
  48. /package/{KNXEngine → _JS_KNXEngine}/LICENSE +0 -0
  49. /package/{KNXEngine → _JS_KNXEngine}/img/dpt 2.png +0 -0
  50. /package/{KNXEngine → _JS_KNXEngine}/img/dpt.png +0 -0
  51. /package/{KNXEngine → _JS_KNXEngine}/img/logo 2.png +0 -0
  52. /package/{KNXEngine → _JS_KNXEngine}/img/logo-big 2.png +0 -0
  53. /package/{KNXEngine → _JS_KNXEngine}/img/logo-big.png +0 -0
  54. /package/{KNXEngine → _JS_KNXEngine}/img/logo.png +0 -0
  55. /package/{KNXEngine → _JS_KNXEngine}/img/nodered 2.png +0 -0
  56. /package/{KNXEngine → _JS_KNXEngine}/img/nodered.png +0 -0
  57. /package/{KNXEngine → _JS_KNXEngine}/package.json +0 -0
  58. /package/{KNXEngine → _JS_KNXEngine}/simpleSample.js +0 -0
  59. /package/{KNXEngine → _JS_KNXEngine}/src/Curve25519.js +0 -0
  60. /package/{KNXEngine → _JS_KNXEngine}/src/KNXSocketOptions.js +0 -0
  61. /package/{KNXEngine → _JS_KNXEngine}/src/KNXsecureKeyring.js +0 -0
  62. /package/{KNXEngine → _JS_KNXEngine}/src/KnxLog.js +0 -0
  63. /package/{KNXEngine → _JS_KNXEngine}/src/cur.js +0 -0
  64. /package/{KNXEngine → _JS_KNXEngine}/src/dptlib/dpt1.js +0 -0
  65. /package/{KNXEngine → _JS_KNXEngine}/src/dptlib/dpt10.js +0 -0
  66. /package/{KNXEngine → _JS_KNXEngine}/src/dptlib/dpt11.js +0 -0
  67. /package/{KNXEngine → _JS_KNXEngine}/src/dptlib/dpt12.js +0 -0
  68. /package/{KNXEngine → _JS_KNXEngine}/src/dptlib/dpt13.js +0 -0
  69. /package/{KNXEngine → _JS_KNXEngine}/src/dptlib/dpt14.js +0 -0
  70. /package/{KNXEngine → _JS_KNXEngine}/src/dptlib/dpt15.js +0 -0
  71. /package/{KNXEngine → _JS_KNXEngine}/src/dptlib/dpt16.js +0 -0
  72. /package/{KNXEngine → _JS_KNXEngine}/src/dptlib/dpt17.js +0 -0
  73. /package/{KNXEngine → _JS_KNXEngine}/src/dptlib/dpt18.js +0 -0
  74. /package/{KNXEngine → _JS_KNXEngine}/src/dptlib/dpt19.js +0 -0
  75. /package/{KNXEngine → _JS_KNXEngine}/src/dptlib/dpt2.js +0 -0
  76. /package/{KNXEngine → _JS_KNXEngine}/src/dptlib/dpt20.js +0 -0
  77. /package/{KNXEngine → _JS_KNXEngine}/src/dptlib/dpt21.js +0 -0
  78. /package/{KNXEngine → _JS_KNXEngine}/src/dptlib/dpt213.js +0 -0
  79. /package/{KNXEngine → _JS_KNXEngine}/src/dptlib/dpt22.js +0 -0
  80. /package/{KNXEngine → _JS_KNXEngine}/src/dptlib/dpt222.js +0 -0
  81. /package/{KNXEngine → _JS_KNXEngine}/src/dptlib/dpt232.js +0 -0
  82. /package/{KNXEngine → _JS_KNXEngine}/src/dptlib/dpt235.js +0 -0
  83. /package/{KNXEngine → _JS_KNXEngine}/src/dptlib/dpt237.js +0 -0
  84. /package/{KNXEngine → _JS_KNXEngine}/src/dptlib/dpt238.js +0 -0
  85. /package/{KNXEngine → _JS_KNXEngine}/src/dptlib/dpt242.js +0 -0
  86. /package/{KNXEngine → _JS_KNXEngine}/src/dptlib/dpt249.js +0 -0
  87. /package/{KNXEngine → _JS_KNXEngine}/src/dptlib/dpt251.js +0 -0
  88. /package/{KNXEngine → _JS_KNXEngine}/src/dptlib/dpt275.js +0 -0
  89. /package/{KNXEngine → _JS_KNXEngine}/src/dptlib/dpt28.js +0 -0
  90. /package/{KNXEngine → _JS_KNXEngine}/src/dptlib/dpt29.js +0 -0
  91. /package/{KNXEngine → _JS_KNXEngine}/src/dptlib/dpt3.js +0 -0
  92. /package/{KNXEngine → _JS_KNXEngine}/src/dptlib/dpt4.js +0 -0
  93. /package/{KNXEngine → _JS_KNXEngine}/src/dptlib/dpt5.js +0 -0
  94. /package/{KNXEngine → _JS_KNXEngine}/src/dptlib/dpt6.js +0 -0
  95. /package/{KNXEngine → _JS_KNXEngine}/src/dptlib/dpt60001.js +0 -0
  96. /package/{KNXEngine → _JS_KNXEngine}/src/dptlib/dpt7.js +0 -0
  97. /package/{KNXEngine → _JS_KNXEngine}/src/dptlib/dpt8.js +0 -0
  98. /package/{KNXEngine → _JS_KNXEngine}/src/dptlib/dpt9.js +0 -0
  99. /package/{KNXEngine → _JS_KNXEngine}/src/dptlib/dpt999.js +0 -0
  100. /package/{KNXEngine → _JS_KNXEngine}/src/dptlib/index.js +0 -0
  101. /package/{KNXEngine → _JS_KNXEngine}/src/errors/BufferLengthError.js +0 -0
  102. /package/{KNXEngine → _JS_KNXEngine}/src/errors/DateFormatError.js +0 -0
  103. /package/{KNXEngine → _JS_KNXEngine}/src/errors/DuplicateRequestError.js +0 -0
  104. /package/{KNXEngine → _JS_KNXEngine}/src/errors/InvalidValueError.js +0 -0
  105. /package/{KNXEngine → _JS_KNXEngine}/src/errors/NotImplementedError.js +0 -0
  106. /package/{KNXEngine → _JS_KNXEngine}/src/errors/RequestTimeoutError.js +0 -0
  107. /package/{KNXEngine → _JS_KNXEngine}/src/errors/index.js +0 -0
  108. /package/{KNXEngine → _JS_KNXEngine}/src/index.js +0 -0
  109. /package/{KNXEngine → _JS_KNXEngine}/src/protocol/CRD.js +0 -0
  110. /package/{KNXEngine → _JS_KNXEngine}/src/protocol/CRI.js +0 -0
  111. /package/{KNXEngine → _JS_KNXEngine}/src/protocol/CRIFactory.js +0 -0
  112. /package/{KNXEngine → _JS_KNXEngine}/src/protocol/DIB.js +0 -0
  113. /package/{KNXEngine → _JS_KNXEngine}/src/protocol/DeviceInfo.js +0 -0
  114. /package/{KNXEngine → _JS_KNXEngine}/src/protocol/HPAI.js +0 -0
  115. /package/{KNXEngine → _JS_KNXEngine}/src/protocol/IPConfig.js +0 -0
  116. /package/{KNXEngine → _JS_KNXEngine}/src/protocol/IPCurrentConfig.js +0 -0
  117. /package/{KNXEngine → _JS_KNXEngine}/src/protocol/KNXAddress.js +0 -0
  118. /package/{KNXEngine → _JS_KNXEngine}/src/protocol/KNXAddresses.js +0 -0
  119. /package/{KNXEngine → _JS_KNXEngine}/src/protocol/KNXConnectRequest.js +0 -0
  120. /package/{KNXEngine → _JS_KNXEngine}/src/protocol/KNXConnectionStateRequest.js +0 -0
  121. /package/{KNXEngine → _JS_KNXEngine}/src/protocol/KNXConnectionStateResponse.js +0 -0
  122. /package/{KNXEngine → _JS_KNXEngine}/src/protocol/KNXDataBuffer.js +0 -0
  123. /package/{KNXEngine → _JS_KNXEngine}/src/protocol/KNXDescriptionRequest.js +0 -0
  124. /package/{KNXEngine → _JS_KNXEngine}/src/protocol/KNXDescriptionResponse.js +0 -0
  125. /package/{KNXEngine → _JS_KNXEngine}/src/protocol/KNXDisconnectRequest.js +0 -0
  126. /package/{KNXEngine → _JS_KNXEngine}/src/protocol/KNXDisconnectResponse.js +0 -0
  127. /package/{KNXEngine → _JS_KNXEngine}/src/protocol/KNXHeader.js +0 -0
  128. /package/{KNXEngine → _JS_KNXEngine}/src/protocol/KNXPacket.js +0 -0
  129. /package/{KNXEngine → _JS_KNXEngine}/src/protocol/KNXProtocol.js +0 -0
  130. /package/{KNXEngine → _JS_KNXEngine}/src/protocol/KNXRoutingIndication.js +0 -0
  131. /package/{KNXEngine → _JS_KNXEngine}/src/protocol/KNXSearchRequest.js +0 -0
  132. /package/{KNXEngine → _JS_KNXEngine}/src/protocol/KNXSearchResponse.js +0 -0
  133. /package/{KNXEngine → _JS_KNXEngine}/src/protocol/KNXSecureSessionRequest.js +0 -0
  134. /package/{KNXEngine → _JS_KNXEngine}/src/protocol/KNXTunnelingAck.js +0 -0
  135. /package/{KNXEngine → _JS_KNXEngine}/src/protocol/KNXTunnelingRequest.js +0 -0
  136. /package/{KNXEngine → _JS_KNXEngine}/src/protocol/KNXUtils.js +0 -0
  137. /package/{KNXEngine → _JS_KNXEngine}/src/protocol/ServiceFamilies.js +0 -0
  138. /package/{KNXEngine → _JS_KNXEngine}/src/protocol/TunnelCRI.js +0 -0
  139. /package/{KNXEngine → _JS_KNXEngine}/src/protocol/cEMI/AdditionalInfo.js +0 -0
  140. /package/{KNXEngine → _JS_KNXEngine}/src/protocol/cEMI/CEMIConstants.js +0 -0
  141. /package/{KNXEngine → _JS_KNXEngine}/src/protocol/cEMI/CEMIFactory.js +0 -0
  142. /package/{KNXEngine → _JS_KNXEngine}/src/protocol/cEMI/CEMIMessage.js +0 -0
  143. /package/{KNXEngine → _JS_KNXEngine}/src/protocol/cEMI/ControlField.js +0 -0
  144. /package/{KNXEngine → _JS_KNXEngine}/src/protocol/cEMI/LDataCon.js +0 -0
  145. /package/{KNXEngine → _JS_KNXEngine}/src/protocol/cEMI/LDataInd.js +0 -0
  146. /package/{KNXEngine → _JS_KNXEngine}/src/protocol/cEMI/LDataReq.js +0 -0
  147. /package/{KNXEngine → _JS_KNXEngine}/src/protocol/cEMI/NPDU.js +0 -0
  148. /package/{KNXEngine → _JS_KNXEngine}/src/protocol/cEMI/TLVInfo.js +0 -0
  149. /package/{KNXEngine → _JS_KNXEngine}/src/protocol/index.js +0 -0
  150. /package/{KNXEngine → _JS_KNXEngine}/src/util/ipAddressHelper.js +0 -0
@@ -1,3 +1,5 @@
1
+ <script type="text/javascript" src="resources/node-red-contrib-knx-ultimate/htmlUtils.js"></script>
2
+
1
3
  <script type="text/javascript">
2
4
  RED.nodes.registerType('knxUltimateGlobalContext', {
3
5
  category: "KNX Ultimate",
@@ -1,5 +1,7 @@
1
1
  <script type="text/javascript" src="resources/node-red-contrib-knx-ultimate/11f26b4500.js"></script>
2
2
 
3
+ <script type="text/javascript" src="resources/node-red-contrib-knx-ultimate/htmlUtils.js"></script>
4
+
3
5
  <script type="text/javascript">
4
6
  RED.nodes.registerType('knxUltimateHueBattery', {
5
7
  category: "KNX Ultimate",
@@ -57,16 +59,7 @@
57
59
  } catch (error) { }
58
60
  });
59
61
 
60
- // 31/03/2020 Search Helper
61
- function fullSearch(sourceText, searchString) {
62
- // This searches for all words in a string
63
- var aSearchWords = searchString.toLowerCase().split(" ");
64
- var i = 0;
65
- for (let index = 0; index < aSearchWords.length; index++) {
66
- if (sourceText.toLowerCase().indexOf(aSearchWords[index]) > -1) i += 1;
67
- }
68
- return i == aSearchWords.length;
69
- }
62
+
70
63
 
71
64
  // DPT
72
65
  // ########################
@@ -83,13 +76,13 @@
83
76
 
84
77
  // Autocomplete suggestion with ETS csv File
85
78
  $("#node-input-GAbatterysensor").autocomplete({
86
- minLength: 1,
79
+ minLength: 0,
87
80
  source: function (request, response) {
88
81
  //$.getJSON("csv", request, function( data, status, xhr ) {
89
82
  $.getJSON("knxUltimatecsv?nodeID=" + oNodeServer.id, (data) => {
90
83
  response($.map(data, function (value, key) {
91
84
  var sSearch = (value.ga + " (" + value.devicename + ") DPT" + value.dpt);
92
- if (fullSearch(sSearch, request.term + " 5.001")) {
85
+ if (htmlUtilsfullCSVSearch(sSearch, request.term + " 5.001")) {
93
86
  return {
94
87
  label: value.ga + " # " + value.devicename + " # " + value.dpt, // Label for Display
95
88
  value: value.ga // Value
@@ -111,6 +104,8 @@
111
104
  // Select the option value
112
105
  $("#node-input-dptbatterysensor").val(optVal);
113
106
  }
107
+ }).focus(function () {
108
+ $(this).autocomplete('search', $(this).val() + 'exactmatch');
114
109
  });
115
110
  // ########################
116
111
 
@@ -119,13 +114,13 @@
119
114
 
120
115
  // Autocomplete suggestion with HUE
121
116
  $("#node-input-name").autocomplete({
122
- minLength: 1,
117
+ minLength: 0,
123
118
  source: function (request, response) {
124
119
  $.getJSON("KNXUltimateGetResourcesHUE?rtype=device_power&serverId=" + oNodeServerHue.id, (data) => {
125
120
  response($.map(data.devices, function (value, key) {
126
121
  //alert(JSON.stringify(value) + " "+ key)
127
122
  var sSearch = (value.name);
128
- if (fullSearch(sSearch, request.term)) {
123
+ if (htmlUtilsfullCSVSearch(sSearch, request.term)) {
129
124
  return {
130
125
  hueDevice: value.id, // Label for Display
131
126
  value: value.name // Value
@@ -139,6 +134,8 @@
139
134
  // Sets the fields
140
135
  $('#node-input-hueDevice').val(ui.item.hueDevice);
141
136
  }
137
+ }).focus(function () {
138
+ $(this).autocomplete('search', $(this).val() + 'exactmatch');
142
139
  });
143
140
 
144
141
 
@@ -1,5 +1,7 @@
1
1
  <script type="text/javascript" src="resources/node-red-contrib-knx-ultimate/11f26b4500.js"></script>
2
2
 
3
+ <script type="text/javascript" src="resources/node-red-contrib-knx-ultimate/htmlUtils.js"></script>
4
+
3
5
  <script type="text/javascript">
4
6
  RED.nodes.registerType('knxUltimateHueButton', {
5
7
  category: "KNX Ultimate",
@@ -94,16 +96,7 @@
94
96
  }]
95
97
  })
96
98
 
97
- // 31/03/2020 Search Helper
98
- function fullSearch(sourceText, searchString) {
99
- // This searches for all words in a string
100
- var aSearchWords = searchString.toLowerCase().split(" ");
101
- var i = 0;
102
- for (let index = 0; index < aSearchWords.length; index++) {
103
- if (sourceText.toLowerCase().indexOf(aSearchWords[index]) > -1) i += 1;
104
- }
105
- return i == aSearchWords.length;
106
- }
99
+
107
100
 
108
101
  // DPT Dim
109
102
  // ########################
@@ -120,12 +113,12 @@
120
113
 
121
114
  // Autocomplete suggestion with ETS csv File
122
115
  $("#node-input-GArepeat").autocomplete({
123
- minLength: 1,
116
+ minLength: 0,
124
117
  source: function (request, response) {
125
118
  $.getJSON("knxUltimatecsv?nodeID=" + oNodeServer.id, (data) => {
126
119
  response($.map(data, function (value, key) {
127
120
  var sSearch = (value.ga + " (" + value.devicename + ") DPT" + value.dpt);
128
- if (fullSearch(sSearch, request.term)) {
121
+ if (htmlUtilsfullCSVSearch(sSearch, request.term)) {
129
122
  if (value.dpt.startsWith('3.007')) {
130
123
  return {
131
124
  label: value.ga + " # " + value.devicename + " # " + value.dpt, // Label for Display
@@ -149,6 +142,8 @@
149
142
  // Select the option value
150
143
  $("#node-input-dptrepeat").val(optVal);
151
144
  }
145
+ }).focus(function () {
146
+ $(this).autocomplete('search', $(this).val() + 'exactmatch');
152
147
  });
153
148
 
154
149
 
@@ -170,12 +165,12 @@
170
165
 
171
166
  // Autocomplete suggestion with ETS csv File
172
167
  $("#node-input-GAshort_release").autocomplete({
173
- minLength: 1,
168
+ minLength: 0,
174
169
  source: function (request, response) {
175
170
  $.getJSON("knxUltimatecsv?nodeID=" + oNodeServer.id, (data) => {
176
171
  response($.map(data, function (value, key) {
177
172
  var sSearch = (value.ga + " (" + value.devicename + ") DPT" + value.dpt);
178
- if (fullSearch(sSearch, request.term + " 1.")) {
173
+ if (htmlUtilsfullCSVSearch(sSearch, request.term + " 1.")) {
179
174
  return {
180
175
  label: value.ga + " # " + value.devicename + " # " + value.dpt, // Label for Display
181
176
  value: value.ga // Value
@@ -197,16 +192,18 @@
197
192
  // Select the option value
198
193
  $("#node-input-dptshort_release").val(optVal);
199
194
  }
195
+ }).focus(function () {
196
+ $(this).autocomplete('search', $(this).val() + 'exactmatch');
200
197
  });
201
198
 
202
199
  // Autocomplete suggestion with ETS csv File
203
200
  $("#node-input-GAshort_releaseStatus").autocomplete({
204
- minLength: 1,
201
+ minLength: 0,
205
202
  source: function (request, response) {
206
203
  $.getJSON("knxUltimatecsv?nodeID=" + oNodeServer.id, (data) => {
207
204
  response($.map(data, function (value, key) {
208
205
  var sSearch = (value.ga + " (" + value.devicename + ") DPT" + value.dpt);
209
- if (fullSearch(sSearch, request.term + " 1.")) {
206
+ if (htmlUtilsfullCSVSearch(sSearch, request.term + " 1.")) {
210
207
  return {
211
208
  label: value.ga + " # " + value.devicename + " # " + value.dpt, // Label for Display
212
209
  value: value.ga // Value
@@ -228,17 +225,19 @@
228
225
  // Select the option value
229
226
  $("#node-input-dptshort_releaseStatus").val(optVal);
230
227
  }
228
+ }).focus(function () {
229
+ $(this).autocomplete('search', $(this).val() + 'exactmatch');
231
230
  });
232
231
 
233
232
 
234
233
  // Autocomplete suggestion with ETS csv File
235
234
  $("#node-input-GAdouble_short_release").autocomplete({
236
- minLength: 1,
235
+ minLength: 0,
237
236
  source: function (request, response) {
238
237
  $.getJSON("knxUltimatecsv?nodeID=" + oNodeServer.id, (data) => {
239
238
  response($.map(data, function (value, key) {
240
239
  var sSearch = (value.ga + " (" + value.devicename + ") DPT" + value.dpt);
241
- if (fullSearch(sSearch, request.term + " 1.")) {
240
+ if (htmlUtilsfullCSVSearch(sSearch, request.term + " 1.")) {
242
241
  return {
243
242
  label: value.ga + " # " + value.devicename + " # " + value.dpt, // Label for Display
244
243
  value: value.ga // Value
@@ -260,16 +259,18 @@
260
259
  // Select the option value
261
260
  $("#node-input-dptdouble_short_release").val(optVal);
262
261
  }
262
+ }).focus(function () {
263
+ $(this).autocomplete('search', $(this).val() + 'exactmatch');
263
264
  });
264
265
 
265
266
  // Autocomplete suggestion with ETS csv File
266
267
  $("#node-input-GAdouble_short_releaseStatus").autocomplete({
267
- minLength: 1,
268
+ minLength: 0,
268
269
  source: function (request, response) {
269
270
  $.getJSON("knxUltimatecsv?nodeID=" + oNodeServer.id, (data) => {
270
271
  response($.map(data, function (value, key) {
271
272
  var sSearch = (value.ga + " (" + value.devicename + ") DPT" + value.dpt);
272
- if (fullSearch(sSearch, request.term + " 1.")) {
273
+ if (htmlUtilsfullCSVSearch(sSearch, request.term + " 1.")) {
273
274
  return {
274
275
  label: value.ga + " # " + value.devicename + " # " + value.dpt, // Label for Display
275
276
  value: value.ga // Value
@@ -291,17 +292,19 @@
291
292
  // Select the option value
292
293
  $("#node-input-dptdouble_short_releaseStatus").val(optVal);
293
294
  }
295
+ }).focus(function () {
296
+ $(this).autocomplete('search', $(this).val() + 'exactmatch');
294
297
  });
295
298
 
296
299
  // Autocomplete suggestion with HUE
297
300
  $("#node-input-name").autocomplete({
298
- minLength: 1,
301
+ minLength: 0,
299
302
  source: function (request, response) {
300
303
  $.getJSON("KNXUltimateGetResourcesHUE?rtype=button&serverId=" + oNodeServerHue.id, (data) => {
301
304
  response($.map(data.devices, function (value, key) {
302
305
  //alert(JSON.stringify(value) + " "+ key)
303
306
  var sSearch = (value.name);
304
- if (fullSearch(sSearch, request.term)) {
307
+ if (htmlUtilsfullCSVSearch(sSearch, request.term)) {
305
308
  return {
306
309
  hueDevice: value.id, // Label for Display
307
310
  value: value.name // Value
@@ -315,6 +318,8 @@
315
318
  // Sets the fields
316
319
  $('#node-input-hueDevice').val(ui.item.hueDevice)
317
320
  }
321
+ }).focus(function () {
322
+ $(this).autocomplete('search', $(this).val() + 'exactmatch');
318
323
  });
319
324
 
320
325
 
@@ -1,5 +1,5 @@
1
1
  module.exports = function (RED) {
2
- const dptlib = require("../KNXEngine/src/dptlib");
2
+ const dptlib = require('knxultimate').dptlib;
3
3
 
4
4
  function knxUltimateHueButton(config) {
5
5
  RED.nodes.createNode(this, config);
@@ -1,5 +1,7 @@
1
1
  <script type="text/javascript" src="resources/node-red-contrib-knx-ultimate/11f26b4500.js"></script>
2
2
 
3
+ <script type="text/javascript" src="resources/node-red-contrib-knx-ultimate/htmlUtils.js"></script>
4
+
3
5
  <script type="text/javascript">
4
6
  RED.nodes.registerType('knxUltimateHueContactSensor', {
5
7
  category: 'KNX Ultimate',
@@ -83,13 +85,13 @@
83
85
 
84
86
  // Autocomplete suggestion with ETS csv File
85
87
  $('#node-input-GAcontact').autocomplete({
86
- minLength: 1,
88
+ minLength: 0,
87
89
  source: function (request, response) {
88
90
  //$.getJSON("csv", request, function( data, status, xhr ) {
89
91
  $.getJSON('knxUltimatecsv?nodeID=' + oNodeServer.id, (data) => {
90
92
  response($.map(data, function (value, key) {
91
93
  var sSearch = (value.ga + ' (' + value.devicename + ') DPT' + value.dpt)
92
- if (fullSearch(sSearch, request.term + ' 1.')) {
94
+ if (htmlUtilsfullCSVSearch(sSearch, request.term + ' 1.')) {
93
95
  return {
94
96
  label: value.ga + ' # ' + value.devicename + ' # ' + value.dpt, // Label for Display
95
97
  value: value.ga, // Value
@@ -111,19 +113,21 @@
111
113
  // Select the option value
112
114
  $('#node-input-dptcontact').val(optVal)
113
115
  },
114
- })
116
+ }).focus(function () {
117
+ $(this).autocomplete('search', $(this).val() + 'exactmatch');
118
+ });
115
119
  // ########################
116
120
 
117
121
 
118
122
  // Autocomplete suggestion with HUE
119
123
  $('#node-input-name').autocomplete({
120
- minLength: 1,
124
+ minLength: 0,
121
125
  source: function (request, response) {
122
126
  $.getJSON('KNXUltimateGetResourcesHUE?rtype=contact&serverId=' + oNodeServerHue.id, (data) => {
123
127
  response($.map(data.devices, function (value, key) {
124
128
  //alert(JSON.stringify(value) + " "+ key)
125
129
  var sSearch = (value.name)
126
- if (fullSearch(sSearch, request.term)) {
130
+ if (htmlUtilsfullCSVSearch(sSearch, request.term)) {
127
131
  return {
128
132
  hueDevice: value.id, // Label for Display
129
133
  value: value.name, // Value
@@ -137,9 +141,9 @@
137
141
  // Sets the fields
138
142
  $('#node-input-hueDevice').val(ui.item.hueDevice)
139
143
  },
140
- })
141
-
142
-
144
+ }).focus(function () {
145
+ $(this).autocomplete('search', $(this).val() + 'exactmatch');
146
+ });
143
147
  // ########################
144
148
 
145
149
 
@@ -2,22 +2,11 @@
2
2
 
3
3
  <script type="text/javascript" src="resources/node-red-contrib-knx-ultimate/11f26b4500.js"></script>
4
4
 
5
+ <script type="text/javascript" src="resources/node-red-contrib-knx-ultimate/htmlUtils.js"></script>
6
+
5
7
  <script type="text/javascript">
6
8
  (function () {
7
9
 
8
- // 31/03/2020 Search Helper
9
- function fullSearch(sourceText, searchString) {
10
- // node searches for all words in a string
11
- var aSearchWords = searchString.toLowerCase().split(" ");
12
- var i = 0;
13
- for (let index = 0; index < aSearchWords.length; index++) {
14
- if (sourceText.toLowerCase().indexOf(aSearchWords[index]) > -1) i += 1;
15
- }
16
- return i == aSearchWords.length;
17
- }
18
-
19
-
20
-
21
10
  RED.nodes.registerType("knxUltimateHueLight", {
22
11
  category: "KNX Ultimate",
23
12
  color: "#C0C7E9",
@@ -129,6 +118,8 @@
129
118
 
130
119
  hueDevice: { value: "" },
131
120
  hueDeviceObject: { value: {} },
121
+
122
+ restoreDayMode: { value: "no" }
132
123
  },
133
124
  inputs: 0,
134
125
  outputs: 0,
@@ -195,7 +186,7 @@
195
186
 
196
187
  function getGroupAddress(_sourceWidgetAutocomplete, _destinationWidgetName, _destinationWidgetDPT, _additionalSearchTerm) {
197
188
  $(_sourceWidgetAutocomplete).autocomplete({
198
- minLength: 1,
189
+ minLength: 0,
199
190
  source: function (request, response) {
200
191
  //$.getJSON("csv", request, function( data, status, xhr ) {
201
192
  $.getJSON("knxUltimatecsv?nodeID=" + $("#node-input-server").val() + "&" + { _: new Date().getTime() }, (data) => {
@@ -204,7 +195,7 @@
204
195
  var sSearch = value.ga + " (" + value.devicename + ") DPT" + value.dpt;
205
196
  for (let index = 0; index < _additionalSearchTerm.length; index++) {
206
197
  const sDPT = _additionalSearchTerm[index];
207
- if (fullSearch(sSearch, request.term + " " + sDPT)) {
198
+ if (htmlUtilsfullCSVSearch(sSearch, request.term + " " + sDPT)) {
208
199
  return {
209
200
  label: value.ga + " # " + value.devicename + " # " + value.dpt, // Label for Display
210
201
  value: value.ga, // Value
@@ -226,6 +217,8 @@
226
217
  // Select the option value
227
218
  $(_destinationWidgetDPT).val(optVal);
228
219
  },
220
+ }).focus(function () {
221
+ $(this).autocomplete('search', $(this).val() + 'exactmatch');
229
222
  });
230
223
  }
231
224
 
@@ -688,14 +681,14 @@
688
681
 
689
682
  // Autocomplete suggestion with HUE Lights
690
683
  $("#node-input-name").autocomplete({
691
- minLength: 1,
684
+ minLength: 0,
692
685
  source: function (request, response) {
693
686
  $.getJSON("KNXUltimateGetResourcesHUE?rtype=light&serverId=" + $("#node-input-serverHue").val() + "&" + { _: new Date().getTime() }, (data) => {
694
687
  response(
695
688
  $.map(data.devices, function (value, key) {
696
689
  var sSearch = value.name;
697
690
  if (!value.name.includes("I'm still connecting")) {
698
- if (fullSearch(sSearch, request.term)) {
691
+ if (htmlUtilsfullCSVSearch(sSearch, request.term)) {
699
692
  return {
700
693
  hueDevice: value.id,
701
694
  value: value.name,
@@ -722,6 +715,8 @@
722
715
  }
723
716
  Go();
724
717
  }
718
+ }).focus(function () {
719
+ $(this).autocomplete('search', $(this).val() + 'exactmatch');
725
720
  });
726
721
 
727
722
  // Timer connection to backend ####################################################
@@ -965,13 +960,13 @@
965
960
 
966
961
  <div id="tabs" hidden" style="width: 900px;">
967
962
  <ul>
968
- <li><a href="#tabs-1"><i class="fa-solid fa-toggle-on fa-beat"></i> Switch</a></li>
969
- <li><a href="#tabs-2"><i class="fa-solid fa-arrow-up-wide-short fa-beat"></i> Dim</a></li>
970
- <li><a href="#tabs-3"><i class="fa-solid fa-temperature-quarter fa-beat"></i> Tunable white</a></li>
971
- <li><a href="#tabs-4"><i class="fa-solid fa-palette fa-beat"></i> RGB/HSV</a></li>
972
- <li><a href="#tabs-5"><i class="fa-solid fa-heart-circle-check fa-beat"></i> Effects</a></li>
973
- <li><a href="#tabs-6"><i class="fa-solid fa-code-merge fa-beat"></i> Behaviour</a></li>
974
- <li><a href="#tabs-7"><i class="fa-solid fa-house fa-beat"></i> Home Assistant Export (beta)</a></li>
963
+ <li><a href="#tabs-1"><i class="fa-solid fa-toggle-on"></i> Switch</a></li>
964
+ <li><a href="#tabs-2"><i class="fa-solid fa-arrow-up-wide-short"></i> Dim</a></li>
965
+ <li><a href="#tabs-3"><i class="fa-solid fa-temperature-quarter"></i> Tunable white</a></li>
966
+ <li><a href="#tabs-4"><i class="fa-solid fa-palette"></i> RGB/HSV</a></li>
967
+ <li><a href="#tabs-5"><i class="fa-solid fa-heart-circle-check"></i> Effects</a></li>
968
+ <li><a href="#tabs-6"><i class="fa-solid fa-code-merge"></i> Behaviour</a></li>
969
+ <li><a href="#tabs-7"><i class="fa-solid fa-house"></i> Home Assistant Export (beta)</a></li>
975
970
  </ul>
976
971
  <div id="tabs-1">
977
972
  <p>
@@ -1406,11 +1401,21 @@
1406
1401
  </div>
1407
1402
  <div class="form-row">
1408
1403
  <label style="width:170px" for="node-input-invertDayNight">
1409
- <i class="fa fa-shuffle"></i> Invert day/night values
1404
+ <i class="fa fa-shuffle"></i> Invert day/night value
1410
1405
  </label>
1411
1406
  <input type="checkbox" id="node-input-invertDayNight"
1412
1407
  style="display:inline-block; width:auto; vertical-align:top;" />
1413
1408
  </div>
1409
+ <div class="form-row">
1410
+ <label for="node-input-restoreDayMode" style="width:260px;">
1411
+ <i class="fa fa-circle"></i> Override night mode
1412
+ </label>
1413
+ <select id="node-input-restoreDayMode">
1414
+ <option value="no">No</option>
1415
+ <option value="setDayByFastSwitchLightSingle">Switch to DAY mode by rapid switching the ligth off then on. (This light only)</option>
1416
+ <option value="setDayByFastSwitchLightALL">Switch to DAY mode by rapid switching the ligth off then on (apply yo ALL light nodes)</option>
1417
+ </select>
1418
+ </div>
1414
1419
  </div>
1415
1420
  </div>
1416
1421
  <br/>
@@ -1521,8 +1526,9 @@ For controlling the "V" (brightness) of the HSV, please use the standard control
1521
1526
  | Switch on behaviour | It sets the behaviour of your lights when switched on. You can choose from differents behaviours.<br/>**Select color:** the light will be switched on with the color of your choice. To change color, just CLICK on the color selector (under the *Select color* control).<br/>**Select temperature and brightness:** the light will be switched on with the temperature (Kelvin) and brightness (0-100) of your choice.<br/>**None:** the light will retain its last status. In case you've enable the night lighting, after the night time ends, the lamp will resume the color/temperature/brightness state set at day time. |
1522
1527
  | Night Lighting | It allows to set a particular light color/brightness at nighttime. The options are the same as the daytime. You could select either a temperature/brightness or color. A cozy temperature of 2700 Kelvin, with a brightness of 10% or 20%, is a good choice for bathroom's night light.|
1523
1528
  | Day/Night | Select the group address used to set the day/night behaviour. The group address value is _true_ if daytime, _false_ if nighttime. |
1524
- | Invert day/night values | Invert the values of _Day/Night_ group address. Default value is **unchecked**. |
1529
+ | Invert day/night value | Invert the values of _Day/Night_ group address. Default value is **unchecked**. |
1525
1530
  | Read status at startup | Read the status at startup and emit the event to the KNX bus at startup/reconnection. (Default "no")|
1531
+ | Override night mode | You can override the night mode by manually switching the light as described here: **Switch to DAY mode by rapid switching the ligth off then on (This light only)** does what described and acts only on this light. **Switch to DAY mode by rapid switching the ligth off then on (apply yo ALL light nodes)** acts to ALL Light nodes, by setting the Day/Night group address to Day mode. |
1526
1532
  | Node Input/Output PINs | Hide or show the input/output PINs. Input/output PINS allow the node to accept msg input from the flow and send msg output to the flow. Input msg must follow the HUE API v.2 Standards. This is an example msg, that turns on the light: <code>msg.on = {"on":true}</code>. Please refer to the [official HUE Api page](https://developers.meethue.com/develop/hue-api-v2/api-reference/#resource_light__id__put) |
1527
1533
 
1528
1534
  ### Note
@@ -3,7 +3,7 @@
3
3
  /* eslint-disable max-len */
4
4
  /* eslint-disable no-lonely-if */
5
5
  const cloneDeep = require("lodash/cloneDeep");
6
- const dptlib = require("../KNXEngine/src/dptlib");
6
+ const dptlib = require('knxultimate').dptlib;
7
7
  const hueColorConverter = require("./utils/colorManipulators/hueColorConverter");
8
8
 
9
9
  module.exports = function (RED) {
@@ -62,7 +62,10 @@ module.exports = function (RED) {
62
62
  config.colorAtSwitchOnNightTime = config.colorAtSwitchOnNightTime.replace("geen", "green");
63
63
  config.dimSpeed = (config.dimSpeed === undefined || config.dimSpeed === '') ? 5000 : Number(config.dimSpeed);
64
64
  config.HSVDimSpeed = (config.HSVDimSpeed === undefined || config.HSVDimSpeed === '') ? 5000 : Number(config.HSVDimSpeed);
65
- config.invertDimTunableWhiteDirection = config.invertDimTunableWhiteDirection === undefined ? false : true;
65
+ config.invertDimTunableWhiteDirection = config.invertDimTunableWhiteDirection !== undefined;
66
+ config.restoreDayMode = config.restoreDayMode === undefined ? "no" : config.restoreDayMode; // no or setDayByFastSwitchLightSingle or setDayByFastSwitchLightALL
67
+ node.timerCheckForFastLightSwitch = null;
68
+ config.invertDayNight = config.invertDayNight === undefined ? false : config.invertDayNight;
66
69
  node.HSVObject = null; //{ h, s, v };// Store the current light calculated HSV
67
70
 
68
71
  // Transform HEX in RGB and stringified json in json oblects.
@@ -96,7 +99,6 @@ module.exports = function (RED) {
96
99
  RED.log.error(`knxUltimateHueLight: config.colorAtSwitchOnDayTime = JSON.parse(config.colorAtSwitchOnNightTime): ${error.message} : ${error.stack || ""} `);
97
100
  config.colorAtSwitchOnNightTime = "";
98
101
  }
99
-
100
102
  }
101
103
 
102
104
  // Used to call the status update from the config node.
@@ -134,6 +136,42 @@ module.exports = function (RED) {
134
136
  switch (msg.knx.destination) {
135
137
  case config.GALightSwitch:
136
138
  msg.payload = dptlib.fromBuffer(msg.knx.rawValue, dptlib.resolve(config.dptLightSwitch));
139
+
140
+ // 15/05/2024 Supergiovane: check the Override to Day option
141
+ // config.restoreDayMode can be: no or setDayByFastSwitchLightSingle or setDayByFastSwitchLightALL
142
+ // ----------------------------------------------------------
143
+ if (config.restoreDayMode === "setDayByFastSwitchLightSingle" || config.restoreDayMode === "setDayByFastSwitchLightALL") {
144
+ if (node.DayTime === false) {
145
+ if (msg.payload === true) {
146
+ if (node.timerCheckForFastLightSwitch === null) {
147
+ node.timerCheckForFastLightSwitch = setTimeout(() => {
148
+ node.DayTime = false;
149
+ RED.log.debug("knxUltimateHueLight: node.timerCheckForFastLightSwitch: set daytime to false after node.timerCheckForFastLightSwitch elapsed");
150
+ node.timerCheckForFastLightSwitch = null;
151
+ }, 10000); // 10 seconds
152
+ } else {
153
+ if (config.restoreDayMode === "setDayByFastSwitchLightALL") {
154
+ // Turn off the Day/Night group address
155
+ if (config.GADaylightSensor !== undefined && config.GADaylightSensor !== "") {
156
+ if (node.timerCheckForFastLightSwitch !== null) { clearTimeout(node.timerCheckForFastLightSwitch); node.timerCheckForFastLightSwitch = null; }
157
+ RED.log.debug(`knxUltimateHueLight: node.timerCheckForFastLightSwitch: set daytime the group address ${config.GADaylightSensor}`);
158
+ node.server.writeQueueAdd({
159
+ grpaddr: config.GADaylightSensor,
160
+ payload: config.invertDayNight === false,
161
+ dpt: config.dptDaylightSensor,
162
+ outputtype: "write",
163
+ nodecallerid: node.id,
164
+ });
165
+ }
166
+ }
167
+ node.DayTime = true;
168
+ RED.log.debug("knxUltimateHueLight: node.timerCheckForFastLightSwitch: set daytime to true");
169
+ }
170
+ }
171
+ }
172
+ }
173
+ // ----------------------------------------------------------
174
+
137
175
  if (msg.payload === true) {
138
176
  // From HUE Api core concepts:
139
177
  // If you try and control multiple conflicting parameters at once e.g. {"color": {"xy": {"x":0.5,"y":0.5}}, "color_temperature": {"mirek": 250}}
@@ -309,7 +347,7 @@ module.exports = function (RED) {
309
347
  break;
310
348
  case config.GADaylightSensor:
311
349
  node.DayTime = Boolean(dptlib.fromBuffer(msg.knx.rawValue, dptlib.resolve(config.dptDaylightSensor)));
312
- if (config.invertDayNight !== undefined && config.invertDayNight === true) node.DayTime = !node.DayTime;
350
+ if (config.invertDayNight === true) node.DayTime = !node.DayTime;
313
351
  if (config.specifySwitchOnBrightness === "no") {
314
352
  // This retains the HUE device status while daytime, to be restored after nighttime elapsed. https://github.com/Supergiovane/node-red-contrib-knx-ultimate/issues/298
315
353
  if (node.DayTime === false) {
@@ -918,7 +956,6 @@ module.exports = function (RED) {
918
956
  // !!!! >>> For all others properties like for example color and tunable white, i must get the data from one of the child lights.
919
957
 
920
958
  //(async () => {
921
- // Check and set canContinue true or false ------------------------------------------------------------
922
959
  try {
923
960
  if (node.currentHUEDevice === undefined || node.serverHue === null || node.serverHue === undefined) {
924
961
  node.setNodeStatusHue({
@@ -1405,6 +1442,6 @@ module.exports = function (RED) {
1405
1442
  }
1406
1443
  done();
1407
1444
  });
1408
- };
1445
+ }
1409
1446
  RED.nodes.registerType("knxUltimateHueLight", knxUltimateHueLight);
1410
1447
  };
@@ -1,5 +1,7 @@
1
1
  <script type="text/javascript" src="resources/node-red-contrib-knx-ultimate/11f26b4500.js"></script>
2
2
 
3
+ <script type="text/javascript" src="resources/node-red-contrib-knx-ultimate/htmlUtils.js"></script>
4
+
3
5
  <script type="text/javascript">
4
6
  RED.nodes.registerType('knxUltimateHueLightSensor', {
5
7
  category: "KNX Ultimate",
@@ -56,16 +58,7 @@
56
58
  } catch (error) { }
57
59
  });
58
60
 
59
- // 31/03/2020 Search Helper
60
- function fullSearch(sourceText, searchString) {
61
- // This searches for all words in a string
62
- var aSearchWords = searchString.toLowerCase().split(" ");
63
- var i = 0;
64
- for (let index = 0; index < aSearchWords.length; index++) {
65
- if (sourceText.toLowerCase().indexOf(aSearchWords[index]) > -1) i += 1;
66
- }
67
- return i == aSearchWords.length;
68
- }
61
+
69
62
 
70
63
  // DPT
71
64
  // ########################
@@ -82,13 +75,13 @@
82
75
 
83
76
  // Autocomplete suggestion with ETS csv File
84
77
  $("#node-input-GAlightsensor").autocomplete({
85
- minLength: 1,
78
+ minLength: 0,
86
79
  source: function (request, response) {
87
80
  //$.getJSON("csv", request, function( data, status, xhr ) {
88
81
  $.getJSON("knxUltimatecsv?nodeID=" + oNodeServer.id, (data) => {
89
82
  response($.map(data, function (value, key) {
90
83
  var sSearch = (value.ga + " (" + value.devicename + ") DPT" + value.dpt);
91
- if (fullSearch(sSearch, request.term + " 9.004")) {
84
+ if (htmlUtilsfullCSVSearch(sSearch, request.term + " 9.004")) {
92
85
  return {
93
86
  label: value.ga + " # " + value.devicename + " # " + value.dpt, // Label for Display
94
87
  value: value.ga // Value
@@ -110,6 +103,8 @@
110
103
  // Select the option value
111
104
  $("#node-input-dptlightsensor").val(optVal);
112
105
  }
106
+ }).focus(function () {
107
+ $(this).autocomplete('search', $(this).val() + 'exactmatch');
113
108
  });
114
109
  // ########################
115
110
 
@@ -118,13 +113,13 @@
118
113
 
119
114
  // Autocomplete suggestion with HUE
120
115
  $("#node-input-name").autocomplete({
121
- minLength: 1,
116
+ minLength: 0,
122
117
  source: function (request, response) {
123
118
  $.getJSON("KNXUltimateGetResourcesHUE?rtype=light_level&serverId=" + oNodeServerHue.id, (data) => {
124
119
  response($.map(data.devices, function (value, key) {
125
120
  //alert(JSON.stringify(value) + " "+ key)
126
121
  var sSearch = (value.name);
127
- if (fullSearch(sSearch, request.term)) {
122
+ if (htmlUtilsfullCSVSearch(sSearch, request.term)) {
128
123
  return {
129
124
  hueDevice: value.id, // Label for Display
130
125
  value: value.name // Value
@@ -138,6 +133,8 @@
138
133
  // Sets the fields
139
134
  $('#node-input-hueDevice').val(ui.item.hueDevice);
140
135
  }
136
+ }).focus(function () {
137
+ $(this).autocomplete('search', $(this).val() + 'exactmatch');
141
138
  });
142
139
 
143
140