matterbridge-roborock-vacuum-plugin 1.0.8-rc04 → 1.0.8-rc06

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 (68) hide show
  1. package/README.md +5 -1
  2. package/README_CLEANMODE.md +29 -0
  3. package/dist/behaviorFactory.js +11 -15
  4. package/dist/behaviors/roborock.vacuum/default/default.js +108 -57
  5. package/dist/behaviors/roborock.vacuum/default/initalData.js +69 -8
  6. package/dist/behaviors/roborock.vacuum/default/runtimes.js +18 -30
  7. package/dist/behaviors/roborock.vacuum/smart/initalData.js +18 -0
  8. package/dist/behaviors/roborock.vacuum/smart/runtimes.js +11 -0
  9. package/dist/behaviors/roborock.vacuum/smart/smart.js +119 -0
  10. package/dist/initialData/getOperationalStates.js +2 -12
  11. package/dist/initialData/getSupportedCleanModes.js +8 -5
  12. package/dist/initialData/getSupportedRunModes.js +5 -15
  13. package/dist/model/DockingStationStatus.js +1 -2
  14. package/dist/platform.js +10 -4
  15. package/dist/platformRunner.js +36 -22
  16. package/dist/roborockCommunication/Zmodel/deviceStatus.js +2 -2
  17. package/dist/roborockCommunication/broadcast/client/MQTTClient.js +1 -2
  18. package/dist/roborockCommunication/broadcast/messageProcessor.js +36 -0
  19. package/dist/roborockService.js +11 -1
  20. package/dist/rvc.js +8 -5
  21. package/dist/share/runtimeHelper.js +11 -44
  22. package/eslint.config.js +1 -1
  23. package/matterbridge-roborock-vacuum-plugin.config.json +4 -3
  24. package/matterbridge-roborock-vacuum-plugin.schema.json +15 -37
  25. package/package.json +2 -1
  26. package/src/behaviorFactory.ts +14 -18
  27. package/src/behaviors/roborock.vacuum/default/default.ts +123 -60
  28. package/src/behaviors/roborock.vacuum/default/initalData.ts +73 -8
  29. package/src/behaviors/roborock.vacuum/default/runtimes.ts +19 -22
  30. package/src/behaviors/roborock.vacuum/smart/initalData.ts +19 -0
  31. package/src/behaviors/roborock.vacuum/smart/runtimes.ts +14 -0
  32. package/src/behaviors/roborock.vacuum/smart/smart.ts +159 -0
  33. package/src/initialData/getOperationalStates.ts +2 -12
  34. package/src/initialData/getSupportedCleanModes.ts +10 -5
  35. package/src/initialData/getSupportedRunModes.ts +5 -15
  36. package/src/model/DockingStationStatus.ts +2 -2
  37. package/src/model/ExperimentalFeatureSetting.ts +1 -0
  38. package/src/platform.ts +20 -4
  39. package/src/platformRunner.ts +47 -24
  40. package/src/roborockCommunication/Zmodel/deviceStatus.ts +4 -4
  41. package/src/roborockCommunication/broadcast/client/MQTTClient.ts +2 -2
  42. package/src/roborockCommunication/broadcast/messageProcessor.ts +41 -1
  43. package/src/roborockService.ts +12 -1
  44. package/src/rvc.ts +10 -5
  45. package/src/share/runtimeHelper.ts +12 -46
  46. package/src/tests/behaviors/roborock.vacuum/{S7_MAXV/a27.test.ts → default/default.test.ts} +26 -26
  47. package/src/tests/behaviors/roborock.vacuum/smart/runtimes.test.ts +64 -0
  48. package/src/tests/behaviors/roborock.vacuum/{QREVO_EDGE_5V1/a187.test.ts → smart/smart.test.ts} +51 -38
  49. package/src/tests/model/DockingStationStatus.test.ts +1 -1
  50. package/dist/behaviors/roborock.vacuum/QREVO_EDGE_5V1/a187.js +0 -142
  51. package/dist/behaviors/roborock.vacuum/QREVO_EDGE_5V1/initalData.js +0 -81
  52. package/dist/behaviors/roborock.vacuum/QREVO_EDGE_5V1/runtimes.js +0 -39
  53. package/dist/behaviors/roborock.vacuum/S7_MAXV/a27.js +0 -133
  54. package/dist/behaviors/roborock.vacuum/S7_MAXV/initalData.js +0 -76
  55. package/dist/behaviors/roborock.vacuum/S7_MAXV/runtimes.js +0 -33
  56. package/dist/behaviors/roborock.vacuum/S8_PRO_ULTRA/a51.js +0 -132
  57. package/dist/behaviors/roborock.vacuum/S8_PRO_ULTRA/initalData.js +0 -76
  58. package/dist/behaviors/roborock.vacuum/S8_PRO_ULTRA/runtimes.js +0 -33
  59. package/src/behaviors/roborock.vacuum/QREVO_EDGE_5V1/a187.ts +0 -181
  60. package/src/behaviors/roborock.vacuum/QREVO_EDGE_5V1/initalData.ts +0 -85
  61. package/src/behaviors/roborock.vacuum/QREVO_EDGE_5V1/runtimes.ts +0 -29
  62. package/src/behaviors/roborock.vacuum/S7_MAXV/a27.ts +0 -172
  63. package/src/behaviors/roborock.vacuum/S7_MAXV/initalData.ts +0 -79
  64. package/src/behaviors/roborock.vacuum/S7_MAXV/runtimes.ts +0 -26
  65. package/src/behaviors/roborock.vacuum/S8_PRO_ULTRA/a51.ts +0 -171
  66. package/src/behaviors/roborock.vacuum/S8_PRO_ULTRA/initalData.ts +0 -79
  67. package/src/behaviors/roborock.vacuum/S8_PRO_ULTRA/runtimes.ts +0 -26
  68. package/src/tests/behaviors/roborock.vacuum/QREVO_EDGE_5V1/runtimes.test.ts +0 -83
package/README.md CHANGED
@@ -40,7 +40,7 @@
40
40
  - **Matterbridge must be run in child bridge mode** for proper operation.
41
41
  - **Use one Matterbridge instance per Roborock vacuum.**
42
42
  If you have more than one vacuum, please run separate instances.
43
- Please put the **duid** of device you want to use into **whiteList** section in the plugin configuration popup.
43
+ Please put the <**Vacuum name**>-<**duid**> of device you want to use into **whiteList** section in the plugin configuration popup.
44
44
 
45
45
 
46
46
  More details available here: [Discussion #264](https://github.com/Luligu/matterbridge/discussions/264)
@@ -76,6 +76,10 @@ To get the **DUID** for your devices, you have two options:
76
76
 
77
77
  **➡️ [See Supported & Tested Roborock Devices](./README_SUPPORTED.md)**
78
78
 
79
+ > 📋 **Apple Home ↔️ Roborock Clean Mode Mapping:**
80
+ > For a detailed table of how Apple Home clean modes map to Roborock settings, see
81
+ > 👉 [Apple Home ↔️ Roborock Clean Mode Mapping](./README_CLEANMODE.md)
82
+
79
83
  ### 📦 Prerequisites
80
84
 
81
85
  - A working installation of [Matterbridge](https://github.com/Luligu/matterbridge)
@@ -0,0 +1,29 @@
1
+ # Apple Home RVC Clean Mode Mapping to Roborock Clean Setting
2
+
3
+ This table shows the mapping between **Apple Home RVC Clean Modes** and the corresponding **Roborock Clean Settings** as defined in `smart.ts` and `default.ts`.
4
+
5
+ | Apple Home RVC Clean Mode (Key) | Apple Home Mode Name | Roborock Clean Mode | suctionPower (enum value) | waterFlow (enum value) | distance_off | mopRoute (enum value) |
6
+ |:-------------------------------:|:-----------------------------|:--------------------|:--------------------------|:----------------------|:------------:|:---------------------:|
7
+ | 4 *(smart only)* | Mop & Vacuum: Automatic | Smart Plan | 0 | 0 | 0 | Smart (306) |
8
+ | 5 | Mop & Vacuum: Day (Automatic)| Vac & Mop | Balanced (102) | Medium (202) | 0 | Standard (300) |
9
+ | 6 | Mop & Vacuum: Quick | Vac & Mop | Balanced (102) | Medium (202) | 0 | Fast (304) |
10
+ | 7 | Mop & Vacuum: Max | Vac & Mop | Max (104) | Medium (202) | 0 | Standard (300) |
11
+ | 8 | Mop & Vacuum: Min | Vac & Mop | Balanced (102) | Low (201) | 0 | Standard (300) |
12
+ | 9 | Mop & Vacuum: Quiet | Vac & Mop | Quiet (101) | Medium (202) | 0 | Standard (300) |
13
+ | 10 | Mop & Vacuum: LowEnergy | Custom | Custom (106) | Custom (204) | 0 | Custom (302) |
14
+ | 31 | Mop: Default | Mop | Off (105) | Medium (202) | 0 | Standard (300) |
15
+ | 32 | Mop: Max | Mop | Off (105) | High (203) | 0 | Standard (300) |
16
+ | 33 | Mop: Min | Mop | Off (105) | Low (201) | 0 | Standard (300) |
17
+ | 34 | Mop: Quick | Mop | Off (105) | Medium (202) | 0 | Fast (304) |
18
+ | 35 | Mop: DeepClean | Mop | Off (105) | Medium (202) | 0 | Deep (301) |
19
+ | 66 | Vacuum: Default | Vacuum | Balanced (102) | Off (200) | 0 | Standard (300) |
20
+ | 67 | Vacuum: Max | Vacuum | Max (104) | Off (200) | 0 | Standard (300) |
21
+ | 68 | Vacuum: Quiet | Vacuum | Quiet (101) | Off (200) | 0 | Standard (300) |
22
+ | 69 | Vacuum: Quick | Vacuum | Balanced (102) | Off (200) | 0 | Fast (304) |
23
+ | 99 | Mop & Vacuum: Vacation | | | | | |
24
+
25
+ **Notes:**
26
+ - The values in parentheses are enum values from `VacuumSuctionPowerSmart`/`VacuumSuctionPower`, `MopWaterFlowSmart`/`MopWaterFlow`, and `MopRouteSmart`/`MopRoute` in `smart.ts` and `default.ts`.
27
+ - Key 4 ("Smart Plan") is only available on some new vacuums.
28
+ - This mapping helps you understand how Apple Home clean modes correspond to Roborock's internal cleaning settings for both "smart" and "default" behaviors.
29
+ - Key 99 is a tricky mode to support go to charge in Apple Home Automation
@@ -1,26 +1,22 @@
1
1
  import { BehaviorDeviceGeneric } from './behaviors/BehaviorDeviceGeneric.js';
2
- import { setCommandHandlerA187 } from './behaviors/roborock.vacuum/QREVO_EDGE_5V1/a187.js';
3
2
  import { setDefaultCommandHandler } from './behaviors/roborock.vacuum/default/default.js';
4
3
  import { DeviceModel } from './roborockCommunication/Zmodel/deviceModel.js';
5
- import { setCommandHandlerA27 } from './behaviors/roborock.vacuum/S7_MAXV/a27.js';
6
- import { setCommandHandlerA51 } from './behaviors/roborock.vacuum/S8_PRO_ULTRA/a51.js';
7
- export function configurateBehavior(model, duid, roborockService, cleanModeSettings, logger) {
4
+ import { setCommandHandlerSmart } from './behaviors/roborock.vacuum/smart/smart.js';
5
+ export function configurateBehavior(model, duid, roborockService, cleanModeSettings, forceRunAtDefault, logger) {
6
+ if (forceRunAtDefault) {
7
+ const deviceHandler = new BehaviorDeviceGeneric(logger);
8
+ setDefaultCommandHandler(duid, deviceHandler, logger, roborockService, cleanModeSettings);
9
+ return deviceHandler;
10
+ }
8
11
  switch (model) {
9
12
  case DeviceModel.QREVO_EDGE_5V1: {
10
13
  const deviceHandler = new BehaviorDeviceGeneric(logger);
11
- setCommandHandlerA187(duid, deviceHandler, logger, roborockService, cleanModeSettings);
12
- return deviceHandler;
13
- }
14
- case DeviceModel.S7_MAXV: {
15
- const deviceHandler = new BehaviorDeviceGeneric(logger);
16
- setCommandHandlerA27(duid, deviceHandler, logger, roborockService, cleanModeSettings);
17
- return deviceHandler;
18
- }
19
- case DeviceModel.S8_PRO_ULTRA: {
20
- const deviceHandler = new BehaviorDeviceGeneric(logger);
21
- setCommandHandlerA51(duid, deviceHandler, logger, roborockService, cleanModeSettings);
14
+ setCommandHandlerSmart(duid, deviceHandler, logger, roborockService, cleanModeSettings);
22
15
  return deviceHandler;
23
16
  }
17
+ case DeviceModel.S7_MAXV:
18
+ case DeviceModel.S8_PRO_ULTRA:
19
+ case DeviceModel.S6_PURE:
24
20
  default: {
25
21
  const deviceHandler = new BehaviorDeviceGeneric(logger);
26
22
  setDefaultCommandHandler(duid, deviceHandler, logger, roborockService, cleanModeSettings);
@@ -19,6 +19,7 @@ export var MopWaterFlow;
19
19
  MopWaterFlow[MopWaterFlow["Medium"] = 202] = "Medium";
20
20
  MopWaterFlow[MopWaterFlow["High"] = 203] = "High";
21
21
  MopWaterFlow[MopWaterFlow["Custom"] = 204] = "Custom";
22
+ MopWaterFlow[MopWaterFlow["CustomizeWithDistanceOff"] = 207] = "CustomizeWithDistanceOff";
22
23
  })(MopWaterFlow || (MopWaterFlow = {}));
23
24
  export var MopRoute;
24
25
  (function (MopRoute) {
@@ -28,50 +29,98 @@ export var MopRoute;
28
29
  MopRoute[MopRoute["DeepPlus"] = 303] = "DeepPlus";
29
30
  MopRoute[MopRoute["Fast"] = 304] = "Fast";
30
31
  })(MopRoute || (MopRoute = {}));
31
- const RvcRunMode = {
32
+ export const RvcRunMode = {
32
33
  [1]: 'Idle',
33
34
  [2]: 'Cleaning',
34
35
  [3]: 'Mapping',
35
36
  };
36
- const RvcCleanMode = {
37
- [5]: 'Mop',
38
- [6]: 'Vacuum',
39
- [7]: 'Vac & Mop',
40
- [8]: 'Custom',
37
+ export const RvcCleanMode = {
38
+ [5]: 'Mop & Vacuum: Default',
39
+ [6]: 'Mop & Vacuum: Quick',
40
+ [7]: 'Mop & Vacuum: Max',
41
+ [8]: 'Mop & Vacuum: Min',
42
+ [9]: 'Mop & Vacuum: Quiet',
43
+ [10]: 'Mop & Vacuum: Custom',
44
+ [31]: 'Mop: Default',
45
+ [32]: 'Mop: Max',
46
+ [33]: 'Mop: Min',
47
+ [34]: 'Mop: Quick',
48
+ [35]: 'Mop: DeepClean',
49
+ [66]: 'Vacuum: Default',
50
+ [67]: 'Vacuum: Max',
51
+ [68]: 'Vacuum: Quiet',
52
+ [69]: 'Vacuum: Quick',
53
+ [99]: 'Go Vacation',
41
54
  };
42
- const CleanSetting = {
43
- [5]: { suctionPower: VacuumSuctionPower.Off, waterFlow: MopWaterFlow.Medium, distance_off: 0, mopRoute: MopRoute.Standard },
44
- [6]: { suctionPower: VacuumSuctionPower.Balanced, waterFlow: MopWaterFlow.Off, distance_off: 0, mopRoute: MopRoute.Standard },
45
- [7]: { suctionPower: VacuumSuctionPower.Balanced, waterFlow: MopWaterFlow.Medium, distance_off: 0, mopRoute: MopRoute.Standard },
46
- [8]: { suctionPower: VacuumSuctionPower.Custom, waterFlow: MopWaterFlow.Custom, distance_off: 0, mopRoute: MopRoute.Custom },
55
+ export const CleanSetting = {
56
+ [5]: { suctionPower: VacuumSuctionPower.Balanced, waterFlow: MopWaterFlow.Medium, distance_off: 0, mopRoute: MopRoute.Standard },
57
+ [6]: { suctionPower: VacuumSuctionPower.Balanced, waterFlow: MopWaterFlow.Medium, distance_off: 0, mopRoute: MopRoute.Fast },
58
+ [7]: { suctionPower: VacuumSuctionPower.Max, waterFlow: MopWaterFlow.Medium, distance_off: 0, mopRoute: MopRoute.Standard },
59
+ [8]: { suctionPower: VacuumSuctionPower.Balanced, waterFlow: MopWaterFlow.Low, distance_off: 0, mopRoute: MopRoute.Standard },
60
+ [9]: { suctionPower: VacuumSuctionPower.Quiet, waterFlow: MopWaterFlow.Medium, distance_off: 0, mopRoute: MopRoute.Standard },
61
+ [10]: { suctionPower: VacuumSuctionPower.Custom, waterFlow: MopWaterFlow.Custom, distance_off: 0, mopRoute: MopRoute.Custom },
62
+ [31]: { suctionPower: VacuumSuctionPower.Off, waterFlow: MopWaterFlow.Medium, distance_off: 0, mopRoute: MopRoute.Standard },
63
+ [32]: { suctionPower: VacuumSuctionPower.Off, waterFlow: MopWaterFlow.High, distance_off: 0, mopRoute: MopRoute.Standard },
64
+ [33]: { suctionPower: VacuumSuctionPower.Off, waterFlow: MopWaterFlow.Low, distance_off: 0, mopRoute: MopRoute.Standard },
65
+ [34]: { suctionPower: VacuumSuctionPower.Off, waterFlow: MopWaterFlow.Medium, distance_off: 0, mopRoute: MopRoute.Fast },
66
+ [35]: { suctionPower: VacuumSuctionPower.Off, waterFlow: MopWaterFlow.Medium, distance_off: 0, mopRoute: MopRoute.Deep },
67
+ [66]: { suctionPower: VacuumSuctionPower.Balanced, waterFlow: MopWaterFlow.Off, distance_off: 0, mopRoute: MopRoute.Standard },
68
+ [67]: { suctionPower: VacuumSuctionPower.Max, waterFlow: MopWaterFlow.Off, distance_off: 0, mopRoute: MopRoute.Standard },
69
+ [68]: { suctionPower: VacuumSuctionPower.Quiet, waterFlow: MopWaterFlow.Off, distance_off: 0, mopRoute: MopRoute.Standard },
70
+ [69]: { suctionPower: VacuumSuctionPower.Balanced, waterFlow: MopWaterFlow.Off, distance_off: 0, mopRoute: MopRoute.Fast },
47
71
  };
48
72
  export function setDefaultCommandHandler(duid, handler, logger, roborockService, cleanModeSettings) {
49
73
  handler.setCommandHandler('changeToMode', async (newMode) => {
50
74
  const activity = RvcRunMode[newMode] || RvcCleanMode[newMode];
51
75
  switch (activity) {
52
76
  case 'Cleaning': {
77
+ logger.notice('DefaultBehavior-ChangeRunMode to: ', activity);
53
78
  await roborockService.startClean(duid);
54
- return;
79
+ break;
55
80
  }
56
- case 'Mop':
57
- case 'Vacuum':
58
- case 'Vac & Mop': {
59
- const setting = cleanModeSettings ? getSettingFromCleanMode(activity, cleanModeSettings) : CleanSetting[newMode];
81
+ case 'Go Vacation': {
82
+ logger.notice('DefaultBehavior-GoHome');
83
+ await roborockService.stopAndGoHome(duid);
84
+ break;
85
+ }
86
+ case 'Mop & Vacuum: Custom': {
87
+ const setting = CleanSetting[newMode];
88
+ logger.notice(`DefaultBehavior-ChangeCleanMode to: ${activity}, setting: ${debugStringify(setting)}`);
89
+ await roborockService.changeCleanMode(duid, setting);
90
+ break;
91
+ }
92
+ case 'Mop & Vacuum: Default':
93
+ case 'Mop: Default':
94
+ case 'Vacuum: Default': {
95
+ const setting = cleanModeSettings ? (getSettingFromCleanMode(activity, cleanModeSettings) ?? CleanSetting[newMode]) : CleanSetting[newMode];
60
96
  logger.notice(`DefaultBehavior-ChangeCleanMode to: ${activity}, setting: ${debugStringify(setting ?? {})}`);
61
97
  if (setting) {
62
98
  await roborockService.changeCleanMode(duid, setting);
63
99
  }
64
- return;
100
+ break;
65
101
  }
66
- case 'Custom': {
102
+ case 'Mop & Vacuum: Quick':
103
+ case 'Mop & Vacuum: Max':
104
+ case 'Mop & Vacuum: Min':
105
+ case 'Mop & Vacuum: Quiet':
106
+ case 'Mop: Max':
107
+ case 'Mop: Min':
108
+ case 'Mop: Quick':
109
+ case 'Mop: DeepClean':
110
+ case 'Vacuum: Max':
111
+ case 'Vacuum: Min':
112
+ case 'Vacuum: Quiet':
113
+ case 'Vacuum: Quick': {
67
114
  const setting = CleanSetting[newMode];
68
- logger.notice(`DefaultBehavior-ChangeCleanMode to: ${activity}, setting: ${debugStringify(setting)}`);
69
- await roborockService.changeCleanMode(duid, setting);
70
- return;
115
+ logger.notice(`DefaultBehavior-ChangeCleanMode to: ${activity}, setting: ${debugStringify(setting ?? {})}`);
116
+ if (setting) {
117
+ await roborockService.changeCleanMode(duid, setting);
118
+ }
119
+ break;
71
120
  }
72
121
  default:
73
122
  logger.notice('DefaultBehavior-changeToMode-Unknown: ', newMode);
74
- return;
123
+ break;
75
124
  }
76
125
  });
77
126
  handler.setCommandHandler('selectAreas', async (newAreas) => {
@@ -94,39 +143,41 @@ export function setDefaultCommandHandler(duid, handler, logger, roborockService,
94
143
  logger.notice('DefaultBehavior-playSoundToLocate');
95
144
  await roborockService.playSoundToLocate(duid);
96
145
  });
97
- const getSettingFromCleanMode = (activity, cleanModeSettings) => {
98
- switch (activity) {
99
- case 'Mop': {
100
- const mopSetting = cleanModeSettings?.mopping;
101
- const waterFlow = MopWaterFlow[mopSetting?.waterFlowMode] ?? MopWaterFlow.Medium;
102
- return {
103
- suctionPower: VacuumSuctionPower.Off,
104
- waterFlow,
105
- distance_off: 0,
106
- mopRoute: MopRoute[mopSetting?.mopRouteMode] ?? MopRoute.Standard,
107
- };
108
- }
109
- case 'Vacuum': {
110
- const vacuumSetting = cleanModeSettings?.vacuuming;
111
- return {
112
- suctionPower: VacuumSuctionPower[vacuumSetting?.fanMode] ?? VacuumSuctionPower.Balanced,
113
- waterFlow: MopWaterFlow.Off,
114
- distance_off: 0,
115
- mopRoute: MopRoute[vacuumSetting?.mopRouteMode] ?? MopRoute.Standard,
116
- };
117
- }
118
- case 'Vac & Mop': {
119
- const vacmopSetting = cleanModeSettings?.vacmop;
120
- const waterFlow = MopWaterFlow[vacmopSetting?.waterFlowMode] ?? MopWaterFlow.Medium;
121
- return {
122
- suctionPower: VacuumSuctionPower[vacmopSetting?.fanMode] ?? VacuumSuctionPower.Balanced,
123
- waterFlow,
124
- distance_off: 0,
125
- mopRoute: MopRoute[vacmopSetting?.mopRouteMode] ?? MopRoute.Standard,
126
- };
127
- }
128
- default:
129
- return undefined;
130
- }
131
- };
132
146
  }
147
+ export const getSettingFromCleanMode = (activity, cleanModeSettings) => {
148
+ switch (activity) {
149
+ case 'Mop: Default': {
150
+ const mopSetting = cleanModeSettings?.mopping;
151
+ const waterFlow = MopWaterFlow[mopSetting?.waterFlowMode] ?? MopWaterFlow.Medium;
152
+ const distance_off = waterFlow == MopWaterFlow.CustomizeWithDistanceOff ? 210 - 5 * (mopSetting?.distanceOff ?? 25) : 0;
153
+ return {
154
+ suctionPower: VacuumSuctionPower.Off,
155
+ waterFlow,
156
+ distance_off,
157
+ mopRoute: MopRoute[mopSetting?.mopRouteMode] ?? MopRoute.Standard,
158
+ };
159
+ }
160
+ case 'Vacuum: Default': {
161
+ const vacuumSetting = cleanModeSettings?.vacuuming;
162
+ return {
163
+ suctionPower: VacuumSuctionPower[vacuumSetting?.fanMode] ?? VacuumSuctionPower.Balanced,
164
+ waterFlow: MopWaterFlow.Off,
165
+ distance_off: 0,
166
+ mopRoute: MopRoute[vacuumSetting?.mopRouteMode] ?? MopRoute.Standard,
167
+ };
168
+ }
169
+ case 'Mop & Vacuum: Default': {
170
+ const vacmopSetting = cleanModeSettings?.vacmop;
171
+ const waterFlow = MopWaterFlow[vacmopSetting?.waterFlowMode] ?? MopWaterFlow.Medium;
172
+ const distance_off = waterFlow == MopWaterFlow.CustomizeWithDistanceOff ? 210 - 5 * (vacmopSetting?.distanceOff ?? 25) : 0;
173
+ return {
174
+ suctionPower: VacuumSuctionPower[vacmopSetting?.fanMode] ?? VacuumSuctionPower.Balanced,
175
+ waterFlow,
176
+ distance_off,
177
+ mopRoute: MopRoute[vacmopSetting?.mopRouteMode] ?? MopRoute.Standard,
178
+ };
179
+ }
180
+ default:
181
+ return undefined;
182
+ }
183
+ };
@@ -1,4 +1,5 @@
1
1
  import { RvcCleanMode, RvcOperationalState, RvcRunMode } from 'matterbridge/matter/clusters';
2
+ import { RvcCleanMode as RvcCleanModeDisplayMap } from './default.js';
2
3
  export function getDefaultSupportedRunModes() {
3
4
  return [
4
5
  {
@@ -21,24 +22,84 @@ export function getDefaultSupportedRunModes() {
21
22
  export function getDefaultSupportedCleanModes() {
22
23
  return [
23
24
  {
24
- label: 'Mop',
25
+ label: RvcCleanModeDisplayMap[5],
25
26
  mode: 5,
26
- modeTags: [{ value: RvcCleanMode.ModeTag.Mop }, { value: RvcCleanMode.ModeTag.Auto }],
27
+ modeTags: [{ value: RvcCleanMode.ModeTag.Mop }, { value: RvcCleanMode.ModeTag.Vacuum }, { value: RvcCleanMode.ModeTag.Auto }],
27
28
  },
28
29
  {
29
- label: 'Vacuum',
30
+ label: RvcCleanModeDisplayMap[6],
30
31
  mode: 6,
31
- modeTags: [{ value: RvcCleanMode.ModeTag.Vacuum }, { value: RvcCleanMode.ModeTag.Auto }],
32
+ modeTags: [{ value: RvcCleanMode.ModeTag.Mop }, { value: RvcCleanMode.ModeTag.Vacuum }, { value: RvcCleanMode.ModeTag.Quick }],
32
33
  },
33
34
  {
34
- label: 'Mop & Vacuum',
35
+ label: RvcCleanModeDisplayMap[7],
35
36
  mode: 7,
36
- modeTags: [{ value: RvcCleanMode.ModeTag.Mop }, { value: RvcCleanMode.ModeTag.Vacuum }, { value: RvcCleanMode.ModeTag.DeepClean }],
37
+ modeTags: [{ value: RvcCleanMode.ModeTag.Mop }, { value: RvcCleanMode.ModeTag.Vacuum }, { value: RvcCleanMode.ModeTag.Max }],
37
38
  },
38
39
  {
39
- label: 'Custom',
40
+ label: RvcCleanModeDisplayMap[8],
40
41
  mode: 8,
41
- modeTags: [{ value: RvcCleanMode.ModeTag.Mop }, { value: RvcCleanMode.ModeTag.Vacuum }, { value: RvcCleanMode.ModeTag.Quick }],
42
+ modeTags: [{ value: RvcCleanMode.ModeTag.Mop }, { value: RvcCleanMode.ModeTag.Vacuum }, { value: RvcCleanMode.ModeTag.Min }],
43
+ },
44
+ {
45
+ label: RvcCleanModeDisplayMap[9],
46
+ mode: 9,
47
+ modeTags: [{ value: RvcCleanMode.ModeTag.Mop }, { value: RvcCleanMode.ModeTag.Vacuum }, { value: RvcCleanMode.ModeTag.Quiet }],
48
+ },
49
+ {
50
+ label: RvcCleanModeDisplayMap[10],
51
+ mode: 10,
52
+ modeTags: [{ value: RvcCleanMode.ModeTag.Mop }, { value: RvcCleanMode.ModeTag.Vacuum }, { value: RvcCleanMode.ModeTag.LowEnergy }],
53
+ },
54
+ {
55
+ label: RvcCleanModeDisplayMap[31],
56
+ mode: 31,
57
+ modeTags: [{ value: RvcCleanMode.ModeTag.Mop }, { value: RvcCleanMode.ModeTag.Auto }],
58
+ },
59
+ {
60
+ label: RvcCleanModeDisplayMap[32],
61
+ mode: 32,
62
+ modeTags: [{ value: RvcCleanMode.ModeTag.Mop }, { value: RvcCleanMode.ModeTag.Max }],
63
+ },
64
+ {
65
+ label: RvcCleanModeDisplayMap[33],
66
+ mode: 33,
67
+ modeTags: [{ value: RvcCleanMode.ModeTag.Mop }, { value: RvcCleanMode.ModeTag.Min }],
68
+ },
69
+ {
70
+ label: RvcCleanModeDisplayMap[34],
71
+ mode: 34,
72
+ modeTags: [{ value: RvcCleanMode.ModeTag.Mop }, { value: RvcCleanMode.ModeTag.Quick }],
73
+ },
74
+ {
75
+ label: RvcCleanModeDisplayMap[35],
76
+ mode: 35,
77
+ modeTags: [{ value: RvcCleanMode.ModeTag.Mop }, { value: RvcCleanMode.ModeTag.DeepClean }],
78
+ },
79
+ {
80
+ label: RvcCleanModeDisplayMap[66],
81
+ mode: 66,
82
+ modeTags: [{ value: RvcCleanMode.ModeTag.Vacuum }, { value: RvcCleanMode.ModeTag.Auto }],
83
+ },
84
+ {
85
+ label: RvcCleanModeDisplayMap[67],
86
+ mode: 67,
87
+ modeTags: [{ value: RvcCleanMode.ModeTag.Vacuum }, { value: RvcCleanMode.ModeTag.Max }],
88
+ },
89
+ {
90
+ label: RvcCleanModeDisplayMap[68],
91
+ mode: 68,
92
+ modeTags: [{ value: RvcCleanMode.ModeTag.Vacuum }, { value: RvcCleanMode.ModeTag.Quiet }],
93
+ },
94
+ {
95
+ label: RvcCleanModeDisplayMap[69],
96
+ mode: 69,
97
+ modeTags: [{ value: RvcCleanMode.ModeTag.Vacuum }, { value: RvcCleanMode.ModeTag.Quick }],
98
+ },
99
+ {
100
+ label: RvcCleanModeDisplayMap[99],
101
+ mode: 99,
102
+ modeTags: [{ value: RvcCleanMode.ModeTag.Mop }, { value: RvcCleanMode.ModeTag.Vacuum }, { value: RvcCleanMode.ModeTag.Vacation }],
42
103
  },
43
104
  ];
44
105
  }
@@ -1,33 +1,21 @@
1
- import { MopWaterFlow, VacuumSuctionPower } from './default.js';
2
- export function getCurrentCleanModeDefault(fan_power, water_box_mode) {
3
- if (!fan_power || !water_box_mode)
1
+ import { CleanSetting, MopRoute, MopWaterFlow, VacuumSuctionPower } from './default.js';
2
+ export function getCurrentCleanModeDefault(setting) {
3
+ if (!setting || typeof setting !== 'object') {
4
4
  return undefined;
5
- if (fan_power == VacuumSuctionPower.Custom || water_box_mode == MopWaterFlow.Custom)
6
- return 8;
7
- if (fan_power == VacuumSuctionPower.Off)
5
+ }
6
+ if (setting.suctionPower === VacuumSuctionPower.Custom || setting.waterFlow === MopWaterFlow.Custom || setting.mopRoute === MopRoute.Custom) {
7
+ return 10;
8
+ }
9
+ for (const [key, value] of Object.entries(CleanSetting)) {
10
+ if (value.suctionPower === setting.suctionPower && value.waterFlow === setting.waterFlow && value.mopRoute === setting.mopRoute) {
11
+ return Number(key);
12
+ }
13
+ }
14
+ if (setting.suctionPower == VacuumSuctionPower.Off)
15
+ return 31;
16
+ if (setting.waterFlow == MopWaterFlow.Off)
17
+ return 66;
18
+ if ((setting.suctionPower !== VacuumSuctionPower.Off && setting.waterFlow) !== MopWaterFlow.Off)
8
19
  return 5;
9
- if (water_box_mode == MopWaterFlow.Off)
10
- return 6;
11
- else
12
- return 7;
13
- }
14
- export function getCurrentCleanModeFromFanPowerDefault(fan_power) {
15
- if (!fan_power)
16
- return undefined;
17
- if (fan_power == VacuumSuctionPower.Custom)
18
- return 8;
19
- if (fan_power == VacuumSuctionPower.Off)
20
- return 5;
21
- else
22
- return undefined;
23
- }
24
- export function getCurrentCleanModeFromWaterBoxModeDefault(water_box_mode) {
25
- if (!water_box_mode)
26
- return undefined;
27
- if (water_box_mode == MopWaterFlow.Custom)
28
- return 8;
29
- if (water_box_mode == MopWaterFlow.Off)
30
- return 6;
31
- else
32
- return undefined;
20
+ return undefined;
33
21
  }
@@ -0,0 +1,18 @@
1
+ import { RvcCleanMode } from 'matterbridge/matter/clusters';
2
+ import { RvcCleanMode as RvcCleanModeDisplayMap } from './smart.js';
3
+ import { getDefaultSupportedCleanModes } from '../default/initalData.js';
4
+ export function getSupportedCleanModesSmart() {
5
+ return [
6
+ {
7
+ label: RvcCleanModeDisplayMap[4],
8
+ mode: 4,
9
+ modeTags: [{ value: RvcCleanMode.ModeTag.Mop }, { value: RvcCleanMode.ModeTag.Vacuum }, { value: RvcCleanMode.ModeTag.Auto }],
10
+ },
11
+ {
12
+ label: RvcCleanModeDisplayMap[5],
13
+ mode: 5,
14
+ modeTags: [{ value: RvcCleanMode.ModeTag.Mop }, { value: RvcCleanMode.ModeTag.Vacuum }, { value: RvcCleanMode.ModeTag.Day }],
15
+ },
16
+ ...getDefaultSupportedCleanModes().filter((x) => x.mode !== 4 && x.mode !== 5),
17
+ ];
18
+ }
@@ -0,0 +1,11 @@
1
+ import { getCurrentCleanModeDefault } from '../default/runtimes.js';
2
+ import { MopRouteSmart, MopWaterFlowSmart, VacuumSuctionPowerSmart } from './smart.js';
3
+ export function getCurrentCleanModeSmart(setting) {
4
+ if (!setting || typeof setting !== 'object') {
5
+ return undefined;
6
+ }
7
+ if (setting.suctionPower === VacuumSuctionPowerSmart.Smart || setting.waterFlow === MopWaterFlowSmart.Smart || setting.mopRoute === MopRouteSmart.Smart) {
8
+ return 4;
9
+ }
10
+ return getCurrentCleanModeDefault(setting);
11
+ }
@@ -0,0 +1,119 @@
1
+ import { debugStringify } from 'matterbridge/logger';
2
+ import { BehaviorRoborock } from '../../BehaviorDeviceGeneric.js';
3
+ import { RvcCleanMode as DefaultRvcCleanMode, CleanSetting as DefaultCleanSetting, getSettingFromCleanMode, RvcRunMode } from '../default/default.js';
4
+ export class BehaviorSmart extends BehaviorRoborock {
5
+ }
6
+ export var VacuumSuctionPowerSmart;
7
+ (function (VacuumSuctionPowerSmart) {
8
+ VacuumSuctionPowerSmart[VacuumSuctionPowerSmart["Quiet"] = 101] = "Quiet";
9
+ VacuumSuctionPowerSmart[VacuumSuctionPowerSmart["Balanced"] = 102] = "Balanced";
10
+ VacuumSuctionPowerSmart[VacuumSuctionPowerSmart["Turbo"] = 103] = "Turbo";
11
+ VacuumSuctionPowerSmart[VacuumSuctionPowerSmart["Max"] = 104] = "Max";
12
+ VacuumSuctionPowerSmart[VacuumSuctionPowerSmart["Off"] = 105] = "Off";
13
+ VacuumSuctionPowerSmart[VacuumSuctionPowerSmart["Custom"] = 106] = "Custom";
14
+ VacuumSuctionPowerSmart[VacuumSuctionPowerSmart["MaxPlus"] = 108] = "MaxPlus";
15
+ VacuumSuctionPowerSmart[VacuumSuctionPowerSmart["Smart"] = 110] = "Smart";
16
+ })(VacuumSuctionPowerSmart || (VacuumSuctionPowerSmart = {}));
17
+ export var MopWaterFlowSmart;
18
+ (function (MopWaterFlowSmart) {
19
+ MopWaterFlowSmart[MopWaterFlowSmart["Off"] = 200] = "Off";
20
+ MopWaterFlowSmart[MopWaterFlowSmart["Low"] = 201] = "Low";
21
+ MopWaterFlowSmart[MopWaterFlowSmart["Medium"] = 202] = "Medium";
22
+ MopWaterFlowSmart[MopWaterFlowSmart["High"] = 203] = "High";
23
+ MopWaterFlowSmart[MopWaterFlowSmart["Custom"] = 204] = "Custom";
24
+ MopWaterFlowSmart[MopWaterFlowSmart["CustomizeWithDistanceOff"] = 207] = "CustomizeWithDistanceOff";
25
+ MopWaterFlowSmart[MopWaterFlowSmart["Smart"] = 209] = "Smart";
26
+ })(MopWaterFlowSmart || (MopWaterFlowSmart = {}));
27
+ export var MopRouteSmart;
28
+ (function (MopRouteSmart) {
29
+ MopRouteSmart[MopRouteSmart["Standard"] = 300] = "Standard";
30
+ MopRouteSmart[MopRouteSmart["Deep"] = 301] = "Deep";
31
+ MopRouteSmart[MopRouteSmart["Custom"] = 302] = "Custom";
32
+ MopRouteSmart[MopRouteSmart["DeepPlus"] = 303] = "DeepPlus";
33
+ MopRouteSmart[MopRouteSmart["Fast"] = 304] = "Fast";
34
+ MopRouteSmart[MopRouteSmart["Smart"] = 306] = "Smart";
35
+ })(MopRouteSmart || (MopRouteSmart = {}));
36
+ export const RvcCleanMode = {
37
+ [4]: 'Smart Plan',
38
+ ...DefaultRvcCleanMode,
39
+ };
40
+ export const CleanSetting = {
41
+ [4]: { suctionPower: 0, waterFlow: 0, distance_off: 0, mopRoute: MopRouteSmart.Smart },
42
+ ...DefaultCleanSetting,
43
+ };
44
+ export function setCommandHandlerSmart(duid, handler, logger, roborockService, cleanModeSettings) {
45
+ handler.setCommandHandler('changeToMode', async (newMode) => {
46
+ const activity = RvcRunMode[newMode] || RvcCleanMode[newMode];
47
+ switch (activity) {
48
+ case 'Cleaning': {
49
+ logger.notice('BehaviorSmart-ChangeRunMode to: ', activity);
50
+ await roborockService.startClean(duid);
51
+ break;
52
+ }
53
+ case 'Go Vacation': {
54
+ logger.notice('DefaultBehavior-GoHome');
55
+ await roborockService.stopAndGoHome(duid);
56
+ break;
57
+ }
58
+ case 'Smart Plan':
59
+ case 'Mop & Vacuum: Custom': {
60
+ const setting = CleanSetting[newMode];
61
+ logger.notice(`BehaviorSmart-ChangeCleanMode to: ${activity}, setting: ${debugStringify(setting)}`);
62
+ await roborockService.changeCleanMode(duid, setting);
63
+ break;
64
+ }
65
+ case 'Mop & Vacuum: Default':
66
+ case 'Mop: Default':
67
+ case 'Vacuum: Default': {
68
+ const setting = cleanModeSettings ? (getSettingFromCleanMode(activity, cleanModeSettings) ?? CleanSetting[newMode]) : CleanSetting[newMode];
69
+ logger.notice(`BehaviorSmart-ChangeCleanMode to: ${activity}, setting: ${debugStringify(setting ?? {})}`);
70
+ if (setting) {
71
+ await roborockService.changeCleanMode(duid, setting);
72
+ }
73
+ break;
74
+ }
75
+ case 'Mop & Vacuum: Quick':
76
+ case 'Mop & Vacuum: Max':
77
+ case 'Mop & Vacuum: Min':
78
+ case 'Mop & Vacuum: Quiet':
79
+ case 'Mop: Max':
80
+ case 'Mop: Min':
81
+ case 'Mop: Quick':
82
+ case 'Mop: DeepClean':
83
+ case 'Vacuum: Max':
84
+ case 'Vacuum: Min':
85
+ case 'Vacuum: Quiet':
86
+ case 'Vacuum: Quick': {
87
+ const setting = CleanSetting[newMode];
88
+ logger.notice(`BehaviorSmart-ChangeCleanMode to: ${activity}, setting: ${debugStringify(setting ?? {})}`);
89
+ if (setting) {
90
+ await roborockService.changeCleanMode(duid, setting);
91
+ }
92
+ break;
93
+ }
94
+ default:
95
+ logger.notice('BehaviorSmart-changeToMode-Unknown: ', newMode);
96
+ break;
97
+ }
98
+ });
99
+ handler.setCommandHandler('selectAreas', async (newAreas) => {
100
+ logger.notice(`BehaviorSmart-selectAreas: ${newAreas}`);
101
+ roborockService.setSelectedAreas(duid, newAreas ?? []);
102
+ });
103
+ handler.setCommandHandler('pause', async () => {
104
+ logger.notice('BehaviorSmart-Pause');
105
+ await roborockService.pauseClean(duid);
106
+ });
107
+ handler.setCommandHandler('resume', async () => {
108
+ logger.notice('BehaviorSmart-Resume');
109
+ await roborockService.resumeClean(duid);
110
+ });
111
+ handler.setCommandHandler('goHome', async () => {
112
+ logger.notice('BehaviorSmart-GoHome');
113
+ await roborockService.stopAndGoHome(duid);
114
+ });
115
+ handler.setCommandHandler('playSoundToLocate', async () => {
116
+ logger.notice('BehaviorSmart-playSoundToLocate');
117
+ await roborockService.playSoundToLocate(duid);
118
+ });
119
+ }
@@ -1,18 +1,8 @@
1
1
  import { RvcOperationalState } from 'matterbridge/matter/clusters';
2
- import { getOperationalStatesA187 } from '../behaviors/roborock.vacuum/QREVO_EDGE_5V1/initalData.js';
3
2
  import { getDefaultOperationalStates } from '../behaviors/roborock.vacuum/default/initalData.js';
4
- import { DeviceModel } from '../roborockCommunication/Zmodel/deviceModel.js';
5
3
  import { VacuumErrorCode } from '../roborockCommunication/Zenum/vacuumAndDockErrorCode.js';
6
- import { getOperationalStatesA27 } from '../behaviors/roborock.vacuum/S7_MAXV/initalData.js';
7
- export function getOperationalStates(model) {
8
- switch (model) {
9
- case DeviceModel.QREVO_EDGE_5V1:
10
- return getOperationalStatesA187();
11
- case DeviceModel.S7_MAXV:
12
- return getOperationalStatesA27();
13
- default:
14
- return getDefaultOperationalStates();
15
- }
4
+ export function getOperationalStates() {
5
+ return getDefaultOperationalStates();
16
6
  }
17
7
  export function getOperationalErrorState(errorCode) {
18
8
  switch (errorCode) {
@@ -1,13 +1,16 @@
1
- import { getSupportedCleanModesA187 } from '../behaviors/roborock.vacuum/QREVO_EDGE_5V1/initalData.js';
1
+ import { getSupportedCleanModesSmart } from '../behaviors/roborock.vacuum/smart/initalData.js';
2
2
  import { getDefaultSupportedCleanModes } from '../behaviors/roborock.vacuum/default/initalData.js';
3
3
  import { DeviceModel } from '../roborockCommunication/Zmodel/deviceModel.js';
4
- import { getSupportedCleanModesA27 } from '../behaviors/roborock.vacuum/S7_MAXV/initalData.js';
5
- export function getSupportedCleanModes(model) {
4
+ export function getSupportedCleanModes(model, forceRunAtDefault) {
5
+ if (forceRunAtDefault) {
6
+ return getDefaultSupportedCleanModes();
7
+ }
6
8
  switch (model) {
7
9
  case DeviceModel.QREVO_EDGE_5V1:
8
- return getSupportedCleanModesA187();
10
+ return getSupportedCleanModesSmart();
9
11
  case DeviceModel.S7_MAXV:
10
- return getSupportedCleanModesA27();
12
+ case DeviceModel.S8_PRO_ULTRA:
13
+ case DeviceModel.S6_PURE:
11
14
  default:
12
15
  return getDefaultSupportedCleanModes();
13
16
  }