Skip to content

Commit 5576abc

Browse files
committed
Begin pixel.proto migration
1 parent c164dc3 commit 5576abc

File tree

9 files changed

+478
-1
lines changed

9 files changed

+478
-1
lines changed

CLAUDE.md

Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,24 @@
1+
# CLAUDE.md
2+
3+
This file provides guidance to Claude Code (claude.ai/code) when working with code in this repository.
4+
5+
## Build/Test Commands
6+
- Build with PlatformIO: `pio run`
7+
- Upload firmware: `python upload_no_build.py`
8+
- Run tests: `cd tests && python test_offline.py`
9+
- Run single test: `wokwi-cli --elf tests/bin/offline/firmware.elf --timeout 120000 --scenario tests/scenarios/offline/[test-file].scenario.yaml --diagram tests/diagrams/offline.json`
10+
11+
## Code Style Guidelines
12+
- Follow Adafruit library conventions
13+
- Header guards: UPPERCASE_WITH_UNDERSCORES
14+
- Classes: Model-View-Controller pattern (see components directory)
15+
- Naming: camelCase for methods, snake_case for variables, UPPER_CASE for constants
16+
- Imports: Group Arduino core, Adafruit libraries, then project-specific headers
17+
- Documentation: Use Doxygen-style comments for classes and functions
18+
- Error handling: Return error codes, use status LEDs for user feedback
19+
- Follow existing code patterns for new components
20+
21+
## Contributing
22+
- Follow Code of Conduct in CODE_OF_CONDUCT.md
23+
- For new components: https://learn.adafruit.com/how-to-add-a-new-component-to-adafruit-io-wippersnapper
24+
- For new boards: https://learn.adafruit.com/how-to-add-a-new-board-to-wippersnapper

src/Wippersnapper_V2.cpp

Lines changed: 34 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -54,6 +54,7 @@ Wippersnapper_V2::Wippersnapper_V2() {
5454
WsV2.analogio_controller = new AnalogIOController();
5555
WsV2._ds18x20_controller = new DS18X20Controller();
5656
WsV2._i2c_controller = new I2cController();
57+
WsV2._pixels_controller = new PixelsController();
5758
};
5859

5960
/**************************************************************************/
@@ -408,6 +409,28 @@ bool cbDecodeBrokerToDevice(pb_istream_t *stream, const pb_field_t *field,
408409
WS_DEBUG_PRINTLN("ERROR: Unable to remove I2C device!");
409410
return false;
410411
}
412+
break;
413+
case wippersnapper_signal_BrokerToDevice_pixels_add_tag:
414+
WS_DEBUG_PRINTLN("-> Pixels Add Message Type");
415+
if (!WsV2._pixels_controller->Handle_Pixels_Add(stream)) {
416+
WS_DEBUG_PRINTLN("ERROR: Unable to add pixels strand!");
417+
return false;
418+
}
419+
break;
420+
case wippersnapper_signal_BrokerToDevice_pixels_remove_tag:
421+
WS_DEBUG_PRINTLN("-> Pixels Remove Message Type");
422+
if (!WsV2._pixels_controller->Handle_Pixels_Remove(stream)) {
423+
WS_DEBUG_PRINTLN("ERROR: Unable to remove pixels strand!");
424+
return false;
425+
}
426+
break;
427+
case wippersnapper_signal_BrokerToDevice_pixels_write_tag:
428+
WS_DEBUG_PRINTLN("-> Pixels Write Message Type");
429+
if (!WsV2._pixels_controller->Handle_Pixels_Write(stream)) {
430+
WS_DEBUG_PRINTLN("ERROR: Unable to write to pixels strand!");
431+
return false;
432+
}
433+
break;
411434
default:
412435
WS_DEBUG_PRINTLN("ERROR: BrokerToDevice message type not found!");
413436
return false;
@@ -975,6 +998,13 @@ bool Wippersnapper_V2::PublishSignal(pb_size_t which_payload, void *payload) {
975998
MsgSignal.payload.ds18x20_event =
976999
*(wippersnapper_ds18x20_Ds18x20Event *)payload;
9771000
break;
1001+
case wippersnapper_signal_DeviceToBroker_pixels_added_tag:
1002+
WS_DEBUG_PRINTLN("PixelsAdded");
1003+
MsgSignal.which_payload =
1004+
wippersnapper_signal_DeviceToBroker_pixels_added_tag;
1005+
MsgSignal.payload.pixels_added =
1006+
*(wippersnapper_pixels_PixelsAdded *)payload;
1007+
break;
9781008
default:
9791009
WS_DEBUG_PRINTLN("ERROR: Invalid signal payload type, bailing out!");
9801010
return false;
@@ -1331,7 +1361,10 @@ ws_status_t Wippersnapper_V2::run() {
13311361

13321362
// TODO: Process I2C sensor events
13331363
WsV2._i2c_controller->update();
1334-
1364+
1365+
// Process Pixels events
1366+
// TODO: Add update() method to PixelsController if needed
1367+
13351368
// TODO: Process UART sensor events
13361369

13371370
return WS_NET_CONNECTED; // TODO: Make this funcn void!

src/Wippersnapper_V2.h

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -86,6 +86,7 @@
8686
#include "protos/checkin.pb.h"
8787
#include "protos/digitalio.pb.h"
8888
#include "protos/ds18x20.pb.h"
89+
#include "protos/pixels.pb.h"
8990
#include "protos/signal.pb.h"
9091

9192
// External libraries
@@ -109,6 +110,7 @@
109110
#include "components/digitalIO/controller.h"
110111
#include "components/ds18x20/controller.h"
111112
#include "components/i2c/controller.h"
113+
#include "components/pixels/controller.h"
112114
#include "components/sensor/model.h"
113115

114116
// Display
@@ -149,6 +151,7 @@ class DigitalIOController;
149151
class AnalogIOController;
150152
class DS18X20Controller;
151153
class I2cController;
154+
class PixelsController;
152155

153156
/**************************************************************************/
154157
/*!
@@ -250,6 +253,7 @@ class Wippersnapper_V2 {
250253
DS18X20Controller *_ds18x20_controller =
251254
nullptr; ///< Instance of DS18X20 controller
252255
I2cController *_i2c_controller = nullptr; ///< Instance of I2C controller
256+
PixelsController *_pixels_controller = nullptr; ///< Instance of Pixels controller
253257

254258
// TODO: does this really need to be global?
255259
uint8_t _macAddrV2[6]; /*!< Unique network iface identifier */
Lines changed: 69 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,69 @@
1+
/*!
2+
* @file controller.cpp
3+
*
4+
* Implementation for the pixels API controller.
5+
*
6+
* Adafruit invests time and resources providing this open source code,
7+
* please support Adafruit and open-source hardware by purchasing
8+
* products from Adafruit!
9+
*
10+
* Copyright (c) Brent Rubell 2025 for Adafruit Industries.
11+
*
12+
* BSD license, all text here must be included in any redistribution.
13+
*
14+
*/
15+
#include "controller.h"
16+
17+
/**************************************************************************/
18+
/*!
19+
@brief Constructs a new PixelsController object
20+
*/
21+
/**************************************************************************/
22+
PixelsController::PixelsController() {
23+
_pixels_model = new PixelsModel();
24+
_num_strands = 0;
25+
}
26+
27+
/**************************************************************************/
28+
/*!
29+
@brief Destructs a PixelsController object
30+
*/
31+
/**************************************************************************/
32+
PixelsController::~PixelsController() {
33+
delete _pixels_model;
34+
delete _pixel_strands;
35+
_num_strands = 0;
36+
}
37+
38+
/**************************************************************************/
39+
/*!
40+
@brief Handles a request to add a pixel strand
41+
@param stream
42+
Protocol buffer input stream
43+
@returns True if successful, False otherwise
44+
*/
45+
/**************************************************************************/
46+
bool PixelsController::Handle_Pixels_Add(pb_istream_t *stream) {
47+
}
48+
49+
/**************************************************************************/
50+
/*!
51+
@brief Handles a request to write to a pixel strand
52+
@param stream
53+
Protocol buffer input stream
54+
@returns True if successful, False otherwise
55+
*/
56+
/**************************************************************************/
57+
bool PixelsController::Handle_Pixels_Write(pb_istream_t *stream) {
58+
}
59+
60+
/**************************************************************************/
61+
/*!
62+
@brief Handles a request to remove a pixel strand
63+
@param stream
64+
Protocol buffer input stream
65+
@returns True if successful, False otherwise
66+
*/
67+
/**************************************************************************/
68+
bool PixelsController::Handle_Pixels_Remove(pb_istream_t *stream) {
69+
}

src/components/pixels/controller.h

Lines changed: 48 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,48 @@
1+
/*!
2+
* @file controller.h
3+
*
4+
* Controller for the pixels API
5+
*
6+
* Adafruit invests time and resources providing this open source code,
7+
* please support Adafruit and open-source hardware by purchasing
8+
* products from Adafruit!
9+
*
10+
* Copyright (c) Brent Rubell 2025 for Adafruit Industries.
11+
*
12+
* BSD license, all text here must be included in any redistribution.
13+
*
14+
*/
15+
#ifndef WS_PIXELS_CONTROLLER_H
16+
#define WS_PIXELS_CONTROLLER_H
17+
#include "Wippersnapper_V2.h"
18+
#include "hardware.h"
19+
#include "model.h"
20+
21+
#define MAX_PIXEL_STRANDS 5 ///< Maximum number of pixel strands connected to a WipperSnapper device
22+
23+
class Wippersnapper_V2; ///< Forward declaration
24+
class PixelsModel; ///< Forward declaration
25+
class PixelsHardware; ///< Forward declaration
26+
27+
/**************************************************************************/
28+
/*!
29+
@brief Routes messages using the pixels.proto API to the
30+
appropriate hardware and model classes, controls and tracks
31+
the state of pixel strands.
32+
*/
33+
/**************************************************************************/
34+
class PixelsController {
35+
public:
36+
PixelsController();
37+
~PixelsController();
38+
// Called by the cbDecodeBrokerToDevice router function
39+
bool Handle_Pixels_Add(pb_istream_t *stream);
40+
bool Handle_Pixels_Write(pb_istream_t *stream);
41+
bool Handle_Pixels_Remove(pb_istream_t *stream);
42+
private:
43+
PixelsModel *_pixels_model = nullptr; ///< Pointer to the model class
44+
PixelsHardware *_pixel_strands[MAX_PIXEL_STRANDS] = {nullptr}; ///< Pointer to the hardware class
45+
uint8_t _num_strands; ///< Number of pixel strands
46+
};
47+
extern Wippersnapper_V2 WsV2; ///< Wippersnapper V2 instance
48+
#endif // WS_PIXELS_CONTROLLER_H

src/components/pixels/hardware.cpp

Lines changed: 78 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,78 @@
1+
/*!
2+
* @file hardware.cpp
3+
*
4+
* Hardware implementation for pixel strands.
5+
*
6+
* Adafruit invests time and resources providing this open source code,
7+
* please support Adafruit and open-source hardware by purchasing
8+
* products from Adafruit!
9+
*
10+
* Copyright (c) Brent Rubell 2025 for Adafruit Industries.
11+
*
12+
* BSD license, all text here must be included in any redistribution.
13+
*
14+
*/
15+
#include "hardware.h"
16+
#include "Wippersnapper_V2.h"
17+
18+
/**************************************************************************/
19+
/*!
20+
@brief Constructs a new PixelsHardware object
21+
*/
22+
/**************************************************************************/
23+
PixelsHardware::PixelsHardware() {
24+
}
25+
26+
/**************************************************************************/
27+
/*!
28+
@brief Destructs a PixelsHardware object
29+
*/
30+
/**************************************************************************/
31+
PixelsHardware::~PixelsHardware() {
32+
}
33+
34+
/**************************************************************************/
35+
/*!
36+
@brief Configures a pixel strand
37+
@param pin_data
38+
Data pin for the pixel strand
39+
@param pin_clock
40+
Clock pin for DotStar pixel strands
41+
@param type
42+
Type of pixel strand (NeoPixel, DotStar)
43+
@param order
44+
Color ordering of pixels
45+
@param num_pixels
46+
Number of pixels in the strand
47+
@param brightness
48+
Initial brightness (0-255)
49+
@returns True if successful, False otherwise
50+
*/
51+
/**************************************************************************/
52+
bool PixelsHardware::ConfigurePixelStrand(uint8_t pin_data, uint8_t pin_clock,
53+
wippersnapper_pixels_PixelsType type,
54+
wippersnapper_pixels_PixelsOrder order,
55+
uint32_t num_pixels, uint32_t brightness) {
56+
}
57+
58+
/**************************************************************************/
59+
/*!
60+
@brief Sets the color of all pixels in the strand
61+
@param pin_data
62+
Data pin for the pixel strand
63+
@param color
64+
32-bit color value
65+
*/
66+
/**************************************************************************/
67+
void PixelsHardware::SetPixelColor(uint8_t pin_data, uint32_t color) {
68+
}
69+
70+
/**************************************************************************/
71+
/*!
72+
@brief Deinitializes a pixel strand
73+
@param pin_data
74+
Data pin for the pixel strand
75+
*/
76+
/**************************************************************************/
77+
void PixelsHardware::deinit(uint8_t pin_data) {
78+
}

src/components/pixels/hardware.h

Lines changed: 50 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,50 @@
1+
/*!
2+
* @file hardware.h
3+
*
4+
* Hardware interface for pixel strands.
5+
*
6+
* Adafruit invests time and resources providing this open source code,
7+
* please support Adafruit and open-source hardware by purchasing
8+
* products from Adafruit!
9+
*
10+
* Copyright (c) Brent Rubell 2025 for Adafruit Industries.
11+
*
12+
* BSD license, all text here must be included in any redistribution.
13+
*
14+
*/
15+
#ifndef WS_PIXELS_HARDWARE_H
16+
#define WS_PIXELS_HARDWARE_H
17+
#include "Wippersnapper_V2.h"
18+
19+
// TODO: Do we need this?
20+
/**
21+
* @struct PixelStrand
22+
* @brief This struct represents a NeoPixel or DotStar strand.
23+
*/
24+
struct PixelStrand {
25+
uint8_t pin_data; ///< Data pin
26+
uint8_t pin_clock; ///< Clock pin (for DotStar)
27+
wippersnapper_pixels_PixelsType type; ///< Pixel type
28+
wippersnapper_pixels_PixelsOrder order; ///< Color ordering
29+
uint32_t num_pixels; ///< Number of pixels
30+
uint32_t brightness; ///< Current brightness (0-255)
31+
};
32+
33+
/**************************************************************************/
34+
/*!
35+
@brief Interface for interacting with hardware's pixel strands.
36+
*/
37+
/**************************************************************************/
38+
class PixelsHardware {
39+
public:
40+
PixelsHardware();
41+
~PixelsHardware();
42+
bool ConfigurePixelStrand(uint8_t pin_data, uint8_t pin_clock,
43+
wippersnapper_pixels_PixelsType type,
44+
wippersnapper_pixels_PixelsOrder order,
45+
uint32_t num_pixels, uint32_t brightness);
46+
void SetPixelColor(uint8_t pin_data, uint32_t color);
47+
void deinit(uint8_t pin_data);
48+
private:
49+
};
50+
#endif // WS_PIXELS_HARDWARE_H

0 commit comments

Comments
 (0)