亿迅智能制造网
工业4.0先进制造技术信息网站!
首页 | 制造技术 | 制造设备 | 工业物联网 | 工业材料 | 设备保养维修 | 工业编程 |
home  MfgRobots >> 亿迅智能制造网 >  >> Manufacturing Technology >> 制造工艺

基于有限状态机的 Arduino 电子表 – YAKINDU Statechart Tools 实战

项目简介

本项目展示如何使用 YAKINDU Statechart Tools (SCT) 图形化建模有限状态机 (FSM),自动生成 C++ 代码并部署到 Arduino,实现功能完整的数字电子表。包含时钟、日期、双闹钟、整点报时、秒表、背光控制等经典功能,通过 LCD Keypad Shield 交互。适合学习状态机建模、代码生成与嵌入式系统设计。

核心工具链

工具用途备注
YAKINDU Statechart Tools图形化状态机建模、仿真、C++ 代码生成非商业免费,官网下载
Eclipse C++ IDE for Arduino (Sloeber)Arduino C++ 开发、编译、上传集成 SCT 生成代码
Arduino IDE备选上传工具

硬件平台

状态机设计核心

功能规格 (参考 David Harel 经典数字表模型)

状态机结构 (层次化设计)

完整状态机图见项目图片(主图、子图拆解)。

LCD Keypad Shield 按键映射

5 个按键共用 A0 模拟口,通过分压电阻产生不同电压:

按键ADC 典型值阈值区间映射事件
Right0< 50onoff
Up~100< 150light_r (秒表启动/圈数)
Down~257< 300light (秒表停止)
Left~411< 550set
Select~640< 850mode
None1023>= 850—

按键消抖与事件上报

#define NONE 0
#define SELECT 1
#define LEFT 2
#define DOWN 3
#define UP 4
#define RIGHT 5

int oldState = NONE;

static int readButton() {
  int result = analogRead(0);
  if (result < 50) return RIGHT;
  if (result < 150) return UP;
  if (result < 300) return DOWN;
  if (result < 550) return LEFT;
  if (result < 850) return SELECT;
  return NONE;
}

static void raiseEvents() {
  int buttonPressed = readButton();
  delay(80);                // 消抖延时
  oldState = buttonPressed;
  if (oldState != NONE && readButton() == NONE) { // 检测下降沿 (释放)
    switch (oldState) {
      case SELECT: stateMachine->getSCI_Button()->raise_mode(); break;
      case LEFT:   stateMachine->getSCI_Button()->raise_set(); break;
      case DOWN:   stateMachine->getSCI_Button()->raise_light(); break;
      case UP:     stateMachine->getSCI_Button()->raise_light_r(); break;
      case RIGHT:  stateMachine->getSCI_Button()->raise_onoff(); break;
    }
  }
}

主程序框架

DigitalWatch* stateMachine = new DigitalWatch();
CPPTimerInterface* timer_sct = new CPPTimerInterface();
DisplayHandler* displayHandler = new DisplayHandler();

void setup() {
  stateMachine->setSCI_Display_OCB(displayHandler); // 注册显示回调
  stateMachine->setTimer(timer_sct);                // 注册定时器接口
  stateMachine->init();
  stateMachine->enter();
}

long current_time = 0, last_cycle_time = 0;

void loop() {
  raiseEvents();                                    // 1. 处理按键事件
  last_cycle_time = current_time;
  current_time = millis();
  timer_sct->updateActiveTimer(stateMachine,        // 2. 更新定时器 (驱动 every 100ms)
                               current_time - last_cycle_time);
  stateMachine->runCycle();                         // 3. 运行状态机周期
}

DisplayHandler 关键实现

class DisplayHandler : public sc::io::Display_OCB {
  LiquidCrystal lcd;
public:
  DisplayHandler() : lcd(8,9,4,5,6,7) {} // LCD Keypad Shield 引脚
  void updateLCD(int first, int second, int third, const char* text) override {
    lcd.setCursor(0,0);
    // 格式化显示 HH:MM:SS 或 文本模式
    if (text) { lcd.print(text); }
    else {
      char buf[17];
      sprintf(buf, "%02d:%02d:%02d", first, second, third);
      lcd.print(buf);
    }
  }
};

获取与运行示例

  1. 安装 YAKINDU SCT (非商业免费,30 天试用后需申请免费许可)
  2. File → New → Example → YAKINDU Statechart Examples → Arduino - Digital Watch (C++)
  3. 连接硬件,使用 Sloeber/Eclipse 或 Arduino IDE 编译上传

扩展与学习价值

资源链接

制造工艺

  1. 用 Arduino 打造绚丽显示器 Ambilight 系统
  2. Arduino 数字骰子:LCD 显示随机点数的电子骰子
  3. 用 Arduino 制作超声波悬浮装置:分步指南
  4. Arduino 与智能手机打造智能电压表——简单易做的 DIY 项目
  5. 基于 Arduino 与 MAX30100 的实时物联网心率监测系统
  6. Arduino Uno WiFi 网页服务器:通过浏览器控制 LED 开关
  7. 自制 Arduino 电子宠物「Tamaguino」:复刻经典 Tamagotchi 全攻略
  8. DIY Arduino 智能手表:打造属于你的 Apple Watch 风格腕表
  9. Arduino 自动化 Chrome 恐龙游戏 - LDR 光敏电阻 + Python 实现全自动跳跃
  10. 使用 Arduino Nano 和 RDA8057M 制作紧凑型 FM 收音机
  11. 无线Arduino编程盾:HC-05蓝牙模块实现免USB线烧录
  12. 设计有限状态机:从概念到实现