arduino定时器1 TimerOne 一篇搞懂

目录

0.arduino uno的定时器:

1.TimerOne 说明

2.10us中断,定时1s的demo.

3.TimerOne的PWM的使用

        TimerOne的PWM有什么优势和区别呢?

        实现呼吸灯的demo(加上定时器)

极其简单的呼吸灯demo,更易理解TimerOne的PWM

4.0PWM核心代码


0.arduino uno的定时器:

timer0:一个被Arduino的delay(), millis()和micros()使用的8位定时器
timer1:一个被Arduino的Servo()库使用的16位定时器
timer2:一个被Arduino的Tone()库使用的8位定时器

"Arduino Mega"板有另外三个可使用的timer(3,4,5)

1.TimerOne 说明

        Timer1是一个16位定时器

        如果你使用了 Timer1 库 (TimerOne 库), pin 9 和 pin 10 就不能再用做 PWM 输出了!
 timer1 的PWM通道是pin 9 和 pin 10

        注意 Servo.h 库使用定时器 timer1,所以, 用了 TimerOne 也不能再用 Servo.h 库了

技术文档: TimerOne & Timer三个Arduino库

经测试,TimerOne 的精度可以达到10us.下面给出一个demo方便大家理解.

2.10us中断,定时1s的demo.

        10us触发一次中断 累加100000次 也就是1s将标志位置1,实现1s执行一次命令.

        其中里面的ms_tick本来想设置int型,arduino中的int型是2字节的 范围是-32768~32767.

Arduino常用数据类型简介 – 太极创客

        累加100000次超量程了,这里采用long类型.

        关于volatile的运用,道友们可以去单独了解一下.

Timer1.initialize(10); //设置定时器的周期 ,这里是10us

Timer1.attachInterrupt(Interrupt_callback); // 定时器的中断回调函数

Timer1.setPeriod(microseconds);//设置定时器的周期

#include <TimerOne.h>

volatile long ms_tick=0,ms_tick_flag=0;
void setup(void)
{
  pinMode(13, OUTPUT);
  Timer1.initialize(10);//精确度10us 
  Timer1.attachInterrupt(Interrupt_callback); // 定时器的中断回调函数
  Serial.begin(115200);
}
void Interrupt_callback(void)
{
  if(ms_tick_flag==0)
  { 
    ms_tick++;
    if(ms_tick>100000)//这里10*100000 也就是1s标志位置1.
    {
      ms_tick=0;
      ms_tick_flag=1;
    }
  }
}
void loop(void)
{
  if(ms_tick_flag==1)
  {
    static boolean output = HIGH;
    digitalWrite(13,output);
    output =!output;

    Serial.println("test");
    ms_tick_flag=0;
  }
}

3.TimerOne的PWM的使用

Timer1.pwm(pin,duty,Frequency);    //PWM初始化,第二个变量是 “duty” 是从 0 到 1023 ,通过改变它来改变占空比,第三个频率,可以不填.  Timer1.initialize(10);//这个是设置周期,也相当于设置频率

Timer1.setPwmDuty(pin,duty) ;  //设置PWM的占空比,不需要再重新初始化引脚,相较于Timer1.pwm速度快

Timer1.disablePwm(pin);  //关闭PWM

        TimerOne的PWM有什么优势和区别呢?

        简单的操作方法.一行代码就可设定PWM频率

        arduino的analogWrite();也能实现PWM的功能,主要原因是arduino自带的analogWrite()函数的PWM的默认频率:

timer0 控制 pin 5, pin 6, PWM 频率 976.5625Hz, duty cycle可以 2/256 ~ 255/256 (对应 1 到254);
timer1 控制 pin 9, pin 10, PWM 频率 490.196Hz, duty cycle 可以 1/255 ~ 254/255(对应 1 到254);
timer2 控制 pin 11, pin 3, PWM 频率 与 duty cycle 跟 timer1 控制的相同 !

        Timer1.pwm(pin,duty,Frequency);可以设定PWM的频率,对某些设备如步进电机对脉冲信号有要求.

        实现呼吸灯的demo(加上定时器)

#include <TimerOne.h>

volatile long ms_tick=0,ms_tick_flag=0;
void setup(void)
{
  Timer1.initialize(10);//精确度10us
  Timer1.pwm(9,0);
  Timer1.attachInterrupt(Interrupt_callback); // 定时器的中断回调函数
  Serial.begin(115200);
}
void Interrupt_callback(void)
{
  if(ms_tick_flag==0)
  { 
    ms_tick++;
    if(ms_tick>100)//这里1ms触发一次  1秒内实现一个上升期 2s完成亮灭.
    {
      ms_tick=0;
      ms_tick_flag=1;
    }
  }
}
void loop(void)
{
  if(ms_tick_flag==1)
  {
    static int i=0,flag=0;
    if(i<=0)
      flag=0;
    if(i>=1023)
      flag=1;

    if(flag==0)
      i++;
    else
      i--;
    
    Timer1.setPwmDuty(9, i); // setup pwm on pin 9, 50% duty cycle
    ms_tick_flag=0;
  }
}

极其简单的呼吸灯demo,更易理解TimerOne的PWM

#include <TimerOne.h>

volatile long ms_tick=0,ms_tick_flag=0;
void setup(void)
{
  Timer1.initialize(10);//精确度10us
  Timer1.pwm(9,0);
  Serial.begin(115200);
}

void loop(void)
{
    static int i=0,flag=0;
    //这两个if语句主要是为了实现亮灭亮交替
    if(i<=0)
      flag=0;
    if(i>=1023)
      flag=1;

    if(flag==0)
      i++;
    else
      i--;
    delay(1);
    Timer1.setPwmDuty(9, i); // setup pwm on pin 9, 50% duty cycle
  
}

4.0PWM核心代码

#include <TimerOne.h>
 
volatile long ms_tick=0,ms_tick_flag=0;
void setup(void)
{
  Timer1.initialize(10);//精确度10us
  Timer1.pwm(9,0);//0-1023 控制占空比
  Serial.begin(115200);
}
 
void loop(void)
{

  
}

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值