示例#1
0
class PWMOut(object):
    """PWM output."""
    def __init__(self, pin, freq=50, duty=0, verbose=False, channel=-1):
        if channel in [i for i in range(RMT_MAX_CHAN)]:
            self._chanRMT = channel
            self._pin = RMT(channel, pin=Pin(pin), clock_div=RMT_CLOCK_DIV)
            self.__setRMTDuty(duty)
            self._pin.loop(True)
        else:
            self._chanRMT = -1
            self._pin = PWM(Pin(pin))
            self._pin.init(freq=freq, duty=duty)
        self._verbose = verbose
        if self._verbose:
            self.__logFrequency()

    def deinit(self):
        self._pin.deinit()

    @property
    def duty_percent(self):
        """ duty in percent
    """
        if self._chanRMT < 0:
            return self._pin.duty() / MAX_DUTY * 100
        else:
            return self._dutyRMT / RMT_DUTY_SCALER

    @duty_percent.setter
    def duty_percent(self, value):
        if self._chanRMT < 0:
            self._pin.duty(int(min(max(0, value / 100.0 * MAX_DUTY),
                                   MAX_DUTY)))
        else:
            self.__setRMTDuty(
                min(max(0, value / 100. * RMT_MAX_DUTY), RMT_MAX_DUTY))

    @property
    def duty(self):
        """ duty as raw value
    """
        if self._chanRMT < 0:
            return self._pin.duty()
        else:
            return self._dutyRMT

    @duty.setter
    def duty(self, value):
        if self._chanRMT < 0:
            self._pin.duty(int(value))
        else:
            self.__setRMTDuty(value)

    @property
    def freq_Hz(self):
        """ frequency in [Hz]
    """
        if self._chanRMT < 0:
            return self._pin.freq()
        else:
            return self._pin.source_freq() / RMT_CLOCK_DIV

    @freq_Hz.setter
    def freq_Hz(self, value):
        if self._chanRMT < 0:
            self._pin.freq(value)
        else:
            if value == 0:
                self._pin.loop(False)
            else:
                self._pin.loop(True)
                d2 = int(
                    (self._pin.source_freq() / RMT_CLOCK_DIV) / value // 2)
                self._pin.write_pulses((d2, d2))
        if self._verbose:
            self.__logFrequency()

    @property
    def max_duty(self):
        if self._chanRMT < 0:
            return MAX_DUTY
        else:
            return RMT_MAX_DUTY

    @property
    def uses_rmt(self):
        return self._chanRMT >= 0

    def __logFrequency(self):
        print("PWM frequency is {0:.1f} kHz".format(self.freq_Hz / 1000))

    def __setRMTDuty(self, value):
        self._dutyRMT = int(min(max(1, value), RMT_MAX_DUTY))
        self._pin.write_pulses((self._dutyRMT, RMT_MAX_DUTY - self._dutyRMT))