> 文档中心 > 单片机---HLK-W801图形框架LVGL下开发(二)

单片机---HLK-W801图形框架LVGL下开发(二)


前文回顾

《单片机—HLK-W801并口驱动ST7789》
《单片机—HLK-W801驱动触摸屏》
《单片机—HLK-W801图形框架LVGL移植》
《单片机—HLK-W801图形框架LVGL下开发(一)》

2022.2.21日的效果如下

W801上移植lvgl,并增加APP模拟

本章重点

框架移植好了之后,就打算开发一些软件应用,目前做出了桌面和菜单,能够进行软件打开关闭,准备把这个打造成一个微型的计算机系统,那么必然是需要应用软件的。
谁……谁在喊扫雷……
在这里插入图片描述
今天开发一下计算器这个功能。

界面绘制

显示部分,这里主要是绘制了一个textarea和一个软键盘,这个键盘是一个矩阵键盘,在官方的表述中这种还是很节省资源的。
绘制键盘上增加我们要输入的数字键,运算符。模拟windows上的计算器即可
在这里插入图片描述
这不会被微软起诉吧,
在这里插入图片描述

下面是绘制界面部分代码。绘制了一个textarea,用来显示算式。然后绘制了一个键盘,用来输入运算符和操作符。

    lv_obj_t * ta = lv_textarea_create(cont);    lv_textarea_set_one_line(ta, true);    lv_obj_align(ta, LV_ALIGN_TOP_MID, 0, -5);    lv_obj_add_event_cb(ta, textarea_event_handler, LV_EVENT_READY, ta);    lv_obj_add_state(ta, LV_STATE_FOCUSED); /*To be sure the cursor is visible*/    static const char * btnm_map[] = {"(", ")", "%", "*","\n","9", "8", "7","/", "\n","6", "5", "4","-","\n","3", "2", "1", "+","\n",LV_SYMBOL_BACKSPACE, "0", "CE", "="""};    lv_obj_t * btnm = lv_btnmatrix_create(cont);    lv_obj_align(btnm, LV_ALIGN_TOP_MID, 0, 25);    lv_obj_set_size(btnm, 260, 160);    lv_obj_add_event_cb(btnm, btnm_event_handler, LV_EVENT_VALUE_CHANGED, ta);    lv_obj_clear_flag(btnm, LV_OBJ_FLAG_CLICK_FOCUSABLE); /*To keep the text area focused on button clicks*/    lv_btnmatrix_set_map(btnm, btnm_map);

回调函数,这里用来即时的响应键盘,将键盘的数字发送到textarea中,并且个别处理一下操作字符。例如回退,清空,等号等。

static void btnm_event_handler(lv_event_t * e){    lv_obj_t * obj = lv_event_get_target(e);    lv_obj_t * ta = lv_event_get_user_data(e);    const char * txt = lv_btnmatrix_get_btn_text(obj, lv_btnmatrix_get_selected_btn(obj));    if(strcmp(txt, LV_SYMBOL_BACKSPACE) == 0) {lv_textarea_del_char(ta);}    else if(strcmp(txt, "CE") == 0){lv_textarea_set_text(ta,"");}    else if(strcmp(txt, "=") == 0){//lv_event_send(ta, LV_EVENT_READY, NULL);char result[32]={0};calc_main(lv_textarea_get_text(ta),result);lv_textarea_set_text(ta,result);}    else    {lv_textarea_add_text(ta, txt);    }}

绘制代码和回调比较简单,也不是核心所在
在这里插入图片描述

计算器C语言实现

这里我们要做到的就是将一个运算式,直接计算出结果。这里要用的知识点,就是前缀,中缀和后缀表达式。具体可以参考一下这篇文章 chensongxian的《前缀、中缀、后缀表达式(逆波兰表达式)》

这里提炼一下。
我们常见的手写算式,属于中缀表达式,例如(3+2)*8-2,简单来说就是符合人类阅读习惯的表达式。

在这里插入图片描述

不过计算机能处理的,不是这种,常处理的就是后缀表达式。

后缀表达式就是运算符在数字之后,例如 3 2 + 5 -,表达的就是3和2相加,然后-5。
计算方法,下面介绍常用的堆栈法:
从左至右扫描表达式,遇到数字时,将数字压入堆栈,遇到运算符时,弹出栈顶的两个数,用运算符对它们做相应的计算(次顶元素 op 栈顶元素),并将结果入栈;重复上述过程直到表达式最右端,最后运算得出的值即为表达式的结果。

代码可以参考 肖志峰 《利用栈实现计算表达式字符串的值(C语言)》
这里的代码是只能计算到整数。

还可以参考Java3L《C语言中缀表达式求值(综合)》
这里取了浮点数作为中间结果,可以计算出小数。

整体效果

w801上lvgl实现计算器

还算比较流畅啊。

结束语

这两天大事太多了,借用朋友的一张图,暖一下场吧。
在这里插入图片描述

周末老家里一位亲人也心脏病突发故去,正赶上疫情严重,人也就很快入土为安了。
在这里插入图片描述
还是那句简单的话,珍惜当下。