移植emWin_5.22

2023-10-14 19:20
文章标签 移植 emwin 5.22

本文主要是介绍移植emWin_5.22,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

        emwin是续开源uc/GUI 3.98之后的不开源版本,所以它们的API函数几乎相同,只是emwin作了很多改进,增加了很多新功能,并且已经有很多免费的版本支持于ST、NXP等大公司的芯片上,它的移植接口也作了很大的改进,如果有了以前开源版本的移植,移植emwin不在话下,本文主要讲述移植到NXP的LPC1788上。

1、不开源的emwin其实很简单,我们可以从NXP的官方得到,加载到MDK的源文件目录如下:

从上图可以看到,不开源的emwin实在比起以前的uc/GUI简洁了很多,提供lib的库,也使编译速度快了很多。另外的hzk12.c是中文字库,下面会讲述如何在emwin上增加中文字库。
2、按顺序,先移植GUIConf.c文件,主要有以下代码:
#define GUI_NUMBYTES (1024 * 40)
#define GUI_BLOCKSIZE (500)
U32 static _aMemory[GUI_NUMBYTES / 4] __attribute__ ((section ("GUI_RAM"), zero_init));
前面两个宏定义是定义GUI缓存的大小,可以根据需要自行定义,另外定义的_aMenory数组是很有意思的,把这个数组的空间命名为“GUI_RAM”,是为了方便在分散加载里面,把GUI的缓存放在SDRAM或者其它地方。
另外,GUIConf.c文件里面还要实现一个函数void GUI_X_Config(void),如下:
void GUI_X_Config(void) {
  GUI_ALLOC_AssignMemory(_aMemory, GUI_NUMBYTES);
  GUI_ALLOC_SetAvBlockSize(GUI_BLOCKSIZE);
  GUI_SetDefaultFont(GUI_FONT_6X8);
  GUITASK_SetMaxTask(GUI_MAX_TASK);
}
这个函数会在初始化时调用,完成内存分配,默认字体,多任务的配置(无操作系统是可以不需要)。
3、完成GUIConf.c文件后,接下来是GUIConf.h文件,该文件主要完成一些配置宏的定义:
#define GUI_NUM_LAYERS 16 // Maximum number of available layers
#define GUI_OS (1) // Compile with multitasking support
#define GUI_MAX_TASK (1) // Max. number of tasks that may call emWin
#define GUI_SUPPORT_TOUCH (1) // Support a touch screen (req. win-manager)
#define GUI_DEFAULT_FONT &GUI_Font6x8
#define GUI_SUPPORT_MOUSE 1 // Support a mouse
#define GUI_WINSUPPORT 1 // Use window manager
#define GUI_SUPPORT_MEMDEV 0 // Memory device package available
#define GUI_SUPPORT_DEVICES 1 // Enable use of device pointers
根据需要进行配置就行了,每个宏都有注释。
4、上面两个文件都没什么,接下来的LCDConf.c才是大块头,该文件内容稍多些,这里拿出重点说说。
#define XSIZE_PHYS 800
#define YSIZE_PHYS 480
#define COLOR_CONVERSION GUICC_M8888
#define PIXEL_WIDTH 4
上面的宏很好理解,LCD的像素,显示颜色的模式及像素宽度,我这里用的是24位色的,把它定义成32位的,方便编写,但会超成一定的内存浪费,一般应用中,26位色就足够了。
接下来是一个关键,如果你在裸机的情况下实现过LCD显示就很好办了,主要有以下两部分:
1)、初始化,在LCD_X_DisplayDriver函数的case LCD_X_INITCONTROLLER:里增加初始化代码:
 __lcdInit();
 __touchInit();
是一个函数,还是两个函数,还是其它函数名字,你自己喜欢。
2)、像素操作函数,在LCD_X_DisplayDriver函数的case LCD_X_SETORG:里增加像素操作函数:
__SetDisplayOrigin(p->xPos, p->yPos);
一样的道理,函数名字自己喜欢,但函数的两个函数是必需这样的。
5、好了,其实经过上面几个步骤,你的GUI基本可以显示了,好像很简单的样子。是的,接下来加入操作系统相关函数,因为在操作系统的多任务同时操作GUI函数时,必然要考虑保护机制,其实也很简单,官方都有给出代码,稍作修改即可,重要的是要理解其用意。我这里用的是uCOS-II,如果你在某个地方找到一个GUI_X_uCOS.c的文件,恭喜你,这个文件基本可以用的了,下面讲讲这个文件的原理。
1)、加入GUI的时间相关函数
int GUI_X_GetTime (void)
{
    return ((int)OSTimeGet());
}
void GUI_X_Delay (int period)
{
    INT32U ticks;
    ticks = (period * 1000) / OS_TICKS_PER_SEC;
    OSTimeDly((INT16U)ticks);
}
这很好理解,只接调用uCOS-II里面的时间相关函数就行了。
2)、GUI支持多任务的核心都是围绕下面的3个变量,在uCOS-II里面很基本的一个东西:信号量、邮箱,如果这个不懂,好好玩通了uCOS-II再来搞。
static OS_EVENT *DispSem;
static OS_EVENT *EventMbox;
static OS_EVENT *KeySem;
void GUI_X_InitOS (void)
{
    DispSem = OSSemCreate(1);
    EventMbox = OSMboxCreate((void *)0);
}
GUI_X_InitOS函数主要先建立DispSem信号量、EventMbox邮箱。
3)、建立互斥相关函数
void GUI_X_Lock (void)
{
    INT8U err;
   
    OSSemPend(DispSem, 0, &err);
}
void GUI_X_Unlock (void)
{
    OSSemPost(DispSem);
}
U32 GUI_X_GetTaskId (void)
{
    return ((U32)(OSTCBCur->OSTCBPrio));
}
GUI_X_Lock、GUI_X_Unlock两个函数通过信号量,来达到一个互斥的作用,该信号量是当作2值量来用的,就相当于一个厕所的锁有两个状态,要么开、要么关,一个人进了厕所后就关上,出来时再打开,来达到一个厕所里面同时只有一个人的保护作用(除非你喜欢同时两个人一起上大急,呵呵)。GUI_X_GetTaskId函数是用于获取当前任务的ID,在uCOS-II里面ID就是优先级。这三个函数,GUI里面怎么调用你不需要理会,你告诉GUI,它自己会调用的(emwin不开源,你知道也没用)。
3)、等待事件发生,与任务上锁的原理其实都相同,只是官方给的代码里面通过邮箱的方式来实现,原理是一样的
void GUI_X_WaitEvent (void)
{
    INT8U err;
    (void)OSMboxPend(EventMbox, 0, &err);
}
void GUI_X_SignalEvent (void)
{
    (void)OSMboxPost(EventMbox, (void *)1);
}
4)、最后是键盘相关的OS_EVENT *KeySem;,后面几个关于键盘的键值保存等功能函数都很好理解,这里实际没用到键盘,但在后边的输入法里面,可能会涉及到,这里依然保存。
6、好了,多任务也有了,现在就放心地在uCOS-II里面自由调用吧。但,好像事情还没结束,我们用的是触摸屏,不管是电容屏、电阻屏都好,道理都是一样的,在早期开源的版本中,我们可以直接在开源代码的GUI_PID.C源文件里的void GUI_PID_StoreState(const GUI_PID_STATE *pState)函数里面增加,但在emwin里面,该方法已行不通,可以用以下的办法:
在uCOS-II里面本来会用一个单独的任务用于刷新界面,这里就把触摸事件也通过这个任务里面更新,代码如下:
void TaskGUI(void *pvData)
{
    GUI_PID_STATE State;
    while(1) {
        if (!(LPC_GPIO2->PIN & 1 << 10)) { // 有按键按下
            if (__checkUpdateTouch()) {
                State.Pressed = 1;
                State.x = measureX;
                State.y = measureY;
                GUI_PID_StoreState(&State);
                GUI_TOUCH_Exec(); // 刷新坐标
            }
        } else {
            GUI_PID_GetState(&State);
            State.Pressed = 0;
            GUI_PID_StoreState(&State);
        }
        WM_Paint(0);
        GUI_Delay(1);
    }
}
其中的 __checkUpdateTouch() 函数是自己写的获取当前触摸屏的坐标值函数,更新后的值在measureX、measureY这两个全局变量里,当然不用全局变量,通过函数返回等各种方法都是可以的,道理都是一样:当我们改变不了源代码时,调用API接口把当前的触摸事件及坐标更新给GUI内核处理。
7、经过上面几步操作,emwin的移植其实已经结束了,这里面要增加一点:emwin默认没有中文字库,需要我们自行增加字库存。
字库文件就是hzk12.c了,为什么把它方在GUI内核同个目录里面,因为它应属于内核里面的一部分,该源文件里面把中文的字库都封装成GUI_FLASH const GUI_FONT GUI_FontHZ12,然后在GUI.h头文件里的大约第1724行左右,增加以下宏:
extern const GUI_FONT GUI_FontHZ12;
#define GUI_FONT_HZ12 &GUI_FontHZ12
这样在你的emwin里面就多了一个名称为GUI_FONT_HZ12的中文字体了,hzk12.c在网上应该也可以找到,有需要的也可以联系我。
经过上边的移植,emwin就可以用了,其它的函数调用就看官方的文档操作即可,最后有几个小问题,暂时没时间去处理了:
1、为何多任务时,GUI_MAX_TASK一定要宏定义成1,并且一定要在GUI_X_Config()函数里面调用GUITASK_SetMaxTask(GUI_MAX_TASK);
2、emwin的显存指向片外SDRAM有问题,如果指向片内的SRAM就没有问题,初步确定SDRAM的初始化有问题。

这篇关于移植emWin_5.22的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/212609

相关文章

FreeRTOS-基本介绍和移植STM32

FreeRTOS-基本介绍和STM32移植 一、裸机开发和操作系统开发介绍二、任务调度和任务状态介绍2.1 任务调度2.1.1 抢占式调度2.1.2 时间片调度 2.2 任务状态 三、FreeRTOS源码和移植STM323.1 FreeRTOS源码3.2 FreeRTOS移植STM323.2.1 代码移植3.2.2 时钟中断配置 一、裸机开发和操作系统开发介绍 裸机:前后台系

RT-Thread(Nano版本)的快速移植(基于NUCLEO-F446RE)

目录 概述 1 RT-Thread 1.1 RT-Thread的版本  1.2 认识Nano版本 2 STM32F446U上移植RT-Thread  2.1 STM32Cube创建工程 2.2 移植RT-Thread 2.2.1 安装RT-Thread Packet  2.2.2 加载RT-Thread 2.2.3 匹配相关接口 2.2.3.1 初次编译代码  2.2.3.

【视频教程】手把手AppWizard轻松制作一个emWin滑动主界面控制框架,任意跳转控制(2024-09-06)

现在的新版AppWizard已经比较好用,用户可以轻松的创建各种项目常规界面。 比如早期创建一个支持滑动的主界面框架,并且可以跳转各种子界面,仅仅界面布局和各种图片格式转换都要花不少时间,而现在使用AppWizard,可以说轻轻松松,毫不费力。 用户唯一要做的就是根据自己的芯片性能做一定的速度优化。 视频: https://www.bilibili.com/video/BV17Rp3eLE

libmad音频解码库-Linux交叉编译移植

下载并解压libmad-0.15.1b.tar.gz 下载链接:https://downloads.sourceforge.net/mad/libmad-0.15.1b.tar.gz $tar -xvf libmad-0.15.1b.tar.gz$cd libmad-0.15.1b 1、先执行下面的命令:这条命令是为了适配高版本的gcc,因为高版本的gcc已经将-fforce-mem去除了:

arm linux lua移植

lua: lua home 1.下载lua源码 lua下载 lua-5.3.4.tar.gz 2.解压: tar xvf lua-5.3.4.tar.gz 3.修改makefile and luaconf.h $修改 lua-5.3.4/Makefile #INSTALL_TOP= /usr/local INSTALL_TOP= $(shell pwd)/out #修改安装目录(当前目录/o

s3c2440---PWM使用之蜂鸣器驱动移植

一、蜂鸣器驱动介绍 1.1.什么是蜂鸣器               蜂鸣器是一种简单的声响发生器,常用于电子产品中作为警示或提醒作用。其基本原理是通过交替改变直流电的电压方向来产生声音,一般使用交替电流产生声音会比较稳定。 1.2.蜂鸣器的类别 1.有源蜂鸣器 1)结构原理 有源蜂鸣器内部自带振荡源,只需接通电源即可发声。内部电路会自动产生一定频率的振荡信号,从而驱动蜂鸣器发声。

【GD32】---- 移植工程模板及点灯测试

1 新建模板文件夹 新建一个名叫03_GD32TemplateProject的文件夹,用于建造工程模板 2 移植官方库文件 在模板文件夹里新建5个文件夹,分别存放官方库文件和系统驱动文件 01_main 存放main函数 02_Startup 存放系统启动文件 03_System 存放官方的系统文件 04_Firmware_PeripheralDriver 存放官方

[rk3588 ubuntu20.04]移植ROS2

目录 1 使用命令行安装ROS2 1.1设置语言 1.2添加源 1.3安装ROS2 1.4设置环境变量 2 在编译源码阶段安装ROS2 2.1调整roofts.img大小 2.2 安装ROS2 3 ROS2功能测试 1 使用命令行安装ROS2 1.1设置语言         设置语言为UTF-8。 sudo apt update && sudo apt insta

让linux下无线网卡变身随身wifi----hostapd移植-Nazgul

有了前面的检测,确定了我们的网卡是能够拥有热点共享功能的,但是如何让它共享出来呢? 于是有了这篇文章的诞生,hostapd移植 hostapd    可以让我们的网线网卡变成热点 1、下载     git clone git://w1.fi/srv/git/hostap.git   得到hostap目录,但是里面wpa_supplicant and hostapd的结合在

让linux下无线网卡变身随身wifi----前言--iw移植-Nazgul

最痛苦的事莫过于--上班 最最痛苦的事莫过于--上班有网不能上 最最最痛苦的事莫过于--上班有网能上却没有wifi 最最最最痛苦的事莫过于--你有无线网卡却没有U口可插 最最最最最痛苦的事莫过于--有U口插却发现U口只在开发板上 最最最最最最痛苦的事莫过于--开发板上有u口但是跑的是linux 最最最最最最最痛苦的事莫过于--linux能驱动网卡,但是如何共享出wifi来啊 于是,,,