Text editor base?

Simple text input console

Simple text input console, not a text editor.

I like that often help pops up in a small tetx box.

Use commands like:

  • Hello circle rect fill dump quit help show.
  • circle 110
  • fill 0 0 255
  • rect 110

Example Input:

rect
fill 0 0 255
circle

Warm regards,

Chrisir

Sketch:






// ********************************************************************************
//         joined pde-file of folder EditorSimple6
// ********************************************************************************


// ********************************************************************************
// tab: EditorSimple6.pde main file (file name is folder name)




// from https://discourse.processing.org/t/closed-user-types-codes-special-strings-if-correct-something-happends

// A Console.  
// The main program can send to console.
// Use commands like:: Hello circle rect fill dump quit help show. 
// Search for "Add your" here in the code to see where you can add more commands (3 major occurances with ****). 

// The main class 
Console console;

// texts 
MinorTexts minorTexts = new  MinorTexts();

// help text in yellow box
final String helpText = 
  "My little Console \n\n"
  +"Hit PgUp to toggle this help text.\n"
  +"Type text.\n"
  +"Hit enter to go to the next line.\n"
  +"Cursor up to copy previous line.\n"
  +"Use Backspace.\n"
  +"Try to type Hello and dump\n"
  +"Try circle 33 or circle x y r; circle help.\n"
  +"Try rect 33 or rect x y r; rect help.\n"
  +"Try fill/fill help and quit, show, clear.\n"
  +"Esc is disabled; use Alt-F4 instead.";

// help texts for cmds
final String strCircleHelp            = "circle can be used as: circle, circle radius, circle x y, circle x y r or circle x y w h. Example: circle 111.";
final String strRectHelp              = "rect can be used as: rect, rect radius, rect x y, rect x y r or rect x y w h. Example: rect 111.";
final String strFillHelp              = "fill can be used as: fill (just gives blue), fill GRAY-value (0..255), fill Red Green Blue. Example: fill 111.";
final String strQuestionMarkHelp      = "? can be used instead of help: ?fill or ?rect or ? circle"; 
final String strGeneralHelp1          = "Commands are help, quit, dump, show, fill, rect and circle.";
final String strGeneralHelp2          = "With some Commands, use ?rect etc. to get help for the command.";
final String strShowHelp              = "The command 'show' dumps only the internal list with your draw commands.";
final String strClearHelp             = "The command 'clear' clears the internal list with your draw commands.";

// list of commands
ListOfCommands listOfCommands = new ListOfCommands ();

// --------------------------------------------
// Processing Core Functions  

void setup() {
  size(660, 660);
  background(255);

  console = new Console(9, height-130, width-18, 125);
  //  console = new Console(9, height-330, 160, 310);

  console.send("Hello.");
}//setup()

void draw() {
  background(255);

  // show yellow box with help text 
  minorTexts.showHelpText();

  // parse list of commands - draws rects and circles...
  listOfCommands.parseList();

  // show console 
  console.showTextArrayConsole();

  // show error text in red 
  minorTexts.showErrorMessage(); 

  // show help message
  minorTexts.showHelpMessage();
}//draw()
//

// ********************************************************************************
// tab: classConsole.pde


// The core class 

class Console {

  // Pos of box
  float xBoxConsole, yBoxConsole;

  // writing pos inside box
  float xWriteConsole, yWriteConsole;

  // w and h 
  float wConsole, hConsole;

  // space between lines 
  int lineSpaceConsole=22; 

  //font
  PFont fontEditor; 

  // Editor variables 
  String[] lines = new String[300];
  int lineCounter1 = 0; // current line number 
  String lastLine="";      // after hitting Enter 
  String currentLine="";   // before hitting Enter

  // cursor sign blinks 
  boolean cursorBlinkFlag; 
  int timerCursorBlink;

  DateTimeTool dateTimeTool = new DateTimeTool(); 

  // constr 
  Console( float x_, float y_, 
    float w_, float h_) {

    xBoxConsole=x_;
    yBoxConsole=y_;

    xWriteConsole = xBoxConsole+3;
    yWriteConsole = yBoxConsole+20;

    wConsole=w_;
    hConsole=h_;

    fontEditor = createFont("ARIAL", 14);
    textFont(fontEditor); 
    lines[lineCounter1]="";
  }// constr   

  void showTextArrayConsole() {
    // The text field

    // box
    fill(190);     // gray
    stroke(0);     // Black
    rect(xBoxConsole, yBoxConsole, 
      wConsole, hConsole);

    // Text 
    fill(0); // black 
    // for loop 
    int start=lineCounter1- int((hConsole-25) / lineSpaceConsole);
    if (start<0)
      start=0; 
    int stop=lines.length; 
    int lineCounterForLoop=0;
    for (int i=start; i<stop+1; i++) {

      if ((lineCounterForLoop*lineSpaceConsole+yWriteConsole) > hConsole-10+yBoxConsole) {
        break;
      }

      if (lines[i]!=null) {

        text(lines[i], 
          xWriteConsole, lineCounterForLoop*lineSpaceConsole+yWriteConsole);

        showBlinkingCursor(lines[i], i, lineCounterForLoop);
      }//if
      lineCounterForLoop++;
    }//for
    //
  }//func

  // ------------------------------------

  boolean lastLineIs(String line_) {
    // equality 
    return lastLine.equals(line_);
  }// method

  boolean lastLineStartsWith(String line_) {
    // Is the param line_ present at start of last line? Rest of line is ignored
    return lastLine.indexOf(line_) == 0;
  }// method

  boolean isStringAtTheBeginningOfTheCurrentLine(String line_) {

    // This is checking if line_ (e.g. circle) is at the start of the line that is cuurently entered (console.currentLine)

    if (line_==null) 
      return false; 

    int lenLine = line_.length();
    lenLine = min(lenLine, currentLine.length());

    String compare1 = currentLine.substring(0, lenLine); 

    return line_.indexOf(compare1) == 0;
  }//func 

  // ------------------------------------

  void send(String line_) {
    lines[lineCounter1]=line_;
    lineCounter1++; // pitfall ???
    lines[lineCounter1]="";
  }//method

  boolean keyPressedConsole() {
    // eval key 
    // The return value is true for return or false for any other key. 
    boolean result=false; 
    if (key==CODED) {
      //CODED
      result=keyPressedConsoleForCodedKeys();
    } else {
      //not CODED
      result=keyPressedConsoleForNotCodedKeys();
    }
    //
    currentLine = lines[lineCounter1]; 
    return result; 
    //
  } // keyPressedConsole() 

  // ----

  boolean keyPressedConsoleForCodedKeys() {
    // Coded
    // CURSOR KEYS
    if (keyCode==UP) {
      // copy prev line
      if (lineCounter1>0) {
        lines[lineCounter1]=lines[lineCounter1-1];
      }
    } else if (keyCode==DOWN) {
      // ignore
    } else if (keyCode==LEFT) {
      // ignore
    } else if (keyCode==RIGHT) {
      // ignore
    }
    // IGNORE 
    else if (keyCode==ALT) {
      // ignore
    } else if (keyCode==CONTROL) {
      // ignore
    } else if (keyCode==SHIFT) {
      // ignore
    }   
    // IGNORE 
    else {
      // ignore
    } //else

    return false;
  }//func

  boolean keyPressedConsoleForNotCodedKeys() {
    // not Coded
    if ( keyCode == ENTER || keyCode == RETURN ) {
      // new line 
      lastLine=lines[lineCounter1]; 
      lineCounter1++; // pitfall ??? 
      lines[lineCounter1]="";
      currentLine=""; // (it's deleted below as well)
      return true;
    }//if 
    // Backspace and Escape keys
    else if (keyCode==BACKSPACE) {
      lines[lineCounter1] = shortenStringByOneSign(lines[lineCounter1]);
    } else if (key==ESC) {
      key=0; // kill ESC, stay in the program
    }
    // LETTERS - the usual input
    else if (keyCode>0||key=='?') {   // was: else if (keyCode>30||key=='?') {
      // normal text input 
      lines[lineCounter1] += key;
    } else {
      // ignore
    }//else 

    return false;
  }//func 

  // ----

  String shortenStringByOneSign( String strIn_) {
    if (strIn_.length()>0)
      return 
        strIn_.substring( 0, strIn_.length()-1 );
    else 
    return strIn_;
  }

  void showBlinkingCursor(String oneLine, int i, int lineCounterForLoop) {
    // manage and show the red Blinking Cursor |
    // Is it the current/active line?
    if (i==lineCounter1 && cursorBlinkFlag) {
      // show text cursor
      fill(255, 0, 0); // RED 
      text("|", 
        xWriteConsole + textWidth(oneLine), lineCounterForLoop*lineSpaceConsole+yWriteConsole);
      // back to normal
      fill(0);
    }//if

    // timer to toggle the flag cursorBlinkFlag
    if (millis()-timerCursorBlink > 330) {
      cursorBlinkFlag  = !cursorBlinkFlag; // toggle
      timerCursorBlink = millis();
    }//if
  }

  void dump() {
    // dump as file AND as println

    // For the file: get a date-time-stamp
    String dateTimeStampShort = dateTimeTool.dateTimeStampShort(); 
    // make a new array without null
    String[] newArray = arrayWithoutNull(lines); 
    // save array to file
    saveStrings( "result"+dateTimeStampShort+".txt", newArray);

    // Println array - this: printArray( newArray ); wouldn't work as good.  
    for (int i=0; i<newArray.length; i++) {
      println( newArray[i] );
    }//for
  }//method

  String[] arrayWithoutNull(String[] linesLocal) {
    String[] newArray = new String[0]; 
    for (int i=0; i<linesLocal.length; i++) {
      if (linesLocal[i]!=null) {
        newArray = append(newArray, linesLocal[i]);
      }//if
    }//for
    return newArray;
  }//method
  //
}//class
//

// ********************************************************************************
// tab: classDateTime.pde


// minor class to get a date-time-stamp from. 

class DateTimeTool {

  String dateTimeStampShort() {
    // short version 
    return getDate() + "_" + getTime();
  }

  String dateTimeStampLong() {
    // long version 
    return getDateLong()
      + " at " 
      + getTimeLong();
  }

  //-----

  String getTime() {
    return leadingZeros(hour()) 
      + leadingZeros(minute()) 
      + leadingZeros(second());
  }

  String getTimeLong() {
    return leadingZeros(hour()) 
      +":"+ leadingZeros(minute()) 
      +":"+ leadingZeros(second());
  }

  String getDate() {
    return leadingZeros(year()) 
      + leadingZeros(month()) 
      + leadingZeros(day());
  }

  String getDateLong() {
    return leadingZeros(year()) 
      +"/"+ leadingZeros(month()) 
      +"/"+ leadingZeros(day());
  }

  //-----

  String leadingZeros(int a) {
    String Buffer;
    Buffer=nf(a, 2);
    return(Buffer);
  }
  //
}//class
//

// ********************************************************************************
// tab: classListOfCommands.pde


// tab for the list of commands 

class ListOfCommands {

  ArrayList<String> listCmds = new ArrayList();

  void showCmdList() {
    // 
    for (String lineOfTheForLoop : listCmds) {
      println(lineOfTheForLoop);
    }//for

    String remark1="";
    if (listCmds.size()==0)
      remark1=" List is empty at the moment.";
    console.send("List of Commands are dumped in the processing console."
      +remark1);
  }//func 

  void parseList() {
    // parsing the cmd list 

    // *********************************************************************
    // Add your PERSISTENT commands here ***********************************
    // *********************************************************************

    fill(255, 0, 0);  // RED 

    for (String lineOfTheForLoop : listCmds) {

      // 1. circle command 
      if (lineOfTheForLoop.indexOf("circle")==0) {
        String line = lineOfTheForLoop.replace("circle", "");
        line = line.trim();
        // empty?
        if (line.equals("")) {
          // 0 params
          ellipse(width/2, height/2, 33, 33); // default circle
        }//if
        else {
          String[] params = split(line, " "); 
          // Different number of params:  
          if (params.length==3) 
            ellipse(float(params[0]), float(params[1]), float(params[2]), float(params[2]));
          else if (params.length==2) 
            ellipse(float(params[0]), float(params[1]), 33, 33);
          else if (params.length==1) 
            ellipse(width/2, height/2, float(params[0]), float(params[0]));
          else if (params.length==4) 
            ellipse(float(params[0]), float(params[1]), float(params[2]), float(params[3]));
          else {
            minorTexts.errMsg = "Circle command says unknown number of parameters("
              +params.length
              +"): " 
              + lineOfTheForLoop;
          }//else
        }//else
      }//if
      //
      // 2. rect command 
      else if (lineOfTheForLoop.indexOf("rect")==0) {
        String line = lineOfTheForLoop.replace("rect", "");
        line = line.trim();
        // empty?
        if (line.equals("")) {
          // 0 params
          rect(width/2, height/2, 33, 33); // default rect
        }//if
        else {
          String[] params = split(line, " "); 
          // Different number of params:  
          if (params.length==3) 
            rect(float(params[0]), float(params[1]), float(params[2]), float(params[2]));
          else if (params.length==2) 
            rect(float(params[0]), float(params[1]), 33, 33);
          else if (params.length==1) 
            rect(width/2, height/2, float(params[0]), float(params[0]));
          else if (params.length==4) 
            rect(float(params[0]), float(params[1]), float(params[2]), float(params[3]));
          else {
            minorTexts.errMsg = "rect command says unknown number of parameters("
              +params.length
              +"): " 
              + lineOfTheForLoop;
          }//else
        }//else
      }//else if
      //
      // 3. fill command 
      else if (lineOfTheForLoop.indexOf("fill")==0) {
        String line = lineOfTheForLoop.replace("fill", "");
        line = line.trim();
        // empty?
        if (line.equals("")) {
          // 0 params (also valid)
          fill(0, 0, 255); //  default : blue
        }//if
        else {
          String[] params = split(line, " "); 
          // Different number of params:  
          if (params.length==3) 
            fill(int(params[0]), int(params[1]), int(params[2])); // RGB 
          else if (params.length==1) 
            fill(float(params[0])); // GRAY 
          else {
            minorTexts.errMsg = "fill command says unknown number of parameters("
              +params.length
              +"): " 
              + lineOfTheForLoop;
          }//else
        }//else
      }//else if
      // 
      // add more commands here : triangle....
      // 
      else { 
        minorTexts.errMsg = "Unknown command in command list: "+lineOfTheForLoop;
      }//else 
      //
    }//for
    //
  }//func 
  //
}//class
//

// ********************************************************************************
// tab: classMinorTexts.pde


// Minor Tools: Text and messages 

class MinorTexts {

  // yellow box height
  final int heightYellowBox = 234; 

  // show the yellow box yes/ no (PgUp)
  boolean showYellowHelpBoxFlag = true; 

  // when we switch off the yellow box, this text is displayed  
  final String errMsgForShowYellowHelpBoxFlag = "Hit PgUp to toggle the yellow box help text.";

  // error 
  String errMsg="";

  // help 
  String helpMsg=""; 

  void showHelpText() {
    // Yellow box and text

    if (!showYellowHelpBoxFlag) { 
      return; // leave here
    }

    // Yellow box
    fill(#F6FA1C); // Yellow
    stroke(0);     // Black
    rect(width-225, 3, 
      210, heightYellowBox);

    // Black text
    fill(0); // Black
    textSize(12); 
    text(helpText, 
      width-220, 20);
    textSize(14);
  }

  void showErrorMessage() {
    // show error msg
    fill(255, 0, 0); // red
    text(errMsg, 
      console.xBoxConsole+10, console.yBoxConsole-23);
  }

  void showHelpMessage() {
    // show help msg in white

    // when there is no help msg, we leave here 
    if (helpMsg.equals(""))
      return;  // leave here 

    // The box for the help text
    float x = console.xBoxConsole+133; 
    float y = console.yBoxConsole-123; 
    float w = 224; 
    float h = 62;

    // for longer text we can make the box higher 
    if (helpMsg.length()>110) {
      h=82;
    }

    // draw 2 lines as a right angle
    stroke(0);
    // line left <- 
    line(x-1, y+h/2, 
      console.xBoxConsole+4, y+h/2);
    // line down |
    line(console.xBoxConsole+4, y+h/2, 
      console.xBoxConsole+4, console.yBoxConsole-4);

    // draw box
    noFill(); 
    fill(255); 
    rect(x, y, 
      w, h);

    // draw text
    fill( 0); //black
    text(helpMsg, 
      x+4, y+1, 
      w-2, h+10);
  }
  //
}//class
//

// ********************************************************************************
// tab: InputsKeyboard.pde


// Inputs Keyboard 

void keyPressed() {
  // eval key
  // println (keyCode);

  if (keyCode==33) {
    // PG Up
    evalPgUp();
  } //if
  else {
    // eval other keys
    sendKeyToConsole();  // see tab toolsInputs
  }//else
}//keyPressed() 

void evalPgUp() {
  // eval page up

  minorTexts.showYellowHelpBoxFlag = ! minorTexts.showYellowHelpBoxFlag;
  if (!minorTexts.showYellowHelpBoxFlag) {
    minorTexts.errMsg=minorTexts.errMsgForShowYellowHelpBoxFlag;
  }//if
  else {
    if (minorTexts.errMsg.equals(minorTexts.errMsgForShowYellowHelpBoxFlag))
      minorTexts.errMsg="";
  }//else
}
//

// ********************************************************************************
// tab: toolsInputs.pde


// Main Tools ; Inputs. 
// This tab takes inputs and communicates with the console class and executes commands, shows help for the commands during typing etc. 

void sendKeyToConsole() {
  // we send the key to the console.

  // The return value is true for RETURN or false for any other key. 
  if (console.keyPressedConsole()) {
    // return was pressed 
    // eval the last line
    evalTheLastLine();
  } else {
    // Any other key than return was pressed 
    // Show help during typing  
    evalTheCurrentLine();
  }//else
}//sendKeyToConsole() 

// --------------------------------------------

void evalTheLastLine() {
  // Evaluates the last line of the console (after ENTER has been pressed) 

  // reset 
  minorTexts.errMsg="";

  // Delete the help msg (reset) 
  minorTexts.helpMsg="";

  // *********************************************************************
  // Add your commands here **********************************************
  // *********************************************************************

  // We check the last line.
  // We use 
  //      * console.lastLineIs("Hello") for entire line check and 
  //      * console.lastLineStartsWith("circle ") for the beginning of a line (when parameters follow like in circle 120).  
  // 
  // The shorter a command is, the further back in the if..else if.. list it has to be ( console.lastLineStartsWith("circle help") BEFORE console.lastLineStartsWith("circle").
  // Commands like circle that draw on the screen need to be added to the listCmds:  listCmds.add(console.lastLine);   because background is used in draw() and deletes the canvas. 
  // You want to add your commands here and to parseList().
  // 
  if (console.lastLineIs("Hello")||console.lastLineIs("hello")) {
    // Hello 
    console.send("Hello to you, too");
  } else if (console.lastLineIs("show")) {
    // show
    listOfCommands.showCmdList();
  } else if (console.lastLineIs("box")) {
    // 
    console.send("Use rect instead of box please ");
  } else if (console.lastLineIs("clear")) {
    // show
    console.dump();
    listOfCommands.listCmds.clear();
    console.send("I dumped and cleared the draw commands list.");
  } else if (console.lastLineIs("dump")) {
    console.send("I dump the console. (dump as file AND as println)");
    console.dump();
  } else if (console.lastLineIs("help circle")||
    console.lastLineIs("circle help")||
    console.lastLineIs("circle?")||
    console.lastLineIs("?circle")||
    console.lastLineIs("circle ?")||
    console.lastLineIs("? circle")) {
    // we show help for circle 
    console.send(strCircleHelp);
  } else if (console.lastLineIs("help fill")||
    console.lastLineIs("fill help")||
    console.lastLineIs("fill?")||
    console.lastLineIs("?fill")||
    console.lastLineIs("fill ?")||
    console.lastLineIs("? fill")) {
    // we show help for fill 
    console.send(strFillHelp);
  } else if (console.lastLineIs("help rect")||
    console.lastLineIs("rect help")||
    console.lastLineIs("rect?")||
    console.lastLineIs("?rect")||
    console.lastLineIs("rect ?")||
    console.lastLineIs("? rect")) {
    // we show help for rect 
    console.send(strRectHelp);
  } else if (console.lastLineIs("help rect")||
    console.lastLineIs("? help")||
    console.lastLineIs("??")||
    console.lastLineIs("?")||
    console.lastLineIs("? ?")||
    console.lastLineIs("? ?")) {
    // we show help for ?
    console.send(strQuestionMarkHelp);
  }     
  //  
  else if (console.lastLineStartsWith("circle")) {
    // we add this to a list of commands 
    listOfCommands.listCmds.add(console.lastLine);
  }//
  else if (console.lastLineStartsWith("rect")) {
    // we add this to a list of commands 
    listOfCommands.listCmds.add(console.lastLine);
  }//
  else if (console.lastLineStartsWith("fill")) {
    // we add this to a list of commands 
    listOfCommands.listCmds.add(console.lastLine);
  }//
  else if (console.lastLineStartsWith("help")) {
    // 
    // we show help (2 lines) 
    console.send(strGeneralHelp1);
    console.send(strGeneralHelp2);
  }//
  else if (console.lastLineStartsWith("quit")) {
    // 
    console.send("I dump the console. (dump as file AND as println)");
    console.dump();
    exit();
  }//
  else {
    minorTexts.errMsg="Unknown command";
  }
}//evalTheLastLine() 

void evalTheCurrentLine() {
  // eval the line that is typed at the moment (before hitting Enter).
  // eval throughout (not only when Enter has been hit).
  // shows a help for the current word the user is typing. 

  // *********************************************************************
  // Add your help here **********************************************
  // *********************************************************************

  if (console.currentLine.equals("")) {
    minorTexts.helpMsg = "";//reset
  } else if (console.isStringAtTheBeginningOfTheCurrentLine("circle")) {
    minorTexts.helpMsg = strCircleHelp;
  } else if (console.isStringAtTheBeginningOfTheCurrentLine("fill")) {
    minorTexts.helpMsg = strFillHelp;
  } else if (console.isStringAtTheBeginningOfTheCurrentLine("rect")) {
    minorTexts.helpMsg = strRectHelp;
  } else if (console.isStringAtTheBeginningOfTheCurrentLine("show")) {
    minorTexts.helpMsg = strShowHelp;
  } else if (console.isStringAtTheBeginningOfTheCurrentLine("clear")) {
    minorTexts.helpMsg = strClearHelp;
  } else if (console.isStringAtTheBeginningOfTheCurrentLine("help")) {
    // 2 lines 
    minorTexts.helpMsg = strGeneralHelp1
      +"\n"
      +strGeneralHelp2;
  } else if ("?".indexOf(console.currentLine) == 0) {
    minorTexts.helpMsg = strQuestionMarkHelp;
  } 
  // ---
  else {
    minorTexts.helpMsg = ""; // reset
  }//else
}//func 
//

// End of joined file. ********************************************************************************



1 Like