Arduino 使用Metor库 简单实现多线程编程

欢迎关注「凌顺实验室」微信公众号

 

 

 

 

 

 

 

当LED 1 在每隔一秒闪烁着的时候,LED2 在每隔 0.5 秒闪烁

又或者控制两个舵机转动指定角度,同时进行

 

有想过要怎么实现这样的程序吗?

 

这次带来的是,多线程的实例方法

 

实验效果

同时控制两个LED 分别按照1秒和0.5秒闪烁。

LED1 每隔1秒亮,每隔1秒灭

LED2 每隔0.5秒亮,每隔0.5秒灭

 

同时,同时,同时进行,这就是多任务,多线程的作用,可以实现同时。

但是在细化到很小很小的时间单位,在单片机中,其实也是一条一条指令的分别执行,只是时间间隔太小,我们看到的好像是同时进行而已。

 

BOM表

Arduino UNO    *1

LED灯                *1-2

条线若干

(如果怕烧LED,可以添加一些电阻)

 

接线

 

 

开源程序

 

本实验使用METOR库,下载地址为

https://github.com/thomasfredericks/Metro-Arduino-Wiring

下载后请正确安装到库中

 

 

/*    
    simpleMultiTask.ino
    Copyright (c) 2016 ItKindaWorks All right reserved.
    github.com/ItKindaWorks
    This file is part of simpleMultiTask
    simpleMultiTask is free software: you can redistribute it and/or modify
    it under the terms of the GNU General Public License as published by
    the Free Software Foundation, either version 3 of the License, or
    (at your option) any later version.
    simpleMultiTask is distributed in the hope that it will be useful,
    but WITHOUT ANY WARRANTY; without even the implied warranty of
    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    GNU General Public License for more details.
    You should have received a copy of the GNU General Public License
    along with simpleMultiTask.  If not, see <http://www.gnu.org/licenses/>.
*/

#include <Metro.h> 

const int blinkPin1 = 13; //定义 LED 引脚13
const int blinkPin2 = 12; //定义 LED 引脚12

boolean blink1State = false;   //定义 blink1State 为false状态
boolean blink2State = false;   //定义 blink2State 为false状态  

Metro blink1Metro = Metro(100);   //把 blink1Metro 实例化 Metro 对象 ,并设置间隔时间
Metro blink2Metro = Metro(0);     //把 blink2Metro 实例化 Metro 对象 ,并设置间隔时间


void setup(){
  pinMode(blinkPin1 , OUTPUT);   //设置blinkPin1 为输出模式
  pinMode(blinkPin2 , OUTPUT);   //设置blinkPin2 为输出模式
}


void loop(){

  if(blink1Metro.check()){  //检查blink1Metro间隔(我的理解是计时器每隔100毫秒就会返回true,就执行以下程序)
    blink1State = !blink1State;   //反转blink1State的逻辑真或假(false or true)
    digitalWrite(blinkPin1, blink1State); //数字引脚,设置为blink1State的状态
  }


  if(blink2Metro.check()){
    blink2State = !blink2State;
    digitalWrite(blinkPin2, blink2State);
  }
  
}

 

 

 

 

 

程序实现思路讲解

 

Metro 库的一些函数

 

Metro()     

 

Instantiates a Metro object with a default interval of 1000 milliseconds.

实例化一个 Metro 对象 ,设置默认1000毫秒间隔时间

Metro(unsigned long interval)

 

Instantiates a Metro object with a set interval in milliseconds.

实例化一个 Metro 对象,设置间隔时间(单位为毫秒)。

byte check() 

 

Because Metro does not use interrupts, you have to "check" the Metro regularly (as often as possible). check() returns true if the interval has lapsed. Returns false if not.

因为Metro不使用中断,所以你必须定期(经常地)检查Metro。 如果间隔失效,则check()返回true。 如果没有则返回false。

void interval(unsigned long interval)

 

Changes the interval in milliseconds.

更改间隔时间(以毫秒为单位)。

void reset()

 

Restarts/resets the Metro. Often a good idea if you change the interval.

重新启动/重置。 如果您更改间隔时间通常是一个好主意。

 

  • 7
    点赞
  • 69
    收藏
    觉得还不错? 一键收藏
  • 7
    评论
这款基于Metro Mini微控制器的时钟是一款极简时计,可以庆祝而不是隐藏其组件。这是一个简单的构建,电子化,你可以按照自己喜欢的方式存放和显示它! 您可以将它构建到面包板,perma-proto板上,甚至可以在没有板的情况下连接它。 材料: Metro迷你微控制器 X1 DS3231 X1 4位7段显示器 X1 5V USB电源 X1 面包板 X1 可选: Perma Proto板,或 母头针条,x2 彩色滤胶,胶带 时钟电路: 您可以在技术上仅使用Metro Mini和显示器制作时钟,但每次断电或复位时都需要重新设置时钟。它也不是非常准确。这就是实时时钟模块的用武之地。它有一个纽扣电池备份,比Metro Mini上的水晶更准确。 编码时钟: 首先,确保您习惯使用Arduino IDE将代码上传到Metro Mini。 接下来,您将向Arduino IDE添加三个, 转到 草图>包含>管理...以打开 管理器 。 在这里,搜索并安装这三个: Adafruit GFX图书馆 Adafruit的RTCLib Adafruit LED背包图书馆 现在,您已准备好上传时钟代码。复制附件中的代码,然后将其粘贴到新的Arduino草图中。将草图保存为metroMiniClock.ino,然后将其上传到您的电路板。 确保在 工具 - >板 菜单下选择了Adafruit Metro ,并在 工具 - >端口 菜单下 选择Metro Mini的串行端口。然后按上传按钮或单击 草图 - >上传 项目将代码发送到电路板。 上传后,Metro Minimalist Clock将启动,并显示时间!您现在可以从计算机上拔下USB电缆,并将其插入墙上适配器 - 它只需要从计算机上获取一次时间,从现在开始它将保持RTC模块的正确时间。即使拔下电源插头,RTC时钟的电池也会保持稳定。 如果您愿意,可以通过轻微更改草图代码来更改时钟是以24小时还是12小时时间格式显示时间。默认情况下,时钟使用12小时格式。
ESP32可以通过Arduino IDE进行编程,并且支持多线编程。以下是一个简单的示例: ``` #include <Arduino.h> #include <FreeRTOS.h> #include <task.h> TaskHandle_t Task1Handle; TaskHandle_t Task2Handle; void Task1(void *pvParameters) { for (;;) { Serial.println("Task 1 is running"); vTaskDelay(1000 / portTICK_PERIOD_MS); } } void Task2(void *pvParameters) { for (;;) { Serial.println("Task 2 is running"); vTaskDelay(2000 / portTICK_PERIOD_MS); } } void setup() { Serial.begin(9600); xTaskCreate(Task1, "Task 1", 10000, NULL, 1, &Task1Handle); xTaskCreate(Task2, "Task 2", 10000, NULL, 1, &Task2Handle); } void loop() { // This function should not be used in a multi-tasking environment. // It is provided for compatibility with existing Arduino code that // may not have been written with multi-tasking in mind. } ``` 在这个示例中,我们创建了两个任务Task1和Task2。每个任务都是一个无限循环,分别在1秒和2秒的间隔内打印一条消息。在setup函数中,我们使用xTaskCreate函数创建了两个任务,并指定了任务的名称、堆栈大小和任务句柄。在loop函数中,我们没有编写任何代码,因为在多线编程中,loop函数不再需要使用。相反,我们将任务的代码放在Task1和Task2函数中,并使用vTaskDelay函数来指定任务的周期。最后,我们使用Serial.begin函数初始化串口,以便我们可以查看任务输出的消息。 在多线编程中,需要特别注意内存管理和同步问题。由于ESP32具有多个处理器核心,因此可以将任务分配到不同的核心上,以实现更好的性能和并发性。您可以使用FreeRTOS API来管理任务和同步对象,例如互斥量和信号量。

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值