/******************************************************************* File: gui.c Date: 29-September-2025 Author: Peter Spindler Description: Functions to create a simple grafical user interface (gui) ********************************************************************/ #include "stm32f7xx_hal.h" #include "FreeRTOS.h" #include "task.h" #include "queue.h" #include #include "display.h" #include "touch.h" TaskHandle_t GUITaskHandle = NULL; QueueHandle_t GUIQueue; #define BUTTON_MARGIN_X 20 #define BUTTON_MARGIN_Y 22 #define GUI_BUTTONSIZE 16 typedef struct { uint16_t xPos; uint16_t yPos; uint16_t Width; uint16_t Height; char Text[16]; uint8_t Msg; } GUI_BUTTON_TypeDef; static uint8_t GUI_ButtonCnt = 0; static GUI_BUTTON_TypeDef GUI_Button[GUI_BUTTONSIZE]; uint8_t GUI_IsPressed( void ) { if( HAL_GPIO_ReadPin( GPIOC,GPIO_PIN_13 ) == 0 ) { return 1; } else { return 0; } } void GUI_AddButton( uint16_t xPos, uint16_t yPos, char *Text, uint8_t Msg ) { uint8_t i; i = GUI_ButtonCnt; if( i < GUI_BUTTONSIZE ) { GUI_Button[i].xPos = xPos; GUI_Button[i].yPos = yPos; memset(GUI_Button[i].Text, 0, sizeof(GUI_Button[i].Text) ); strncpy(GUI_Button[i].Text, Text, sizeof(GUI_Button[i].Text) ); GUI_Button[i].Msg = Msg; GUI_Button[i].Width = Display_GetStringWidth(&FontBig,Text)+2*BUTTON_MARGIN_X; GUI_Button[i].Height = Display_GetFontCharHeight(&FontBig)+2*BUTTON_MARGIN_Y; GUI_ButtonCnt ++; } } static void GUI_DisplayButton( uint8_t Index, uint8_t State ) { GUI_BUTTON_TypeDef *Button = &GUI_Button[Index]; uint16_t ColorBack; if( State == 0 ) { ColorBack = LCD_COLOR_BLACK; } else { ColorBack = LCD_COLOR_BLUE; } Display_FillRect( Button->xPos,Button->yPos, Button->Width,Button->Height, ColorBack ); Display_DrawRect(Button->xPos,Button->yPos, Button->Width,Button->Height, LCD_COLOR_WHITE ); Display_PrintString( Button->xPos+BUTTON_MARGIN_X, Button->yPos+BUTTON_MARGIN_Y, LCD_COLOR_WHITE,ColorBack, &FontBig, Button->Text); } static void GUI_Task( void *arguments ) { uint8_t TouchState = 0; uint16_t xTouch, yTouch; uint8_t i; uint8_t ButtonPressedIndex=0; uint8_t Msg; uint32_t EventTime; for(i=0;i= GUI_Button[i].xPos && xTouch <= GUI_Button[i].xPos + GUI_Button[i].Width && yTouch >= GUI_Button[i].yPos && yTouch <= GUI_Button[i].yPos + GUI_Button[i].Height ) { ButtonPressedIndex = i; } } if( ButtonPressedIndex != 0xff ) { GUI_DisplayButton(ButtonPressedIndex,1); xQueueSendToBack( GUIQueue, ( void * ) &GUI_Button[ButtonPressedIndex].Msg, ( portTickType ) 0 ); TouchState = 1; EventTime = HAL_GetTick() + 500; } } } else if( TouchState == 1 ) { if( !Touch_IsPressed() ) { if( ButtonPressedIndex != 0xff ) { GUI_DisplayButton(ButtonPressedIndex,0); } TouchState = 0; } else if( HAL_GetTick() > EventTime ) { if( ButtonPressedIndex != 0xff ) { Msg = GUI_Button[ButtonPressedIndex].Msg; // | 0x80; xQueueSendToBack( GUIQueue, ( void * ) &Msg, ( portTickType ) 0 ); } EventTime = HAL_GetTick() + 50; } } } } void GUI_Init( void ) { portENABLE_INTERRUPTS(); // Workaround to re-enable interrupts after FreeRTOS functions Touch_Init(); GUIQueue = xQueueCreate( 10, sizeof( uint8_t) ); xTaskCreate(GUI_Task,"GUI", configMINIMAL_STACK_SIZE,NULL,0,&GUITaskHandle); portENABLE_INTERRUPTS(); // Workaround to re-enable interrupts after FreeRTOS functions }