seveibar/pico-w-3x5-led-matrix
A 15-LED WS2812B RGB matrix with a Raspberry Pi Pico W, connected in a daisy-chain configuration and powered via 5V, controlled by the microcontroller's GPIO pins.
Usage: To import and use the "@tsci/seveibar.pico-w-3x5-led-matrix" component: 1. Import the component in your project: ```tsx import PicoLedMatrix from "@tsci/seveibar.pico-w-3x5-led-matrix" ``` 2. Use the component in a circuit board: ```tsx export default () => ( <board> <PicoLedMatrix /> </board> ) ``` The component creates a 3x5 LED matrix connected to a Raspberry Pi Pico W, with automatic grid layout and tracing between LEDs and the microcontroller. Key features: - Generates a 3x5 LED grid - Automatically connects LEDs - Includes Pico W placement - Uses WS2812B LEDs - Configures power and ground connections
- Version
- 0.0.1
- License
- unset
- Stars
- 4
index.ts
PCB
Schematic
import { WS2812B_2020 as LedWithIc } from "@tsci/seveibar.WS2812B_2020"
import { usePICO_W } from "@tsci/seveibar.PICO_W"
type Point = { x: number; y: number }
type GridCellPositions = {
index: number
center: Point
topLeft: Point
bottomRight: Point
}
type GridOptions = {
rows: number
cols: number
xSpacing?: number
ySpacing?: number
width?: number
height?: number
offsetX?: number
offsetY?: number
yDirection?: "cartesian" | "up-is-negative"
}
// ToDO import from tscircuit utils in the future
function grid({
rows,
cols,
xSpacing,
ySpacing,
width,
height,
offsetX = 0,
offsetY = 0,
yDirection = "cartesian",
}: GridOptions): GridCellPositions[] {
// Calculate cell dimensions
const cellWidth = width ? width / cols : xSpacing ?? 1
const cellHeight = height ? height / rows : ySpacing ?? 1
const cells: GridCellPositions[] = []
for (let row = 0; row < rows; row++) {
for (let col = 0; col < cols; col++) {
const index = row * cols + col
// Calculate center position
const centerX = offsetX + col * cellWidth + cellWidth / 2
const rawCenterY = offsetY + row * cellHeight + cellHeight / 2
// Adjust Y coordinate based on yDirection
const centerY =
yDirection === "cartesian"
? offsetY + (rows - 1 - row) * cellHeight + cellHeight / 2
: rawCenterY
cells.push({
index,
center: { x: centerX, y: centerY },
topLeft: {
x: centerX - cellWidth / 2,
y: centerY + cellHeight / 2,
},
bottomRight: {
x: centerX + cellWidth / 2,
y: centerY - cellHeight / 2,
},
})
}
}
return cells
}
export default () => {
const U1 = usePICO_W("U1")
return (
<board
width="55mm"
height="52mm"
>
<U1 pcbRotation="90deg" pcbX={-15} pcbY={0} />
{grid({ cols: 3, rows: 5, xSpacing: 8, ySpacing: 5, offsetX: 3 }).map(
({ center, index }) => {
const ledName = `LED${index + 1}`
const prevLedName = index > 0 ? `LED${index}` : null
return (
<>
<LedWithIc schX={center.x/2} schY={5 + center.y/2} name={ledName} pcbX={center.x} pcbY={center.y} />
<trace from={`.${ledName} .GND`} to="net.GND" />
<trace from={`.${ledName} .VDD`} to="net.V5" />
{prevLedName && <trace from={`.${prevLedName} .DO`} to={`.${ledName} .DI`} />}
</>
)
}
)}
<trace from=".LED1 .DI" to={U1.GP6_SPI0SCK_I2C1SDA} />
<trace from={U1.GND1} to="net.GND" />
<trace from={U1.GND2} to="net.GND" />
<trace from={U1.GND3} to="net.GND" />
<trace from={U1.GND4} to="net.GND" />
<trace from={U1.GND5} to="net.GND" />
<trace from={U1.GND6} to="net.GND" />
<trace from={U1.GND7} to="net.GND" />
<trace from={U1.VBUS} to="net.V5" />
<LedWithIc name="LED16" schX={8} />
<trace from={`.LED16 .GND`} to="net.GND" />
<trace from={`.LED16 .VDD`} to={"net.V5"} />
<trace from=".LED16 .DI" to={U1.GP10_SPI1SCK_I2C1SDA} />
</board>
)
}