搜索
bottom↓
回复: 29

分享一份原创开源的通用型多级菜单设计代码

  [复制链接]

出0入0汤圆

发表于 2017-12-13 11:32:43 | 显示全部楼层 |阅读模式
坛子里有很多多级菜单设计的代码,一般都是先创建一个结构体数组,将每个界面编号后,放在结构体数组中。
我觉得可以设计一种更加优雅的方式,提高移植性,于是有了现在的代码(代码很简单,大神勿喷)。

主要思路:

1、每一级菜单称为object,  当级菜单的页面为 item
对应接口:

  1. bM_OBJ_Handle bM_CreateObject(bM_ITEM_Handle hParent, bM_ID id);
  2. bM_ITEM_Handle bM_AddItemToObject(bM_OBJ_Handle hobj, bM_ID id, bM_CreateUI_t func);
复制代码

2、下一级菜单一定是基于上一级菜单的某个子页面。这样就可以理解在上面的接口中bM_CreateObject的一个入口参数 hParent就是指定上级菜单的子页面。
3、创建object和item都需要指定用户得id。在添加item到object时可以指定显示界面的功能函数。
4、根据功能的不同,有些情况下需要动态的隐藏和显示某个界面。则可以通过如下接口:
  1. bM_Result_t bM_ChangeVisibleStatus(bM_ID id, bM_bool_t visible);
复制代码

5、有些项目需要动态更换整个菜单结构,可以提前创建多个菜单结构后,通过下面接口指定当前使用哪一个。
  1. bM_Result_t bM_SetMenuEntryPoint(bM_OBJ_Handle hobj);
复制代码



例如,创建4级菜单:
item1----item2-----item3-----item4
           |
           item5----item6----item7
                      |
                      item8--item9
                      |
                      item10

细化为:
object1 {item1----item2----item3----item4}
object2 {item5----item6----item7}
object3 {item8----item9}
object4 {item10}

准备用户id:

  1. enum
  2.    {
  3.    USER_ID_OBJECT_1,
  4.    USER_ID_ITEM1,
  5.    USER_ID_ITEM2,
  6.    USER_ID_ITME3,
  7.    USER_ID_ITEM4,
  8.    USER_ID_OBJECT_2,
  9.    USER_ID_ITEM5,
  10.    USER_ID_ITEM6,
  11.    USER_ID_ITEM7,
  12.    USER_ID_OBJECT_3,
  13.    USER_ID_ITEM8,
  14.    USER_ID_ITEM9,
  15.    USER_ID_OBJECT_4,
  16.    USER_ID_ITEM10
  17.    };
复制代码


开始创建菜单结构:

  1. example_func
  2.    {
  3.       bM_OBJ_Handle  hobj, hobj_tmp;
  4.       bM_ITEM_Handle hItem;
  5.       
  6.       hobj = bM_CreateObject(bM_HANDLE_INVALID, USER_ID_OBJECT_1);        //一级菜单
  7.       bM_AddItemToObject(hobj, USER_ID_ITEM1, func1);
  8.       hItem = bM_AddItemToObject(hobj, USER_ID_ITEM2, func2);
  9.       bM_AddItemToObject(hobj, USER_ID_ITME3, func3);
  10.       bM_AddItemToObject(hobj, USER_ID_ITEM4, func4);
  11.       
  12.       hobj_tmp = bM_CreateObject(hItem, USER_ID_OBJECT_2);                     //二级菜单
  13.       bM_AddItemToObject(hobj_tmp, USER_ID_ITEM5, func5);
  14.       hItem = bM_AddItemToObject(hobj_tmp, USER_ID_ITEM6, func6);
  15.       bM_AddItemToObject(hobj_tmp, USER_ID_ITEM7, func7);  
  16.   
  17.       hobj_tmp = bM_CreateObject(hItem, USER_ID_OBJECT_3);                    //三级菜单
  18.       hItem = bM_AddItemToObject(hobj_tmp, USER_ID_ITEM8, func8);
  19.       bM_AddItemToObject(hobj_tmp, USER_ID_ITEM9, func9);

  20.       hobj_tmp = bM_CreateObject(hItem, USER_ID_OBJECT_4);                   //四级菜单
  21.       bM_AddItemToObject(hobj_tmp, USER_ID_ITEM10, func10);
  22.       
  23.       //then set the entry point:
  24.       bM_SetMenuEntryPoint(hobj);                                                              //指定当前的菜单结构入口
  25.   }
复制代码





结构创建好后,需要工作起来,则在主循环里调用:
  1. void bM_BMenuModuleTask(void);
复制代码


需要切换界面时:
  1. bM_Result_t bM_SendMessage(bM_Operation_t opt, bM_ID id);
复制代码

例如:

  1.   bM_SendMessage(BM_OPERATE_NEXT, 0);   // to show the next item
  2.   
  3.   bM_SendMessage(BM_OPERATE_JUMP_TO, USER_ID_ITEM5);   //to show the item5
复制代码


当然在开始使用前需要调用初始化函数指定malloc和free接口
  1. bM_Result_t bM_Init(bM_DMC_Interface_t bM_DMC_Interface);
复制代码





有兴趣的盆友可以使用使用,如果不好用则告诉我,如果好用就留着用吧 !!!

https://github.com/notrynohigh/bMenu

本帖子中包含更多资源

您需要 登录 才可以下载或查看,没有帐号?注册

x

阿莫论坛20周年了!感谢大家的支持与爱护!!

月入3000的是反美的。收入3万是亲美的。收入30万是移民美国的。收入300万是取得绿卡后回国,教唆那些3000来反美的!

出10入23汤圆

发表于 2017-12-13 11:40:11 | 显示全部楼层
https://www.amobbs.com/thread-5670258-1-1.html

出0入0汤圆

发表于 2017-12-13 20:30:23 | 显示全部楼层
有点复杂,还没有弄清楚,得仔细研究一下

出100入85汤圆

发表于 2017-12-13 21:57:09 来自手机 | 显示全部楼层
谢谢分享,想法不错。

出0入4汤圆

发表于 2017-12-14 07:19:20 来自手机 | 显示全部楼层
谢谢分享

出0入0汤圆

发表于 2017-12-14 07:22:38 | 显示全部楼层
谢谢分享

出100入101汤圆

发表于 2017-12-14 09:01:12 | 显示全部楼层
多年前搞过多级菜单,大同小异

出0入0汤圆

发表于 2017-12-14 09:41:33 | 显示全部楼层
搞过一个液晶显示界面,用的就是lz说过的结构体数组的办法,初始化的时候确实太麻烦。

出0入0汤圆

 楼主| 发表于 2017-12-14 11:12:55 | 显示全部楼层
zouzhichao 发表于 2017-12-13 11:40
https://www.amobbs.com/thread-5670258-1-1.html

你这个软件挺方便的,是生成结构体数组。其实我觉得结构体数组最不好的地方就是无法直接从代码中清晰的分出各级菜单。 小弟这份代码,创建菜单后,菜单的分层还是挺清楚的。

出0入0汤圆

 楼主| 发表于 2017-12-14 11:13:31 | 显示全部楼层
zhousun 发表于 2017-12-13 20:30
有点复杂,还没有弄清楚,得仔细研究一下

多谢支持

出0入0汤圆

 楼主| 发表于 2017-12-14 11:13:53 | 显示全部楼层
whatcanitbe 发表于 2017-12-13 21:57
谢谢分享,想法不错。

多谢支持,希望多多指教

出0入0汤圆

 楼主| 发表于 2017-12-14 11:15:14 | 显示全部楼层
simplorer 发表于 2017-12-14 09:41
搞过一个液晶显示界面,用的就是lz说过的结构体数组的办法,初始化的时候确实太麻烦。
...

以前也是一直用结构体数组,觉得不好直观的看出菜单的分层,时间长了回头都不知道哪一项对应哪个界面了。

出10入23汤圆

发表于 2017-12-14 12:24:55 来自手机 | 显示全部楼层
怂包BB 发表于 2017-12-14 11:12
你这个软件挺方便的,是生成结构体数组。其实我觉得结构体数组最不好的地方就是无法直接从代码中清晰的分 ...

菜单分层直接在xml文件里面管理,很清晰

出0入0汤圆

发表于 2017-12-18 22:57:35 来自手机 | 显示全部楼层
很久没有讲菜单结构的了,有想法

出0入0汤圆

 楼主| 发表于 2017-12-21 10:13:11 | 显示全部楼层
lovecxm 发表于 2017-12-18 22:57
很久没有讲菜单结构的了,有想法

多谢支持

出0入0汤圆

发表于 2017-12-21 10:47:01 | 显示全部楼层
zouzhichao 发表于 2017-12-13 11:40
https://www.amobbs.com/thread-5670258-1-1.html

你是来砸场子的吧

出0入0汤圆

发表于 2017-12-21 11:06:19 | 显示全部楼层
学习一下,多谢。

出0入0汤圆

发表于 2018-1-24 11:38:36 | 显示全部楼层
楼主,为啥一直无法下载!

出0入0汤圆

发表于 2018-1-25 17:21:10 | 显示全部楼层
if (_bM_GetIdFromHandle(gp_bM_MenuEntryPoint->pFirstItem, BM_ID_USER) == id)
楼主这里不会报错吗?
C1822: Type mismatch
[ERROR]
Description
There is no conversion between the two specified types.
Example
void main() {
  int *p;
  int j;
  p=j;     // error
}

Tips
Use types that can be converted.

出0入0汤圆

发表于 2018-1-27 08:11:51 | 显示全部楼层
请教楼主,
bM_ITEM_Handle bM_AddItemToObject(bM_OBJ_Handle hobj, bM_ID id, bM_CreateUI_t func)这个函数的这个bM_CreateUI_t func形参,只有指针类型,没有函数原型啊?

出0入0汤圆

发表于 2018-3-3 20:49:55 | 显示全部楼层
表示没看懂,先收藏,谢谢

出0入0汤圆

发表于 2018-3-3 20:59:48 来自手机 | 显示全部楼层
谢谢分享。

出0入17汤圆

发表于 2018-3-3 22:19:56 | 显示全部楼层
本帖最后由 wicy001 于 2018-3-3 22:22 编辑

支持动态的菜单项吗?

比如一个菜单系统
一级菜单有 “添加传感器”,“查看传感器”
同过添加传感器菜单,添加几种传感器, 那么查看传感器菜单下,就有几个子菜单

出0入0汤圆

 楼主| 发表于 2018-3-5 16:44:21 | 显示全部楼层
wicy001 发表于 2018-3-3 22:19
支持动态的菜单项吗?

比如一个菜单系统

可以动态的添加

出0入0汤圆

发表于 2018-3-5 16:56:29 | 显示全部楼层
需要 malloc和free接口  单片机怎么玩?


出0入0汤圆

 楼主| 发表于 2018-3-6 09:14:58 | 显示全部楼层
ljt80158015 发表于 2018-3-5 16:56
需要 malloc和free接口  单片机怎么玩?

在启动文件给堆分配空间,就可以跑了,单片机支持动态内存管理的!

出0入0汤圆

发表于 2018-3-6 09:50:36 | 显示全部楼层
怂包BB 发表于 2018-3-6 09:14
在启动文件给堆分配空间,就可以跑了,单片机支持动态内存管理的!



单片机重来不用内存管理,影响稳定性,单片机稳定第一


出0入0汤圆

 楼主| 发表于 2018-3-6 10:09:24 | 显示全部楼层
ljt80158015 发表于 2018-3-6 09:50
单片机重来不用内存管理,影响稳定性,单片机稳定第一

不能说重来不用吧,根据具体项目来看。这个根据需求做选择了。没其他的。

出20入118汤圆

发表于 2019-4-28 17:36:37 | 显示全部楼层
怂包BB 发表于 2018-3-6 10:09
不能说重来不用吧,根据具体项目来看。这个根据需求做选择了。没其他的。 ...

看了您的github,这个多级菜单框架 有没有例子参考下

出0入0汤圆

发表于 2020-1-4 11:21:53 | 显示全部楼层
多谢分享
回帖提示: 反政府言论将被立即封锁ID 在按“提交”前,请自问一下:我这样表达会给举报吗,会给自己惹麻烦吗? 另外:尽量不要使用Mark、顶等没有意义的回复。不得大量使用大字体和彩色字。【本论坛不允许直接上传手机拍摄图片,浪费大家下载带宽和论坛服务器空间,请压缩后(图片小于1兆)才上传。压缩方法可以在微信里面发给自己(不要勾选“原图),然后下载,就能得到压缩后的图片】。另外,手机版只能上传图片,要上传附件需要切换到电脑版(不需要使用电脑,手机上切换到电脑版就行,页面底部)。
您需要登录后才可以回帖 登录 | 注册

本版积分规则

手机版|Archiver|amobbs.com 阿莫电子技术论坛 ( 粤ICP备2022115958号, 版权所有:东莞阿莫电子贸易商行 创办于2004年 (公安交互式论坛备案:44190002001997 ) )

GMT+8, 2024-4-24 19:28

© Since 2004 www.amobbs.com, 原www.ourdev.cn, 原www.ouravr.com

快速回复 返回顶部 返回列表