AnsweredAssumed Answered

Problems loading XBF fonts using STemWin

Question asked by warden.thelast on May 26, 2016
Hi everyone.
We have an STM32F746G-Discovery board and we are now developing a program to our application. As a starting point we have used the demonstration program supplied in the CUBEF7 but we have added some modifications so it fits our needs.
In fact, we need to load XBF fonts from files stored in a MicroSD card using the FatFs and of course running with the freeRTOS. But we have an annoying problem that only appears some times.
So, some times, we read the XBF font from the files in the MicroSD card and we display text in the LCD, with the read font, without problems, but other times (when the problem appears), the text it's not shown.
We are using the API functions supplied in the STemWin, and we are following exactly the examples illustrated to do this, but we have this annoying problem.
After more than three days testing our program, we realized that in the getData function used to read the XBF font file from the microSD card some times appears a problem when we call the function f_lseek (FatFs API function to set the position of the pointer to read/write a file). f_lseek fails.
We have no idea why some times all goes ok and then, suddenly the commented problem appears and all goes wrong.
The code that is running in the GUI_THREAD is the following:
static void GUIThread(void const * argument)
{  
   int salidaAM[100];
 
 
 
   GUI_SetFont(GUI_FONT_20B_1);
   GUI_SetColor((GUI_COLOR)AppGUI::COLOR::LIGHT_BLUE);
 
 
 
   if(!MicroSDStorage::init())
   {
      GUI_DispStringAt("Error al montar la micro SD", 0, 20);
   }
 
 
 
   else GUI_DispStringAt("Micro SD ok", 0, 20);
 
 
 
   if (!SplashScreen::show())               // Visualizacion de la splash screen
   {
      GUI_DispStringAt("Error al mostrar la imagen", 0, 40);
   }
 
 
 
   else GUI_DispStringAt("Imagen ok", 0, 40);
 
 
 
 
   for (int i = 0; i < 100; i++) salidaAM[i] = XBFFontFile::salida[i];
 
 
 
   char buffer[20];
   sprintf(buffer, "ci=%u", XBFFontFile::contadorI);
   GUI_DispStringAt(buffer, 0, 150);
 
 
 
   sprintf(buffer, "cf=%u", XBFFontFile::contadorF);
   GUI_DispStringAt(buffer, 0, 170);
 
 
 
   sprintf(buffer, "nci=%u", XBFFontFile::newContI);
   GUI_DispStringAt(buffer, 0, 190);
 
 
 
   sprintf(buffer, "ncf=%u", XBFFontFile::newContF);
   GUI_DispStringAt(buffer, 0, 210);
 
 
 
  /* Gui background Task */
  while(1) {
    GUI_Exec(); /* Do the background work ... Update windows etc.) */
    osDelay(20); /* Nothing left to do for the moment ... Idle processing */
  }
}
The show() method is the following:
bool SplashScreen::show(void)
{
   GUI_SetBkColor(GUI_WHITE);
   GUI_Clear();
 
   FIL file;
 
   GUI_SetFont(GUI_FONT_20B_1);
   GUI_SetColor((GUI_COLOR)AppGUI::COLOR::LIGHT_BLUE);
 
   GUI_UC_SetEncodeUTF8();
   GUI_UC_EnableBIDI(1);
   GUI_DispStringHCenterAt("Texto España prueba.", LCD_GetXSize() / 2, 20);
 
   GUI_FONT font;
   GUI_XBF_DATA xbfData;
 
   if (f_open(&file, "Arial16.xbf", FA_OPEN_EXISTING | FA_READ) != FR_OK) return false;
 
   if (GUI_XBF_CreateFont(&font, &xbfData, GUI_XBF_TYPE_PROP, XBFFontFile::getData, &file) != 0)
   {
      f_close(&file);
      return false;
   }
 
   GUI_DispStringHCenterAt("Texto españa de prueba", LCD_GetXSize() / 2, 80);
   if (f_close(&file) != FR_OK) return false;
 
   GUI_XBF_DeleteFont(&font);
   GUI_SetFont(GUI_FONT_20B_1);
 
   return true;
}

And the getData function used by the GUI_XBF_CreateFont is the following.
int XBFFontFile::getData(U32 offset, U16 bytesToRead, void* file, void* data)
{
   unsigned int bytesRead;
   contadorI += 1;
 
 
 
   if (f_lseek((FIL*)file, offset) != FR_OK)
   {
      salida[contadorI] = 0;
      return 1;
   }
 
 
 
   if (f_tell((FIL*)file) != offset)
   {
      salida[contadorI] = 1;
      return 1;
   }
 
 
 
   if (f_read((FIL*)file, (U8*)data, bytesToRead, &bytesRead) != FR_OK)
   {
      salida[contadorI] = 2;
      return 1;
   }
 
 
 
   if (bytesRead != bytesToRead)
   {
      salida[contadorI] = 3;
      return 1;
   }
 
 
 
   salida[contadorI] = 4;
   contadorF += 1;
   return 0;
}
We use the contadorI and contadorF to verify if we return from the function without problems (contadorI and contadorF has the same value). If these values are different we check the salida array to view what happens.
 Any advice or suggestion would be apreciated.
Thanks in advance.

Outcomes