2024-12-11 04:21 AM - edited 2024-12-11 04:35 AM
Hi everyone,
I encountered a challenging issue while using GUIDRV_LIN_OSY_16 with STemWin on an STM32 project. After much debugging, I found a solution and wanted to share it here to help others.
I changed the driver to rotated the display. From GUIDRV_LIN_16 to GUIDRV_LIN_OSY_16.
The problem was related to the framebuffer width (layer_prop[LayerIndex].xSize).
When the display is rotated using GUIDRV_LIN_OSY_16, layer_prop[LayerIndex].xSize is automatically updated from the original 800 (XSIZE_PHYS) to 480.
However, the framebuffer itself does not rotate, meaning its width in memory remains 800 (XSIZE_PHYS).
As a result, using layer_prop[LayerIndex].xSize in calculations caused incorrect framebuffer address computations, leading to drawing errors and background refresh issues.
Solution:
I fixed the issue by replacing layer_prop[LayerIndex].xSize with XSIZE_PHYS in both the framebuffer address calculation and the DMA2D_FillBuffer() call.
Here is the corrected version of my CUSTOM_FillRect() function.
Note:
CUSTOM_FillRect is called in LCD_X_Config via LCD_SetDevFunc.
In addition, the function is called LCD_LL_FillRect in newer STM32Cube packages.
However, the problem still exists here because nothing has changed in this logic.
/*
Note:
CUSTOM_FillRect is called in LCD_X_Config via LCD_SetDevFunc.
In addition, the function is called LCD_LL_FillRect in newer STM32Cube packages.
However, the problem still exists here because nothing has changed in this logic.
*/
static void CUSTOM_FillRect(int32_t LayerIndex, int32_t x0, int32_t y0, int32_t x1,
int32_t y1,uint32_t PixelIndex)
{
uint32_t BufferSize, AddrDst;
int32_t xSize, ySize;
if (GUI_GetDrawMode() == GUI_DM_XOR)
{
LCD_SetDevFunc(LayerIndex, LCD_DEVFUNC_FILLRECT, NULL);
LCD_FillRect(x0, y0, x1, y1);
LCD_SetDevFunc(LayerIndex, LCD_DEVFUNC_FILLRECT, (void(*)(void))CUSTOM_FillRect);
}
else
{
xSize = x1 - x0 + 1;
ySize = y1 - y0 + 1;
BufferSize = GetBufferSize(LayerIndex);
//Old:
// AddrDst = layer_prop[LayerIndex].address +
// BufferSize * layer_prop[LayerIndex].buffer_index +
// y0 * layer_prop[LayerIndex].xSize + x0) * layer_prop[LayerIndex].BytesPerPixel;
//New:
AddrDst = layer_prop[LayerIndex].address +
BufferSize * layer_prop[LayerIndex].buffer_index +
(y0 * XSIZE_PHYS + x0) * layer_prop[LayerIndex].BytesPerPixel;
//Old:
//DMA2D_FillBuffer(LayerIndex, (void *)AddrDst, xSize, ySize, layer_prop[LayerIndex].xSize - xSize, PixelIndex);
//New:
DMA2D_FillBuffer(LayerIndex, (void *)AddrDst, xSize, ySize, XSIZE_PHYS - xSize, PixelIndex);
}
}