Datascope Arduino sketch
This sketch implements a simple serial receive terminal program for monitoring serial debug messages from another board. Connect GND to target board GND Connect RX line to TX line of target board Make sure the target and terminal have the same baud rate and serial stettings! The sketch works with the ILI9341 TFT 240x320 display and the called up libraries. The sketch uses the hardware scrolling feature of the display. Modification of this sketch may lead to problems unless the ILI9341 data sheet has been understood! Written by Vittorio Margherita during February 2015 BSD license applies, all text above must be included in any redistribution In most cases characters don't get lost at 9600 baud but it is a good idea to increase the serial Rx buffer from 64 to 512 or 1024 bytes especially if higher baud rates are used (this sketch does not need much RAM).

                                      
                      #include "Wire.h" 

                      // this is needed even tho we aren't using it
                      #include "Adafruit_STMPE610.h"
                      #include "Adafruit_GFX_AS.h"

                      // Core graphics library
                      #include "Adafruit_ILI9341_AS.h"

                      // Hardware-specific library
                      #include "SPI.h"


                          // These are the pins used for the UNO, we must use hardware SPI

                          #define _sclk 13
                          #define _miso 12 // Not used
                          #define _mosi 11
                          #define _cs 10

                          #define _rst 7
                          #define _dc  9
                          #define BOXSIZE 40

                          //Touch definitions
                          #define STMPE_CS 8
                          #define TS_MINX 150
                          #define TS_MINY 130
                          #define TS_MAXX 3800
                          #define TS_MAXY 4000

                                          


                          // Must use hardware SPI for speed
                          Adafruit_ILI9341_AS tft = Adafruit_ILI9341_AS(_cs, _dc, _rst);
                          Adafruit_STMPE610 ts = Adafruit_STMPE610(STMPE_CS);

                          // The scrolling area must be a integral multiple of TEXT_HEIGHT
                          #define TEXT_HEIGHT 16 // Height of text to be printed and scrolled

                          // Number of lines in bottom fixed area (lines counted from bottom of screen)
                          #define BOT_FIXED_AREA 0 
                          // Number of lines in top fixed area (lines counted from top of screen) was 16
                          #define TOP_FIXED_AREA 16 


                          // The initial y coordinate of the top of the scrolling area
                          uint16_t yStart = TOP_FIXED_AREA + BOXSIZE;
                          // yArea must be a integral multiple of TEXT_HEIGHT
                          uint16_t yArea = 320-(TOP_FIXED_AREA + BOXSIZE) -BOT_FIXED_AREA;
                          // The initial y coordinate of the top of the bottom text line
                          uint16_t yDraw = 320 - BOT_FIXED_AREA - TEXT_HEIGHT;

                          // Keep track of the drawing x coordinate
                          uint16_t xPos = 0;

                          // For the byte we read from the serial port
                          byte data = 0;

                          // A few test varaibles used during debugging
                          boolean change_colour = 1;
                          boolean selected = 1;
                          boolean IsLogStart = 0;     //Menu setting
                          boolean Is9600 = 1;         //Menu setting
                          boolean Retrasmit;

                          //char Buffer[35][10];          //array of strings (requires more space)
                          //int   BufferCurrent = 0;

                          int menu[6] = { 1, 0, 0, 1, 0, 0 };
                          int MovePoint = 0;

                          // We have to blank the top line each time the display is scrolled, 
                          // but this takes up to 13 milliseconds
                          // for a full width line, meanwhile the serial buffer may be filling... and 
                          // overflowing
                          // We can speed up scrolling of short text lines by just blanking the 
                          // character we drew

                          int blank[18]; // We keep all the strings pixel lengths to optimise the 
                                                         // speed of the top line blanking

                          void setup() {
                            // Setup the TFT display
                            tft.init();
                            ts.begin();
                            tft.setRotation(0);
                            tft.fillScreen(ILI9341_BLACK);
                            // Setup scroll area
                            setupScrollArea(TOP_FIXED_AREA + BOXSIZE, BOT_FIXED_AREA);

                            // Setup baud rate and draw top banner
                            Serial.begin(9600);
                            tft.setTextColor(ILI9341_WHITE, ILI9341_BLUE);
                            tft.fillRect(0, 0, 240, 16, ILI9341_BLUE);
                            tft.drawCentreString(" Margherita Datascope - 9600 baud ", 120, 0, 2);

                            // Change colour for scrolling zone
                            tft.setTextColor(ILI9341_WHITE, ILI9341_BLACK);

                            // Zero the array
                            for (byte i = 0; i < 18; i++) blank[i] = 0;

                            // make the Lateral selection buttons
                            tft.fillRect(0, TOP_FIXED_AREA, BOXSIZE, BOXSIZE, ILI9341_RED);
                            tft.fillRect(BOXSIZE , TOP_FIXED_AREA, BOXSIZE, BOXSIZE, ILI9341_YELLOW);
                            tft.fillRect(BOXSIZE * 2 , TOP_FIXED_AREA, BOXSIZE, BOXSIZE, ILI9341_GREEN);
                            tft.fillRect(BOXSIZE * 3 , TOP_FIXED_AREA, BOXSIZE, BOXSIZE, ILI9341_CYAN);
                            tft.fillRect(BOXSIZE * 4 , TOP_FIXED_AREA, BOXSIZE, BOXSIZE, ILI9341_BLUE);
                            tft.fillRect(BOXSIZE * 5 , TOP_FIXED_AREA, BOXSIZE, BOXSIZE, ILI9341_MAGENTA);
                            SetMenu();
                            DrawMenu();

                          }

                          void SetMenu(){

	                          //Set the Empty menu
	                          tft.setTextColor(ILI9341_WHITE, ILI9341_RED);
	                          tft.drawCentreString("9600", (BOXSIZE / 2), (TOP_FIXED_AREA / 2) + (BOXSIZE / 2), 2);
	                          tft.setTextColor(ILI9341_WHITE, ILI9341_YELLOW);
	                          tft.drawCentreString("14400", (BOXSIZE * 2) - (BOXSIZE / 2), (TOP_FIXED_AREA / 2) + (BOXSIZE / 2), 2);
	                          tft.setTextColor(ILI9341_WHITE, ILI9341_GREEN);
	                          tft.drawCentreString("Start", (BOXSIZE * 3) - (BOXSIZE / 2), (TOP_FIXED_AREA / 2) + (BOXSIZE / 2), 2);
	                          tft.setTextColor(ILI9341_WHITE, ILI9341_CYAN);
	                          tft.drawCentreString("Stop", (BOXSIZE * 4) - (BOXSIZE / 2), (TOP_FIXED_AREA / 2) + (BOXSIZE / 2), 2);
	                          tft.setTextColor(ILI9341_WHITE, ILI9341_BLUE);
	                          tft.drawCentreString("Forw", (BOXSIZE * 5) - (BOXSIZE / 2), (TOP_FIXED_AREA / 2) + (BOXSIZE / 2), 2);
	                          tft.setTextColor(ILI9341_WHITE, ILI9341_MAGENTA);
                              tft.drawCentreString("Stay", (BOXSIZE * 6) - (BOXSIZE / 2), (TOP_FIXED_AREA / 2) + (BOXSIZE / 2), 2);
                          }

                          void Raise9600()  {
	                          tft.setTextColor(ILI9341_WHITE, ILI9341_BLACK);
	                          tft.drawCentreString("9600", (BOXSIZE / 2), (TOP_FIXED_AREA / 2) + (BOXSIZE / 2), 2);

	                          //Set the main header
	                          tft.setTextColor(ILI9341_WHITE, ILI9341_BLUE);
	                          tft.fillRect(0, 0, 240, 16, ILI9341_BLUE);
	                          tft.drawCentreString(" Margherita Datascope - 9600 baud ", 120, 0, 2);

                          }

                          void Raise14400()  {
	                          tft.setTextColor(ILI9341_WHITE, ILI9341_BLACK);
	                          tft.drawCentreString("14400", (BOXSIZE * 2) - (BOXSIZE / 2), (TOP_FIXED_AREA / 2) + (BOXSIZE / 2), 2);

	                          //Set the main header
	                          tft.setTextColor(ILI9341_WHITE, ILI9341_BLUE);
	                          tft.fillRect(0, 0, 240, 16, ILI9341_BLUE);
	                          tft.drawCentreString(" Margherita Datascope - 14400 baud ", 120, 0, 2);

                          }
                          void RaiseStart()  {

	                          tft.setTextColor(ILI9341_WHITE, ILI9341_BLACK);
	                          tft.drawCentreString("Start", (BOXSIZE * 3) - (BOXSIZE / 2), (TOP_FIXED_AREA / 2) + (BOXSIZE / 2), 2);


                          }
                          void RaiseStop() {
	                          tft.setTextColor(ILI9341_WHITE, ILI9341_BLACK);
	                          tft.drawCentreString("Stop", (BOXSIZE * 4) - (BOXSIZE / 2), (TOP_FIXED_AREA / 2) + (BOXSIZE / 2), 2);

                          }

                          void RaiseForward() {
	                          tft.setTextColor(ILI9341_WHITE, ILI9341_BLACK);
	                          tft.drawCentreString("Forw", (BOXSIZE * 5) - (BOXSIZE / 2), (TOP_FIXED_AREA / 2) + (BOXSIZE / 2), 2);

                          }

                          void RaiseStay() {
	                          tft.setTextColor(ILI9341_WHITE, ILI9341_BLACK);
	                          tft.drawCentreString("Stay", (BOXSIZE * 6) - (BOXSIZE / 2), (TOP_FIXED_AREA / 2) + (BOXSIZE / 2), 2);

                          }

                          void DrawMenu()  {

	                          if (Is9600 == 1) {
	                          Raise9600();
	                          Serial.end();
	                          Serial.begin(9600);
	                          }
	                          else
	                          {
	                          Raise14400();
	                          Serial.end();
	                          Serial.begin(14400);
	                          }
	                          if (IsLogStart == 1)
	                          RaiseStart();
	                          else
	                          RaiseStop();
	                          if (Retrasmit == 1)
	                          RaiseForward();
	                          else
                              RaiseStay();
                          }

                          void loop(void) {
	                          //  These lines change the text colour when the serial buffer is emptied
	                          //  These are test lines to see if we may be losing characters
	                          //  Also uncomment the change_colour line below to try them
	                          //
	                          //  if (change_colour){
	                          //  change_colour = 0;
	                          //  if (selected == 1) {tft.setTextColor(ILI9341_CYAN, ILI9341_BLACK); selected = 0;}
	                          //  else {tft.setTextColor(ILI9341_MAGENTA, ILI9341_BLACK); selected = 1;}
	                          //}

	                          if (!ts.bufferEmpty()) {

	                            TS_Point p = ts.getPoint();
	                            p.x = map(p.x, TS_MINX, TS_MAXX, 0, tft.width());
	                            p.y = map(p.y, TS_MINY, TS_MAXY, 0, tft.height());
	                            MenuSelection(p);

	                          }

	                          while (Serial.available()) {
	                            //read in any case data from the port (flush)
	                            data = Serial.read();

	                            //check if we reached the end of the buffer (Requires more space on Arduino
	                            //      if (BufferCurrent == 150) BufferCurrent = 0;

	                            //If the user pressed the start button then:
	                          if (IsLogStart == 1)  {
	                            if (data == '\r' || xPos > 231) {
	                                xPos = 0;
	                                yDraw = scroll_line(); // It takes about 13ms to scroll 16 pixel lines

	                            }
	                            if (data > 31 && data < 128) {

	                            //Draw the char at the right position
	                            xPos += tft.drawChar(data, xPos, yDraw, 2);

	                            //If the signal must be retrasmitted
	                            if (Retrasmit == 1)
	                            Serial.write(data);

	                            // Keep a record of line lengths
	                            blank[(17 + (yStart - (TOP_FIXED_AREA + BOXSIZE)) / TEXT_HEIGHT) % 18] = xPos;
	                            }
	                            //change_colour = 1; // Line to indicate buffer is being emptied
                              }
                            } 
                          }

                          void MenuSelection(TS_Point p)
                          {
                            int16_t selection;
                            if (p.y < (BOXSIZE + TOP_FIXED_AREA))  {        //is in the menuBar
                            selection = p.x / BOXSIZE;
                            }

                            SetMenu();

                            switch ((int)selection) {

                            case 0:

	                          Is9600 = 1;
	                          break;
	                          case 1:
	                          Is9600 = 0; //14400
	                          break;
	                          case 2:
	                          IsLogStart = 1;
	                          break;
	                          case 3:
	                          IsLogStart = 0;
	                          break;
	                          case 4:
	                          Retrasmit = 1;
	                          break;
	                          case 5:
	                          Retrasmit = 0;
	                          break;

                            }
                              DrawMenu();

                          }


                          // ##############################################################################################
                          // Call this function to scroll the display one text line
                          // ##############################################################################################
                          int scroll_line() {
	                          int yTemp = yStart; // Store the old yStart, this is where we draw the next line
	                          // Use the record of line lengths to optimise the rectangle size we need to erase the top line
	                          tft.fillRect(0,yStart,blank[(yStart-(TOP_FIXED_AREA + BOXSIZE))/TEXT_HEIGHT],TEXT_HEIGHT, ILI9341_BLACK);

	                          // Change the top of the scroll area
	                          yStart+=TEXT_HEIGHT;
	                          // The value must wrap around as the screen memory is a circular buffer
	                          if (yStart >= 320 - BOT_FIXED_AREA) yStart = (TOP_FIXED_AREA + BOXSIZE) + (yStart - 320 + BOT_FIXED_AREA);
	                          // Now we can scroll the display
	                          scrollAddress(yStart);
	                          return  yTemp;
                          }

                          // ##############################################################################################
                          // Setup a portion of the screen for vertical scrolling
                          // ##############################################################################################
                          // We are using a hardware feature of the display, so we can only scroll in portrait orientation
                          void setupScrollArea(uint16_t TFA, uint16_t BFA) {
	                          tft.writecommand(ILI9341_VSCRDEF); // Vertical scroll definition
	                          tft.writedata(TFA >> 8);
	                          tft.writedata(TFA);
	                          tft.writedata((320-TFA-BFA)>>8);
	                          tft.writedata(320-TFA-BFA);
	                          tft.writedata(BFA >> 8);
	                          tft.writedata(BFA);
	                       }

                          // ##############################################################################################
                          // Setup the vertical scrolling start address
                          // ##############################################################################################
                          void scrollAddress(uint16_t VSP) {
	                          tft.writecommand(ILI9341_VSCRSADD); // Vertical scrolling start address
	                          tft.writedata(VSP>>8);
	                          tft.writedata(VSP);
                          }