psychogenic / SerialUI

A Serial User Interface for embedded devices, namely Arduinos.
48 stars 7 forks source link

Feature request - Echo Back chars as they are typed #7

Open marshallbrown123 opened 6 years ago

marshallbrown123 commented 6 years ago

Hi There, Thanks for the efforts in writing this terminal

One small improvement could be to echo back the characters as they are typed at the console (and consume the backspace)

Here's what I put in the readBytesToEOL function

    //only bother echoing if it is from a terminal
    if (mode() == Mode::User){
        //mkb edit - echo back typed char's 
        if ( c == '\r' || c == '\n' ) {
            println("");
            showPrompt();
        }
        else{
            print((char)c);
        }

        //mkb edit (consume backspace)
        if (c == '\b'){
            count--;
            continue;
        }
    }

and here is the entire function for anyone else that may want to cut and paste it.

 size_t SerialUI::readBytesToEOL(char* buffer, size_t max_length, bool left_trim){
// a modified version of readBytesUntil, from Arduino Stream,  LGPLed
// Copyright (c) 2010 David A. Mellis.
size_t count = 0;
unsigned long millistimeout = PLATFORM_NOW_MILLIS() + timeout();
bool infiniteWaitForEOL = (timeout() < 1);
bool isEndline = false;

memset(buffer, 0, max_length); // forced clean

// loop around until we either
//  - get an EOL;
//  - accumulate max_length chars; or
//  - timeout
do {

    if (!this->available()) {
        // nothing in queue, sync & loop
        delegateSynch(true);
        continue;
    }

    // get next char
    int c = read();

    if (c < 0) {
        // sanity check fail
        continue;
    }

    // flag if it's an endline
    if ( c == '\r' || c == '\n' ) {
        isEndline = true;
    } else {
        isEndline = false;
    }

    //mkb edit only bother echoing if it is from a terminal
    if (mode() == Mode::User){
        //mkb edit - echo back typed char's 
        if ( c == '\r' || c == '\n' ) {
            println("");
            showPrompt();
        }
        else{
            print((char)c);
        }

        //mkb edit (consume backspace)
        if (c == '\b'){
            count--;
            continue;
        }
    }

    // if we're left trimming, do so.
    if (left_trim) {

        if (isEndline || c == ' ' || c == '\t') {
            // left trimming and this is whitespace: throw it away
            // and loop
            continue;
        }

        // we were left trimming, but are now done
        left_trim = false;
    }

    if (isEndline || c == read_terminator_char ) {
        // we hit the EOL
        return count;
    }

    // still accumulating, add it to ret buf
    buffer[count++] = (char) c;

} while ( (count < max_length) && (infiniteWaitForEOL || (PLATFORM_NOW_MILLIS() < millistimeout) ));

return count;

}

psychogenic commented 6 years ago

Cool, thanks for the input/info/code.

I'm in the midst of a major rewrite of SerialUI to both modernize it and hopefully reduce it's footprint.

I will try to integrate these mods into the new codebase.

Thanks again! Pat D