diff --git a/server/drivers/apa102.py b/server/drivers/apa102.py index aa3de8c..f100219 100644 --- a/server/drivers/apa102.py +++ b/server/drivers/apa102.py @@ -1,5 +1,6 @@ import spidev import logging as log +from multiprocessing import Array as multiprocessing_array """ Driver for APA102 LEDS (aka "DotStar"). @@ -21,6 +22,10 @@ - combineColor - wheel + +If the parameter multiprocessing is enabled in the constructor, the LED buffer is stored in a static array which is +available to all processes of apa102.py + The rest of the methods are used internally and should not be used by the user of the library. Very brief overview of APA102: An APA102 LED is addressed with SPI. The bits are shifted in one by one, @@ -59,13 +64,16 @@ class APA102: - def __init__(self, numLEDs, globalBrightness=31, order='rgb', max_spi_speed_hz=8000000): + def __init__(self, numLEDs, globalBrightness=31, order='rgb', max_spi_speed_hz=8000000, multiprocessing=False): self.numLEDs = numLEDs order = order.lower() self.rgb = rgb_map.get(order, rgb_map['rgb']) # LED startframe is three "1" bits, followed by 5 brightness bits self.setGlobalBrightness(brightness=globalBrightness, update_buffer=False) self.leds = [self.ledstart, 0, 0, 0] * self.numLEDs # Pixel buffer + self.multiprocessing = multiprocessing # if multiprocessing enabled: convert array to a shared state + if self.multiprocessing: + self.leds = multiprocessing_array('i', self.leds) self.spi = spidev.SpiDev() # Init the SPI device self.spi.open(0, 1) # Open SPI port 0, slave device (CS) 1 self.spi.max_speed_hz = max_spi_speed_hz # should not be higher than 8000000 @@ -202,6 +210,8 @@ def setPixelRGB(self, ledNum, rgbColor): def rotate(self, positions=1): cutoff = 4 * (positions % self.numLEDs) self.leds = self.leds[cutoff:] + self.leds[:cutoff] + if self.multiprocessing: + self.leds = multiprocessing_array('i', self.leds) """ void show() @@ -211,7 +221,7 @@ def rotate(self, positions=1): def show(self): self.clockStartFrame() - self.spi.xfer2(self.leds) # SPI takes up to 4096 Integers. So we are fine for up to 1024 LEDs. + self.spi.xfer2(list(self.leds)) # SPI takes up to 4096 Integers. So we are fine for up to 1024 LEDs. self.clockEndFrame() """ diff --git a/server/mqtt/MQTTControl.py b/server/mqtt/MQTTControl.py index 8cabe6e..8d74268 100644 --- a/server/mqtt/MQTTControl.py +++ b/server/mqtt/MQTTControl.py @@ -121,8 +121,6 @@ def stop_running_show(timeout_sec: int = 0.5): else: log.info("no show running; all good") - strip.clearBuffer() # just in case - def set_strip_brightness(brightness: int): global conf, strip @@ -146,7 +144,11 @@ def run(config) -> None: log.info("Starting {name}".format(name=conf.sys_name)) log.info("Initializing LED strip...") - strip = APA102(conf.strip.num_leds, conf.strip.initial_brightness, 'rgb', conf.strip.max_spi_speed_hz) + strip = APA102(numLEDs=conf.strip.num_leds, + globalBrightness=conf.strip.initial_brightness, + order='rgb', + max_spi_speed_hz=conf.strip.max_spi_speed_hz, + multiprocessing=True) log.info("Connecting to the MQTT broker") client = mqtt.Client()