cancel
Showing results for 
Search instead for 
Did you mean: 

How to understand if frame buffer has changed with TouchGFX lib

Danix2k
Associate III

Hi,

I have integrated with lwIP and freeRTOS a VNC server on a STM32H757-EVAL.

A VNC client works fine and I can see on it the first frame buffer drawn by the application; according to the VNC standard, the server should send a "new tile" (a square of pixel) to re-draw the frame buffer changed (if something happens and change it - i.e. slider, button clicked, etc..).

Is there any function or method to understand which pixel (or pixelS) has changed (in term of X and Y coordinates) from the previous frame buffer?

In this way, I can recreate a new tile and send it to the VNC client without re-send every time the whole frame buffer using less bandwidth.

Thanks for your help.

Regards.

1 ACCEPTED SOLUTION

Accepted Solutions
MM..1
Chief III

Try breakpoint and check rect

/**
 * This function is called whenever the framework has performed a partial draw.
 *
 * @param rect The area of the screen that has been drawn, expressed in absolute coordinates.
 *
 * @see flushFrameBuffer().
 */
void TouchGFXHAL::flushFrameBuffer(const touchgfx::Rect& rect)
{
    // Calling parent implementation of flushFrameBuffer(const touchgfx::Rect& rect).
    //
    // To overwrite the generated implementation, omit call to parent function
    // and implemented needed functionality here.
    // Please note, HAL::flushFrameBuffer(const touchgfx::Rect& rect) must
    // be called to notify the touchgfx framework that flush has been performed.
 
    TouchGFXGeneratedHAL::flushFrameBuffer(rect);
}
 

View solution in original post

15 REPLIES 15
MM..1
Chief III

In partial framebuffer mode you can simple handle this in handle rectangle target implementation.

For full single or double you can too use target parts of code ...

ktrofimo
Senior III

What VNC server do you use?​

Hi,

in my case I'm using full single buffer for my display.

Do you think that the API for partial frame buffer continue to work even if I set it as REFRESH_STRATEGY_DEFAULT? Because I use a LTDC-DSI display in video mode and I don't need to re-write touchgfxDisplayDriverTransmitActive or touchgfxDisplayDriverTransmitBlock.

I use VNC server from ecos operating System; on the internet you can find VNC server source code and adapt it to FreeRTOS and LWIP.

I am doing actually the same thing (also ecos). Not using any of their drawing ot text functions (thanks to TouchGFX)​, but you just step ahead of me :) I was thinking to extend Invalidate() function because it should contain coordinates of area was drawn, but I not realized this idea yet.

Now I'm trying to understand if I can use API for partial frame buffer strategy (as suggest by @MM..1​ . After that I can check Invalidate function. Let me know if you can try it before I do.

MM..1
Chief III

Try breakpoint and check rect

/**
 * This function is called whenever the framework has performed a partial draw.
 *
 * @param rect The area of the screen that has been drawn, expressed in absolute coordinates.
 *
 * @see flushFrameBuffer().
 */
void TouchGFXHAL::flushFrameBuffer(const touchgfx::Rect& rect)
{
    // Calling parent implementation of flushFrameBuffer(const touchgfx::Rect& rect).
    //
    // To overwrite the generated implementation, omit call to parent function
    // and implemented needed functionality here.
    // Please note, HAL::flushFrameBuffer(const touchgfx::Rect& rect) must
    // be called to notify the touchgfx framework that flush has been performed.
 
    TouchGFXGeneratedHAL::flushFrameBuffer(rect);
}
 

Hi @MM..1​ ,

I was exactly trying this and it works.

I report below the modified code.

void TouchGFXHAL::flushFrameBuffer(const touchgfx::Rect& rect)
{
    // Calling parent implementation of flushFrameBuffer(const touchgfx::Rect& rect).
    //
    // To overwrite the generated implementation, omit call to parent function
    // and implemented needed functionality here.
    // Please note, HAL::flushFrameBuffer(const touchgfx::Rect& rect) must
    // be called to notify the touchgfx framework that flush has been performed.
 
    /* USER CODE BEGIN flushFrameBuffer step 1 */
    TouchGFXGeneratedHAL::flushFrameBuffer(rect);
    extern volatile int tile_updated[NUM_TILES_Y_AXIS][NUM_TILES_X_AXIS];
    extern SemaphoreHandle_t    s_xMutexClientLock;
    extern SemaphoreHandle_t    s_xSemphClientWait;
    extern volatile int update_req;
    
    uint16_t i,j;
    printf("RECT: x=%d, y=%d, width=%d, height=%d\r\n", 
	   rect.x, rect.y, rect.width, rect.height);
    if(s_xSemphClientWait != NULL && s_xMutexClientLock != NULL)
    {
      /* Non-incremental mode - mark the squares that need to be updated */
      for (i = (rect.x)/TILE_SIZE;
	   i <= (rect.x + rect.width)/TILE_SIZE;
	   i++)
      {
	for (j = (rect.y)/TILE_SIZE;
	     j <= (rect.y + rect.height)/TILE_SIZE;
	     j++)
	{
	  tile_updated[j][i] = 1;
	}
      }
      xSemaphoreTake(s_xMutexClientLock, portMAX_DELAY);
      update_req = 1;
      printf("signal da flushFrameBuffer\r\n");
      xSemaphoreGive(s_xMutexClientLock);
      xSemaphoreGive(s_xSemphClientWait);
    }
    /* USER CODE END flushFrameBuffer step 1 */
}

JureL
Associate III

Hi @Danix2k​ and @ktrofimo​,

did you managed to sucessfuly port ecos VNC to freertos+lwip+touchgfx ? Are you willing to share project or source code for it ?

Best regards