Storing a series of command

the user is allowed to enter a set of command in the void loop() and according to the command, the program will shift to a specific function and do the task. This is direct, you enter, shift to a function and it returns to main loop and continues or limits can be made for controlling.
What I want to implement is the ability for the user to set a series of command and the arduino will do one at a time, that is, the user enters 4 data, a b c d. the program will do the first one a then will do the b and so on.
Couldnt find the appropriate keywords to search for this. Is it realizable as arduino is sequential. the data are stored and use one at a time. And also I thought of doing a count sytem so that it can eliminate one at a time, I dont know if it makes sense.

Help

What sort of commands do you want to enter, store and replay ? Have you got any examples ?

the data entered will be numbers up to hundreds(ranging from 0 to 180) and a text.
These data will be related to the motion of stepper motor in other functions.

You said replay, Im not doing a replay but more of doing one at a time and after the end, the main function is done.

For examples, i have none.

Im using the accelstepper library btw

here's a couple of approaches

pcRead accepts a optional multii-digit # followed by a single char command

// pcRead - debugging using serial monitor

const char version [] = "PcRead 201114a";

int debug = 0;

// ---------------------------------------------------------
// toggle output bit
void
pinToggle (
    int pin)
{
    static int  bits = 0;
    int     bit = 1 << pin;

    if (debug)  {
        Serial.print ("pinToggle: ");
        Serial.println (pin);
    }

    if (bits & bit)  {
        digitalWrite (pin, LOW);
        bits &= ~bit;
    }
    else {
        digitalWrite (pin, HIGH);
        bits |= bit;
    }
}

// ---------------------------------------------------------
// toggle output bit
int
readString (
    char *s,
    int   maxChar )
{
    int  n = 0;

    Serial.print ("> ");
    do {
        if (Serial.available()) {
            int c    = Serial.read ();

            if ('\n' == c)
                break;

            s [n++] = c;
            if (maxChar == n)
                break;
        }
    } while (true);

    return n;
}

// -----------------------------------------------------------------------------
// process single character commands from the PC
#define MAX_CHAR  10
char s [MAX_CHAR] = {};

int  analogPin = 0;

void
pcRead (void)
{

    static int  val = 0;

    if (Serial.available()) {
        int c = Serial.read ();

        switch (c)  {
        case '0':
        case '1':
        case '2':
        case '3':
        case '4':
        case '5':
        case '6':
        case '7':
        case '8':
        case '9':
            val = c - '0' + (10 * val);
            break;

        case 'A':
            analogPin = val;
            Serial.print   ("analogPin = ");
            Serial.println (val);
            val = 0;
            break;

        case 'D':
            debug ^= 1;
            break;

        case 'I':
            pinMode (val, INPUT);
            Serial.print   ("pinMode ");
            Serial.print   (val);
            Serial.println (" INPUT");
            val = 0;
            break;

        case 'O':
            pinMode (val, OUTPUT);
            Serial.print   ("pinMode ");
            Serial.print   (val);
            Serial.println (" OUTPUT");
            val = 0;
            break;

        case 'P':
            pinMode (val, INPUT_PULLUP);
            Serial.print   ("pinMode ");
            Serial.print   (val);
            Serial.println (" INPUT_PULLUP");
            val = 0;
            break;


        case 'a':
            Serial.print   ("analogRead: ");
            Serial.println (analogRead (val));
            val = 0;
            break;

        case 'c':
            digitalWrite (val, LOW);
            Serial.print   ("digitalWrite: LOW  ");
            Serial.println (val);
            val = 0;
            break;

        case 'p':
#if !defined(ARDUINO_ARCH_ESP32)
            analogWrite (analogPin, val);
            Serial.print   ("analogWrite: pin ");
            Serial.print   (analogPin);
            Serial.print   (", ");
            Serial.println (val);
            val = 0;
#endif
            break;

        case 'r':
            Serial.print   ("digitalRead: pin ");
            Serial.print   (val);
            Serial.print   (", ");
            Serial.println (digitalRead (val));
            val = 0;
            break;

        case 's':
            digitalWrite (val, HIGH);
            Serial.print   ("digitalWrite: HIGH ");
            Serial.println (val);
            val = 0;
            break;

        case 't':
            Serial.print   ("pinToggle ");
            Serial.println (val);
            digitalWrite (val, ! digitalRead (val));
            val = 0;
            break;

        case 'v':
            Serial.print ("\nversion: ");
            Serial.println (version);
            break;

        case '\n':          // ignore
            break;

        case '"':
            while ('\n' != Serial.read ())     // discard linefeed
                ;

            readString (s, MAX_CHAR-1);
            Serial.println (s);
            break;

        case '?':
            Serial.println ("\npcRead:\n");
            Serial.println ("    [0-9] append to #");
            Serial.println ("    A # - set analog pin #");
            Serial.println ("    D # - set debug to #");
            Serial.println ("    I # - set pin # to INPUT");
            Serial.println ("    O # - set pin # to OUTPUT");
            Serial.println ("    P # - set pin # to INPUT_PULLUP");
            Serial.println ("    a # - analogRead (pin #)");
            Serial.println ("    c # - digitalWrite (pin #, LOW)");
            Serial.println ("    p # -- analogWrite (analogPin, #)");
            Serial.println ("    r # - digitalRead (pin #)");
            Serial.println ("    s   - digitalWrite (pin #, HIGH)");
            Serial.println ("    t   -- toggle pin # output");
            Serial.println ("    v   - print version");
            Serial.println ("    \"   - read string");
            Serial.println ("    ?   - list of commands");
            break;

        default:
            Serial.print ("unknown char ");
            Serial.println (c,HEX);
            break;
        }
    }
}

// -----------------------------------------------------------------------------
void
loop (void)
{
    pcRead ();
}

// -----------------------------------------------------------------------------
void
setup (void)
{
    Serial.begin(115200);

    Serial.println (version);
#if defined(ARDUINO_ARCH_ESP32)
    Serial.println ("esp32");
#endif
}

the following code demonstrates reading a multi-char string which could be compared to a list (as demonstrated). that list can have function pointers to executer when there's a match. capturing a optional argument is a bit more work

int array1[] = {2,3};
int array2[] = {5,6};

struct Array_s {
    const char *name;
    int        *array;
    int         size;
};

Array_s arrays [] = {
    { "array1", array1, sizeof(array1)/sizeof(int) },
    { "array2", array2, sizeof(array2)/sizeof(int) },
};
#define N_ARRAYS    (sizeof(arrays)/sizeof(Array_s))

const char *prompt = "Which array do you want? array1[] or array2.[]";


char line [80];
int  idx = 0;

// -----------------------------------------------------------------------------
void
process (
    char *line )
{
    for (unsigned n = 0; n < N_ARRAYS; n++)  {
        if (! strcmp (arrays [n].name, line))  {
            for (int i = 0; i < arrays [n].size; i++)  {
                Serial.print   (" ");
                Serial.print   (arrays [n].array [i]);
            }
            Serial.println ();
            return;
        }
    }
    Serial.println ("  unknown array name");
}

// -----------------------------------------------------------------------------
void loop() {
    if (Serial.available ()) {
        char c = Serial.read ();
        if ('\n' == c) {
            line [idx] = '\0';
            process (line);
            idx = 0;
            Serial.print (prompt);
        }
        else
            line [idx++] = c;
    }
}

void setup() {
    Serial.begin(9600);
    Serial.print (prompt);
}

cant see where I can use it.
Im not using a single function but a main function to call other sub function

Check out the QueueArray library https://github.com/luceralabs/arduino-libraries/tree/master/QueueArray (or any Queue Library)

As you receive your commands, push them into the Queue. When you receive the last command or otherwise know you are done, start popping commands off the queue and executing them until the queue is empty.

If you design your program properly, you can receive new commands while executing commands.

niceee, thnks

I need more explanation on the coding link youve sent me.

This will demo that library

/*
   example of using a queue
   send:  A,B,C,D
   send:  BAD DAD
*/

#include <QueueArray.h>

// These are user callable actions
enum Cmds { CMD_A, CMD_B, CMD_C, CMD_D };

// create a queue of ints to hold list of states that need to be executed in order
QueueArray <int> cmdQueue;

void setup() {
  Serial.begin(9600);
  delay(500);
  Serial.println("Send a series of A,B,C,D....");

}

void loop() {

  // fetch any input

  while (Serial.available()) {
    int inByte = Serial.read();
    if ( isLowerCase(inByte) ) {
      inByte -= 32;
    }
    switch (inByte) {
      case '?': // help
        Serial.println("Send a series of A,B,C,D....");
        break;

      case 'A': 
        cmdQueue.push( CMD_A );
        break;

      case 'B':
        cmdQueue.push( CMD_B );
        break;

      case 'C':
        cmdQueue.push( CMD_C );
        break;

      case 'D':
        cmdQueue.push( CMD_D );
        break;

      case ' ':
      case ',':
      case '\r':
      case '\n':
        break;

      default:  // unknown command
        Serial.println("Unknown command. Type ? for help" );
    }
  }


  // execute any commands in the queue

  if (cmdQueue.isEmpty() == false) {
    switch ( cmdQueue.pop()) {
      case CMD_A:
        Serial.println("Cmd A executed");
        break;

      case CMD_B:
        Serial.println("Cmd B executed");
        break;

      case CMD_C:
        Serial.println("Cmd C executed");
        break;

      case CMD_D:
        Serial.println("Cmd D executed");
        break;

    }
  }
}

well pcRead is a simple approach that allows commands to be concatenated together. the other code shows how strings can be read and searched for in a table.

i assumed you would see how the two could be combined to do what you want

This topic was automatically closed 120 days after the last reply. New replies are no longer allowed.