Skip to content

Add typing, small refactoring #10

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 9 commits into from
Jan 10, 2022
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
48 changes: 27 additions & 21 deletions adafruit_hts221.py
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,12 @@
from adafruit_register.i2c_bits import RWBits, ROBits
from adafruit_register.i2c_bit import RWBit, ROBit

try:
from typing import Union, Sequence, Tuple
from busio import I2C
except ImportError:
pass

_WHO_AM_I = const(0x0F)

_CTRL_REG1 = const(0x20)
Expand Down Expand Up @@ -65,21 +71,21 @@ class CV:
"""struct helper"""

@classmethod
def add_values(cls, value_tuples):
def add_values(
cls, value_tuples: Sequence[Tuple[str, int, Union[int, float]]]
) -> None:
"""creates CV entries"""
cls.string = {}
cls.lsb = {}
cls.label = {}

for value_tuple in value_tuples:
name, value, string, lsb = value_tuple
name, value, label = value_tuple
setattr(cls, name, value)
cls.string[value] = string
cls.lsb[value] = lsb
cls.label[value] = label

@classmethod
def is_valid(cls, value):
def is_valid(cls, value: int) -> bool:
"""Returns true if the given value is a member of the CV"""
return value in cls.string
return value in cls.label


class Rate(CV):
Expand All @@ -105,10 +111,10 @@ class Rate(CV):

Rate.add_values(
(
("ONE_SHOT", 0, 0, None),
("RATE_1_HZ", 1, 1, None),
("RATE_7_HZ", 2, 7, None),
("RATE_12_5_HZ", 3, 12.5, None),
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Did these Nones serve any purpose previously?

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

My understanding from other libraries that do this is the store the resolution or LSB. As an example, if an option changes the sensitivity of a sensor to the equivalent of 8 bits, this would be 0.0039. So it's just that it doesn't here because it changes rate, not anything where the value of a "unit" of it changes, if that makes sense.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Did you run it with a device? Seems okay to me. But want to try to make sure it won't cause IndexError anywhere ifi we can. I don't have one of these sensors.

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't think I did, I don't think I own this sensor. The other libraries use it in calculations (calculating temperature using the LSB value and digital value, like from ADC) but it never seemed to be used in communication with the sensor. Happy to find a sensor and test with it if you'd like!

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Turns out the HTS221 is out of stock on Adafruit and Digi-Key with no restock date :/ depreciated maybe?

("ONE_SHOT", 0, 0),
("RATE_1_HZ", 1, 1),
("RATE_7_HZ", 2, 7),
("RATE_12_5_HZ", 3, 12.5),
)
)

Expand Down Expand Up @@ -170,7 +176,7 @@ class HTS221: # pylint: disable=too-many-instance-attributes
_h0_t0_out = ROUnaryStruct(_H0_T0_OUT, "<h")
_h1_t0_out = ROUnaryStruct(_H1_T1_OUT, "<h")

def __init__(self, i2c_bus):
def __init__(self, i2c_bus: I2C) -> None:
self.i2c_device = i2cdevice.I2CDevice(i2c_bus, _HTS221_DEFAULT_ADDRESS)
if not self._chip_id in [_HTS221_CHIP_ID]:
raise RuntimeError(
Expand Down Expand Up @@ -203,14 +209,14 @@ def __init__(self, i2c_bus):
self.calib_hum_meas_1 = self._h1_t0_out

# This is the closest thing to a software reset. It re-loads the calibration values from flash
def _boot(self):
def _boot(self) -> None:
self._boot_bit = True
# wait for the reset to finish
while self._boot_bit:
pass

@property
def relative_humidity(self):
def relative_humidity(self) -> float:
"""The current relative humidity measurement in %rH"""
calibrated_value_delta = self.calib_hum_value_1 - self.calib_hum_value_0
calibrated_measurement_delta = self.calib_hum_meas_1 - self.calib_hum_meas_0
Expand All @@ -228,7 +234,7 @@ def relative_humidity(self):
return adjusted_humidity

@property
def temperature(self):
def temperature(self) -> float:
"""The current temperature measurement in degrees Celsius"""

calibrated_value_delta = self.calibrated_value_1 - self.calib_temp_value_0
Expand All @@ -247,7 +253,7 @@ def temperature(self):
return adjusted_temp

@property
def data_rate(self):
def data_rate(self) -> int:
"""The rate at which the sensor measures :attr:`relative_humidity` and :attr:`temperature`.
:attr:`data_rate` should be set to one of the values of :class:`adafruit_hts221.Rate`.
Note that setting :attr:`data_rate` to ``Rate.ONE_SHOT`` will cause
Expand All @@ -256,23 +262,23 @@ def data_rate(self):
return self._data_rate

@data_rate.setter
def data_rate(self, value):
def data_rate(self, value: int) -> None:
if not Rate.is_valid(value):
raise AttributeError("data_rate must be a `Rate`")

self._data_rate = value

@property
def humidity_data_ready(self):
def humidity_data_ready(self) -> bool:
"""Returns true if a new relative humidity measurement is available to be read"""
return self._humidity_status_bit

@property
def temperature_data_ready(self):
def temperature_data_ready(self) -> bool:
"""Returns true if a new temperature measurement is available to be read"""
return self._temperature_status_bit

def take_measurements(self):
def take_measurements(self) -> None:
"""Update the value of :attr:`relative_humidity` and :attr:`temperature` by taking a single
measurement. Only meaningful if :attr:`data_rate` is set to ``ONE_SHOT``"""
self._one_shot_bit = True
Expand Down
8 changes: 6 additions & 2 deletions examples/hts221_simpletest.py
Original file line number Diff line number Diff line change
Expand Up @@ -8,8 +8,12 @@
i2c = board.I2C()
hts = adafruit_hts221.HTS221(i2c)

data_rate = adafruit_hts221.Rate.label[hts.data_rate]
print("Using data rate of: {:.1f} Hz".format(data_rate))
print("")

while True:
print("Relative Humidity: %.2f %% rH" % hts.relative_humidity)
print("Temperature: %.2f C" % hts.temperature)
print("Relative Humidity: {:.2f} % rH".format(hts.relative_humidity))
print("Temperature: {:.2f} C".format(hts.temperature))
print("")
time.sleep(1)