求救:红外控制28BYJ-48

2019-07-15 18:36发布

本帖最后由 babamamadeningb 于 2014-9-3 14:59 编辑

如标题,我想用红外遥控器实现控制28BYJ-48电机 正转 反转 停止 三个功能。 但实际效果是遥控器按下去以后电机只工作了一会,之后就停下来了,再按其他键也没有反应。 反复琢磨自己的程序,都觉得没有问题。 故想请大家帮我看看到底是哪里出错了。#include<reg52.h>sbit A1=P3^0;   
sbit B1=P3^1;
sbit C1=P3^2;
sbit D1=P3^3;      //A1-D1 分别是电机的四个接口,我是通过ULN2003来实现对单片机I/0口输出电压的放大,之后再接给电机。



unsigned char time;
bit n;
bit m;
unsigned char a[33];
unsigned char b[4];
unsigned char i=0;
unsigned char code display[10]={0x3f,0x06,0x5b,0x4f,0x66,0x6d,0x7d,0x07,0x7f,0x6f};
bit startflag;
unsigned char time;    //用于定时器中断的时间记录
bit n;                           //外部中断 判别标志 1表示中断发生
bit m;
unsigned char a[33];   //红外接收的33个中断信号
unsigned char b[4];    //解码后的 分别对应引导码 客户码 操作码 操作反码
unsigned char i=0;
void DelayUs2x(unsigned char t)     //延时函数
{   
while(--t);
}
void DelayMs(unsigned char t)    //延时函数
{
     
while(t--)
{
     //大致延时1mS
     DelayUs2x(245);
DelayUs2x(245);
}

void timer_inital()     //定时器初始化
{
ET0=1;
TMOD=0x02;
EA=1;
TH0=0;
TL0=0;
TR0=1;
}
void EX0_inital()   //外部中断初始化
{
EA=1;
EX0=1;
IT0=1;
}

void EXO(void)interrupt 0    //外部中断函数 1、把每次中断所用的时间记录到了a[33]里面,以便之后的解码  2、把n置为1来标志中断
{
if(startflag)                        
   {
    if(time<63&&time>=33)    //引导码 遥控器的头码,9ms+4.5ms
                        i=0;
    a=time;                         //存储每个电平的持续时间,用于以后判断是0还是1
    time=0;
    i++;
            if(i==33)
      {
          n=1 ;
i=0;
startflag=0;
m=1;
      }
   }
  else
{
time=0;
startflag=1;
}
}
void timer(void)interrupt 1         //计时器中断函数 记录时间用
{
time++;
}
void codetransmit()                  //解码函数 解码以后的8为二进制存入b[4]中
{
unsigned char j,k,l,y;
l=1;
for(j=0;j<4;j++)
  {
    for(k=0; k<8;k++)
{
         y>>=1;
if(a[l]>7)
  y=y|0x80;
l++;
}

b[j]=y;
     y=0;
  }
}
void step1()                           //电机工作函数
{
A1=1;B1=0;C1=0;D1=0;
}
void step2()                       //电机工作函数
{
A1=0;B1=1;C1=0;D1=0;
}
void step3()                      //电机工作函数
{
A1=0;B1=0;C1=1;D1=0;
}
void step4()                     //电机工作函数
{
A1=0;B1=0;C1=0;D1=1;
}
void machine1()             //电机工作函数 正转
{
step1();DelayMs(5);
step2();DelayMs(5);
step3();DelayMs(5);
step4();DelayMs(5);
}
void machine2()             //电机工作函数 倒转
{
step4();DelayMs(5);
step3();DelayMs(5);
step2();DelayMs(5);
step1();DelayMs(5);
}
void machinestop()       //电机工作函数 停止
{
A1=0;B1=0;C1=0;D1=0;DelayMs(5);
}
void work(unsigned char value)    //电机工作
{
switch(value)
   {
case 0x44:             //转码后如果是0x44,则正转
             m=0;
             machine1();
             if(m==1)         //我检查过,发现这里m的值在刚开始的时候为0,当电机停止的时候就置1了,所以电机不会工作了。但是我
                                       怎么都想不通这里m怎么会置1的,又没有发生中断,只有中断发生的时候m才被置1啊。
                n=1;
             else
                n=0;
             break;
case 0x40:                   //转码后如果是0x40,则倒转
            m=0;
            machine2();
            if(m==1)
              n=1;
            else
              n=0;
            break;
case 0x43:                   //转码后如果是0x43,则停止
            m=0;
            machinestop();
            if(m==1)
               n=1;
           else
              n=0;
           break;
default:break;
   }
}
void main()
{
unsigned char value;
timer_inital();
EX0_inital();

while(1)
  {
   if(n==1)
       {
        codetransmit();
        value=b[2];
        }
   work(value);
   DelayMs(5);
  }
}
友情提示: 此问题已得到解决,问题已经关闭,关闭后问题禁止继续编辑,回答。