[应用相关] 在STM32上使用HAL库和SSD1306 OLED显示屏实现菜单功能

[复制链接]
1562|11
 楼主| 小明的同学 发表于 2023-4-26 20:21 | 显示全部楼层 |阅读模式
注意,这里的代码使用了HAL库和STM32CubeMX代码生成器来初始化STM32芯片和I2C总线,以及SSD1306 OLED显示屏的硬件配置。确保正确配置了I2C总线和SSD1306 OLED屏幕,然后将以下代码添加到main.c文件中即可。
  1. #include "main.h"
  2. #include <string.h>
  3. #include <stdio.h>
  4. #include <stdlib.h>

  5. #include "ssd1306.h"

  6. #define OLED_RESET_PIN GPIO_PIN_15
  7. #define OLED_RESET_PORT GPIOA
  8. #define OLED_I2C_PORT hi2c1

  9. SSD1306 display(&hi2c1, OLED_RESET_PORT, OLED_RESET_PIN);

  10. // 菜单节点
  11. struct MenuItem
  12. {
  13.   const char* name;  // 节点名称
  14.   MenuItem* next;    // 下一个节点的指针
  15.   void (*function)();  // 节点功能函数的指针
  16. };

  17. // 菜单类
  18. class Menu
  19. {
  20. public:
  21.   Menu();
  22.   void AddItem(const char* name, void (*function)());
  23.   void Run();

  24. private:
  25.   MenuItem* mHead;
  26. };

  27. // 菜单构造函数
  28. Menu::Menu()
  29.   : mHead(nullptr)
  30. {
  31. }

  32. // 添加菜单节点
  33. void Menu::AddItem(const char* name, void (*function)())
  34. {
  35.   MenuItem* item = new MenuItem;
  36.   item->name = name;
  37.   item->function = function;
  38.   item->next = mHead;
  39.   mHead = item;
  40. }

  41. // 运行菜单系统
  42. void Menu::Run()
  43. {
  44.   display.clear();

  45.   MenuItem* current = mHead;
  46.   char input[32];

  47.   // 遍历链表,打印菜单选项
  48.   int y = 0;
  49.   while (current != nullptr)
  50.   {
  51.     display.setCursor(0, y);
  52.     display.println(current->name);
  53.     y += 10;
  54.     current = current->next;
  55.   }
  56.   display.display();

  57.   // 等待用户输入选择
  58.   HAL_UART_Transmit(&huart2, (uint8_t*)"Enter your choice: ", strlen("Enter your choice: "), HAL_MAX_DELAY);
  59.   HAL_UART_Receive(&huart2, (uint8_t*)input, sizeof(input), HAL_MAX_DELAY);
  60.   input[strcspn(input, "\r\n")] = 0;  // 去除输入末尾的回车符

  61.   // 查找用户输入对应的菜单节点,并执行功能函数
  62.   current = mHead;
  63.   while (current != nullptr)
  64.   {
  65.     if (strcmp(current->name, input) == 0)
  66.     {
  67.       current->function();
  68.       return;
  69.     }
  70.     current = current->next;
  71.   }

  72.   HAL_UART_Transmit(&huart2, (uint8_t*)"Invalid choice.\r\n", strlen("Invalid choice.\r\n"), HAL_MAX_DELAY);
  73. }

  74. // 菜单功能函数1
  75. void Function1()
  76. {
  77.   HAL_UART_Transmit(&huart2, (uint8_t*)"Function 1 executed.\r\n", strlen("Function 1 executed.\r\n"), HAL_MAX_DELAY);
  78. }

  79. // 菜单功能函数2
  80. void Function2()
  81. {
  82.   HAL_UART_Transmit(&huart2, (uint8_t*)"Function 2 executed.\r\n", strlen("Function 2 executed.\r\n"), HAL_MAX_DELAY);
  83. }

  84. int main()
  85. {
  86.   // 初始化硬件和HAL库
  87.   HAL_Init();
  88.   SystemClock_Config();
  89.   MX_GPIO_Init();
  90.   MX_I2C1_Init();
  91.   MX_USART2_UART_Init();

  92.   // 初始化OLED显示屏
  93.   display.init();
  94.   display.setFont(ArialMT_Plain_10);

  95.   // 创建菜单对象,添加菜单选项
  96.   Menu menu;
  97. menu.AddItem("Option 1", Function1);
  98. menu.AddItem("Option 2", Function2);

  99. // 循环执行菜单
  100. while (1)
  101. {
  102. menu.Run();
  103. }
  104. }


 楼主| 小明的同学 发表于 2023-4-26 20:21 | 显示全部楼层
请注意,这里使用了OLED显示屏,需要先初始化并使用SSD1306库进行控制。此外,为了使用串口进行输入输出,还需要初始化并使用USART2库。其他部分与前面给出的示例代码相同。
zwsam 发表于 2024-1-21 09:16 | 显示全部楼层
Wordsworth 发表于 2024-6-6 07:29 | 显示全部楼层

模块电源选购灌封材料的时候,需要注意导热系数要能达到电子部件散热的需求,不过粘接能力不太强
Clyde011 发表于 2024-6-6 08:32 | 显示全部楼层

A、B组分先分别用手动或机械进行充分搅拌,让A、B灌封料充分融合
公羊子丹 发表于 2024-6-6 09:25 | 显示全部楼层

可能击穿开关器件,
万图 发表于 2024-6-6 10:28 | 显示全部楼层

如果想要让它正常工作且不会损坏
Uriah 发表于 2024-6-6 11:31 | 显示全部楼层

前模块电源灌封时用的最多的是加成型有机灌封硅胶
帛灿灿 发表于 2024-6-6 13:27 | 显示全部楼层

电阻属于一个普通的元件
Pulitzer 发表于 2024-6-6 14:30 | 显示全部楼层

并且考虑到TVS相同的尺寸
周半梅 发表于 2024-6-6 16:26 | 显示全部楼层

当异常过压消失,恢复至高阻态
童雨竹 发表于 2024-6-6 19:25 | 显示全部楼层

ESD电压一般超过导通电压
您需要登录后才可以回帖 登录 | 注册

本版积分规则

159

主题

1640

帖子

2

粉丝
快速回复 在线客服 返回列表 返回顶部