Esempio n. 1
0
    def buzz(self, identifier: int, duration: timedelta,
             frequency: float) -> None:
        """Queue a pitch to be played."""
        if identifier != 0:
            raise ValueError(f"Invalid piezo identifier {identifier!r}; "
                             f"the only valid identifier is 0.")

        duration_ms = round(duration / timedelta(milliseconds=1))
        if duration_ms > 65535:
            raise NotSupportedByHardwareError(
                "Maximum piezo duration is 65535ms.")

        frequency_int = int(round(frequency))
        if frequency_int > 65535:
            raise NotSupportedByHardwareError(
                "Maximum piezo frequency is 65535Hz.")

        data = struct.pack("<HH", frequency_int, duration_ms)
        try:
            self._write(CMD_WRITE_PIEZO, data)
        except USBCommunicationError as e:
            if e.usb_error.errno == 32:  # pipe error
                raise CommunicationError(
                    f"{e}; are you sending buzz commands to the "
                    f"power board too quickly", )
            raise
Esempio n. 2
0
 def _check_ultrasound_pins(
     self,
     trigger_pin_identifier: int,
     echo_pin_identifier: int,
 ) -> None:
     if trigger_pin_identifier >= FIRST_ANALOGUE_PIN:
         raise NotSupportedByHardwareError(
             "Ultrasound functions not supported on analogue pins", )
     if echo_pin_identifier >= FIRST_ANALOGUE_PIN:
         raise NotSupportedByHardwareError(
             "Ultrasound functions not supported on analogue pins", )
Esempio n. 3
0
 def _check_ultrasound_pins(
         trigger_pin_identifier: int,
         echo_pin_identifier: int,
 ) -> None:
     """Verify the validity of a pair of ultrasound pins."""
     if trigger_pin_identifier >= SBArduinoBoard.FIRST_ANALOGUE_PIN:
         raise NotSupportedByHardwareError(
             "Ultrasound functions not supported on analogue pins",
         )
     if echo_pin_identifier >= SBArduinoBoard.FIRST_ANALOGUE_PIN:
         raise NotSupportedByHardwareError(
             "Ultrasound functions not supported on analogue pins",
         )
Esempio n. 4
0
 def read_gpio_pin_analogue_value(self, identifier: int) -> float:
     """Read the analogue voltage of the GPIO pin."""
     if identifier < ArduinoUno.FIRST_ANALOGUE_PIN:
         raise NotSupportedByHardwareError(
             "Analogue functions not supported on digital pins.",
         )
     return self._read_analogue_pin(identifier)
Esempio n. 5
0
 def read_gpio_pin_analogue_value(self, identifier: int) -> float:
     """Read the analogue voltage of the GPIO pin."""
     if identifier < FIRST_ANALOGUE_PIN:
         raise NotSupportedByHardwareError(
             "Analogue functions not supported on digital pins", )
     if identifier >= FIRST_ANALOGUE_PIN + 4:
         raise NotSupportedByHardwareError(
             f"Arduino Uno firmware only supports analogue pins 0-3 (IDs 14-17)",
         )
     analogue_pin_num = identifier - 14
     results = self._command("A")
     for result in results:
         pin_name, reading = result.split(None, 1)
         if pin_name == f"a{analogue_pin_num}":
             voltage = (int(reading) / 1024.0) * 5.0
             return voltage
     raise CommunicationError(f"Invalid response from Arduino: {results!r}")
Esempio n. 6
0
    def buzz(self, identifier: int, duration: timedelta,
             frequency: float) -> None:
        """Queue a pitch to be played."""
        if identifier != 0:
            raise ValueError(f"invalid piezo identifier {identifier!r}; "
                             f"the only valid identifier is 0")

        duration_ms = round(duration / timedelta(milliseconds=1))
        if duration_ms > 65535:
            raise NotSupportedByHardwareError(
                "Maximum piezo duration is 65535ms.")

        frequency_int = int(round(frequency))
        if frequency_int > 65535:
            raise NotSupportedByHardwareError(
                "Maximum piezo frequency is 65535Hz.")

        data = struct.pack("<HH", frequency_int, duration_ms)
        self._write(CMD_WRITE_PIEZO, data)
Esempio n. 7
0
 def get_gpio_pin_digital_state(self, identifier: int) -> bool:
     """Get the last written state of the GPIO pin."""
     if identifier >= ArduinoUno.FIRST_ANALOGUE_PIN:
         raise NotSupportedByHardwareError(
             "Digital functions not supported on analogue pins.",
         )
     if self._digital_pins[identifier].mode is not GPIOPinMode.DIGITAL_OUTPUT:
         raise ValueError(f"Pin {identifier} mode needs to be DIGITAL_OUTPUT "
                          f"in order to read the digital state.")
     return self._digital_pins[identifier].state
Esempio n. 8
0
 def write_gpio_pin_digital_state(self, identifier: int, state: bool) -> None:
     """Write to the digital state of a GPIO pin."""
     if identifier >= ArduinoUno.FIRST_ANALOGUE_PIN:
         raise NotSupportedByHardwareError(
             "Digital functions not supported on analogue pins",
         )
     if self._digital_pins[identifier].mode is not GPIOPinMode.DIGITAL_OUTPUT:
         raise ValueError(f"Pin {identifier} mode needs to be DIGITAL_OUTPUT "
                          f"in order to set the digital state.")
     self._digital_pins[identifier].state = state
     self._update_digital_pin(identifier)
Esempio n. 9
0
 def read_gpio_pin_digital_state(self, identifier: int) -> bool:
     """Read the digital state of the GPIO pin."""
     if identifier >= ArduinoUno.FIRST_ANALOGUE_PIN:
         raise NotSupportedByHardwareError(
             "Digital functions not supported on analogue pins.",
         )
     if self._digital_pins[identifier].mode not in (
         GPIOPinMode.DIGITAL_INPUT,
         GPIOPinMode.DIGITAL_INPUT_PULLUP,
     ):
         raise ValueError(f"Pin {identifier} mode needs to be DIGITAL_INPUT_* "
                          f"in order to read the digital state.")
     return self._read_digital_pin(identifier)
Esempio n. 10
0
    def set_servo_position(self, identifier: int,
                           position: ServoPosition) -> None:
        """Set the position of a servo."""
        if identifier not in range(0, 12):
            raise ValueError(
                "Only integers 0 - 12 are valid servo identifiers.")

        if position is None:
            raise NotSupportedByHardwareError(
                f"{self.board.name} does not support unpowered servos.", )

        self._positions[identifier] = position
        value = round(position * 100)
        self._write(CMD_WRITE_SET_SERVO[identifier], value)
Esempio n. 11
0
 def _read_analogue_pin(self, identifier: int) -> float:
     """Read the value of an analogue pin from the Arduino."""
     if identifier >= SBArduinoBoard.FIRST_ANALOGUE_PIN + 4:
         raise NotSupportedByHardwareError(
             "Arduino Uno firmware only supports analogue pins 0-3 (IDs 14-17)",
         )
     analogue_pin_num = identifier - 14
     results = self._command("A")
     for result in results:
         pin_name, reading = result.split(None, 1)
         if pin_name == f"a{analogue_pin_num}":
             voltage = (int(reading) / 1024.0) * 5.0
             return voltage
     raise CommunicationError(f"Invalid response from Arduino: {results!r}")
Esempio n. 12
0
 def set_gpio_pin_mode(self, identifier: int, pin_mode: GPIOPinMode) -> None:
     """Set the hardware mode of a GPIO pin."""
     digital_pin_modes = {
         GPIOPinMode.DIGITAL_INPUT,
         GPIOPinMode.DIGITAL_INPUT_PULLUP,
         GPIOPinMode.DIGITAL_OUTPUT,
     }
     if identifier < ArduinoUno.FIRST_ANALOGUE_PIN:
         # Digital pin
         if pin_mode in digital_pin_modes:
             self._digital_pins[identifier].mode = pin_mode
             self._update_digital_pin(identifier)
             return
     else:
         # Analogue pin
         if pin_mode is GPIOPinMode.ANALOGUE_INPUT:
             return
     raise NotSupportedByHardwareError(
         f"{self.board.name} does not support mode {pin_mode} on pin {identifier}.",
     )
Esempio n. 13
0
 def read_gpio_pin_digital_state(self, identifier: int) -> bool:
     """Read the digital state of the GPIO pin."""
     if identifier >= FIRST_ANALOGUE_PIN:
         raise NotSupportedByHardwareError(
             "Digital functions not supported on analogue pins", )
     if self._digital_pins[identifier].mode not in (
             GPIOPinMode.DIGITAL_INPUT,
             GPIOPinMode.DIGITAL_INPUT_PULLUP,
     ):
         raise ValueError(
             f"Pin {identifier} mode needs to be DIGITAL_INPUT_*"
             f"in order to read the digital state.")
     results = self._command("R", str(identifier))
     if len(results) != 1:
         raise CommunicationError(
             f"Invalid response from Arduino: {results!r}")
     result = results[0]
     if result == "H":
         return True
     elif result == "L":
         return False
     else:
         raise CommunicationError(
             f"Invalid response from Arduino: {result!r}")
Esempio n. 14
0
 def write_gpio_pin_pwm_value(self, identifier: int,
                              duty_cycle: float) -> None:
     """Write a scaled analogue value to the PWM on the GPIO pin."""
     raise NotSupportedByHardwareError(
         "SB Arduino firmware does not implement PWM output", )
Esempio n. 15
0
 def write_gpio_pin_dac_value(self, identifier: int,
                              scaled_value: float) -> None:
     """Write a scaled analogue value to the DAC on the GPIO pin."""
     raise NotSupportedByHardwareError("SB Arduino does not have a DAC")