diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml index fff3aa9..1dad804 100644 --- a/.github/workflows/build.yml +++ b/.github/workflows/build.yml @@ -40,7 +40,7 @@ jobs: source actions-ci/install.sh - name: Pip install pylint, black, & Sphinx run: | - pip install --force-reinstall pylint==1.9.2 black==19.10b0 Sphinx sphinx-rtd-theme + pip install --force-reinstall pylint black==19.10b0 Sphinx sphinx-rtd-theme - name: Library version run: git describe --dirty --always --tags - name: PyLint diff --git a/.pylintrc b/.pylintrc index 55d2db8..d8f0ee8 100644 --- a/.pylintrc +++ b/.pylintrc @@ -119,7 +119,7 @@ spelling-store-unknown-words=no [MISCELLANEOUS] # List of note tags to take in consideration, separated by a comma. -#notes=FIXME,XXX,TODO +# notes=FIXME,XXX,TODO notes=FIXME,XXX @@ -301,7 +301,7 @@ function-rgx=(([a-z][a-z0-9_]{2,30})|(_[a-z0-9_]*))$ # Good variable names which should always be accepted, separated by a comma # good-names=i,j,k,ex,Run,_ -good-names=r,g,b,i,j,k,n,x,y,z,ex,Run,_ +good-names=r,g,b,w,i,j,k,n,x,y,z,ex,ok,Run,_ # Include a hint for the correct naming format with invalid-name include-naming-hint=no @@ -423,7 +423,7 @@ max-returns=6 max-statements=50 # Minimum number of public methods for a class (see R0903). -min-public-methods=2 +min-public-methods=1 [EXCEPTIONS] diff --git a/adafruit_ht16k33/bargraph.py b/adafruit_ht16k33/bargraph.py index 0057a80..ca89f3e 100644 --- a/adafruit_ht16k33/bargraph.py +++ b/adafruit_ht16k33/bargraph.py @@ -33,6 +33,7 @@ __version__ = "0.0.0-auto.0" __repo__ = "https://github.com/adafruit/Adafruit_CircuitPython_HT16K33.git" + class Bicolor24(HT16K33): """Bi-color 24-bar bargraph display.""" @@ -46,7 +47,7 @@ def __getitem__(self, key): 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 + return self._pixel(x, y) | self._pixel(x + 8, y) << 1 def __setitem__(self, key, value): # map to HT16K33 row (x) and column (y), see schematic @@ -55,7 +56,7 @@ def __setitem__(self, key, value): # conditionally turn on red LED self._pixel(x, y, value & 0x01) # conditionally turn on green LED - self._pixel(x+8, y, value >> 1) + self._pixel(x + 8, y, value >> 1) def fill(self, color): """Fill the whole display with the given color.""" diff --git a/adafruit_ht16k33/ht16k33.py b/adafruit_ht16k33/ht16k33.py index dff931c..f6047ed 100644 --- a/adafruit_ht16k33/ht16k33.py +++ b/adafruit_ht16k33/ht16k33.py @@ -49,6 +49,7 @@ class HT16K33: set. If False, `show` must be called explicitly. :param float brightness: 0.0 - 1.0 default brightness level. """ + def __init__(self, i2c, address=0x70, auto_write=True, brightness=1.0): self.i2c_device = i2c_device.I2CDevice(i2c, address) self._temp = bytearray(1) @@ -74,11 +75,10 @@ def blink_rate(self): @blink_rate.setter def blink_rate(self, rate=None): if not 0 <= rate <= 3: - raise ValueError('Blink rate must be an integer in the range: 0-3') + raise ValueError("Blink rate must be an integer in the range: 0-3") rate = rate & 0x03 self._blink_rate = rate - self._write_cmd(_HT16K33_BLINK_CMD | - _HT16K33_BLINK_DISPLAYON | rate << 1) + self._write_cmd(_HT16K33_BLINK_CMD | _HT16K33_BLINK_DISPLAYON | rate << 1) @property def brightness(self): @@ -88,7 +88,9 @@ def brightness(self): @brightness.setter def brightness(self, brightness): if not 0.0 <= brightness <= 1.0: - raise ValueError('Brightness must be a decimal number in the range: 0.0-1.0') + raise ValueError( + "Brightness must be a decimal number in the range: 0.0-1.0" + ) self._brightness = brightness xbright = round(15 * brightness) @@ -105,7 +107,7 @@ def auto_write(self, auto_write): if isinstance(auto_write, bool): self._auto_write = auto_write else: - raise ValueError('Must set to either True or False.') + raise ValueError("Must set to either True or False.") def show(self): """Refresh the display and show the changes.""" @@ -116,14 +118,14 @@ def show(self): def fill(self, color): """Fill the whole display with the given color.""" - fill = 0xff if color else 0x00 + fill = 0xFF if color else 0x00 for i in range(16): - self._buffer[i+1] = fill + self._buffer[i + 1] = fill if self._auto_write: self.show() def _pixel(self, x, y, color=None): - addr = 2*y + x // 8 + addr = 2 * y + x // 8 mask = 1 << x % 8 if color is None: return bool(self._buffer[addr + 1] & mask) @@ -138,7 +140,7 @@ def _pixel(self, x, y, color=None): return None def _set_buffer(self, i, value): - self._buffer[i+1] = value # Offset by 1 to move past register address. + self._buffer[i + 1] = value # Offset by 1 to move past register address. def _get_buffer(self, i): - return self._buffer[i+1] # Offset by 1 to move past register address. + 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 b57d6e2..843ac00 100755 --- a/adafruit_ht16k33/matrix.py +++ b/adafruit_ht16k33/matrix.py @@ -30,8 +30,10 @@ __version__ = "0.0.0-auto.0" __repo__ = "https://github.com/adafruit/Adafruit_CircuitPython_HT16K33.git" + class Matrix8x8(HT16K33): """A single matrix.""" + _columns = 8 _rows = 8 @@ -52,7 +54,7 @@ def __setitem__(self, key, value): x, y = key self.pixel(x, y, value) - #pylint: disable=too-many-branches + # pylint: disable=too-many-branches def shift(self, x, y, rotate=False): """ Shift pixels by x and y @@ -61,28 +63,28 @@ def shift(self, x, y, rotate=False): """ auto_write = self.auto_write self._auto_write = False - if x > 0: # Shift Right + if x > 0: # Shift Right for _ in range(x): for row in range(0, self.rows): last_pixel = self[self.columns - 1, row] if rotate else 0 for col in range(self.columns - 1, 0, -1): self[col, row] = self[col - 1, row] self[0, row] = last_pixel - elif x < 0: # Shift Left + elif x < 0: # Shift Left for _ in range(-x): for row in range(0, self.rows): last_pixel = self[0, row] if rotate else 0 for col in range(0, self.columns - 1): self[col, row] = self[col + 1, row] self[self.columns - 1, row] = last_pixel - if y > 0: # Shift Up + if y > 0: # Shift Up for _ in range(y): for col in range(0, self.columns): last_pixel = self[col, self.rows - 1] if rotate else 0 for row in range(self.rows - 1, 0, -1): self[col, row] = self[col, row - 1] self[col, 0] = last_pixel - elif y < 0: # Shift Down + elif y < 0: # Shift Down for _ in range(-y): for col in range(0, self.columns): last_pixel = self[col, 0] if rotate else 0 @@ -92,7 +94,8 @@ def shift(self, x, y, rotate=False): self._auto_write = auto_write if auto_write: self.show() - #pylint: enable=too-many-branches + + # pylint: enable=too-many-branches def shift_right(self, rotate=False): """ @@ -131,12 +134,15 @@ def image(self, img): be in 1 bit mode and a size equal to the display size.""" imwidth, imheight = img.size if imwidth != self.columns or imheight != self.rows: - raise ValueError('Image must be same dimensions as display ({0}x{1}).' \ - .format(self.columns, self.rows)) + raise ValueError( + "Image must be same dimensions as display ({0}x{1}).".format( + self.columns, self.rows + ) + ) # Grab all the pixels from the image, faster than getpixel. - pixels = img.convert('1').load() + pixels = img.convert("1").load() # Iterate through the pixels - for x in range(self.columns): # yes this double loop is slow, + for x in range(self.columns): # yes this double loop is slow, for y in range(self.rows): # but these displays are small! self.pixel(x, y, pixels[(x, y)]) if self._auto_write: @@ -152,8 +158,10 @@ def rows(self): """Read-only property for number of rows""" return self._rows + class Matrix16x8(Matrix8x8): """The matrix wing.""" + _columns = 16 def pixel(self, x, y, color=None): @@ -165,10 +173,12 @@ def pixel(self, x, y, color=None): if x >= 8: x -= 8 y += 8 - return super()._pixel(y, x, color) + return super()._pixel(y, x, color) # pylint: disable=arguments-out-of-order + class MatrixBackpack16x8(Matrix16x8): """A double matrix backpack.""" + def pixel(self, x, y, color=None): """Get or set the color of a given pixel.""" if not 0 <= x <= 15: @@ -177,6 +187,7 @@ def pixel(self, x, y, color=None): return None return super()._pixel(x, y, color) + class Matrix8x8x2(Matrix8x8): """A bi-color matrix.""" @@ -200,8 +211,8 @@ def pixel(self, x, y, color=None): def fill(self, color): """Fill the whole display with the given color.""" - fill1 = 0xff if color & 0x01 else 0x00 - fill2 = 0xff if color & 0x02 else 0x00 + fill1 = 0xFF if color & 0x01 else 0x00 + fill2 = 0xFF if color & 0x02 else 0x00 for i in range(8): self._set_buffer(i * 2, fill1) self._set_buffer(i * 2 + 1, fill2) @@ -213,12 +224,15 @@ def image(self, img): be a size equal to the display size.""" imwidth, imheight = img.size if imwidth != self.columns or imheight != self.rows: - raise ValueError('Image must be same dimensions as display ({0}x{1}).' \ - .format(self.columns, self.rows)) + raise ValueError( + "Image must be same dimensions as display ({0}x{1}).".format( + self.columns, self.rows + ) + ) # Grab all the pixels from the image, faster than getpixel. - pixels = img.convert('RGB').load() + pixels = img.convert("RGB").load() # Iterate through the pixels - for x in range(self.columns): # yes this double loop is slow, + for x in range(self.columns): # yes this double loop is slow, for y in range(self.rows): # but these displays are small! if pixels[(x, y)] == (255, 0, 0): self.pixel(x, y, self.LED_RED) diff --git a/adafruit_ht16k33/segments.py b/adafruit_ht16k33/segments.py index f754c07..0f7aff7 100755 --- a/adafruit_ht16k33/segments.py +++ b/adafruit_ht16k33/segments.py @@ -31,6 +31,7 @@ __version__ = "0.0.0-auto.0" __repo__ = "https://github.com/adafruit/Adafruit_CircuitPython_HT16K33.git" +# fmt: off CHARS = ( 0b00000000, 0b00000000, # 0b01000000, 0b00000110, # ! @@ -129,26 +130,28 @@ 0b00000101, 0b00100000, # ~ 0b00111111, 0b11111111, ) +# fmt: on NUMBERS = ( - 0x3F, # 0 - 0x06, # 1 - 0x5B, # 2 - 0x4F, # 3 - 0x66, # 4 - 0x6D, # 5 - 0x7D, # 6 - 0x07, # 7 - 0x7F, # 8 - 0x6F, # 9 - 0x77, # a - 0x7C, # b - 0x39, # C - 0x5E, # d - 0x79, # E - 0x71, # F - 0x40, # - + 0x3F, # 0 + 0x06, # 1 + 0x5B, # 2 + 0x4F, # 3 + 0x66, # 4 + 0x6D, # 5 + 0x7D, # 6 + 0x07, # 7 + 0x7F, # 8 + 0x6F, # 9 + 0x77, # a + 0x7C, # b + 0x39, # C + 0x5E, # d + 0x79, # E + 0x71, # F + 0x40, # - ) + class Seg14x4(HT16K33): """Alpha-numeric, 14-segment display.""" @@ -159,14 +162,14 @@ def print(self, value, decimal=0): elif isinstance(value, (int, float)): self._number(value, decimal) else: - raise ValueError('Unsupported display value type: {}'.format(type(value))) + raise ValueError("Unsupported display value type: {}".format(type(value))) if self._auto_write: self.show() def print_hex(self, value): """Print the value as a hexidecimal string to the display.""" if isinstance(value, int): - self.print('{0:X}'.format(value)) + self.print("{0:X}".format(value)) else: self.print(value) @@ -190,8 +193,10 @@ def _put(self, char, index=0): return if not 32 <= ord(char) <= 127: return - if char == '.': - self._set_buffer(index * 2 + 1, self._get_buffer(index * 2 + 1) | 0b01000000) + if char == ".": + self._set_buffer( + index * 2 + 1, self._get_buffer(index * 2 + 1) | 0b01000000 + ) return character = ord(char) * 2 - 64 self._set_buffer(index * 2, CHARS[1 + character]) @@ -199,9 +204,9 @@ def _put(self, char, index=0): def _push(self, char): """Scroll the display and add a character at the end.""" - if char != '.' or self._get_buffer(7) & 0b01000000: + if char != "." or self._get_buffer(7) & 0b01000000: self.scroll() - self._put(' ', 3) + self._put(" ", 3) self._put(char, 3) def _text(self, text): @@ -210,7 +215,7 @@ def _text(self, text): self._push(character) def _number(self, number, decimal=0): - ''' + """ Display a floating point or integer number on the Adafruit HT16K33 based displays Param: number - The floating point or integer number to be displayed, which must be @@ -220,32 +225,34 @@ def _number(self, number, decimal=0): is greater than zero, or the input number is an integer if decimal is zero. Returns: The output text string to be displayed. - ''' + """ auto_write = self._auto_write self._auto_write = False stnum = str(number) - dot = stnum.find('.') + dot = stnum.find(".") - if ((len(stnum) > 5) or ((len(stnum) > 4) and (dot < 0))): - raise ValueError("Input overflow - {0} is too large for the display!".format(number)) + if (len(stnum) > 5) or ((len(stnum) > 4) and (dot < 0)): + raise ValueError( + "Input overflow - {0} is too large for the display!".format(number) + ) if dot < 0: - # No decimal point (Integer) + # No decimal point (Integer) places = len(stnum) else: places = len(stnum[:dot]) - if places <= 0 and decimal > 0: + if places <= 0 < decimal: self.fill(False) places = 4 - if '.' in stnum: + if "." in stnum: places += 1 # Set decimal places, if number of decimal places is specified (decimal > 0) - if (places > 0 and decimal > 0 and dot > 0 and (len(stnum[places:]) > decimal)): - txt = stnum[:dot + decimal + 1] + if places > 0 < decimal < len(stnum[places:]) and dot > 0: + txt = stnum[: dot + decimal + 1] elif places > 0: txt = stnum[:places] @@ -265,7 +272,7 @@ def set_digit_raw(self, index, bitmask): If 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') + raise ValueError("Index value must be an integer in the range: 0-3") if isinstance(bitmask, (tuple, list)): bitmask = ((bitmask[0] & 0xFF) << 8) | (bitmask[1] & 0xFF) @@ -304,15 +311,17 @@ def _scroll_marquee(self, text, delay): for character in text: self.print(character) # Add delay if character is not a dot or more than 2 in a row - if character != '.' or char_is_dot: + if character != "." or char_is_dot: sleep(delay) - char_is_dot = (character == '.') + char_is_dot = character == "." self.show() + class Seg7x4(Seg14x4): """Numeric 7-segment display. It has the same methods as the alphanumeric display, but only supports displaying a limited set of characters.""" - POSITIONS = (0, 2, 6, 8) # The positions of characters. + + POSITIONS = (0, 2, 6, 8) # The positions of characters. def __init__(self, i2c, address=0x70, auto_write=True): super().__init__(i2c, address, auto_write) @@ -326,17 +335,18 @@ def scroll(self, count=1): else: offset = 1 for i in range(3): - self._set_buffer(self.POSITIONS[i + offset], - self._get_buffer(self.POSITIONS[i + count])) + self._set_buffer( + self.POSITIONS[i + offset], self._get_buffer(self.POSITIONS[i + count]) + ) def _push(self, char): """Scroll the display and add a character at the end.""" - if char in ':;': + if char in ":;": self._put(char) else: - if char != '.' or self._get_buffer(self.POSITIONS[3]) & 0b10000000: + if char != "." or self._get_buffer(self.POSITIONS[3]) & 0b10000000: self.scroll() - self._put(' ', 3) + self._put(" ", 3) self._put(char, 3) def _put(self, char, index=0): @@ -345,22 +355,22 @@ def _put(self, char, index=0): return char = char.lower() index = self.POSITIONS[index] - if char == '.': + if char == ".": self._set_buffer(index, self._get_buffer(index) | 0b10000000) return - if char in 'abcdef': + if char in "abcdef": character = ord(char) - 97 + 10 - elif char == '-': + elif char == "-": character = 16 - elif char in '0123456789': + elif char in "0123456789": character = ord(char) - 48 - elif char == ' ': + elif char == " ": self._set_buffer(index, 0x00) return - elif char == ':': + elif char == ":": self._set_buffer(4, 0x02) return - elif char == ';': + elif char == ";": self._set_buffer(4, 0x00) return else: @@ -372,7 +382,7 @@ def set_digit_raw(self, index, bitmask): of 0 to 3 with 0 being the left most digit on the display. """ if not isinstance(index, int) or not 0 <= index <= 3: - raise ValueError('Index value must be an integer in the range: 0-3') + raise ValueError("Index value must be an integer in the range: 0-3") # Set the digit bitmask value at the appropriate position. self._set_buffer(self.POSITIONS[index], bitmask & 0xFF) @@ -389,9 +399,11 @@ def colon(self): def colon(self, turn_on): self._colon[0] = turn_on + 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): super().__init__(i2c, address, auto_write) # Use colon for controling two-dots indicator at the center (index 0) @@ -449,9 +461,11 @@ def ampm(self): def ampm(self, value): self._setindicator(3, value) -class Colon(): + +class Colon: """Helper class for controlling the colons. Not intended for direct use.""" - #pylint: disable=protected-access + + # pylint: disable=protected-access MASKS = (0x02, 0x0C) diff --git a/docs/conf.py b/docs/conf.py index 147f41e..28e23e3 100644 --- a/docs/conf.py +++ b/docs/conf.py @@ -2,7 +2,8 @@ import os import sys -sys.path.insert(0, os.path.abspath('..')) + +sys.path.insert(0, os.path.abspath("..")) # -- General configuration ------------------------------------------------ @@ -10,9 +11,9 @@ # extensions coming with Sphinx (named 'sphinx.ext.*') or your custom # ones. extensions = [ - 'sphinx.ext.autodoc', - 'sphinx.ext.intersphinx', - 'sphinx.ext.viewcode', + "sphinx.ext.autodoc", + "sphinx.ext.intersphinx", + "sphinx.ext.viewcode", ] # Uncomment the below if you use native CircuitPython modules such as @@ -20,30 +21,36 @@ # autodoc module docs will fail to generate with a warning. # autodoc_mock_imports = ["adafruit_bus_device", "micropython"] -intersphinx_mapping = {'python': ('https://docs.python.org/3.4', None),'BusDevice': ('https://circuitpython.readthedocs.io/projects/busdevice/en/latest/', None), - 'CircuitPython': ('https://circuitpython.readthedocs.io/en/latest/', None)} +intersphinx_mapping = { + "python": ("https://docs.python.org/3.4", None), + "BusDevice": ( + "https://circuitpython.readthedocs.io/projects/busdevice/en/latest/", + None, + ), + "CircuitPython": ("https://circuitpython.readthedocs.io/en/latest/", None), +} # Add any paths that contain templates here, relative to this directory. -templates_path = ['_templates'] +templates_path = ["_templates"] -source_suffix = '.rst' +source_suffix = ".rst" # The master toctree document. -master_doc = 'index' +master_doc = "index" # General information about the project. -project = u'Adafruit HT16K33 Library' -copyright = u'2016 Radomir Dopieralski' -author = u'Radomir Dopieralski' +project = u"Adafruit HT16K33 Library" +copyright = u"2016 Radomir Dopieralski" +author = u"Radomir Dopieralski" # The version info for the project you're documenting, acts as replacement for # |version| and |release|, also used in various other places throughout the # built documents. # # The short X.Y version. -version = u'1.0' +version = u"1.0" # The full version, including alpha/beta/rc tags. -release = u'1.0' +release = u"1.0" # The language for content autogenerated by Sphinx. Refer to documentation # for a list of supported languages. @@ -55,7 +62,7 @@ # List of patterns, relative to source directory, that match files and # directories to ignore when looking for source files. # This patterns also effect to html_static_path and html_extra_path -exclude_patterns = ['_build', 'Thumbs.db', '.DS_Store', '.env', 'CODE_OF_CONDUCT.md'] +exclude_patterns = ["_build", "Thumbs.db", ".DS_Store", ".env", "CODE_OF_CONDUCT.md"] # The reST default role (used for this markup: `text`) to use for all # documents. @@ -67,7 +74,7 @@ add_function_parentheses = True # The name of the Pygments (syntax highlighting) style to use. -pygments_style = 'sphinx' +pygments_style = "sphinx" # If true, `todo` and `todoList` produce output, else they produce nothing. todo_include_todos = False @@ -81,59 +88,62 @@ # The theme to use for HTML and HTML Help pages. See the documentation for # a list of builtin themes. # -on_rtd = os.environ.get('READTHEDOCS', None) == 'True' +on_rtd = os.environ.get("READTHEDOCS", None) == "True" if not on_rtd: # only import and set the theme if we're building docs locally try: import sphinx_rtd_theme - html_theme = 'sphinx_rtd_theme' - html_theme_path = [sphinx_rtd_theme.get_html_theme_path(), '.'] + + html_theme = "sphinx_rtd_theme" + html_theme_path = [sphinx_rtd_theme.get_html_theme_path(), "."] except: - html_theme = 'default' - html_theme_path = ['.'] + html_theme = "default" + html_theme_path = ["."] else: - html_theme_path = ['.'] + html_theme_path = ["."] # Add any paths that contain custom static files (such as style sheets) here, # relative to this directory. They are copied after the builtin static files, # so a file named "default.css" will overwrite the builtin "default.css". -html_static_path = ['_static'] +html_static_path = ["_static"] # The name of an image file (relative to this directory) to use as a favicon of # the docs. This file should be a Windows icon file (.ico) being 16x16 or 32x32 # pixels large. # -html_favicon = '_static/favicon.ico' +html_favicon = "_static/favicon.ico" # Output file base name for HTML help builder. -htmlhelp_basename = 'AdafruitHT16K33Librarydoc' +htmlhelp_basename = "AdafruitHT16K33Librarydoc" # -- Options for LaTeX output --------------------------------------------- latex_elements = { - # The paper size ('letterpaper' or 'a4paper'). - # - # 'papersize': 'letterpaper', - - # The font size ('10pt', '11pt' or '12pt'). - # - # 'pointsize': '10pt', - - # Additional stuff for the LaTeX preamble. - # - # 'preamble': '', - - # Latex figure (float) alignment - # - # 'figure_align': 'htbp', + # The paper size ('letterpaper' or 'a4paper'). + # + # 'papersize': 'letterpaper', + # The font size ('10pt', '11pt' or '12pt'). + # + # 'pointsize': '10pt', + # Additional stuff for the LaTeX preamble. + # + # 'preamble': '', + # Latex figure (float) alignment + # + # 'figure_align': 'htbp', } # Grouping the document tree into LaTeX files. List of tuples # (source start file, target name, title, # author, documentclass [howto, manual, or own class]). latex_documents = [ - (master_doc, 'AdafruitHT16K33Library.tex', u'Adafruit HT16K33 Library Documentation', - author, 'manual'), + ( + master_doc, + "AdafruitHT16K33Library.tex", + u"Adafruit HT16K33 Library Documentation", + author, + "manual", + ), ] # -- Options for manual page output --------------------------------------- @@ -141,8 +151,13 @@ # One entry per manual page. List of tuples # (source start file, name, description, authors, manual section). man_pages = [ - (master_doc, 'adafruitHT16K33library', u'Adafruit HT16K33 Library Documentation', - [author], 1) + ( + master_doc, + "adafruitHT16K33library", + u"Adafruit HT16K33 Library Documentation", + [author], + 1, + ) ] # -- Options for Texinfo output ------------------------------------------- @@ -151,7 +166,13 @@ # (source start file, target name, title, author, # dir menu entry, description, category) texinfo_documents = [ - (master_doc, 'AdafruitHT16K33Library', u'Adafruit HT16K33 Library Documentation', - author, 'AdafruitHT16K33Library', 'One line description of project.', - 'Miscellaneous'), + ( + master_doc, + "AdafruitHT16K33Library", + u"Adafruit HT16K33 Library Documentation", + author, + "AdafruitHT16K33Library", + "One line description of project.", + "Miscellaneous", + ), ] diff --git a/examples/ht16k33_animation_demo.py b/examples/ht16k33_animation_demo.py index d12f1e5..3c9f9fb 100644 --- a/examples/ht16k33_animation_demo.py +++ b/examples/ht16k33_animation_demo.py @@ -16,20 +16,20 @@ # N = 16384 -M = 8192 -L = 4096 -K = 2048 -J = 1024 -I = 512 -H = 256 -G2= 128 -G1= 64 -F = 32 -E = 16 -D = 8 -C = 4 -B = 2 -A = 1 +M = 8192 +L = 4096 +K = 2048 +J = 1024 +I = 512 +H = 256 +G2 = 128 +G1 = 64 +F = 32 +E = 16 +D = 8 +C = 4 +B = 2 +A = 1 # The number of seconds to delay between writing segments DEFAULT_CHAR_DELAY_SEC = 0.2 @@ -49,8 +49,9 @@ display = Seg14x4(i2c, auto_write=False) display.brightness = DEFAULT_DISPLAY_BRIGHTNESS + def animate(digits, bitmasks, delay=DEFAULT_CHAR_DELAY_SEC, auto_write=True): - ''' + """ Main driver for all alphanumeric display animations (WIP!!!) Param: digits - a list of the digits to write to, in order, like [0, 1, 3]. The digits are 0 to 3 starting at the left most digit. @@ -59,29 +60,33 @@ def animate(digits, bitmasks, delay=DEFAULT_CHAR_DELAY_SEC, auto_write=True): Param: auto_write - Whether to actually write to the display immediately or not. Returns: Nothing - ''' + """ if not isinstance(digits, list): raise ValueError("The first parameter MUST be a list!") - elif not isinstance(bitmasks, list): + if not isinstance(bitmasks, list): raise ValueError("The second parameter MUST be a list!") - elif delay < 0: + if delay < 0: raise ValueError("The delay between frames must be positive!") - else: - for dig in digits: - if not 0 <= dig <= 3: - raise ValueError('Digit value must be \ - an integer in the range: 0-3') + for dig in digits: + if not 0 <= dig <= 3: + raise ValueError( + "Digit value must be \ + an integer in the range: 0-3" + ) + + for bits in bitmasks: + if not 0 <= bits <= 0xFFFF: + raise ValueError( + "Bitmask value must be an \ + integer in the range: 0-65535" + ) - for bits in bitmasks: - if not 0 <= bits <= 0xFFFF: - raise ValueError('Bitmask value must be an \ - integer in the range: 0-65535') + display.set_digit_raw(dig, bits) - display.set_digit_raw(dig, bits) + if auto_write: + display.show() + sleep(delay) - if auto_write: - display.show() - sleep(delay) def chase_forward_and_reverse(delay=DEFAULT_CHAR_DELAY_SEC, cycles=DEFAULT_CYCLES): cy = 0 @@ -102,6 +107,7 @@ def chase_forward_and_reverse(delay=DEFAULT_CHAR_DELAY_SEC, cycles=DEFAULT_CYCLE cy += 1 + def prelude_to_spinners(delay=DEFAULT_CHAR_DELAY_SEC, cycles=DEFAULT_CYCLES): cy = 0 auto_write = False @@ -115,43 +121,43 @@ def prelude_to_spinners(delay=DEFAULT_CHAR_DELAY_SEC, cycles=DEFAULT_CYCLES): display.show() sleep(delay) - animate([0], [A+F], 0, auto_write) - animate([3], [A+B], 0, auto_write) + animate([0], [A + F], 0, auto_write) + animate([3], [A + B], 0, auto_write) display.show() sleep(delay) - animate([0], [A+E+F], 0, auto_write) - animate([3], [A+B+C], 0, auto_write) + animate([0], [A + E + F], 0, auto_write) + animate([3], [A + B + C], 0, auto_write) display.show() sleep(delay) - animate([0], [A+D+E+F], 0, auto_write) - animate([3], [A+B+C+D], 0, auto_write) + animate([0], [A + D + E + F], 0, auto_write) + animate([3], [A + B + C + D], 0, auto_write) display.show() sleep(delay) - animate([1], [A+D], 0, auto_write) - animate([2], [A+D], 0, auto_write) + animate([1], [A + D], 0, auto_write) + animate([2], [A + D], 0, auto_write) display.show() sleep(delay) - animate([1], [A+D+M], 0, auto_write) - animate([2], [A+D+K], 0, auto_write) + animate([1], [A + D + M], 0, auto_write) + animate([2], [A + D + K], 0, auto_write) display.show() sleep(delay) - animate([1], [A+D+M+H], 0, auto_write) - animate([2], [A+D+K+J], 0, auto_write) + animate([1], [A + D + M + H], 0, auto_write) + animate([2], [A + D + K + J], 0, auto_write) display.show() sleep(delay) - animate([0], [A+E+F+J+D], 0, auto_write) - animate([3], [A+B+C+H+D], 0, auto_write) + animate([0], [A + E + F + J + D], 0, auto_write) + animate([3], [A + B + C + H + D], 0, auto_write) display.show() sleep(delay) - animate([0], [A+E+F+J+K+D], 0, auto_write) - animate([3], [A+B+C+H+M+D], 0, auto_write) + animate([0], [A + E + F + J + K + D], 0, auto_write) + animate([3], [A + B + C + H + M + D], 0, auto_write) display.show() sleep(delay) @@ -161,29 +167,30 @@ def prelude_to_spinners(delay=DEFAULT_CHAR_DELAY_SEC, cycles=DEFAULT_CYCLES): cy += 1 + def spinners(delay=DEFAULT_CHAR_DELAY_SEC, cycles=DEFAULT_CYCLES): cy = 0 auto_write = False while cy < cycles: - animate([0], [H+M], 0, auto_write) - animate([1], [J+K], 0, auto_write) - animate([2], [H+M], 0, auto_write) - animate([3], [J+K], 0, auto_write) + animate([0], [H + M], 0, auto_write) + animate([1], [J + K], 0, auto_write) + animate([2], [H + M], 0, auto_write) + animate([3], [J + K], 0, auto_write) display.show() sleep(delay) - animate([0], [G1+G2], 0, auto_write) - animate([1], [G1+G2], 0, auto_write) - animate([2], [G1+G2], 0, auto_write) - animate([3], [G1+G2], 0, auto_write) + animate([0], [G1 + G2], 0, auto_write) + animate([1], [G1 + G2], 0, auto_write) + animate([2], [G1 + G2], 0, auto_write) + animate([3], [G1 + G2], 0, auto_write) display.show() sleep(delay) - animate([0], [J+K], 0, auto_write) - animate([1], [H+M], 0, auto_write) - animate([2], [J+K], 0, auto_write) - animate([3], [H+M], 0, auto_write) + animate([0], [J + K], 0, auto_write) + animate([1], [H + M], 0, auto_write) + animate([2], [J + K], 0, auto_write) + animate([3], [H + M], 0, auto_write) display.show() sleep(delay) @@ -191,29 +198,30 @@ def spinners(delay=DEFAULT_CHAR_DELAY_SEC, cycles=DEFAULT_CYCLES): display.fill(0) + def enclosed_spinners(delay=DEFAULT_CHAR_DELAY_SEC, cycles=DEFAULT_CYCLES): cy = 0 auto_write = False while cy < cycles: - animate([0], [A+D+E+F+H+M], 0, auto_write) - animate([1], [A+D+J+K], 0, auto_write) - animate([2], [A+D+H+M], 0, auto_write) - animate([3], [A+B+C+D+J+K], 0, auto_write) + animate([0], [A + D + E + F + H + M], 0, auto_write) + animate([1], [A + D + J + K], 0, auto_write) + animate([2], [A + D + H + M], 0, auto_write) + animate([3], [A + B + C + D + J + K], 0, auto_write) display.show() sleep(delay) - animate([0], [A+D+E+F+G1+G2], 0, auto_write) - animate([1], [A+D+G1+G2], 0, auto_write) - animate([2], [A+D+G1+G2], 0, auto_write) - animate([3], [A+B+C+D+G1+G2], 0, auto_write) + animate([0], [A + D + E + F + G1 + G2], 0, auto_write) + animate([1], [A + D + G1 + G2], 0, auto_write) + animate([2], [A + D + G1 + G2], 0, auto_write) + animate([3], [A + B + C + D + G1 + G2], 0, auto_write) display.show() sleep(delay) - animate([0], [A+D+E+F+J+K], 0, auto_write) - animate([1], [A+D+H+M], 0, auto_write) - animate([2], [A+D+J+K], 0, auto_write) - animate([3], [A+B+C+D+H+M], 0, auto_write) + animate([0], [A + D + E + F + J + K], 0, auto_write) + animate([1], [A + D + H + M], 0, auto_write) + animate([2], [A + D + J + K], 0, auto_write) + animate([3], [A + B + C + D + H + M], 0, auto_write) display.show() sleep(delay) @@ -221,9 +229,14 @@ def enclosed_spinners(delay=DEFAULT_CHAR_DELAY_SEC, cycles=DEFAULT_CYCLES): display.fill(0) + def count_down(): auto_write = False - numbers = [ [A+B+C+D+G1+G2+N], [A+B+D+E+G1+G2+N], [B+C+N] ] + numbers = [ + [A + B + C + D + G1 + G2 + N], + [A + B + D + E + G1 + G2 + N], + [B + C + N], + ] index = 0 display.fill(0) @@ -240,6 +253,7 @@ def count_down(): sleep(1) display.fill(0) + try: text = "Init" @@ -272,8 +286,8 @@ def count_down(): while True: # Arrow print("Arrow") - animate([0, 1, 2], [G1+G2], 0.1) - animate([3], [G1+H+K], 0.1) + animate([0, 1, 2], [G1 + G2], 0.1) + animate([3], [G1 + H + K], 0.1) sleep(1.0) display.fill(0) sleep(1.0) @@ -283,7 +297,7 @@ def count_down(): cyc = 0 while cyc < DEFAULT_CYCLES: - animate([0], [H+J, G1+G2, K+M, G1+G2], DEFAULT_CHAR_DELAY_SEC) + animate([0], [H + J, G1 + G2, K + M, G1 + G2], DEFAULT_CHAR_DELAY_SEC) cyc += 1 @@ -314,7 +328,6 @@ def count_down(): display.show() sleep(1.0) - print("Enclosed Spinners") enclosed_spinners(0.1, 20) sleep(1.0) diff --git a/examples/ht16k33_matrix_pillow_image.py b/examples/ht16k33_matrix_pillow_image.py index 38da454..71cb41e 100644 --- a/examples/ht16k33_matrix_pillow_image.py +++ b/examples/ht16k33_matrix_pillow_image.py @@ -23,13 +23,13 @@ # This creates a 16x8 matrix: mtrx = matrix.Matrix16x8(i2c) # Or this creates a 16x8 matrix backpack: -#mtrx = matrix.MatrixBackpack16x8(i2c) +# mtrx = matrix.MatrixBackpack16x8(i2c) # Or this creates a 8x8 matrix: -#mtrx = matrix.Matrix8x8(i2c) +# mtrx = matrix.Matrix8x8(i2c) # Or this creates a 8x8 bicolor matrix: -#mtrx = matrix.Matrix8x8x2(i2c) +# mtrx = matrix.Matrix8x8x2(i2c) # Finally you can optionally specify a custom I2C address of the HT16k33 like: -#mtrx = matrix.Matrix16x8(i2c, address=0x70) +# mtrx = matrix.Matrix16x8(i2c, address=0x70) if isinstance(mtrx, matrix.Matrix8x8x2): image = Image.open("squares-color.png") diff --git a/examples/ht16k33_matrix_simpletest.py b/examples/ht16k33_matrix_simpletest.py index 03dc93e..ee7b599 100644 --- a/examples/ht16k33_matrix_simpletest.py +++ b/examples/ht16k33_matrix_simpletest.py @@ -19,13 +19,13 @@ # This creates a 16x8 matrix: matrix = matrix.Matrix16x8(i2c) # Or this creates a 16x8 matrix backpack: -#matrix = matrix.MatrixBackpack16x8(i2c) +# matrix = matrix.MatrixBackpack16x8(i2c) # Or this creates a 8x8 matrix: -#matrix = matrix.Matrix8x8(i2c) +# matrix = matrix.Matrix8x8(i2c) # Or this creates a 8x8 bicolor matrix: -#matrix = matrix.Matrix8x8x2(i2c) +# matrix = matrix.Matrix8x8x2(i2c) # Finally you can optionally specify a custom I2C address of the HT16k33 like: -#matrix = matrix.Matrix16x8(i2c, address=0x70) +# matrix = matrix.Matrix16x8(i2c, address=0x70) # Clear the matrix. matrix.fill(0) diff --git a/examples/ht16k33_matrix_text_example.py b/examples/ht16k33_matrix_text_example.py index 8958510..5d7f38c 100644 --- a/examples/ht16k33_matrix_text_example.py +++ b/examples/ht16k33_matrix_text_example.py @@ -42,4 +42,4 @@ bit = 1 << y & bite # if bit > 0 then set the pixel brightness if bit: - matrix[16-x, y+1] = 1 + matrix[16 - x, y + 1] = 1 diff --git a/examples/ht16k33_segments_simpletest.py b/examples/ht16k33_segments_simpletest.py index a80ed8d..5b446b4 100644 --- a/examples/ht16k33_segments_simpletest.py +++ b/examples/ht16k33_segments_simpletest.py @@ -19,11 +19,11 @@ # This creates a 7 segment 4 character display: display = segments.Seg7x4(i2c) # Or this creates a 14 segment alphanumeric 4 character display: -#display = segments.Seg14x4(i2c) +# display = segments.Seg14x4(i2c) # Or this creates a big 7 segment 4 character display -#display = segments.BigSeg7x4(i2c) +# display = segments.BigSeg7x4(i2c) # Finally you can optionally specify a custom I2C address of the HT16k33 like: -#display = segments.Seg7x4(i2c, address=0x70) +# display = segments.Seg7x4(i2c, address=0x70) # Clear the display. display.fill(0) @@ -44,13 +44,13 @@ # Or, can set indivdual digits / characters # Set the first character to '1': -display[0] = '1' +display[0] = "1" # Set the second character to '2': -display[1] = '2' +display[1] = "2" # Set the third character to 'A': -display[2] = 'A' +display[2] = "A" # Set the forth character to 'B': -display[3] = 'B' +display[3] = "B" time.sleep(2) # Or, can even set the segments to make up characters @@ -68,5 +68,5 @@ display.set_digit_raw(3, [0x2D, 0x3F]) time.sleep(2) -#Show a looping marquee -display.marquee('Deadbeef 192.168.100.102... ', 0.2) +# Show a looping marquee +display.marquee("Deadbeef 192.168.100.102... ", 0.2) diff --git a/setup.py b/setup.py index 0e5ebf3..cde5fcc 100644 --- a/setup.py +++ b/setup.py @@ -7,6 +7,7 @@ # Always prefer setuptools over distutils from setuptools import setup, find_packages + # To use a consistent encoding from codecs import open from os import path @@ -14,47 +15,38 @@ here = path.abspath(path.dirname(__file__)) # Get the long description from the README file -with open(path.join(here, 'README.rst'), encoding='utf-8') as f: +with open(path.join(here, "README.rst"), encoding="utf-8") as f: long_description = f.read() setup( - name='adafruit-circuitpython-ht16k33', - + name="adafruit-circuitpython-ht16k33", use_scm_version=True, - setup_requires=['setuptools_scm'], - - description='CircuitPython library for HT16K33 LED matrices and segment displays.', + setup_requires=["setuptools_scm"], + description="CircuitPython library for HT16K33 LED matrices and segment displays.", long_description=long_description, - long_description_content_type='text/x-rst', - + long_description_content_type="text/x-rst", # The project's main homepage. - url='https://github.com/adafruit/Adafruit_CircuitPython_HT16K33', - + url="https://github.com/adafruit/Adafruit_CircuitPython_HT16K33", # Author details - author='Adafruit Industries', - author_email='circuitpython@adafruit.com', - - install_requires=['Adafruit-Blinka', 'adafruit-circuitpython-busdevice'], - + author="Adafruit Industries", + author_email="circuitpython@adafruit.com", + install_requires=["Adafruit-Blinka", "adafruit-circuitpython-busdevice"], # Choose your license - license='MIT', - + license="MIT", # See https://pypi.python.org/pypi?%3Aaction=list_classifiers classifiers=[ - 'Development Status :: 3 - Alpha', - 'Intended Audience :: Developers', - 'Topic :: Software Development :: Libraries', - 'Topic :: System :: Hardware', - 'License :: OSI Approved :: MIT License', - 'Programming Language :: Python :: 3', - 'Programming Language :: Python :: 3.4', - 'Programming Language :: Python :: 3.5', + "Development Status :: 3 - Alpha", + "Intended Audience :: Developers", + "Topic :: Software Development :: Libraries", + "Topic :: System :: Hardware", + "License :: OSI Approved :: MIT License", + "Programming Language :: Python :: 3", + "Programming Language :: Python :: 3.4", + "Programming Language :: Python :: 3.5", ], - # What does your project relate to? - keywords='adafruit ht16k33 led matrix segment displays hardware micropython circuitpython', - + keywords="adafruit ht16k33 led matrix segment displays hardware micropython circuitpython", # You can just specify the packages manually here if your project is # simple. Or you can use find_packages(). - packages=['adafruit_ht16k33'], + packages=["adafruit_ht16k33"], )