cancel
Showing results for 
Search instead for 
Did you mean: 

Problem configuring double framebuffer and 24bpp on STM32F769I-DISCO

MGass.1
Associate II

Good day,

I am currently trying to change the configuration of the STM32F769-DISCO Rev. A from single to double framebuffer. Unfortunately I am not able to get an output without artifacts for animated objects. With static screens there are no really visible problems even if there is some flickering. Especially problematic are objects which are moved with a MoveAnimator or which are distorted with the TextureMapper.

I created my configuration with the Touchgfx-Designer by selecting the STM32F769DISCO. I am using the default DSI display for this board.

If I use a color depth of 16bit with the double framebuffer the configuration works without errors.

Also the configuration with a color depth of 24Bit and Singlebuffer works without problems. But as soon as I try to use 24Bit + Doublebuffer errors occur.

According to support.touchgfx.com/4.18/docs/basic-concepts/framebuffer the size of the framebuffer is 800 * 480 * 24/8 = 1152000.0 which means a start address 1 of 0xC0000000 and start address 2 0xc0119400. To be on the safe side I took 0xC0200000 to have definitely enough space for the buffer.

For the conversion of the project to 24Bpp I made the following changes.

- LTDC Display Type from RGB565 to RGB888

- Layer Settings -> Pixel Format from RGB565 to RGB888

- Software Packs -> TouchGFX -> Frambuffer pixel format to RGB888

- main.c line 628 OTM8009A_Init(OTM8009A_FORMAT_RGB888, LCD_ORIENTATION_LANDSCAPE);

Inside TouchGFXHAL.cpp I made the following changes to get a working result. (Attached below as screenshot).

For the configuration of the double buffer for a DSI display I followed the following post from the forum: community.st.com/s/question/0D53W00001fROnsSAG/enabling-double-framebuffer-on-dsi-displays.

As addresses I used the ones calculated above.

I would be very grateful for any suggestions for improvement and solutions, since I currently have no idea what the problem could be.

If i minimal example project would help you figure out my problem i can upload it later.

9 REPLIES 9
Romain DIELEMAN
ST Employee

Hi,

A minimal example would be nice :grinning_face_with_sweat: so that I/we can try to replicate it.

/Romain

MGass.1
Associate II

Hello,

I have added a minimal example of my configuration with the occurring error to this topic.

MGass.1
Associate II

Hi, i couldnt figure out a solution for this problem in the last week. Does anybody have suggestions what i could try to change in my configuration? I attached a minimal example in my previous post.

Manuel

Osman SOYKURT
ST Employee

Hello MGass.1,

I've looked into your project and it's almost correct except that in TouchGFXHAL.cpp, it's still using the 16bpp "way" of refreshing your screen. In 16 bpp, the screen is splitted in 4 and your refresh 200 pixel at a time, whereas in 24 bpp, it should refresh the 448 pixels.

In the HAL_DSI_TearingEffectCallback() funtion, there's commented code that you need to use instead of what it's currently implemented (because originally designed for 16bpp).

2 things to change :

In HAL_DSI_TearingEffectCallback()

 LCD_SetUpdateRegionLeft();
//LCD_SetUpdateRegion(updateRegion);

In HAL_DSI_EndOfRefreshCallback(), use :

void HAL_DSI_EndOfRefreshCallback(DSI_HandleTypeDef *hdsi)
    {
         if (displayRefreshing)
         {
             if (updateRegion == 0)
             {
                 // If we transferred the left half, also transfer right half.
                 __HAL_DSI_WRAPPER_DISABLE(hdsi);
                 LTDC_LAYER(&hltdc, 0)->CFBAR = ((uint32_t)currFbBase) + 448 * 3;
                 uint16_t ADJUSTED_WIDTH = 384; //64-byte aligned width
                 uint16_t REAL_WIDTH = 384 - 32; //we only actually have this amount of pixels on display
                 LTDC->AWCR = ((ADJUSTED_WIDTH + 2) << 16) | 0x1E2; //adj
                 LTDC->TWCR = ((REAL_WIDTH + 2 + 1 - 1) << 16) | 0x1E3;
                 LTDC_LAYER(&hltdc, 0)->WHPCR = ((REAL_WIDTH + 2) << 16) | 3;
                 LTDC_LAYER(&hltdc, 0)->CFBLR = ((832 * 3) << 16) | ((REAL_WIDTH) * 3 + 3);
                 __HAL_LTDC_RELOAD_IMMEDIATE_CONFIG(&hltdc);
                 LCD_SetUpdateRegionRight(); //Set display column to 448-799
                 __HAL_DSI_WRAPPER_ENABLE(hdsi);
                 updateRegion = 1;
 
                 HAL_DSI_Refresh(hdsi);
             }
             else
             {
                 // Otherwise we are done refreshing.
 
                 __HAL_DSI_WRAPPER_DISABLE(hdsi);
                 LTDC_LAYER(&hltdc, 0)->CFBAR = (uint32_t)currFbBase;
                 uint16_t WIDTH = 448;
                 LTDC->AWCR = ((WIDTH + 2) << 16) | 0x1E2;
                 LTDC->TWCR = ((WIDTH + 2 + 1) << 16) | 0x1E3;
                 LTDC_LAYER(&hltdc, 0)->WHPCR = ((WIDTH + 2) << 16) | 3;
                 LTDC_LAYER(&hltdc, 0)->CFBLR = (((832 * 3) << 16) | ((WIDTH * 3) + 3));
                 __HAL_LTDC_RELOAD_IMMEDIATE_CONFIG(&hltdc);
                 LCD_SetUpdateRegionLeft(); //Set display column to 0-447
                 __HAL_DSI_WRAPPER_ENABLE(hdsi);
                 GPIO::clear(GPIO::VSYNC_FREQ);
 
                 // Turn on display if not already active
                 LCD_ReqEnable();
 
                 displayRefreshing = false;
                 if (HAL::getInstance())
                 {
                     // Signal to the framework that display update has finished.
                     HAL::getInstance()->frontPorchEntered();
                 }
             }
         }
    }

With these changes it should be working fine :)

/Osman

Osman SOYKURT
ST Software Developer | TouchGFX

Hello thanks for answer :)

As adviced i changed the code with your improvements.

The animations look nearly perfect now. The only thing i am noticing is some tearing in the bottom left corner and in the middle in form of a triangle.

This behaviour can better be seen when switching the screen pretty fast. I implemented a testcase in the new version of my minimal example to show this.

Is this another implementation/configuration error or does my display malfunction.

With this posted i also added the updated code and a video of the malfunction.

Updated code here:

Hello,

Great :)

For the "triangle" glitch, we have another thread treating this subject. You could try the workaround suggested there, or, we found another fix ; try with a different value of the scanline in the LCD_ReqTear() function in TouchGFXHAL.cpp :

void LCD_ReqTear(void)
    {
        ...
        uint16_t scanline = 500; // This value should work
        ...
    }

/Osman

Osman SOYKURT
ST Software Developer | TouchGFX

Hello,

i changed the optimization of my project to -Ofast and tried adjusting the scanline value.

The result looks alot better with scanline = 424 but there is still a small triangle in the corner. I also tried 500 as scanline value but the result is worse than at 424. Is there any way to calculate the scanline value or do i have to flash the binary and try to get closer to the perfect value.

Thanks in advance Manuel

Hello,

No apparently it's project specific, can't really calculate that value.

/Osman

Osman SOYKURT
ST Software Developer | TouchGFX