homebridge-frontier-silicon-plugin 1.0.2 → 1.0.3
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 +12 -0
- package/index.js +28 -22
- package/package.json +1 -1
package/CHANGELOG.md
CHANGED
|
@@ -4,6 +4,18 @@ All notable changes to this project are documented in this file.
|
|
|
4
4
|
|
|
5
5
|
The format is based on Keep a Changelog, and this project follows Semantic Versioning.
|
|
6
6
|
|
|
7
|
+
## [1.1.0] – 2025-12-28
|
|
8
|
+
|
|
9
|
+
### Changed
|
|
10
|
+
- Replaced the Lightbulb Brightness based volume control with a native HomeKit **Speaker** service.
|
|
11
|
+
- Volume is now exposed using the official `Volume` characteristic.
|
|
12
|
+
- Power and volume are logically separated, matching HomeKit audio device expectations.
|
|
13
|
+
|
|
14
|
+
### Improved
|
|
15
|
+
- More natural HomeKit UI for audio devices.
|
|
16
|
+
- Better compatibility with HomeKit audio controls and third-party Home apps.
|
|
17
|
+
- Non-linear volume mapping retained for precise low-volume control.
|
|
18
|
+
|
|
7
19
|
## [1.0.2] – 2025-12-28
|
|
8
20
|
|
|
9
21
|
### Changed
|
package/index.js
CHANGED
|
@@ -21,11 +21,13 @@ function FrontierSiliconAccessory(log, config) {
|
|
|
21
21
|
this.ip = config.ip;
|
|
22
22
|
this.pin = String(config.pin ?? "1234");
|
|
23
23
|
this.pollIntervalSeconds = Number(config.pollIntervalSeconds ?? 5);
|
|
24
|
+
|
|
25
|
+
// Keep volume enabled by default. This now uses a Speaker service.
|
|
24
26
|
this.enableVolume = config.enableVolume !== false;
|
|
25
27
|
|
|
26
28
|
this.lastKnownPower = null;
|
|
27
29
|
|
|
28
|
-
//
|
|
30
|
+
// Store last known RADIO volume in device scale 0..100
|
|
29
31
|
this.lastKnownRadioVolume = null;
|
|
30
32
|
|
|
31
33
|
if (!this.ip) {
|
|
@@ -38,39 +40,45 @@ function FrontierSiliconAccessory(log, config) {
|
|
|
38
40
|
log: this.log
|
|
39
41
|
});
|
|
40
42
|
|
|
41
|
-
this.
|
|
43
|
+
this.informationService = new Service.AccessoryInformation()
|
|
44
|
+
.setCharacteristic(Characteristic.Manufacturer, "Frontier Silicon")
|
|
45
|
+
.setCharacteristic(Characteristic.Model, "FSAPI Radio")
|
|
46
|
+
.setCharacteristic(Characteristic.SerialNumber, this.ip || "unknown");
|
|
42
47
|
|
|
48
|
+
// Power as Switch (kept as-is for maximum Home app compatibility)
|
|
49
|
+
this.switchService = new Service.Switch(this.name);
|
|
43
50
|
this.switchService
|
|
44
51
|
.getCharacteristic(Characteristic.On)
|
|
45
52
|
.on("get", this.handleGetPower.bind(this))
|
|
46
53
|
.on("set", this.handleSetPower.bind(this));
|
|
47
54
|
|
|
55
|
+
// Speaker service for volume (and optional mute)
|
|
48
56
|
if (this.enableVolume) {
|
|
49
|
-
|
|
50
|
-
this.volumeService = new Service.Lightbulb(this.name + " Volume");
|
|
51
|
-
|
|
52
|
-
this.volumeService
|
|
53
|
-
.getCharacteristic(Characteristic.On)
|
|
54
|
-
.on("get", (cb) => cb(null, true))
|
|
55
|
-
.on("set", (_val, cb) => cb(null));
|
|
57
|
+
this.speakerService = new Service.Speaker(this.name + " Speaker");
|
|
56
58
|
|
|
57
|
-
|
|
58
|
-
|
|
59
|
+
// Volume characteristic uses HomeKit scale 0..100
|
|
60
|
+
this.speakerService
|
|
61
|
+
.getCharacteristic(Characteristic.Volume)
|
|
59
62
|
.on("get", this.handleGetVolume.bind(this))
|
|
60
63
|
.on("set", this.handleSetVolume.bind(this));
|
|
61
|
-
}
|
|
62
64
|
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
65
|
+
// Optional mute support placeholder:
|
|
66
|
+
// If you want real mute later, we can map this to an FSAPI endpoint if available.
|
|
67
|
+
// For now, we expose mute but keep it non-functional (always false) to avoid confusion.
|
|
68
|
+
if (Characteristic.Mute) {
|
|
69
|
+
this.speakerService
|
|
70
|
+
.getCharacteristic(Characteristic.Mute)
|
|
71
|
+
.on("get", (cb) => cb(null, false))
|
|
72
|
+
.on("set", (_val, cb) => cb(null));
|
|
73
|
+
}
|
|
74
|
+
}
|
|
67
75
|
|
|
68
76
|
this.startPolling();
|
|
69
77
|
}
|
|
70
78
|
|
|
71
79
|
FrontierSiliconAccessory.prototype.getServices = function () {
|
|
72
80
|
const services = [this.informationService, this.switchService];
|
|
73
|
-
if (this.enableVolume && this.
|
|
81
|
+
if (this.enableVolume && this.speakerService) services.push(this.speakerService);
|
|
74
82
|
return services;
|
|
75
83
|
};
|
|
76
84
|
|
|
@@ -142,14 +150,14 @@ FrontierSiliconAccessory.prototype.startPolling = function () {
|
|
|
142
150
|
if (this.log.debug) this.log.debug("Polling power failed.", toMsg(err));
|
|
143
151
|
}
|
|
144
152
|
|
|
145
|
-
if (this.enableVolume && this.
|
|
153
|
+
if (this.enableVolume && this.speakerService) {
|
|
146
154
|
try {
|
|
147
155
|
const radioVol = await this.client.getVolume();
|
|
148
156
|
if (this.lastKnownRadioVolume !== radioVol) {
|
|
149
157
|
this.lastKnownRadioVolume = radioVol;
|
|
150
158
|
const homekitVol = radioToHomekitVolume(radioVol);
|
|
151
|
-
this.
|
|
152
|
-
.getCharacteristic(Characteristic.
|
|
159
|
+
this.speakerService
|
|
160
|
+
.getCharacteristic(Characteristic.Volume)
|
|
153
161
|
.updateValue(homekitVol);
|
|
154
162
|
}
|
|
155
163
|
} catch (err) {
|
|
@@ -179,7 +187,6 @@ FsApiClient.prototype.getPower = async function () {
|
|
|
179
187
|
|
|
180
188
|
FsApiClient.prototype.setPower = async function (on) {
|
|
181
189
|
const v = on ? 1 : 0;
|
|
182
|
-
// Important: SET must start query with ?value= so pin can be appended with &
|
|
183
190
|
await this.fetchText("/fsapi/SET/netRemote.sys.power?value=" + v);
|
|
184
191
|
};
|
|
185
192
|
|
|
@@ -191,7 +198,6 @@ FsApiClient.prototype.getVolume = async function () {
|
|
|
191
198
|
|
|
192
199
|
FsApiClient.prototype.setVolume = async function (volume) {
|
|
193
200
|
const v = clampInt(Number(volume), 0, 100);
|
|
194
|
-
// Important: SET must start query with ?value= so pin can be appended with &
|
|
195
201
|
await this.fetchText("/fsapi/SET/netRemote.sys.audio.volume?value=" + v);
|
|
196
202
|
};
|
|
197
203
|
|
package/package.json
CHANGED