Skip to content

Commit e569fc6

Browse files
gandarezclaude
andcommitted
ws2812: wrap Device in Strip instead of custom writeFunc
Refactor Strip to compose the existing Device type, using its writeColorFunc to inject PIO behavior on RP2040/RP2350 instead of a separate write closure. Also fix brightness math off-by-one (255*255>>8 = 254) and pre-allocate the adjusted pixel buffer to avoid allocation on every Show() call. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
1 parent ddf7d54 commit e569fc6

3 files changed

Lines changed: 30 additions & 23 deletions

File tree

ws2812/strip.go

Lines changed: 17 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -5,12 +5,14 @@ import "image/color"
55
// Strip controls a strip of WS2812B LEDs with a pixel buffer and brightness control.
66
// Use NewStrip to create a new instance.
77
type Strip struct {
8+
dev Device
89
pixels []color.RGBA
10+
adjusted []color.RGBA
911
brightness uint8
10-
writeFunc func(pixels []color.RGBA, brightness uint8) error
1112
}
1213

1314
// SetPixel sets the color of pixel at index i.
15+
// Out-of-range indices are silently ignored.
1416
func (s *Strip) SetPixel(i int, c color.RGBA) {
1517
if i >= 0 && i < len(s.pixels) {
1618
s.pixels[i] = c
@@ -19,7 +21,10 @@ func (s *Strip) SetPixel(i int, c color.RGBA) {
1921

2022
// Show sends the current pixel buffer to the LED strip.
2123
func (s *Strip) Show() error {
22-
return s.writeFunc(s.pixels, s.brightness)
24+
for i, c := range s.pixels {
25+
s.adjusted[i] = applyBrightness(c, s.brightness)
26+
}
27+
return s.dev.WriteColors(s.adjusted)
2328
}
2429

2530
// SetBrightness sets the global brightness (0-255).
@@ -45,9 +50,14 @@ func (s *Strip) NumPixels() int {
4550
}
4651

4752
// applyBrightness scales a color by the brightness value.
48-
func applyBrightness(c color.RGBA, brightness uint8) (r, g, b uint8) {
49-
r = uint8((uint16(c.R) * uint16(brightness)) >> 8)
50-
g = uint8((uint16(c.G) * uint16(brightness)) >> 8)
51-
b = uint8((uint16(c.B) * uint16(brightness)) >> 8)
52-
return
53+
func applyBrightness(c color.RGBA, brightness uint8) color.RGBA {
54+
if brightness == 255 {
55+
return c
56+
}
57+
return color.RGBA{
58+
R: uint8((uint16(c.R) * (uint16(brightness) + 1)) >> 8),
59+
G: uint8((uint16(c.G) * (uint16(brightness) + 1)) >> 8),
60+
B: uint8((uint16(c.B) * (uint16(brightness) + 1)) >> 8),
61+
A: c.A,
62+
}
5363
}

ws2812/strip_other.go

Lines changed: 2 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -11,17 +11,10 @@ import (
1111
// number of pixels. On platforms without PIO, it uses the bit-bang driver.
1212
func NewStrip(pin machine.Pin, numPixels int) (*Strip, error) {
1313
pin.Configure(machine.PinConfig{Mode: machine.PinOutput})
14-
dev := NewWS2812(pin)
1514
return &Strip{
15+
dev: NewWS2812(pin),
1616
pixels: make([]color.RGBA, numPixels),
17+
adjusted: make([]color.RGBA, numPixels),
1718
brightness: 255,
18-
writeFunc: func(pixels []color.RGBA, brightness uint8) error {
19-
adjusted := make([]color.RGBA, len(pixels))
20-
for i, c := range pixels {
21-
r, g, bl := applyBrightness(c, brightness)
22-
adjusted[i] = color.RGBA{R: r, G: g, B: bl}
23-
}
24-
return dev.WriteColors(adjusted)
25-
},
2619
}, nil
2720
}

ws2812/strip_rp2.go

Lines changed: 11 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -21,15 +21,19 @@ func NewStrip(pin machine.Pin, numPixels int) (*Strip, error) {
2121
if err != nil {
2222
return nil, err
2323
}
24-
return &Strip{
25-
pixels: make([]color.RGBA, numPixels),
26-
brightness: 255,
27-
writeFunc: func(pixels []color.RGBA, brightness uint8) error {
28-
for _, c := range pixels {
29-
r, g, bl := applyBrightness(c, brightness)
30-
ws.PutRGB(r, g, bl)
24+
dev := Device{
25+
Pin: pin,
26+
writeColorFunc: func(d Device, buf []color.RGBA) error {
27+
for _, c := range buf {
28+
ws.PutRGB(c.R, c.G, c.B)
3129
}
3230
return nil
3331
},
32+
}
33+
return &Strip{
34+
dev: dev,
35+
pixels: make([]color.RGBA, numPixels),
36+
adjusted: make([]color.RGBA, numPixels),
37+
brightness: 255,
3438
}, nil
3539
}

0 commit comments

Comments
 (0)