Skip to content

Commit

Permalink
Support of the Xiaomi Air Humidifier CA (zhimi.humidifier.ca1) (#249) (
Browse files Browse the repository at this point in the history
…Closes: #241)
  • Loading branch information
syssi authored Mar 7, 2018
1 parent cc98300 commit c78e9cd
Show file tree
Hide file tree
Showing 2 changed files with 90 additions and 12 deletions.
72 changes: 60 additions & 12 deletions miio/airhumidifier.py
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,7 @@ class OperationMode(enum.Enum):
Silent = 'silent'
Medium = 'medium'
High = 'high'
Auto = 'auto'


class LedBrightness(enum.Enum):
Expand All @@ -32,15 +33,9 @@ def __init__(self, data: Dict[str, Any]) -> None:
{'power': 'off', 'mode': 'high', 'temp_dec': 294,
'humidity': 33, 'buzzer': 'on', 'led_b': 0,
'child_lock': 'on', 'limit_hum': 40, 'trans_level': 85}
TODO: Features of the Air Humidifier Ca (zhimi.humidifier.ca1):
- Same properties: power, mode, temp_dec, humidity,
buzzer, led_b, child_lock, limit_hum
- Additional properties: speed, depth, dry, hw_version,
use_time, button_pressed
- Operation modes: auto, high, medium, silent
- Additional setters: set_dry on/off
'child_lock': 'on', 'limit_hum': 40, 'trans_level': 85,
'speed': None, 'depth': None, 'dry': None, 'use_time': 941100,
'hw_version': 0, 'button_pressed': 'led'}
"""

self.data = data
Expand Down Expand Up @@ -99,6 +94,38 @@ def trans_level(self) -> int:
"""The meaning of the property is unknown."""
return self.data["trans_level"]

@property
def speed(self) -> Optional[int]:
"""Current fan speed."""
return self.data["speed"]

@property
def depth(self) -> Optional[int]:
"""Current depth."""
return self.data["depth"]

@property
def dry(self) -> Optional[bool]:
"""Return True if dry mode is on if available."""
if self.data["dry"] is not None:
return self.data["dry"] == "on"
return None

@property
def use_time(self) -> Optional[int]:
"""How long the device has been active in seconds."""
return self.data["use_time"]

@property
def hardware_version(self) -> Optional[str]:
"""The hardware version."""
return self.data["hw_version"]

@property
def button_pressed(self) -> Optional[str]:
"""Button pressed."""
return self.data["button_pressed"]

def __str__(self) -> str:
s = "<AirHumidiferStatus power=%s, " \
"mode=%s, " \
Expand All @@ -108,7 +135,13 @@ def __str__(self) -> str:
"buzzer=%s, " \
"child_lock=%s, " \
"target_humidity=%s%%, " \
"trans_level=%s>" % \
"trans_level=%s, " \
"speed=%s, " \
"depth=%s, " \
"dry=%s, " \
"use_time=%s, " \
"hardware_version=%s, " \
"button_pressed=%s>" % \
(self.power,
self.mode,
self.temperature,
Expand All @@ -117,7 +150,13 @@ def __str__(self) -> str:
self.buzzer,
self.child_lock,
self.target_humidity,
self.trans_level)
self.trans_level,
self.speed,
self.depth,
self.dry,
self.use_time,
self.hardware_version,
self.button_pressed)
return s


Expand All @@ -128,7 +167,9 @@ def status(self) -> AirHumidifierStatus:
"""Retrieve properties."""

properties = ['power', 'mode', 'temp_dec', 'humidity', 'buzzer',
'led_b', 'child_lock', 'limit_hum', 'trans_level', ]
'led_b', 'child_lock', 'limit_hum', 'trans_level',
'speed', 'depth', 'dry', 'use_time', 'button_pressed',
'hw_version', ]

values = self.send(
"get_prop",
Expand Down Expand Up @@ -183,3 +224,10 @@ def set_target_humidity(self, humidity: int):
"Invalid target humidity: %s" % humidity)

return self.send("set_limit_hum", [humidity])

def set_dry(self, dry: bool):
"""Set dry mode on/off."""
if dry:
return self.send("set_dry", ["on"])
else:
return self.send("set_dry", ["off"])
30 changes: 30 additions & 0 deletions miio/tests/test_airhumidifier.py
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,13 @@ def __init__(self, *args, **kwargs):
'child_lock': 'on',
'limit_hum': 40,
'trans_level': 85,
'use_time': 941100,
'button_pressed': 'led',
'hw_version': 0,
# Additional attributes of the zhimi.humidifier.ca1
'speed': 100,
'depth': 1,
'dry': 'off',
}
self.return_values = {
'get_prop': self._get_state,
Expand All @@ -26,6 +33,7 @@ def __init__(self, *args, **kwargs):
'set_buzzer': lambda x: self._set_state("buzzer", x),
'set_child_lock': lambda x: self._set_state("child_lock", x),
'set_limit_hum': lambda x: self._set_state("limit_hum", x),
'set_dry': lambda x: self._set_state("dry", x),
}
super().__init__(args, kwargs)

Expand Down Expand Up @@ -72,6 +80,12 @@ def test_status(self):
assert self.state().child_lock == (self.device.start_state["child_lock"] == 'on')
assert self.state().target_humidity == self.device.start_state["limit_hum"]
assert self.state().trans_level == self.device.start_state["trans_level"]
assert self.state().speed == self.device.start_state["speed"]
assert self.state().depth == self.device.start_state["depth"]
assert self.state().dry == (self.device.start_state["dry"] == 'on')
assert self.state().use_time == self.device.start_state["use_time"]
assert self.state().hardware_version == self.device.start_state["hw_version"]
assert self.state().button_pressed == self.device.start_state["button_pressed"]

def test_set_mode(self):
def mode():
Expand Down Expand Up @@ -153,3 +167,19 @@ def child_lock():

self.device.set_child_lock(False)
assert child_lock() is False

def test_set_dry(self):
def dry():
return self.device.status().dry

self.device.set_dry(True)
assert dry() is True

self.device.set_dry(False)
assert dry() is False

def test_status_without_dry(self):
self.device._reset_state()
self.device.state["dry"] = None

assert self.state().dry is None

0 comments on commit c78e9cd

Please sign in to comment.