From 964eb338c060b5408d248ab20da389f29ba91430 Mon Sep 17 00:00:00 2001 From: viernullvier Date: Wed, 8 Apr 2026 00:05:33 +0200 Subject: [PATCH] chore(tiny): Add demo script to test LEDs and buttons --- neogrid-tiny/software/main.py | 149 ++++++++++++++++++++++++++++++++++ 1 file changed, 149 insertions(+) create mode 100644 neogrid-tiny/software/main.py diff --git a/neogrid-tiny/software/main.py b/neogrid-tiny/software/main.py new file mode 100644 index 0000000..11a404f --- /dev/null +++ b/neogrid-tiny/software/main.py @@ -0,0 +1,149 @@ +# Example using PIO to drive a set of WS2812 LEDs. + +import array, time +from machine import Pin +import rp2 + +# Configure the number of WS2812 LEDs. +NUM_LEDS = 32 +PIN_NUM = 16 +brightness = 0.2 + +@rp2.asm_pio(sideset_init=rp2.PIO.OUT_LOW, out_shiftdir=rp2.PIO.SHIFT_LEFT, autopull=True, pull_thresh=24) +def ws2812(): + T1 = 2 + T2 = 5 + T3 = 3 + wrap_target() + label("bitloop") + out(x, 1) .side(1) [T3 - 1] + jmp(not_x, "do_zero") .side(0) [T1 - 1] + jmp("bitloop") .side(0) [T2 - 1] + label("do_zero") + nop() .side(1) [T2 - 1] + wrap() + + +# Create the StateMachine with the ws2812 program, outputting on pin +sm = rp2.StateMachine(0, ws2812, freq=8_000_000, sideset_base=Pin(PIN_NUM)) + +# Start the StateMachine, it will wait for data on its FIFO. +sm.active(1) + +# Display a pattern on the LEDs via an array of LED RGB values. +ar = array.array("I", [0 for _ in range(NUM_LEDS)]) + +########################################################################## +def pixels_show(): + dimmer_ar = array.array("I", [0 for _ in range(NUM_LEDS)]) + for i,c in enumerate(ar): + r = int(((c >> 8) & 0xFF) * brightness) + g = int(((c >> 16) & 0xFF) * brightness) + b = int((c & 0xFF) * brightness) + dimmer_ar[i] = (g<<16) + (r<<8) + b + sm.put(dimmer_ar, 8) + time.sleep_ms(10) + +def pixels_set(i, color): + ar[i] = (color[1]<<16) + (color[0]<<8) + color[2] + +def pixels_fill(color): + for i in range(len(ar)): + pixels_set(i, color) + +def color_chase(color, wait): + for i in range(NUM_LEDS): + pixels_set(i, color) + time.sleep(wait) + pixels_show() + time.sleep(0.2) + +def wheel(pos): + # Input a value 0 to 255 to get a color value. + # The colours are a transition r - g - b - back to r. + if pos < 0 or pos > 255: + return (0, 0, 0) + if pos < 85: + return (255 - pos * 3, pos * 3, 0) + if pos < 170: + pos -= 85 + return (0, 255 - pos * 3, pos * 3) + pos -= 170 + return (pos * 3, 0, 255 - pos * 3) + +def rainbow_cycle(wait): + for j in range(255): + for i in range(NUM_LEDS): + rc_index = (i * 256 // NUM_LEDS) + j + pixels_set(i, wheel(rc_index & 255)) + pixels_show() + time.sleep(wait) + +BLACK = (0, 0, 0) +RED = (255, 0, 0) +YELLOW = (255, 150, 0) +GREEN = (0, 255, 0) +CYAN = (0, 255, 255) +BLUE = (0, 0, 255) +PURPLE = (180, 0, 255) +WHITE = (255, 255, 255) +COLORS = (BLACK, RED, YELLOW, GREEN, CYAN, BLUE, PURPLE, WHITE) + +print("fills") +for color in COLORS: + pixels_fill(color) + pixels_show() + time.sleep(0.2) + +print("chases") +for color in COLORS: + color_chase(color, 0.01) + +print("rainbow") +rainbow_cycle(0) + +row_pins = [ + Pin(0, Pin.OUT), + Pin(1, Pin.OUT), + Pin(2, Pin.OUT), + Pin(3, Pin.OUT), + Pin(4, Pin.OUT), + Pin(5, Pin.OUT), + Pin(6, Pin.OUT), + Pin(7, Pin.OUT), +] + +col_pins = [ + Pin(32, Pin.IN, Pin.PULL_UP), + Pin(33, Pin.IN, Pin.PULL_UP), + Pin(34, Pin.IN, Pin.PULL_UP), + Pin(35, Pin.IN, Pin.PULL_UP), +] + +# reset cols + +for pin in row_pins: + pin.value(1) + + +row_count = len(row_pins) +col_count = len(col_pins) +key_num = 0 +pressed_keys = set() +while True: + pressed_keys.clear() + for row, row_pin in enumerate(row_pins): + # set only active pin low, keep rest high + row_pin.value(0) + # for col, col_pin in enumerate(col_pins): + # col_pin.value(1) + # time.sleep_ms(10) + for col, col_pin in enumerate(col_pins): + key = col_count * row + col + 1 + if not col_pin.value(): + pressed_keys.add(key) + # print("key", key, "pin", col, ":", row, col_pin.value()) + row_pin.value(1) + print("pressed", pressed_keys) + time.sleep_ms(50) +