金砂紫钰 发表于 2012-10-27 13:53:57

关于51控制 4线 5线 和6线和三线步进电机的问题

本帖最后由 金砂紫钰 于 2012-10-27 14:20 编辑

#include "reg51.h"       //包含头文件

sbit S_A=P2^0;         //定义步进电机A相
sbit S_B=P2^1;         //定义步进电机B相
sbit S_C=P2^2;         //定义步进电机C相
sbit S_D=P2^3;         //定义步进电机D相

sbit P24=P2^4;         //定义步进3线电机A相
sbit P25=P2^5;         //定义步进3线电机B相

sbit S17=P3^7;         //正传
sbit S18=P3^6;         //定义S18控制IO,电机转速减小
sbit S19=P3^5;         //启动/暂停
sbit S20=P3^4;         //定义S20控制IO,电机转速加大
sbit S21=P3^3;         //反转

sbit LE1=P2^6;         //位选573锁存器使能
sbit LE2=P2^7;         //段选573锁存器使能

bit zf,stop;

#define uchar unsigned char
#define uintunsigned int

uintspeed;             //电机转速

uchar keyValue;          //定义键盘扫描结果参数
uchar temp;
uchar code dis={0x3F,0x06,0x5B,0x4F,0x66,0x6D,0x7D,0x07,
                   //0    1    2    3    4    5    6    7   
                     0x7F,0x6F,0x77,0x7C,0x39,0x5E,0x79,0x71};//0~F的段码
                   //8    9    A    B    C    D    E    F

//**************************************************************************************************
//延时函数
//**************************************************************************************************
delay(uint time)         //int型数据为16位,所以最大值为65535            
{
uinti,j;             //定义变量i,j,用于循环语句
for(i=0;i<time;i++)    //for循环,循环50*time次
   for(j=0;j<50;j++);//for循环,循环50次
}

//**************************************************************************************************
//数码管显示函数
//**************************************************************************************************
smg_show(uchar n)
{
      //显示个位
   P1=0xbf;               //0xbf=1011 1111,即选通个位
   LE1=1;                   //锁存位
   LE1=0;                   //断开锁存,位选573的Q7~Q0仍保持
   P1=dis;            //dis为0~9的编码
   LE2=1;                   //锁存段码
   LE2=0;                   //断开锁存,段选573的Q7~Q0仍保持
   delay(10);            //延时保持一下,延时过大会闪动,延时过小会有重影   

   P1=0x00;LE2=1;LE2=0;   //清除P1口数据,以免造重影
   //显示十分位
   P1=0x7f;               //0xbf=0111 1111,即选通十分位
   LE1=1;                   //锁存位
   LE1=0;                   //断开锁存,位选573的Q7~Q0仍保持
   P1=dis;            //0~9的编码
   LE2=1;                   //锁存段码
   LE2=0;                   //断开锁存,段选573的Q7~Q0仍保持
   delay(10);            //延时保持一下,延时过大会闪动,延时过小会有重影

   P1=0x00;LE2=1;LE2=0;   //清除P1口数据,以免造重影   
         
}
//**************************************************************************************************
//1*5按键扫描函数
//**************************************************************************************************
keyScan()                           
{
   P3=P3|0xf8;                //P3高5位置1,设置为输入
   if((P3&0xf8)!=0xf8)      //判断是否有按键按下
    {
   delay(20);               //延时肖抖
   if((P3&0xf8)!=0xf8)      //再次判断是否有按键按下
       keyValue=(P3&0xf8);    //读取扫描结果
       while((P3&0xf8)!=0xf8);
    }
}
//**************************************************************************************************
//1*5按键扫描结果处理函数
//**************************************************************************************************
keyHandle()                     
{      
      switch(keyValue)         
          {
            case 0x78:               //如果S17按键按下
                                {
               zf=1;               //正反标志置1,正向
               break;         
                }
            case 0xb8:               //如果S18按键按下
                                {
               if(speed>15)speed--;//减速
                   else speed=30;   
               break;
                }
            case 0xd8:               //如果S19按键按下
                                {
               stop=~stop;         //启动/暂停
               break;
                }
            case 0xe8:               //如果S20按键按下
                                {               
               if(speed<45)speed++;//减速
                   else speed=30;
               break;
                }
            case 0xf0:               //如果S21按键按下
                                {
               zf=0;               //正反标志置0,反向            
               break;
                }
            default:
                                        break;
          }
}
//**************************************************************************************************
//步进电机控制 (测试好的程序4线和6线共用)
//**************************************************************************************************
/*stepmotor()
{   
   if(stop==0)         //停止标志位为0,执行以下程序,如果为1,不执行以下程序
       {
         if(zf)          //zf,即正反标志为1,正向转动
            {
            // P2=0x01;      //等效于S_D=0,S_C=0,S_B=0,S_A=1
                       P2=0xFE;      //           4
             delay(speed); //延时,修改此参数即可修改电机转速
            // P2=0x03;      //等效于S_D=0,S_C=0,S_B=1,S_A=1
                       P2=0XFC;      //   4
             delay(speed);
            // P2=0x02;      //i等效于S_D=0,S_C=0,S_B=1,S_A=0
             P2=0xFD;          //4
                       delay(speed);
            // P2=0x06;      //等效于S_D=0,S_C=1,S_B=1,S_A=0
                       P2=0xF9;
             delay(speed);
             //P2=0x04;      //等效于S_D=0,S_C=1,S_B=0,S_A=0
                       P2=0xFB;
             delay(speed);
             //P2=0x0c;      //等效于S_D=1,S_C=1,S_B=0,S_A=0
                       P2=0xF3;
             delay(speed);
            // P2=0x08;      //等效于S_D=1,S_C=0,S_B=0,S_A=0
                       P2=0xF7;
             delay(speed);
            // P2=0x09;      //等效于S_D=1,S_C=0,S_B=0,S_A=1
                       P2=0xF6;
             delay(speed);
            }
         else            //zf,即正反标志为0,反向转动?   
            {
            // P2=0x09;      //等效于S_D=1,S_C=0,S_B=0,S_A=1
                       P2=0xF6;
             delay(speed); //延时,修改此参数即可修改电机转速
            // P2=0x08;      //等效于S_D=1,S_C=0,S_B=0,S_A=0
                       P2=0xF7;
             delay(speed);
            // P2=0x0c;      //等效于S_D=1,S_C=1,S_B=0,S_A=0
                       P2=0xF3;
             delay(speed);
             //P2=0x04;      //等效于S_D=0,S_C=1,S_B=0,S_A=0
                       P2=0xFB;
             delay(speed);
             //P2=0x06;      //等效于S_D=0,S_C=1,S_B=1,S_A=0
                       P2=0xF9;
             delay(speed);      
             //P2=0x02;      //i等效于S_D=0,S_C=0,S_B=1,S_A=0
                       P2=0xFD;
             delay(speed);
             //P2=0x03;      //等效于S_D=0,S_C=0,S_B=1,S_A=1
                       P2=0xFC;
             delay(speed);      
             //P2=0x01;      //等效于S_D=0,S_C=0,S_B=0,S_A=1
                       P2=0xFE;
             delay(speed);
            }         
       }         
}   */       
//**************************************************************************************************
//三线步进电机控制
//**************************************************************************************************
void stepmotor()intertupt 1 using 1
{
        TMOD=0X01;
        THO=0X3C;
        TLO=0Xb0;
        P2=0x10;
        if(temp>=39)        //       定时2S
        {
                temp=0x00;
                P2=0x00;
       }
}                                 //这段程序老是报错,我这里是要输出一个,4S 一个周期的脉冲
////////////////////////////////////////////////////////////////////////////////////////////
//**************************************************************************************************
//三线步进检测程序
//**************************************************************************************************
/*stepmotor()
{   
   if(stop==0)         //停止标志位为0,执行以下程序,如果为1,不执行以下程序
       {
         if(zf)          //zf,即正反标志为1,正向转动
            {
             P2=0x01;      //等效于S_D=0,S_C=0,S_B=0,S_A=1
             delay(speed); //延时,修改此参数即可修改电机转速
             P2=0x02;      //等效于S_D=0,S_C=0,S_B=1,S_A=1
             delay(speed);
             //P2=0x00;      //i等效于S_D=0,S_C=0,S_B=1,S_A=0
             //delay(speed);
             // P2=0x05;
                       // P2=0x01;
                       // P2=0x00;

            }
         else            //zf,即正反标志为0,反向转动?   
            {
               
             P2=0x05;      //i等效于S_D=0,S_C=0,S_B=1,S_A=0
            delay(speed);
         
             P2=0x06;      //等效于S_D=0,S_C=0,S_B=0,S_A=1
            delay(speed);
                        // P2=0x09;
                       //P2=0x01;
                        // P2=0x00;
            }         
       }         
} */



//**************************************************************************************************
//主函数
//**************************************************************************************************
main()
{
                TMOD=0X11;                               //开二个定时器
                TH0=0X3C;
                TH0=0Xb0;
                TH1=0X3C;
                TH1=0Xb0;
                EA=1;
                ET0=1;
                ET1=1;
                TR0=1;
                TR1=1;

speed=30;                      //初始化转速
   while(1)                      //死循环,等待定时器中断
   {   keyValue=0;             //初始化键值为0
         keyScan();            //按键扫描
         keyHandle();            //处理扫描结果
         stepmotor();            //电机转动
         smg_show(speed);      //数码管最低两位显示转速,初始化为30,值越大,转速越小
   }
}




请教各位,
void stepmotor()intertupt 1 using 1    //interrupt
{
        TMOD=0X01;
        THO=0X3C;
        TLO=0Xb0;
        P2=0x10;
        if(temp>=39)        //       定时2S
        {
                temp=0x00;
                P2=0x00;
       }
}                                 //这段程序老是报错,我这里是要输出一个,4S 一个周期的脉冲

devcang 发表于 2012-10-27 15:03:04

既然是报错,那报的是啥错呢

xiao_yao 发表于 2012-10-27 21:34:55

中断程序加一句 temp++;

金砂紫钰 发表于 2012-10-28 00:15:59

devcang 发表于 2012-10-27 15:03 static/image/common/back.gif
既然是报错,那报的是啥错呢

无法调用中断,,,我用示波器,测没有波形输出,

金砂紫钰 发表于 2012-10-28 00:16:49

xiao_yao 发表于 2012-10-27 21:34 static/image/common/back.gif
中断程序加一句 temp++;

加了也没有用,错误提示:无法调用中断,

devcang 发表于 2012-10-28 01:15:29

初始化的代码,写在中断之外

金砂紫钰 发表于 2012-10-28 09:56:40

devcang 发表于 2012-10-28 01:15 static/image/common/back.gif
初始化的代码,写在中断之外

能不能说详细点,本人刚学,谢谢,
页: [1]
查看完整版本: 关于51控制 4线 5线 和6线和三线步进电机的问题