問題困擾了我?guī)滋炝耍泻玫霓k法,在文檔里給我解答,謝謝、
方案一: 1、誰能提供一個思路:用一個固定的中斷時間,中斷一次,變量加一次。變量每加一次,刷新的數(shù)據(jù)更新一次,這個變量的作用是:改變中斷的頻率的。比如說:一開始定時1ms中斷一次,刷新一次數(shù)據(jù),然后又中斷一次,變量在之前的基礎上加一,即2ms后數(shù)據(jù)跟著刷新一次,再中斷一次,3ms后數(shù)據(jù)刷新一次,依次往下進行,即想實現(xiàn)勻減速。之所以用固定時間中斷是因為我還需要一個脈沖(這個可以實現(xiàn),但是實現(xiàn)不了勻減速)。 我現(xiàn)在這程序,你們看下,步進電機設置了3個速度,一圈一個固定速度,不是我想要的。我想要的是總共轉3圈的話,速度慢慢降下來,減速的等級設多點,平滑點就好了。 方案二: 2、當然你們要說改變定時器的初值的話,這樣行,我實現(xiàn)了電機的勻減速,我還需要一個固定的脈沖,定時的初值又是變化的,又實現(xiàn)不了固定脈沖了。這兩個方案,問題相互交叉,很是煩惱。 方案三: 3、你們會想使用2個定時器,一個定時器給電機做勻減速運動,一個定時器做固定脈沖輸出,我試了,勻減速沒問題,但是固定脈沖會受影響,不是一個穩(wěn)定的脈沖占空比。
- #include<reg52.h>
- #include<intrins.h>
- #define uchar unsigned char
- #define uint unsigned int
- volatile unsigned long beats1=0;//電機1轉動節(jié)拍總數(shù)
- void startmotor1(unsigned long angle1);//電機1函數(shù)
- static unsigned char index1 =0;//節(jié)拍輸出索引1
- unsigned char code beatcode1[8]={0x1,0x3,0x2,0x6,0x4,0xc,0x8,0x9};//步進電機1、3節(jié)拍控制碼
- uchar temp1=0;//臨時變量
- uchar n=0;//小電機中斷頻率計數(shù)變量
- uint k=0;//小電機刷新節(jié)拍計數(shù)
- void delay(unsigned char i)
- {
- unsigned x,y;
- for(x=i;x>0;x--)
- for(y=50;y>0;y--);
- }
- bit flag1=0,flag2=0,flag3=0,flag4=0;
- unsigned char dir=0;
- sbit k1=P3^5;//按鍵1--啟動電機/正轉
- sbit k2=P3^6;//按鍵2--電機反轉
- sbit k3=P3^7;//按鍵3--暫停/開始
- sbit PWM=P2^0;//42步進電機脈沖引腳
- sbit buffer=P2^5;//蜂鳴器
- sbit fangxiang=P2^6;//電機正反轉控制線
- sbit EN=P2^7; //使能停止線
- sbit P1_0=P1^0;
- sbit P1_1=P1^1;
- sbit P1_2=P1^2;
- sbit P1_3=P1^3;
- sbit P1_4=P1^4;
- sbit P1_5=P1^5;
- sbit P1_6=P1^6;
- sbit P1_7=P1^7;
- void di() //蜂鳴器函數(shù)
- {
- unsigned char a;
- for(a=0;a<100;a++)
- {
- delay(1);
- buffer=0;
- delay(1);
- buffer=1;
- }
- }
- void keyscan() //按鍵掃描程序
- {
- if(k1==0)
- delay(10); //消抖
- if(k1==0) //啟動電機
- {
- while(!k1); //等待按鍵1松手
- TR0=1;
- // EN=1;
- // fangxiang=0;
- startmotor1(360*5); //調用電機1函數(shù)
- }
- }
- void startmotor1(unsigned long angle1) //步進電機1啟動函數(shù),angle1為所轉動角度
- {
- EA=0;
- beats1=(angle1*4076)/360;
- EA=1;
- }
- void motor1() //電機函數(shù);固定格式,調用就行。
- {
- if(beats1!=0)
- {
- temp1=P1;
- temp1=temp1&0xf0; //清零P1口低4位 11110000
- temp1=temp1|beatcode1[index1];
- P1=temp1;
- index1++;
- index1=index1&0x07;
- beats1--;
- }
- else
- {
- P1_0=0;
- P1_1=0;
- P1_2=0;
- P1_3=0;
- }
- }
- void main()
- {
- TMOD=0x01;//設置T0為模式1
- TH0=0xfc; //1ms中斷一次
- TL0=0x18;
- ET0=1;
- while(1)
- {
- keyscan(); //按鍵掃描
- if(flag1==1)
- {
- flag1=0;
- if(flag3==1) //進入第3圈速度;
- {
- if(n==8) //第3圈速度,3ms刷新一次節(jié)拍;
- {
- n=5;
- k++; //第3圈節(jié)拍計數(shù);
- if(k==4076) //第3圈以3ms的速度刷新4076個節(jié)拍后(即轉了一圈),停止轉動。
- {
- k=0;
- beats1=0;//停止轉動
- flag3=0;//標志3清楚,以便再次啟動定時器;
- n=0; //n清零
- TR0=0;//關定時器
- }
- motor1();
- }
- }
- if(flag2==1) //進入第2圈速度;
- {
- if(n==4) //第2圈速度,2ms刷新一次節(jié)拍;
- {
- n=2;
- k++; //第2圈節(jié)拍計數(shù);
- if(k==4076) //第2圈以2ms的速度刷新4076個節(jié)拍后(即轉了一圈),重新設置速度n=5,進入標志3判斷;
- {
- k=0;
- n=5;
- flag3=1; //速度3標志,進入速度3,3ms刷新一次;
- }
- motor1();
- }
- }
- if(n==1) //進入第1圈速度,1ms刷新一次節(jié)拍;
- {
- n=0;
- k++; //第1圈節(jié)拍計數(shù);
- if(k==4076) //第1圈以1ms的速度刷新4076個節(jié)拍后(即轉了一圈),重新設置速度n=2,進入標志2判斷;
- {
- k=0;
- n=2;
- flag2=1;//速度2標志,進入速度2,2ms刷新一次;
- }
- motor1();
- }
- }
- }
- }
- void timer0() interrupt 1
- {
- TH0=0xfc; //重新賦值,1ms中斷一次
- TL0=0x18;
- n++; //小電機中斷刷新頻率計數(shù)
- flag1=1;//標志的作用是跳至主函數(shù)中,以節(jié)省中斷時間。
- }
復制代碼
|