关注+星标公众,不错过精彩内容

转自 | 嵌入式云IOT技术圈

微信公众号 | 嵌入式专栏

不知道有多少人折腾过液晶显示的菜单,我觉得很多人都应该搞过,我还记得以前大学参加电子设计竞赛获奖的作品,我就用到了一个12864,里面有菜单功能。

以前可能觉得菜单高大上,其实并不是想象中的复杂,本文为大家分享一个用单色屏做的菜单框架。

嵌入式专栏

1

概述

代码托管在github:

https://github.com/wujique/stm32f407/tree/sw_arch

本处所说的菜单是用在128*64这种小屏幕的菜单,例如下面这种,不是彩屏上的GUI。

嵌入式专栏

2

菜单框架设计

作为一个底层驱动工程师,驱动写完了,是要写硬件测试程序的。这个测试程序,一般给测试部/硬件工程师用来测试硬件, 也会给工厂产线测试准成品。

开始的人偷懒,不想一秒就直接上,所有菜单都这样做,一层套一层

void test_main(void)
{while(1){get_key(&key);switch(key){case 1:test_key();break;case 2:test_lcd();break;....}}
}

当菜单越来越多,就开始纠结了,这样写维护不便,看起来也不美,还浪费程序空间。

作为一个天天看《编程之美》的码农,决定改变现状。酷狗百度一番,找到了两个参考:《基于二叉树的多层的液晶菜单界面设计》 《基于节点编号的通用树状菜单设计方法与实现.pdf》 按照他们的设计方法,鼓捣了一个版本,能用,挺好,但是也纠结。因为他们用了树这种数据结构。对于程序运行来说,非常好,效率高。但是对于我来说,菜单代码是一次性的,但是菜单内容,却是会经常改的。让我用人脑去维护一个包含几十个上百个菜单的树,不容易。

想来想去,这些菜单到底有什么不好?对于我来说,为什么不好用?得出下面结论:

  1. 管得太宽 菜单,你就管菜单切换就行了,到了最低一层,也就是实际的测试功能,就不要管了。菜单切换是类似的,实际测试都是不同的。比如在菜单中,按键1,是进入第一个菜单。但是在测试中,按键1,功能都不一样。如果菜单连这个也要管,相同动作功能太多,无法进行统一抽象,就很难模块化。

  2. 出发点不一样 上面说到的菜单,出发点都是如何设计一个好的菜单数据结构,让程序快速,高效运行。我想要的却是一个容易维护的菜单结构,至于菜单的代码有多乱多纠结,没关系, 而且,几百上千个菜单,就算用轮询的方法,也不过几百us吧,没关系。

嵌入式专栏

3

改进菜单

根据需求,我重新设计了一个菜单结构体

/*** @brief  菜单对象
*/
typedef struct _strMenu
{MenuLel l;     ///<菜单等级char cha[MENU_LANG_BUF_SIZE];   ///中文char eng[MENU_LANG_BUF_SIZE];   ///英文MenuType type;  ///菜单类型s32 (*fun)(void);  ///测试函数} MENU;

是的,就这么简单,每一个菜单都是这个结构体 用这个结构体填充一个列表,就是我们的菜单了

const MENU EMenuListTest[]=
{MENU_L_0,//菜单等级"测试程序",//中文"test",        //英文MENU_TYPE_LIST,//菜单类型NULL,//菜单函数,功能菜单才会执行,有子菜单的不会执行MENU_L_1,//菜单等级"LCD",//中文"LCD",        //英文MENU_TYPE_LIST,//菜单类型NULL,//菜单函数,功能菜单才会执行,有子菜单的不会执行MENU_L_2,//菜单等级"VSPI OLED",//中文"VSPI OLED",        //英文MENU_TYPE_FUN,//菜单类型test_oled,//菜单函数,功能菜单才会执行,有子菜单的不会执行MENU_L_2,//菜单等级"I2C OLED",//中文"I2C OLED",        //英文MENU_TYPE_FUN,//菜单类型test_i2coled,//菜单函数,功能菜单才会执行,有子菜单的不会执行MENU_L_1,//菜单等级"声音",//中文"sound",        //英文MENU_TYPE_LIST,//菜单类型NULL,//菜单函数,功能菜单才会执行,有子菜单的不会执行MENU_L_2,//菜单等级"蜂鸣器",//中文"buzzer",        //英文MENU_TYPE_FUN,//菜单类型test_test,//菜单函数,功能菜单才会执行,有子菜单的不会执行MENU_L_2,//菜单等级"DAC音乐",//中文"DAC music",        //英文MENU_TYPE_FUN,//菜单类型test_test,//菜单函数,功能菜单才会执行,有子菜单的不会执行MENU_L_2,//菜单等级"收音",//中文"FM",        //英文MENU_TYPE_FUN,//菜单类型test_test,//菜单函数,功能菜单才会执行,有子菜单的不会执行MENU_L_1,//菜单等级"触摸屏",//中文"tp",        //英文MENU_TYPE_LIST,//菜单类型NULL,//菜单函数,功能菜单才会执行,有子菜单的不会执行MENU_L_2,//菜单等级"校准",//中文"calibrate",        //英文MENU_TYPE_FUN,//菜单类型test_cal,//菜单函数,功能菜单才会执行,有子菜单的不会执行MENU_L_2,//菜单等级"测试",//中文"test",        //英文MENU_TYPE_FUN,//菜单类型test_tp,//菜单函数,功能菜单才会执行,有子菜单的不会执行MENU_L_1,//菜单等级"按键",//中文"KEY",        //英文MENU_TYPE_FUN,//菜单类型test_key,//菜单函数,功能菜单才会执行,有子菜单的不会执行/*最后的菜单是结束菜单,无意义*/                        MENU_L_0,//菜单等级"END",//中文"END",        //英文MENU_TYPE_NULL,//菜单类型NULL,//菜单函数,功能菜单才会执行,有子菜单的不会执行
};

这个菜单列表有什么特点和要求呢?1 需要一个根节点和结束节点 2 子节点必须跟父节点,类似下面结构

-----------------------------------------------
根节点第1个1级菜单第1个子菜单第2个子菜单第3个子菜单第2个1级菜单第1个子菜单第1个孙菜单第2个孙菜单第2个子菜单第3个子菜单第3个1级菜单第4个1级菜单第5个1级菜单
结束节点
------------------------------------------------

第2个1级菜单有3个子菜单,子菜单是2级菜单,其中第1个子菜单下面又有2个孙菜单(3级菜单)。

维护菜单,就是维护这个列表,添加删除修改,非常容易。那菜单程序怎么样呢?管他呢。定义好菜单后,通过下面函数运行菜单,

 emenu_run(WJQTestLcd, (MENU *)&WJQTestList[0], sizeof(WJQTestList)/sizeof(MENU), FONT_SONGTI_1616, 2);

-第1个参数是在哪个LCD上显示菜单, -第2个是菜单列表, -第3个是菜单长度, -第4个四字体, -第5则是行间距

注意:运行这个菜单需要有rtos,因为菜单代码是while(1)的,陷进去就不出来了。需要有其他线程(TASK)维护系统,例如按键扫描。

嵌入式专栏

4

菜单实现效果

相关文件:emenu.c、emenu.h、emenu_test.c

当前代码:

1实现了双列菜单,用数字键选择进入下一层。每页最多显示8个菜单(4*4键盘用1-8键)

2 实现了单列菜单,通过上下翻查看菜单,确认键进入菜单。3 天顶菜单未实现,谁有兴趣可以加上。

3 基于LCD驱动架构,这个简易菜单自适应于多种LCD。

效果如下,有需要的尽管拿去,不用谢。

显示效果

128*64 OLED

128*128 tft lcd

320*240 tft lcd

嵌入式专栏

5

最后说明

以上菜单框架来源屋脊雀工作室,适合初学者练习。我看下这个菜单框架,其实还有很多改进地方。

我当初大学电子设计竞赛用到类似结构体方式,但我那菜单框架用到了二级指针,可以做到无限极扩展,而且可以指向(跳转)任意菜单,方便按键进入、返回等操作。

本文就分享到这里,感兴趣的读者可以自己写一个菜单框架。

免责声明:本文素材来源网络,版权归原作者所有。如涉及作品版权问题,请与我联系删除。

------------ END ------------

推荐阅读:

精选汇总 | 专栏 | 目录 | 搜索

精选汇总 | ARM、Cortex-M

精选汇总 | ST工具、下载编程工具

关注微信公众号『嵌入式专栏』,底部菜单查看更多内容,回复“加群”按规则加入技术交流群。

点击“阅读原文”查看更多分享,欢迎点分享、收藏、点赞、在看。

一个产品级MCU菜单框架设计相关推荐

  1. 一个开源经典的MCU菜单框架设计

    来源:嵌入式专栏 不知道有多少人折腾过液晶显示的菜单,我觉得很多人都应该搞过,我还记得以前大学参加电子设计竞赛获奖的作品,我就用到了一个12864,里面有菜单功能. 以前可能觉得菜单高大上,其实并不是 ...

  2. 微信小程序 - 实践- 001-实现一个多TAB的菜单框架

    1 前言: 多TAB的菜单框架,可以把不同内容的菜单选项进行分类,应该是常用的方法: 例如上面这个主界面由4个TAB菜单构成. 在微信给出的DEMO例子里面,也有相应的多TAB的使用, 在前一篇博客文 ...

  3. 值得学习的单片机菜单框架(附源码)

    点击上方"小麦大叔",选择"置顶/星标公众号" 福利干货,第一时间送达 大家好,我是小麦,以前用单片机做用户交互的菜单的时候,都比较痛苦,如何写一个复用性高,方 ...

  4. 设计php框架_PHP微型框架设计

    一.框架整体分析 在实现一个框架之前,我们需要了解这个框架应该达到一个怎样的效果,按照传统框架的思路,大致可以总结出以下这么几条: 1.实现MVC架构,将控制.逻辑.视图层进行分离. 2.封装各种函数 ...

  5. 战胜主导设计:一个整合性的分析框架

    文章目录 一.引言 二.相关文献回顾 三.主导设计形成后的新进入企业的SWOT分析 (一)NE的优势分析 (二)NE的劣势分析 (三)NE的机会分析 (四)NE的威胁分析 四.结论 五.参考文献 一. ...

  6. JavaWeb框架设计之菜单设计

    近来工作,要求自己搭建框架.从中遇到了这样一个诉求---动态菜单. 这个诉求在Java Web框架设计中属于最普遍的需求.那么我们来探讨下. 一般的Java Web框架的菜单层级都是为二级,那么在数据 ...

  7. SSM框架之酒店管理系统三(菜单数据库设计,菜单列表查询渲染)

    SSM框架之酒店管理系统三(菜单数据库设计,菜单列表查询渲染) 参考LAYUI MINI官网给出的数据库设计规范 Java示例(spring) · layuimini开发手册 (99php.cn) 数 ...

  8. 干货!如何设计实现一个通用的分布式事务框架?

    来源:https://www.bytesoft.org/ 一个TCC事务框架需要解决的当然是分布式事务的管理.关于TCC事务机制的介绍,可以参考TCC事务机制简介. TCC事务模型虽然说起来简单,然而 ...

  9. Dubbo面试 - 如何自己设计一个类似 Dubbo 的 RPC 框架?

    Dubbo面试 - 如何自己设计一个类似 Dubbo 的 RPC 框架? 面试题 如何自己设计一个类似 Dubbo 的 RPC 框架? 面试官心理分析 说实话,就这问题,其实就跟问你如何自己设计一个 ...

最新文章

  1. 网页中嵌套网页flush_如何修改网页中的内容?
  2. golang中container/list包中的坑
  3. 如何用 JavaScript+Canvas 开发一款超级烧脑小游戏?
  4. matlab 矢量化编程(三) —— 软阈值函数
  5. fortran调用MKL函数库中的gemm的fortran95接口计算矩阵相乘
  6. 销售管理系统哪个好用?
  7. 【原创抖音互动无人直播项目大鱼吃小鱼,进入直播间的用户开始吃鱼,吃的鱼越多等级越高越厉害】
  8. 计算入瞳、出瞳位置及孔径大小
  9. 有多少程序员干到35岁,那么其他人去干什么了?
  10. Ubuntu 16.04 显示器分辨率低
  11. Android中Gson使用,flutter调用原生sdk
  12. 湖北地图html代码,echarts全国省市地图代码
  13. Robocup 2D 的学习
  14. 数学文化 卢卡斯数列和黄金分割
  15. nginx运行php程序
  16. Class文件结构分析
  17. cass如何导入tif格式_CASS导入坐标文件的方法,一般人我不告诉他!-DAT文件
  18. RK3229方案测评 RK3299方案设计定制 RK3299方案开发板 RK3229智能音响
  19. 2021-2027全球与中国智能迷你无人机服务市场现状及未来发展趋势
  20. java荣誉勋章下载_荣誉勋章2011BT版

热门文章

  1. Linux与Android安全差异
  2. 做了一个仿吃鸡游戏,可多人联网,算是学习总结。
  3. Android Push实现总结
  4. css调颜色,CSS3 简单的调色板
  5. Element表格出现闪动问题
  6. 联想y7000电脑未正确启动_Lenovo/联想 拯救者 Y7000简单装系统教程
  7. android qq接口,手机QQ Scheme接口
  8. TensorFlow keras数据集本地下载路径
  9. 学java日志框架,看这一篇就够了!!!
  10. Beyond Compare解决java文件对比中文乱码问题