Pas d'envoi de données sur broche Tx

Bonjour,
J'utilise deux versions du même programme. La version originale fonctionne bien: les données de la carte microSD sont bien transmises à l'ordinateur(voir description du montage par l'auteur). J'utilise cette version avec un shield TFT tactile et le pilote ILI9341. SD_CS est sur le pin 10.

J'essaie de réaliser le même montage pour un ami mais avec un shield qui utilise ST7783 et la broche 5 pour SD_CS. Si je prends la version originale du programme en modifiant SD_CS, je n'obtiens qu'un écran blanc.
J'ai cherché une modification en partant d'un exemple qui fonctionne avec ce matériel. Le programme fonctionne presque jusqu'au bout sauf qu'à la fin, aucune donnée n'est transmise à l'ordinateur par la broche Tx. L'écran répond à la demande "LOAD" de l'ordinateur en affichant "playing" mais rien ne part.

Première version:


/**************************************************\
*           S D L E P - T F T - 2 0 2 1            * 
*            (c) 2021 - Daniel Coulom              *  
*                                                  *
*              http://dcmoto.free.fr/              *
*           http://forum.system-cfg.com/           *
*                                                  *
*   Credits :                                      *   
*   Andrea Ottaviani :  SDLEP-TFT 2.8"             * 
*   C. Catalanotto...:  SDLEP-TFT+                 *
*                                                  *
*--------------------------------------------------*
* SDLEP TFT 2021 remplace un lecteur de cassettes  *
* pour charger des programmes et des donnees avec  *
* un micro-ordinateur.                             *
* Les cassettes sont remplacees par des fichiers   *
* .lep stockes sur une carte microSD ou microSDHC. *
*--------------------------------------------------*
* Ce code est distribue gratuitement dans l'espoir *
* qu'il sera utile, mais sans aucune  garantie  et *
* sans  engager  la  responsabilite  de  l'auteur. *
* Vous  pouvez  l' utiliser,  le  modifier  et  le *
* diffuser librement, en conservant cette  licence *
* et les references de l'auteur dans   toutes  les *
* copies. L'exploitation commerciale est interdite.*
\**************************************************/

/********************************************************************************\
Un fichier .lep est une image de cassette de données pour ordinateur.
Un octet du fichier .lep contient la durée jusqu'au prochain changement de sens
du signal. Cette durée N est exprimée en nombre de periodes de 50 microsecondes.
Si N est supérieur à 127, l'octet est le reste de N/127 (ou 1 si le reste est 0),
suivi de N/127 octets à zéro. Le signe du premier octet donne le niveau du signal,
positif = niveau haut et negatif = niveau bas.
\********************************************************************************/


/***************************************************
* Wiring instructions                              *
****************************************************

SD Card (if not integrated to TFT shield) :
  o GND --> GND
  o D13 --> SCK
  o D12 --> MISO
  o D11 --> MOSI
  o D10 --> CS 
  o +5V --> VCC

Microcomputer :
  o GND   --> GND
  o +5V   --> +5V
  o MOTOR --> D0
  o READ  --> D1 
   
SDLEP Activity LED :
  o LED+  --> A5 through ~2k resistor
  o LED-  --> GND

*/


/***************************************************
* HISTORY of SDLEP-TFT 2021                              
****************************************************
  
2021.04.28: Read from card directly with SPI
2021.04.27: Minor improvements
2021.04.26: First version adapted from SDLEP-TFT+
*/

/***************************************************
* NOTES                                            
****************************************************

  o The following libraries are used
      . SdFat                version 1.1.4  
      . Adafruit_GFX         version 1.10.7
      . Adafruit TouchScreen version 1.1.1
      . MCUFRIEND_kbv        version 2.9.9
      . FastGPIO             version 2.1.0

*/

#define SDLEP_VERSION  "Version 2021.04.28"
#define SDLEP_URL      "http://dcmoto.free.fr"

#include <SdFat.h>                   // SdFat             
#include <FastGPIO.h>                // Faster GPIO handling
#include <MCUFRIEND_kbv.h>           // TFT display        

// Touchscreen parameters depending on your own setup (some sample files are provided).
#include "TouchScreen.h"             // Touchscreen
//#include "touchscreen-param_7783.h"  // Parametres ecran 7783 
#include "touchscreen-param-2-8-ILI9341.h"  //Paramstres ecran 9341

//#define IGNORE_MOTOR_COMMAND      //Ne pas attendre la télécommande du moteur pour démarrer.

//Cablage
#define SD_CS_PIN             10  // Set the SD chip select line to whatever pin you use (10 doesn't conflict with the library)
#define SDLEP_MOTOR_PIN        0  // Set this to whatever pin you use for MOTOR ON input signal (Generally D0 is used)
#define SDLEP_DATA_PIN         1  // Set this to whatever pin you use for DIGITAL DATA output signal (Generally D1 is used)
#define SDLEP_ACTIVITY_PIN    A5  // Set this to whatever pin you use for SDLEP activity LED (A5 is generally the only one left free)

//Temporisations
#define PERIOD_UNIT           50  // Period unit in µs (50 µs as per LEP file format spec)
#define PROGRESSBAR_DELAY     50  // Define this to compensate progress bar update execution time. Value in us (need code profiling or a scope to obtain this value !). Comment if not needed.
#define BLOCKCHANGE_DELAY     80  // Define this to compensate SD block change execution time. Value in us (need code profiling or a scope to obtain this value !). Comment if not needed.

// Assign human-readable names to some common 16-bit color values:
#define BLACK  0x0000
#define WHITE  0xFFFF
#define GRAY   0x8410
#define RED    0xF800
#define YELLOW 0xFFE0

// Assign human-readable names to custom color values:
#define DARK_GREEN tft.color565(0, 160, 0)
#define DARK_BLUE  tft.color565(0, 0, 224)
#define NAVY_BLUE  tft.color565(0, 0, 128)

// Progress Bar parameters
#define PROGRESSBAR_Y  230
#define PROGRESSBAR_L  300
#define PROGRESSBAR_H    5
#define PROGRESSBAR_X  ((320-PROGRESSBAR_L)/2)
#define PROGRESSBAR_COLOR RED

//MACRO to read one byte from SD card to SPDR register
#define SD_READ_BYTE {SPDR=0xff;while(!(SPSR &(1<<SPIF)));SPSR&=~(1<<SPIF);}

typedef struct  {
  uint8_t     PartType;           // Use this to test whether it is FAT16 or FAT32 or not initialized
  // Stuff from FAT boot sector
  uint8_t     SecPerClus;
  uint16_t    RsvdSecCnt;
  uint8_t     NumFATs;
  uint16_t    RootEntryCount;
  uint32_t    TotalSec;
  uint32_t    SecPerFAT;
  uint32_t    RootClus;
  // For cluster calculations
  uint8_t     ClusterSizeShift;
  uint32_t    ClusterCount;
  // Start addresses (all in blocks / sector addresses)
  uint32_t    BootSectorStart;    // Address of boot sector from FAT
  uint32_t    FatStart;           // First file allocation table starts here
  uint32_t    RootDirStart;       // Root directory starts here
  uint32_t    DataStart;          // Cluster 0 starts here
  uint32_t    ClusterEndMarker;   // if Cluster >= this then end of file reached.
} SD_FAT_t;

//variables globales
MCUFRIEND_kbv tft;
TouchScreen   ts = TouchScreen(XP, YP, XM, YM, OHMS);
SdFat  sd;
SdFile root;
SdFile entry;                     // entree de repertoire
uint32_t selectedfile_size;       // taille du fichier choisi
uint32_t selectedfile_firstblock; // premier bloc du fichier choisi


////////////////////////////////////////////////////////////////////////////////
// PROGRAMME PRINCIPAL
////////////////////////////////////////////////////////////////////////////////
void setup()
{
  uint16_t tft_identifier;                            //code d'identification de l'écran TFT
  
  //Initialisation des broches d'entrees-sorties
  FastGPIO::Pin<SDLEP_DATA_PIN>::setOutputHigh();     //data au niveau haut pour detection du LEP 
  FastGPIO::Pin<SDLEP_ACTIVITY_PIN>::setOutputLow();  //diode d'activité eteinte
  FastGPIO::Pin<SDLEP_MOTOR_PIN>::setInputPulledUp(); //entree moteur au niveau haut (arret) 

  //Initialisation de l'ecran TFT  
  tft.reset();
  tft_identifier = tft.readID(); // lecture de l'identifiant
  tft.begin(0x9341);     // initialisation de l'ecran
  tft.setRotation(1);            // mode paysage
  
  //Affichage du titre
  tft.fillScreen(BLACK);
  tft.fillRect(0,0,320,22,YELLOW);
  tft.setTextSize(2);
  tft.setCursor(35,4); 
  tft.setTextColor(BLACK); tft.print(F("SDLEP "));
  tft.setTextColor(RED); tft.print(F("T"));
  tft.setTextColor(DARK_GREEN); tft.print(F("F"));
  tft.setTextColor(DARK_BLUE); tft.print(F("T"));
  tft.setTextSize(1);
  tft.setTextColor(GRAY);
  tft.setCursor(175,2); tft.print(F(SDLEP_VERSION));
  tft.setCursor(175,13); tft.print(F(SDLEP_URL));

  //Identification de l'ecran  
  tft.setTextColor(WHITE);
  tft.setCursor(16, 40);
  tft.setTextSize(2);
  tft.print(F("TFT identifier = "));
  tft.print(tft_identifier, HEX);
  delay(1000);
  
  // Initialisation de la carte SD 
  while(!sd.begin(SD_CS_PIN))
  {tft.setCursor(16, 68); tft.print(F("SD error. Try RESET."));} 

  // Selection et lecture du fichier
  SelectLepFile();    //selection du fichier .lep
  ReadLepFile();      //lecture du fichier selectionne
}


////////////////////////////////////////////////////////////////////
// Selection du fichier .lep
////////////////////////////////////////////////////////////////////

char* SelectLepFile()
{
  int i; 
  byte numentry;                // numero de l'entree de repertoire
  byte numfiles;                // nombres de fichiers affiches
  boolean dirEnd;               // indicateur de fin de repertoire de la carte SD
  boolean prev;                 // indicateur d'existence d'un ecran precedent
  char suf[10];                 // extension du nom de fichier
  char longfilename[25];        // nom long (tronque) d'un fichier
  char shortfilename[13];       // nom court d'un fichier
  uint32_t file_size[8];        // tailles des fichiers affiches
  uint32_t file_firstblock[8];  // premiers blocs des fichiers affiches
  int selected_line;            // numero de la ligne choisie

  // Affichage boutons FIRST-OK-NEXT
  tft.setTextColor(BLACK);
  tft.fillRect(  0,214,100,22,YELLOW);
  tft.fillRect(110,214,100,22,YELLOW);
  tft.fillRect(220,214,100,22,YELLOW);
  tft.setCursor( 20,218); tft.print(F("FIRST"));
  tft.setCursor(150,218); tft.print(F("OK"));
  tft.setCursor(250,218); tft.print(F("NEXT"));
  tft.setTextColor(WHITE); // ecriture en blanc

  // Initialisations
  dirEnd = false;                 // fin de directory pas atteinte
  prev = false;                   // pas d'ecran precedent
  selectedfile_size = 0;          // initialisation de la taille du fichier choisi
  selectedfile_firstblock = 0;    // initialisation de la taille du fichier choisi

  // Boucle de choix du fichier
  while (1)
  {
    numentry=0;
    numfiles=0;
    selected_line = -1;

    //affichage de huit lignes au maximum
    tft.fillRect(0,23,320,184,NAVY_BLUE);
    while (1)
    {
      if(numfiles > 0)
        entry.close();  //fermer la derniere entree lue
      
      if(numentry >= 8)
        break;         //fin quand 8 lignes sont affichees
      
      //lecture de l'entree suivante du repertoire
      //en fin de repertoire sortir de la boucle
      if(!entry.openNext(sd.vwd(), O_READ))
      {
        entry.close();
        dirEnd=true;
        break;      
      }
      
      numfiles++;
      
      if(entry.isDir())
        continue; //ne pas traiter les sous-repertoires

      //recherche du point dans le nom court du fichier  
      entry.getSFN(shortfilename);
      file_size[numentry] = entry.fileSize();
      file_firstblock[numentry] = entry.firstBlock();
      for(i=0; i<10; i++)
        if (shortfilename[i]=='.')
          break;  //point trouve
      
      if(i==10)
        continue; //point pas trouve, entree de repertoire suivante
   
      //test du suffixe
      suf[0]=shortfilename[i+1];
      suf[1]=shortfilename[i+2];
      suf[2]=shortfilename[i+3];
      suf[3]=0;
      
      if( strcmp(suf,"lep")!=0  && strcmp(suf,"LEP")!=0 )
        continue; //ne pas traiter si ce n'est pas un fichier lep 
   
      //affichage d'un fichier d'extension .lep
      entry.getName(longfilename,24);
      tft.setCursor(35,30+22*numentry);
      tft.print(longfilename);
      tft.drawCircle(15,35+22*numentry,8,WHITE);
      numentry++;
    }
  
    //test de l'action de l'utilisateur
    while (1)
    {
      int x, y;

      //Lire le Touch Screen
      TSPoint p = ts.getPoint();

      //Retablir le sens pour les boches partagees avec l'ecran LCD
      //A3=Chip Select et A2=Command/Data
      FastGPIO::Pin<XM>::setOutput(x);
      FastGPIO::Pin<YP>::setOutput(x);
  
      if ((p.z < MINPRESSURE) || (p.z > MAXPRESSURE))
        continue;

      //calcul des coordonn�es pointees
      //x est defini de la gauche vers la droite de l'affichage   
      //y est defini du haut vers le bas de l'affichage   
      x = map(p.x, TS_MINX, TS_MAXX, 0, tft.width());
      y = map(p.y, TS_MINY, TS_MAXY, 0, tft.height());      
  
      //selection d'un nom de fichier
      if((y > 35) && (y < 205))
      {
        //annuler si necessaire l'ancienne selection
        if(selected_line >= 0)
          tft.fillCircle(15,35+22*(selected_line),5,NAVY_BLUE);        
       
        //nouvelle selection
        selected_line = (y-35)/22;
        if(selected_line >= numentry)
          selected_line = -1;
       
        if(selected_line >= 0)
          tft.fillCircle(15,35+22*(selected_line),5,RED);
      }
  
      // Action boutons
      if(y > 214)               //si appui en bas de l'ecran
      {
        //action du bouton FIRST
        if(x < 115 && prev)  // sur bouton first et s'il y a un ecran precedent
        {
          sd.vwd()->rewind();     //revenir au debut de la carte SD
          dirEnd=false;           //remettre a zero l'indicateur de fin
          prev=false;             //remettre a zero l'indicateur d'ecran precedent 
          break;                  //afficher le premier ecran
        }
  
        //action du bouton OK
        if(x > 114 && x < 215 && selected_line >= 0) // sur bouton OK & fichier choisi
        {
          selectedfile_size = file_size[selected_line];
          selectedfile_firstblock = file_firstblock[selected_line];
          break;
        }
     
        //action du bouton NEXT
        if(x > 214 && !dirEnd)              // sur bouton FIRST & il y a d'autres fichiers
        {
          prev=true;              //positionner indicateur d'ecran precedent 
          break;                  //afficher l'ecran suivant 
        }
      }  
    } //fin du test de l'action de l'utilisateur (on en sort par le break des boutons FIRST, OK et NEXT)
  
    if(selectedfile_size != 0) break; //le fichier a ete choisi par le bouton OK  
  } //fin de la boucle de choix du fichier (on en sort si le fichier a ete choisi)
  
  root.close();  //fermeture du repertoire de la carte SD
}


////////////////////////////////////////////////////////////////////
// Lecture du fichier .lep selectionne
////////////////////////////////////////////////////////////////////
void ReadLepFile()
{
  int       i;                        // Loop counter
  bool      lepOutput;                // Output signal level
  uint16_t  microseconds;             // Period in microseconds
  uint32_t  count;                    // Total byte counter
  uint16_t  progressCountPerStep;
  uint32_t  progressNextStepCount;
  uint16_t  progress;

  //Test du type de carte pour CMD18.
  //Inutile pour readStart(block) car block est toujours le numero de bloc de 512 octets, meme pour une carte non SDHC
  //if(sd.card()->type() != SD_CARD_TYPE_SDHC) selectedfile_firstblock <<= 9;
  
  //Affichage de la taille du fichier
  tft.setTextSize(2);
  tft.setTextColor(BLACK);
  tft.fillRect(0,207,320,33,YELLOW);
  //setLeftStatusText(selectedfile_firstblock);    //premier bloc du fichier
  setLeftStatusText(selectedfile_size);          //taille du fichier
  setRightStatusText(F("Ready."));
  drawProgressBar(0, GRAY);

  lepOutput = HIGH;  // signal a 1 pour detection lep
  FastGPIO::Pin<SDLEP_DATA_PIN>::setOutputValue(lepOutput);
  FastGPIO::Pin<SDLEP_ACTIVITY_PIN>::setOutputValueLow();

  // Initialize progress variables
  progress = PROGRESSBAR_X;
  progressCountPerStep = selectedfile_size / (PROGRESSBAR_L - 2); //arrondi superieur pour ne pas depasser PROGRESSBAR_L
  progressNextStepCount = progressCountPerStep;

  //Start a read multiple blocks sequence  
  count = 0;       // nombre d'octets lus 
  if(!sd.card()->readStart(selectedfile_firstblock))
  {
   setRightStatusText(F("CMD18 Error"));
   return; 
  }

  // Attendre moteur ON (sauf s'il n'y a pas de telecommande du moteur) 
  #ifdef IGNORE_MOTOR_COMMAND
    for(i = 0; i < 100; i++) delayMicroseconds(10000);       
  #else
    while( FastGPIO::Pin<SDLEP_MOTOR_PIN>::isInputHigh() );
  #endif
  
  // Change status text and progess bar color
  setRightStatusText(F("Playing..."));
  drawProgressBar(0, PROGRESSBAR_COLOR);

  noInterrupts();  // desactiver les interruptions

  while(count < selectedfile_size)    // tant qu'il reste des octets
  {
    // attente octet 0xfe de debut de bloc
    SD_READ_BYTE                      //lecture d'un octet de la carte dans le registre SPDR
    while(SPDR != 0xfe) SD_READ_BYTE  //attente octet $FE de debut de bloc

    // Handle each 512-byte block read from SD 
    for(i = 0; i < 512; i++)
    {
     //lecture d'un octet et sortie du signal
     count++;                        // nombre d'octets lus 
     SD_READ_BYTE                    //lecture d'un octet
     microseconds  = abs((char)SPDR);      // initialisation delai
     if(SPDR == 0) microseconds = 127;     // absence de signal (127 unites)
     microseconds *= PERIOD_UNIT;          // conversion en microsecondes
     if(SPDR != 0) lepOutput = (SPDR & 0x80) ? LOW : HIGH; //niveau du signal  
     FastGPIO::Pin<SDLEP_DATA_PIN>::setOutputValue(lepOutput);

     //update progress bar
     if( count >= progressNextStepCount )
     {
      tft.drawFastVLine(progress, PROGRESSBAR_Y, PROGRESSBAR_H, PROGRESSBAR_COLOR);
      progress++;
      progressNextStepCount += progressCountPerStep;
      if( microseconds > PROGRESSBAR_DELAY ) microseconds -= PROGRESSBAR_DELAY;
      else microseconds = 0;
     }

     //Test MOTOR ON
     #ifndef IGNORE_MOTOR_COMMAND
     if( FastGPIO::Pin<SDLEP_MOTOR_PIN>::isInputHigh() )         // si le moteur est arrete   
     {                      
       FastGPIO::Pin<SDLEP_DATA_PIN>::setOutputValueHigh();      // Set LEP DIGITAL OUT high (enable LEP detection)
       setRightStatusText(F("Paused."));                         // Change status text
       drawProgressBar(progress, GRAY);                          // Change progress bar color
       while( FastGPIO::Pin<SDLEP_MOTOR_PIN>::isInputHigh() );   // Wait until motor is back on
       FastGPIO::Pin<SDLEP_DATA_PIN>::setOutputValue(lepOutput); // Restore last LEP DIGITAL OUT level
       setRightStatusText(F("Playing..."));                      // Change status text
       drawProgressBar(progress, PROGRESSBAR_COLOR);             // Change progress bar color
     }
     #endif

     // Compensation du delai de changement de bloc
     if( i == 511 )
     {
      if( microseconds > BLOCKCHANGE_DELAY )  microseconds -= BLOCKCHANGE_DELAY;
      else microseconds = 0;
     }
    
     // Temporisation avant lecture de l'octet suivant
     delayMicroseconds(microseconds);
    }

    //lecture des deux octets de CRC
    SD_READ_BYTE                      //lecture octet CRC1
    SD_READ_BYTE                      //lecture octet CRC2
  
    // Toggle activity LED
    FastGPIO::Pin<SDLEP_ACTIVITY_PIN>::setOutputValueToggle();     
  }
 
  FastGPIO::Pin<SDLEP_ACTIVITY_PIN>::setOutputValueLow(); 
  interrupts();                     //activer les interruptions

  // Change status text and progress bar color
  setRightStatusText(F("Done."));
  drawProgressBar(progress, GRAY);
}


////////////////////////////////////////////////////////////////////
// Status et barre de progression
////////////////////////////////////////////////////////////////////

void setLeftStatusText(uint32_t fileSize)
{
  tft.fillRect(0,207,160,20,YELLOW);
  tft.setCursor(9,209);
  tft.print(fileSize);
  tft.print(F(" bytes"));
}

void setRightStatusText(const __FlashStringHelper *text)
{
  tft.fillRect(160,207,160,20,YELLOW);
  tft.setCursor(169,209);
  tft.print(text);
}

void drawProgressBar(uint16_t progress, uint16_t color)
{
  tft.drawRect(PROGRESSBAR_X - 2, PROGRESSBAR_Y - 2, PROGRESSBAR_L + 4, PROGRESSBAR_H + 4, BLACK);
  if( progress > PROGRESSBAR_X )
  {
    progress -= PROGRESSBAR_X;
    tft.fillRect(PROGRESSBAR_X, PROGRESSBAR_Y, progress, PROGRESSBAR_H, color);
  }
}


////////////////////////////////////////////////////////////////////
// Boucle en fin de cassette
////////////////////////////////////////////////////////////////////
void loop()
{
  //la lecture est arrivee en fin de fichier
  //clignotement lent de la diode d'activite
  FastGPIO::Pin<SDLEP_ACTIVITY_PIN>::setOutputValueHigh();
  delay(100);                   // temporisation
  FastGPIO::Pin<SDLEP_ACTIVITY_PIN>::setOutputValueLow();
  delay(1900);                  // temporisation
}

Version modifiée qui bloque à la fin:

/**************************************************\
*           S D L E P - T F T - 2 0 2 1            * 
*            (c) 2021 - Daniel Coulom              *  
*                                                  *
*              http://dcmoto.free.fr/              *
*           http://forum.system-cfg.com/           *
*                                                  *
*   Credits :                                      *   
*   Andrea Ottaviani :  SDLEP-TFT 2.8"             * 
*   C. Catalanotto...:  SDLEP-TFT+                 *
*                                                  *
*--------------------------------------------------*
* SDLEP TFT 2021 remplace un lecteur de cassettes  *
* pour charger des programmes et des donnees avec  *
* un micro-ordinateur.                             *
* Les cassettes sont remplacees par des fichiers   *
* .lep stockes sur une carte microSD ou microSDHC. *
*--------------------------------------------------*
* Ce code est distribue gratuitement dans l'espoir *
* qu'il sera utile, mais sans aucune  garantie  et *
* sans  engager  la  responsabilite  de  l'auteur. *
* Vous  pouvez  l' utiliser,  le  modifier  et  le *
* diffuser librement, en conservant cette  licence *
* et les references de l'auteur dans   toutes  les *
* copies. L'exploitation commerciale est interdite.*
\**************************************************/

/********************************************************************************\
Un fichier .lep est une image de cassette de données pour ordinateur.
Un octet du fichier .lep contient la durée jusqu'au prochain changement de sens
du signal. Cette durée N est exprimée en nombre de periodes de 50 microsecondes.
Si N est supérieur à 127, l'octet est le reste de N/127 (ou 1 si le reste est 0),
suivi de N/127 octets à zéro. Le signe du premier octet donne le niveau du signal,
positif = niveau haut et negatif = niveau bas.
\********************************************************************************/


/***************************************************
* Wiring instructions                              *
****************************************************

SD Card (if not integrated to TFT shield) :
  o GND --> GND
  o D13 --> SCK
  o D12 --> MISO
  o D11 --> MOSI
  o D10 --> CS 
  o +5V --> VCC

Microcomputer :
  o GND   --> GND
  o +5V   --> +5V
  o MOTOR --> D0
  o READ  --> D1 
   
SDLEP Activity LED :
  o LED+  --> A5 through ~2k resistor
  o LED-  --> GND

*/


/***************************************************
* HISTORY of SDLEP-TFT 2021                              
****************************************************
  
2021.04.28: Read from card directly with SPI
2021.04.27: Minor improvements
2021.04.26: First version adapted from SDLEP-TFT+
*/

/***************************************************
* NOTES                                            
****************************************************

  o The following libraries are used
      . SdFat                version 1.1.4  
      . Adafruit_GFX         version 1.10.7
      . Adafruit TouchScreen version 1.1.1
      . MCUFRIEND_kbv        version 2.9.9
      . FastGPIO             version 2.1.0

*/
#include <SPI.h>
#include <SdFat.h>                   // SdFat             
#include <FastGPIO.h>                // Faster GPIO handling
#include <MCUFRIEND_kbv.h>           // TFT display        

#define SDLEP_URL      "http://dcmoto.free.fr"
#define SDLEP_VERSION  "Version 2021.04.28"     
// Touchscreen parameters depending on your own setup (some sample files are provided).
#include "TouchScreen.h"             // Touchscreen
#include "touchscreen-param_7783-12.h" 
//#include "touchscreen-param_7783d.h"


#if ENABLE_SOFTWARE_SPI_CLASS  // Must be set in SdFat/SdFatConfig.h

// Pin numbers in templates must be constants.
const uint8_t SOFT_MISO_PIN = 12;
const uint8_t SOFT_MOSI_PIN = 11;
const uint8_t SOFT_SCK_PIN  = 13;
//
// Chip select may be constant or RAM variable.
const uint8_t SD_CHIP_SELECT_PIN = 5;

// SdFat software SPI template
SdFatSoftSpi<SOFT_MISO_PIN, SOFT_MOSI_PIN, SOFT_SCK_PIN> sd;

//#define IGNORE_MOTOR_COMMAND      //Ne pas attendre la télécommande du moteur pour démarrer.

//Cablage
#define SD_CHIP_SELECT_PIN     5        // Set the SD chip select line to whatever pin you use (10 doesn't conflict with the library)
#define SDLEP_MOTOR_PIN        0  // Set this to whatever pin you use for MOTOR ON input signal (Generally D0 is used)
#define SDLEP_DATA_PIN         1  // Set this to whatever pin you use for DIGITAL DATA output signal (Generally D1 is used)
#define SDLEP_ACTIVITY_PIN    A5  // Set this to whatever pin you use for SDLEP activity LED (A5 is generally the only one left free)

 
//Temporisations
#define PERIOD_UNIT           50  // Period unit in µs (50 µs as per LEP file format spec)
#define PROGRESSBAR_DELAY     50  // Define this to compensate progress bar update execution time. Value in us (need code profiling or a scope to obtain this value !). Comment if not needed.
#define BLOCKCHANGE_DELAY     80  // Define this to compensate SD block change execution time. Value in us (need code profiling or a scope to obtain this value !). Comment if not needed.

// Assign human-readable names to some common 16-bit color values:
#define BLACK  0x0000
#define WHITE  0xFFFF
#define GRAY   0x8410
#define RED    0xF800
#define YELLOW 0xFFE0

// Assign human-readable names to custom color values:
#define DARK_GREEN tft.color565(0, 160, 0)
#define DARK_BLUE  tft.color565(0, 0, 224)
#define NAVY_BLUE  tft.color565(0, 0, 128)

// Progress Bar parameters
#define PROGRESSBAR_Y  230
#define PROGRESSBAR_L  300
#define PROGRESSBAR_H    5
#define PROGRESSBAR_X  ((320-PROGRESSBAR_L)/2)
#define PROGRESSBAR_COLOR RED

//MACRO to read one byte from SD card to SPDR register
#define SD_READ_BYTE {SPDR=0xff;while(!(SPSR &(1<<SPIF)));SPSR&=~(1<<SPIF);}

typedef struct  {
  uint8_t     PartType;           // Use this to test whether it is FAT16 or FAT32 or not initialized
  // Stuff from FAT boot sector
  uint8_t     SecPerClus;
  uint16_t    RsvdSecCnt;
  uint8_t     NumFATs;
  uint16_t    RootEntryCount;
  uint32_t    TotalSec;
  uint32_t    SecPerFAT;
  uint32_t    RootClus;
  // For cluster calculations
  uint8_t     ClusterSizeShift;
  uint32_t    ClusterCount;
  // Start addresses (all in blocks / sector addresses)
  uint32_t    BootSectorStart;    // Address of boot sector from FAT
  uint32_t    FatStart;           // First file allocation table starts here
  uint32_t    RootDirStart;       // Root directory starts here
  uint32_t    DataStart;          // Cluster 0 starts here
  uint32_t    ClusterEndMarker;   // if Cluster >= this then end of file reached.
} SD_FAT_t;

//variables globales
MCUFRIEND_kbv tft;
TouchScreen   ts = TouchScreen(XP, YP, XM, YM, OHMS);
//SdFat  sd;
SdFile root;
SdFile entry;                     // entree de repertoire
uint32_t selectedfile_size;       // taille du fichier choisi
uint32_t selectedfile_firstblock; // premier bloc du fichier choisi


////////////////////////////////////////////////////////////////////////////////
// PROGRAMME PRINCIPAL
////////////////////////////////////////////////////////////////////////////////
void setup()
{
  uint16_t tft_identifier;                            //code d'identification de l'écran TFT
  
  //Initialisation des broches d'entrees-sorties
  FastGPIO::Pin<SDLEP_DATA_PIN>::setOutputHigh();     //data au niveau haut pour detection du LEP 
  FastGPIO::Pin<SDLEP_ACTIVITY_PIN>::setOutputLow();  //diode d'activité eteinte
  FastGPIO::Pin<SDLEP_MOTOR_PIN>::setInputPulledUp(); //entree moteur au niveau haut (arret) 

  //Initialisation de l'ecran TFT  
  tft.reset();
  tft_identifier = 0x7783; // lecture de l'identifiant
  tft.begin(0x7783);     // initialisation de l'ecran
  tft.setRotation(1);            // mode paysage
  
  //Affichage du titre
  tft.fillScreen(BLACK);
  tft.fillRect(0,0,320,22,YELLOW);
  tft.setTextSize(2);
  tft.setCursor(35,4); 
  tft.setTextColor(BLACK); tft.print(F("SDLEP "));
  tft.setTextColor(RED); tft.print(F("T"));
  tft.setTextColor(DARK_GREEN); tft.print(F("F"));
  tft.setTextColor(DARK_BLUE); tft.print(F("T"));
  tft.setTextSize(1);
  tft.setTextColor(GRAY);
  tft.setCursor(175,2); tft.print(F(SDLEP_VERSION));
  tft.setCursor(175,13); tft.print(F(SDLEP_URL));

  //Identification de l'ecran  
  tft.setTextColor(WHITE);
  tft.setCursor(16, 40);
  tft.setTextSize(2);
  tft.print(F("TFT identifier = "));
  tft.print(tft_identifier, HEX);
  delay(1000);
  
  // Initialisation de la carte SD 
 
  // Initialisation de la carte SD 
  while(!sd.begin(SD_CHIP_SELECT_PIN))
  {tft.setCursor(16, 68); tft.print(F("SD error. Try RESET."));} 

  // Selection et lecture du fichier
  SelectLepFile();    //selection du fichier .lep
  ReadLepFile();      //lecture du fichier selectionne
}

 
///////////////////////////////////////////////////////////////////
// Selection du fichier .lep
////////////////////////////////////////////////////////////////////

char* SelectLepFile()
{
int i; 
  byte numentry;                // numero de l'entree de repertoire
  byte numfiles;                // nombres de fichiers affiches
  boolean dirEnd;               // indicateur de fin de repertoire de la carte SD
  boolean prev;                 // indicateur d'existence d'un ecran precedent
  char suf[10];                 // extension du nom de fichier
  char longfilename[25];        // nom long (tronque) d'un fichier
  char shortfilename[13];       // nom court d'un fichier
  uint32_t file_size[8];        // tailles des fichiers affiches
  uint32_t file_firstblock[8];  // premiers blocs des fichiers affiches
  int selected_line;            // numero de la ligne choisie

  // Affichage boutons FIRST-OK-NEXT
  tft.setTextColor(BLACK);
  tft.fillRect(  0,214,100,22,YELLOW);
  tft.fillRect(110,214,100,22,YELLOW);
  tft.fillRect(220,214,100,22,YELLOW);
  tft.setCursor( 20,218); tft.print(F("FIRST"));
  tft.setCursor(150,218); tft.print(F("OK"));
  tft.setCursor(250,218); tft.print(F("NEXT"));
  tft.setTextColor(WHITE); // ecriture en blanc

  // Initialisations
  dirEnd = false;                 // fin de directory pas atteinte
  prev = false;                   // pas d'ecran precedent
  selectedfile_size = 0;          // initialisation de la taille du fichier choisi
  selectedfile_firstblock = 0;    // initialisation de la taille du fichier choisi

  // Boucle de choix du fichier
  while (1)
  {
    numentry=0;
    numfiles=0;
    selected_line = -1;

    //affichage de huit lignes au maximum
    tft.fillRect(0,23,320,184,NAVY_BLUE);
    while (1)
    {
      if(numfiles > 0)
        entry.close();  //fermer la derniere entree lue
      
      if(numentry >= 8)
        break;         //fin quand 8 lignes sont affichees
      
      //lecture de l'entree suivante du repertoire
      //en fin de repertoire sortir de la boucle
      if(!entry.openNext(sd.vwd(), O_READ))
      {
        entry.close();
        dirEnd=true;
        break;      
      }
      
      numfiles++;
      
      if(entry.isDir())
        continue; //ne pas traiter les sous-repertoires

      //recherche du point dans le nom court du fichier  
      entry.getSFN(shortfilename);
      file_size[numentry] = entry.fileSize();
      file_firstblock[numentry] = entry.firstBlock();
      for(i=0; i<10; i++)
        if (shortfilename[i]=='.')
          break;  //point trouve
      
      if(i==10)
        continue; //point pas trouve, entree de repertoire suivante
   
      //test du suffixe
      suf[0]=shortfilename[i+1];
      suf[1]=shortfilename[i+2];
      suf[2]=shortfilename[i+3];
      suf[3]=0;
      
      if( strcmp(suf,"lep")!=0  && strcmp(suf,"LEP")!=0 )
        continue; //ne pas traiter si ce n'est pas un fichier lep 
   
      //affichage d'un fichier d'extension .lep
      entry.getName(longfilename,24);
      tft.setCursor(35,30+22*numentry);
      tft.print(longfilename);
      tft.drawCircle(15,35+22*numentry,8,WHITE);
      numentry++;
    }
  
    //test de l'action de l'utilisateur
    while (1)
    {
      int x, y;

      //Lire le Touch Screen
      TSPoint p = ts.getPoint();

      //Retablir le sens pour les boches partagees avec l'ecran LCD
      //A3=Chip Select et A2=Command/Data
      FastGPIO::Pin<XM>::setOutput(x);
      FastGPIO::Pin<YP>::setOutput(x);
  
      if ((p.z < MINPRESSURE) || (p.z > MAXPRESSURE))
        continue;

      //calcul des coordonn�es pointees
      //x est defini de la gauche vers la droite de l'affichage   
      //y est defini du haut vers le bas de l'affichage   
      x = map(p.x, TS_MINX, TS_MAXX, 0, tft.width());
      y = map(p.y, TS_MINY, TS_MAXY, 0, tft.height());      
  
      //selection d'un nom de fichier
      if((y > 35) && (y < 205))
      {
        //annuler si necessaire l'ancienne selection
        if(selected_line >= 0)
          tft.fillCircle(15,35+22*(selected_line),5,NAVY_BLUE);        
       
        //nouvelle selection
        selected_line = (y-35)/22;
        if(selected_line >= numentry)
          selected_line = -1;
       
        if(selected_line >= 0)
          tft.fillCircle(15,35+22*(selected_line),5,RED);
      }
  
      // Action boutons
      if(y > 214)               //si appui en bas de l'ecran
      {
        //action du bouton FIRST
        if(x < 115 && prev)  // sur bouton first et s'il y a un ecran precedent
        {
          sd.vwd()->rewind();     //revenir au debut de la carte SD
          dirEnd=false;           //remettre a zero l'indicateur de fin
          prev=false;             //remettre a zero l'indicateur d'ecran precedent 
          break;                  //afficher le premier ecran
        }
  
        //action du bouton OK
        if(x > 114 && x < 215 && selected_line >= 0) // sur bouton OK & fichier choisi
        {
          selectedfile_size = file_size[selected_line];
          selectedfile_firstblock = file_firstblock[selected_line];
          break;
        }
     
        //action du bouton NEXT
        if(x > 214 && !dirEnd)              // sur bouton FIRST & il y a d'autres fichiers
        {
          prev=true;              //positionner indicateur d'ecran precedent 
          break;                  //afficher l'ecran suivant 
        }
      }  
    } //fin du test de l'action de l'utilisateur (on en sort par le break des boutons FIRST, OK et NEXT)
  
    if(selectedfile_size != 0) break; //le fichier a ete choisi par le bouton OK  
  } //fin de la boucle de choix du fichier (on en sort si le fichier a ete choisi)
  
  root.close();  //fermeture du repertoire de la carte SD
}


////////////////////////////////////////////////////////////////////
// Lecture du fichier .lep selectionne
////////////////////////////////////////////////////////////////////
void ReadLepFile()
{
  int       i;                        // Loop counter
  bool      lepOutput;                // Output signal level
  uint16_t  microseconds;             // Period in microseconds
  uint32_t  count;                    // Total byte counter
  uint16_t  progressCountPerStep;
  uint32_t  progressNextStepCount;
  uint16_t  progress;

  //Test du type de carte pour CMD18.
  //Inutile pour readStart(block) car block est toujours le numero de bloc de 512 octets, meme pour une carte non SDHC
  //if(sd.card()->type() != SD_CARD_TYPE_SDHC) selectedfile_firstblock <<= 9;
  
  //Affichage de la taille du fichier
  tft.setTextSize(2);
  tft.setTextColor(BLACK);
  tft.fillRect(0,207,320,33,YELLOW);
  //setLeftStatusText(selectedfile_firstblock);    //premier bloc du fichier
  setLeftStatusText(selectedfile_size);          //taille du fichier
  setRightStatusText(F("Ready."));
  drawProgressBar(0, GRAY);

  lepOutput = HIGH;  // signal a 1 pour detection lep
  FastGPIO::Pin<SDLEP_DATA_PIN>::setOutputValue(lepOutput);
  FastGPIO::Pin<SDLEP_ACTIVITY_PIN>::setOutputValueLow();

  // Initialize progress variables
  progress = PROGRESSBAR_X;
  progressCountPerStep = selectedfile_size / (PROGRESSBAR_L - 2); //arrondi superieur pour ne pas depasser PROGRESSBAR_L
  progressNextStepCount = progressCountPerStep;

  //Start a read multiple blocks sequence  
  count = 0;       // nombre d'octets lus 
  if(!sd.card()->readStart(selectedfile_firstblock))
  {
   setRightStatusText(F("CMD18 Error"));
   return; 
  }

  // Attendre moteur ON (sauf s'il n'y a pas de telecommande du moteur) 
  #ifdef IGNORE_MOTOR_COMMAND
    for(i = 0; i < 100; i++) delayMicroseconds(10000);       
  #else
    while( FastGPIO::Pin<SDLEP_MOTOR_PIN>::isInputHigh() );
  #endif
  
  // Change status text and progess bar color
  setRightStatusText(F("Playing..."));
  drawProgressBar(0, PROGRESSBAR_COLOR);

  noInterrupts();  // desactiver les interruptions

  while(count < selectedfile_size)    // tant qu'il reste des octets
  {
    // attente octet 0xfe de debut de bloc
    SD_READ_BYTE                      //lecture d'un octet de la carte dans le registre SPDR
    while(SPDR != 0xfe) SD_READ_BYTE  //attente octet $FE de debut de bloc

    // Handle each 512-byte block read from SD 
    for(i = 0; i < 512; i++)
    {
     //lecture d'un octet et sortie du signal
     count++;                        // nombre d'octets lus 
     SD_READ_BYTE                    //lecture d'un octet
     microseconds  = abs((char)SPDR);      // initialisation delai
     if(SPDR == 0) microseconds = 127;     // absence de signal (127 unites)
     microseconds *= PERIOD_UNIT;          // conversion en microsecondes
     if(SPDR != 0) lepOutput = (SPDR & 0x80) ? LOW : HIGH; //niveau du signal  
     FastGPIO::Pin<SDLEP_DATA_PIN>::setOutputValue(lepOutput);

     //update progress bar
     if( count >= progressNextStepCount )
     {
      tft.drawFastVLine(progress, PROGRESSBAR_Y, PROGRESSBAR_H, PROGRESSBAR_COLOR);
      progress++;
      progressNextStepCount += progressCountPerStep;
      if( microseconds > PROGRESSBAR_DELAY ) microseconds -= PROGRESSBAR_DELAY;
      else microseconds = 0;
     }

     //Test MOTOR ON
     #ifndef IGNORE_MOTOR_COMMAND
     if( FastGPIO::Pin<SDLEP_MOTOR_PIN>::isInputHigh() )         // si le moteur est arrete   
     {                      
       FastGPIO::Pin<SDLEP_DATA_PIN>::setOutputValueHigh();      // Set LEP DIGITAL OUT high (enable LEP detection)
       setRightStatusText(F("Paused."));                         // Change status text
       drawProgressBar(progress, GRAY);                          // Change progress bar color
       while( FastGPIO::Pin<SDLEP_MOTOR_PIN>::isInputHigh() );   // Wait until motor is back on
       FastGPIO::Pin<SDLEP_DATA_PIN>::setOutputValue(lepOutput); // Restore last LEP DIGITAL OUT level
       setRightStatusText(F("Playing..."));                      // Change status text
       drawProgressBar(progress, PROGRESSBAR_COLOR);             // Change progress bar color
     }
     #endif

     // Compensation du delai de changement de bloc
     if( i == 511 )
     {
      if( microseconds > BLOCKCHANGE_DELAY )  microseconds -= BLOCKCHANGE_DELAY;
      else microseconds = 0;
     }
    
     // Temporisation avant lecture de l'octet suivant
     delayMicroseconds(microseconds);
    }

    //lecture des deux octets de CRC
    SD_READ_BYTE                      //lecture octet CRC1
    SD_READ_BYTE                      //lecture octet CRC2
  
    // Toggle activity LED
    FastGPIO::Pin<SDLEP_ACTIVITY_PIN>::setOutputValueToggle();     
  }
 
  FastGPIO::Pin<SDLEP_ACTIVITY_PIN>::setOutputValueLow(); 
  interrupts();                     //activer les interruptions

  // Change status text and progress bar color
  setRightStatusText(F("Done."));
  drawProgressBar(progress, GRAY);
}


////////////////////////////////////////////////////////////////////
// Status et barre de progression
////////////////////////////////////////////////////////////////////

void setLeftStatusText(uint32_t fileSize)
{
  tft.fillRect(0,207,160,20,YELLOW);
  tft.setCursor(9,209);
  tft.print(fileSize);
  tft.print(F(" bytes"));
}

void setRightStatusText(const __FlashStringHelper *text)
{
  tft.fillRect(160,207,160,20,YELLOW);
  tft.setCursor(169,209);
  tft.print(text);
}

void drawProgressBar(uint16_t progress, uint16_t color)
{
  tft.drawRect(PROGRESSBAR_X - 2, PROGRESSBAR_Y - 2, PROGRESSBAR_L + 4, PROGRESSBAR_H + 4, BLACK);
  if( progress > PROGRESSBAR_X )
  {
    progress -= PROGRESSBAR_X;
    tft.fillRect(PROGRESSBAR_X, PROGRESSBAR_Y, progress, PROGRESSBAR_H, color);
  }
}


////////////////////////////////////////////////////////////////////
// Boucle en fin de cassette
////////////////////////////////////////////////////////////////////

void loop()

{
  //la lecture est arrivee en fin de fichier
  //clignotement lent de la diode d'activite
  FastGPIO::Pin<SDLEP_ACTIVITY_PIN>::setOutputValueHigh();
  delay(100);                   // temporisation
  FastGPIO::Pin<SDLEP_ACTIVITY_PIN>::setOutputValueLow();
  delay(1900);                  // temporisation

}


#else  // ENABLE_SOFTWARE_SPI_CLASS
#error ENABLE_SOFTWARE_SPI_CLASS must be set non-zero in SdFat/SdFatConfig.h
#endif  //ENABLE_SOFTWARE_SPI_CLASS


J'ai modifié SdFat.config selon ce qui est indiqué au début du programme en mettant ENABLE_SOFTWARE_SPI_CLASS à 1 (version 1.1.4 de SdFat)
Je ne vois pas ce qui bloque...En tout avec mes connaissances limitées.

Quel Arduino ?

parlez vous de la broche 1 qui est souvent Tx de l'UART de votre arduino (si on l'active avec un Serial.begin())

PS: vous avez

// Chip select may be constant or RAM variable.
const uint8_t SD_CHIP_SELECT_PIN = 5;

et

#define SD_CHIP_SELECT_PIN 5 // Set the SD chip select line to whatever pin you use (10 doesn't conflict with the library)

Il y a peut-être un conflit au niveau de la pin 5 avec une des bibliothèques utilisées dans le second sketch, mais pas dans le premier ?

Ca me semble la seule différence entre les deux versions, au niveau des bibliothèques. La pin 5 sert pour le tactile ?

C'est un Uno R3. La broche D0 (Rx) reçoit l'ordre de démarrage venant de l'ordinateur, et ça marche comme prévu. La broche D1 (Tx) doit envoyer des données (lecture du contenu des fichiers sur la carte Sd). Mais rien ne sort.
Le fait que SD_CHIP_SELECT_PIN soit déclaré deux fois pourrait-il générer un problème?

Le tactile n'utilise pas la broche 5. Les broches utilisées par le tactile sont A2, A1, 6 et 7 (spécifiées dans le fichier touchscreen-param_7783-12.h)


Selon le descriptif de l'écran, les broches 0,1, 2 et 3 sont libres.

Les broches 0 et 1 sont le port série mais il faut l’activer avec un Serial.begin()

Peut-être une piste dans cet extrait de cours:
Autre subtilité à garder en tête : la broche D10 (Arduino UNO et compatible) ou D53 (Arduino Mega) doit impérativement être configurée en SORTIE. C'est une limitation matérielle. Même si vous n'utilisez pas cette broche, elle doit être en sortie pour que le bus SPI fonctionne.
Sinon, je peux toujours essayer le Serial.begin()

J'ai essayé les deux modifications mais sans plus de résultat. La différence entre les deux programmes c'est que dans le deuxième j'utilise software_spi_class. je pense que le problème vient de là.

si le port série n'est pas configuré, je ne vois pas comment ça fonctionne... mais peut-être qu'il y a un Serial.begin() caché quelque part...

J'ai justement rajouté les deux premières lignes:


  // Initialisation de la carte SD 
  Serial.begin(9600);
  pinMode(10, OUTPUT);
  while(!sd.begin(SD_CHIP_SELECT_PIN))
  {tft.setCursor(16, 68); tft.print(F("SD error. Try RESET."));} 

Il y a quoi réellement de connecté sur les pins 0 et 1 ?

A l'origine, on a un ordinateur des années 80 (Thomson) qui charge ses programmes (jeux ou éducatifs) à partir d'un magnétophone à cassettes. Si on tape "load" sur l'ordinateur, le moteur du magnéto se met en marche, l'ordinateur affiche alors "searching" et il reçoit normalement les données numériques de la cassette. Si les données arrivent bien, il affiche "found nom-du-programme". Puis à la fin "OK" et on lance un "RUN" pour faire tourner le programme.
Le montage réalisé ici remplace le magnétophone à cassettes. Il utilise un Arduino, un écran tactile et un module de carte microSd. Les programmes sont stockés sur la carte Sd. De l'Arduino, on fait partir 3 fils: un ground, un pour Rx et un pour Tx. Ces 3 fils sont soudés à une prise DIN qui se branche sur l'ordinateur Thomson à la place du magnéto-cassette. Donc Rx reçoit le signal de commande et Tx envoie les données du programme enregistré sur la carte Sd.
Sur mon exemplaire qui pose problème, Rx reçoit bien le signal de départ venant de l'ordinateur, l'écran tactile affiche bien "playing" avec une barre de progression pour dire qu'il lit les données mais par contre, l'ordinateur reste à "searching.." et la barre de progression du TFT n'affiche rien. Donc rien ne passe par Tx.
Donc, soit il n'arrive pas à lire les données, soit le passage par Tx est bloqué. J'utilise la même carte microSd et les mêmes fichiers de programmes que sur mon premier exemplaire qui marche bien. Le câblage est strictement le même.

Pourquoi avoir utilisé les pins 0 et 1?
Est-ce que l’usb de l’arduino est branché à un ordinateur ?

Il me semble que j'avais déjà essayé avec 2 et 3. Je peux réessayer éventuellement. J'ai essayé aussi bien avec une alim extérieure de 9V qu'avec l'usb de mon portable.

Disons que 0 et 1 sont liés au port série et donc à l’upload du code

Oui. Avec cette carte, je n'ai pas de problème d'upload donc je pense a priori que les broches 0 et 1 sont fonctionnelles. Peut-être à vérifier quand même avec un autre croquis.
Les auteurs du programme initial ont choisi naturellement Rx et Tx pour recevoir et envoyer des données. Comme dit au début, le programme initial tourne parfaitement avec l'écran qui a SD_CS sur le pin 10.
Je n'arrive pas à le faire tourner du tout avec l'écran qui a SD_CS sur le pin 5. Le croquis original indique dans les commentaires que les données de la carte sont lues directement avec SPI.
C'est pour cette raison que j'ai cherché une modification avec SOFTWARE_SPI_CLASS. J'ai un progrès certain. Ma carte Sd est reconnue, son contenu s'affiche sur le LCD et le touchscreen fonctionne. Par contre les données de la carte ne partent pas.
Je pense que je vais réessayer un croquis qui permet de voir si des fichiers texte enregistrés sur la carte sont bien lus dans le port série.
Il faut que je revérifie aussi si l'upload reste possible avec le shield TFT en place ou s'il faut l'enlever.

Une vue du montage et l'affichage du contenu de la carte avec le dernier fichier sélectionné:

Sinon, en ce qui concerne l'upload avec le TFT en place, ça reste possible mais l'accès à la carte Sd ne fonctionne plus (écran blanc). Il y a sans doute un conflit de broches. Je pense qu'il faut enlever le TFT avant l'upload et le remettre après. C'est ce que j'avais fait la première fois. De toute façon ça ne résout pas le problème de l'envoi des données.

10 est la broche CS hardware. Elle doit rester en OUTPUT même si vous ne l’utilisez pas comme CS.. ce devrait être fait AVANT que SPI soit activé donc au tout début du setup

Je n'arrive à rien avec la version initiale (premier croquis). Il s'arrête à l'affichage du type d'écran et ne donne pas le contenu de la carte même en mettant le pin10 en output au début du setup.
La seconde version avec le soft_spi affiche les fichiers de la carte mais toujours pas de sortie des données. J'ai essayé de les faire sortir sur D2 au lieu de D1 sur les deux versions mais sans résultat.
Il y aurait une solution hardware qui consisterait à câbler le SD_CS de l'écran (actuellement sur le pin 5) sur le pin10 de l'Arduino. Malheureusement l'écran utilise déjà le pin10 pour l'affichage.
Si j'arrivais à afficher le contenu de la carte avec la première version, je pense que ça marcherait pour l'envoi des données.

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