diff --git a/adafruit_ht16k33/bargraph.py b/adafruit_ht16k33/bargraph.py index 815ea61..19eea73 100644 --- a/adafruit_ht16k33/bargraph.py +++ b/adafruit_ht16k33/bargraph.py @@ -12,6 +12,11 @@ from adafruit_ht16k33.ht16k33 import HT16K33 +try: + from typing import Optional +except ImportError: + pass + __version__ = "0.0.0-auto.0" __repo__ = "https://github.com/adafruit/Adafruit_CircuitPython_HT16K33.git" @@ -24,14 +29,14 @@ class Bicolor24(HT16K33): LED_GREEN = 2 LED_YELLOW = 3 - def __getitem__(self, key): + def __getitem__(self, key: int) -> Optional[bool]: # map to HT16K33 row (x) and column (y), see schematic x = key % 4 + 4 * (key // 12) y = key // 4 - 3 * (key // 12) # construct the color value and return it return self._pixel(x, y) | self._pixel(x + 8, y) << 1 - def __setitem__(self, key, value): + def __setitem__(self, key: int, value: bool): # map to HT16K33 row (x) and column (y), see schematic x = key % 4 + 4 * (key // 12) y = key // 4 - 3 * (key // 12) @@ -40,7 +45,7 @@ def __setitem__(self, key, value): # conditionally turn on green LED self._pixel(x + 8, y, value >> 1) - def fill(self, color): + def fill(self, color: bool): """Fill the whole display with the given color.""" what_it_was = self.auto_write self.auto_write = False diff --git a/adafruit_ht16k33/ht16k33.py b/adafruit_ht16k33/ht16k33.py index e95e312..07fbf97 100644 --- a/adafruit_ht16k33/ht16k33.py +++ b/adafruit_ht16k33/ht16k33.py @@ -14,6 +14,12 @@ from adafruit_bus_device import i2c_device from micropython import const +try: + from typing import Optional + from busio import I2C +except ImportError: + pass + __version__ = "0.0.0-auto.0" __repo__ = "https://github.com/adafruit/Adafruit_CircuitPython_HT16K33.git" @@ -33,7 +39,13 @@ class HT16K33: :param float brightness: 0.0 - 1.0 default brightness level. """ - def __init__(self, i2c, address=0x70, auto_write=True, brightness=1.0): + def __init__( + self, + i2c: I2C, + address: int = 0x70, + auto_write: bool = True, + brightness: float = 1.0, + ): self.i2c_device = i2c_device.I2CDevice(i2c, address) self._temp = bytearray(1) self._buffer = bytearray(17) @@ -45,7 +57,7 @@ def __init__(self, i2c, address=0x70, auto_write=True, brightness=1.0): self.blink_rate = 0 self.brightness = brightness - def _write_cmd(self, byte): + def _write_cmd(self, byte: bytearray): self._temp[0] = byte with self.i2c_device: self.i2c_device.write(self._temp) @@ -56,7 +68,7 @@ def blink_rate(self): return self._blink_rate @blink_rate.setter - def blink_rate(self, rate=None): + def blink_rate(self, rate: int = None): if not 0 <= rate <= 3: raise ValueError("Blink rate must be an integer in the range: 0-3") rate = rate & 0x03 @@ -69,7 +81,7 @@ def brightness(self): return self._brightness @brightness.setter - def brightness(self, brightness): + def brightness(self, brightness: float): if not 0.0 <= brightness <= 1.0: raise ValueError( "Brightness must be a decimal number in the range: 0.0-1.0" @@ -86,7 +98,7 @@ def auto_write(self): return self._auto_write @auto_write.setter - def auto_write(self, auto_write): + def auto_write(self, auto_write: bool): if isinstance(auto_write, bool): self._auto_write = auto_write else: @@ -99,7 +111,7 @@ def show(self): # bytes are the display register data to set. self.i2c_device.write(self._buffer) - def fill(self, color): + def fill(self, color: bool): """Fill the whole display with the given color.""" fill = 0xFF if color else 0x00 for i in range(16): @@ -107,7 +119,7 @@ def fill(self, color): if self._auto_write: self.show() - def _pixel(self, x, y, color=None): + def _pixel(self, x: int, y: int, color: Optional[bool] = None) -> Optional[bool]: addr = 2 * y + x // 8 mask = 1 << x % 8 if color is None: @@ -122,8 +134,8 @@ def _pixel(self, x, y, color=None): self.show() return None - def _set_buffer(self, i, value): + def _set_buffer(self, i: int, value: bool): self._buffer[i + 1] = value # Offset by 1 to move past register address. - def _get_buffer(self, i): + def _get_buffer(self, i: int) -> bool: return self._buffer[i + 1] # Offset by 1 to move past register address. diff --git a/adafruit_ht16k33/matrix.py b/adafruit_ht16k33/matrix.py index 5bffbe6..51085e1 100755 --- a/adafruit_ht16k33/matrix.py +++ b/adafruit_ht16k33/matrix.py @@ -10,6 +10,12 @@ """ from adafruit_ht16k33.ht16k33 import HT16K33 +try: + from typing import Optional + from PIL import Image +except ImportError: + pass + __version__ = "0.0.0-auto.0" __repo__ = "https://github.com/adafruit/Adafruit_CircuitPython_HT16K33.git" @@ -20,7 +26,7 @@ class Matrix8x8(HT16K33): _columns = 8 _rows = 8 - def pixel(self, x, y, color=None): + def pixel(self, x: int, y: int, color: Optional[bool] = None) -> Optional[bool]: """Get or set the color of a given pixel.""" if not 0 <= x <= 7: return None @@ -29,16 +35,16 @@ def pixel(self, x, y, color=None): x = (x - 1) % 8 return super()._pixel(x, y, color) - def __getitem__(self, key): + def __getitem__(self, key: int) -> Optional[bool]: x, y = key return self.pixel(x, y) - def __setitem__(self, key, value): + def __setitem__(self, key: int, value: bool): x, y = key self.pixel(x, y, value) # pylint: disable=too-many-branches - def shift(self, x, y, rotate=False): + def shift(self, x: int, y: int, rotate: bool = False): """ Shift pixels by x and y @@ -80,7 +86,7 @@ def shift(self, x, y, rotate=False): # pylint: enable=too-many-branches - def shift_right(self, rotate=False): + def shift_right(self, rotate: bool = False): """ Shift all pixels right @@ -88,7 +94,7 @@ def shift_right(self, rotate=False): """ self.shift(1, 0, rotate) - def shift_left(self, rotate=False): + def shift_left(self, rotate: bool = False): """ Shift all pixels left @@ -96,7 +102,7 @@ def shift_left(self, rotate=False): """ self.shift(-1, 0, rotate) - def shift_up(self, rotate=False): + def shift_up(self, rotate: bool = False): """ Shift all pixels up @@ -104,7 +110,7 @@ def shift_up(self, rotate=False): """ self.shift(0, 1, rotate) - def shift_down(self, rotate=False): + def shift_down(self, rotate: bool = False): """ Shift all pixels down @@ -205,7 +211,7 @@ def fill(self, color): if self._auto_write: self.show() - def image(self, img): + def image(self, img: Image): """Set buffer to value of Python Imaging Library image. The image should be a size equal to the display size.""" imwidth, imheight = img.size diff --git a/adafruit_ht16k33/segments.py b/adafruit_ht16k33/segments.py index 228219a..81cb94d 100755 --- a/adafruit_ht16k33/segments.py +++ b/adafruit_ht16k33/segments.py @@ -11,6 +11,12 @@ from time import sleep from adafruit_ht16k33.ht16k33 import HT16K33 +try: + from typing import Union, List, Tuple + from busio import I2C +except ImportError: + pass + __version__ = "0.0.0-auto.0" __repo__ = "https://github.com/adafruit/Adafruit_CircuitPython_HT16K33.git" @@ -138,7 +144,7 @@ class Seg14x4(HT16K33): """Alpha-numeric, 14-segment display.""" - def print(self, value, decimal=0): + def print(self, value: Union[str, int, float], decimal: int = 0): """Print the value to the display.""" if isinstance(value, (str)): self._text(value) @@ -149,19 +155,19 @@ def print(self, value, decimal=0): if self._auto_write: self.show() - def print_hex(self, value): + def print_hex(self, value: int): """Print the value as a hexidecimal string to the display.""" if isinstance(value, int): self.print("{0:X}".format(value)) else: self.print(value) - def __setitem__(self, key, value): + def __setitem__(self, key: str, value: Union[str, int, float]): self._put(value, key) if self._auto_write: self.show() - def scroll(self, count=1): + def scroll(self, count: int = 1): """Scroll the display by specified number of places.""" if count >= 0: offset = 0 @@ -170,7 +176,7 @@ def scroll(self, count=1): for i in range(6): self._set_buffer(i + offset, self._get_buffer(i + 2 * count)) - def _put(self, char, index=0): + def _put(self, char: str, index: int = 0): """Put a character at the specified place.""" if not 0 <= index <= 3: return @@ -185,19 +191,19 @@ def _put(self, char, index=0): self._set_buffer(index * 2, CHARS[1 + character]) self._set_buffer(index * 2 + 1, CHARS[character]) - def _push(self, char): + def _push(self, char: str): """Scroll the display and add a character at the end.""" if char != "." or self._get_buffer(7) & 0b01000000: self.scroll() self._put(" ", 3) self._put(char, 3) - def _text(self, text): + def _text(self, text: str): """Display the specified text.""" for character in text: self._push(character) - def _number(self, number, decimal=0): + def _number(self, number: Union[int, float], decimal: int = 0): """ Display a floating point or integer number on the Adafruit HT16K33 based displays @@ -247,12 +253,12 @@ def _number(self, number, decimal=0): return txt - def set_digit_raw(self, index, bitmask): + def set_digit_raw(self, index: int, bitmask: Union[int, List, Tuple]): """Set digit at position to raw bitmask value. Position should be a value of 0 to 3 with 0 being the left most character on the display. bitmask should be 2 bytes such as: 0xFFFF - If can be passed as an integer, list, or tuple + It can be passed as an integer, list, or tuple """ if not isinstance(index, int) or not 0 <= index <= 3: raise ValueError("Index value must be an integer in the range: 0-3") @@ -270,7 +276,7 @@ def set_digit_raw(self, index, bitmask): if self._auto_write: self.show() - def marquee(self, text, delay=0.25, loop=True): + def marquee(self, text: str, delay: float = 0.25, loop: bool = True): """ Automatically scroll the text at the specified delay between characters @@ -288,7 +294,7 @@ def marquee(self, text, delay=0.25, loop=True): else: self._scroll_marquee(text, delay) - def _scroll_marquee(self, text, delay): + def _scroll_marquee(self, text: str, delay: float): """Scroll through the text string once using the delay""" char_is_dot = False for character in text: @@ -306,12 +312,12 @@ class Seg7x4(Seg14x4): POSITIONS = (0, 2, 6, 8) # The positions of characters. - def __init__(self, i2c, address=0x70, auto_write=True): + def __init__(self, i2c: I2C, address: int = 0x70, auto_write: bool = True): super().__init__(i2c, address, auto_write) # Use colon for controling two-dots indicator at the center (index 0) self._colon = Colon(self) - def scroll(self, count=1): + def scroll(self, count: int = 1): """Scroll the display by specified number of places.""" if count >= 0: offset = 0 @@ -322,7 +328,7 @@ def scroll(self, count=1): self.POSITIONS[i + offset], self._get_buffer(self.POSITIONS[i + count]) ) - def _push(self, char): + def _push(self, char: str): """Scroll the display and add a character at the end.""" if char in ":;": self._put(char) @@ -332,7 +338,7 @@ def _push(self, char): self._put(" ", 3) self._put(char, 3) - def _put(self, char, index=0): + def _put(self, char: str, index: int = 0): """Put a character at the specified place.""" if not 0 <= index <= 3: return @@ -360,7 +366,7 @@ def _put(self, char, index=0): return self._set_buffer(index, NUMBERS[character]) - def set_digit_raw(self, index, bitmask): + def set_digit_raw(self, index: int, bitmask: int): """Set digit at position to raw bitmask value. Position should be a value of 0 to 3 with 0 being the left most digit on the display. """ @@ -379,7 +385,7 @@ def colon(self): return self._colon[0] @colon.setter - def colon(self, turn_on): + def colon(self, turn_on: bool): self._colon[0] = turn_on @@ -387,13 +393,13 @@ class BigSeg7x4(Seg7x4): """Numeric 7-segment display. It has the same methods as the alphanumeric display, but only supports displaying a limited set of characters.""" - def __init__(self, i2c, address=0x70, auto_write=True): + def __init__(self, i2c: I2C, address: int = 0x70, auto_write: bool = True): super().__init__(i2c, address, auto_write) # Use colon for controling two-dots indicator at the center (index 0) # or the two-dots indicators at the left (index 1) self.colon = Colon(self, 2) - def _setindicator(self, index, value): + def _setindicator(self, index: int, value: bool): """Set side LEDs (dots) Index is as follow : * 0 : two dots at the center @@ -410,7 +416,7 @@ def _setindicator(self, index, value): if self._auto_write: self.show() - def _getindicator(self, index): + def _getindicator(self, index: int): """Get side LEDs (dots) See setindicator() for indexes """ @@ -423,7 +429,7 @@ def top_left_dot(self): return bool(self._getindicator(1)) @top_left_dot.setter - def top_left_dot(self, value): + def top_left_dot(self, value: bool): self._setindicator(1, value) @property @@ -432,7 +438,7 @@ def bottom_left_dot(self): return bool(self._getindicator(2)) @bottom_left_dot.setter - def bottom_left_dot(self, value): + def bottom_left_dot(self, value: bool): self._setindicator(2, value) @property @@ -441,7 +447,7 @@ def ampm(self): return bool(self._getindicator(3)) @ampm.setter - def ampm(self, value): + def ampm(self, value: bool): self._setindicator(3, value) @@ -452,11 +458,11 @@ class Colon: MASKS = (0x02, 0x0C) - def __init__(self, disp, num_of_colons=1): + def __init__(self, disp: Seg7x4, num_of_colons: int = 1): self._disp = disp self._num_of_colons = num_of_colons - def __setitem__(self, key, value): + def __setitem__(self, key: int, value: bool): if key > self._num_of_colons - 1: raise ValueError("Trying to set a non-existent colon.") current = self._disp._get_buffer(0x04) @@ -467,7 +473,7 @@ def __setitem__(self, key, value): if self._disp.auto_write: self._disp.show() - def __getitem__(self, key): + def __getitem__(self, key: int) -> bool: if key > self._num_of_colons - 1: raise ValueError("Trying to access a non-existent colon.") return bool(self._disp._get_buffer(0x04) & self.MASKS[key]) diff --git a/requirements.txt b/requirements.txt index f675e3b..6d5905c 100644 --- a/requirements.txt +++ b/requirements.txt @@ -4,3 +4,4 @@ Adafruit-Blinka adafruit-circuitpython-busdevice +pillow