Permalink
Browse files

Convert the aJson library to use Wiring-style streams

Currently, the aJson library uses FILE* avr-libc streams, which
does not play well with the Arduino ecosystem. We introduce a new
class aJsonStream (plus two subclasses aJsonClientStream and
aJsonStringStream) that use the Wiring Stream object. This allows
to easily exchange JSON data e.g. over Serial and EthernetClient.

An accompanying example Json_Serial shows how to use this
functionality to send and receive JSON data over Serial.
  • Loading branch information...
1 parent 9a20c85 commit fa8387fe8237649e80e5505655542a2f91773494 @pasky pasky committed Nov 1, 2012
Showing with 442 additions and 377 deletions.
  1. +99 −0 Examples/Json_Serial/Json_Serial.ino
  2. +228 −160 aJSON.cpp
  3. +115 −29 aJSON.h
  4. +0 −142 utility/streamhelper.c
  5. +0 −46 utility/streamhelper.h
@@ -0,0 +1,99 @@
+/*
+ Sample sketch communicating over Serial using JSON
+
+ This sketch communicates over serial link with a computer, sending
+ JSON-encoded state of its analog pints every second and accepting
+ per-line JSON messages with desired values of PWM pins on input.
+
+ Circuit:
+ * (Optional) Analog sensors attached to analog pin.
+ * (Optional) LEDs attached to PWM pins 9 and 8.
+
+ created 1 November 2012
+ by Petr Baudis
+
+ https://github.com/interactive-matter/ajson
+ This code is in the public domain.
+ */
+
+#include <aJSON.h>
+
+unsigned long last_print = 0;
+aJsonStream serial_stream(&Serial);
+
+void setup()
+{
+ Serial.begin(9600);
+}
+
+/* Generate message like: { "analog": [0, 200, 400, 600, 800, 1000] } */
+aJsonObject *createMessage()
+{
+ aJsonObject *msg = aJson.createObject();
+
+ int analogValues[6];
+ for (int i = 0; i < 6; i++) {
+ analogValues[i] = analogRead(i);
+ }
+ aJsonObject *analog = aJson.createIntArray(analogValues, 6);
+ aJson.addItemToObject(msg, "analog", analog);
+
+ return msg;
+}
+
+/* Process message like: { "pwm": { "8": 0, "9": 128 } } */
+void processMessage(aJsonObject *msg)
+{
+ aJsonObject *pwm = aJson.getObjectItem(msg, "pwm");
+ if (!pwm) {
+ Serial.println("no pwm data");
+ return;
+ }
+
+ const static int pins[] = { 8, 9 };
+ const static int pins_n = 2;
+ for (int i = 0; i < pins_n; i++) {
+ char pinstr[3];
+ snprintf(pinstr, sizeof(pinstr), "%d", pins[i]);
+
+ aJsonObject *pwmval = aJson.getObjectItem(pwm, pinstr);
+ if (!pwmval) continue; /* Value not provided, ok. */
+ if (pwmval->type != aJson_Int) {
+ Serial.print("invalid data type ");
+ Serial.print(pwmval->type, DEC);
+ Serial.print(" for pin ");
+ Serial.println(pins[i], DEC);
+ continue;
+ }
+
+ Serial.print("setting pin ");
+ Serial.print(pins[i], DEC);
+ Serial.print(" to value ");
+ Serial.println(pwmval->valueint, DEC);
+ analogWrite(pins[i], pwmval->valueint);
+ }
+}
+
+void loop()
+{
+ if (millis() - last_print > 1000) {
+ /* One second elapsed, send message. */
+ aJsonObject *msg = createMessage();
+ aJson.print(msg, &serial_stream);
+ Serial.println(); /* Add newline. */
+ aJson.deleteItem(msg);
+ last_print = millis();
+ }
+
+ if (serial_stream.available()) {
+ /* First, skip any accidental whitespace like newlines. */
+ serial_stream.skip();
+ }
+
+ if (serial_stream.available()) {
+ /* Something real on input, let's take a look. */
+ aJsonObject *msg = aJson.parse(&serial_stream);
+ processMessage(msg);
+ aJson.deleteItem(msg);
+ }
+}
Oops, something went wrong.

0 comments on commit fa8387f

Please sign in to comment.