Skip to content

Commit 8b88c02

Browse files
committed
Merge remote-tracking branch 'ebaauw/master'
2 parents d707e1f + 7b561f1 commit 8b88c02

14 files changed

+581
-258
lines changed

bindings.cpp

Lines changed: 7 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1422,7 +1422,7 @@ bool DeRestPluginPrivate::sendConfigureReportingRequest(BindingTask &bt)
14221422
rq.minInterval = 1;
14231423
rq.maxInterval = 600;
14241424
rq.reportableChange16bit = 50;
1425-
1425+
14261426
ConfigureReportingRequest rq2;
14271427
rq2.dataType = deCONZ::Zcl8BitUint;
14281428
rq2.attributeId = 0x0008; // Pi heating demand
@@ -1548,7 +1548,7 @@ bool DeRestPluginPrivate::sendConfigureReportingRequest(BindingTask &bt)
15481548
rq.minInterval = 0;
15491549
rq.maxInterval = 300;
15501550
rq.reportableChange16bit = 10;
1551-
1551+
15521552
ConfigureReportingRequest rq2;
15531553
rq2.dataType = deCONZ::Zcl16BitInt;
15541554
rq2.attributeId = 0x0011; // Occupied cooling setpoint
@@ -2578,6 +2578,10 @@ void DeRestPluginPrivate::checkLightBindingsForAttributeReporting(LightNode *lig
25782578
}
25792579
else if (lightNode->manufacturerCode() == VENDOR_XIAOMI)
25802580
{
2581+
if (lightNode->modelId().startsWith(QLatin1String("lumi.curtain.acn002")))
2582+
{
2583+
return;
2584+
}
25812585
}
25822586
else if (lightNode->manufacturerCode() == VENDOR_STELPRO)
25832587
{
@@ -3060,7 +3064,7 @@ bool DeRestPluginPrivate::checkSensorBindingsForAttributeReporting(Sensor *senso
30603064
sensor->modelId().startsWith(QLatin1String("TS0041")) ||
30613065
sensor->modelId().startsWith(QLatin1String("TS0044")) ||
30623066
sensor->modelId().startsWith(QLatin1String("TS0203")) ||
3063-
sensor->modelId().startsWith(QLatin1String("TS0222")) || // TYZB01 light sensor
3067+
sensor->modelId().startsWith(QLatin1String("TS0222")) || // TYZB01 light sensor
30643068
sensor->modelId().startsWith(QLatin1String("TS004F")) || // 4 Gang Tuya ZigBee Wireless 12 Scene Switch
30653069
sensor->modelId().startsWith(QLatin1String("TS011F")) || // Plugs
30663070
// Tuyatec

button_maps.json

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -749,7 +749,7 @@
749749
[1, "0x02", "LEVEL_CONTROL", "MOVE_WITH_ON_OFF", "0", "S_BUTTON_1", "S_BUTTON_ACTION_HOLD", "Move up (with on/off)"],
750750
[1, "0x02", "LEVEL_CONTROL", "STOP_WITH_ON_OFF", "0", "S_BUTTON_1", "S_BUTTON_ACTION_LONG_RELEASED", "Stop_ (with on/off)"],
751751
[1, "0x02", "LEVEL_CONTROL", "MOVE_WITH_ON_OFF", "1", "S_BUTTON_1", "S_BUTTON_ACTION_HOLD", "Move down (with on/off)"],
752-
[1, "0x02", "LEVEL_CONTROL", "STOP_WITH_ON_OFF", "1", "S_BUTTON_1", "S_BUTTON_ACTION_LONG_RELEASED", "Stop_ (with on/off)"]
752+
[1, "0x02", "LEVEL_CONTROL", "STOP_WITH_ON_OFF", "1", "S_BUTTON_1", "S_BUTTON_ACTION_LONG_RELEASED", "Stop_ (with on/off)"]
753753
]
754754
},
755755
"ubisysD1Map": {
@@ -1076,7 +1076,7 @@
10761076
"sunricherMap": {
10771077
"vendor": "Sunricher",
10781078
"doc": "Wireless switches from Sunricher, Namron, SLC and EcoDim",
1079-
"modelids": ["ED-10010", "ED-10011", "ED-10012", "ED-10013", "ED-10014", "ED-10015", "ZG2833K8_EU05", "ZG2835", "4512700", "4512701", "4512702", "4512703", "4512705", "4512714", "4512719", "4512720", "4512721", "4512722", "4512729", "S57003", "ROB_200-008", "ROB_200-009-0", "ROB_200-008-0", "ROB_200-007-0"],
1079+
"modelids": ["ED-10010", "ED-10011", "ED-10012", "ED-10013", "ED-10014", "ED-10015", "ZG2833K8_EU05", "ZG2833K4_EU06", "ZG2835", "4512700", "4512701", "4512702", "4512703", "4512705", "4512714", "4512719", "4512720", "4512721", "4512722", "4512729", "S57003", "ROB_200-008", "ROB_200-009-0", "ROB_200-008-0", "ROB_200-007-0"],
10801080
"map": [
10811081
[1, "0x01", "ONOFF", "ON", "0", "S_BUTTON_1", "S_BUTTON_ACTION_SHORT_RELEASED", "On"],
10821082
[1, "0x01", "LEVEL_CONTROL", "MOVE_WITH_ON_OFF", "0", "S_BUTTON_1", "S_BUTTON_ACTION_HOLD", "Move up (with on/off)"],

database.cpp

Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -3625,7 +3625,7 @@ static int sqliteLoadAllSensorsCallback(void *user, int ncols, char **colval , c
36253625
clusterId = clusterId ? clusterId : TUYA_CLUSTER_ID;
36263626
sensor.addItem(DataTypeBool, RStateLowBattery)->setValue(false);
36273627
}
3628-
3628+
36293629
item = sensor.addItem(DataTypeBool, RStateFire);
36303630
item->setValue(false);
36313631
}
@@ -3987,12 +3987,20 @@ static int sqliteLoadAllSensorsCallback(void *user, int ncols, char **colval , c
39873987
{
39883988
clusterId = POWER_CONFIGURATION_CLUSTER_ID;
39893989
}
3990+
else if (sensor.fingerPrint().hasInCluster(XIAOMI_CLUSTER_ID))
3991+
{
3992+
clusterId = XIAOMI_CLUSTER_ID;
3993+
}
39903994
else if (sensor.fingerPrint().hasInCluster(TUYA_CLUSTER_ID))
39913995
{
39923996
clusterId = TUYA_CLUSTER_ID;
39933997
}
39943998
item = sensor.addItem(DataTypeUInt8, RStateBattery);
39953999
item->setValue(100);
4000+
if (sensor.modelId().startsWith(QLatin1String("lumi.curtain.acn002")))
4001+
{
4002+
sensor.addItem(DataTypeBool, RStateCharging);
4003+
}
39964004
}
39974005
else if (sensor.type() == QLatin1String("CLIPDaylightOffset"))
39984006
{
@@ -4145,7 +4153,7 @@ static int sqliteLoadAllSensorsCallback(void *user, int ncols, char **colval , c
41454153
item = sensor.addItem(DataTypeUInt16, RConfigPending);
41464154
item->setValue(item->toNumber() | R_PENDING_MODE);
41474155
}
4148-
4156+
41494157
if (sensor.modelId() == QLatin1String("lumi.switch.n0agl1"))
41504158
{
41514159
sensor.removeItem(RConfigBattery);

de_web_plugin.cpp

Lines changed: 43 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -286,6 +286,7 @@ static const SupportedDevice supportedDevices[] = {
286286
{ VENDOR_XIAOMI, "lumi.plug", xiaomiMacPrefix }, // Xiaomi smart plugs (router)
287287
{ VENDOR_XIAOMI, "lumi.switch.b1naus01", xiaomiMacPrefix }, // Xiaomi Aqara ZB3.0 Smart Wall Switch Single Rocker WS-USC03
288288
// { VENDOR_XIAOMI, "lumi.curtain", jennicMacPrefix}, // Xiaomi curtain controller (router) - exposed only as light
289+
{ VENDOR_XIAOMI, "lumi.curtain.acn002", lumiMacPrefix}, // Xiaomi roller shade driver E1
289290
{ VENDOR_XIAOMI, "lumi.curtain.hagl04", xiaomiMacPrefix}, // Xiaomi B1 curtain controller
290291
{ VENDOR_XIAOMI, "lumi.remote.cagl01", xiaomiMacPrefix }, // Xiaomi Aqara T1 Cube MFKZQ11LM
291292
{ VENDOR_XIAOMI, "lumi.sensor_magnet.agl02", xiaomiMacPrefix}, // Xiaomi Aqara T1 open/close sensor MCCGQ12LM
@@ -496,7 +497,7 @@ static const SupportedDevice supportedDevices[] = {
496497
{ VENDOR_ALERTME, "SLT3", computimeMacPrefix }, // Hive thermostat
497498
{ VENDOR_DANFOSS, "TRV001", silabs2MacPrefix }, // Hive thermostat (From Danfoss)
498499
{ VENDOR_SUNRICHER, "45127", silabs2MacPrefix }, // Namron 1/2/4-ch remote controller
499-
{ VENDOR_SUNRICHER, "S57003", silabs2MacPrefix }, // SLC 4-ch remote controller
500+
{ VENDOR_SUNRICHER, "S57003", silabs2MacPrefix }, // SLC 4-ch remote controller
500501
{ VENDOR_SENGLED_OPTOELEC, "E13-", zhejiangMacPrefix }, // Sengled PAR38 Bulbs
501502
{ VENDOR_SENGLED_OPTOELEC, "E1D-", zhejiangMacPrefix }, // Sengled contact sensor
502503
{ VENDOR_SENGLED_OPTOELEC, "E1E-", zhejiangMacPrefix }, // Sengled Smart Light Switch
@@ -2432,7 +2433,7 @@ void DeRestPluginPrivate::addLightNode(const deCONZ::Node *node)
24322433
}
24332434
if (node->nodeDescriptor().manufacturerCode() == VENDOR_KEEN_HOME || // Keen Home Vent
24342435
node->nodeDescriptor().manufacturerCode() == VENDOR_JENNIC || // Xiaomi lumi.ctrl_neutral1, lumi.ctrl_neutral2
2435-
node->nodeDescriptor().manufacturerCode() == VENDOR_XIAOMI || // Xiaomi lumi.curtain.hagl04
2436+
node->nodeDescriptor().manufacturerCode() == VENDOR_XIAOMI || // Xiaomi lumi.curtain.hagl04, lumi.curtain.acn002
24362437
node->nodeDescriptor().manufacturerCode() == VENDOR_EMBER || // atsmart Z6-03 switch + Heiman plug + Tuya stuff
24372438
(!node->nodeDescriptor().isNull() && node->nodeDescriptor().manufacturerCode() == VENDOR_NONE) || // Climax Siren
24382439
node->nodeDescriptor().manufacturerCode() == VENDOR_DEVELCO || // Develco Smoke sensor with siren
@@ -3971,6 +3972,11 @@ LightNode *DeRestPluginPrivate::updateLightNode(const deCONZ::NodeEvent &event)
39713972
updated = true;
39723973
setLightNodeStaticCapabilities(lightNode);
39733974
enqueueEvent({lightNode->prefix(), item->descriptor().suffix, lightNode->id(), item, lightNode->address().ext()});
3975+
3976+
{
3977+
Q_Q(DeRestPlugin);
3978+
emit q->nodeUpdated(lightNode->address().ext(), QLatin1String("vendor"), str);
3979+
}
39743980
}
39753981
}
39763982
else if (ia->id() == 0x0005) // Model identifier
@@ -4014,6 +4020,11 @@ LightNode *DeRestPluginPrivate::updateLightNode(const deCONZ::NodeEvent &event)
40144020
setLightNodeStaticCapabilities(lightNode);
40154021
enqueueEvent({lightNode->prefix(), item->descriptor().suffix, lightNode->id(), item, lightNode->address().ext()});
40164022
}
4023+
4024+
{
4025+
Q_Q(DeRestPlugin);
4026+
emit q->nodeUpdated(lightNode->address().ext(), QLatin1String("modelid"), str);
4027+
}
40174028
}
40184029
else if (ia->id() == 0x0006) // Date code
40194030
{
@@ -4029,6 +4040,11 @@ LightNode *DeRestPluginPrivate::updateLightNode(const deCONZ::NodeEvent &event)
40294040
updated = true;
40304041
}
40314042
item->setValue(str); // always needed to refresh set timestamp
4043+
4044+
{
4045+
Q_Q(DeRestPlugin);
4046+
emit q->nodeUpdated(lightNode->address().ext(), QLatin1String("version"), str);
4047+
}
40324048
}
40334049
}
40344050
else if (ia->id() == 0x4000) // Software build identifier
@@ -5752,7 +5768,7 @@ void DeRestPluginPrivate::addSensorNode(const deCONZ::Node *node, const deCONZ::
57525768
{
57535769
fpDoorLockSensor.inClusters.push_back(DOOR_LOCK_CLUSTER_ID);
57545770
}
5755-
5771+
57565772
fpAirQualitySensor.inClusters.push_back(ci->id());
57575773
fpAlarmSensor.inClusters.push_back(ci->id());
57585774
fpBatterySensor.inClusters.push_back(ci->id());
@@ -5794,11 +5810,6 @@ void DeRestPluginPrivate::addSensorNode(const deCONZ::Node *node, const deCONZ::
57945810
{
57955811
fpBatterySensor.inClusters.push_back(ci->id());
57965812
}
5797-
if (node->nodeDescriptor().manufacturerCode() == VENDOR_XIAOMI &&
5798-
modelId.startsWith(QLatin1String("lumi.curtain.hagl04")))
5799-
{
5800-
fpBatterySensor.inClusters.push_back(ci->id());
5801-
}
58025813
if ((node->nodeDescriptor().manufacturerCode() == VENDOR_AXIS || node->nodeDescriptor().manufacturerCode() == VENDOR_MMB) &&
58035814
(modelId == QLatin1String("Gear")) && (i->endpoint() == 0x01))
58045815
{
@@ -6463,6 +6474,10 @@ void DeRestPluginPrivate::addSensorNode(const deCONZ::Node *node, const deCONZ::
64636474
fpSwitch.inClusters.push_back(ci->id());
64646475
fpTemperatureSensor.inClusters.push_back(ci->id());
64656476
fpThermostatSensor.inClusters.push_back(ci->id());
6477+
if (modelId.startsWith(QLatin1String("lumi.curtain")))
6478+
{
6479+
fpBatterySensor.inClusters.push_back(ci->id());
6480+
}
64666481
}
64676482
}
64686483
break;
@@ -6692,11 +6707,11 @@ void DeRestPluginPrivate::addSensorNode(const deCONZ::Node *node, const deCONZ::
66926707
checkSensorNodeReachable(sensor);
66936708
}
66946709
}
6695-
6710+
66966711
//ZHAAncillaryControl
66976712
if (fpAncillaryControlSensor.hasOutCluster(IAS_ACE_CLUSTER_ID))
66986713
{
6699-
6714+
67006715
fpAncillaryControlSensor.endpoint = i->endpoint();
67016716
fpAncillaryControlSensor.deviceId = i->deviceId();
67026717
fpAncillaryControlSensor.profileId = i->profileId();
@@ -6844,7 +6859,7 @@ void DeRestPluginPrivate::addSensorNode(const deCONZ::Node *node, const deCONZ::
68446859
checkSensorNodeReachable(sensor);
68456860
}
68466861
}
6847-
6862+
68486863
// ZHAMoisture
68496864
if (fpMoistureSensor.hasInCluster(SOIL_MOISTURE_CLUSTER_ID))
68506865
{
@@ -7040,6 +7055,7 @@ void DeRestPluginPrivate::addSensorNode(const deCONZ::Node *node, const deCONZ::
70407055

70417056
// ZHABattery
70427057
if (fpBatterySensor.hasInCluster(POWER_CONFIGURATION_CLUSTER_ID) ||
7058+
fpBatterySensor.hasInCluster(XIAOMI_CLUSTER_ID) ||
70437059
fpBatterySensor.hasInCluster(TUYA_CLUSTER_ID))
70447060
{
70457061
fpBatterySensor.endpoint = i->endpoint();
@@ -7309,7 +7325,7 @@ void DeRestPluginPrivate::addSensorNode(const deCONZ::Node *node, const SensorFi
73097325
sensorNode.addItem(DataTypeInt16, RStateTemperature);
73107326
item = sensorNode.addItem(DataTypeInt16, RConfigOffset);
73117327
item->setValue(0);
7312-
7328+
73137329
if (R_GetProductId(&sensorNode).startsWith(QLatin1String("Tuya_SEN")))
73147330
{
73157331
// Enable reporting in "blind mode"
@@ -7781,11 +7797,19 @@ void DeRestPluginPrivate::addSensorNode(const deCONZ::Node *node, const SensorFi
77817797
{
77827798
clusterId = POWER_CONFIGURATION_CLUSTER_ID;
77837799
}
7800+
else if (sensorNode.fingerPrint().hasInCluster(XIAOMI_CLUSTER_ID))
7801+
{
7802+
clusterId = XIAOMI_CLUSTER_ID;
7803+
}
77847804
else if (sensorNode.fingerPrint().hasInCluster(TUYA_CLUSTER_ID))
77857805
{
77867806
clusterId = TUYA_CLUSTER_ID;
77877807
}
77887808
sensorNode.addItem(DataTypeUInt8, RStateBattery);
7809+
if (modelId.startsWith(QLatin1String("lumi.curtain.")))
7810+
{
7811+
sensorNode.addItem(DataTypeBool, RStateCharging);
7812+
}
77897813
}
77907814
else if (sensorNode.type().endsWith(QLatin1String("Time")))
77917815
{
@@ -8972,7 +8996,7 @@ void DeRestPluginPrivate::updateSensorNode(const deCONZ::NodeEvent &event)
89728996
{
89738997
pressure += item2->toNumber();
89748998
}
8975-
8999+
89769000
item->setValue(pressure);
89779001
i->updateStateTimestamp();
89789002
i->setNeedSaveDatabase(true);
@@ -9223,7 +9247,7 @@ void DeRestPluginPrivate::updateSensorNode(const deCONZ::NodeEvent &event)
92239247
{
92249248
continue;
92259249
}
9226-
9250+
92279251
// Correct incomplete sensor fingerprint
92289252
if (!i->fingerPrint().hasInCluster(BASIC_CLUSTER_ID))
92299253
{
@@ -10939,12 +10963,12 @@ bool DeRestPluginPrivate::processZclAttributes(Sensor *sensorNode)
1093910963
if (item)
1094010964
{
1094110965
quint64 sensitivity = item->toNumber();
10942-
10966+
1094310967
if (nd.manufacturerCode() == VENDOR_PHILIPS)
1094410968
{
1094510969
deCONZ::ZclAttribute attr(0x0030, deCONZ::Zcl8BitUint, "sensitivity", deCONZ::ZclReadWrite, true);
1094610970
attr.setValue(sensitivity);
10947-
10971+
1094810972
if (writeAttribute(sensorNode, sensorNode->fingerPrint().endpoint, OCCUPANCY_SENSING_CLUSTER_ID, attr, VENDOR_PHILIPS))
1094910973
{
1095010974
sensorNode->setNextReadTime(WRITE_SENSITIVITY, tNow.addSecs(7200));
@@ -10955,7 +10979,7 @@ bool DeRestPluginPrivate::processZclAttributes(Sensor *sensorNode)
1095510979
{
1095610980
deCONZ::ZclAttribute attr(XIAOMI_ATTRID_MOTION_SENSITIVITY, deCONZ::Zcl8BitUint, "sensitivity", deCONZ::ZclReadWrite, true);
1095710981
attr.setValue(sensitivity);
10958-
10982+
1095910983
if (writeAttribute(sensorNode, sensorNode->fingerPrint().endpoint, XIAOMI_CLUSTER_ID, attr, VENDOR_XIAOMI))
1096010984
{
1096110985
sensorNode->setNextReadTime(WRITE_SENSITIVITY, tNow.addSecs(3300)); // Default special reporting intervall
@@ -15872,9 +15896,9 @@ void DeRestPluginPrivate::delayedFastEnddeviceProbe(const deCONZ::NodeEvent *eve
1587215896
{
1587315897
std::vector<uint16_t> attributes;
1587415898
auto *item = sensor->item(RConfigSensitivity);
15875-
15899+
1587615900
if (item) { attributes.push_back(XIAOMI_ATTRID_MOTION_SENSITIVITY); }
15877-
15901+
1587815902
if (!attributes.empty() && readAttributes(sensor, sensor->fingerPrint().endpoint, XIAOMI_CLUSTER_ID, attributes, VENDOR_XIAOMI))
1587915903
{
1588015904
DBG_Printf(DBG_INFO, "Read 0x%016llX motion sensitivity attribute 0x010C...\n", sensor->address().ext());

de_web_plugin_private.h

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -192,6 +192,7 @@ using namespace deCONZ::literals;
192192
#define ANALOG_OUTPUT_CLUSTER_ID 0x000D
193193
#define BINARY_INPUT_CLUSTER_ID 0x000F
194194
#define MULTISTATE_INPUT_CLUSTER_ID 0x0012
195+
#define MULTISTATE_OUTPUT_CLUSTER_ID 0x0013
195196
#define OTAU_CLUSTER_ID 0x0019
196197
#define POLL_CONTROL_CLUSTER_ID 0x0020
197198
#define DOOR_LOCK_CLUSTER_ID 0x0101
@@ -223,6 +224,7 @@ using namespace deCONZ::literals;
223224
#define DEVELCO_AIR_QUALITY_CLUSTER_ID 0xFC03
224225
#define SENGLED_CLUSTER_ID 0xFC10
225226
#define LEGRAND_CONTROL_CLUSTER_ID 0xFC40
227+
#define XIAOMI_CLUSTER_ID 0xFCC0
226228
#define ADUROLIGHT_CLUSTER_ID 0xFCCC
227229
#define XAL_CLUSTER_ID 0xFCCE
228230
#define BOSCH_AIR_QUALITY_CLUSTER_ID quint16(0xFDEF)

0 commit comments

Comments
 (0)