@iobroker/adapter-react-v5 6.1.9 → 7.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.
Files changed (210) hide show
  1. package/Components/404.js +13 -13
  2. package/Components/FileBrowser.js +24 -19
  3. package/Components/FileViewer.js +14 -5
  4. package/Components/Loader.js +223 -223
  5. package/Components/Loaders/PT.css +108 -108
  6. package/Components/Loaders/PT.js +103 -103
  7. package/Components/Loaders/Vendor.css +13 -13
  8. package/Components/Loaders/Vendor.js +7 -7
  9. package/Components/ObjectBrowser.d.ts +2 -0
  10. package/Components/ObjectBrowser.js +214 -115
  11. package/Components/UploadImage.js +305 -305
  12. package/Components/loader.css +221 -221
  13. package/Components/types.d.ts +82 -82
  14. package/GenericApp.js +49 -49
  15. package/LICENSE +22 -22
  16. package/Prompt.js +7 -7
  17. package/README.md +1004 -1008
  18. package/Theme.js +8 -7
  19. package/assets/devices/Alarm Systems.svg +18 -18
  20. package/assets/devices/Amplifier.svg +21 -21
  21. package/assets/devices/Awnings.svg +4 -4
  22. package/assets/devices/Battery Status.svg +4 -4
  23. package/assets/devices/Ceiling Spotlights.svg +15 -15
  24. package/assets/devices/Chandelier.svg +6 -6
  25. package/assets/devices/Climate.svg +11 -11
  26. package/assets/devices/Coffee Makers.svg +5 -5
  27. package/assets/devices/Cold Water.svg +31 -31
  28. package/assets/devices/Computer.svg +21 -21
  29. package/assets/devices/Consumption.svg +7 -7
  30. package/assets/devices/Curtains.svg +43 -43
  31. package/assets/devices/Dishwashers.svg +11 -11
  32. package/assets/devices/Doors.svg +5 -5
  33. package/assets/devices/Doorstep.svg +35 -35
  34. package/assets/devices/Dryer.svg +13 -13
  35. package/assets/devices/Fan.svg +20 -20
  36. package/assets/devices/Floor Lamps.svg +4 -4
  37. package/assets/devices/Garage Doors.svg +9 -9
  38. package/assets/devices/Gates.svg +32 -32
  39. package/assets/devices/Hairdryer.svg +23 -23
  40. package/assets/devices/Handle.svg +6 -6
  41. package/assets/devices/Hanging Lamps.svg +8 -8
  42. package/assets/devices/Heater.svg +44 -44
  43. package/assets/devices/Hoods.svg +11 -11
  44. package/assets/devices/Hot Water.svg +9 -9
  45. package/assets/devices/Humidity.svg +41 -41
  46. package/assets/devices/Iron.svg +4 -4
  47. package/assets/devices/Irrigation.svg +22 -22
  48. package/assets/devices/Led Strip.svg +30 -30
  49. package/assets/devices/Light.svg +29 -29
  50. package/assets/devices/Lightings.svg +46 -46
  51. package/assets/devices/Lock.svg +19 -19
  52. package/assets/devices/Louvre.svg +6 -6
  53. package/assets/devices/Mowing Machine.svg +8 -8
  54. package/assets/devices/Music.svg +12 -12
  55. package/assets/devices/Outdoor Blinds.svg +6 -6
  56. package/assets/devices/People.svg +19 -19
  57. package/assets/devices/Pool.svg +7 -7
  58. package/assets/devices/Power Consumption.svg +12 -12
  59. package/assets/devices/Printer.svg +9 -9
  60. package/assets/devices/Pump.svg +9 -9
  61. package/assets/devices/Receiver.svg +18 -18
  62. package/assets/devices/Sconces.svg +9 -9
  63. package/assets/devices/Security.svg +34 -34
  64. package/assets/devices/Shading.svg +4 -4
  65. package/assets/devices/Shutters.svg +10 -10
  66. package/assets/devices/SmokeDetector.svg +12 -12
  67. package/assets/devices/Sockets.svg +13 -13
  68. package/assets/devices/Speaker.svg +35 -35
  69. package/assets/devices/Stove.svg +11 -11
  70. package/assets/devices/Table Lamps.svg +11 -11
  71. package/assets/devices/Temperature Sensors.svg +28 -28
  72. package/assets/devices/Tv.svg +7 -7
  73. package/assets/devices/Vacuum Cleaner.svg +15 -15
  74. package/assets/devices/Ventilation.svg +12 -12
  75. package/assets/devices/Washing Machines.svg +15 -15
  76. package/assets/devices/Water Consumption.svg +5 -5
  77. package/assets/devices/Water Heater.svg +8 -8
  78. package/assets/devices/Water.svg +40 -40
  79. package/assets/devices/Weather.svg +28 -28
  80. package/assets/devices/Window.svg +7 -7
  81. package/assets/lamp_ceiling.svg +8 -8
  82. package/assets/lamp_table.svg +7 -7
  83. package/assets/no_icon.svg +9 -9
  84. package/assets/rooms/Anteroom.svg +52 -52
  85. package/assets/rooms/Attic.svg +21 -21
  86. package/assets/rooms/Balcony.svg +12 -12
  87. package/assets/rooms/Barn.svg +5 -5
  88. package/assets/rooms/Basement.svg +4 -4
  89. package/assets/rooms/Bathroom.svg +38 -38
  90. package/assets/rooms/Bedroom.svg +5 -5
  91. package/assets/rooms/Boiler Room.svg +12 -12
  92. package/assets/rooms/Carport.svg +17 -17
  93. package/assets/rooms/Cellar.svg +89 -89
  94. package/assets/rooms/Chamber.svg +9 -9
  95. package/assets/rooms/Corridor.svg +52 -52
  96. package/assets/rooms/Dining Area.svg +37 -37
  97. package/assets/rooms/Dining Room.svg +37 -37
  98. package/assets/rooms/Dining.svg +37 -37
  99. package/assets/rooms/Dressing Room.svg +4 -4
  100. package/assets/rooms/Driveway.svg +14 -14
  101. package/assets/rooms/Entrance.svg +44 -44
  102. package/assets/rooms/Equipment Room.svg +14 -14
  103. package/assets/rooms/Front Yard.svg +64 -64
  104. package/assets/rooms/Gallery.svg +13 -13
  105. package/assets/rooms/Garage.svg +20 -20
  106. package/assets/rooms/Garden.svg +12 -12
  107. package/assets/rooms/Ground Floor.svg +95 -95
  108. package/assets/rooms/Guest Bathroom.svg +32 -32
  109. package/assets/rooms/Guest Room.svg +5 -5
  110. package/assets/rooms/Gym.svg +4 -4
  111. package/assets/rooms/Hall.svg +19 -19
  112. package/assets/rooms/Home Theater.svg +7 -7
  113. package/assets/rooms/Kitchen.svg +17 -17
  114. package/assets/rooms/Laundry Room.svg +11 -11
  115. package/assets/rooms/Living Area.svg +10 -10
  116. package/assets/rooms/Living Room.svg +10 -10
  117. package/assets/rooms/Locker Room.svg +16 -16
  118. package/assets/rooms/Nursery.svg +4 -4
  119. package/assets/rooms/Office.svg +8 -8
  120. package/assets/rooms/Outdoors.svg +7 -7
  121. package/assets/rooms/Playroom.svg +5 -5
  122. package/assets/rooms/Pool.svg +7 -7
  123. package/assets/rooms/Rear Wall.svg +30 -30
  124. package/assets/rooms/Second Floor.svg +95 -95
  125. package/assets/rooms/Shed.svg +16 -16
  126. package/assets/rooms/Sleeping Area.svg +22 -22
  127. package/assets/rooms/Stairway.svg +4 -4
  128. package/assets/rooms/Stairwell.svg +15 -15
  129. package/assets/rooms/Storeroom.svg +4 -4
  130. package/assets/rooms/Summer House.svg +27 -27
  131. package/assets/rooms/Swimming Pool.svg +21 -21
  132. package/assets/rooms/Terrace.svg +6 -6
  133. package/assets/rooms/Toilet.svg +10 -10
  134. package/assets/rooms/Upstairs.svg +5 -5
  135. package/assets/rooms/Wardrobe.svg +60 -60
  136. package/assets/rooms/Washroom.svg +19 -19
  137. package/assets/rooms/Wc.svg +10 -10
  138. package/assets/rooms/Windscreen.svg +60 -60
  139. package/assets/rooms/Workshop.svg +22 -22
  140. package/assets/rooms/Workspace.svg +8 -8
  141. package/craco-module-federation.js +71 -71
  142. package/icons/IconFx.js +1 -1
  143. package/icons/IconLogout.js +1 -1
  144. package/index.css +54 -54
  145. package/modulefederation.admin.config.js +31 -31
  146. package/package.json +9 -9
  147. package/src/AdminConnection.tsx +3 -3
  148. package/src/Components/404.tsx +121 -121
  149. package/src/Components/ColorPicker.tsx +315 -315
  150. package/src/Components/ComplexCron.tsx +507 -507
  151. package/src/Components/CopyToClipboard.tsx +165 -165
  152. package/src/Components/CustomModal.tsx +163 -163
  153. package/src/Components/FileBrowser.tsx +2414 -2394
  154. package/src/Components/FileViewer.tsx +393 -384
  155. package/src/Components/Icon.tsx +210 -210
  156. package/src/Components/IconPicker.tsx +149 -149
  157. package/src/Components/IconSelector.tsx +2202 -2202
  158. package/src/Components/Image.tsx +176 -176
  159. package/src/Components/Loader.tsx +304 -304
  160. package/src/Components/Logo.tsx +166 -166
  161. package/src/Components/MDUtils.tsx +100 -100
  162. package/src/Components/ObjectBrowser.tsx +8032 -7915
  163. package/src/Components/Router.tsx +90 -90
  164. package/src/Components/SaveCloseButtons.tsx +113 -113
  165. package/src/Components/Schedule.tsx +1724 -1724
  166. package/src/Components/SelectWithIcon.tsx +197 -197
  167. package/src/Components/TabContainer.tsx +55 -55
  168. package/src/Components/TabContent.tsx +37 -37
  169. package/src/Components/TabHeader.tsx +19 -19
  170. package/src/Components/TableResize.tsx +259 -259
  171. package/src/Components/TextWithIcon.tsx +148 -148
  172. package/src/Components/ToggleThemeMenu.tsx +34 -34
  173. package/src/Components/TreeTable.tsx +919 -919
  174. package/src/Components/UploadImage.tsx +599 -599
  175. package/src/Components/Utils.tsx +1794 -1794
  176. package/src/Components/loader.css +221 -221
  177. package/src/Components/withWidth.tsx +21 -21
  178. package/src/Connection.tsx +7 -7
  179. package/src/Dialogs/ComplexCron.tsx +129 -129
  180. package/src/Dialogs/Confirm.tsx +162 -162
  181. package/src/Dialogs/Cron.tsx +182 -182
  182. package/src/Dialogs/Error.tsx +72 -72
  183. package/src/Dialogs/Message.tsx +71 -71
  184. package/src/Dialogs/SelectFile.tsx +270 -270
  185. package/src/Dialogs/SelectID.tsx +298 -298
  186. package/src/Dialogs/SimpleCron.tsx +100 -100
  187. package/src/Dialogs/TextInput.tsx +107 -107
  188. package/src/GenericApp.tsx +976 -976
  189. package/src/LegacyConnection.tsx +3589 -3589
  190. package/src/Prompt.tsx +20 -20
  191. package/src/Theme.tsx +479 -479
  192. package/src/icons/IconAdapter.tsx +20 -20
  193. package/src/icons/IconAlias.tsx +20 -20
  194. package/src/icons/IconChannel.tsx +21 -21
  195. package/src/icons/IconClearFilter.tsx +22 -22
  196. package/src/icons/IconClosed.tsx +17 -17
  197. package/src/icons/IconCopy.tsx +16 -16
  198. package/src/icons/IconDevice.tsx +27 -27
  199. package/src/icons/IconDocument.tsx +17 -17
  200. package/src/icons/IconDocumentReadOnly.tsx +18 -18
  201. package/src/icons/IconExpert.tsx +18 -18
  202. package/src/icons/IconFx.tsx +36 -36
  203. package/src/icons/IconInstance.tsx +20 -20
  204. package/src/icons/IconLogout.tsx +30 -30
  205. package/src/icons/IconNoIcon.tsx +19 -19
  206. package/src/icons/IconOpen.tsx +17 -17
  207. package/src/icons/IconProps.tsx +15 -15
  208. package/src/icons/IconState.tsx +17 -17
  209. package/src/index.css +54 -54
  210. package/types.d.ts +134 -134
package/README.md CHANGED
@@ -1,1334 +1,1330 @@
1
- # Help ReactJS classes for adapter config
2
- You can find demo on https://github.com/ioBroker/adapter-react-demo
3
-
4
- ## Getting started
5
- If you want to create the configuration page with ReactJS:
6
- 1. Create github repo for adapter.
7
- 2. execute `npx create-react-app src` . It will take a while.
8
- 3. `cd src`
9
- 4. Modify package.json file in src directory:
10
- - Change `name` from `src` to `ADAPTERNAME-admin` (Of course replace `ADAPTERNAME` with yours)
11
- - Add to devDependencies:
12
- ```
13
- "@iobroker/adapter-react": "^4.0.10",
14
- ```
15
- Versions can be higher.
16
- So your src/package.json should look like:
17
- ```
18
- {
19
- "name": "ADAPTERNAME-admin",
20
- "version": "0.1.0",
21
- "private": true,
22
- "dependencies": {
23
- "react": "^18.2.0",
24
- "react-dom": "^18.2.0",
25
- "react-icons": "^4.6.0",
26
- "react-scripts": "^5.0.1",
27
- "@iobroker/adapter-react-v5": "^3.2.7",
28
- "del": "^6.1.1",
29
- "gulp": "^4.0.2"
30
- },
31
- "scripts": {
32
- "start": "react-scripts start",
33
- "build": "react-scripts build",
34
- "test": "react-scripts test",
35
- "eject": "react-scripts eject"
36
- },
37
- "eslintConfig": {
38
- "extends": "react-app"
39
- },
40
- "homepage": ".",
41
- "browserslist": [
42
- ">0.2%",
43
- "not dead",
44
- "not ie <= 11",
45
- "not op_mini all"
46
- ]
47
- }
48
- ```
49
- 5. Call in `src`: `npm install`
50
- 6. Copy gulpfile.js into `src`: `cp node_modules/@iobroker/adapter-react/gulpfile.js gulpfile.js`
51
- 7. Start your dummy application `npm run start` for developing or build with `npm run build` and
52
- copy files in `build` directory to `www` or to `admin`. In the admin you must rename `index.html` to `index_m.html`.
53
- 8. You can do that with `gulp` tasks: `gulp build`, `gulp copy`, `gulp renameIndex` or `gulp renameTab`
54
-
55
- ## Development
56
- 1. Add `socket.io` to `public/index.html`.
57
- After
58
-
59
- ```
60
- <link rel="manifest" href="%PUBLIC_URL%/manifest.json" />
61
- ```
62
-
63
- insert
64
-
65
- ```
66
- <script>
67
- var script = document.createElement('script');
68
- window.registerSocketOnLoad = function (cb) {
69
- window.socketLoadedHandler = cb;
70
- };
71
- const parts = (window.location.search || '').replace(/^\?/, '').split('&');
72
- const query = {};
73
- parts.forEach(item => {
74
- const [name, val] = item.split('=');
75
- query[decodeURIComponent(name)] = val !== undefined ? decodeURIComponent(val) : true;
76
- });
77
- script.onload = function () { typeof window.socketLoadedHandler === 'function' && window.socketLoadedHandler(); };
78
- script.src = window.location.port === '3000' ? window.location.protocol + '//' + (query.host || window.location.hostname) + ':' + (query.port || 8081) + '/lib/js/socket.io.js' : '%PUBLIC_URL%/../../lib/js/socket.io.js';
79
-
80
- document.head.appendChild(script);
81
- </script>
82
- ```
83
-
84
- 3. Add to App.js constructor initialization for I18n:
85
- ```
86
- class App extends GenericApp {
87
- constructor(props) {
88
- const extendedProps = {...props};
89
- extendedProps.encryptedFields = ['pass']; // this parameter will be encrypted and decrypted automatically
90
- extendedProps.translations = {
91
- 'en': require('./i18n/en'),
92
- 'de': require('./i18n/de'),
93
- 'ru': require('./i18n/ru'),
94
- 'pt': require('./i18n/pt'),
95
- 'nl': require('./i18n/nl'),
96
- 'fr': require('./i18n/fr'),
97
- 'it': require('./i18n/it'),
98
- 'es': require('./i18n/es'),
99
- 'pl': require('./i18n/pl'),
100
- 'uk': require('./i18n/uk'),
101
- 'zh-cn': require('./i18n/zh-cn'),
102
- };
103
- // get actual admin port
104
- extendedProps.socket = {port: parseInt(window.location.port, 10)};
105
-
106
- // Only if close, save buttons are not required at the bottom (e.g. if admin tab)
107
- // extendedProps.bottomButtons = false;
108
-
109
- // only for debug purposes
110
- if (extendedProps.socket.port === 3000) {
111
- extendedProps.socket.port = 8081;
112
- }
113
-
114
- // allow to manage GenericApp the sentry initialisation or do not set the sentryDSN if no sentry available
115
- extendedProps.sentryDSN = 'https://yyy@sentry.iobroker.net/xx';
116
-
117
- super(extendedProps);
118
- }
119
- ...
120
- }
121
- ```
122
-
123
- 4. Replace `index.js` with the following code to support themes:
124
- ```
125
- import React from 'react';
126
- import ReactDOM from 'react-dom';
127
- import { MuiThemeProvider} from '@material-ui/core/styles';
128
- import * as serviceWorker from './serviceWorker';
129
-
130
- import './index.css';
131
- import App from './App';
132
- import { version } from '../package.json';
133
-
134
- import theme from '@iobroker/adapter-react/Theme';
135
-
136
- console.log('iobroker.scenes@' + version);
137
- let themeName = window.localStorage ? window.localStorage.getItem('App.theme') || 'light' : 'light';
138
-
139
- function build() {
140
- return ReactDOM.render(<MuiThemeProvider theme={ theme(themeName) }>
141
- <App onThemeChange={_theme => {
142
- themeName = _theme;
143
- build();
144
- }}/>
145
- </MuiThemeProvider>, document.getElementById('root'));
146
- }
147
-
148
- build();
149
-
150
- // If you want your app to work offline and load faster, you can change
151
- // unregister() to register() below. Note this comes with some pitfalls.
152
- // Learn more about service workers: http://bit.ly/CRA-PWA
153
- serviceWorker.unregister();
154
- ```
155
-
156
- 5. Add to App.js encoding and decoding of values:
157
- ```
158
- class App extend GenericApp {
159
- ...
160
- onPrepareLoad(settings) {
161
- settings.pass = this.decode(settings.pass);
162
- }
163
- onPrepareSave(settings) {
164
- settings.pass = this.encode(settings.pass);
165
- }
166
- }
167
- ```
168
-
169
- 6. The optional step is to validate the data to be saved:
170
- ```
171
- onPrepareSave(settings) {
172
- super.onPrepareSave(settings);
173
- if (DATA_INVALID) {
174
- return false; // configuration will not be saved
175
- } else {
176
- return true;
177
- }
178
- }
179
- ```
180
-
181
- ## Components
182
-
183
- ### Connection.tsx
184
- This is a non-react class to provide the communication for socket connection with the server.
185
-
186
- ### GenericApp.tsx
187
-
188
- ### i18n.ts
189
-
190
- ### Theme.tsx
191
-
192
- ### Dialogs
193
- Some dialogs are predefined and could be used out of the box.
194
-
195
- #### Confirm.tsx
196
- <!-- TODO: Provide screenshot here -->
197
-
198
- Usage:
199
- ```
200
- import React from 'react';
201
- import ConfirmDialog from '@iobroker/adapter-react/Dialogs/Confirm'
202
- import I18n from '@iobroker/adapter-react/i18n';
203
-
204
- class ExportImportDialog extends React.Component {
205
- constructor(props) {
206
- super(props);
207
-
208
- this.state = {
209
- confirmDialog: false,
210
- };
211
- }
212
-
213
- renderConfirmDialog() {
214
- if (!this.state.confirmDialog) {
215
- return null;
216
- }
217
- return <ConfirmDialog
218
- title={ I18n.t('Scene will be overwritten.') }
219
- text={ I18n.t('All data will be lost. Confirm?') }
220
- ok={ I18n.t('Yes') }
221
- cancel={ I18n.t('Cancel') }
222
- suppressQuestionMinutes={5}
223
- dialogName="myConfirmDialogThatCouldBeSuppressed"
224
- suppressText={I18n.t('Suppress question for next %s minutes', 5)}
225
- onClose={isYes => {
226
- this.setState({ confirmDialog: false} );
227
- }}
228
- />;
229
- }
230
- render() {
231
- return <div>
232
- <Button onClick={ () => this.setState({confirmDialog: true}) }>Click</Button>
233
- { this.renderConfirmDialog() }
234
- </div>
235
- }
236
- }
237
-
238
- export default ExportImportDialog;
239
- ```
240
-
241
- #### Error.tsx
242
- <!-- TODO: Provide screenshot here -->
243
-
244
- #### Message.tsx
245
- <!-- TODO: Provide screenshot here -->
246
- ```
247
- renderMessage() {
248
- if (this.state.showMessage) {
249
- return <Message
250
- text={this.state.showMessage}
251
- onClose={() => this.setState({showMessage: false})}
252
- />;
253
- } else {
254
- return null;
255
- }
256
- }
257
- ```
258
-
259
- #### SelectID.tsx
260
- ![Logo](img/selectID.png)
261
- ```
262
- import DialogSelectID from '@iobroker/adapter-react/Dialogs/SelectID';
263
-
264
- class MyComponent extends Component {
265
- constructor(props) {
266
- super(props);
267
- this.state = {
268
- showSelectId: false,
269
- };
270
- }
271
-
272
- renderSelectIdDialog() {
273
- if (this.state.showSelectId) {
274
- return <DialogSelectID
275
- key="tableSelect"
276
- imagePrefix="../.."
277
- dialogName={this.props.adapterName}
278
- themeType={this.props.themeType}
279
- socket={this.props.socket}
280
- statesOnly={true}
281
- selected={this.state.selectIdValue}
282
- onClose={() => this.setState({showSelectId: false})}
283
- onOk={(selected, name) => {
284
- this.setState({showSelectId: false, selectIdValue: selected});
285
- }}
286
- />;
287
- } else {
288
- return null;
289
- }
290
- }
291
- render() {
292
- return renderSelectIdDialog();
293
- }
294
- }
295
- ```
296
-
297
- #### Cron
298
- Include `"react-text-mask": "^5.4.3",` in package.json.
299
-
300
- <!-- TODO: Provide screenshot here -->
301
-
302
- ```
303
- function renderCron() {
304
- if (!showCron) {
305
- return null;
306
- } else {
307
- return <DialogCron
308
- key="dialogCron1"
309
- cron={this.state.cronValue || '* * * * *'}
310
- onClose={() => this.setState({ showCron: false })}
311
- onOk={cronValue => {
312
- this.setState({ cronValue })
313
- }}
314
- />;
315
- }
316
- }
317
- ```
318
-
319
- ### Components
320
-
321
- #### Utils.tsx
322
- ##### getObjectNameFromObj
323
- `getObjectNameFromObj(obj, settings, options, isDesc)`
324
-
325
- Get object name from a single object.
326
-
327
- Usage: `Utils.getObjectNameFromObj(this.objects[id], null, {language: I18n.getLanguage()})`
328
-
329
- ##### getObjectIcon
330
- `getObjectIcon(id, obj)`
331
-
332
- Get icon from the object.
333
-
334
- Usage:
335
- ```
336
- const icon = Utils.getObjectIcon(id, this.objects[id]);
337
- return (<img src={icon}/>);
338
- ```
339
-
340
- ##### isUseBright
341
- `isUseBright(color, defaultValue)`
342
-
343
- Usage: `
344
-
345
- #### Loader.tsx
346
- ![Logo](img/loader.png)
347
-
348
- ```
349
- render() {
350
- if (!this.state.loaded) {
351
- return <MuiThemeProvider theme={this.state.theme}>
352
- <Loader theme={this.state.themeType}/>
353
- </MuiThemeProvider>;
354
- }
355
- // render loaded data
356
- }
357
-
358
- ```
359
-
360
- #### Logo.tsx
361
- ![Logo](img/logo.png)
362
-
363
- ```
364
- render() {
365
- return <form className={this.props.classes.tab}>
366
- <Logo
367
- instance={this.props.instance}
368
- common={this.props.common}
369
- native={this.props.native}
370
- onError={text => this.setState({errorText: text})}
371
- onLoad={this.props.onLoad}
372
- />
373
- ...
374
- </form>;
375
- }
376
- ```
377
-
378
- #### Router.tsx
379
-
380
- #### ObjectBrowser.js
381
- It is better to use `Dialog/SelectID`, but if you want:
382
-
383
- ![Logo](img/objectBrowser.png)
384
-
385
- ```
386
- <ObjectBrowser
387
- foldersFirst={this.props.foldersFirst}
388
- imagePrefix={this.props.imagePrefix || this.props.prefix} // prefix is for back compatibility
389
- defaultFilters={this.filters}
390
- dialogName={this.dialogName}
391
- showExpertButton={this.props.showExpertButton !== undefined ? this.props.showExpertButton : true}
392
- style={{ width: '100%', height: '100%' }}
393
- columns={this.props.columns || ['name', 'type', 'role', 'room', 'func', 'val']}
394
- types={this.props.types || ['state']}
395
- t={I18n.t}
396
- lang={this.props.lang || I18n.getLanguage()}
397
- socket={this.props.socket}
398
- selected={this.state.selected}
399
- multiSelect={this.props.multiSelect}
400
- notEditable={this.props.notEditable === undefined ? true : this.props.notEditable}
401
- name={this.state.name}
402
- themeName={this.props.themeName}
403
- themeType={this.props.themeType}
404
- customFilter={this.props.customFilter}
405
- onFilterChanged={filterConfig => {
406
- this.filters = filterConfig;
407
- window.localStorage.setItem(this.dialogName, JSON.stringify(filterConfig));
408
- }}
409
- onSelect={(selected, name, isDouble) => {
410
- if (JSON.stringify(selected) !== JSON.stringify(this.state.selected)) {
411
- this.setState({selected, name}, () =>
412
- isDouble && this.handleOk());
413
- } else if (isDouble) {
414
- this.handleOk();
415
- }
416
- }}
417
- />
418
- ```
419
-
420
- #### TreeTable.ts
421
- ![Logo](img/tableTree.png)
422
-
423
- ```
424
- // STYLES
425
- const styles = theme => ({
426
- tableDiv: {
427
- width: '100%',
428
- overflow: 'hidden',
429
- height: 'calc(100% - 48px)',
430
- },
431
- });
432
- class MyComponent extends Component {
433
- constructor(props) {
434
- super(props);
435
-
436
- this.state = {
437
- data: [
438
- {
439
- id: 'UniqueID1' // required
440
- fieldIdInData: 'Name1',
441
- myType: 'number',
442
- },
443
- {
444
- id: 'UniqueID2' // required
445
- fieldIdInData: 'Name12',
446
- myType: 'string',
447
- },
448
- ],
449
- };
450
-
451
- this.columns = [
452
- {
453
- title: 'Name of field', // required, else it will be "field"
454
- field: 'fieldIdInData', // required
455
- editable: false, // or true [default - true]
456
- cellStyle: { // CSS style - // optional
457
- maxWidth: '12rem',
458
- overflow: 'hidden',
459
- wordBreak: 'break-word',
460
- },
461
- lookup: { // optional => edit will be automatically "SELECT"
462
- 'value1': 'text1',
463
- 'value2': 'text2',
464
- }
465
- },
466
- {
467
- title: 'Type', // required, else it will be "field"
468
- field: 'myType', // required
469
- editable: true, // or true [default - true]
470
- lookup: { // optional => edit will be automatically "SELECT"
471
- 'number': 'Number',
472
- 'string': 'String',
473
- 'boolean': 'Boolean',
474
- },
475
- type: 'number/string/color/oid/icon/boolean', // oid=ObjectID,icon=base64-icon
476
- editComponent: props =>
477
- <div>Prefix&#123; <br/>
478
- <textarea
479
- rows={4}
480
- style={{width: '100%', resize: 'vertical'}}
481
- value={props.value}
482
- onChange={e => props.onChange(e.target.value)}
483
- />
484
- Suffix
485
- </div>,
486
- },
487
- ];
488
- }
489
- // renderTable
490
- render() {
491
- return <div className={this.props.classes.tableDiv}>
492
- <TreeTable
493
- columns={this.columns}
494
- data={this.state.data}
495
- onUpdate={(newData, oldData) => {
496
- const data = JSON.parse(JSON.stringify(this.state.data));
497
-
498
- // Added new line
499
- if (newData === true) {
500
- // find unique ID
501
- let i = 1;
502
- let id = 'line_' + i;
503
-
504
- // eslint-disable-next-line
505
- while(this.state.data.find(item => item.id === id)) {
506
- i++;
507
- id = 'line_' + i;
508
- }
509
-
510
- data.push({
511
- id,
512
- name: I18n.t('New resource') + '_' + i,
513
- color: '',
514
- icon: '',
515
- unit: '',
516
- price: 0,
517
- });
518
- } else {
519
- // existing line was modifed
520
- const pos = this.state.data.indexOf(oldData);
521
- if (pos !== -1) {
522
- Object.keys(newData).forEach(attr => data[pos][attr] = newData[attr]);
523
- }
524
- }
525
-
526
- this.setState({data});
527
- }}
528
- onDelete={oldData => {
529
- console.log('Delete: ' + JSON.stringify(oldData));
530
- const pos = this.state.data.indexOf(oldData);
531
- if (pos !== -1) {
532
- const data = JSON.parse(JSON.stringify(this.state.data));
533
- data.splice(pos, 1);
534
- this.setState({data});
535
- }
536
- }}
537
- />
538
- </div>;
539
- }
540
- }
541
- ```
542
-
543
- #### Toast
544
- <!-- TODO: Provide screenshot here -->
545
-
546
- Toast is not a part of `adapter-react` but it is an example how to use toast in application:
547
-
548
- ```
549
- import Snackbar from '@material-ui/core/Snackbar';
550
-
551
- class MyComponent {
552
- constructor(props) {
553
- super(props);
554
- this.state = {
555
- // ....
556
- toast: '',
557
- };
558
- }
559
- // ...
560
- renderToast() {
561
- if (!this.state.toast) {
562
- return null;
563
- }
564
- return <Snackbar
565
- anchorOrigin={{
566
- vertical: 'bottom',
567
- horizontal: 'left',
568
- }}
569
- open={true}
570
- autoHideDuration={6000}
571
- onClose={() => this.setState({toast: ''})}
572
- ContentProps={{'aria-describedby': 'message-id'}}
573
- message={<span id="message-id">{this.state.toast}</span>}
574
- action={[
575
- <IconButton
576
- key="close"
577
- aria-label="Close"
578
- color="inherit"
579
- className={this.props.classes.close}
580
- onClick={() => this.setState({toast: ''})}
581
- >
582
- <IconClose />
583
- </IconButton>,
584
- ]}
585
- />;
586
- }
587
- render() {
588
- return <div>
589
- {this.renderToast()}
590
- </div>;
591
- }
592
- }
593
- ```
594
-
595
- ## List of adapters that use adapter-react
596
- - Admin
597
- - Backitup
598
- - iot
599
- - echarts
600
- - text2command
601
- - scenes
602
- - javascript
603
- - devices
604
- - eventlist
605
- - cameras
606
- - web
607
- - vis-2
608
- - vis-2-widgets-xxx
609
- - fullcalendar
610
- - openweathermap
611
-
612
- ## Usability
613
- In dialogs, the OK button is first (on the left) and the cancel button is last (on the right)
614
-
615
- ## Used icons
616
- This project uses icons from [Flaticon](https://www.flaticon.com/).
617
-
618
- ioBroker GmbH has a valid license for all the used icons.
619
- The icons may not be reused in other projects without the proper flaticon license or flaticon subscription.
620
-
621
- ## Migration from adapter-react to adapter-react-v5
622
- ### In src/package.json => dependencies
623
- - `"@iobroker/adapter-react": "^2.0.22",` => `"@iobroker/adapter-react-v5": "^3.1.34",`
624
- - `"@material-ui/core": "^4.12.3",` => `"@mui/material": "^5.10.9",`
625
- - `"@material-ui/icons": "^4.11.2",` => `"@mui/icons-material": "^5.10.9",`
626
- - Add `"@mui/styles": "^5.10.9",`
627
- - Add `"babel-eslint": "^10.1.0",`
628
-
629
- ### In Source files
630
- - All `@iobroker/adapter-react/...` => `@iobroker/adapter-react-v5/...`
631
- - All `@material-ui/icons/...` => `@mui/icons-material/...`
632
- - Change `import { withStyles } from '@material-ui/core/styles';` => `import { withStyles } from '@mui/styles';`
633
- - Change `import { makeStyles } from '@mui/material/styles';` => `import { makeStyles } from '@mui/styles';`
634
- - Change `import withWidth from '@material-ui/core/withWidth';` => `import { withWidth } from '@iobroker/adapter-react-v5';`
635
- - All `@material-ui/core...` => `@mui/material...`
636
- - Change `import { MuiThemeProvider } from '@material-ui/core/styles';` => `import { ThemeProvider, StyledEngineProvider } from '@mui/material/styles';`
637
- - Change all `<MuiThemeProvider theme={this.state.theme}>` to `<StyledEngineProvider injectFirst><ThemeProvider theme={this.state.theme}>`
638
- - Rename in styles `theme.palette.type` => `theme.palette.mode`
639
- - Add to all `TextField`, `Select`, `FormControl` the property `variant="standard"`
640
- - Add to all `Button` that do not have `color` property: `color="grey"`
641
- - Replace by `TextField` the `readOnly` attribute (if exists) with `InputProps={{readOnly: true}}`
642
- - Remove px by all `theme.spacing`: `calc(100% - ${theme.spacing(4)}px)` => `calc(100% - ${theme.spacing(4)})`
643
- - Replace `this.selectTab(e.target.parentNode.dataset.name, index)` => `this.selectTab(e.target.dataset.name, index)`
644
-
645
- If you still have questions, try to find an answer [here](https://mui.com/guides/migration-v4/).
646
-
647
- ## Migration from adapter-react-v5@3.x to adapter-react-v5@4.x
648
- - Look for getObjectView socket requests and replace `socket.getObjectView('startKey', 'endKey', 'instance')` to `socket.getObjectViewSystem('instance', 'startKey', 'endKey')`
649
- - Look for calls of custom like
650
- ```
651
- this.props.socket._socket.emit('getObjectView', 'system', 'custom', {startKey: '', endKey:'\u9999'}, (err, objs) => {
652
- (objs?.rows || [])
653
- .forEach(item => console.log(item.id, item.value));
654
- });
655
- ```
656
- to
657
- ```
658
- socket.getObjectViewCustom('custom', 'state', 'startKey', 'endKey')
659
- .then(objects => {
660
- Object.keys(objects).forEach(obj => console.log(obj._id));
661
- });
662
- ```
663
- - Replace all `socket.log.error('text')` to `socket.log('text', 'error')`
664
- - Add to App.js `import { AdminConnection } from '@iobroker/adapter-react-v5';` and `super(props, { Connection: AdminConnection });` if run in admin
665
-
666
- ## Migration from adapter-react-v5@4.x to adapter-react-v5@5.x
667
- - `Theme` is renamed to IobTheme. It is an object with classes inside. `Theme` is still inside and it same as mui `createTheme`.
668
- - adapter-react-v5 has all types exported. So you can use `import { type IobTheme, Theme } from '@iobroker/adapter-react-v5';` and `const theme: IobTheme = Theme('light');`
669
- - Json-Config is now an external package and must be included as dependency separately.
670
- - Use type `Translate` for `t(word: string, ...args: any[]) => string`
671
- - All components for admin JsonConfig must be changed:
672
- Before `adapter-react-v5@5.x`:
673
-
674
- ```
675
- import { ConfigGeneric, I18n } from '@iobroker/adapter-react-v5';
676
- class JsonComponent extends ConfigGeneric {
677
- ...
678
- }
679
- ```
680
-
681
- With `adapter-react-v5@5.x`:
682
-
683
- ```
684
- import { I18n } from '@iobroker/adapter-react-v5';
685
- import { ConfigGeneric } from '@iobroker/json-config';
686
- class JsonComponent extends ConfigGeneric {
687
- ...
688
- }
689
- ```
690
- ## Migration from v5 to v6
691
- The main change is that the `withStyles` was removed. So you have to replace all `withStyles` with `sx` or `style` properties.
692
-
693
- You can read more about sx [here](https://mui.com/system/getting-started/the-sx-prop/).
694
- - Remove at start of the file `import { withStyles } from '@mui/styles';`
695
- - Replace at the very end of the file `export default withStyles(styles)(MyComponent);` with `export default MyComponent;`
696
- - Modify `const styles`:
697
- Before:
698
- ```
699
- const styles: Record<string, any> = (theme: IobTheme) => ({
700
- dialog: {
701
- height: `calc(100% - ${theme.mixins.toolbar.minHeight}px)`,
702
- padding: theme.spacing(1),
703
- margin: theme.spacing(2),
704
- gap: 5,
705
- borderRadius: 5,
706
- marginLeft: 10, // marginTop, marginRight, marginBottom
707
- paddingLeft: 10, // paddingTop, paddingRight, paddingBottom
708
- },
709
- ...
710
- });
711
- ```
712
-
713
- After:
714
- ```
715
- const styles: Record<string, any> = {
716
- dialog: (theme: IobTheme) => ({
717
- height: `calc(100% - ${theme => theme.mixins.toolbar.minHeight}px)`,
718
- p: 1, // or 8px, padding is OK too
719
- m: '16px', // or 2, margin is OK too
720
- gap: '5px',
721
- borderRadius: '5px',
722
- ml: '10px', // mt, mr, mb, but marginLeft, marginRight, marginBottom is OK too
723
- pl: '10px', // pt, pr, pb, but paddingTop, paddingRight, paddingBottom is OK too
724
- }),
725
- };
726
- ```
727
-
728
- - Modify `className`:
729
- Before: `<div className={this.props.classes.box}>`
730
-
731
- After: `<Box sx={styles.box}>`
732
-
733
- Before: `<span className={Utils.clsx(this.props.classes.box1, condition && this.props.classes.box2)}>`
734
-
735
- After: `<Box component="span" sx={Utils.getStyle(this.props.theme, this.props.classes.box1, condition && this.props.classes.box2)}>`
736
- Or if no one style is a function: `<Box component="div" sx={{ ...this.props.classes.box1, ...(condition ? this.props.classes.box2 : undefined) }}>`
737
-
738
- Do not use `sx` if the style is not dynamic (not a function). Use `style` instead.
739
-
740
- Be aware, that all paddings and margins are now in `theme.spacing(1)` format.
741
- So you have to replace all `padding: 8` with `padding: 1` or with `padding: '8px'`.
742
-
743
- The best practice is to replace `padding` with `p` and `margin` with `m`, so you will see immediately that it is a padding or margin for `sx` property.
744
-
745
- - Modify `classes`:
746
- Before: `<Dialog classes={{ scrollPaper: this.props.classes.dialog, paper: this.props.classes.paper }}>`
747
-
748
- After: `<Dialog sx={{ '&.MuiDialog-scrollPaper': styles.dialog, '& .MuiDialog-paper': styles.paper }}>`
749
-
750
- Before: `<Dialog classes={{ scrollPaper: this.props.classes.dialog, paper: this.props.classes.paper }}>`
751
-
752
- After: `<Dialog sx={{ '&.MuiDialog-scrollPaper': styles.dialog, '& .MuiDialog-paper': styles.paper }}>`
753
-
754
- Before: `<ListItem classes={{ root: styles.listItem }} >`
755
-
756
- After: `<ListItem sx={{ '&.MuiListItem-root': styles.listItem }} >`
757
-
758
- Before: `<Typography component="h2" variant="h6" classes={{ root: styles.typography }}>`
759
-
760
- After: `<Typography component="h2" variant="h6" sx={{ '&.MuiTypography-root': styles.typography }}>`
761
-
762
- Before: `<Badge classes={{ 'badge': styles.expertBadge }}>`
763
-
764
- After: `<Badge sx={{ '& .MuiBadge-badge': styles.expertBadge }}>`
765
-
766
- Before: `<Tab classes={{ selected: styles.selected }} />`
767
-
768
- After: `<Tab sx={{ '&.Mui-selected': styles.selected }} />`
769
-
770
- Before: `<Tooltip title={this.props.t('ra_Refresh tree')} classes={{ popper: styles.tooltip }}>`
771
-
772
- After: `<Tooltip title={this.props.t('ra_Refresh tree')} componentsProps={{ popper: { sx: { pointerEvents: 'none' } } }}>`
773
- Or: `<Tooltip title={this.props.t('ra_Refresh tree')} componentsProps={{ popper: { sx: styles.tooltip } }}>`
774
-
775
- Before. `<AccordionSummary classes={{ root: styles.rootStyle, content: styles.content }}>`
776
-
777
- After. `<AccordionSummary sx={{ '&.MuiAccordionSummary-root': styles.rootStyle, '& .MuiAccordionSummary-content': styles.content }}>`
778
-
779
- Before. `<Drawer classes={{ paper: styles.paperStyle }}>`
780
-
781
- After. `<Drawer sx={{ '& .MuiDrawer-paper': styles.paperStyle }}>`
782
-
783
- <!--
784
- Placeholder for the next version (at the beginning of the line):
785
- ### **WORK IN PROGRESS**
786
- -->
787
-
1
+ # Help ReactJS classes for adapter config
2
+ You can find demo on https://github.com/ioBroker/adapter-react-demo
3
+
4
+ ## Getting started
5
+ If you want to create the configuration page with ReactJS:
6
+ 1. Create github repo for adapter.
7
+ 2. execute `npx create-react-app src` . It will take a while.
8
+ 3. `cd src`
9
+ 4. Modify package.json file in src directory:
10
+ - Change `name` from `src` to `ADAPTERNAME-admin` (Of course replace `ADAPTERNAME` with yours)
11
+ - Add to devDependencies:
12
+ ```
13
+ "@iobroker/adapter-react": "^4.0.10",
14
+ ```
15
+ Versions can be higher.
16
+ So your src/package.json should look like:
17
+ ```
18
+ {
19
+ "name": "ADAPTERNAME-admin",
20
+ "version": "0.1.0",
21
+ "private": true,
22
+ "dependencies": {
23
+ "react": "^18.2.0",
24
+ "react-dom": "^18.2.0",
25
+ "react-icons": "^4.6.0",
26
+ "react-scripts": "^5.0.1",
27
+ "@iobroker/adapter-react-v5": "^3.2.7",
28
+ "del": "^6.1.1",
29
+ "gulp": "^4.0.2"
30
+ },
31
+ "scripts": {
32
+ "start": "react-scripts start",
33
+ "build": "react-scripts build",
34
+ "test": "react-scripts test",
35
+ "eject": "react-scripts eject"
36
+ },
37
+ "eslintConfig": {
38
+ "extends": "react-app"
39
+ },
40
+ "homepage": ".",
41
+ "browserslist": [
42
+ ">0.2%",
43
+ "not dead",
44
+ "not ie <= 11",
45
+ "not op_mini all"
46
+ ]
47
+ }
48
+ ```
49
+ 5. Call in `src`: `npm install`
50
+ 6. Copy gulpfile.js into `src`: `cp node_modules/@iobroker/adapter-react/gulpfile.js gulpfile.js`
51
+ 7. Start your dummy application `npm run start` for developing or build with `npm run build` and
52
+ copy files in `build` directory to `www` or to `admin`. In the admin you must rename `index.html` to `index_m.html`.
53
+ 8. You can do that with `gulp` tasks: `gulp build`, `gulp copy`, `gulp renameIndex` or `gulp renameTab`
54
+
55
+ ## Development
56
+ 1. Add `socket.io` to `public/index.html`.
57
+ After
58
+
59
+ ```
60
+ <link rel="manifest" href="%PUBLIC_URL%/manifest.json" />
61
+ ```
62
+
63
+ insert
64
+
65
+ ```
66
+ <script>
67
+ var script = document.createElement('script');
68
+ window.registerSocketOnLoad = function (cb) {
69
+ window.socketLoadedHandler = cb;
70
+ };
71
+ const parts = (window.location.search || '').replace(/^\?/, '').split('&');
72
+ const query = {};
73
+ parts.forEach(item => {
74
+ const [name, val] = item.split('=');
75
+ query[decodeURIComponent(name)] = val !== undefined ? decodeURIComponent(val) : true;
76
+ });
77
+ script.onload = function () { typeof window.socketLoadedHandler === 'function' && window.socketLoadedHandler(); };
78
+ script.src = window.location.port === '3000' ? window.location.protocol + '//' + (query.host || window.location.hostname) + ':' + (query.port || 8081) + '/lib/js/socket.io.js' : '%PUBLIC_URL%/../../lib/js/socket.io.js';
79
+
80
+ document.head.appendChild(script);
81
+ </script>
82
+ ```
83
+
84
+ 3. Add to App.js constructor initialization for I18n:
85
+ ```
86
+ class App extends GenericApp {
87
+ constructor(props) {
88
+ const extendedProps = {...props};
89
+ extendedProps.encryptedFields = ['pass']; // this parameter will be encrypted and decrypted automatically
90
+ extendedProps.translations = {
91
+ 'en': require('./i18n/en'),
92
+ 'de': require('./i18n/de'),
93
+ 'ru': require('./i18n/ru'),
94
+ 'pt': require('./i18n/pt'),
95
+ 'nl': require('./i18n/nl'),
96
+ 'fr': require('./i18n/fr'),
97
+ 'it': require('./i18n/it'),
98
+ 'es': require('./i18n/es'),
99
+ 'pl': require('./i18n/pl'),
100
+ 'uk': require('./i18n/uk'),
101
+ 'zh-cn': require('./i18n/zh-cn'),
102
+ };
103
+ // get actual admin port
104
+ extendedProps.socket = {port: parseInt(window.location.port, 10)};
105
+
106
+ // Only if close, save buttons are not required at the bottom (e.g. if admin tab)
107
+ // extendedProps.bottomButtons = false;
108
+
109
+ // only for debug purposes
110
+ if (extendedProps.socket.port === 3000) {
111
+ extendedProps.socket.port = 8081;
112
+ }
113
+
114
+ // allow to manage GenericApp the sentry initialisation or do not set the sentryDSN if no sentry available
115
+ extendedProps.sentryDSN = 'https://yyy@sentry.iobroker.net/xx';
116
+
117
+ super(extendedProps);
118
+ }
119
+ ...
120
+ }
121
+ ```
122
+
123
+ 4. Replace `index.js` with the following code to support themes:
124
+ ```
125
+ import React from 'react';
126
+ import ReactDOM from 'react-dom';
127
+ import { MuiThemeProvider} from '@material-ui/core/styles';
128
+ import * as serviceWorker from './serviceWorker';
129
+
130
+ import './index.css';
131
+ import App from './App';
132
+ import { version } from '../package.json';
133
+
134
+ import theme from '@iobroker/adapter-react/Theme';
135
+
136
+ console.log('iobroker.scenes@' + version);
137
+ let themeName = window.localStorage ? window.localStorage.getItem('App.theme') || 'light' : 'light';
138
+
139
+ function build() {
140
+ return ReactDOM.render(<MuiThemeProvider theme={ theme(themeName) }>
141
+ <App onThemeChange={_theme => {
142
+ themeName = _theme;
143
+ build();
144
+ }}/>
145
+ </MuiThemeProvider>, document.getElementById('root'));
146
+ }
147
+
148
+ build();
149
+
150
+ // If you want your app to work offline and load faster, you can change
151
+ // unregister() to register() below. Note this comes with some pitfalls.
152
+ // Learn more about service workers: http://bit.ly/CRA-PWA
153
+ serviceWorker.unregister();
154
+ ```
155
+
156
+ 5. Add to App.js encoding and decoding of values:
157
+ ```
158
+ class App extend GenericApp {
159
+ ...
160
+ onPrepareLoad(settings) {
161
+ settings.pass = this.decode(settings.pass);
162
+ }
163
+ onPrepareSave(settings) {
164
+ settings.pass = this.encode(settings.pass);
165
+ }
166
+ }
167
+ ```
168
+
169
+ 6. The optional step is to validate the data to be saved:
170
+ ```
171
+ onPrepareSave(settings) {
172
+ super.onPrepareSave(settings);
173
+ if (DATA_INVALID) {
174
+ return false; // configuration will not be saved
175
+ } else {
176
+ return true;
177
+ }
178
+ }
179
+ ```
180
+
181
+ ## Components
182
+
183
+ ### Connection.tsx
184
+ This is a non-react class to provide the communication for socket connection with the server.
185
+
186
+ ### GenericApp.tsx
187
+
188
+ ### i18n.ts
189
+
190
+ ### Theme.tsx
191
+
192
+ ### Dialogs
193
+ Some dialogs are predefined and could be used out of the box.
194
+
195
+ #### Confirm.tsx
196
+ <!-- TODO: Provide screenshot here -->
197
+
198
+ Usage:
199
+ ```
200
+ import React from 'react';
201
+ import ConfirmDialog from '@iobroker/adapter-react/Dialogs/Confirm'
202
+ import I18n from '@iobroker/adapter-react/i18n';
203
+
204
+ class ExportImportDialog extends React.Component {
205
+ constructor(props) {
206
+ super(props);
207
+
208
+ this.state = {
209
+ confirmDialog: false,
210
+ };
211
+ }
212
+
213
+ renderConfirmDialog() {
214
+ if (!this.state.confirmDialog) {
215
+ return null;
216
+ }
217
+ return <ConfirmDialog
218
+ title={ I18n.t('Scene will be overwritten.') }
219
+ text={ I18n.t('All data will be lost. Confirm?') }
220
+ ok={ I18n.t('Yes') }
221
+ cancel={ I18n.t('Cancel') }
222
+ suppressQuestionMinutes={5}
223
+ dialogName="myConfirmDialogThatCouldBeSuppressed"
224
+ suppressText={I18n.t('Suppress question for next %s minutes', 5)}
225
+ onClose={isYes => {
226
+ this.setState({ confirmDialog: false} );
227
+ }}
228
+ />;
229
+ }
230
+ render() {
231
+ return <div>
232
+ <Button onClick={ () => this.setState({confirmDialog: true}) }>Click</Button>
233
+ { this.renderConfirmDialog() }
234
+ </div>
235
+ }
236
+ }
237
+
238
+ export default ExportImportDialog;
239
+ ```
240
+
241
+ #### Error.tsx
242
+ <!-- TODO: Provide screenshot here -->
243
+
244
+ #### Message.tsx
245
+ <!-- TODO: Provide screenshot here -->
246
+ ```
247
+ renderMessage() {
248
+ if (this.state.showMessage) {
249
+ return <Message
250
+ text={this.state.showMessage}
251
+ onClose={() => this.setState({showMessage: false})}
252
+ />;
253
+ } else {
254
+ return null;
255
+ }
256
+ }
257
+ ```
258
+
259
+ #### SelectID.tsx
260
+ ![Logo](img/selectID.png)
261
+ ```
262
+ import DialogSelectID from '@iobroker/adapter-react/Dialogs/SelectID';
263
+
264
+ class MyComponent extends Component {
265
+ constructor(props) {
266
+ super(props);
267
+ this.state = {
268
+ showSelectId: false,
269
+ };
270
+ }
271
+
272
+ renderSelectIdDialog() {
273
+ if (this.state.showSelectId) {
274
+ return <DialogSelectID
275
+ key="tableSelect"
276
+ imagePrefix="../.."
277
+ dialogName={this.props.adapterName}
278
+ themeType={this.props.themeType}
279
+ socket={this.props.socket}
280
+ statesOnly={true}
281
+ selected={this.state.selectIdValue}
282
+ onClose={() => this.setState({showSelectId: false})}
283
+ onOk={(selected, name) => {
284
+ this.setState({showSelectId: false, selectIdValue: selected});
285
+ }}
286
+ />;
287
+ } else {
288
+ return null;
289
+ }
290
+ }
291
+ render() {
292
+ return renderSelectIdDialog();
293
+ }
294
+ }
295
+ ```
296
+
297
+ #### Cron
298
+ Include `"react-text-mask": "^5.4.3",` in package.json.
299
+
300
+ <!-- TODO: Provide screenshot here -->
301
+
302
+ ```
303
+ function renderCron() {
304
+ if (!showCron) {
305
+ return null;
306
+ } else {
307
+ return <DialogCron
308
+ key="dialogCron1"
309
+ cron={this.state.cronValue || '* * * * *'}
310
+ onClose={() => this.setState({ showCron: false })}
311
+ onOk={cronValue => {
312
+ this.setState({ cronValue })
313
+ }}
314
+ />;
315
+ }
316
+ }
317
+ ```
318
+
319
+ ### Components
320
+
321
+ #### Utils.tsx
322
+ ##### getObjectNameFromObj
323
+ `getObjectNameFromObj(obj, settings, options, isDesc)`
324
+
325
+ Get object name from a single object.
326
+
327
+ Usage: `Utils.getObjectNameFromObj(this.objects[id], null, {language: I18n.getLanguage()})`
328
+
329
+ ##### getObjectIcon
330
+ `getObjectIcon(id, obj)`
331
+
332
+ Get icon from the object.
333
+
334
+ Usage:
335
+ ```
336
+ const icon = Utils.getObjectIcon(id, this.objects[id]);
337
+ return (<img src={icon}/>);
338
+ ```
339
+
340
+ ##### isUseBright
341
+ `isUseBright(color, defaultValue)`
342
+
343
+ Usage: `
344
+
345
+ #### Loader.tsx
346
+ ![Logo](img/loader.png)
347
+
348
+ ```
349
+ render() {
350
+ if (!this.state.loaded) {
351
+ return <MuiThemeProvider theme={this.state.theme}>
352
+ <Loader theme={this.state.themeType}/>
353
+ </MuiThemeProvider>;
354
+ }
355
+ // render loaded data
356
+ }
357
+
358
+ ```
359
+
360
+ #### Logo.tsx
361
+ ![Logo](img/logo.png)
362
+
363
+ ```
364
+ render() {
365
+ return <form className={this.props.classes.tab}>
366
+ <Logo
367
+ instance={this.props.instance}
368
+ common={this.props.common}
369
+ native={this.props.native}
370
+ onError={text => this.setState({errorText: text})}
371
+ onLoad={this.props.onLoad}
372
+ />
373
+ ...
374
+ </form>;
375
+ }
376
+ ```
377
+
378
+ #### Router.tsx
379
+
380
+ #### ObjectBrowser.js
381
+ It is better to use `Dialog/SelectID`, but if you want:
382
+
383
+ ![Logo](img/objectBrowser.png)
384
+
385
+ ```
386
+ <ObjectBrowser
387
+ foldersFirst={this.props.foldersFirst}
388
+ imagePrefix={this.props.imagePrefix || this.props.prefix} // prefix is for back compatibility
389
+ defaultFilters={this.filters}
390
+ dialogName={this.dialogName}
391
+ showExpertButton={this.props.showExpertButton !== undefined ? this.props.showExpertButton : true}
392
+ style={{ width: '100%', height: '100%' }}
393
+ columns={this.props.columns || ['name', 'type', 'role', 'room', 'func', 'val']}
394
+ types={this.props.types || ['state']}
395
+ t={I18n.t}
396
+ lang={this.props.lang || I18n.getLanguage()}
397
+ socket={this.props.socket}
398
+ selected={this.state.selected}
399
+ multiSelect={this.props.multiSelect}
400
+ notEditable={this.props.notEditable === undefined ? true : this.props.notEditable}
401
+ name={this.state.name}
402
+ themeName={this.props.themeName}
403
+ themeType={this.props.themeType}
404
+ customFilter={this.props.customFilter}
405
+ onFilterChanged={filterConfig => {
406
+ this.filters = filterConfig;
407
+ window.localStorage.setItem(this.dialogName, JSON.stringify(filterConfig));
408
+ }}
409
+ onSelect={(selected, name, isDouble) => {
410
+ if (JSON.stringify(selected) !== JSON.stringify(this.state.selected)) {
411
+ this.setState({selected, name}, () =>
412
+ isDouble && this.handleOk());
413
+ } else if (isDouble) {
414
+ this.handleOk();
415
+ }
416
+ }}
417
+ />
418
+ ```
419
+
420
+ #### TreeTable.ts
421
+ ![Logo](img/tableTree.png)
422
+
423
+ ```
424
+ // STYLES
425
+ const styles = theme => ({
426
+ tableDiv: {
427
+ width: '100%',
428
+ overflow: 'hidden',
429
+ height: 'calc(100% - 48px)',
430
+ },
431
+ });
432
+ class MyComponent extends Component {
433
+ constructor(props) {
434
+ super(props);
435
+
436
+ this.state = {
437
+ data: [
438
+ {
439
+ id: 'UniqueID1' // required
440
+ fieldIdInData: 'Name1',
441
+ myType: 'number',
442
+ },
443
+ {
444
+ id: 'UniqueID2' // required
445
+ fieldIdInData: 'Name12',
446
+ myType: 'string',
447
+ },
448
+ ],
449
+ };
450
+
451
+ this.columns = [
452
+ {
453
+ title: 'Name of field', // required, else it will be "field"
454
+ field: 'fieldIdInData', // required
455
+ editable: false, // or true [default - true]
456
+ cellStyle: { // CSS style - // optional
457
+ maxWidth: '12rem',
458
+ overflow: 'hidden',
459
+ wordBreak: 'break-word',
460
+ },
461
+ lookup: { // optional => edit will be automatically "SELECT"
462
+ 'value1': 'text1',
463
+ 'value2': 'text2',
464
+ }
465
+ },
466
+ {
467
+ title: 'Type', // required, else it will be "field"
468
+ field: 'myType', // required
469
+ editable: true, // or true [default - true]
470
+ lookup: { // optional => edit will be automatically "SELECT"
471
+ 'number': 'Number',
472
+ 'string': 'String',
473
+ 'boolean': 'Boolean',
474
+ },
475
+ type: 'number/string/color/oid/icon/boolean', // oid=ObjectID,icon=base64-icon
476
+ editComponent: props =>
477
+ <div>Prefix&#123; <br/>
478
+ <textarea
479
+ rows={4}
480
+ style={{width: '100%', resize: 'vertical'}}
481
+ value={props.value}
482
+ onChange={e => props.onChange(e.target.value)}
483
+ />
484
+ Suffix
485
+ </div>,
486
+ },
487
+ ];
488
+ }
489
+ // renderTable
490
+ render() {
491
+ return <div className={this.props.classes.tableDiv}>
492
+ <TreeTable
493
+ columns={this.columns}
494
+ data={this.state.data}
495
+ onUpdate={(newData, oldData) => {
496
+ const data = JSON.parse(JSON.stringify(this.state.data));
497
+
498
+ // Added new line
499
+ if (newData === true) {
500
+ // find unique ID
501
+ let i = 1;
502
+ let id = 'line_' + i;
503
+
504
+ // eslint-disable-next-line
505
+ while(this.state.data.find(item => item.id === id)) {
506
+ i++;
507
+ id = 'line_' + i;
508
+ }
509
+
510
+ data.push({
511
+ id,
512
+ name: I18n.t('New resource') + '_' + i,
513
+ color: '',
514
+ icon: '',
515
+ unit: '',
516
+ price: 0,
517
+ });
518
+ } else {
519
+ // existing line was modifed
520
+ const pos = this.state.data.indexOf(oldData);
521
+ if (pos !== -1) {
522
+ Object.keys(newData).forEach(attr => data[pos][attr] = newData[attr]);
523
+ }
524
+ }
525
+
526
+ this.setState({data});
527
+ }}
528
+ onDelete={oldData => {
529
+ console.log('Delete: ' + JSON.stringify(oldData));
530
+ const pos = this.state.data.indexOf(oldData);
531
+ if (pos !== -1) {
532
+ const data = JSON.parse(JSON.stringify(this.state.data));
533
+ data.splice(pos, 1);
534
+ this.setState({data});
535
+ }
536
+ }}
537
+ />
538
+ </div>;
539
+ }
540
+ }
541
+ ```
542
+
543
+ #### Toast
544
+ <!-- TODO: Provide screenshot here -->
545
+
546
+ Toast is not a part of `adapter-react` but it is an example how to use toast in application:
547
+
548
+ ```
549
+ import Snackbar from '@material-ui/core/Snackbar';
550
+
551
+ class MyComponent {
552
+ constructor(props) {
553
+ super(props);
554
+ this.state = {
555
+ // ....
556
+ toast: '',
557
+ };
558
+ }
559
+ // ...
560
+ renderToast() {
561
+ if (!this.state.toast) {
562
+ return null;
563
+ }
564
+ return <Snackbar
565
+ anchorOrigin={{
566
+ vertical: 'bottom',
567
+ horizontal: 'left',
568
+ }}
569
+ open={true}
570
+ autoHideDuration={6000}
571
+ onClose={() => this.setState({toast: ''})}
572
+ ContentProps={{'aria-describedby': 'message-id'}}
573
+ message={<span id="message-id">{this.state.toast}</span>}
574
+ action={[
575
+ <IconButton
576
+ key="close"
577
+ aria-label="Close"
578
+ color="inherit"
579
+ className={this.props.classes.close}
580
+ onClick={() => this.setState({toast: ''})}
581
+ >
582
+ <IconClose />
583
+ </IconButton>,
584
+ ]}
585
+ />;
586
+ }
587
+ render() {
588
+ return <div>
589
+ {this.renderToast()}
590
+ </div>;
591
+ }
592
+ }
593
+ ```
594
+
595
+ ## List of adapters that use adapter-react
596
+ - Admin
597
+ - iot
598
+ - echarts
599
+ - text2command
600
+ - scenes
601
+ - javascript
602
+ - devices
603
+ - eventlist
604
+ - cameras
605
+ - web
606
+ - vis-2
607
+ - vis-2-widgets-xxx
608
+ - fullcalendar
609
+ - openweathermap
610
+
611
+ ## Usability
612
+ In dialogs, the OK button is first (on the left) and the cancel button is last (on the right)
613
+
614
+ ## Used icons
615
+ This project uses icons from [Flaticon](https://www.flaticon.com/).
616
+
617
+ ioBroker GmbH has a valid license for all the used icons.
618
+ The icons may not be reused in other projects without the proper flaticon license or flaticon subscription.
619
+
620
+ ## Migration from adapter-react to adapter-react-v5
621
+ ### In src/package.json => dependencies
622
+ - `"@iobroker/adapter-react": "^2.0.22",` => `"@iobroker/adapter-react-v5": "^3.1.34",`
623
+ - `"@material-ui/core": "^4.12.3",` => `"@mui/material": "^5.10.9",`
624
+ - `"@material-ui/icons": "^4.11.2",` => `"@mui/icons-material": "^5.10.9",`
625
+ - Add `"@mui/styles": "^5.10.9",`
626
+ - Add `"babel-eslint": "^10.1.0",`
627
+
628
+ ### In Source files
629
+ - All `@iobroker/adapter-react/...` => `@iobroker/adapter-react-v5/...`
630
+ - All `@material-ui/icons/...` => `@mui/icons-material/...`
631
+ - Change `import { withStyles } from '@material-ui/core/styles';` => `import { withStyles } from '@mui/styles';`
632
+ - Change `import { makeStyles } from '@mui/material/styles';` => `import { makeStyles } from '@mui/styles';`
633
+ - Change `import withWidth from '@material-ui/core/withWidth';` => `import { withWidth } from '@iobroker/adapter-react-v5';`
634
+ - All `@material-ui/core...` => `@mui/material...`
635
+ - Change `import { MuiThemeProvider } from '@material-ui/core/styles';` => `import { ThemeProvider, StyledEngineProvider } from '@mui/material/styles';`
636
+ - Change all `<MuiThemeProvider theme={this.state.theme}>` to `<StyledEngineProvider injectFirst><ThemeProvider theme={this.state.theme}>`
637
+ - Rename in styles `theme.palette.type` => `theme.palette.mode`
638
+ - Add to all `TextField`, `Select`, `FormControl` the property `variant="standard"`
639
+ - Add to all `Button` that do not have `color` property: `color="grey"`
640
+ - Replace by `TextField` the `readOnly` attribute (if exists) with `InputProps={{readOnly: true}}`
641
+ - Remove px by all `theme.spacing`: `calc(100% - ${theme.spacing(4)}px)` => `calc(100% - ${theme.spacing(4)})`
642
+ - Replace `this.selectTab(e.target.parentNode.dataset.name, index)` => `this.selectTab(e.target.dataset.name, index)`
643
+
644
+ If you still have questions, try to find an answer [here](https://mui.com/guides/migration-v4/).
645
+
646
+ ## Migration from adapter-react-v5@3.x to adapter-react-v5@4.x
647
+ - Look for getObjectView socket requests and replace `socket.getObjectView('startKey', 'endKey', 'instance')` to `socket.getObjectViewSystem('instance', 'startKey', 'endKey')`
648
+ - Look for calls of custom like
649
+ ```
650
+ this.props.socket._socket.emit('getObjectView', 'system', 'custom', {startKey: '', endKey:'\u9999'}, (err, objs) => {
651
+ (objs?.rows || [])
652
+ .forEach(item => console.log(item.id, item.value));
653
+ });
654
+ ```
655
+ to
656
+ ```
657
+ socket.getObjectViewCustom('custom', 'state', 'startKey', 'endKey')
658
+ .then(objects => {
659
+ Object.keys(objects).forEach(obj => console.log(obj._id));
660
+ });
661
+ ```
662
+ - Replace all `socket.log.error('text')` to `socket.log('text', 'error')`
663
+ - Add to App.js `import { AdminConnection } from '@iobroker/adapter-react-v5';` and `super(props, { Connection: AdminConnection });` if run in admin
664
+
665
+ ## Migration from adapter-react-v5@4.x to adapter-react-v5@5.x
666
+ - `Theme` is renamed to IobTheme. It is an object with classes inside. `Theme` is still inside and it same as mui `createTheme`.
667
+ - adapter-react-v5 has all types exported. So you can use `import { type IobTheme, Theme } from '@iobroker/adapter-react-v5';` and `const theme: IobTheme = Theme('light');`
668
+ - Json-Config is now an external package and must be included as dependency separately.
669
+ - Use type `Translate` for `t(word: string, ...args: any[]) => string`
670
+ - All components for admin JsonConfig must be changed:
671
+ Before `adapter-react-v5@5.x`:
672
+
673
+ ```
674
+ import { ConfigGeneric, I18n } from '@iobroker/adapter-react-v5';
675
+ class JsonComponent extends ConfigGeneric {
676
+ ...
677
+ }
678
+ ```
679
+
680
+ With `adapter-react-v5@5.x`:
681
+
682
+ ```
683
+ import { I18n } from '@iobroker/adapter-react-v5';
684
+ import { ConfigGeneric } from '@iobroker/json-config';
685
+ class JsonComponent extends ConfigGeneric {
686
+ ...
687
+ }
688
+ ```
689
+ ## Migration from v5 to v6
690
+ The main change is that the `withStyles` was removed. So you have to replace all `withStyles` with `sx` or `style` properties.
691
+
692
+ You can read more about sx [here](https://mui.com/system/getting-started/the-sx-prop/).
693
+ - Remove at start of the file `import { withStyles } from '@mui/styles';`
694
+ - Replace at the very end of the file `export default withStyles(styles)(MyComponent);` with `export default MyComponent;`
695
+ - Modify `const styles`:
696
+ Before:
697
+ ```
698
+ const styles: Record<string, any> = (theme: IobTheme) => ({
699
+ dialog: {
700
+ height: `calc(100% - ${theme.mixins.toolbar.minHeight}px)`,
701
+ padding: theme.spacing(1),
702
+ margin: theme.spacing(2),
703
+ gap: 5,
704
+ borderRadius: 5,
705
+ marginLeft: 10, // marginTop, marginRight, marginBottom
706
+ paddingLeft: 10, // paddingTop, paddingRight, paddingBottom
707
+ },
708
+ ...
709
+ });
710
+ ```
711
+
712
+ After:
713
+ ```
714
+ const styles: Record<string, any> = {
715
+ dialog: (theme: IobTheme) => ({
716
+ height: `calc(100% - ${theme => theme.mixins.toolbar.minHeight}px)`,
717
+ p: 1, // or 8px, padding is OK too
718
+ m: '16px', // or 2, margin is OK too
719
+ gap: '5px',
720
+ borderRadius: '5px',
721
+ ml: '10px', // mt, mr, mb, but marginLeft, marginRight, marginBottom is OK too
722
+ pl: '10px', // pt, pr, pb, but paddingTop, paddingRight, paddingBottom is OK too
723
+ }),
724
+ };
725
+ ```
726
+
727
+ - Modify `className`:
728
+ Before: `<div className={this.props.classes.box}>`
729
+
730
+ After: `<Box sx={styles.box}>`
731
+
732
+ Before: `<span className={Utils.clsx(this.props.classes.box1, condition && this.props.classes.box2)}>`
733
+
734
+ After: `<Box component="span" sx={Utils.getStyle(this.props.theme, this.props.classes.box1, condition && this.props.classes.box2)}>`
735
+ Or if no one style is a function: `<Box component="div" sx={{ ...this.props.classes.box1, ...(condition ? this.props.classes.box2 : undefined) }}>`
736
+
737
+ Do not use `sx` if the style is not dynamic (not a function). Use `style` instead.
738
+
739
+ Be aware, that all paddings and margins are now in `theme.spacing(1)` format.
740
+ So you have to replace all `padding: 8` with `padding: 1` or with `padding: '8px'`.
741
+
742
+ The best practice is to replace `padding` with `p` and `margin` with `m`, so you will see immediately that it is a padding or margin for `sx` property.
743
+
744
+ - Modify `classes`:
745
+ Before: `<Dialog classes={{ scrollPaper: this.props.classes.dialog, paper: this.props.classes.paper }}>`
746
+
747
+ After: `<Dialog sx={{ '&.MuiDialog-scrollPaper': styles.dialog, '& .MuiDialog-paper': styles.paper }}>`
748
+
749
+ Before: `<Dialog classes={{ scrollPaper: this.props.classes.dialog, paper: this.props.classes.paper }}>`
750
+
751
+ After: `<Dialog sx={{ '&.MuiDialog-scrollPaper': styles.dialog, '& .MuiDialog-paper': styles.paper }}>`
752
+
753
+ Before: `<ListItem classes={{ root: styles.listItem }} >`
754
+
755
+ After: `<ListItem sx={{ '&.MuiListItem-root': styles.listItem }} >`
756
+
757
+ Before: `<Typography component="h2" variant="h6" classes={{ root: styles.typography }}>`
758
+
759
+ After: `<Typography component="h2" variant="h6" sx={{ '&.MuiTypography-root': styles.typography }}>`
760
+
761
+ Before: `<Badge classes={{ 'badge': styles.expertBadge }}>`
762
+
763
+ After: `<Badge sx={{ '& .MuiBadge-badge': styles.expertBadge }}>`
764
+
765
+ Before: `<Tab classes={{ selected: styles.selected }} />`
766
+
767
+ After: `<Tab sx={{ '&.Mui-selected': styles.selected }} />`
768
+
769
+ Before: `<Tooltip title={this.props.t('ra_Refresh tree')} classes={{ popper: styles.tooltip }}>`
770
+
771
+ After: `<Tooltip title={this.props.t('ra_Refresh tree')} componentsProps={{ popper: { sx: { pointerEvents: 'none' } } }}>`
772
+ Or: `<Tooltip title={this.props.t('ra_Refresh tree')} componentsProps={{ popper: { sx: styles.tooltip } }}>`
773
+
774
+ Before. `<AccordionSummary classes={{ root: styles.rootStyle, content: styles.content }}>`
775
+
776
+ After. `<AccordionSummary sx={{ '&.MuiAccordionSummary-root': styles.rootStyle, '& .MuiAccordionSummary-content': styles.content }}>`
777
+
778
+ Before. `<Drawer classes={{ paper: styles.paperStyle }}>`
779
+
780
+ After. `<Drawer sx={{ '& .MuiDrawer-paper': styles.paperStyle }}>`
781
+
782
+ <!--
783
+ Placeholder for the next version (at the beginning of the line):
784
+ ### **WORK IN PROGRESS**
785
+ -->
786
+
788
787
  ## Changelog
789
- ### 6.1.9 (2024-08-14)
790
- * (bluefox) Updated JSON schema
791
-
792
- ### 6.1.8 (2024-08-03)
788
+ ### 6.1.7 (2024-08-03)
793
789
  * (bluefox) Added translations
794
790
 
795
- ### 6.1.6 (2024-07-23)
791
+ ### 6.1.6 (2024-07-23)
796
792
  * (bluefox) Optimize package
797
793
 
798
- ### 6.1.5 (2024-07-20)
794
+ ### 6.1.5 (2024-07-20)
799
795
  * (bluefox) Added sources to package
800
796
 
801
- ### 6.1.3 (2024-07-20)
797
+ ### 6.1.3 (2024-07-20)
802
798
  * (bluefox) Better typing of legacy connection
803
799
 
804
- ### 6.1.1 (2024-07-16)
800
+ ### 6.1.1 (2024-07-16)
805
801
  * (bluefox) Added translations
806
802
 
807
- ### 6.1.0 (2024-07-15)
803
+ ### 6.1.0 (2024-07-15)
808
804
  * (bluefox) Replace by CRON to text the package to `cronstrue`
809
805
 
810
- ### 6.0.19 (2024-07-14)
806
+ ### 6.0.19 (2024-07-14)
811
807
  * (bluefox) added some packages for federation
812
808
 
813
- ### 6.0.17 (2024-07-14)
814
- * (bluefox) Allowed playing mp3 files in the file browser
809
+ ### 6.0.17 (2024-07-14)
810
+ * (bluefox) Allowed playing mp3 files in the file browser
815
811
  * (bluefox) Corrected jump by object selection
816
812
 
817
- ### 6.0.14 (2024-07-07)
813
+ ### 6.0.14 (2024-07-07)
818
814
  * (bluefox) Corrected theme type selection
819
815
 
820
- ### 6.0.13 (2024-06-30)
816
+ ### 6.0.13 (2024-06-30)
821
817
  * (bluefox) Corrected color picker
822
818
 
823
- ### 6.0.12 (2024-06-29)
819
+ ### 6.0.12 (2024-06-29)
824
820
  * (bluefox) Added support for the overrides in the theme
825
821
 
826
- ### 6.0.10 (2024-06-27)
827
- * (bluefox) Added translation
822
+ ### 6.0.10 (2024-06-27)
823
+ * (bluefox) Added translation
828
824
  * (bluefox) Mobile object browser improved
829
825
 
830
- ### 6.0.9 (2024-06-26)
826
+ ### 6.0.9 (2024-06-26)
831
827
  * (bluefox) Corrected Icons
832
828
 
833
- ### 6.0.8 (2024-06-26)
834
- * (bluefox) Corrected types of the select ID dialog
829
+ ### 6.0.8 (2024-06-26)
830
+ * (bluefox) Corrected types of the select ID dialog
835
831
  * (bluefox) Made the tooltips neutral to the pointer events
836
832
 
837
- ### 6.0.6 (2024-06-24)
838
- * (bluefox) Synchronised with admin
833
+ ### 6.0.6 (2024-06-24)
834
+ * (bluefox) Synchronised with admin
839
835
  * (bluefox) Added translations for time scheduler
840
836
 
841
- ### 6.0.4 (2024-06-21)
842
- * (bluefox) Removed the usage of `withStyles` in favor of `sx` and `style` properties (see [Migration from v5 to v6](#migration-from-v5-to-v6)
837
+ ### 6.0.4 (2024-06-21)
838
+ * (bluefox) Removed the usage of `withStyles` in favor of `sx` and `style` properties (see [Migration from v5 to v6](#migration-from-v5-to-v6)
843
839
  * (bluefox) (BREAKING) Higher version of `@mui/material` (5.15.20) is used
844
840
 
845
- ### 5.0.8 (2024-06-15)
841
+ ### 5.0.8 (2024-06-15)
846
842
  * (bluefox) Added `modulefederation.admin.config.js` for module federation
847
843
 
848
- ### 5.0.5 (2024-06-10)
844
+ ### 5.0.5 (2024-06-10)
849
845
  * (bluefox) Sources were synchronized with admin
850
846
 
851
- ### 5.0.4 (2024-06-07)
847
+ ### 5.0.4 (2024-06-07)
852
848
  * (bluefox) Added better typing
853
849
 
854
- ### 5.0.2 (2024-05-30)
855
- * (bluefox) Added better typing
850
+ ### 5.0.2 (2024-05-30)
851
+ * (bluefox) Added better typing
856
852
  * (bluefox) Json-Config is now a separate package and must be installed additionally
857
853
 
858
- ### 5.0.0 (2024-05-29)
859
- * (bluefox) Types are now exported
860
- * (bluefox) Translator renamed to Translate
854
+ ### 5.0.0 (2024-05-29)
855
+ * (bluefox) Types are now exported
856
+ * (bluefox) Translator renamed to Translate
861
857
  * (bluefox) Breaking: Theme renamed to IobTheme because of the naming conflict
862
858
 
863
- ### 4.13.24 (2024-05-25)
864
- * (bluefox) Updated packages
865
-
866
- * ### 4.13.22 (2024-05-23)
859
+ ### 4.13.24 (2024-05-25)
860
+ * (bluefox) Updated packages
861
+
862
+ * ### 4.13.22 (2024-05-23)
867
863
  * (bluefox) Updated packages
868
864
 
869
- ### 4.13.20 (2024-05-22)
870
- * (bluefox) Better types added
871
- * (bluefox) updated theme definitions
865
+ ### 4.13.20 (2024-05-22)
866
+ * (bluefox) Better types added
867
+ * (bluefox) updated theme definitions
872
868
  * (bluefox) corrected dates in cron dialog
873
869
 
874
- ### 4.13.14 (2024-05-19)
870
+ ### 4.13.14 (2024-05-19)
875
871
  * (bluefox) Updated packages
876
872
 
877
- ### 4.13.13 (2024-05-09)
873
+ ### 4.13.13 (2024-05-09)
878
874
  * (bluefox) Updated ioBroker types
879
875
 
880
- ### 4.13.12 (2024-05-06)
876
+ ### 4.13.12 (2024-05-06)
881
877
  * (bluefox) All files are migrated to Typescript
882
878
 
883
- ### 4.13.11 (2024-04-23)
879
+ ### 4.13.11 (2024-04-23)
884
880
  * (bluefox) Corrected the size of icons
885
881
 
886
- ### 4.13.10 (2024-04-22)
882
+ ### 4.13.10 (2024-04-22)
887
883
  * (bluefox) Migrated all icons to Typescript
888
884
 
889
- ### 4.13.9 (2024-04-20)
885
+ ### 4.13.9 (2024-04-20)
890
886
  * (bluefox) Updated socket-client package
891
887
 
892
- ### 4.13.8 (2024-04-19)
888
+ ### 4.13.8 (2024-04-19)
893
889
  * (bluefox) Corrected CRON selector
894
890
 
895
- ### 4.13.7 (2024-04-19)
891
+ ### 4.13.7 (2024-04-19)
896
892
  * (bluefox) Migrated ColorPicker to typescript
897
893
 
898
- ### 4.13.6 (2024-04-11)
899
- * (bluefox) Migrated TreeTable to typescript
894
+ ### 4.13.6 (2024-04-11)
895
+ * (bluefox) Migrated TreeTable to typescript
900
896
  * (bluefox) corrected the object subscription
901
897
 
902
- ### 4.13.5 (2024-04-02)
903
- * (bluefox) used new connection classes
898
+ ### 4.13.5 (2024-04-02)
899
+ * (bluefox) used new connection classes
904
900
  * (bluefox) Improved the `SelectID` dialog
905
901
 
906
- ### 4.13.3 (2024-04-01)
902
+ ### 4.13.3 (2024-04-01)
907
903
  * (bluefox) used new connection classes
908
904
 
909
- ### 4.12.3 (2024-03-30)
905
+ ### 4.12.3 (2024-03-30)
910
906
  * (bluefox) Migrated legacy connection to typescript
911
907
 
912
- ### 4.12.2 (2024-03-25)
908
+ ### 4.12.2 (2024-03-25)
913
909
  * (bluefox) Added support for remote cloud
914
910
 
915
- ### 4.11.6 (2024-03-19)
911
+ ### 4.11.6 (2024-03-19)
916
912
  * (bluefox) Corrected rendering of LoaderMV
917
913
 
918
- ### 4.11.4 (2024-03-18)
914
+ ### 4.11.4 (2024-03-18)
919
915
  * (bluefox) Corrected types of IconPicker
920
916
 
921
- ### 4.11.3 (2024-03-17)
917
+ ### 4.11.3 (2024-03-17)
922
918
  * (bluefox) Made filters for the file selector dialog optional
923
919
 
924
- ### 4.11.2 (2024-03-16)
920
+ ### 4.11.2 (2024-03-16)
925
921
  * (bluefox) Migrated GenericApp to typescript
926
922
 
927
- ### 4.10.4 (2024-03-16)
923
+ ### 4.10.4 (2024-03-16)
928
924
  * (bluefox) Migrated some components to typescript
929
925
 
930
- ### 4.10.1 (2024-03-11)
926
+ ### 4.10.1 (2024-03-11)
931
927
  * (bluefox) Migrated some components to typescript
932
928
 
933
- ### 4.9.11 (2024-03-08)
929
+ ### 4.9.11 (2024-03-08)
934
930
  * (foxriver76) type GenericApp socket correctly
935
931
 
936
- ### 4.9.10 (2024-02-21)
937
- * (bluefox) translations
932
+ ### 4.9.10 (2024-02-21)
933
+ * (bluefox) translations
938
934
  * (bluefox) updated json config
939
935
 
940
- ### 4.9.9 (2024-02-16)
936
+ ### 4.9.9 (2024-02-16)
941
937
  * (foxriver76) also check plugin state of instance to see if Sentry is explicitly disabled
942
938
 
943
- ### 4.9.8 (2024-02-13)
939
+ ### 4.9.8 (2024-02-13)
944
940
  * (bluefox) allowed hiding wizard in cron dialog
945
941
 
946
- ### 4.9.7 (2024-02-03)
942
+ ### 4.9.7 (2024-02-03)
947
943
  * (foxriver76) allow passing down the instance number do avoid determining from url
948
944
 
949
- ### 4.9.5 (2024-01-01)
945
+ ### 4.9.5 (2024-01-01)
950
946
  * (foxriver76) make `copyToClipboard` event parameter optional
951
947
 
952
- ### 4.9.4 (2024-01-01)
948
+ ### 4.9.4 (2024-01-01)
953
949
  * (foxriver76) try to fix `SelectID` scrolling
954
950
 
955
- ### 4.9.2 (2023-12-30)
951
+ ### 4.9.2 (2023-12-30)
956
952
  * (foxriver76) bump version of `@iobroker/json-config`
957
953
 
958
- ### 4.9.1 (2023-12-22)
954
+ ### 4.9.1 (2023-12-22)
959
955
  * (foxriver76) `@iobroker/json-config` moved to real dependencies
960
956
 
961
- ### 4.9.0 (2023-12-22)
962
- * (foxriver76) migrate to `@iobroker/json-config` module to have a single point of truth
957
+ ### 4.9.0 (2023-12-22)
958
+ * (foxriver76) migrate to `@iobroker/json-config` module to have a single point of truth
963
959
  * (bluefox) Allowed using of `filterFunc` as string
964
960
 
965
- ### 4.8.1 (2023-12-14)
961
+ ### 4.8.1 (2023-12-14)
966
962
  * (bluefox) Added Device manager to JSON Config
967
963
 
968
- ### 4.7.15 (2023-12-12)
964
+ ### 4.7.15 (2023-12-12)
969
965
  * (bluefox) Corrected parsing of a text
970
966
 
971
- ### 4.7.13 (2023-12-10)
967
+ ### 4.7.13 (2023-12-10)
972
968
  * (bluefox) Added possibility to define the root style and embedded property
973
969
 
974
- ### 4.7.11 (2023-12-06)
970
+ ### 4.7.11 (2023-12-06)
975
971
  * (bluefox) Extended color picker with "noInputField" option
976
972
 
977
- ### 4.7.9 (2023-12-04)
973
+ ### 4.7.9 (2023-12-04)
978
974
  * (bluefox) Corrected the icon picker
979
975
 
980
- ### 4.7.8 (2023-12-04)
976
+ ### 4.7.8 (2023-12-04)
981
977
  * (foxriver76) port to `@iobroker/types`
982
978
 
983
- ### 4.7.6 (2023-11-29)
979
+ ### 4.7.6 (2023-11-29)
984
980
  * (bluefox) Added translations
985
981
 
986
- ### 4.7.5 (2023-11-28)
982
+ ### 4.7.5 (2023-11-28)
987
983
  * (bluefox) Corrected subscribe on objects in the legacy connection
988
984
 
989
- ### 4.7.4 (2023-11-23)
990
- * (bluefox) Updated packages
985
+ ### 4.7.4 (2023-11-23)
986
+ * (bluefox) Updated packages
991
987
  * (bluefox) Made getStates method in legacy connection compatible with new one
992
988
 
993
- ### 4.7.3 (2023-11-08)
989
+ ### 4.7.3 (2023-11-08)
994
990
  * (bluefox) Updated packages
995
991
 
996
- ### 4.7.2 (2023-11-03)
997
- * (foxriver76) fixed problem with color picker, where editing TextField was buggy
992
+ ### 4.7.2 (2023-11-03)
993
+ * (foxriver76) fixed problem with color picker, where editing TextField was buggy
998
994
  * (foxriver76) fixed light mode color of a path in FileBrowser
999
995
 
1000
- ### 4.7.0 (2023-10-31)
1001
- * (bluefox) Synced with admin
996
+ ### 4.7.0 (2023-10-31)
997
+ * (bluefox) Synced with admin
1002
998
  * (bluefox) Added GIF to image files
1003
999
 
1004
- ### 4.6.7 (2023-10-19)
1000
+ ### 4.6.7 (2023-10-19)
1005
1001
  * (bluefox) Added return value for `subscribeOnInstance` for Connection class
1006
1002
 
1007
- ### 4.6.6 (2023-10-13)
1003
+ ### 4.6.6 (2023-10-13)
1008
1004
  * (bluefox) Fixed the legacy connection
1009
1005
 
1010
- ### 4.6.5 (2023-10-12)
1006
+ ### 4.6.5 (2023-10-12)
1011
1007
  * (foxriver76) fixed object browser with date
1012
1008
 
1013
- ### 4.6.4 (2023-10-11)
1009
+ ### 4.6.4 (2023-10-11)
1014
1010
  * (bluefox) Updated the packages
1015
1011
 
1016
- ### 4.6.3 (2023-10-09)
1017
- * (bluefox) Just updated the packages
1012
+ ### 4.6.3 (2023-10-09)
1013
+ * (bluefox) Just updated the packages
1018
1014
  * (bluefox) Synced with admin
1019
1015
 
1020
- ### 4.6.2 (2023-09-29)
1016
+ ### 4.6.2 (2023-09-29)
1021
1017
  * (bluefox) Experimental feature added: update states on re-subscribe
1022
1018
 
1023
- ### 4.5.5 (2023-09-27)
1019
+ ### 4.5.5 (2023-09-27)
1024
1020
  * (bluefox) Added export for IconNoIcon
1025
1021
 
1026
- ### 4.5.4 (2023-09-17)
1022
+ ### 4.5.4 (2023-09-17)
1027
1023
  * (bluefox) Added the restricting to folder property for select file dialog
1028
1024
 
1029
- ### 4.5.3 (2023-08-20)
1025
+ ### 4.5.3 (2023-08-20)
1030
1026
  * (foxriver76) fixed css classes of TableResize, see https://github.com/ioBroker/ioBroker.admin/issues/1860
1031
1027
 
1032
- ### 4.5.2 (2023-08-20)
1028
+ ### 4.5.2 (2023-08-20)
1033
1029
  * (foxriver76) added missing export of TableResize
1034
1030
 
1035
- ### 4.5.1 (2023-08-19)
1031
+ ### 4.5.1 (2023-08-19)
1036
1032
  * (foxriver76) fix dialog TextInput
1037
1033
 
1038
- ### 4.5.0 (2023-08-18)
1034
+ ### 4.5.0 (2023-08-18)
1039
1035
  * (bluefox) Synchronize components with admin
1040
1036
 
1041
- ### 4.4.8 (2023-08-17)
1037
+ ### 4.4.8 (2023-08-17)
1042
1038
  * (bluefox) Added translations
1043
1039
 
1044
- ### 4.4.7 (2023-08-10)
1045
- * (bluefox) Added `subscribeStateAsync` method to wait for answer
1040
+ ### 4.4.7 (2023-08-10)
1041
+ * (bluefox) Added `subscribeStateAsync` method to wait for answer
1046
1042
  * (bluefox) Added support for arrays for un/subscriptions
1047
1043
 
1048
- ### 4.4.5 (2023-08-01)
1044
+ ### 4.4.5 (2023-08-01)
1049
1045
  * (bluefox) Updated packages
1050
1046
 
1051
- ### 4.3.3 (2023-07-28)
1047
+ ### 4.3.3 (2023-07-28)
1052
1048
  * (bluefox) Added translations
1053
1049
 
1054
- ### 4.3.0 (2023-07-19)
1055
- * (bluefox) Updated packages
1056
- * (bluefox) Added translations
1057
- * (bluefox) Synced object browser
1050
+ ### 4.3.0 (2023-07-19)
1051
+ * (bluefox) Updated packages
1052
+ * (bluefox) Added translations
1053
+ * (bluefox) Synced object browser
1058
1054
  * (bluefox) formatting
1059
1055
 
1060
- ### 4.2.1 (2023-07-17)
1061
- * (bluefox) Updated packages
1056
+ ### 4.2.1 (2023-07-17)
1057
+ * (bluefox) Updated packages
1062
1058
  * (bluefox) Added translations
1063
1059
 
1064
- ### 4.2.0 (2023-07-07)
1065
- * (bluefox) Updated packages
1060
+ ### 4.2.0 (2023-07-07)
1061
+ * (bluefox) Updated packages
1066
1062
  * (bluefox) Added new method `getObjectsById` to the socket communication
1067
1063
 
1068
- ### 4.1.2 (2023-06-20)
1064
+ ### 4.1.2 (2023-06-20)
1069
1065
  * (bluefox) Allowed setting theme name directly by theme toggle
1070
1066
 
1071
- ### 4.1.0 (2023-05-10)
1067
+ ### 4.1.0 (2023-05-10)
1072
1068
  * (bluefox) `craco-module-federation.js` was added. For node 16
1073
1069
 
1074
- ### 4.0.27 (2023-05-09)
1070
+ ### 4.0.27 (2023-05-09)
1075
1071
  * (bluefox) Allowed showing only specific root in SelectIDDialog
1076
1072
 
1077
- ### 4.0.26 (2023-05-08)
1073
+ ### 4.0.26 (2023-05-08)
1078
1074
  * (bluefox) Added IDs to the buttons in the dialog for GUI tests
1079
1075
 
1080
- ### 4.0.25 (2023-04-23)
1076
+ ### 4.0.25 (2023-04-23)
1081
1077
  * (bluefox) Extended `TextWithIcon` with defined color and icon
1082
1078
 
1083
- ### 4.0.24 (2023-04-03)
1079
+ ### 4.0.24 (2023-04-03)
1084
1080
  * (bluefox) Updated the file selector in tile mode
1085
1081
 
1086
- ### 4.0.23 (2023-03-27)
1082
+ ### 4.0.23 (2023-03-27)
1087
1083
  * (bluefox) Added translations
1088
1084
 
1089
- ### 4.0.22 (2023-03-22)
1085
+ ### 4.0.22 (2023-03-22)
1090
1086
  * (bluefox) Re-Activate legacy connection
1091
1087
 
1092
- ### 4.0.21 (2023-03-22)
1088
+ ### 4.0.21 (2023-03-22)
1093
1089
  * (bluefox) Added translations
1094
1090
 
1095
- ### 4.0.20 (2023-03-21)
1091
+ ### 4.0.20 (2023-03-21)
1096
1092
  * (bluefox) Color picker was improved
1097
1093
 
1098
- ### 4.0.19 (2023-03-20)
1099
- * (bluefox) Packages were updated
1094
+ ### 4.0.19 (2023-03-20)
1095
+ * (bluefox) Packages were updated
1100
1096
  * (bluefox) Added new translations
1101
1097
 
1102
- ### 4.0.18 (2023-03-16)
1098
+ ### 4.0.18 (2023-03-16)
1103
1099
  * (bluefox) Packages were updated
1104
1100
 
1105
- ### 4.0.17 (2023-03-15)
1106
- * (bluefox) Added translations
1101
+ ### 4.0.17 (2023-03-15)
1102
+ * (bluefox) Added translations
1107
1103
  * (bluefox) Added port controller to JSON config
1108
1104
 
1109
- ### 4.0.15 (2023-03-12)
1105
+ ### 4.0.15 (2023-03-12)
1110
1106
  * (bluefox) Updated the object browser and file browser
1111
1107
 
1112
- ### 4.0.14 (2023-03-03)
1108
+ ### 4.0.14 (2023-03-03)
1113
1109
  * (bluefox) added handler of alert messages
1114
1110
 
1115
- ### 4.0.13 (2023-02-15)
1111
+ ### 4.0.13 (2023-02-15)
1116
1112
  * (bluefox) Corrected the theme button
1117
1113
 
1118
- ### 4.0.12 (2023-02-15)
1114
+ ### 4.0.12 (2023-02-15)
1119
1115
  * (bluefox) made the fix for `echarts`
1120
1116
 
1121
- ### 4.0.11 (2023-02-14)
1122
- * (bluefox) Updated packages
1117
+ ### 4.0.11 (2023-02-14)
1118
+ * (bluefox) Updated packages
1123
1119
  * (bluefox) The `chartReady` event was omitted
1124
1120
 
1125
- ### 4.0.10 (2023-02-10)
1126
- * (bluefox) Updated packages
1121
+ ### 4.0.10 (2023-02-10)
1122
+ * (bluefox) Updated packages
1127
1123
  * (bluefox) made the fix for `material`
1128
1124
 
1129
- ### 4.0.9 (2023-02-02)
1125
+ ### 4.0.9 (2023-02-02)
1130
1126
  * (bluefox) Updated packages
1131
1127
 
1132
- ### 4.0.8 (2022-12-19)
1128
+ ### 4.0.8 (2022-12-19)
1133
1129
  * (bluefox) Extended socket with `log` command
1134
1130
 
1135
- ### 4.0.6 (2022-12-19)
1131
+ ### 4.0.6 (2022-12-19)
1136
1132
  * (bluefox) Corrected URL for the connection
1137
1133
 
1138
- ### 4.0.5 (2022-12-14)
1134
+ ### 4.0.5 (2022-12-14)
1139
1135
  * (bluefox) Added support of custom palette for color picker
1140
1136
 
1141
- ### 4.0.2 (2022-12-01)
1137
+ ### 4.0.2 (2022-12-01)
1142
1138
  * (bluefox) use `@iobroker/socket-client` instead of `Connection.tsx`
1143
1139
 
1144
- ### 3.5.3 (2022-11-30)
1140
+ ### 3.5.3 (2022-11-30)
1145
1141
  * (bluefox) Improved `renderTextWithA` function to support `<b>` and `<i>` tags
1146
1142
 
1147
- ### 3.5.2 (2022-11-30)
1143
+ ### 3.5.2 (2022-11-30)
1148
1144
  * (bluefox) updated json config component
1149
1145
 
1150
- ### 3.4.1 (2022-11-29)
1146
+ ### 3.4.1 (2022-11-29)
1151
1147
  * (bluefox) Added button text for message dialog
1152
1148
 
1153
- ### 3.4.0 (2022-11-29)
1149
+ ### 3.4.0 (2022-11-29)
1154
1150
  * (bluefox) Added file selector
1155
1151
 
1156
- ### 3.3.0 (2022-11-26)
1152
+ ### 3.3.0 (2022-11-26)
1157
1153
  * (bluefox) Added subscribe on files
1158
1154
 
1159
- ### 3.2.7 (2022-11-13)
1155
+ ### 3.2.7 (2022-11-13)
1160
1156
  * (bluefox) Added `fullWidth` property to `Dialog`
1161
1157
 
1162
- ### 3.2.6 (2022-11-08)
1158
+ ### 3.2.6 (2022-11-08)
1163
1159
  * (xXBJXx) Improved TreeTable component
1164
1160
 
1165
- ### 3.2.5 (2022-11-08)
1161
+ ### 3.2.5 (2022-11-08)
1166
1162
  * (bluefox) Added the role filter for the object browser
1167
1163
 
1168
- ### 3.2.4 (2022-11-03)
1164
+ ### 3.2.4 (2022-11-03)
1169
1165
  * (bluefox) Added support for alfa channel for `invertColor`
1170
1166
 
1171
- ### 3.2.3 (2022-10-26)
1167
+ ### 3.2.3 (2022-10-26)
1172
1168
  * (bluefox) Corrected expert mode for object browser
1173
1169
 
1174
- ### 3.2.2 (2022-10-25)
1170
+ ### 3.2.2 (2022-10-25)
1175
1171
  * (bluefox) Added support for prefixes for translations
1176
1172
 
1177
- ### 3.2.1 (2022-10-24)
1173
+ ### 3.2.1 (2022-10-24)
1178
1174
  * (bluefox) Corrected color inversion
1179
1175
 
1180
- ### 3.2.0 (2022-10-19)
1176
+ ### 3.2.0 (2022-10-19)
1181
1177
  * (bluefox) Added ukrainian translation
1182
1178
 
1183
- ### 3.1.35 (2022-10-17)
1179
+ ### 3.1.35 (2022-10-17)
1184
1180
  * (bluefox) small changes for material
1185
1181
 
1186
- ### 3.1.34 (2022-08-24)
1182
+ ### 3.1.34 (2022-08-24)
1187
1183
  * (bluefox) Implemented fallback to english by translations
1188
1184
 
1189
- ### 3.1.33 (2022-08-24)
1185
+ ### 3.1.33 (2022-08-24)
1190
1186
  * (bluefox) Added support for onchange flag
1191
1187
 
1192
- ### 3.1.30 (2022-08-23)
1193
- * (bluefox) Added method `getCompactSystemRepositories`
1188
+ ### 3.1.30 (2022-08-23)
1189
+ * (bluefox) Added method `getCompactSystemRepositories`
1194
1190
  * (bluefox) corrected error in `ObjectBrowser`
1195
1191
 
1196
- ### 3.1.27 (2022-08-01)
1192
+ ### 3.1.27 (2022-08-01)
1197
1193
  * (bluefox) Disable file editing in FileViewer
1198
1194
 
1199
- ### 3.1.26 (2022-08-01)
1200
- * (bluefox) Added translations
1195
+ ### 3.1.26 (2022-08-01)
1196
+ * (bluefox) Added translations
1201
1197
  * (bluefox) JSON schema was extended with missing definitions
1202
1198
 
1203
- ### 3.1.24 (2022-07-28)
1199
+ ### 3.1.24 (2022-07-28)
1204
1200
  * (bluefox) Updated file browser and object browser
1205
1201
 
1206
- ### 3.1.23 (2022-07-25)
1202
+ ### 3.1.23 (2022-07-25)
1207
1203
  * (bluefox) Extend custom filter for object selector
1208
1204
 
1209
- ### 3.1.22 (2022-07-22)
1205
+ ### 3.1.22 (2022-07-22)
1210
1206
  * (bluefox) Added i18n tools for development
1211
1207
 
1212
- ### 3.1.20 (2022-07-14)
1208
+ ### 3.1.20 (2022-07-14)
1213
1209
  * (bluefox) Allowed to show select dialog with the expert mode enabled
1214
1210
 
1215
- ### 3.1.19 (2022-07-08)
1211
+ ### 3.1.19 (2022-07-08)
1216
1212
  * (bluefox) Allowed extending translations for all languages together
1217
1213
 
1218
- ### 3.1.18 (2022-07-06)
1214
+ ### 3.1.18 (2022-07-06)
1219
1215
  * (bluefox) Added translation
1220
1216
 
1221
- ### 3.1.17 (2022-07-05)
1217
+ ### 3.1.17 (2022-07-05)
1222
1218
  * (bluefox) Deactivate JSON editor for JSONConfig because of space
1223
1219
 
1224
- ### 3.1.16 (2022-06-27)
1220
+ ### 3.1.16 (2022-06-27)
1225
1221
  * (bluefox) Update object browser
1226
1222
 
1227
- ### 3.1.15 (2022-06-27)
1223
+ ### 3.1.15 (2022-06-27)
1228
1224
  * (bluefox) Allowed using of spaces in name
1229
1225
 
1230
- ### 3.1.14 (2022-06-23)
1226
+ ### 3.1.14 (2022-06-23)
1231
1227
  * (bluefox) Added translations
1232
1228
 
1233
- ### 3.1.11 (2022-06-22)
1229
+ ### 3.1.11 (2022-06-22)
1234
1230
  * (bluefox) Added preparations for iobroker cloud
1235
1231
 
1236
- ### 3.1.10 (2022-06-22)
1232
+ ### 3.1.10 (2022-06-22)
1237
1233
  * (bluefox) Added translations
1238
1234
 
1239
- ### 3.1.9 (2022-06-20)
1235
+ ### 3.1.9 (2022-06-20)
1240
1236
  * (bluefox) Allowed working behind reverse proxy
1241
1237
 
1242
- ### 3.1.7 (2022-06-19)
1238
+ ### 3.1.7 (2022-06-19)
1243
1239
  * (bluefox) Added file select dialog
1244
1240
 
1245
- ### 3.1.3 (2022-06-13)
1241
+ ### 3.1.3 (2022-06-13)
1246
1242
  * (bluefox) Added table with resized headers
1247
1243
 
1248
- ### 3.1.2 (2022-06-09)
1244
+ ### 3.1.2 (2022-06-09)
1249
1245
  * (bluefox) Added new document icon (read only)
1250
1246
 
1251
- ### 3.1.1 (2022-06-09)
1247
+ ### 3.1.1 (2022-06-09)
1252
1248
  * (bluefox) Allowed working behind reverse proxy
1253
1249
 
1254
- ### 3.1.0 (2022-06-07)
1250
+ ### 3.1.0 (2022-06-07)
1255
1251
  * (bluefox) Some german texts were corrected
1256
1252
 
1257
- ### 3.0.17 (2022-06-03)
1253
+ ### 3.0.17 (2022-06-03)
1258
1254
  * (bluefox) Allowed calling getAdapterInstances not for admin too
1259
1255
 
1260
- ### 3.0.15 (2022-06-01)
1256
+ ### 3.0.15 (2022-06-01)
1261
1257
  * (bluefox) Updated JsonConfigComponent: password, table
1262
1258
 
1263
- ### 3.0.14 (2022-05-25)
1259
+ ### 3.0.14 (2022-05-25)
1264
1260
  * (bluefox) Added ConfigGeneric to import
1265
1261
 
1266
- ### 3.0.7 (2022-05-25)
1262
+ ### 3.0.7 (2022-05-25)
1267
1263
  * (bluefox) Made the module definitions
1268
1264
 
1269
- ### 3.0.6 (2022-05-25)
1265
+ ### 3.0.6 (2022-05-25)
1270
1266
  * (bluefox) Added JsonConfigComponent
1271
1267
 
1272
- ### 2.1.11 (2022-05-24)
1268
+ ### 2.1.11 (2022-05-24)
1273
1269
  * (bluefox) Update file browser. It supports now the file changed events.
1274
1270
 
1275
- ### 2.1.10 (2022-05-24)
1271
+ ### 2.1.10 (2022-05-24)
1276
1272
  * (bluefox) Corrected object browser
1277
1273
 
1278
- ### 2.1.9 (2022-05-16)
1274
+ ### 2.1.9 (2022-05-16)
1279
1275
  * (bluefox) Corrected expert mode in object browser
1280
1276
 
1281
- ### 2.1.7 (2022-05-09)
1282
- * (bluefox) Changes were synchronized with adapter-react-v5
1277
+ ### 2.1.7 (2022-05-09)
1278
+ * (bluefox) Changes were synchronized with adapter-react-v5
1283
1279
  * (bluefox) Added `I18n.disableWarning` method
1284
1280
 
1285
- ### 2.1.6 (2022-03-28)
1286
- * (bluefox) Added `log` method to connection
1281
+ ### 2.1.6 (2022-03-28)
1282
+ * (bluefox) Added `log` method to connection
1287
1283
  * (bluefox) Corrected translations
1288
1284
 
1289
- ### 2.1.1 (2022-03-27)
1285
+ ### 2.1.1 (2022-03-27)
1290
1286
  * (bluefox) Corrected error in TreeTable
1291
1287
 
1292
- ### 2.1.0 (2022-03-26)
1288
+ ### 2.1.0 (2022-03-26)
1293
1289
  * (bluefox) BREAKING_CHANGE: Corrected error with readFile(base64=false)
1294
1290
 
1295
- ### 2.0.0 (2022-03-26)
1291
+ ### 2.0.0 (2022-03-26)
1296
1292
  * (bluefox) Initial version
1297
1293
 
1298
- ### 0.1.0 (2022-03-23)
1294
+ ### 0.1.0 (2022-03-23)
1299
1295
  * (bluefox) Fixed theme errors
1300
1296
 
1301
- ### 0.0.4 (2022-03-22)
1297
+ ### 0.0.4 (2022-03-22)
1302
1298
  * (bluefox) Fixed eslint warnings
1303
1299
 
1304
- ### 0.0.3 (2022-03-19)
1300
+ ### 0.0.3 (2022-03-19)
1305
1301
  * (bluefox) beta version
1306
1302
 
1307
- ### 0.0.2 (2022-02-24)
1303
+ ### 0.0.2 (2022-02-24)
1308
1304
  * (bluefox) try to publish a first version
1309
1305
 
1310
- ### 0.0.1 (2022-02-24)
1306
+ ### 0.0.1 (2022-02-24)
1311
1307
  * initial commit
1312
1308
 
1313
- ## License
1314
- The MIT License (MIT)
1315
-
1316
- Copyright (c) 2019-2024 bluefox <dogafox@gmail.com>
1317
-
1318
- Permission is hereby granted, free of charge, to any person obtaining a copy
1319
- of this software and associated documentation files (the "Software"), to deal
1320
- in the Software without restriction, including without limitation the rights
1321
- to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
1322
- copies of the Software, and to permit persons to whom the Software is
1323
- furnished to do so, subject to the following conditions:
1324
-
1325
- The above copyright notice and this permission notice shall be included in all
1326
- copies or substantial portions of the Software.
1327
-
1328
- THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
1329
- IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
1330
- FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
1331
- AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
1332
- LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
1333
- OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
1309
+ ## License
1310
+ The MIT License (MIT)
1311
+
1312
+ Copyright (c) 2019-2024 bluefox <dogafox@gmail.com>
1313
+
1314
+ Permission is hereby granted, free of charge, to any person obtaining a copy
1315
+ of this software and associated documentation files (the "Software"), to deal
1316
+ in the Software without restriction, including without limitation the rights
1317
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
1318
+ copies of the Software, and to permit persons to whom the Software is
1319
+ furnished to do so, subject to the following conditions:
1320
+
1321
+ The above copyright notice and this permission notice shall be included in all
1322
+ copies or substantial portions of the Software.
1323
+
1324
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
1325
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
1326
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
1327
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
1328
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
1329
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
1334
1330
  SOFTWARE.