找回密码
 立即注册

QQ登录

只需一步,快速开始

搜索
查看: 1693|回复: 9
收起左侧

关于单片机通过中断切换led模式的问题?

[复制链接]
ID:687423 发表于 2020-2-17 09:50 | 显示全部楼层 |阅读模式
这个程序现在可以通过按键k3切换led模式,但是只能在上一个模式程序执行完之后才可以通过按键K3切换到下一个模式,我想知道如才可在上一个led模式执行的时候,按下按键k3就可以切换到下一个模式,希望大家帮我改一下程序,我还想知道为什么按键的延时不能再中断中使用,我中断的程序关于对按键的处理对吗,谢谢。
#include<reg52.h>
sbit beep=P1^5;
sbit k1=P3^1;
sbit k3=P3^2;
sbit led=P2^0;
#define N P2
typedef unsigned int ui;
typedef unsigned char uc;
uc num;
void delay(ui i)
{
while(i--);
}
void fmq()//蜂鸣器
{
beep=~beep;
delay(100);
}
void led0()//流水灯
{
N=0xff;
N=0xfe;
fmq();
delay(50000);
N=0xfd;
fmq();
delay(50000);
N=0xfb;
fmq();
delay(50000);
N=0xf7;
fmq();
delay(50000);
N=0xef;
fmq();
delay(50000);
N=0xdf;
fmq();
delay(50000);

N=0xbf;
fmq();
delay(50000);

N=0x7f;
fmq();
delay(50000);
  
}
void led1()//led对称亮
{
N=0x7e;
fmq();
delay(35000);
delay(35000);
N=0xbd;
fmq();
delay(35000);
delay(35000);
N=0xdb;
fmq();
delay(35000);
delay(35000);
N=0xe7;
fmq();
delay(35000);
delay(35000);
N=0xe7;
fmq();
delay(35000);
delay(35000);
N=0xdb;
fmq();
delay(35000);
delay(35000);
N=0xbd;
fmq();
delay(35000);
delay(35000);
N=0x7e;
fmq();
delay(35000);
delay(35000);
}
void led2()//led分别单双数亮
{
N=0xaa;
fmq();
delay(50000);
delay(50000);
N=0x55;
fmq();
delay(50000);
delay(50000);
}
void led3()//通过按键k1使led一个一个亮
{
ui i;
N=0xfe;
while(1)
{
  if(k1==0)
  {  
   delay(1000);
   if(k1==0)
   {
    switch(i)
    {
     case(0):N=0xfd;fmq();i++;break;
     case(1):N=0xfb;fmq();i++;break;
     case(2):N=0xf7;fmq();i++;break;
     case(3):N=0xef;fmq();i++;break;
     case(4):N=0xdf;fmq();i++;break;
     case(5):N=0xbf;fmq();i++;break;
     case(6):N=0x7f;fmq();i++;break;
     case(7):N=0xff;fmq();i++;break;
    }
   while(!k1);
   }
  }
  if(i==8)
  {
   i=0;
   break;
  }
}
}
void init()//中断初始化
{
IT0=1;
EX0=1;
EA=1;
}
void main()
{
init();
while(1);
}
void init0() interrupt 0//中断程序
{
EX0=0;
delay(1000);
{
  while(1)
  {
   if(k3==0)
   {
    EX1=0;
    switch(num)
    {
     case(0):led0();num++;break;
     case(1):led1();num++;break;
     case(2):led2();num++;break;
     case(3):led3();num++;break;
     case(4):num=0;N=0x00;break;
    }
   }
   while(!k3);
  }  
}
}

回复

使用道具 举报

ID:584814 发表于 2020-2-17 10:40 | 显示全部楼层
把中断里的那个延时设短或去掉。
回复

使用道具 举报

ID:94031 发表于 2020-2-17 10:59 | 显示全部楼层
中断程序里只设置标志,执行放在main while循环里。
回复

使用道具 举报

ID:462827 发表于 2020-2-17 11:10 | 显示全部楼层
按键可以在主循环中轮询置标志位,比如流动方向、速度呀等等,在定时器中断中完成led的控制,不要在一次中断中做完成所有动作,而是每一次中断只执行该动作的一个子状态。
回复

使用道具 举报

ID:159575 发表于 2020-2-17 12:05 来自手机 | 显示全部楼层
我当年直接用了goto语句解决,方便快捷。
回复

使用道具 举报

ID:687423 发表于 2020-2-17 14:10 | 显示全部楼层
xuyaqi 发表于 2020-2-17 10:59
中断程序里只设置标志,执行放在main while循环里。

我没看懂你说的意思,能写一下程序吗
回复

使用道具 举报

ID:687423 发表于 2020-2-17 14:12 | 显示全部楼层
hantu 发表于 2020-2-17 11:10
按键可以在主循环中轮询置标志位,比如流动方向、速度呀等等,在定时器中断中完成led的控制,不要在一次中 ...

什么意思,没看懂。
回复

使用道具 举报

ID:687423 发表于 2020-2-17 15:20 | 显示全部楼层
我把程序改了一下,但还是不行,我想知道应该怎么写。
void init()
{
        IT0=1;
        EX0=1;
        EA=1;
}
void main()
{
        init();
        while(1)
        {
                if(num==1)
                        led0();
                if(num==2)
                        led1();
                if(num==3)
                        led2();
                if(num==4)
                        led3();
                if(num==5)
                        num=0;
        }       
}
void init0() interrupt 0
{
        delay(100);
        {       
                if(k3==0)
                        num++;
                while(!k3);
        }
}
回复

使用道具 举报

ID:94031 发表于 2020-2-17 22:45 | 显示全部楼层
。。jj 发表于 2020-2-17 14:10
我没看懂你说的意思,能写一下程序吗

按你的要求编了一个程序。 通过中断切换led模式.rar (39.37 KB, 下载次数: 15)
回复

使用道具 举报

ID:688355 发表于 2020-2-19 08:34 | 显示全部楼层
。。jj 发表于 2020-2-17 15:20
我把程序改了一下,但还是不行,我想知道应该怎么写。
void init()
{

中断里面的括号不对吧?你这样试试
void init0() interrupt 0
{
        delay(100);
               
                if(k3==0)
                {        num++;
                while(!k3);
                 }
}
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

手机版|小黑屋|51黑电子论坛 |51黑电子论坛6群 QQ 管理员QQ:125739409;技术交流QQ群281945664

Powered by 单片机教程网

快速回复 返回顶部 返回列表