Quellcode durchsuchen

add art-pi spi-LCD port

HelloByeAll vor 5 Jahren
Ursprung
Commit
ea35f73b40
3 geänderte Dateien mit 175 neuen und 28 gelöschten Zeilen
  1. 144 0
      Port/gx_display_driver_art_pi_888rgb_spi.c
  2. 28 27
      Port/gx_system_rtos_bind_rtthread.c
  3. 3 1
      README.md

+ 144 - 0
Port/gx_display_driver_art_pi_888rgb_spi.c

@@ -0,0 +1,144 @@
+/* 
+*	模块名称 : art-pi rgb888显示驱动接口
+*	文件名称 : gx_display_driver_art_pi_888rgb_spi.c
+*	版    本 : V1.0
+*	说    明 : 
+*              
+*	修改记录 :
+*		版本号   日期         作者          说明
+*       V1.0    2020-12-01   HelloByeAll    首版           
+*        
+*
+*/
+
+#include <rtdevice.h>
+#include "lcd_spi_port.h"
+#define DBG_LEVEL DBG_LOG
+#include "rtdbg.h"
+
+#include "gx_api.h"
+#include "gx_system.h"
+#include "gx_display.h"
+#include "gx_utility.h"
+#include "guiapp_resources.h"
+#include "guiapp_specifications.h"
+
+struct drv_lcd_device *lcd;
+rt_uint8_t *Canvas_Memory;
+/*
+*********************************************************************************************************
+*	函 数 名: gx_initconfig
+*	功能说明: GUIX
+*	形    参: 无   	
+*	返 回 值: 无
+*********************************************************************************************************
+*/
+void gx_initconfig(void)
+{
+    extern GX_STUDIO_DISPLAY_INFO guiapp_display_table[1];
+
+    Canvas_Memory = rt_malloc(LCD_WIDTH * LCD_HEIGHT * 4);
+
+    lcd = (struct drv_lcd_device *)rt_device_find("lcd");
+
+    guiapp_display_table[0].canvas_memory = (GX_COLOR *)Canvas_Memory;
+}
+
+static int rgbx8888_to_rgb888(void *psrc, struct rt_device_rect_info *rect_info, void *pdst)
+{
+    int srclinesize = LCD_WIDTH * 4;
+    int dstlinesize = LCD_WIDTH * LCD_BYTES_PER_PIXEL;
+    const rt_uint8_t *psrcline;
+    const rt_uint8_t *psrcdot;
+    rt_uint8_t *pdstline;
+    rt_uint8_t *pdstdot;
+
+    int i, j;
+
+    if (!psrc || !pdst || rect_info->width <= 0 || rect_info->height <= 0)
+    {
+        rt_kprintf("rgbx8888_to_rgb888 : parameter error\n");
+        return -1;
+    }
+
+    psrcline = (rt_uint8_t *)psrc;
+    pdstline = (rt_uint8_t *)pdst;
+
+    for (i = 0; i < rect_info->height; i++)
+    {
+        psrcdot = psrcline;
+        pdstdot = pdstline;
+
+        for (j = 0; j < rect_info->width; j++)
+        {
+            *pdstdot++ = psrcdot[2]; //r
+            *pdstdot++ = psrcdot[1]; //g
+            *pdstdot++ = psrcdot[0]; //b
+            psrcdot += 4;
+        }
+
+        psrcline += srclinesize;
+        pdstline += dstlinesize;
+    }
+
+    return 0;
+}
+
+/*
+*********************************************************************************************************
+*	函 数 名: stm32h7_565rgb_buffer_toggle
+*	功能说明: 更新canvas内容到LCD显存
+*	形    参: 无
+*	返 回 值: 无
+*********************************************************************************************************
+*/
+void art_pi_888rgb_spi_buffer_toggle(GX_CANVAS *canvas, GX_RECTANGLE *dirty)
+{
+    GX_RECTANGLE Limit;
+    GX_RECTANGLE Copy;
+    ULONG offset;
+    INT copy_width;
+    INT copy_height;
+    INT row;
+    INT src_stride_ulongs;
+    INT dest_stride_ulongs;
+
+    ULONG *get = 0;
+    ULONG *put = 0;
+
+    struct rt_device_rect_info rect_info;
+
+    gx_utility_rectangle_define(&Limit, 0, 0,
+                                canvas->gx_canvas_x_resolution - 1,
+                                canvas->gx_canvas_y_resolution - 1);
+
+    if (gx_utility_rectangle_overlap_detect(&Limit, &canvas->gx_canvas_dirty_area, &Copy))
+    {
+        Copy.gx_rectangle_left &= 0xfffe;
+        Copy.gx_rectangle_right |= 0x01;
+        copy_width = Copy.gx_rectangle_right - Copy.gx_rectangle_left + 1;
+        copy_height = Copy.gx_rectangle_bottom - Copy.gx_rectangle_top + 1;
+
+        /* 从canvas读取更新区 */
+        offset = Copy.gx_rectangle_top * canvas->gx_canvas_x_resolution;
+        offset += Copy.gx_rectangle_left;
+        offset *= 4;
+        get = canvas->gx_canvas_memory;
+        get = (ULONG *)((UCHAR *)get + offset);
+
+        /* 从LCD显存读取要更新的区域,将canvas更新的数据复制进来 */
+        offset = (canvas->gx_canvas_display_offset_y + Copy.gx_rectangle_top) * LCD_WIDTH;
+        offset += canvas->gx_canvas_display_offset_x + Copy.gx_rectangle_left;
+        offset *= 3;
+        put = (ULONG *)(lcd->lcd_info.framebuffer);
+        put = (ULONG *)((UCHAR *)put + offset);
+
+        rect_info.x = dirty->gx_rectangle_left;
+        rect_info.y = dirty->gx_rectangle_top;
+        rect_info.width = dirty->gx_rectangle_right - dirty->gx_rectangle_left + 1;
+        rect_info.height = dirty->gx_rectangle_bottom - dirty->gx_rectangle_top + 1;
+
+        rgbx8888_to_rgb888(get, &rect_info, put);
+        lcd->parent.control(&lcd->parent, RTGRAPHIC_CTRL_RECT_UPDATE, &rect_info);
+    }
+}

+ 28 - 27
Port/gx_system_rtos_bind_rtthread.c

@@ -7,7 +7,7 @@
 *	修改记录 :
 *		版本号   日期         作者          说明
 *       V1.0    2020-11-20   HelloByeAll    首版           
-*        
+*       V1.1    2020-12-03   HelloByeAll    修改互斥量等初始化方法  
 *
 */
 
@@ -48,7 +48,7 @@ char guix_task_stack[GX_THREAD_STACK_SIZE];
 char guix_timer_task_stack[GX_TIMER_TASK_STACK_SIZE];
 
 /* define semaphore for lock/unlock macros */
-struct rt_mutex guix_system_lock_mutex;
+static rt_mutex_t guix_system_lock_mutex;
 
 struct rt_thread guix_tcb;
 struct rt_thread guix_timer_tcb;
@@ -65,12 +65,12 @@ typedef struct guix_linked_event_struct
 
 typedef struct guix_event_queue_struct
 {
-    GUIX_LINKED_EVENT *first;      /* first (oldest) event in fifo */
-    GUIX_LINKED_EVENT *last;       /* last (newest) event in fifo  */
-    GUIX_LINKED_EVENT *free;       /* linked list of free events   */
-    GUIX_LINKED_EVENT *free_end;   /* end of the free list         */
-    struct rt_semaphore count_sem; /* number of queued events      */
-    struct rt_mutex lock;          /* lock to protect queue update */
+    GUIX_LINKED_EVENT *first;    /* first (oldest) event in fifo */
+    GUIX_LINKED_EVENT *last;     /* last (newest) event in fifo  */
+    GUIX_LINKED_EVENT *free;     /* linked list of free events   */
+    GUIX_LINKED_EVENT *free_end; /* end of the free list         */
+    rt_sem_t count_sem;          /* number of queued events      */
+    rt_mutex_t lock;             /* lock to protect queue update */
 } GUIX_EVENT_QUEUE;
 
 /* an array of GX_EVENTs used to implement fifo queue */
@@ -85,10 +85,10 @@ VOID gx_generic_rtos_initialize(VOID)
     GUIX_LINKED_EVENT *current;
 
     guix_timer_event_pending = GX_FALSE;
-    rt_mutex_init(&guix_system_lock_mutex, "gx_system_lock", RT_IPC_FLAG_FIFO);
 
-    gx_system_memory_allocator_set(rt_malloc, rt_free);
+    guix_system_lock_mutex = rt_mutex_create("gx_system_lock", RT_IPC_FLAG_FIFO);
 
+    gx_system_memory_allocator_set(rt_malloc, rt_free);
     /* initialize a custom fifo queue structure */
 
     guix_event_queue.first = GX_NULL;
@@ -107,13 +107,14 @@ VOID gx_generic_rtos_initialize(VOID)
     guix_event_queue.free_end = current;
 
     /* create mutex for lock access to this queue */
-    rt_mutex_init(&guix_event_queue.lock, "gx_queue_lock", RT_IPC_FLAG_FIFO);
+    guix_event_queue.lock = rt_mutex_create("gx_queue_lock", RT_IPC_FLAG_FIFO);
 
     /* create counting semaphore to track queue entries */
-    rt_sem_init(&guix_event_queue.count_sem, "gx_queue_count", 0, RT_IPC_FLAG_FIFO);
+    guix_event_queue.count_sem = rt_sem_create("gx_queue_count", 0, RT_IPC_FLAG_FIFO);
 }
 
-VOID(*gx_system_thread_entry)(ULONG);
+VOID(*gx_system_thread_entry)
+(ULONG);
 
 // A small shell function to convert the void * arg expected by uC/OS to
 // a ULONG parameter expected by GUIX thread entry
@@ -161,13 +162,13 @@ UINT gx_generic_event_post(GX_EVENT *event_ptr)
     GUIX_LINKED_EVENT *linked_event;
 
     /* lock down the guix event queue */
-    rt_mutex_take(&guix_event_queue.lock, RT_WAITING_FOREVER);
+    rt_mutex_take(guix_event_queue.lock, RT_WAITING_FOREVER);
 
     /* grab a free event slot */
     if (!guix_event_queue.free)
     {
         /* there are no free events, return failure */
-        rt_mutex_release(&guix_event_queue.lock);
+        rt_mutex_release(guix_event_queue.lock);
         return GX_FAILURE;
     }
 
@@ -195,10 +196,10 @@ UINT gx_generic_event_post(GX_EVENT *event_ptr)
     guix_event_queue.last = linked_event;
 
     /* Unlock the guix queue */
-    rt_mutex_release(&guix_event_queue.lock);
+    rt_mutex_release(guix_event_queue.lock);
 
     /* increment event count */
-    rt_sem_release(&guix_event_queue.count_sem);
+    rt_sem_release(guix_event_queue.count_sem);
     return GX_SUCCESS;
 }
 
@@ -209,7 +210,7 @@ UINT gx_generic_event_fold(GX_EVENT *event_ptr)
 
     /* Lock down the guix queue */
 
-    rt_mutex_take(&guix_event_queue.lock, RT_WAITING_FOREVER);
+    rt_mutex_take(guix_event_queue.lock, RT_WAITING_FOREVER);
 
     // see if the same event is already in the queue:
     pTest = guix_event_queue.first;
@@ -220,7 +221,7 @@ UINT gx_generic_event_fold(GX_EVENT *event_ptr)
         {
             /* found matching event, update it and return */
             pTest->event_data.gx_event_payload.gx_event_ulongdata = event_ptr->gx_event_payload.gx_event_ulongdata;
-            rt_mutex_release(&guix_event_queue.lock);
+            rt_mutex_release(guix_event_queue.lock);
             return GX_SUCCESS;
         }
         pTest = pTest->next;
@@ -228,7 +229,7 @@ UINT gx_generic_event_fold(GX_EVENT *event_ptr)
 
     /* did not find a match, push new event */
 
-    rt_mutex_release(&guix_event_queue.lock);
+    rt_mutex_release(guix_event_queue.lock);
     gx_generic_event_post(event_ptr);
     return GX_SUCCESS;
 }
@@ -246,10 +247,10 @@ UINT gx_generic_event_pop(GX_EVENT *put_event, GX_BOOL wait)
     }
 
     /* wait for an event to arrive in queue */
-    rt_sem_take(&guix_event_queue.count_sem, RT_WAITING_FOREVER);
+    rt_sem_take(guix_event_queue.count_sem, RT_WAITING_FOREVER);
 
     /* lock down the queue */
-    rt_mutex_take(&guix_event_queue.lock, RT_WAITING_FOREVER);
+    rt_mutex_take(guix_event_queue.lock, RT_WAITING_FOREVER);
 
     /* copy the event into destination */
     *put_event = guix_event_queue.first->event_data;
@@ -280,7 +281,7 @@ UINT gx_generic_event_pop(GX_EVENT *put_event, GX_BOOL wait)
     }
 
     /* unlock the queue */
-    rt_mutex_release(&guix_event_queue.lock);
+    rt_mutex_release(guix_event_queue.lock);
     return GX_SUCCESS;
 }
 
@@ -292,7 +293,7 @@ VOID gx_generic_event_purge(GX_WIDGET *target)
 
     /* Lock down the guix queue */
 
-    rt_mutex_take(&guix_event_queue.lock, RT_WAITING_FOREVER);
+    rt_mutex_take(guix_event_queue.lock, RT_WAITING_FOREVER);
 
     // look for events targetted to widget or widget children:
     pTest = guix_event_queue.first;
@@ -320,7 +321,7 @@ VOID gx_generic_event_purge(GX_WIDGET *target)
         pTest = pTest->next;
     }
 
-    rt_mutex_release(&guix_event_queue.lock);
+    rt_mutex_release(guix_event_queue.lock);
 }
 
 /* start the RTOS timer */
@@ -338,13 +339,13 @@ VOID gx_generic_timer_stop(VOID)
 /* lock the system protection mutex */
 VOID gx_generic_system_mutex_lock(VOID)
 {
-    rt_mutex_take(&guix_system_lock_mutex, RT_WAITING_FOREVER);
+    rt_mutex_take(guix_system_lock_mutex, RT_WAITING_FOREVER);
 }
 
 /* unlock system protection mutex */
 VOID gx_generic_system_mutex_unlock(VOID)
 {
-    rt_mutex_release(&guix_system_lock_mutex);
+    rt_mutex_release(guix_system_lock_mutex);
 }
 
 /* return number of low-level system timer ticks. Used for pen speed caculations */

+ 3 - 1
README.md

@@ -1,6 +1,8 @@
 # AzureGUIX
 
-改软件包目前只有单色屏,RGB屏需自行修改驱动接口。请阅读pdf寻找修改方式
+2021-01-14
+增加ART-PI SPI屏驱动
+
 
 调用MainTask.c中的MainTask();即可完成初始化