From 0f65e0227a08a7bc5910434f40e7398e1c172594 Mon Sep 17 00:00:00 2001 From: DeKay Date: Sun, 16 Feb 2014 12:56:51 -0600 Subject: [PATCH 1/3] Added a nullHandler function to deal with blank line input. --- SerialCommand.cpp | 12 +++++++++++- SerialCommand.h | 5 ++++- .../SerialCommandExample/SerialCommandExample.pde | 7 +++++++ keywords.txt | 1 + 4 files changed, 23 insertions(+), 2 deletions(-) diff --git a/SerialCommand.cpp b/SerialCommand.cpp index bbea5ba..4f78b1f 100644 --- a/SerialCommand.cpp +++ b/SerialCommand.cpp @@ -6,7 +6,7 @@ * Copyright (C) 2011 Steven Cogswell * http://husks.wordpress.com * - * Version 20120522 + * Updated for blank line support by DeKay, Feb 2014 * * This library is free software: you can redistribute it and/or modify * it under the terms of the GNU Lesser General Public License as published by @@ -30,6 +30,7 @@ SerialCommand::SerialCommand() : commandList(NULL), commandCount(0), defaultHandler(NULL), + nullHandler(NULL), term('\n'), // default terminator for commands, newline character last(NULL) { @@ -64,6 +65,13 @@ void SerialCommand::setDefaultHandler(void (*function)(const char *)) { defaultHandler = function; } +/** + * This sets up a handler to be called in the event that the user hits enter on a + * blank line + */ +void SerialCommand::setNullHandler(void (*function)()) { + nullHandler = function; +} /** * This checks the Serial stream for characters, and assembles them into a buffer. @@ -111,6 +119,8 @@ void SerialCommand::readSerial() { if (!matched && (defaultHandler != NULL)) { (*defaultHandler)(command); } + } else { + (*nullHandler)(); } clearBuffer(); } diff --git a/SerialCommand.h b/SerialCommand.h index e00dd29..1384692 100644 --- a/SerialCommand.h +++ b/SerialCommand.h @@ -6,7 +6,7 @@ * Copyright (C) 2011 Steven Cogswell * http://husks.wordpress.com * - * Version 20120522 + * Updated for blank line support by DeKay, Feb 2014 * * This library is free software: you can redistribute it and/or modify * it under the terms of the GNU Lesser General Public License as published by @@ -47,6 +47,7 @@ class SerialCommand { SerialCommand(); // Constructor void addCommand(const char *command, void(*function)()); // Add a command to the processing dictionary. void setDefaultHandler(void (*function)(const char *)); // A handler to call when no valid command received. + void setNullHandler(void (*function)()); // A handler to call when empty command received. void readSerial(); // Main entry point. void clearBuffer(); // Clears the input buffer. @@ -63,6 +64,8 @@ class SerialCommand { // Pointer to the default handler function void (*defaultHandler)(const char *); + // Pointer to the null handler function + void (*nullHandler)(); char delim[2]; // null-terminated list of character to be used as delimeters for tokenizing (default " ") char term; // Character that signals end of command (default '\n') diff --git a/examples/SerialCommandExample/SerialCommandExample.pde b/examples/SerialCommandExample/SerialCommandExample.pde index 8d0bf4a..46f6bb5 100644 --- a/examples/SerialCommandExample/SerialCommandExample.pde +++ b/examples/SerialCommandExample/SerialCommandExample.pde @@ -1,6 +1,7 @@ // Demo Code for SerialCommand Library // Steven Cogswell // May 2011 +// Updated for blank line support by DeKay, Feb 2014 #include @@ -20,6 +21,7 @@ void setup() { sCmd.addCommand("HELLO", sayHello); // Echos the string argument back sCmd.addCommand("P", processCommand); // Converts two arguments to integers and echos them back sCmd.setDefaultHandler(unrecognized); // Handler for command that isn't matched (says "What?") + sCmd.setNullHandler(blankLine); // Handler for a blank line (says "No Input.") Serial.println("Ready"); } @@ -81,3 +83,8 @@ void processCommand() { void unrecognized(const char *command) { Serial.println("What?"); } + +// This gets set as the null handler, and gets called a blank line is received. +void blankLine() { + Serial.println("No input."); +} \ No newline at end of file diff --git a/keywords.txt b/keywords.txt index 45ada90..fc547e7 100644 --- a/keywords.txt +++ b/keywords.txt @@ -10,6 +10,7 @@ SerialCommand KEYWORD1 addCommand KEYWORD2 setDefaultHandler KEYWORD2 +setNullHandler KEYWORD2 readSerial KEYWORD2 clearBuffer KEYWORD2 next KEYWORD2 From a6519abfa740973be66689026f0ede711c961bd1 Mon Sep 17 00:00:00 2001 From: DeKay Date: Sun, 16 Feb 2014 13:16:42 -0600 Subject: [PATCH 2/3] Added support for a second line terminator (eg. \n and \r) --- SerialCommand.cpp | 5 +++-- SerialCommand.h | 3 ++- 2 files changed, 5 insertions(+), 3 deletions(-) diff --git a/SerialCommand.cpp b/SerialCommand.cpp index 4f78b1f..042a010 100644 --- a/SerialCommand.cpp +++ b/SerialCommand.cpp @@ -6,7 +6,7 @@ * Copyright (C) 2011 Steven Cogswell * http://husks.wordpress.com * - * Updated for blank line support by DeKay, Feb 2014 + * Updated for blank line support & an alternate line terminator by DeKay, Feb 2014 * * This library is free software: you can redistribute it and/or modify * it under the terms of the GNU Lesser General Public License as published by @@ -32,6 +32,7 @@ SerialCommand::SerialCommand() defaultHandler(NULL), nullHandler(NULL), term('\n'), // default terminator for commands, newline character + term2('\r'), // default alternate terminator for commands, carriage return character last(NULL) { strcpy(delim, " "); // strtok_r needs a null-terminated string @@ -85,7 +86,7 @@ void SerialCommand::readSerial() { Serial.print(inChar); // Echo back to serial stream #endif - if (inChar == term) { // Check for the terminator (default '\r') meaning end of command + if ((inChar == term) || (inChar == term2)) { // Check for the terminators ('\n') or ('\r') meaning end of command #ifdef SERIALCOMMAND_DEBUG Serial.print("Received: "); Serial.println(buffer); diff --git a/SerialCommand.h b/SerialCommand.h index 1384692..3407f38 100644 --- a/SerialCommand.h +++ b/SerialCommand.h @@ -6,7 +6,7 @@ * Copyright (C) 2011 Steven Cogswell * http://husks.wordpress.com * - * Updated for blank line support by DeKay, Feb 2014 + * Updated for blank line support & an alternate line terminator by DeKay, Feb 2014 * * This library is free software: you can redistribute it and/or modify * it under the terms of the GNU Lesser General Public License as published by @@ -69,6 +69,7 @@ class SerialCommand { char delim[2]; // null-terminated list of character to be used as delimeters for tokenizing (default " ") char term; // Character that signals end of command (default '\n') + char term2; // Alternate character that signals end of command (default '\r') char buffer[SERIALCOMMAND_BUFFER + 1]; // Buffer of stored characters while waiting for terminator character byte bufPos; // Current position in the buffer From 93b1d3fe338b5c9b6c531aa44635332f89f7e3bc Mon Sep 17 00:00:00 2001 From: DeKay Date: Sun, 23 Feb 2014 15:15:47 -0600 Subject: [PATCH 3/3] Add support for 0x12 on input to support WeeWX's WRD command. --- SerialCommand.cpp | 19 ++++++++++++------- readme.md | 4 ++-- 2 files changed, 14 insertions(+), 9 deletions(-) diff --git a/SerialCommand.cpp b/SerialCommand.cpp index 042a010..601c0dd 100644 --- a/SerialCommand.cpp +++ b/SerialCommand.cpp @@ -1,23 +1,24 @@ /** * SerialCommand - A Wiring/Arduino library to tokenize and parse commands * received over a serial port. - * + * * Copyright (C) 2012 Stefan Rado * Copyright (C) 2011 Steven Cogswell * http://husks.wordpress.com - * - * Updated for blank line support & an alternate line terminator by DeKay, Feb 2014 - * + * + * Updated for blank line support, an alternate line terminator, and a + * non-printable character in the input buffer by DeKay, Feb 2014 + * * This library is free software: you can redistribute it and/or modify * it under the terms of the GNU Lesser General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. - * + * * This library is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU Lesser General Public License for more details. - * + * * You should have received a copy of the GNU General Public License * along with this library. If not, see . */ @@ -125,7 +126,11 @@ void SerialCommand::readSerial() { } clearBuffer(); } - else if (isprint(inChar)) { // Only printable characters into the buffer + // Only printable characters into the buffer EXCEPT for 0x12. + // This is necessary to implement the WRD<0x12><0x4d> command used by + // WeeWx when talking to a Davis weather station. Note 0x4d is printable + // so it does not need an exception below. + else if (isprint(inChar) || (inChar == 0x12)) { if (bufPos < SERIALCOMMAND_BUFFER) { buffer[bufPos++] = inChar; // Put character into buffer buffer[bufPos] = '\0'; // Null terminate diff --git a/readme.md b/readme.md index c439eca..5935574 100644 --- a/readme.md +++ b/readme.md @@ -1,7 +1,7 @@ SerialCommand ============= -A Wiring/Arduino library to tokenize and parse commands received over a serial port. +A Wiring/Arduino library to tokenize and parse commands received over a serial port. The original version of this library was written by [Steven Cogswell](http://husks.wordpress.com) (published May 23, 2011 in his blog post ["A Minimal Arduino Library for Processing Serial Commands"](http://husks.wordpress.com/2011/05/23/a-minimal-arduino-library-for-processing-serial-commands/)). -This is a heavily modified version with smaller footprint and a cleaned up code by Stefan Rado. +My changes are based on a heavily modified version with smaller footprint and cleaned up code by Stefan Rado. They add support for a return entered on an empty line, a second line terminator, and the allowance of non-printable characters in the input buffer when necessary when talking to a Davis weather station.