homebridge-eliot-smart-control 1.3.0 → 1.5.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +88 -1
- package/README.md +44 -6
- package/config.schema.json +120 -10
- package/dist/accessory.js +233 -21
- package/dist/accessory.js.map +1 -1
- package/dist/auto-move.d.ts +87 -0
- package/dist/auto-move.js +153 -0
- package/dist/auto-move.js.map +1 -0
- package/dist/config.d.ts +61 -5
- package/dist/config.js +84 -0
- package/dist/config.js.map +1 -1
- package/dist/eliot/desk.d.ts +7 -0
- package/dist/eliot/desk.js +61 -20
- package/dist/eliot/desk.js.map +1 -1
- package/dist/eliot/discover.d.ts +7 -1
- package/dist/eliot/discover.js +2 -1
- package/dist/eliot/discover.js.map +1 -1
- package/homebridge-ui/public/index.html +72 -6
- package/homebridge-ui/server.js +4 -3
- package/package.json +1 -1
package/CHANGELOG.md
CHANGED
|
@@ -6,6 +6,91 @@ adheres to [semantic versioning](https://semver.org/spec/v2.0.0.html).
|
|
|
6
6
|
|
|
7
7
|
## [Unreleased]
|
|
8
8
|
|
|
9
|
+
## [1.5.0] — 2026-09-21
|
|
10
|
+
|
|
11
|
+
### Fixed
|
|
12
|
+
|
|
13
|
+
- **A new target while the desk is moving now works.** Cancelling a move sent
|
|
14
|
+
`STOP` and then a step command, as insurance for a control box too old to
|
|
15
|
+
know `STOP`. On a box driving a `GOTO_HEIGHT` that step starts a small move
|
|
16
|
+
of its own, and the replacement target arrives in the middle of it — which is
|
|
17
|
+
a command arriving mid-move, the one thing this box answers by giving up. The
|
|
18
|
+
desk took the 4 mm step and ignored where it had been told to go, so setting
|
|
19
|
+
the slider to 65% moved it by one. `STOP` alone now, followed by a pause long
|
|
20
|
+
enough for the desk to finish coasting before it is given somewhere new.
|
|
21
|
+
- **The idle poll no longer cancels a move.** It skipped polling while the
|
|
22
|
+
plugin was driving the desk, but not while the *control box* was — which is
|
|
23
|
+
precisely the case that must not be polled, because `SETTINGS` is a command
|
|
24
|
+
and one arriving mid-move makes the box abandon it. The move died, the desk
|
|
25
|
+
stopped short, and the box then looked like one that had never understood
|
|
26
|
+
`GOTO_HEIGHT`, so the step-command fallback took over and the position
|
|
27
|
+
jumped. Dragging the slider was where this showed.
|
|
28
|
+
- **Service names are back, and the room can be changed.** `ConfiguredName` is
|
|
29
|
+
what the Home app displays for a bridged accessory's services — without it
|
|
30
|
+
every switch shows as "Schalter 1", "Schalter 2" and so on — but Switch,
|
|
31
|
+
MotionSensor and WindowCovering do not list it, so it has to be declared with
|
|
32
|
+
`addOptionalCharacteristic` before it is set. Setting it undeclared made
|
|
33
|
+
Homebridge warn on every start and left an accessory the Home app would not
|
|
34
|
+
fully edit. It is also written only when empty, so a name given in the Home
|
|
35
|
+
app stays.
|
|
36
|
+
|
|
37
|
+
### Added
|
|
38
|
+
|
|
39
|
+
- **Automatic sit/stand movement.** Set a sitting height, a standing height, an
|
|
40
|
+
interval and the hours it applies to, and the desk alternates between them.
|
|
41
|
+
It arrives switched off behind an **Auto Movement** switch in the Home app,
|
|
42
|
+
because starting to move somebody's furniture on the strength of a config
|
|
43
|
+
file being saved is not a good first impression.
|
|
44
|
+
- **A *Desk Move Soon* sensor**, tripped a few minutes before each move. It is
|
|
45
|
+
a motion sensor because HomeKit gives an accessory no way to send a
|
|
46
|
+
notification and a sensor is the one thing the Home app will offer to notify
|
|
47
|
+
about; turning that on is a one-time step in the Home app that nothing here
|
|
48
|
+
can do for you.
|
|
49
|
+
- **The settings page checks the pairs of values the schema cannot.** A warning
|
|
50
|
+
that is not shorter than the interval, a sitting height above the standing
|
|
51
|
+
one, and a working-hours entry that is not a time range are all said while
|
|
52
|
+
they are being typed, rather than in the Homebridge log after a restart where
|
|
53
|
+
nobody is looking.
|
|
54
|
+
- **A warning of 0 turns the warning off** and takes the *Desk Move Soon*
|
|
55
|
+
sensor out of the Home app with it. A motion sensor that can never report
|
|
56
|
+
motion is a thing in somebody's house that does nothing and cannot be
|
|
57
|
+
explained.
|
|
58
|
+
- **Moving the desk by hand restarts the timer**, which makes a nudge on the
|
|
59
|
+
handset the snooze: the warning says it is about to move, you touch the
|
|
60
|
+
handset, and you have another interval.
|
|
61
|
+
|
|
62
|
+
### Changed
|
|
63
|
+
|
|
64
|
+
- **Slider targets are allowed to settle before one is acted on.** A drag is
|
|
65
|
+
dozens of them, and each taken literally meant stopping the desk, waiting out
|
|
66
|
+
its coast and handing it somewhere new. Seven targets now make one command.
|
|
67
|
+
- **A target the desk is already at is not a move.** The Home app sends the
|
|
68
|
+
current position the moment the slider is touched, and the desk was setting
|
|
69
|
+
off towards where it already was — the small movement before the real one.
|
|
70
|
+
- **The settings page says less, and says it once.** Field hints had grown into
|
|
71
|
+
paragraphs and the sit/stand section said the same thing twice. What was cut
|
|
72
|
+
is in the README, where the long version belongs.
|
|
73
|
+
- **The dongle is no longer described as advertising under one particular
|
|
74
|
+
name.** It carries whatever name the desk was given in the Eliot app, which
|
|
75
|
+
on many units is nothing useful. The scan always matched the service UUID
|
|
76
|
+
instead, which does not depend on what anybody called it.
|
|
77
|
+
|
|
78
|
+
## [1.4.0] — 2026-09-21
|
|
79
|
+
|
|
80
|
+
### Changed
|
|
81
|
+
|
|
82
|
+
- **Eco mode now means travel speed 20**, not 28. 28 was where the Eliot app
|
|
83
|
+
stops offering, which turned out to be a fact about the app rather than the
|
|
84
|
+
control box — the desk here was found storing 21, a value no version of the
|
|
85
|
+
app could have written, and took 21 back without complaint. Eco mode that is
|
|
86
|
+
barely slower than no eco mode is not worth resetting a desk to switch on.
|
|
87
|
+
- **Switches are called what they are** — *Memory 1*, *Child Lock* — instead of
|
|
88
|
+
carrying the desk's name in front of them. The Home app already shows which
|
|
89
|
+
accessory a switch belongs to, and *Schreibtisch Memory 1* said it twice.
|
|
90
|
+
Switches named by an earlier version are renamed on the next start, but only
|
|
91
|
+
where the name is still exactly what that version wrote: anything else is
|
|
92
|
+
yours, including a rename that happens to begin with the desk's name.
|
|
93
|
+
|
|
9
94
|
## [1.3.0] — 2026-09-21
|
|
10
95
|
|
|
11
96
|
### Removed
|
|
@@ -261,7 +346,9 @@ First release.
|
|
|
261
346
|
verified against hardware, including the measured travel speed and stopping
|
|
262
347
|
distance.
|
|
263
348
|
|
|
264
|
-
[Unreleased]: https://github.com/rummeyer/homebridge-eliot-smart-control/compare/v1.
|
|
349
|
+
[Unreleased]: https://github.com/rummeyer/homebridge-eliot-smart-control/compare/v1.5.0...HEAD
|
|
350
|
+
[1.5.0]: https://github.com/rummeyer/homebridge-eliot-smart-control/compare/v1.4.0...v1.5.0
|
|
351
|
+
[1.4.0]: https://github.com/rummeyer/homebridge-eliot-smart-control/compare/v1.3.0...v1.4.0
|
|
265
352
|
[1.3.0]: https://github.com/rummeyer/homebridge-eliot-smart-control/compare/v1.2.0...v1.3.0
|
|
266
353
|
[1.2.0]: https://github.com/rummeyer/homebridge-eliot-smart-control/compare/v1.1.0...v1.2.0
|
|
267
354
|
[1.1.0]: https://github.com/rummeyer/homebridge-eliot-smart-control/compare/v1.0.0...v1.1.0
|
package/README.md
CHANGED
|
@@ -67,11 +67,11 @@ your other accessories.
|
|
|
67
67
|
desks**.
|
|
68
68
|
|
|
69
69
|
This is the part worth having help with. The dongle does not announce itself:
|
|
70
|
-
it
|
|
71
|
-
have nothing printed on them — in a scan
|
|
72
|
-
phones with nothing to tell them apart. The
|
|
73
|
-
service the desk actually speaks, so a result
|
|
74
|
-
device and not a good guess.
|
|
70
|
+
it advertises under whatever name the desk was given in the Eliot app, carries
|
|
71
|
+
no manufacturer name, and many units have nothing printed on them — in a scan
|
|
72
|
+
list it sits among forty anonymous phones with nothing to tell them apart. The
|
|
73
|
+
page looks for the Bluetooth service the desk actually speaks, so a result
|
|
74
|
+
marked *confirmed* is the right device and not a good guess.
|
|
75
75
|
|
|
76
76
|
Press **Use this** next to yours, name it, and save.
|
|
77
77
|
|
|
@@ -92,6 +92,7 @@ dongle for five seconds.
|
|
|
92
92
|
| **Memory switches** | on | Offer your stored positions as buttons. Rename them in the Home app |
|
|
93
93
|
| **Child lock switch** | on | Offer the desk's child lock |
|
|
94
94
|
| **Eco mode** | leave alone | Eco mode and travel speed, as a pair. Takes effect only after the desk is reset by hand |
|
|
95
|
+
| **Automatic sit/stand** | off | Move between two heights on a timer, during configured hours |
|
|
95
96
|
|
|
96
97
|
Or by hand, in `config.json`:
|
|
97
98
|
|
|
@@ -100,7 +101,7 @@ Or by hand, in `config.json`:
|
|
|
100
101
|
"platform": "EliotSmartControl",
|
|
101
102
|
"desks": [
|
|
102
103
|
{
|
|
103
|
-
"name": "
|
|
104
|
+
"name": "Desk",
|
|
104
105
|
"mac": "E5:11:22:33:44:55",
|
|
105
106
|
"ecoMode": "off"
|
|
106
107
|
}
|
|
@@ -108,6 +109,31 @@ Or by hand, in `config.json`:
|
|
|
108
109
|
}
|
|
109
110
|
```
|
|
110
111
|
|
|
112
|
+
## Automatic sit/stand
|
|
113
|
+
|
|
114
|
+
Configure it, and the desk gains an **Auto Movement** switch. Nothing moves
|
|
115
|
+
until you turn that on — the switch is the feature's on/off, so that turning it
|
|
116
|
+
off is somewhere obvious rather than in a config file.
|
|
117
|
+
|
|
118
|
+
Once on, inside the hours you have set, the desk alternates between your
|
|
119
|
+
sitting and standing heights. It always heads for whichever of the two it is
|
|
120
|
+
further from, so a desk parked halfway still does the right thing.
|
|
121
|
+
|
|
122
|
+
**Moving the desk yourself restarts the timer.** That is the snooze: when the
|
|
123
|
+
warning says it is about to move and you are mid-call, nudge the desk with the
|
|
124
|
+
handset and you have bought another interval. It is also simply true — the
|
|
125
|
+
timer measures time spent at a height, and that clock restarts when the height
|
|
126
|
+
does.
|
|
127
|
+
|
|
128
|
+
**Getting told about it takes one step you have to do yourself.** HomeKit gives
|
|
129
|
+
a plugin no way to send a notification, so the warning is a motion sensor
|
|
130
|
+
called **Desk Move Soon**. Open it in the Home app, and under *Status and
|
|
131
|
+
Notifications* turn notifications on. Nothing here can do that for you, and if
|
|
132
|
+
you never do it the feature still works, silently.
|
|
133
|
+
|
|
134
|
+
Outside the configured hours nothing moves and no warning is raised — a phone
|
|
135
|
+
buzzing at 17:05 about a move that will never happen is worse than silence.
|
|
136
|
+
|
|
111
137
|
## Things worth knowing
|
|
112
138
|
|
|
113
139
|
**Positions land exactly.** The desk is handed a height and drives there on its
|
|
@@ -128,6 +154,18 @@ its button appears the next time the plugin connects.
|
|
|
128
154
|
and the plugin names them only once, when it first creates them, so whatever
|
|
129
155
|
you rename them to survives restarts.
|
|
130
156
|
|
|
157
|
+
**Eco mode is stored now and takes effect later.** The control box keeps
|
|
158
|
+
running whatever it was last reset with, so the settings it reports back can
|
|
159
|
+
differ from the speed it is visibly travelling at. A reset by hand — run the
|
|
160
|
+
desk to the bottom and hold the down key until it re-homes — is what makes a
|
|
161
|
+
stored setting live. No command over this connection can do it.
|
|
162
|
+
|
|
163
|
+
**The idle refresh is only for what happens between moves.** The control box
|
|
164
|
+
streams its height for as long as it is driving itself, so nothing needs asking
|
|
165
|
+
then. It is also why the poll must stay in seconds: a request arriving while
|
|
166
|
+
the box is moving makes it abandon the move, which looks exactly like a desk
|
|
167
|
+
that stops a centimetre after it starts.
|
|
168
|
+
|
|
131
169
|
**The desk's own safety features are untouched.** Anti-collision and the soft
|
|
132
170
|
limits live in the control box. The plugin adds limits of its own on top: it
|
|
133
171
|
gives up if the desk stops making progress, if a move takes longer than the
|
package/config.schema.json
CHANGED
|
@@ -3,7 +3,7 @@
|
|
|
3
3
|
"pluginType": "platform",
|
|
4
4
|
"singular": true,
|
|
5
5
|
"headerDisplay": "Control an Eliot sit-stand desk with the Smart Dongle from the Home app, over Bluetooth. Requires Linux — the plugin talks to BlueZ.",
|
|
6
|
-
"footerDisplay": "The dongle advertises
|
|
6
|
+
"footerDisplay": "The dongle advertises under whatever name the desk has been given in the Eliot app, and carries no manufacturer name, so there is often nothing in a scan list to pick it out by. The scan above matches on the Bluetooth service it speaks instead, which is the same whatever it is called.\n\nThe desk appears as a window covering: 0% is the lowest height it is set to allow, 100% the highest. Those come from the desk's own limits, so changing them on the handset changes what 0% and 100% mean.",
|
|
7
7
|
"schema": {
|
|
8
8
|
"type": "object",
|
|
9
9
|
"properties": {
|
|
@@ -23,8 +23,8 @@
|
|
|
23
23
|
"title": "Name",
|
|
24
24
|
"type": "string",
|
|
25
25
|
"required": true,
|
|
26
|
-
"default": "
|
|
27
|
-
"placeholder": "
|
|
26
|
+
"default": "Desk",
|
|
27
|
+
"placeholder": "Desk",
|
|
28
28
|
"description": "What the desk is called in the Home app."
|
|
29
29
|
},
|
|
30
30
|
"mac": {
|
|
@@ -40,19 +40,19 @@
|
|
|
40
40
|
"type": "integer",
|
|
41
41
|
"default": 30,
|
|
42
42
|
"minimum": 0,
|
|
43
|
-
"description": "How often to ask a standing desk for its height
|
|
43
|
+
"description": "How often to ask a standing desk for its height, which is how the handset being used gets noticed. 0 turns it off; keep it in seconds, not milliseconds."
|
|
44
44
|
},
|
|
45
45
|
"memorySwitches": {
|
|
46
46
|
"title": "Memory switches",
|
|
47
47
|
"type": "boolean",
|
|
48
48
|
"default": true,
|
|
49
|
-
"description": "Offer the desk's memory positions as switches.
|
|
49
|
+
"description": "Offer the desk's memory positions as switches. Only positions the desk actually has appear."
|
|
50
50
|
},
|
|
51
51
|
"childLockSwitch": {
|
|
52
52
|
"title": "Child lock as a switch",
|
|
53
53
|
"type": "boolean",
|
|
54
54
|
"default": true,
|
|
55
|
-
"description": "Offer the desk's child lock in the Home app. It is the
|
|
55
|
+
"description": "Offer the desk's child lock in the Home app. It is the one setting the control box reports back, so it is the one that can be shown honestly."
|
|
56
56
|
},
|
|
57
57
|
"ecoMode": {
|
|
58
58
|
"title": "Eco mode",
|
|
@@ -66,19 +66,94 @@
|
|
|
66
66
|
]
|
|
67
67
|
},
|
|
68
68
|
{
|
|
69
|
-
"title": "On - slow and quiet",
|
|
69
|
+
"title": "On - slow and quiet (speed 20)",
|
|
70
70
|
"enum": [
|
|
71
71
|
"on"
|
|
72
72
|
]
|
|
73
73
|
},
|
|
74
74
|
{
|
|
75
|
-
"title": "Off - about twice as fast",
|
|
75
|
+
"title": "Off - about twice as fast (speed 40)",
|
|
76
76
|
"enum": [
|
|
77
77
|
"off"
|
|
78
78
|
]
|
|
79
79
|
}
|
|
80
80
|
],
|
|
81
|
-
"description": "Eco mode and travel speed, set as a pair
|
|
81
|
+
"description": "Eco mode and travel speed, set as a pair: about 22 mm/s against 42 mm/s.<br><br><b>Takes effect only after the desk is reset by hand</b> — run it to the bottom and hold the down key until it re-homes. Until then it keeps its old speed, whatever this says."
|
|
82
|
+
},
|
|
83
|
+
"autoMove": {
|
|
84
|
+
"type": "object",
|
|
85
|
+
"description": "Move the desk between two heights on a timer. Adds an <b>Auto Movement</b> switch to the Home app, and nothing moves until you turn it on.",
|
|
86
|
+
"properties": {
|
|
87
|
+
"sittingMm": {
|
|
88
|
+
"title": "Sitting height (mm)",
|
|
89
|
+
"type": "integer",
|
|
90
|
+
"default": 800,
|
|
91
|
+
"minimum": 650,
|
|
92
|
+
"maximum": 1280,
|
|
93
|
+
"description": "Clamped to the desk's own limits if it will not go that far."
|
|
94
|
+
},
|
|
95
|
+
"standingMm": {
|
|
96
|
+
"title": "Standing height (mm)",
|
|
97
|
+
"type": "integer",
|
|
98
|
+
"default": 1200,
|
|
99
|
+
"minimum": 650,
|
|
100
|
+
"maximum": 1280,
|
|
101
|
+
"description": "Must be above the sitting height."
|
|
102
|
+
},
|
|
103
|
+
"intervalMinutes": {
|
|
104
|
+
"title": "Move every (minutes)",
|
|
105
|
+
"type": "integer",
|
|
106
|
+
"default": 30,
|
|
107
|
+
"minimum": 1,
|
|
108
|
+
"description": "Must be longer than the warning."
|
|
109
|
+
},
|
|
110
|
+
"warnMinutes": {
|
|
111
|
+
"title": "Warn before (minutes)",
|
|
112
|
+
"type": "integer",
|
|
113
|
+
"default": 5,
|
|
114
|
+
"minimum": 0,
|
|
115
|
+
"description": "A <b>Desk Move Soon</b> sensor trips this long before each move; turn on its notifications in the Home app to be told. 0 turns the warning off and removes the sensor."
|
|
116
|
+
},
|
|
117
|
+
"windows": {
|
|
118
|
+
"title": "Working hours",
|
|
119
|
+
"type": "array",
|
|
120
|
+
"default": [
|
|
121
|
+
"08:00-12:00",
|
|
122
|
+
"13:00-16:00"
|
|
123
|
+
],
|
|
124
|
+
"items": {
|
|
125
|
+
"type": "string",
|
|
126
|
+
"title": "Window",
|
|
127
|
+
"placeholder": "08:00-12:00",
|
|
128
|
+
"pattern": "^\\s*\\d{1,2}:\\d{2}\\s*-\\s*\\d{1,2}:\\d{2}\\s*$"
|
|
129
|
+
},
|
|
130
|
+
"description": "Outside these hours nothing moves and nothing warns."
|
|
131
|
+
},
|
|
132
|
+
"days": {
|
|
133
|
+
"title": "Days",
|
|
134
|
+
"type": "array",
|
|
135
|
+
"default": [
|
|
136
|
+
"mon",
|
|
137
|
+
"tue",
|
|
138
|
+
"wed",
|
|
139
|
+
"thu",
|
|
140
|
+
"fri"
|
|
141
|
+
],
|
|
142
|
+
"uniqueItems": true,
|
|
143
|
+
"items": {
|
|
144
|
+
"type": "string",
|
|
145
|
+
"enum": [
|
|
146
|
+
"mon",
|
|
147
|
+
"tue",
|
|
148
|
+
"wed",
|
|
149
|
+
"thu",
|
|
150
|
+
"fri",
|
|
151
|
+
"sat",
|
|
152
|
+
"sun"
|
|
153
|
+
]
|
|
154
|
+
}
|
|
155
|
+
}
|
|
156
|
+
}
|
|
82
157
|
}
|
|
83
158
|
}
|
|
84
159
|
}
|
|
@@ -100,7 +175,42 @@
|
|
|
100
175
|
"desks[].idlePollSeconds",
|
|
101
176
|
"desks[].ecoMode",
|
|
102
177
|
"desks[].childLockSwitch",
|
|
103
|
-
"desks[].memorySwitches"
|
|
178
|
+
"desks[].memorySwitches",
|
|
179
|
+
{
|
|
180
|
+
"key": "desks[].autoMove",
|
|
181
|
+
"type": "fieldset",
|
|
182
|
+
"expandable": true,
|
|
183
|
+
"expanded": false,
|
|
184
|
+
"title": "Automatic sit/stand",
|
|
185
|
+
"items": [
|
|
186
|
+
"desks[].autoMove.sittingMm",
|
|
187
|
+
"desks[].autoMove.standingMm",
|
|
188
|
+
"desks[].autoMove.intervalMinutes",
|
|
189
|
+
"desks[].autoMove.warnMinutes",
|
|
190
|
+
{
|
|
191
|
+
"key": "desks[].autoMove.windows",
|
|
192
|
+
"type": "array",
|
|
193
|
+
"orderable": false,
|
|
194
|
+
"buttonText": "Add window",
|
|
195
|
+
"items": [
|
|
196
|
+
"desks[].autoMove.windows[]"
|
|
197
|
+
]
|
|
198
|
+
},
|
|
199
|
+
{
|
|
200
|
+
"key": "desks[].autoMove.days",
|
|
201
|
+
"type": "checkboxes",
|
|
202
|
+
"titleMap": {
|
|
203
|
+
"mon": "Monday",
|
|
204
|
+
"tue": "Tuesday",
|
|
205
|
+
"wed": "Wednesday",
|
|
206
|
+
"thu": "Thursday",
|
|
207
|
+
"fri": "Friday",
|
|
208
|
+
"sat": "Saturday",
|
|
209
|
+
"sun": "Sunday"
|
|
210
|
+
}
|
|
211
|
+
}
|
|
212
|
+
]
|
|
213
|
+
}
|
|
104
214
|
]
|
|
105
215
|
}
|
|
106
216
|
],
|