⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 消抖的另一种方法(avr).txt

📁 430的LCD驱动电路和简单的消抖程序
💻 TXT
字号:
贴上实验二中的2个参考代码 

在实验板上设计一个采用外部中断方式的6位数码管(分、秒、1%秒各占2位)显示的简易秒表系统。可以先使用CVAVR中的程序生成向导功能进行配置,然后在它生成的程序框架基础上完成定时器中断部分程序。该系统程序设计可参考demo_7_2.c,在这个基础上修改代码,最终设计出一个完整的秒表系统。  
提示:使用Mega16两个外部中断源INT0和INT1。将其中一个外部中断源与板上500Hz的标准频率相连,另外的一个外部中断源与一个按键相连。500Hz的标准频率被作为秒表系统的计时基准。按键的起到了“开始/停止/清零”作用。上电后,数码管显示全零,第一次按键,表示秒表计时开始,数码管显示的数值按1%秒速率计时。第二次按键计时停止,数码管显示最终的计时时间。第三次按键对数码管清零。以上功能可反复执行。  

/********************************************* 
Chip type           : ATmega16 
Program type        : Application 
Clock frequency     : 4.000000 MHz 
Memory model        : Small 
External SRAM size  : 0 
Data Stack size     : 256 
*********************************************/ 
#include <mega16.h> 
flash unsigned char led_7[10]={0x3F,0x06,0x5B,0x4F,0x66,0x6D,0x7D,0x07,0x7F,0x6F};  
flash unsigned char position[6]={0xfe,0xfd,0xfb,0xf7,0xef,0xdf}; 

unsigned char time[3];                                        // 时、分、秒计数单元 
unsigned char dis_buff[6];                                // 显示缓冲区,存放要显示的6个字符的段码值 
unsigned char time_counter;                                      // 中断次数计数单元 
unsigned char posit; 
unsigned char key_state=0;                                         
bit pre_pind3, int1_off, time_10ms_ok,time_20ms_ok; 

void display(void)                                                // 6位LED数码管动态扫描函数 
{ 
    PORTC = 0xff;                                                 
    PORTA = led_7[dis_buff[posit]]; 
    if (posit==2 || posit == 4) PORTA |= 0x80;  
    PORTC = position[posit];  
    if (++posit >=6 ) posit = 0;                 
} 

// External Interrupt 0 service routine  2ms 一次 
interrupt [EXT_INT0] void ext_int0_isr(void) 
{ 
    display();                            // 调用LED扫描显示 
    if (++time_counter>=5) 
    { 
        time_counter = 0;                    
        time_10ms_ok = 1;             
    } 
} 

// External Interrupt 1 service routine 外部按键中断 
interrupt [EXT_INT1] void ext_int1_isr(void) 
{ 
    GICR &= 0x7F;                                     // 关INT1中断,是做消抖处理 
    int1_off = 1; 
    pre_pind3 = 0; 
    if (++key_state>=3) key_state = 0; 
} 

void time_to_disbuffer(void)                        // 时钟时间送显示缓冲区函数 
{ 
    unsigned char i,j=0; 
    for (i=0;i<=2;i++) 
    { 
        dis_buff[j++] = time[i] % 10; 
        dis_buff[j++] = time[i] / 10; 
    } 
} 

void main(void) 
{ 
    PORTA=0x00;                    // 显示控制I/O端口初始化 
    DDRA=0xFF; 
    PORTC=0x3F; 
    DDRC=0x3F; 
    PORTD = 0xFF;            // PD2,PD3输入,上拉有效 

    time[2] = 0; time[1] = 0; time[0] = 0;        // 设时间初值00:00:00  
    posit = 0; 
    time_to_disbuffer(); 

    GICR|=0xC0;                                                        // INT1,INT0中断允许 
    MCUCR=0x0A;                                                        // INT1,INT0下降沿触发 

    #asm("sei")                                                        // 全局中断允许 

    while (1) 
    { 
        if (key_state == 0) 
        { 
            time[0] = 0; 
            time[1] = 0; 
            time[2] = 0; 
            time_to_disbuffer(); 
        } 
             
        if (time_10ms_ok)                                        // 10ms到 
        { 
            time_10ms_ok = 0; 
             
            time_20ms_ok = ~time_20ms_ok; 
            if ( time_20ms_ok && int1_off )         // 这段是间隔20ms检测按键是否释放 
            {                                      // 确认释放后开INT1中断,可以接收下次的按键 
                if (PIND.3 && pre_pind3)           // 这样就防止了一次按键过程中按键抖动对INT1的影响,构成消抖功能 
                { 
                    GIFR |= 0x80; 
                    GICR |= 0x80; 
                    int1_off = 0; 
                }     
                pre_pind3 = PIND.3; 
            }     
             
            if (key_state == 1)         
            { 
                if (++time[0] >= 100)                // 以下时间调整 
                { 
                    time[0] = 0; 
                    if (++time[1] >= 60) 
                    { 
                        time[1] = 0; 
                        if (++time[2] >= 60) time[2] = 0; 
                    } 
                } 
                time_to_disbuffer();                // 新调整好的时间送显示缓冲区 
            } 
        } 
    } 
} 



============================================================================================== 

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -