【雕爷学编程】MicroPython手册之 ESP32 特定端口库 esp32.RMT()

在这里插入图片描述

MicroPython是为了在嵌入式系统中运行Python 3编程语言而设计的轻量级版本解释器。与常规Python相比,MicroPython解释器体积小(仅100KB左右),通过编译成二进制Executable文件运行,执行效率较高。它使用了轻量级的垃圾回收机制并移除了大部分Python标准库,以适应资源限制的微控制器。

MicroPython主要特点包括:
1、语法和功能与标准Python兼容,易学易用。支持Python大多数核心语法。
2、对硬件直接访问和控制,像Arduino一样控制GPIO、I2C、SPI等。
3、强大的模块系统,提供文件系统、网络、图形界面等功能。
4、支持交叉编译生成高效的原生代码,速度比解释器快10-100倍。
5、代码量少,内存占用小,适合运行在MCU和内存小的开发板上。
6、开源许可,免费使用。Shell交互环境为开发测试提供便利。
7、内置I/O驱动支持大量微控制器平台,如ESP8266、ESP32、STM32、micro:bit、掌控板和PyBoard等。有活跃的社区。

MicroPython的应用场景包括:
1、为嵌入式产品快速构建原型和用户交互。
2、制作一些小型的可 programmable 硬件项目。
3、作为教育工具,帮助初学者学习Python和物联网编程。
4、构建智能设备固件,实现高级控制和云连接。
5、各种微控制器应用如物联网、嵌入式智能、机器人等。

使用MicroPython需要注意:
1、内存和Flash空间有限。
2、解释执行效率不如C语言。
3、部分库函数与标准版有差异。
4、针对平台优化语法,订正与标准Python的差异。
5、合理使用内存资源,避免频繁分配大内存块。
6、利用原生代码提升速度关键部位的性能。
7、适当使用抽象来封装底层硬件操作。

总体来说,MicroPython让Python进入了微控制器领域,是一项重要的创新,既降低了编程门槛,又提供了良好的硬件控制能力。非常适合各类物联网和智能硬件的开发。
在这里插入图片描述

MicroPython的esp是指针对ESP8266和ESP32芯片的MicroPython固件和相关软件库。ESP8266和ESP32是一类广泛应用于物联网和嵌入式系统的低成本、低功耗的Wi-Fi和蓝牙模块。MicroPython的esp为这两种芯片提供了高级的脚本编程环境,使开发者能够使用Python语言进行快速原型设计和开发。

ESP8266:是一款低成本、低功耗的Wi-Fi模块/芯片,由Espressif Systems开发。它内置了TCP/IP协议栈,可以用于连接互联网,并具备较强的处理能力。MicroPython的esp提供了针对ESP8266的固件和相关软件库,使开发者可以使用MicroPython语言进行ESP8266应用的开发。

ESP32:是Espressif Systems推出的一款高度集成的Wi-Fi和蓝牙模块/芯片,与ESP8266相比,它具备更强大的处理能力、更多的外设接口和更多的内存。MicroPython的esp也提供了针对ESP32的固件和相关软件库,使开发者可以使用MicroPython语言进行ESP32应用的开发。

MicroPython的esp固件:是专门针对ESP8266和ESP32芯片的MicroPython固件版本。这些固件经过了针对性的优化,使得它们可以在ESP8266和ESP32上运行,并提供了与硬件交互、网络通信和外设控制等功能的API。

软件库:MicroPython的esp还提供了一系列与ESP8266和ESP32硬件相关的软件库,用于简化和加速开发过程。这些软件库提供了丰富的功能接口,涵盖了Wi-Fi、蓝牙、GPIO(通用输入输出)、I2C、SPI、PWM等常用的硬件和通信协议,使开发者可以方便地访问和控制硬件资源。
在这里插入图片描述

MicroPython的esp32.RMT()是一个用于在ESP32模块上控制RMT(Remote Control)模块的功能。它有以下主要特点、应用场景和注意事项:

主要特点:

esp32.RMT()是一个类,它的构造函数可以创建一个表示RMT通道的对象,并配置相关的参数,如引脚、时钟分频、空闲电平、载波频率等。
esp32.RMT()对象可以使用write_pulses()方法来发送一系列的高低电平脉冲,或者使用read_pulses()方法来接收一系列的高低电平脉冲。
esp32.RMT()对象可以使用loop()方法来设置是否循环发送或接收脉冲,或者使用wait_done()方法来等待发送或接收完成。
esp32.RMT()对象可以使用deinit()方法来释放RMT通道和引脚资源。

应用场景:

esp32.RMT()的功能最初设计用于发送和接收红外遥控信号,因此可以用于实现红外遥控器或红外接收器的功能,例如控制电视机、空调等设备。
esp32.RMT()的功能由于设计灵活且脉冲生成非常准确(低至12.5ns),因此还可以用于传输或接收许多其他类型的数字信号,例如WS2812 LED灯带、DHT11温湿度传感器、NEC编码等。
esp32.RMT()的功能还可以用于实现一些需要高速或精确时序的应用,例如PWM(脉冲宽度调制)、PPM(脉冲位置调制)、PCM(脉冲编码调制)等。

注意事项:

esp32.RMT()的功能需要注意与其他占用RMT通道或引脚的功能的冲突,例如SPI、I2C、UART等。
esp32.RMT()的功能需要注意与其他占用CPU时间或内存资源的功能的影响,例如网络通信、文件系统、垃圾回收等。
esp32.RMT()的功能需要注意与其他需要中断服务或定时器服务的功能的协调,例如机器定时器、机器中断等。

以下是几个使用MicroPython的esp32.RMT()功能的实际运用程序案例:

案例一:使用esp32.RMT()来发送一个NEC编码的红外遥控信号,控制电视机开关。

# 导入必要的模块
import esp32
from machine import Pin

# 定义一个NEC编码函数,将命令和地址转换为高低电平脉冲序列
def nec_encode(cmd, addr):
    # 定义NEC编码中不同位对应的高低电平脉冲长度(单位为微秒)
    # 0: 562us low, 562us high
    # 1: 562us low, 1687us high
    # start: 9000us low, 4500us high
    # stop: 562us low, high until next start
    pulse0 = (562, 562)
    pulse1 = (562, 1687)
    pulse_start = (9000, 4500)
    pulse_stop = (562,)
    
    # 定义一个空列表,用于存储高低电平脉冲序列
    pulses = []
    
    # 添加起始位
    pulses += pulse_start
    
    # 添加地址位,共16位,先低字节后高字节,先低位后高位
    for i in range(16):
        # 判断地址的第i位是0还是1,并添加相应的脉冲
        if addr & (1 << i):
            pulses += pulse1
        else:
            pulses += pulse0
    
    # 添加命令位,共16位,先低字节后高字节,先低位后高位
    for i in range(16):
        # 判断命令的第i位是0还是1,并添加相应的脉冲
        if cmd & (1 << i):
            pulses += pulse1
        else:
            pulses += pulse0
    
    # 添加结束位
    pulses += pulse_stop
    
    # 返回高低电平脉冲序列
    return pulses

# 定义一个发送红外遥控信号的函数,使用esp32.RMT()对象来发送高低电平脉冲序列
def ir_send(pulses):
    # 创建一个esp32.RMT()对象,使用第0个通道,绑定到第18号引脚
    rmt = esp32.RMT(0, pin=Pin(18))
    # 调用write_pulses()方法来发送高低电平脉冲序列,start参数为True表示立即发送
    rmt.write_pulses(pulses, start=True)
    # 调用wait_done()方法来等待发送完成
    rmt.wait_done()
    # 调用deinit()方法来释放RMT通道和引脚资源
    rmt.deinit()

# 定义一个控制电视机开关的函数,使用NEC编码中的0x00FF为命令,0x0000为地址
def tv_toggle():
    # 调用nec_encode()函数来生成NEC编码的高低电平脉冲序列
    pulses = nec_encode(0x00FF, 0x0000)
    # 调用ir_send()函数来发送红外遥控信号
    ir_send(pulses)

# 调用tv_toggle()函数来控制电视机开关
tv_toggle()

案例二:使用esp32.RMT()来接收一个DHT11温湿度传感器的数字信号,并解析出温度和湿度的值。

# 导入必要的模块
import esp32
from machine import Pin

# 定义一个读取DHT11传感器数据的函数,使用esp32.RMT()对象来接收数字信号,并返回温度和湿度的值
def dht11_read(pin):
    # 创建一个esp32.RMT()对象,使用第1个通道,绑定到指定的引脚
    rmt = esp32.RMT(1, pin=Pin(pin))
    
    # 生成一个开始信号,即拉低数据线18毫秒,然后拉高40微秒
    start_signal = (0, 18000, 1, 40)
    
    # 发送开始信号,start参数为True表示立即发送
    rmt.write_pulses(start_signal, start=True)
    
    # 等待发送完成
    rmt.wait_done()
    
    # 切换到接收模式,准备接收传感器数据
    rmt.init(rx_idle_thresh=50)
    
    # 接收40个数据位,每个数据位由50微秒的低电平和不同长度的高电平组成,
    # 高电平长度为26-28微秒表示0,长度为70微秒表示1,
    # 返回一个元组列表,每个元组包含两个整数,分别表示高低电平的时长(单位为微秒)
    data_pulses = rmt.read_pulses(40)
    
    # 释放RMT通道和引脚资源
    rmt.deinit()
    
    # 定义一个空列表,用于存储数据位的值(0或1)
    data_bits = []
    
    # 遍历接收到的数据脉冲
    for low, high in data_pulses:
        # 判断高电平时长是否在合理范围内(50-90微秒),如果不是,则返回错误提示
        if not 50 <= high <= 90:
            return 'Invalid pulse length.'
        # 如果高电平时长在26-28微秒之间,则认为是0,并添加到数据位列表中
        elif 26 <= high <= 28:
            data_bits.append(0)
        # 如果高电平时长在70微秒左右,则认为是1,并添加到数据位列表中
        elif high >= 70:
            data_bits.append(1)
    
    # 判断数据位列表的长度是否为40,如果不是,则返回错误提示
    if len(data_bits) != 40:
        return 'Invalid bit count.'
    
    # 将数据位列表分割为5个字节,分别表示湿度整数部分、湿度小数部分、温度整数部分、温度小数部分和校验和
    humidity_int, humidity_dec, temp_int, temp_dec, checksum = [int(''.join(map(str, data_bits[i:i+8])), 2) for i in range(0, 40, 8)]
    
    # 计算前四个字节的和,并与校验和比较,如果不相等,则返回错误提示
    if (humidity_int + humidity_dec + temp_int + temp_dec) & 0xFF != checksum:
        return 'Invalid checksum.'
    
    # 计算湿度和温度的值,并返回结果
    humidity = humidity_int + humidity_dec / 10
    temp = temp_int + temp_dec / 10
    return humidity, temp

# 调用dht11_read()函数,并打印出结果
print(dht11_read(19))

案例三:使用machine.Timer类来创建一个定时器中断,并在IRAM中执行一个回调函数,该回调函数会在每次中断时打印出一个计数值。

# 导入必要的模块
import machine

# 定义一个全局变量,用于存储计数值
count = 0

# 定义一个回调函数,并使用@micropython.viper
# 装饰器来指示使用native code emitter,并使用@micropython.alloc_emergency_exception_buf(size)
# 装饰器来分配一些IRAM空间,用于处理异常
@micropython.viper
@micropython.alloc_emergency_exception_buf(256)
def callback(timer):
    # 声明全局变量
    global count
    # 将计数值加一,并打印出结果
    count += 1
    print(count)

# 创建一个定时器对象,使用第0号定时器,设置为周期模式
timer = machine.Timer(0, mode=machine.Timer.PERIODIC)
# 初始化定时器,设置周期为1000毫秒,设置回调函数为callback
timer.init(period=1000, callback=callback)

这是一个使用MicroPython的esp32.HEAP_EXEC功能的实际运用程序案例,它可以在ESP32模块上实现一个定时器中断,并在IRAM中执行一个回调函数。该回调函数会在每次中断时打印出一个计数值,从而展示了esp32.HEAP_EXEC功能的用法和效果。

案例四:发送红外信号:

import machine
import esp32

# 初始化RMT通道
rmt = machine.RMT(0, pin=machine.Pin(14), clock_div=80)

# 创建红外信号模式
carrier_freq = 38000
signal = esp32.RMT.Signal(carrier_freq, [1, 0, 1, 0, 1, 0, 1, 0])

# 发送红外信号
rmt.write_pulses(signal, start_level=0)

在这个例子中,我们使用esp32.RMT()初始化一个RMT通道。我们通过传递通道号、引脚和时钟分频器来创建一个machine.RMT对象。然后,我们使用esp32.RMT.Signal()创建一个红外信号模式,其中包含载波频率和脉冲序列。最后,我们使用write_pulses()方法将红外信号发送出去。

案例五:接收红外信号:

import machine
import esp32

# 初始化RMT通道
rmt = machine.RMT(0, pin=machine.Pin(14), clock_div=80)

# 启用接收模式
rmt_rx = rmt.rx_start(20)

# 接收红外信号
while True:
    if rmt.rx_waiting():
        pulses = rmt.read_pulses()
        print("接收到的脉冲序列:", pulses)

在这个例子中,我们使用esp32.RMT()初始化一个RMT通道。我们通过传递通道号、引脚和时钟分频器来创建一个machine.RMT对象。然后,我们使用rx_start()方法启用接收模式,并指定接收缓冲区的大小。接下来,我们使用一个循环来检查是否有接收到的红外信号。如果有,我们使用read_pulses()方法读取脉冲序列,并打印出来。

案例六:发送脉冲序列:

import machine
import esp32

# 初始化RMT通道
rmt = machine.RMT(0, pin=machine.Pin(14), clock_div=80)

# 创建自定义脉冲序列
pulses = [10, 5, 20, 10, 15, 5, 30, 20]

# 发送脉冲序列
rmt.write_pulses(pulses, start_level=0)

在这个例子中,我们使用esp32.RMT()初始化一个RMT通道。我们通过传递通道号、引脚和时钟分频器来创建一个machine.RMT对象。然后,我们创建一个自定义的脉冲序列,其中包含一系列脉冲的持续时间。最后,我们使用write_pulses()方法将脉冲序列发送出去。

案例七:发送红外信号:

import esp32
from machine import Pin
from esp32 import RMT

# 设置红外遥控器发射器引脚
ir_pin = Pin(14, Pin.OUT, Pin.PULL_DOWN)  # 根据实际引脚连接情况设置

# 创建 RMT 实例
rmt = RMT(0, pin=ir_pin, clock_div=80)  # 根据实际需求设置 RMT 控制器编号和时钟分频

# 定义红外信号数据
data = [0x00, 0xFF, 0x00]  # 根据实际需要定义红外信号的数据

# 发送红外信号
rmt.write_pulses(data, start_level=1)

案例八: 接收红外信号:

import esp32
from machine import Pin
from esp32 import RMT

# 设置红外遥控器接收器引脚
ir_pin = Pin(15, Pin.IN, Pin.PULL_UP)  # 根据实际引脚连接情况设置

# 创建 RMT 实例
rmt = RMT(1, pin=ir_pin)

# 启用红外遥控器接收功能
rmt.rx_start()

# 等待接收到红外信号
while not rmt.rx_received():
    pass

# 获取接收到的红外信号数据
data = rmt.rx_get_values()
print("接收到的红外信号:", data)

案例九:设置红外信号参数:

import esp32
from machine import Pin
from esp32 import RMT

# 设置红外遥控器发射器引脚
ir_pin = Pin(14, Pin.OUT, Pin.PULL_DOWN)  # 根据实际引脚连接情况设置

# 创建 RMT 实例
rmt = RMT(0, pin=ir_pin, clock_div=80)  # 根据实际需求设置 RMT 控制器编号和时钟分频

# 设置红外信号的重复次数
rmt.loop_count(3)  # 设置红外信号重复发送 3 次

# 设置红外信号的占空比
rmt.carrier_duty_percent(50)  # 设置红外信号的占空比为 50%

# 定义红外信号数据
data = [0x00, 0xFF, 0x00]  # 根据实际需要定义红外信号的数据

# 发送红外信号
rmt.write_pulses(data, start_level=1)

这些示例程序展示了如何使用 esp32.RMT() 类来控制 ESP32 的红外遥控器发射和接收功能。根据实际需求,您可以调整和扩展这些示例程序,以满足特定的红外遥控应用场景。

在这里插入图片描述

  • 2
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
MicroPython ESP32端口中,您可以使用FreeRTOS API来管理任务和调度。以下是一些常用的FreeRTOS API: 1. `xTaskCreate`: 创建一个新任务。 ```python import _thread def task_function(): print("Task Running...") _thread.start_new_thread(task_function, ()) ``` 2. `vTaskDelay`: 暂停任务的执行一段时间。 ```python import time def task_function(): while True: print("Task Running...") time.sleep(1) # 暂停1秒 _thread.start_new_thread(task_function, ()) ``` 3. `xSemaphoreCreateBinary`: 创建一个二进制信号量。 ```python import _thread import time from micropython import const from machine import Pin from esp32 import RMT BUTTON_PIN = const(4) RMT_PIN = const(17) BUTTON_SEMAPHORE = None def button_isr(pin): global BUTTON_SEMAPHORE if BUTTON_SEMAPHORE is not None: BUTTON_SEMAPHORE.release() rmt = RMT(channel=0, pin=RMT_PIN, clock_div=80) button = Pin(BUTTON_PIN, Pin.IN, Pin.PULL_UP) button.irq(trigger=Pin.IRQ_FALLING, handler=button_isr) BUTTON_SEMAPHORE = _thread.allocate_lock() BUTTON_SEMAPHORE.acquire() while True: if BUTTON_SEMAPHORE.acquire(False): print("Button Pressed!") rmt.write_pulses([9000, 4500]) time.sleep_ms(100) ``` 在这个示例中,我们创建了一个二进制信号量,当按钮被按下时释放该信号量。在主循环中,我们等待信号量被释放,然后发送一个红外信号。 这只是MicroPython ESP32端口中可用的一小部分FreeRTOS API。您可以使用其他API来创建和管理任务、信号量、消息队列等等。请参考FreeRTOS文档以获取更多信息。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

驴友花雕

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值