2023寒假一起练平台(1)- 基于STEP Pico的嵌入式系统学习平台制作一个交通灯控制器
仿真马路上的交通灯的工作状态切换,利用板上的红、黄、绿三种颜色的LED显示道路状态的切换。行人按键时,具有优先功能,延长下一次红灯时间并用蜂鸣器警报提醒车辆。此外,利用显示屏显示行人小人,绿灯行红灯停。
标签
嵌入式系统
MicroPython
树莓派RP2040
2023寒假在家练
交通灯控制器
mint
更新2023-03-29
北京理工大学
604

项目2 - 制作一个交通灯控制器

项目描述

项目介绍:

仿真马路上的交通灯的工作状态切换,利用板上的红、黄、绿三种颜色的LED显示道路状态的切换,行人按键时,具有优先功能。

设计思路:

搭建Thonny集成开发环境,使用microPython语言进行程序开发。由浅入深,首先,实现程序轮流切换LED灯的三种颜色实现模拟道路状态的切换。然后,在能够模拟交通灯切换颜色的基础上,引入K1按键功能,模拟行人发起过马路请求,将下一个红灯的时间延长,以便行人穿过马路。至此,完成项目要求的基本功能。

在项目要求的基本功能之外,我结合日常生活中观察到的交通灯,添加了一些额外功能,使得项目模拟的交通灯更贴近现实:我引入了Buzzer蜂鸣器的功能,在行人按键后的下一个红灯进行警报,模拟行人过马路对过往车辆的提醒功能。除此之外,我还利用了嵌入式系统学习平台上的SSD1306显示屏,模拟红绿灯里的行人小人。

软件流程图:

iGAAAIOCxBCDg8OTUMAAQSKLkAIFX2E6R8CCCDgsAAh5PDg0DQEEECg6AKEUNFHmP4hgAACDgsQQg4PDk1DAAEEii5ACBV9hOkfAggg4LAAIeTw4NA0BBBAoOgChFDRR5j+IYAAAg4LEEIODw5NQwABBIouQAgVfYTpHwIIIOCwACHk8ODQNAQQQKDoAv8PDVd6+eGIwU0AAAAASUVORK5CYII=

硬件介绍

本次2023寒假在家练我使用的是硬禾学堂研发的基于树莓派Pico的嵌入式系统学习平台,该平台专为嵌入式系统学习而设计,其可以通过C/C++以及MicroPython编程来学习嵌入式系统的工作原理和应用,具体可以参考https://www.eetree.cn/project/detail/584

平台由一个树莓派Pico扩展板和一个硬禾版本树莓派Pico核心模块——STEP Pico组成,STEP Pico是一款低成本,高性能的微控制器开发板,具有灵活数字接口(完全兼容Raspberry Pi Pico)。硬件上,采用Raspberry Pi官方自主研发的RP2040微控制器芯片,搭载了ARM Cortex M0+双核处理器,高达133MHz的运行频率,内置了264KB SRAM和2MB闪存,还板载有多达26个多功能的GPIO引脚。软件上,可选择树莓派提供的C/C++SDK,或者使用MicroPython进行开发且配套有完善的开发资料教程,可方便快速入门开发并嵌入到产品中。

除了STEP Pico核心板外,我还用到了以下硬件:

1个按键输入K1;

12个WS2812B RGB三色灯;

1个128*64 OLED显示屏

1个蜂鸣器

实现的功能

1. 实现程序轮流切换LED灯的三种颜色实现模拟道路状态的切换

程序运行后,LED灯的颜色会由5秒红灯变为5秒绿灯,再由5秒绿灯变为2秒黄灯,之后变为5秒红灯,如此循环。为了便于演示,我将红绿灯的时间设置的较短,实际上可以根据实际路况设置。

实际效果如图所示:

运行后LED灯显示红灯,模拟红灯状态。

9k=

根据生活经验,红灯后为绿灯。故红灯5秒后LED灯显示绿灯,模拟绿灯状态

9k=

绿灯5秒后LED灯显示黄灯,模拟黄灯状态,保持2秒后变为红灯继续循环。

9k=

2. 模拟行人发起过马路请求,将下一个红灯的时间延长

轻按如图所示的K1按钮,即为模拟行人想要过马路的场景,在当前车道的绿灯黄灯结束后(不影响正在因绿灯正在通行的车辆),将下一次红灯的长度延长10秒以便行人穿过马路,受限于图片形式,该功能具体效果我将在视频中展示。

2Q==

3. 引入了Buzzer蜂鸣器的功能,在行人按键后的下一个红灯进行警报

在功能2的情境下,行人按下了过马路按钮(K1按钮),车道下一个红灯将延长10秒以便行人通过。与此同时,蜂鸣器将工作,发出报警声提醒司机注意行人通过。

4. 模拟红绿灯里的行人小人

在生活中,人行道的红绿灯通常是一个小人:在红灯时保持静止,在绿灯(黄灯)时向前走动,我利用学习平台上的SSD1306显示屏,进行一个正在通过屏幕的小人的显示,并且随着红灯停下。鉴于此部分为动态过程,我将在视频中进行演示,如图为小人红灯停下和绿灯(黄灯)向前走的示意。

2Q==

2Q==

主要代码片段

1. 实现交通灯颜色变化、按键延长红灯以及蜂鸣的循环

#进入循环,实现交通灯控制
while True:
    #如果行人按下K1按钮,则为True,进入if语句,实现红灯延长
    if k1.value() == True:
        #首先延长红灯时间
        ws2812b.on_all(red)
        state = 0
        #发出蜂鸣声警告车辆注意行人
        for i in range(10):
            for freq in range(880, 1760, 16):
                PWM(Pin(pin_cfg.buzzer)).freq(freq)
                PWM(Pin(pin_cfg.buzzer)).duty_u16(3000)
                time.sleep_ms(6)
            for freq in range(1760, 880, -16):
                PWM(Pin(pin_cfg.buzzer)).freq(freq)
                PWM(Pin(pin_cfg.buzzer)).duty_u16(3000)
                time.sleep_ms(6)
        #警报结束
        PWM(Pin(pin_cfg.buzzer)).deinit()
        
    #红灯5秒
    ws2812b.on_all(red)
    state = 0
    time.sleep(5)
    #鉴于生活中红灯后为绿灯,此处我注释掉了红灯后的黄灯2秒
    #ws2812b.on_all(yellow)
    #time.sleep(2)
    #红灯后绿灯5秒
    ws2812b.on_all(green)
    state = 1
    time.sleep(5)
    #绿灯后黄灯2秒
    ws2812b.on_all(yellow)
    time.sleep(2)

其中,用判断在检测到K1按键被按下后,在下一次循环开始时,将灯的颜色设置为红色,将state置为0(接下来会讲到这时屏幕上的小人停下)。

#如果行人按下K1按钮,则为True,进入if语句,实现红灯延长
    if k1.value() == True:
        #首先延长红灯时间
        ws2812b.on_all(red)
        state = 0

随后进入延长的10秒红灯,此时蜂鸣器进行警报。

#发出蜂鸣声警告车辆注意行人
        for i in range(10):
            for freq in range(880, 1760, 16):
                PWM(Pin(pin_cfg.buzzer)).freq(freq)
                PWM(Pin(pin_cfg.buzzer)).duty_u16(3000)
                time.sleep_ms(6)
            for freq in range(1760, 880, -16):
                PWM(Pin(pin_cfg.buzzer)).freq(freq)
                PWM(Pin(pin_cfg.buzzer)).duty_u16(3000)
                time.sleep_ms(6)
        #警报结束
        PWM(Pin(pin_cfg.buzzer)).deinit()

随后走出(K1被按下)判断,实现红灯绿灯和黄灯的切换,不难注意到,在红灯时,我将state变量置为0,在绿灯和黄灯时,state变量为1,这涉及到接下来显示屏小人的状态(0时静止不动,1时向右移动)。

#红灯5秒
    ws2812b.on_all(red)
    state = 0
    time.sleep(5)
    #鉴于生活中红灯后为绿灯,此处我注释掉了红灯后的黄灯2秒
    #ws2812b.on_all(yellow)
    #time.sleep(2)
    #红灯后绿灯5秒
    ws2812b.on_all(green)
    state = 1
    time.sleep(5)
    #绿灯后黄灯2秒
    ws2812b.on_all(yellow)
    time.sleep(2)

最后,关于K1的判断和红绿黄灯的切换一起作为一个真循环,实现交通灯的控制功能。

 

2. 实现显示屏小人的移动和停止的循环

#用state控制小人走动
    #state=0则小人停下,state=1则小人移动
    global state
    x = -64
    fb = [framebuf.FrameBuffer(frames[fr], 64, 64, framebuf.MONO_HLSB)
          for fr in range(0, 48)]
    while True:
        for fr in range(0, 48):
            if state == 0: continue
            oled.blit(fb[fr], x, 0)
            gc.collect()
            utime.sleep_ms(40)
            if x < 128:
                x = x + 1
            else:
                x = -64
            print(x)
            oled.show()

其中定义了一个全局变量state,在前面提到了state为0和1的两种状态。在state为0时,用continue语句跳出本次循环,实现小人的静止。

        for fr in range(0, 48):
            if state == 0: continue
            oled.blit(fb[fr], x, 0)
            gc.collect()
            utime.sleep_ms(40)
            if x < 128:
                x = x + 1
            else:
                x = -64
            print(x)
            oled.show()

遇到的主要难题及解决方法

我虽然有一些编程基础,但是并没有进行过microPython甚至是python语言的学习,这对于我一开始的编程开展产生了一些困扰。

在老师的指导下,我学会了查阅开源的Gitee代码,并通过查阅python相关函授的意义,帮助我对代码进行理解,逐渐发现编程语言之间的相似性,对知识进行消化吸收,并尝试自己进行了代码的编写。

未来的计划和建议

通过本次2023寒假一起练的机会,我利用基于树莓派Pico的嵌入式系统学习平台实现了基础的交通灯转换,以及行人按钮功能。之后,继续融入了蜂鸣器警报和显示屏显示的功能,让自己的交通灯功能更加丰富。

经过了这次的深入研究,我领会到了学习平台的魅力,收获了乐趣,我也更明白它的强大功能不只于此。在未来,我会结合手上的学习平台,持续关注相关信息,学习有关知识,实现更多有趣的功能!

编程是我非常感兴趣的领域,虽然没有预先学习过microPython,在老师们耐心的指导下,我结合老师分享的开源gitee代码进行学习与尝试,结合学习其他编程语言的经验,努力完成了任务,我也一直想进行python等编程语言的学习,这一次的实践对我来说是一次很棒的鼓励。

最后,感谢硬禾能提供更多的机会,让我们在实践操作的乐趣中汲取知识,我也希望这样的机会多多益善。

附件下载
traffic-mine.py
可编译下载的代码,实现了交通灯控制器,行人按键延长时间蜂鸣警报,和显示屏小人状态显示。
团队介绍
本团队为来自北京理工大学的个人团队,我来自电子信息工程专业,初次接触嵌入式系统,但从microPython的编程中收获了不少乐趣,乐在其中。
团队成员
周文昊
来自北京理工大学的电子信息工程专业,初次接触嵌入式系统,喜欢编程,在microPython的学习中收获了许多乐趣。
评论
0 / 100
查看更多
目录
硬禾服务号
关注最新动态
0512-67862536
info@eetree.cn
江苏省苏州市苏州工业园区新平街388号腾飞创新园A2幢815室
苏州硬禾信息科技有限公司
Copyright © 2023 苏州硬禾信息科技有限公司 All Rights Reserved 苏ICP备19040198号