cancel
Showing results for 
Search instead for 
Did you mean: 

STemWin on STM32F446ZE and the display driver ST7735 with FlexColor

LHaus
Associate II

Hello,

i tried to get the STM32F446ZE and the STemWin Library running in a Keil Project.

The used OS is emOS from Segger.

I tried to follow you instructions to display "hello world" on the display.

I use the display driver ST7735S which should be supported by the FlexColor driver.

My problem is that instead of "hello world" the display stays white.

I configured GUIConf.h like that 

#define GUI_NUMBYTES 0x8000

In GUI_x I added the following in GUI_X_init() :

void GUI_X_Init(void) {

  UC_ST7735_init();

  USInt current = Sopas_usiGet_IOLink14360ST7735DisplayBacklightCurrent();

  LITA_setDisplayCurrent((uint8_t)current);

  }

In UC_ST7735_init() the SPI-Port gets intiated. This part should work because it ist already used in the same sensor type. The only difference is, that I removed the graphcis library we used before. The addition lines activate the display and it's backlight.

In LCDConf_FlexColor_Template.c I set the resolution like this:

#define XSIZE_PHYS 100 // To be adapted to x-screen size
#define YSIZE_PHYS 40 // To be adapted to y-screen size

I filled the following three methods like that:

(It should be metioned that UC_ST7735_writeSPI4Wire was also used before and should work. It sends one byte after each other instead of 16 bit at once.

I tried to send the high byte and the low byte in different orders.)

static void LcdWriteReg(U16 Data) {
  uint8_t data[2];
  UC_ST7735_dcFLAG_t dcFlag = UC_ST7735_COMMAND;
  data[0] = (uint8_t)UTIL_HLP_LOW_BYTE_OF_INT16(Data);
  data[1] = (uint8_t)UTIL_HLP_HIGH_BYTE_OF_INT16(Data);
  UC_ST7735_writeSPI4Wire(&data[1], 1, dcFlag);
  UC_ST7735_writeSPI4Wire(&data[0], 1, dcFlag);
}
 
static void LcdWriteData(U16 Data) {
  UC_ST7735_dcFLAG_t dcFlag = UC_ST7735_DATA;
  uint8_t data[2];
  data[0] = (uint8_t)UTIL_HLP_LOW_BYTE_OF_INT16(Data);
  data[1] = (uint8_t)UTIL_HLP_HIGH_BYTE_OF_INT16(Data);
  UC_ST7735_writeSPI4Wire(&data[1], 1, dcFlag);
  UC_ST7735_writeSPI4Wire(&data[0], 1, dcFlag);
}
 
static void LcdWriteDataMultiple(U16 * pData, int NumItems) {
  UC_ST7735_dcFLAG_t dcFlag = UC_ST7735_DATA;
  uint8_t data[2];
  int start_size = NumItems;
 
  while (NumItems--) {
    data[0] = (uint8_t)UTIL_HLP_LOW_BYTE_OF_INT16(pData[start_size-NumItems]);
    data[1] = (uint8_t)UTIL_HLP_HIGH_BYTE_OF_INT16(pData[start_size-NumItems]);
    UC_ST7735_writeSPI4Wire(&data[1], 1, dcFlag);
    UC_ST7735_writeSPI4Wire(&data[0], 1, dcFlag);
 }
}

I didn't change the LCD_X_config for the Flexcolor driver

void LCD_X_Config(void) {
  GUI_DEVICE * pDevice;
  CONFIG_FLEXCOLOR Config = {0};
  GUI_PORT_API PortAPI = {0};
  //
  // Set display driver and color conversion
  //
  pDevice = GUI_DEVICE_CreateAndLink(GUIDRV_FLEXCOLOR, GUICC_565, 0, 0);
  //
  // Display driver configuration, required for Lin-driver
  //
  LCD_SetSizeEx (0, XSIZE_PHYS , YSIZE_PHYS);
  LCD_SetVSizeEx(0, VXSIZE_PHYS, VYSIZE_PHYS);
  //
  // Orientation
  //
  Config.Orientation = GUI_SWAP_XY | GUI_MIRROR_Y;
  GUIDRV_FlexColor_Config(pDevice, &Config);
  //
  // Set controller and operation mode
  //
  PortAPI.pfWrite16_A0  = LcdWriteReg;
  PortAPI.pfWrite16_A1  = LcdWriteData;
  PortAPI.pfWriteM16_A1 = LcdWriteDataMultiple;
  PortAPI.pfReadM16_A1  = LcdReadDataMultiple;
  GUIDRV_FlexColor_SetFunc(pDevice, &PortAPI, GUIDRV_FLEXCOLOR_F66708, GUIDRV_FLEXCOLOR_M16C0B16);
}

 The code I run is:

GUI_Init();    
  int xPos, yPos;
  //__HAL_RCC_CRC_CLK_ENABLE();  
    
  xPos = LCD_GetXSize() / 2;
  yPos = LCD_GetYSize() / 3;
  GUI_SetFont(GUI_FONT_COMIC24B_ASCII);
  GUI_DispStringHCenterAt("Hello world!", xPos, yPos);
 
  // Endless loop:
  while(true)
  {
    OS_TASK_Delay(100);
    MW_TWD_arm(); // Arm the watchdog
  }

There is no Compile-Error and the Watch Dog does not cause a problem. 

The problem is that the display stays white. 

I noticed that the command number which the flexchain driver sends over spi does not match the excpeted numbers from the St7735 datasheet.

I debugged the SPI method. The follwing commands and data got sent.

- a command with 0x00 as the high byte

- a command with 0x03 as the low byte. As far I know there is no command number 3 for theSTt7735

- data with 0x00 as the high byte

- data with 0x00 as the low byte

- a command with 0x00 as the high byte

- a command with 0x50 ('P') as the low byte. 

- data with 0x00 as the high byte

- data with 0x00 as the low byte

- a command with 0x00 as the high byte

- a command with 0x51 ('Q') as the low byte. 

- data with 0x00 as the high byte

- data with 0x63 as the low byte

- a command with 0x00 as the high byte

- a command with 0x52 as the low byte. 

- data with 0x00 as the high byte

- data with 0x00 as the low byte

...

- after a while with more alternating commands and data there is just data with 0x00

Did I forget to config something?

Mit freundlichen Grüßen / Best regards

Lukas Hauser

2 REPLIES 2
LHaus
Associate II

​Changing GUIDRV_FLEXCOLOR_F66708​ to GUIDRV_FLEXCOLOR_F667089 helped in order to get the right command numbers for the ST7735 display driver.

Changing GUIDRV_FLEXCOLOR_M16C0B16​ to GUIDRV_FLEXCOLOR_M16C1B8​ doesn't. My device reboots before any SPI communication happens.

I debugged the program to known when The error occurs.

I runs the following methods without crashing but after the last one I didn't see an other name of a method in the disassmbly window of Keil.

emwin_LCD_init

LCD_SETBk_ColorIndex

LCD_set_ClipRectMax

GUI_Alloc_getFixedBlock

GUI_Device_GetpDriver

GUIDRV_Flexcolor_InitOnce

GUI_Alloc_getFixedBlock

LCD_X_DisplayDriver

It get's to the end of LCD_X_DisplayDriver​ but never to LcdWriteReg​, LcdWriteData​, LcdWriteDataMultiple​ or LcdReadDataMultiple​.

What could be the problem? It's hard to debug without having the code.

LHaus
Associate II

Changing the default to this solved my problem:

    // Set controller and operation mode
    //
    PortAPI.pfWrite8_A0 = LcdWriteReg;
    PortAPI.pfWrite8_A1 = LcdWriteData;
    PortAPI.pfWriteM8_A1 = LcdWriteDataMultiple;
//    PortAPI.pfRead8_A1 = LcdReadData;
//    PortAPI.pfReadM8_A1 = LcdReadDataMultiple;