Greetings,
I am looking for ways to optimize the performance of the GRAPH_DATA_XY widget for the refresh of the screen for new data on embedded hardware. The vertical refresh is progressively slower the more data is displayed (# of chart graphs, primarily).
I have an STM32F429ZI running with external 32 MB SPANSION SDRAM on an 800x480 LCD. WM_SetCreateFlags(WM_CF_MEMDEV) is set before GUI_Init(). I believe I have triple buffering on now which helped with screen flicker between emWin screens previously.
Example code:
Display All
I am looking for ways to optimize the performance of the GRAPH_DATA_XY widget for the refresh of the screen for new data on embedded hardware. The vertical refresh is progressively slower the more data is displayed (# of chart graphs, primarily).
I have an STM32F429ZI running with external 32 MB SPANSION SDRAM on an 800x480 LCD. WM_SetCreateFlags(WM_CF_MEMDEV) is set before GUI_Init(). I believe I have triple buffering on now which helped with screen flicker between emWin screens previously.
Example code:
C Source Code
- #include "DIALOG.h"
- #include <stdio.h>
- /*********************************************************************
- *
- * Defines
- *
- **********************************************************************
- */
- #define OutputDebugString(x) printf(x)
- #define ID_WINDOW_0 (GUI_ID_USER + 0x00)
- #define ID_GRAPH_0 (GUI_ID_USER + 0x01)
- #define ID_BUTTON_0 (GUI_ID_USER + 0x02)
- #define ID_BUTTON_1 (GUI_ID_USER + 0x03)
- #define Y_SCALE_MAX 113.0 // So that 100 is the highest Y scale bar number displayed
- #define Y_SCALE_MIN 0
- #define VSCROLL_OFFY 10
- #define GY (340)
- #define GRAPH_PIXELS_Y GY // Delta-Y of our chart area
- #define Y_SCALE_FACTOR ((float)(Y_SCALE_MAX-(Y_SCALE_MIN))/GRAPH_PIXELS_Y)
- #define GX (740)
- #define GRAPH_PIXELS_X GX // Widget pixels
- #define GXp (GX - 5) // Usable graph pixels
- #define GXLO 15 // X left offset pixels
- #define GXRO 15 // X rigt offset pixels
- #define ID_BUTTON_0 (GUI_ID_USER + 0x03)
- #define ID_BUTTON_1 (GUI_ID_USER + 0x04)
- #define ID_BUTTON_2 (GUI_ID_USER + 0x05)
- #define ID_TEXT_0 (GUI_ID_USER + 0x23)
- #define ID_GRAPH_0 (GUI_ID_USER + 0x24)
- #define ID_BUTTON_3 (GUI_ID_USER + 0x25)
- #define ID_BUTTON_4 (GUI_ID_USER + 0x27)
- #define PREPOPULATED_DATA_POINTS (MAXSTRIPINDEX/5)
- #define MAX_GRAPHS 10
- /*********************************************************************
- *
- * Static data
- *
- **********************************************************************
- */
- static GRAPH_DATA_Handle _ahData[MAX_GRAPHS]; // Array of handles for the GRAPH_DATA objects
- static GRAPH_SCALE_Handle _hScaleV; // Handle of vertical scale
- static GRAPH_SCALE_Handle _hScaleH; // Handle of horizontal scale
- static GUI_POINT _aPoint[MAX_GRAPHS];
- static I16 _aValue[MAX_GRAPHS];
- static int _Stop = 0;
- // Array of colors for the GRAPH_DATA objects
- static GUI_COLOR _aColor[] = {
- GUI_LIGHTGRAY, GUI_LIGHTGRAY, GUI_LIGHTGRAY, GUI_ORANGE,
- GUI_GREEN, GUI_GREEN, GUI_RED, GUI_RED,
- GUI_LIGHTBLUE, GUI_LIGHTBLUE };
- static U8 _aLineStyles[] = {
- GUI_LS_SOLID, GUI_LS_SOLID, GUI_LS_SOLID, GUI_LS_DASH,
- GUI_LS_SOLID, GUI_LS_DASH, GUI_LS_SOLID, GUI_LS_DASH,
- GUI_LS_SOLID, GUI_LS_DASH };
- /*********************************************************************
- *
- * _aDialogCreate
- */
- static const GUI_WIDGET_CREATE_INFO _aDialogCreate[] = { {
- WINDOW_CreateIndirect, "Window", ID_WINDOW_0, 0, 0, 780, 440, 0, 0x0, 0 }, {
- GRAPH_CreateIndirect, "Graph", ID_GRAPH_0, 20, 80, GX, GY, 0, 0x0, 0 }, {
- BUTTON_CreateIndirect, "Right", ID_BUTTON_0, 760, 80, 20, GY, 0, 0x0, 0 }, {
- BUTTON_CreateIndirect, "Left", ID_BUTTON_1, 0, 80, 20, GY, 0, 0x0, 0 }, };
- /*********************************************************************
- *
- * Static code
- *
- **********************************************************************
- */
- /*********************************************************************
- *
- * _AddValues
- *
- * Function description
- * This routine calculates new random values in dependence of the previous added values
- * and adds them to the GRAPH_DATA objects
- */
- static void _AddValues(void) {
- static unsigned data_time = 0;
- unsigned i = 0;
- GUI_POINT pt;
- pt.x = data_time;
- for (int i = 0; i < MAX_GRAPHS; i++) {
- pt.y = i * 20 + rand() % 50 / Y_SCALE_FACTOR;
- GRAPH_DATA_XY_AddPoint(_ahData[i], &pt);
- }
- data_time++;
- }
- /*********************************************************************
- *
- * _cbDialog
- */
- static void _cbDialog(WM_MESSAGE * pMsg) {
- WM_HWIN hItem;
- WM_HWIN hDlg;
- static GRAPH_DATA_Handle hGraphData;
- int NCode;
- int Id;
- static int DataAttached;
- unsigned i;
- hDlg = pMsg->hWin;
- switch (pMsg->MsgId) {
- case WM_INIT_DIALOG:
- //
- // Initialization of 'Window'
- //
- hItem = pMsg->hWin;
- WINDOW_SetBkColor(hItem, GUI_GRAY);
- //
- // Initialize the GRAPH widget
- //
- hItem = WM_GetDialogItem(pMsg->hWin, ID_GRAPH_0);
- for (i = 0; i < MAX_GRAPHS; i++) {
- _ahData[i] = GRAPH_DATA_XY_Create(_aColor[i], 2000, 0, 0);
- GRAPH_AttachData(hItem, _ahData[i]);
- GRAPH_DATA_XY_SetLineStyle(_ahData[i], _aLineStyles[i]);
- GRAPH_DATA_XY_SetOffY(_ahData[i], 10 / Y_SCALE_FACTOR);
- }
- GRAPH_SetVSizeY(hItem, 120);
- GRAPH_SetGridVis(hItem, 1);
- WIDGET_SetEffect(hItem, &WIDGET_Effect_3D);
- //
- // Create and add vertical scale
- //
- _hScaleV = GRAPH_SCALE_Create(5, GUI_TA_LEFT | GUI_TA_BOTTOM,
- GRAPH_SCALE_CF_VERTICAL, 10 / Y_SCALE_FACTOR);
- GRAPH_SCALE_SetTextColor(_hScaleV, GUI_YELLOW);
- GRAPH_AttachScale(hItem, _hScaleV);
- GRAPH_SetGridDistY(hItem, 10 / Y_SCALE_FACTOR);
- GRAPH_SCALE_SetFactor(_hScaleV, Y_SCALE_FACTOR);
- GRAPH_SCALE_SetOff(_hScaleV,
- -(Y_SCALE_MIN / Y_SCALE_FACTOR) + VSCROLL_OFFY + 5);
- //
- // Create and add horizontal scale
- //
- _hScaleH = GRAPH_SCALE_Create(320, GUI_TA_RIGHT, GRAPH_SCALE_CF_HORIZONTAL,
- 60);
- GRAPH_SCALE_SetTextColor(_hScaleH, GUI_DARKGREEN);
- GRAPH_AttachScale(hItem, _hScaleH);
- GRAPH_SetGridDistX(hItem, 60);
- GRAPH_SCALE_SetTickDist(_hScaleH, 60);
- break;
- case WM_NOTIFY_PARENT:
- Id = WM_GetId(pMsg->hWinSrc);
- NCode = pMsg->Data.v;
- switch (Id) {
- case ID_BUTTON_0: // Notifications sent by 'Right'
- switch (NCode) {
- case WM_NOTIFICATION_CLICKED:
- break;
- case WM_NOTIFICATION_RELEASED:
- break;
- }
- break;
- case ID_BUTTON_1: // Notifications sent by 'Left'
- switch (NCode) {
- case WM_NOTIFICATION_CLICKED:
- break;
- case WM_NOTIFICATION_RELEASED:
- break;
- }
- break;
- }
- break;
- default:
- WM_DefaultProc(pMsg);
- break;
- }
- }
- /*********************************************************************
- *
- * Public code
- *
- **********************************************************************
- */
- /*********************************************************************
- *
- * CreateWindow
- */
- void MainTask(void) {
- WM_HWIN hGraph;
- WM_HWIN hDlg;
- hGraph = 0;
- WM_SetCreateFlags(WM_CF_MEMDEV);
- GUI_Init();
- hDlg = GUI_CreateDialogBox(_aDialogCreate, GUI_COUNTOF(_aDialogCreate),
- _cbDialog, WM_HBKWIN, 0, 0);
- GUI_Delay(50);
- for (int i = 0; i < 20; i++) // PREPOPULATED_DATA_POINTS
- _AddValues();
- while (1) {
- GUI_Delay(500);
- if (!_Stop) {
- if (!hGraph) {
- hGraph = WM_GetDialogItem(hDlg, GUI_ID_GRAPH0);
- }
- _AddValues();
- }
- }
- }
- /*************************** End of file ****************************/