Skip to content

Commit 5f4a8e4

Browse files
authored
Merge pull request #733 from adafruit/add-pwm-api-v2
v2 API - Add PWM and Servo Support
2 parents 25ad69a + c1a3c4e commit 5f4a8e4

File tree

16 files changed

+1492
-38
lines changed

16 files changed

+1492
-38
lines changed

examples/Wippersnapper_NoFS/Wippersnapper_NoFS.ino

Lines changed: 8 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -1,36 +1,31 @@
1-
// Adafruit IO WipperSnapper Beta
2-
//
3-
//
4-
// NOTE: This software is a BETA release and in active development.
5-
// Please report bugs or errors to
6-
// https://github.com/adafruit/Adafruit_Wippersnapper_Arduino/issues
1+
// Adafruit IO WipperSnapper
72
//
83
// This sketch is for devices which lack USB-MSD or LittleFS support such
9-
// as the Arduino MKR WiFi 1010, Arduino Nano 33 IoT.
4+
// as the ESP32Dev for Wokwi Simulator
105
//
116
// Adafruit invests time and resources providing this open source code.
127
// Please support Adafruit and open source hardware by purchasing
138
// products from Adafruit!
149
//
15-
// Brent Rubell for Adafruit Industries, 2021
10+
// Brent Rubell for Adafruit Industries, 2025
1611
//
1712
// All text above must be included in any redistribution.
1813

19-
#include "Wippersnapper_Networking.h"
20-
14+
#include "ws_adapters.h"
15+
#define WS_DEBUG // Enable debug output
2116
/************************ Adafruit IO Config *******************************/
2217

2318
// Visit io.adafruit.com if you need to create an account,
2419
// or if you need your Adafruit IO key.
2520
#define IO_USERNAME "YOUR_AIO_USERNAME"
2621
#define IO_KEY "YOUR_AIO_KEY"
27-
22+
#define IO_URL "io.adafruit.com"
23+
#define IO_PORT 8883
2824
/**************************** WiFi Config ***********************************/
2925
#define WIFI_SSID "YOUR_WIFI_SSID"
3026
#define WIFI_PASS "YOUR_WIFI_PASSWORD"
3127

32-
#include "Wippersnapper_Networking.h"
33-
ws_adapter_wifi wipper(IO_USERNAME, IO_KEY, WIFI_SSID, WIFI_PASS);
28+
ws_adapter_wifi wipper(IO_USERNAME, IO_KEY, WIFI_SSID, WIFI_PASS, IO_URL, IO_PORT);
3429

3530
void setup() {
3631
// Provisioning must occur prior to serial init.

src/Wippersnapper_V2.cpp

Lines changed: 55 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -55,6 +55,8 @@ Wippersnapper_V2::Wippersnapper_V2() {
5555
WsV2._ds18x20_controller = new DS18X20Controller();
5656
WsV2._i2c_controller = new I2cController();
5757
WsV2._pixels_controller = new PixelsController();
58+
WsV2._pwm_controller = new PWMController();
59+
WsV2._servo_controller = new ServoController();
5860
};
5961

6062
/**************************************************************************/
@@ -335,99 +337,127 @@ bool cbDecodeBrokerToDevice(pb_istream_t *stream, const pb_field_t *field,
335337
WS_DEBUG_PRINTLN("-> Checkin Response Message Type");
336338
WS_DEBUG_PRINT("Handling Checkin Response...");
337339
if (!handleCheckinResponse(stream)) {
338-
WS_DEBUG_PRINTLN("Failure handling Checkin Response!");
339340
return false;
340341
}
341342
WS_DEBUG_PRINTLN("Handled!");
342343
break;
343344
case wippersnapper_signal_BrokerToDevice_digitalio_add_tag:
344345
WS_DEBUG_PRINTLN("-> DigitalIO Add Message Type");
345346
if (!WsV2.digital_io_controller->Handle_DigitalIO_Add(stream)) {
346-
WS_DEBUG_PRINTLN("ERROR: Unable to add digitalio pin!");
347347
return false;
348348
}
349349
break;
350350
case wippersnapper_signal_BrokerToDevice_digitalio_remove_tag:
351351
WS_DEBUG_PRINTLN("-> DigitalIO Remove Message Type");
352352
if (!WsV2.digital_io_controller->Handle_DigitalIO_Remove(stream)) {
353-
WS_DEBUG_PRINTLN("ERROR: Unable to remove digitalio pin!");
354353
return false;
355354
}
356355
break;
357356
case wippersnapper_signal_BrokerToDevice_digitalio_write_tag:
358357
WS_DEBUG_PRINTLN("-> DigitalIO Write Message Type");
359358
if (!WsV2.digital_io_controller->Handle_DigitalIO_Write(stream)) {
360-
WS_DEBUG_PRINTLN("ERROR: Unable to write to digitalio pin!");
361359
return false;
362360
}
363361
break;
364362
case wippersnapper_signal_BrokerToDevice_analogio_add_tag:
365363
WS_DEBUG_PRINTLN("-> AnalogIO Add Message Type");
366364
if (!WsV2.analogio_controller->Handle_AnalogIOAdd(stream)) {
367-
WS_DEBUG_PRINTLN("ERROR: Unable to add analogio pin!");
368365
return false;
369366
}
370367
break;
371368
case wippersnapper_signal_BrokerToDevice_analogio_remove_tag:
372369
WS_DEBUG_PRINTLN("-> AnalogIO Remove Message Type");
373370
if (!WsV2.analogio_controller->Handle_AnalogIORemove(stream)) {
374-
WS_DEBUG_PRINTLN("ERROR: Unable to remove analogio pin!");
375371
return false;
376372
}
377373
break;
378374
case wippersnapper_signal_BrokerToDevice_ds18x20_add_tag:
379375
WS_DEBUG_PRINTLN("-> DS18X20 Add Message Type");
380376
if (!WsV2._ds18x20_controller->Handle_Ds18x20Add(stream)) {
381-
WS_DEBUG_PRINTLN("ERROR: Unable to add DS18X20 sensor!");
382377
return false;
383378
}
384379
break;
385380
case wippersnapper_signal_BrokerToDevice_ds18x20_remove_tag:
386381
WS_DEBUG_PRINTLN("-> DS18X20 Remove Message Type");
387382
if (!WsV2._ds18x20_controller->Handle_Ds18x20Remove(stream)) {
388-
WS_DEBUG_PRINTLN("ERROR: Unable to remove DS18X20 sensor!");
389383
return false;
390384
}
391385
break;
392386
case wippersnapper_signal_BrokerToDevice_i2c_device_add_replace_tag:
393387
WS_DEBUG_PRINTLN("-> I2C Device Add/Replace Message Type");
394388
if (!WsV2._i2c_controller->Handle_I2cDeviceAddOrReplace(stream)) {
395-
WS_DEBUG_PRINTLN("ERROR: Unable to add/replace I2C device!");
396389
return false;
397390
}
398391
break;
399392
case wippersnapper_signal_BrokerToDevice_i2c_bus_scan_tag:
400393
WS_DEBUG_PRINTLN("-> I2C Bus Scan Message Type");
401394
if (!WsV2._i2c_controller->Handle_I2cBusScan(stream)) {
402-
WS_DEBUG_PRINTLN("ERROR: Unable to add/replace I2C device!");
403395
return false;
404396
}
405397
break;
406398
case wippersnapper_signal_BrokerToDevice_i2c_device_remove_tag:
407399
WS_DEBUG_PRINTLN("-> I2C Device Remove Message Type");
408400
if (!WsV2._i2c_controller->Handle_I2cDeviceRemove(stream)) {
409-
WS_DEBUG_PRINTLN("ERROR: Unable to remove I2C device!");
410401
return false;
411402
}
412403
break;
413404
case wippersnapper_signal_BrokerToDevice_pixels_add_tag:
414405
WS_DEBUG_PRINTLN("-> Pixels Add Message Type");
415406
if (!WsV2._pixels_controller->Handle_Pixels_Add(stream)) {
416-
WS_DEBUG_PRINTLN("ERROR: Unable to add pixels strand!");
417407
return false;
418408
}
419409
break;
420410
case wippersnapper_signal_BrokerToDevice_pixels_remove_tag:
421411
WS_DEBUG_PRINTLN("-> Pixels Remove Message Type");
422412
if (!WsV2._pixels_controller->Handle_Pixels_Remove(stream)) {
423-
WS_DEBUG_PRINTLN("ERROR: Unable to remove pixels strand!");
424413
return false;
425414
}
426415
break;
427416
case wippersnapper_signal_BrokerToDevice_pixels_write_tag:
428417
WS_DEBUG_PRINTLN("-> Pixels Write Message Type");
429418
if (!WsV2._pixels_controller->Handle_Pixels_Write(stream)) {
430-
WS_DEBUG_PRINTLN("ERROR: Unable to write to pixels strand!");
419+
return false;
420+
}
421+
break;
422+
case wippersnapper_signal_BrokerToDevice_pwm_add_tag:
423+
WS_DEBUG_PRINTLN("-> PWM Add Message Type");
424+
if (!WsV2._pwm_controller->Handle_PWM_Add(stream)) {
425+
return false;
426+
}
427+
break;
428+
case wippersnapper_signal_BrokerToDevice_pwm_write_duty_tag:
429+
WS_DEBUG_PRINTLN("-> PWM Write Duty Cycle Message Type");
430+
if (!WsV2._pwm_controller->Handle_PWM_Write_DutyCycle(stream)) {
431+
return false;
432+
}
433+
break;
434+
case wippersnapper_signal_BrokerToDevice_pwm_write_freq_tag:
435+
WS_DEBUG_PRINTLN("-> PWM Write Frequency Message Type");
436+
if (!WsV2._pwm_controller->Handle_PWM_Write_Frequency(stream)) {
437+
return false;
438+
}
439+
break;
440+
case wippersnapper_signal_BrokerToDevice_pwm_remove_tag:
441+
WS_DEBUG_PRINTLN("-> PWM Remove Message Type");
442+
if (!WsV2._pwm_controller->Handle_PWM_Remove(stream)) {
443+
return false;
444+
}
445+
break;
446+
case wippersnapper_signal_BrokerToDevice_servo_add_tag:
447+
WS_DEBUG_PRINTLN("-> Servo Add Message Type");
448+
if (!WsV2._servo_controller->Handle_Servo_Add(stream)) {
449+
return false;
450+
}
451+
break;
452+
case wippersnapper_signal_BrokerToDevice_servo_write_tag:
453+
WS_DEBUG_PRINTLN("-> Servo Write Message Type");
454+
if (!WsV2._servo_controller->Handle_Servo_Write(stream)) {
455+
return false;
456+
}
457+
break;
458+
case wippersnapper_signal_BrokerToDevice_servo_remove_tag:
459+
WS_DEBUG_PRINTLN("-> Servo Remove Message Type");
460+
if (!WsV2._servo_controller->Handle_Servo_Remove(stream)) {
431461
return false;
432462
}
433463
break;
@@ -1005,6 +1035,17 @@ bool Wippersnapper_V2::PublishSignal(pb_size_t which_payload, void *payload) {
10051035
MsgSignal.payload.pixels_added =
10061036
*(wippersnapper_pixels_PixelsAdded *)payload;
10071037
break;
1038+
case wippersnapper_signal_DeviceToBroker_pwm_added_tag:
1039+
WS_DEBUG_PRINTLN("PWMAdded");
1040+
MsgSignal.which_payload = wippersnapper_signal_DeviceToBroker_pwm_added_tag;
1041+
MsgSignal.payload.pwm_added = *(wippersnapper_pwm_PWMAdded *)payload;
1042+
break;
1043+
case wippersnapper_signal_DeviceToBroker_servo_added_tag:
1044+
WS_DEBUG_PRINTLN("ServoAdded");
1045+
MsgSignal.which_payload =
1046+
wippersnapper_signal_DeviceToBroker_servo_added_tag;
1047+
MsgSignal.payload.servo_added = *(wippersnapper_servo_ServoAdded *)payload;
1048+
break;
10081049
default:
10091050
WS_DEBUG_PRINTLN("ERROR: Invalid signal payload type, bailing out!");
10101051
return false;

src/Wippersnapper_V2.h

Lines changed: 10 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -76,19 +76,12 @@
7676
#include <string>
7777
#include <vector>
7878

79-
// Nanopb dependencies
79+
// Nanopb messages and dependencies
80+
#include "protos/signal.pb.h"
8081
#include <nanopb/pb_common.h>
8182
#include <nanopb/pb_decode.h>
8283
#include <nanopb/pb_encode.h>
8384
#include <nanopb/ws_pb_helpers.h>
84-
#include <pb.h>
85-
86-
// Include Signal Proto
87-
#include "protos/checkin.pb.h"
88-
#include "protos/digitalio.pb.h"
89-
#include "protos/ds18x20.pb.h"
90-
#include "protos/pixels.pb.h"
91-
#include "protos/signal.pb.h"
9285

9386
// External libraries
9487
#include "Adafruit_MQTT.h" // MQTT Client
@@ -112,7 +105,9 @@
112105
#include "components/ds18x20/controller.h"
113106
#include "components/i2c/controller.h"
114107
#include "components/pixels/controller.h"
108+
#include "components/pwm/controller.h"
115109
#include "components/sensor/model.h"
110+
#include "components/servo/controller.h"
116111

117112
// Display
118113
#ifdef USE_DISPLAY
@@ -153,6 +148,8 @@ class AnalogIOController;
153148
class DS18X20Controller;
154149
class I2cController;
155150
class PixelsController;
151+
class PWMController;
152+
class ServoController;
156153

157154
/**************************************************************************/
158155
/*!
@@ -255,7 +252,10 @@ class Wippersnapper_V2 {
255252
nullptr; ///< Instance of DS18X20 controller
256253
I2cController *_i2c_controller = nullptr; ///< Instance of I2C controller
257254
PixelsController *_pixels_controller =
258-
nullptr; ///< Instance of Pixels controller
255+
nullptr; ///< Instance of Pixels controller
256+
PWMController *_pwm_controller = nullptr; ///< Instance of PWM controller
257+
ServoController *_servo_controller =
258+
nullptr; ///< Instance of Servo controller
259259

260260
// TODO: does this really need to be global?
261261
uint8_t _macAddrV2[6]; /*!< Unique network iface identifier */

src/components/ds18x20/model.cpp

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -24,7 +24,6 @@ DS18X20Model::DS18X20Model() {
2424
memset(&_msg_DS18x20Added, 0, sizeof(_msg_DS18x20Added));
2525
memset(&_msg_DS18x20Remove, 0, sizeof(_msg_DS18x20Remove));
2626
memset(&_msg_DS18x20Event, 0, sizeof(_msg_DS18x20Event));
27-
// no-op
2827
}
2928

3029
/***********************************************************************/

0 commit comments

Comments
 (0)