硬件资源:ATmega8开发板,LED灯,按键,步进电机。
要实现功能:1,跑马灯;2,按键控制跑马灯(按一次亮灯走一位);3,驱动步进电机
程序设计:1,初始化引脚,用TIME0计数器设计延时程序
//IO端口初始化
void port_init()
{
DDRD = 0xFF; //PORTD引脚设置为输出(LED灯) //也可用 DDRD = (1<<PD3)|(1<<PD4); 来置位引脚
DDRC = 0xFE; //PORTC0引脚设置为输入(按键),其他为输出
DDRB = 0xFF; //PORTB引脚设置为输出(驱动电机)
PORTC = 0xFF;// PORTC引脚上拉电阻使能
}
//延时函数 T/C0来计数
void delay_us(int us) // ~和!是不一样的,判断时用“!”,取反时用“~ ”
{
TCCR0 = 0;//关定时器
TIFR |= 1;//TOV0置位;
TCCR0 = 0x02; //16MHz时钟,8分频
TCNT0 = 255 - 2*us;
while(!(TIFR)){;}
TIFR |= 1;
}
void delay_ms(int ms)
{
char j;
while(ms--){
for(j=0;j<10;j++){
delay_us(100);
}
}
}
2,//跑马灯程序
void led()
{
uchar i=0;
for(i;i<8;i++){
PORTD = ~(0x01<<i);
delay_ms(2000);
}
}
3,//按键扫描函数
uchar key_scan()
{
uchar a,i;
i=1;
a = PINC; //不能直接用PINC0
if(a&0x01){ //没按下
return 0;
}else{ //按下
return 1;
}
}
//按键功能函数
char val; // 必须是全局变量!!!!!
void key_led()
{
uchar key;
key = key_scan();
if(key){ //按下,
delay_ms(1); //消抖延时
if(val==7){val=0;}
else {val+=1;}
}else{
val=val;
}
//delay_ms(10);
PORTD = ~(0x01<<val);
}
4,//驱动电机函数
unsigned char CCW[8]={0x08,0x0c,0x04,0x06,0x02,0x03,0x01,0x09}; //逆时钟旋转相序表
unsigned char CW[8]={0x09,0x01,0x03,0x02,0x06,0x04,0x0c,0x08}; //正时钟旋转相序表
void StepMotor(uchar dir,int speed)
{
uchar i;
if(dir){
for(i=0;i<8;i++){
PORTB = CW[i]; //正转
delay_ms(speed); //延时(速度)
}
}else{
for(i=0;i<8;i++){
PORTB = CCW[i]; //反转
delay_ms(speed); //延时(速度)
}
}
}
5,//主函数
void main()
{
port_init();
while(1){
key_led();
StepMotor(0,1); //电机正转
delay_ms(5000);
StepMotor(1,10);// 电机反转
}
}