Python busio.SPI Examples

The following are 18 code examples of busio.SPI(). You can vote up the ones you like or vote down the ones you don't like, and go to the original project or source file by following the links above each example. You may also want to check out all available functions/classes of the module busio , or try the search function .
Example #1
Source File: soil.py    From aws-builders-fair-projects with Apache License 2.0 6 votes vote down vote up
def __init__(self):
        Sensor.__init__(self)

        self.moisture_min = float(self.config["soil"]["min"])
        self.moisture_max = float(self.config["soil"]["max"])

        # create SPI bus
        spi = busio.SPI(clock=board.SCK, MISO=board.MISO, MOSI=board.MOSI)

        # create the cs (chip select)
        cs = digitalio.DigitalInOut(board.D8)

        # create the mcp object
        mcp = MCP.MCP3008(spi, cs)
        
        # create an analog input channel
        self.pin = []
        self.pin.append(AnalogIn(mcp, MCP.P0))
        self.pin.append(AnalogIn(mcp, MCP.P1))
        self.pin.append(AnalogIn(mcp, MCP.P2))
        self.pin.append(AnalogIn(mcp, MCP.P3))
        self.pin.append(AnalogIn(mcp, MCP.P4))
        self.pin.append(AnalogIn(mcp, MCP.P5))
        self.pin.append(AnalogIn(mcp, MCP.P6))
        self.pin.append(AnalogIn(mcp, MCP.P7)) 
Example #2
Source File: adafruit_sdcard.py    From Adafruit_CircuitPython_SD with MIT License 6 votes vote down vote up
def _cmd_nodata(self, card, cmd, response=0xFF):
        """
        Issue a command to the card with no argument.

        :param busio.SPI card: The locked SPI bus.
        :param int cmd: The command number.
        """
        buf = self._cmdbuf
        buf[0] = cmd
        buf[1] = 0xFF

        card.write(buf, end=2)
        for _ in range(_CMD_TIMEOUT):
            card.readinto(buf, end=1, write_value=0xFF)
            if buf[0] == response:
                return 0  # OK
        return 1  # timeout 
Example #3
Source File: adafruit_sdcard.py    From Adafruit_CircuitPython_SD with MIT License 5 votes vote down vote up
def _wait_for_ready(self, card, timeout=0.3):
        """
        Wait for the card to clock out 0xff to indicate its ready.

        :param busio.SPI card: The locked SPI bus.
        :param float timeout: Maximum time to wait in seconds.
        """
        start_time = time.monotonic()
        self._single_byte[0] = 0x00
        while time.monotonic() - start_time < timeout and self._single_byte[0] != 0xFF:
            card.readinto(self._single_byte, write_value=0xFF)

    # pylint: disable-msg=too-many-arguments
    # pylint: disable=no-member
    # no-member disable should be reconsidered when it can be tested 
Example #4
Source File: adc_worker.py    From mudpi-core with MIT License 5 votes vote down vote up
def __init__(self, config: dict, main_thread_running, system_ready):
        self.config = config
        self.main_thread_running = main_thread_running
        self.system_ready = system_ready
        self.node_ready = False

        spi = busio.SPI(clock=board.SCK, MISO=board.MISO, MOSI=board.MOSI)
        cs = digitalio.DigitalInOut(ADCMCP3008Worker.PINS[config['pin']])

        self.mcp = MCP.MCP3008(spi, cs)

        self.sensors = []
        self.init_sensors()

        self.node_ready = True 
Example #5
Source File: board.py    From Adafruit_Blinka with MIT License 5 votes vote down vote up
def SPI():
    """The singleton SPI interface"""
    import busio

    return busio.SPI(SCLK, MOSI, MISO) 
Example #6
Source File: character_lcd_spi.py    From Adafruit_CircuitPython_CharLCD with MIT License 5 votes vote down vote up
def __init__(self, spi, latch, columns, lines, backlight_inverted=False):
        # pylint: disable=too-many-arguments
        """Initialize character LCD connected to backpack using SPI connection
        on the specified SPI bus and latch line with the specified number of
        columns and lines on the display. Optionally specify if backlight is
        inverted.
        """
        # pylint: enable=too-many-arguments

        self._shift_register = adafruit_74hc595.ShiftRegister74HC595(spi, latch)
        reset = self._shift_register.get_pin(1)
        enable = self._shift_register.get_pin(2)
        db4 = self._shift_register.get_pin(6)
        db5 = self._shift_register.get_pin(5)
        db6 = self._shift_register.get_pin(4)
        db7 = self._shift_register.get_pin(3)
        backlight_pin = self._shift_register.get_pin(7)
        super().__init__(
            reset,
            enable,
            db4,
            db5,
            db6,
            db7,
            columns,
            lines,
            backlight_pin=backlight_pin,
            backlight_inverted=backlight_inverted,
        ) 
Example #7
Source File: apa102.py    From apa102-pi with GNU General Public License v2.0 5 votes vote down vote up
def send_to_spi(self, data):
        """Internal method to output data to the chosen SPI device"""
        if self.use_ce:
            with self.spibus as bus_device:
                bus_device.write(data)
        elif self.use_bitbang:
            while not self.spi.try_lock():
                pass
            self.spi.write(data)
            self.spi.unlock()
        else:
            self.spi.write(data) 
Example #8
Source File: apa102.py    From apa102-pi with GNU General Public License v2.0 5 votes vote down vote up
def cleanup(self):
        """Release the SPI device; Call this method at the end"""
        # Try to unlock, in case it is still locked
        try:
            self.spi.unlock()  # Unlock first
        except ValueError:
            # Do nothing, the bus was not locked
            pass
        self.clear_strip()
        self.spi.deinit()  # Close SPI port 
Example #9
Source File: apa102.py    From apa102-pi with GNU General Public License v2.0 5 votes vote down vote up
def show(self):
        """Sends the content of the pixel buffer to the strip.

        Todo: More than 1024 LEDs requires more than one xfer operation.
        """
        self.clock_start_frame()
        # xfer2 kills the list, unfortunately. So it must be copied first
        # SPI takes up to 4096 Integers. So we are fine for up to 1024 LEDs.
        self.send_to_spi(self.leds)
        self.clock_end_frame() 
Example #10
Source File: apa102.py    From apa102-pi with GNU General Public License v2.0 5 votes vote down vote up
def clock_end_frame(self):
        """Sends an end frame to the LED strip.

        As explained above, dummy data must be sent after the last real colour
        information so that all of the data can reach its destination down the line.
        The delay is not as bad as with the human example above.
        It is only 1/2 bit per LED. This is because the SPI clock line
        needs to be inverted.

        Say a bit is ready on the SPI data line. The sender communicates
        this by toggling the clock line. The bit is read by the LED
        and immediately forwarded to the output data line. When the clock goes
        down again on the input side, the LED will toggle the clock up
        on the output to tell the next LED that the bit is ready.

        After one LED the clock is inverted, and after two LEDs it is in sync
        again, but one cycle behind. Therefore, for every two LEDs, one bit
        of delay gets accumulated. For 300 LEDs, 150 additional bits must be fed to
        the input of LED one so that the data can reach the last LED.

        Ultimately, we need to send additional numLEDs/2 arbitrary data bits,
        in order to trigger numLEDs/2 additional clock changes. This driver
        sends zeroes, which has the benefit of getting LED one partially or
        fully ready for the next update to the strip. An optimized version
        of the driver could omit the "clockStartFrame" method if enough zeroes have
        been sent as part of "clockEndFrame".
        """
        # Send reset frame necessary for SK9822 type LEDs
        self.send_to_spi(bytes([0] * 4))
        for _ in range((self.num_led + 15) // 16):
            self.send_to_spi([0x00]) 
Example #11
Source File: apa102.py    From apa102-pi with GNU General Public License v2.0 4 votes vote down vote up
def __init__(self, num_led=8, global_brightness=31,
                 order='rgb', mosi=10, sclk=11, ce=None, bus_speed_hz=8000000):
        """Initializes the library

        :param num_led: Number of LEDs in the strip
        :param global_brightness: Overall brightness
        :param order: Order in which the colours are addressed (this differs from strip to strip)
        :param mosi: Master Out pin. Use 10 for SPI0, 20 for SPI1, any GPIO pin for bitbang.
        :param sclk: Clock, use 11 for SPI0, 21 for SPI1, any GPIO pin for bitbang.
        :param ce: GPIO to use for Chip select. Can be any free GPIO pin. Warning: This will slow down the bus
                   significantly. Note: The hardware CE0 and CE1 are not used
        :param bus_speed_hz: Speed of the hardware SPI bus. If glitches on the bus are visible, lower the value.
        """
        self.num_led = num_led
        order = order.lower()  # Just in case someone use CAPS here.
        self.rgb = RGB_MAP.get(order, RGB_MAP['rgb'])
        self.global_brightness = global_brightness
        self.use_bitbang = False  # Two raw SPI devices exist: Bitbang (software) and hardware SPI.
        self.use_ce = False  # If true, use the BusDevice abstraction layer on top of the raw SPI device

        self.leds = [self.LED_START, 0, 0, 0] * self.num_led  # Pixel buffer
        if ce is not None:
            # If a chip enable value is present, use the Adafruit CircuitPython BusDevice abstraction on top
            # of the raw SPI device (hardware or bitbang)
            # The next line is just here to prevent an "unused" warning from the IDE
            digitalio.DigitalInOut(board.D1)
            # Convert the chip enable pin number into an object (reflection à la Python)
            ce = eval("digitalio.DigitalInOut(board.D"+str(ce)+")")
            self.use_ce = True
        # Heuristic: Test for the hardware SPI pins. If found, use hardware SPI, otherwise bitbang SPI
        if mosi == 10:
            if sclk != 11:
                raise ValueError("Illegal MOSI / SCLK combination")
            self.spi = busio.SPI(clock=board.SCLK, MOSI=board.MOSI)
        elif mosi == 20:
            if sclk != 21:
                raise ValueError("Illegal MOSI / SCLK combination")
            self.spi = busio.SPI(clock=board.SCLK_1, MOSI=board.MOSI_1)
        else:
            # Use Adafruit CircuitPython BitBangIO, because the pins do not match one of the hardware SPI devices
            # Reflection à la Python to get at the digital IO pins
            self.spi = bitbangio.SPI(clock=eval("board.D"+str(sclk)), MOSI=eval("board.D"+str(mosi)))
            self.use_bitbang = True
        # Add the BusDevice on top of the raw SPI
        if self.use_ce:
            self.spibus = SPIDevice(spi=self.spi,  chip_select=ce, baudrate=bus_speed_hz)
        else:
            # If the BusDevice is not used, the bus speed is set here instead
            while not self.spi.try_lock():
                pass
            self.spi.configure(baudrate=bus_speed_hz)
            self.spi.unlock()
        # Debug
        if self.use_ce:
            print("Use software chip enable")
        if self.use_bitbang:
            print("Use bitbang SPI")
        else:
            print("Use hardware SPI") 
Example #12
Source File: demo_circuitpython.py    From micropython-ssd1351 with MIT License 4 votes vote down vote up
def test():
    """CircuitPython Text, Shape & Sprite"""
    if implementation.name != 'circuitpython':
        print()
        print('This demo is for CircuitPython only!')
        exit()
    try:
        # Configuratoin for CS and DC pins:
        cs_pin = DigitalInOut(board.P0_15)
        dc_pin = DigitalInOut(board.P0_17)
        rst_pin = DigitalInOut(board.P0_20)

        # Setup SPI bus using hardware SPI:
        spi = SPI(clock=board.P0_24, MOSI=board.P0_22)

        # Create the SSD1351 display:
        display = Display(spi, dc=dc_pin, cs=cs_pin, rst=rst_pin)
        display.clear()

        # Load Fixed Font
        fixed = XglcdFont('fonts/FixedFont5x8.c', 5, 8, letter_count=96)

        # Title
        WIDTH = 128
        text = 'CircuitPython Demo'
        # Measure text and center
        length = fixed.measure_text(text)
        x = int((WIDTH / 2) - (length / 2))
        display.draw_text(x, 6, text, fixed, color565(255, 255, 0))

        # Draw title outline
        display.draw_rectangle(0, 0, 127, 20, color565(0, 255, 0))

        # Load sprite
        logo = BouncingSprite('images/blinka45x48.raw',
                              45, 48, 128, 128, 1, display)

        while True:
            timer = monotonic()
            logo.update_pos()
            logo.draw()
            # Attempt to set framerate to 30 FPS
            timer_dif = .033333333 - (monotonic() - timer)
            if timer_dif > 0:
                sleep(timer_dif)

    except KeyboardInterrupt:
        display.cleanup() 
Example #13
Source File: demo_scrolling_marquee.py    From micropython-ssd1351 with MIT License 4 votes vote down vote up
def test():
    """Scrolling Marquee"""

    try:
        # Implementation dependant pin and SPI configuration
        if implementation.name == 'circuitpython':
            import board
            from busio import SPI
            from digitalio import DigitalInOut
            cs_pin = DigitalInOut(board.P0_15)
            dc_pin = DigitalInOut(board.P0_17)
            rst_pin = DigitalInOut(board.P0_20)
            spi = SPI(clock=board.P0_24, MOSI=board.P0_22)
        else:
            from machine import Pin, SPI
            cs_pin = Pin(5)
            dc_pin = Pin(17)
            rst_pin = Pin(16)
            spi = SPI(2, baudrate=14500000, sck=Pin(18), mosi=Pin(23))

        # Create the SSD1351 display:
        display = Display(spi, dc=dc_pin, cs=cs_pin, rst=rst_pin)
        display.clear()

        # Draw non-moving circles
        display.fill_circle(63, 63, 63, color565(27, 72, 156))
        display.fill_circle(63, 63, 53, color565(0, 0, 0))
        display.fill_circle(63, 63, 43, color565(189, 0, 36))
        display.fill_circle(63, 63, 33, color565(0, 0, 0))

        # Load Marquee image
        display.draw_image('images\Rototron128x26.raw', 0, 50, 128, 26)

        # Set up scrolling
        display.set_scroll(horiz_offset=1, vert_start_row=50,
                           vert_row_count=26, vert_offset=0, speed=1)
        display.scroll(True)

        while True:
            # Do nothing, scrolling handled by hardware
            sleep(1)

    except KeyboardInterrupt:
        display.cleanup() 
Example #14
Source File: adafruit_dotstar.py    From Adafruit_CircuitPython_DotStar with MIT License 4 votes vote down vote up
def __init__(
        self,
        clock,
        data,
        n,
        *,
        brightness=1.0,
        auto_write=True,
        pixel_order=BGR,
        baudrate=4000000
    ):
        self._spi = None
        try:
            self._spi = busio.SPI(clock, MOSI=data)
            while not self._spi.try_lock():
                pass
            self._spi.configure(baudrate=baudrate)

        except (NotImplementedError, ValueError):
            self.dpin = digitalio.DigitalInOut(data)
            self.cpin = digitalio.DigitalInOut(clock)
            self.dpin.direction = digitalio.Direction.OUTPUT
            self.cpin.direction = digitalio.Direction.OUTPUT
            self.cpin.value = False

        # Supply one extra clock cycle for each two pixels in the strip.
        trailer_size = n // 16
        if n % 16 != 0:
            trailer_size += 1

        # Four empty bytes for the header.
        header = bytearray(START_HEADER_SIZE)
        # 0xff bytes for the trailer.
        trailer = bytearray(b"\xff") * trailer_size

        super().__init__(
            n,
            byteorder=pixel_order,
            brightness=brightness,
            auto_write=auto_write,
            header=header,
            trailer=trailer,
        ) 
Example #15
Source File: adafruit_sdcard.py    From Adafruit_CircuitPython_SD with MIT License 4 votes vote down vote up
def _write(self, card, token, buf, start=0, end=None):
        """
        Write a data block to the card.

        :param busio.SPI card: The locked SPI bus.
        :param int token: The start token
        :param bytearray buf: The buffer to write from
        :param int start: The first index to read data from
        :param int end: The index after the last byte to read from.
        """
        cmd = self._cmdbuf
        if end is None:
            end = len(buf)

        self._wait_for_ready(card)

        # send: start of block, data, checksum
        cmd[0] = token
        card.write(cmd, end=1)
        card.write(buf, start=start, end=end)
        cmd[0] = 0xFF
        cmd[1] = 0xFF
        card.write(cmd, end=2)

        # check the response
        # pylint: disable=no-else-return
        # Disable should be removed when refactor can be tested
        for _ in range(_CMD_TIMEOUT):
            card.readinto(cmd, end=1, write_value=0xFF)
            if not (cmd[0] & 0x80):
                if (cmd[0] & 0x1F) != 0x05:
                    return -1
                else:
                    break

        # wait for write to finish
        card.readinto(cmd, end=1, write_value=0xFF)
        while cmd[0] == 0:
            card.readinto(cmd, end=1, write_value=0xFF)

        return 0  # worked

    # pylint: enable-msg=too-many-arguments 
Example #16
Source File: adafruit_sdcard.py    From Adafruit_CircuitPython_SD with MIT License 4 votes vote down vote up
def _block_cmd(self, card, cmd, block, crc, response_buf=None):
        """
        Issue a command to the card with a block argument.

        :param busio.SPI card: The locked SPI bus.
        :param int cmd: The command number.
        :param int block: The relevant block.
        :param int crc: The crc to allow the card to verify the command and argument.
        """
        if self._cdv == 1:
            return self._cmd(card, cmd, block, crc, response_buf=response_buf)

        # create and send the command
        buf = self._cmdbuf
        buf[0] = 0x40 | cmd
        # We address by byte because cdv is 512. Instead of multiplying, shift
        # the data to the correct spot so that we don't risk creating a long
        # int.
        buf[1] = (block >> 15) & 0xFF
        buf[2] = (block >> 7) & 0xFF
        buf[3] = (block << 1) & 0xFF
        buf[4] = 0

        if crc == 0:
            buf[5] = calculate_crc(buf[:-1])
        else:
            buf[5] = crc

        result = -1
        self._wait_for_ready(card)

        card.write(buf)

        # wait for the response (response[7] == 0)
        for _ in range(_CMD_TIMEOUT):
            card.readinto(buf, end=1, write_value=0xFF)
            if not (buf[0] & 0x80):
                result = buf[0]
                break

        # pylint: disable=singleton-comparison
        # Disable should be removed when refactor can be tested.
        if response_buf != None and result == 0:
            self._readinto(card, response_buf)

        return result

    # pylint: enable-msg=too-many-arguments 
Example #17
Source File: adafruit_sdcard.py    From Adafruit_CircuitPython_SD with MIT License 4 votes vote down vote up
def _cmd(
        self, card, cmd, arg=0, crc=0, response_buf=None, data_block=True, wait=True
    ):
        """
        Issue a command to the card and read an optional data response.

        :param busio.SPI card: The locked SPI bus.
        :param int cmd: The command number.
        :param int|buf(4) arg: The command argument
        :param int crc: The crc to allow the card to verify the command and argument.
        :param bytearray response_buf: Buffer to read a data block response into.
        :param bool data_block: True if the response data is in a data block.
        """
        # create and send the command
        buf = self._cmdbuf
        buf[0] = 0x40 | cmd
        if isinstance(arg, int):
            buf[1] = (arg >> 24) & 0xFF
            buf[2] = (arg >> 16) & 0xFF
            buf[3] = (arg >> 8) & 0xFF
            buf[4] = arg & 0xFF
        elif len(arg) == 4:
            # arg can be a 4-byte buf
            buf[1:5] = arg
        else:
            raise ValueError()

        if crc == 0:
            buf[5] = calculate_crc(buf[:-1])
        else:
            buf[5] = crc

        if wait:
            self._wait_for_ready(card)

        card.write(buf)

        # wait for the response (response[7] == 0)
        for _ in range(_CMD_TIMEOUT):
            card.readinto(buf, end=1, write_value=0xFF)
            if not (buf[0] & 0x80):
                if response_buf:
                    if data_block:
                        # Wait for the start block byte
                        buf[1] = 0xFF
                        while buf[1] != 0xFE:
                            card.readinto(buf, start=1, end=2, write_value=0xFF)
                    card.readinto(response_buf, write_value=0xFF)
                    if data_block:
                        # Read the checksum
                        card.readinto(buf, start=1, end=3, write_value=0xFF)
                return buf[0]
        return -1

    # pylint: enable-msg=too-many-arguments

    # pylint: disable-msg=too-many-arguments 
Example #18
Source File: adafruit_sdcard.py    From Adafruit_CircuitPython_SD with MIT License 4 votes vote down vote up
def _init_card(self, baudrate):
        """Initialize the card in SPI mode."""
        # clock card at least cycles with cs high
        self._clock_card(80)

        with self._spi as card:
            # CMD0: init card; should return _R1_IDLE_STATE (allow 5 attempts)
            for _ in range(5):
                if self._cmd(card, 0, 0, 0x95) == _R1_IDLE_STATE:
                    break
            else:
                raise OSError("no SD card")

            # CMD8: determine card version
            rb7 = bytearray(4)
            r = self._cmd(card, 8, 0x01AA, 0x87, rb7, data_block=False)
            if r == _R1_IDLE_STATE:
                self._init_card_v2(card)
            elif r == (_R1_IDLE_STATE | _R1_ILLEGAL_COMMAND):
                self._init_card_v1(card)
            else:
                raise OSError("couldn't determine SD card version")

            # get the number of sectors
            # CMD9: response R2 (R1 byte + 16-byte block read)
            csd = bytearray(16)
            if self._cmd(card, 9, 0, 0xAF, response_buf=csd) != 0:
                raise OSError("no response from SD card")
            # self.readinto(csd)
            csd_version = (csd[0] & 0xC0) >> 6
            if csd_version >= 2:
                raise OSError("SD card CSD format not supported")

            if csd_version == 1:
                self._sectors = ((csd[8] << 8 | csd[9]) + 1) * 1024
            else:
                block_length = 2 ** (csd[5] & 0xF)
                c_size = ((csd[6] & 0x3) << 10) | (csd[7] << 2) | ((csd[8] & 0xC) >> 6)
                mult = 2 ** (((csd[9] & 0x3) << 1 | (csd[10] & 0x80) >> 7) + 2)
                self._sectors = block_length // 512 * mult * (c_size + 1)

            # CMD16: set block length to 512 bytes
            if self._cmd(card, 16, 512, 0x15) != 0:
                raise OSError("can't set 512 block size")

        # set to high data rate now that it's initialised
        self._spi = spi_device.SPIDevice(
            self._spi.spi, self._spi.chip_select, baudrate=baudrate, extra_clocks=8
        )