Bodmer TFT_eSPI Slider problem

SOLVED !!!
I have solved this problem, so for anyone who lands here with similar problems, please see below
My code is now …

// Trev's Slider experiment
// https://github.com/Bodmer/TFT_eWidget
#include <Arduino.h>
#include <FS.h>
#include <SD.h>
#include <SPI.h>
#include <TFT_eSPI.h>
#include <TFT_eWidget.h>           // Widget library

// Define CS lines stuff
TFT_eSPI tft = TFT_eSPI();
#define TOUCH_CS 5      //CS pin on TFT screen
#define TFT_CS  15      //CS pin on TFT screen
#define SD_CS   22      //CS Pin on SD card reader
uint8_t TFT_Line = 20;

// This is the file name used to store the calibration data
// The SPIFFS file name must start with "/".
#define CALIBRATION_FILE "/TouchCalData2"
// Set REPEAT_CAL to true instead of false to run new calibration
#define REPEAT_CAL false

TFT_eSprite knob = TFT_eSprite(&tft); // Sprite for the slide knob

SliderWidget s1 = SliderWidget(&tft, &knob);    // Slider 1 widget

// TOUCH COORDINATES
uint16_t t_x = 0, t_y = 0;  // To store the touch coordinates

// #########################################################
// ############     CALIBRATE TOUCH SCREEN       ##############
// #########################################################
void touch_calibrate() {
      uint16_t calData[5];
      uint8_t calDataOK = 0;
      // check file system exists
      if (!SPIFFS.begin()) {
            Serial.println("formatting file system");
            SPIFFS.format();
            SPIFFS.begin(); }
            // check if calibration file exists and size is correct 
            if (SPIFFS.exists(CALIBRATION_FILE)) {
                  if (REPEAT_CAL) {
                  // Delete if we want to re-calibrate
                  SPIFFS.remove(CALIBRATION_FILE);
                  } else {
                        File f = SPIFFS.open(CALIBRATION_FILE, "r");
                        if (f) {
                              if (f.readBytes((char *)calData, 14) == 14)
                              calDataOK = 1;
                              f.close();
                 }
           }
      }
// ===================================================
// Touch screen calibration already done and DATA OK ?????
// ===================================================
      if (calDataOK && !REPEAT_CAL) {
            tft.setTouch(calData);   // calibration data valid ???? = EXIT ------
      } else {                       // data not valid so recalibrate ---------------
            tft.fillScreen(TFT_BLACK);
            tft.setCursor(20, 0);
            tft.setTextFont(2);
            tft.setTextSize(1);
            tft.setTextColor(TFT_WHITE, TFT_BLACK);
            tft.println("Touch corners as indicated");
            tft.setTextFont(1);
            tft.println();
            //
            if (REPEAT_CAL) {
              tft.setTextColor(TFT_RED, TFT_BLACK);
              tft.println("Set REPEAT_CAL to false to stop this running again!");
            }
            tft.calibrateTouch(calData, TFT_MAGENTA, TFT_BLACK, 15);
            tft.setTextColor(TFT_GREEN, TFT_BLACK);
            tft.println("Calibration complete!");
            // now store data -----------------------------------------------------------
            File f = SPIFFS.open(CALIBRATION_FILE, "w");
            if (f) {
              f.write((const unsigned char *)calData, 14);
              f.close();
       }
   }
}

// SETUP ##########################################################
void setup() {
      Serial.begin(115200);
      tft.begin();
      tft.setRotation(4);
      tft.fillScreen(TFT_BLACK);
      // Calibrate the touch screen and retrieve the scaling factors
      touch_calibrate();
      // Draw slider
      s1.createSlider(40, 200, TFT_BLUE, TFT_BLACK, V_SLIDER);
      s1.createKnob(60, 20, 5, TFT_WHITE, TFT_RED);
      s1.setSliderScale(200, 0, 2000);
      s1.drawSlider(200, 100);
      s1.setSliderPosition(0);
}

// LOOP ###########################################################
void loop() {
      static uint32_t scanTime = millis();
      t_x = 0, t_y = 0;                               // To store the touch coordinates
      // Scan for touch every 50ms
      if (millis() - scanTime >= 20) {
            // Pressed will be set true if there is a valid touch on the screen
            if( tft.getTouch(&t_x, &t_y, 0) ) {
                  if (s1.checkTouch(t_x, t_y)) {
                  Serial.print("Slider 1 = "); Serial.println(s1.getSliderPosition());
                 }
           }
          scanTime = millis();
    }
}

My PIO.ini is …

; PlatformIO Project Configuration File
; Please visit documentation for the other options and examples
; https://docs.platformio.org/page/projectconf.html
[env:nodemcu-32s]
platform = espressif32
board = nodemcu-32s
framework = arduino
monitor_speed = 115200
lib_deps =
bodmer/TFT_eSPI@^2.5.43
bodmer/TFT_eWidget @ ^0.0.6
SD
lib_ignore = AzureIoTHubMQTTClient //=> this one also has an SD.h file which caused trouble earlier
build_flags =
      -D USER_SETUP_LOADED
      -D ILI9488_DRIVER
      -D TFT_WIDTH=320
      -D TFT_HEIGHT=480
      -D TFT_RST=4
      -D TFT_DC=2
;TFT
      -D TFT_SCLK=18
      -D TFT_MOSI=23
      -D TFT_MISO=19
      -D TFT_CS=15
      ;TOUCH
      -D TOUCH_SCLK=18
      -D TOUCH_DIN=23 ;MOSI
      -D TOUCH_DO=19 ;MISO
      -D TOUCH_CS=5
;SD
      -D SD_SCLK=18
      -D SD_MOSI=23
      -D SD_MISO=19
      -D SD_CS=22
;FONTS
      -D LOAD_GLCD=1
      -D LOAD_FONT2
      -D LOAD_FONT3
      -D LOAD_FONT4
      -D LOAD_FONT6
      -D LOAD_FONT7
      -D LOAD_FONT8
      -D LOAD_GFXFF
      -D SMOOTH_FONT
;SPI Clock
      -D SPI_FREQUENCY=40000000

SOLUTION
The key point is that in Bodmer’s example, the void setup() call to touch_calibrate() was …

void setup()
      tft.begin();
      tft.setRotation(4);
      tft.fillScreen(TFT_BLACK);
      if (REPEAT_CAL) {
        touch_calibrate();
        tft.fillScreen(TFT_BLACK);
      }

So, if REPEAT_CAL is false (= don’t calibrate again), then touch_calibrate() is never ever called, and so the previous calibration data is NEVER retrieved.

My new setup …

void setup()
      tft.begin();
      tft.setRotation(4);
      tft.fillScreen(TFT_BLACK);
      // Calibrate the touch screen and retrieve the scaling factors
      touch_calibrate();

Call tft.setRotation(4) FIRST, before any calibration.
Then touch_calibrate() is called regardless of the state of REPEAT_CAL.
Then in touch_calibrate(), if the REPEAT_CAL is false, it skips a new calibration, to just retrieve the old calibration data.
Trevor

1 Like