# rts_gui **Repository Path**: RTSystem/rts_gui ## Basic Information - **Project Name**: rts_gui - **Description**: RTS GUI is a lightweight and modular embedded graphics library designed for resource-constrained devices. - **Primary Language**: C - **License**: Not specified - **Default Branch**: master - **Homepage**: None - **GVP Project**: No ## Statistics - **Stars**: 0 - **Forks**: 0 - **Created**: 2025-04-19 - **Last Updated**: 2026-02-03 ## Categories & Tags **Categories**: Uncategorized **Tags**: None ## README # rts_gui A lightweight embedded GUI library written in C, featuring low resource consumption and good portability. ## Key Features * **Core Components**: * `rts_gui.h`/`.c`: Core GUI functions. * `rts_gui_page.h`: Page management. * `rts_gui_label.h`: Label widget. * `rts_gui_rect.h`: Rectangle widget. * `rts_gui_line.h`: Line widget. * `rts_gui_img.h`: Image display. * **Portability**: Provides `rts_gui_port.h` and `rts_gui_port.c` for platform porting. * **Supporting Tools**: * `tools/lcd-image-converter`: Font conversion tool. * `tools/rts_gui_image_converter`: Image conversion tool. * **Third-Party Libraries**: * `thirdParty/rts_zip`: Integrated with the `rts_zip` compression library. * **Examples**: * `test/`: Contains test code and UI examples based on `STM32` and `SDL`. ## Directory Structure ``` . ├── rts_gui/ # Core GUI library files ├── test/ # Test code and examples │ ├── STM32F103/ # Keil project for STM32F103 │ └── SDL/ # Test project for SDL ├── thirdParty/ # Third-party libraries (e.g., rts_zip) └── tools/ # Helper tools (e.g., image converters) ``` ## Getting Started 1. **STM32 Platform**: * Open the Keil project at `test/STM32F103/rts_panel.uvprojx`. * Compile and download to the target board. 2. **PC (SDL) Simulation**: * Set up your CMake or Makefile build environment in the `test/SDL/` directory. * Compile and run the PC simulation program. ## Porting Guide Porting `rts_gui` to a new platform requires implementing a few hardware-specific functions defined in `rts_gui_port.h`. The reference implementation in `test/rts_gui_port.c` provides a clear example for both SDL (PC simulation) and an embedded target (ARM/Keil). Below are the essential functions you must provide in your own `rts_gui_port.c` file. ### 1. Time Source (`rts_gui_get_tick`) The GUI system requires a time source that returns the system uptime in milliseconds. This is critical for animations and internal event handling. **Example:** ```c #if defined(__CC_ARM) // For Keil ARM Compiler // On an embedded system, you can use a global variable updated by a SysTick interrupt. extern uint32_t sys_tick; uint32_t rts_gui_get_tick(void) { return sys_tick; } #else // For PC/SDL simulation #include uint32_t rts_gui_get_tick(void) { return (uint32_t)SDL_GetTicks(); } #endif ``` ### 2. Display Flush (`rts_gui_port_flush`) This is the most important function for rendering. The GUI core prepares a buffer of pixel data and calls this function to send it to the display. Your task is to implement the logic that transfers this data to your screen hardware. **Function Signature:** ```c void rts_gui_port_flush(int16_t x, int16_t y, int16_t width, int16_t height, void *colors); ``` **Implementation Steps:** 1. Set the target drawing window on your display controller using the `x`, `y`, `width`, and `height` parameters. 2. Transfer the pixel data from the `colors` buffer to the screen. This is typically done using DMA for high performance. 3. **Crucially**, once the transfer is complete (e.g., in a DMA transfer-complete interrupt), you **must** call `rts_gui_flush_done()` to notify the GUI core that it can proceed with the next rendering cycle. **Example (for an embedded target like STM32): ```c #include "lcd.h" // Your LCD driver header void rts_gui_port_flush(int16_t x, int16_t y, int16_t width, int16_t height, void *colors) { // This is a blocking implementation example. // For better performance, use DMA and call rts_gui_flush_done() in the interrupt. LCD_ShowPicture(x, y, width, height, colors); rts_gui_flush_done(); // Notify GUI that flushing is complete } ``` ### 3. Configuration (`rts_gui_cfg.h`) Remember to configure `rts_gui/rts_gui_cfg.h` to match your hardware, especially: * `CONFIG_RTS_GUI_SCREEN_WIDTH`: The width of your display. * `CONFIG_RTS_GUI_SCREEN_HEIGHT`: The height of your display. ## Quick Start Example Here is a more accurate example based on the project's design, showing how to create a page object and display a "Hello, rts_gui!" label. First, define your page, including its `init`, `loop`, and `uninit` functions. **`my_page.c`** ```c #include "rts_gui.h" // 1. Declare your UI elements (widgets) static rts_gui_label_t *hello_label; // 2. Define the page initialization function static void page_load(void) { // Initialize the label and attach it to the GUI object tree rts_gui_label_init(&hello_label, NULL, 20, 20, 200, 30, 0xFFFF, "Hello, rts_gui!"); rts_gui_obj_attach((rts_gui_obj_t *)&hello_label); } // 3. Define the page loop function static void page_loop(void) { // This function is called repeatedly while the page is active. // To prevent visual artifacts, it is best practice to modify UI elements // only when the renderer is idle. if(RENDER_STATE_IDLE == rts_gui_render_state()) { // You can safely update UI elements here, for example: // rts_gui_label_set_text(hello_label, "Updated Text!"); // After making changes, start the next rendering cycle. rts_gui_render_start(); } } // 4. Define the page uninitialization function static void page_unload(void) { // Detach all objects to clean up the page rts_gui_obj_detach_all(); } // 5. Create the page description structure const rts_gui_page_t my_first_page = { .load = page_load, .unload = page_unload, .loop = page_loop, }; ``` Then, in your `main` function, initialize the GUI and switch to your newly created page. **`main.c`** ```c #include "rts_gui.h" // Externally reference your page object extern const rts_gui_page_t my_first_page; int main(void) { // 1. Initialize your hardware (display, etc.) // 2. Initialize the GUI system rts_gui_init(); // 3. Set the initial page rts_gui_page_change_to(&my_first_page); // 4. Run the GUI task handler in the main loop while(1) { rts_gui_task_handler(); // A small delay is recommended, e.g., your_delay_ms(5); } return 0; } ```