Pickle Ball Scoreboard
To do
add in change to yellow side after home key. DONE
add matrix timeout. Code in activity.py but not currently used
add brightness adjustment. DONE
use score % 10 to keep score in range 0-9 DONE
display symbols S, 1, 2 in the middle instead of red squares. DONE
“menu” should to machine.reset DONE
check out clear_both with fade. NO. takes too long
put classes in separate file
panels 1-4 may be ok. all 6 panels good.
IR imports
from ir_rx import IR_RX
from nec import NEC_8
import print_error
#from ir_rx.print_error import print_error
#from ir_rx.nec import NEC_8 # Adjust based on your remote's protocol
Wires
matrix input connector (DIN) is female at the top
Elegoo 830 supports max 21 awg preferably solid
I bought 24 AWG Elegoo Dupont connectors
Elegoo Fun kit wires are also 24 AWG. Fine for signal, a bit small for power.
The 10×14 digit 8 with a green stripe uses 102 pixels - 40% of 256
orange multimeter is a Neoteck 8233D Pro
grok says 24 AWG wire is generally sufficient for powering 100 out of 256 LEDs on a WS2812B
-
I do not need a reset button in Version 1. They can unplug the Pico from the battery.
run red/black from the baseus to the rails.
run yellow or orange/blue to the matrices.
two green data wire to the matirces.
black jumper from pico to a ground rail.
2026 03 24
changes in digit42
added random.seed(none) to use system time as the seed for different PBS colors
killed show_binary; now just show 4 pixels either red or green
show_brightNess only on su. ToDo
changed blueUp, blueDown, goldUp, and goldDown to change_*_score(integer) where integer is 1 or -1
kill green stripes on each end
move digits to the far left and right.
change digits for better readability Done
write a clear_middle that clear all space between the digits
show a left/right pointing arrow for each side
power does clear_both twice - no machine_reset
2026 03 21
digit41 fixes su.
power does machine reset
brightnessDown cannot go below 0.2
how to turn off lights reliably?
turnOff lets game continue.
should any key do a restore or do I need a timeout.
grok says pic can take usb-a for thonny work even when powered by 5v from a breadboard rail.
2025 03 20
returned amazon remote
got onn remote from walmart
getSamsung.py can read codes
do mapping
onn remote uses samsung codes
created button.py that can be imported as “from buttons import buttonMapSamsung”
getIrSamsung.pr Version 3 reads the codes and looks them up.
on to digit41.py
power shut off lights but game continues
menu/reset does nothing
su does not work Fixed
2026 03 19
digit(34, 35) are failed attempts to display versions of any key on timeout.
digit36 does work but has some timing issues.
bottom line is WE DON'T NEED A SCREEN TIMEOUT
falling back to digit33 because it has no flashing or timeout code
import new PBS positioning DONE
fix draw_middle to support 'S' DONE
modified button_map to be a list of [string, boolean]
if boolean is false, binary will flash red and pass
if boolean is true, binary will flash green and process string
activity code is present but commented out
digit37 is ok
activity was moved to activity.py
default brightness is now 0.2
digit38 is ok
tried to get samsung remote found in basement but none of getIrSamsung*.py worked. All lit the ir and GPIO.
digit39 shows version number in show_binary at start up
copying digit39 to main.py on the pico does run it after a hard boot
2026 03 18
spent the afternoon trying to get “Press Any Key” to scroll in digit34 and digit34.
Grok gave conflicting advice but nothing worked.
Found mutltiple declarations of buf and other, so create an AnyKey class.
Copying failed digit35 to digit36 and using the anyKey in numbers
fixed show PBS where the gold part of B started in column 2 instead of 0.
digit36 will display ANY KEY but response to keyed interrupt is slow commented out
ANY KEY is shown in a random color for all letters
2026 03 17
digit29 does up/down brightness from 0.1 through 0.5 in su mode only
digit30 reduced brightness to 6 pixels
digit31 Use random colors for PBS. repeat every 0.1 for 3 seconds
digit32 adds timeout
digit33 change side to gold after first home key press if done in 15 seconds
digit34 calls the anyKey code but nothing happens
move on to hardware. this is good enough
2026 03 16
digit23 has show_binary rewrite from grok but still flashes entire screen.
also has timeout after 3 minutes to blank the screen with any key restoring it.
cannot get rid of entire redraw even with grok's help.
going back to digit20.py renamed to digit25.py
it does not have timeout that was in digit21.py
add back single column green stripes from digit22 into digit25 DONE
add back new show_binary from digit24 into digit26 DONE
no fade - takes too long DONE
digit27 show brightness centered on the bottom line
digit28 key 0 toggles su on/off. status is a red/black pixel at gold 14,15
2026 03 15
got up at 5:30
it is now 9:30 and display ir code as binary works in digit17
at 4pm the three symbols ('S', 1, 2) all display in the middle area in digit18.py
start replacing the red squares with these in digit19.py
done in digit19.py, but stripe display is slow
will try grok's suggestion in digit20.py
digit20.py has optimization in show() and draw_stripe where I was calling show() 32 times!
going to digit21 to add timeout to blank display
blank display and any key restore works in digit21
going to digit22 to set green stripes to just 1 column DONE
going to digit23 to change side on new game (home)
2026 03 14
0zero.py is a digit13 copy.
key 9 displays the green right stripe
this is the right matrix where 0,0 is top right looking at the face
# xy conversion for the -right- matrix
def xy_to_index(x, y):
"""Top-left origin + reversed serpentine zigzag
- Even rows (y even): right-to-left (x=15 to x=0)
- Odd rows (y odd): left-to-right (x=0 to x=15)
"""
if y % 2 == 0: # ← Changed: even rows reverse
x = 15 - x
return y * 16 + x
we are not changing the xy code. the wires will be fine with similar led orientation.
digit14.py does all ok. copied to digit15.py
digit15 fixes curretn_player. copied to digit16
digit16 makes numbers.py 10×13 and displays an 8 pixel red line centered on the bottom row
2026 03 13
# works - does a soft reboot
if button == "menu":
machine.reset()
added to digit16.py
original hello.py ran for 20 minutes without Baseus shutting down the power using new breakout board SOLVED
hello.py gave repeating patterns.
wrote textxy.py and none of grok's suggestions worked.
tried pin 8 instead of pin 16 and no joy.
panels 5 and 6 both work the same as does (assumed dead) panel 4.
the problems with panels 1 - 4 could have been less than great grounding of everything.
four.py purports to put squares in each corner but –> nothing despite its 4 different calculations of idx, power injection, new green cable, sufficient voltage (4.97), and different pins
textxy.py thinks that 0.0 is the bottom right.
mapping is not right nor is color.
use textcy.py
2026 03 12
got switches and leds today. both too small.
other suggested switches require big (3/4“) holes.
if i use the Turn Off button to kill all the leds, the ir will be alive drawing minimal power.
Power consumption: At 3.3V → ~1.3–3.2 mW; at 5V → ~2–5 mW - battery will last for years.
Green light signals that unit is ready to go
set the home button to do a soft boot which restarts main.py
failing that, they can unplug the pico cable.
use a momentary switch only if that fails.
2026 03 10
blew up original pico. got two new ones for $23!
could not connect o com5. not such port.
tried com7 and all is ok.
copied ir_rx and ir_tx (remote control files) to the pi.
micropython-i2s is part of MP. use from machine import I2S.
some keyword arguments do not work in MP → value.to_bytes(2, 'little', signed=True)
ptone.py and pwave.py both work but sound is low and wav is unrecognizable
looks like matrix 3 and 4 also got toasted along with the pi last friday
suspect the stupid switching power supply
bought some usb-c to power and ground wires to bypass it
also bought some power switches for pico power
bought some power indicator leds complete with the needed resistors.
latest getir*.py do not work
2026 03 07
2026 03 05
2026 03 04
left matrix shows 5V but will not display.
powering both from original side.
ok with brightness set to 0.10
digit9 shows 0 in different colors on both matrices
blue on the left and yellow on the right.
to do: fix digit size and offset in digit10 DONE
digit 10 resets on home and display 0 to 9 forever on 0
todo - add green stripe DONE
digit12 does all but changing green strip kills digit
2026 03 03
red pixel and checkerboard test run if I bypass the resistor
resistors are not directional
use short wire and no resistor
five.py (red pixel) works
check.py works
stripe4.py works. displays green on bottom two rows. can change color and row.
led orientation is pixel 0 top right when facing leds.
pin 17 works better than pin 16
wvBlue looks pink. use blue 0x0000FF. wvGold is ok.
digit0 works.
digit1 has reversed digits.
digit2 works with fuller digits
putting resistor serial in line with data pin works, so resistor is ok if wired correctly.
leftGreen.py works putting a one pixel column on the left. Note the GRB notation.
digit4.py puts a green stripe on the left and then increments blue score with a lot of flashing.
digit5.py is latest good version, but match does not work
digit6 has futile attempt to use blankPattern
xy_to_index(x, y)
def xy_to_index(x, y):
"""Top-left origin + reversed serpentine zigzag
- Even rows (y even): right-to-left (x=15 to x=0)
- Odd rows (y odd): left-to-right (x=0 to x=15)
"""
if y % 2 == 0: # ← Changed: even rows reverse
x = 15 - x
return y * 16 + x
wire gauge
Yes, 0.75 mm is a real and very common wire size — it refers to the cross-sectional area
of the conductor in square millimeters (mm²), which is the standard way wire is specified
in most of the world (especially Europe, Asia, and metric countries).Quick conversion &
context0.75 mm² ≈ AWG 18 (very close) Exact AWG 18 = 0.823 mm²
0.75 mm² is slightly thinner but commonly grouped with AWG 18 in practice
Typical current rating (for low-voltage DC like your 5 V LED project):~6–10 A (depending
on insulation, temperature, length, and safety margin)
Safe for most hobby LED matrix projects (your two 16×16 WS2812B panels likely draw 5–12 A
max at full brightness)
Common uses of 0.75 mm² wirePower distribution in low-voltage DC projects (5 V, 12 V, 24 V)
LED strip power injection (common in WS2812B setups)
Automotive and marine wiring (12 V accessories)
Household low-power lighting (e.g. LED downlights, 230 V but low amps)
Speaker wire (short runs, 8–16 ohm)
Comparison to other common sizes
**Wire size Cross-section Closest AWG Typical max current (5 V DC) Usage**
0.3 mm² 0.3 mm² AWG 22 ~3–5 A Signal/data lines only
0.75 mm² 0.75 mm² AWG 18 ~6–10 A Good for power to matrices
1.0–1.5 mm² 1.0–1.5 mm² AWG 16–14 ~10–15 A+ High current / long runs
2.5 mm² 2.5 mm² AWG 12 20 A+ Heavy power injection
Recommendation for your LED matrices projectUse 0.75 mm² wire for:5 V power wires
from Baseus bank to power distribution point
Power injection wires to matrices (middle and end of strips)
Use thicker (1.0–1.5 mm² / AWG 16–14) if:Runs > 1–2 meters
Full brightness on all LEDs at once (>10 A draw)
Use thinner (0.3–0.5 mm² / AWG 22–20) for:Data lines (GP16/GP17 to matrix DIN)
IR receiver wiring
Color coding tip (very common convention):Red = +5 V
Black = GND
Green/Yellow = data (WS2812B DIN)
Other colors = signals, control lines
So yes — 0.75 mm (meaning 0.75 mm²) is a standard and very useful wire gauge/size
for your project. It's widely available and called "0.75 mm² hookup wire" or "0.75 mm²
flexible cable" when shopping.Let me know if you're asking about a specific wire you
have (photo/link?) or what part of the project you're wiring — I can recommend exact
lengths/colors/gauge!
clear() and show()
From Grok: Yes, that's correct — in the code structure we've been using, the clear() and show() functions work together in exactly the way you described.Here's a precise breakdown of what each does:clear()python
def clear():
for i in range(NUM_LEDS):
leds[i] = 0
What it does:
It resets the software buffer (leds array) by setting every LED's
color value to 0 (black/off).
→ This is just changing values in memory (the Python array leds).
→ Nothing is sent to the LEDs yet — the physical matrix stays unchanged
until you call show().
Purpose: Prepares a "blank" state before drawing new content (prevents
old pixels from remaining lit).
show()python
def show():
dimmed = array.array("I", [0] * NUM_LEDS)
for i, color in enumerate(leds):
r = int(((color >> 8) & 0xFF) * BRIGHTNESS)
g = int(((color >> 16) & 0xFF) * BRIGHTNESS)
b = int( (color & 0xFF) * BRIGHTNESS)
dimmed[i] = (g << 16) + (r << 8) + b
sm.put(dimmed, 8)
time.sleep_ms(10)
What it does: Takes the current values from the software buffer (leds).
Applies brightness scaling (creates a temporary dimmed array).
Sends the final color data to the PIO state machine via sm.put(...).
The PIO hardware then sends the WS2812B protocol bitstream to the
matrix → the physical LEDs update.
Key point:
show() is the only function that actually transfers data from the
buffer to the LEDs.
Any change to leds (clearing, setting pixels, drawing digits, etc.)
is invisible until show() is called.
Summary – Correct SequenceModify the buffer (leds array): clear() → sets all to 0
set_pixel(), draw_digit(), set_bottom_stripe(), etc. → sets desired colors
Call show() → sends the buffer to the state machine → LEDs update on the matrix
So yes:
clear() prepares the state in memory → show() displays it on the hardware.
If you ever change the LEDs but forget to call show(), nothing visible
happens — that's a very common debugging gotcha.Let me know if you want
to add auto-refresh (e.g., call show() inside every drawing function) or any other tweaks!
PIO State Machine
PIO (Programmable I/O) state machines are one of the most powerful and unique
features of the Raspberry Pi Pico (RP2040 chip). They allow you to create
custom, high-performance peripherals in hardware, running independently of
the CPU.Here’s a clear, practical explanation of what PIO state machines are,
how they work, and why they’re used (especially for WS2812B/NeoPixel LEDs in
your project).What is a PIO State Machine?A PIO state machine is a small,
programmable processor inside the RP2040 chip. Each state machine can:Run its
own tiny program (up to 32 instructions)
Execute instructions in parallel with the CPU
Interact directly with GPIO pins
Transfer data to/from memory via DMA (Direct Memory Access)
Run at system clock speed (up to 133 MHz)
The RP2040 has 8 PIO state machines (divided into two PIO blocks of 4 each),
so you can run up to 8 independent custom peripherals at once.Why PIO is
Perfect for WS2812B LEDsWS2812B LEDs require a very precise, high-speed serial
protocol:Each bit is sent as a pulse: ~0.4 µs high for 0, ~0.8 µs high for 1
24 bits per LED (GRB order)
Strict timing (no CPU interrupts allowed to break the stream)
If you try to bit-bang this in normal Python/MicroPython code, timing glitches
occur (CPU is too busy).
PIO solves this by running the bit protocol in hardware, with perfect timing,
while the CPU just prepares data.How a PIO State Machine Works (Simplified)
You write a tiny assembly program (in PIO assembly language) that describes
the waveform you want.
Example: the WS2812 code you’ve been using:pio
.side_set 1
out x, 1 .side 0 [T3-1]
jmp !x do_zero .side 1 [T1-1]
jmp bitloop .side 1 [T2-1]
do_zero:
nop .side 0 [T2-1]
This is the “send one bit” loop — high for longer on 1, shorter on 0.
You load the program into one of the 8 state machines:python
sm = rp2.StateMachine(0, ws2812, freq=8000000, sideset_base=Pin(16))
sm.active(1)
0 = state machine number (0–7)
ws2812 = your PIO program
freq=8000000 = clock speed tuned for WS2812 timing
sideset_base=Pin(16) = GPIO pin where the data signal goes
You feed it data:python
sm.put(buffer, 8) # send 32-bit words, shifted by 8 bits
The state machine automatically turns your color buffer into
the exact WS2812 pulse train — no CPU involvement.
Main Advantages of PIO for LEDsPerfect timing — no jitter, even if CPU is busy
Very low CPU usage — CPU just prepares data and calls put()
High speed — can drive long chains or multiple strips
Flexible — same PIO hardware can do WS2812, I2S audio, VGA, DVI, SPI, I2C, UART, etc.
Summary – What PIO State Machines AreTiny hardware processors inside the RP2040
Run custom programs you write in PIO assembly
Control GPIO pins with precise timing
Used for WS2812B LEDs because they need exact pulse widths the CPU can’t reliably produce
Your code uses one state machine (sm = StateMachine(0, ...)) to drive the matrix
If you want:Code to drive two matrices with two state machines (one per panel)
Explanation of any line in the PIO assembly
How to add IR control or other effects using PIO
2026 03 01