每个人,我正在使用,P10 Dot Matrix Display
与Arduino Uno
. 我正在使用此链接中的 P10 库。P10_LED我需要在显示模块上显示一小时倒计时。给定的库使用TimerOne库。因此,对于倒计时,我使用的是MsTimer2库,它使用了 arduino 的 timer2。
当我单独运行这两个库时,我在显示屏上的滚动是完美的,我的定时器库也产生了一个纯 1 秒的中断。现在我所做的是在我的项目中添加了两个库,并且我正在倒计时。但现在突然我的MsTimer2
不产生纯 1 秒。
这是代码。
#include <MsTimer2.h>
#include <TimerOne.h>
#include"SPI.h"
#include <ledP10.h>
LedP10 myled;
uint8_t minute = 0, second = 0, hour = 1;
volatile bool xIsCountDone = false;
volatile bool xIsInterruptOcuured = false;
char time_buff[100];
void setup()
{
Serial.begin(9600);
myled.init(3,4,8,9 ,3);
sprintf((char*)time_buff, " %d%d:%d%d:%d%d", (hour/10), (hour%10),(minute/10), (minute%10),(second/10), (second%10));
Serial.println((char*)time_buff);
myled.showmsg_single_static((char*)time_buff, 0);
xIsInterruptOcuured = false;
//myled.showmsg_single_scroll("this is single led test",2,8,0);
MsTimer2::set(1000, count);
MsTimer2::start();
}
void loop() {
if (xIsInterruptOcuured == true)
{
sprintf((char*)time_buff, " %d%d:%d%d:%d%d", (hour/10), (hour%10),(minute/10), (minute%10),(second/10), (second%10));
Serial.println((char*)time_buff);
myled.showmsg_single_static((char*)time_buff, 0);
xIsInterruptOcuured = false;
}
}
void count(){
second--;
if (second <= 0 || second > 59)
{
second = 59;
minute--;
if (minute <= 0 || minute > 59)
{
minute = 59;
hour--;
if (hour <= 0 || hour > 12)
{
xIsCountDone =true;
}
}
}
Serial.println(millis());
xIsInterruptOcuured = true;
}
在中断例程中,我正在打印millis()
以查看中断发生的毫秒数。结果是这样的。
15:33:02.684 -> 1199
15:33:04.371 -> 2396
15:33:06.059 -> 3592
15:33:07.746 -> 4783
15:33:09.434 -> 5986
15:33:11.121 -> 7181
15: 33:12.855 -> 8379
15:33:14.543 -> 9578
15:33:16.230 -> 10768
15:33:17.918 -> 11974
15:33:19.605 -> 13168 15:33:21.292 -> 14365
15:
3 22.980 -> 15562
15:33:24.667 -> 16751
15:33:26.402 -> 17955
当我只使用MsTimer2
库时,结果是这样的。
15:37:21.241 -> 998
15:37:22.226 -> 1998
15:37:23.257 -> 2998
15:37:24.241 -> 3998
15:37:25.226 -> 4998
15:37:26.257 -> 5998
15: 37:27.241 -> 6998
15:37:28.225 -> 7998
15:37:29.257 -> 8998
15:37:30.241 -> 9998
15:37:31.225 -> 10998
15:37:32.256 -> 11998
15:37: 33.241 -> 12998
15:37:34.225 -> 13998
15:37:35.256 -> 14998
我的猜测,这是因为TimerOne
图书馆而发生的,但我找不到解决方案。其中ledP10.cpp
有一个回调方法timer1
,它包含循环和可能的代码行。但是timer1的中断优先级是否高于timer2?但根据 ATmega328p 数据表,向量号。Timer2 小于 Timer1。这不是意味着 Timer2 具有更高的优先级吗?我的最终目标是倒计时一小时。对此问题的任何帮助或我遗漏的任何其他信息将非常有用,或者除了使用 timer2 中断之外的任何其他解决方案,我们将不胜感激。
问候。
编辑
这是我与 millis() 一起使用的代码,给了我大约 12 分钟的差异。
uint8_t new_buff[100];
unsigned long startMillis; //some global variables available anywhere in the program
unsigned long currentMillis;
const unsigned long period = 1000; //the value is a number of milliseconds
uint8_t minute = 0, second = 0, hour = 1;
char time_buff[100];
void setup()
{
myled.init(3,4,8,9,3);
Serial.begin(9600);
sprintf((char*)time_buff, " %d%d:%d%d:%d%d", (hour/10), (hour%10),(minute/10), (minute%10),(second/10), (second%10));
//Serial.println((char*)time_buff);
myled.showmsg_single_static((char*)time_buff, 0);
startMillis = millis();
}
void loop() {
currentMillis = millis(); //get the current "time" (actually the number of milliseconds since the program started)
if (currentMillis - startMillis >= period) //test whether the period has elapsed
{
Serial.println(millis());
second--;
startMillis = currentMillis; //IMPORTANT to save the start time of the current LED state.
if (second <=0 || second > 59) {
second = 59;
minute--;
if (minute <=0 || minute > 59) {
minute = 59;
hour--;
if (hour <= 0 || hour > 12) {
hour = 0;
}
}
}
sprintf((char*)time_buff, " %d%d:%d%d:%d%d", (hour/10), (hour%10),(minute/10), (minute%10),(second/10), (second%10));
myled.showmsg_single_static((char*)time_buff, 0);
startMillis = currentMillis;
}
}