控制AVR单片机5路PWM波形
控制AVR单片机5路PWM波形
现开发了单片机控制5路PWM波形,也可以同时控制15路直流三色灯板,按触摸屏顺序点亮的电路和程序,供大家参考。
电路为
单片机ATMEGA128控制5路PWM方波,按照74HC08逻辑编码输出15路PWM信号,一次按照迪文触摸屏点亮3种颜色灯板的5路发光信号。ULN2003提供12V电压。每个灯板通过一个CMOS管IR3205输出功率。一个74HC08通过一路PWM,这路PWM通过74HC08控制的继电器控制IR3205的开关,进而控制24V,13V,36V灯板的开关,灯板的亮度通过PWM波形的占空比调节电路的PCB如下
上面是单片机PCB,它和灯板PCB通过排线连接
图片
图片
图片
图片
图片
图片
上面是灯板PCB。下面是单片机程序,程序用ICC-AVR开发,链接:https://pan.baidu.com/s/1X_7zIHR4K1ipaGRTviVtUw ;
提取码:so7m
链接: https://pan.baidu.com/s/1oK1L9I1EFRVYrHcABoS7Cg?pwd=y7nn 提取码: y7nn
复制这段内容后打开百度网盘手机App,操作更方便哦
//ICC-AVR application builder : 2010-6-22 15:14:03
// Target : M64A
// Crystal: 4.0000Mhz
/*
修改宏定义以实现不同功能,
*/
#include “main.h”
/*******************************************
向串口1发送单个数据,查询方式
***************************************
/
void TxUart1(unsigned char i)
{
//CLI(); //disable all interrupts
//DelayMs(1);
while (!(UCSR0A & (1<<UDRE0))); /
等待发送缓冲器为空
/
UDR0 = i; /
发送数据
/
//SEI(); //re-enable interrupts
}
/*******************************************
向串口0发送数组,查询方式
参数1:数组指针;
参数2:数组长度;
*******************************************/
void TxArrayUart1(unsigned char *ptr,unsigned char number)
{
//CLI(); //disable all interrupts
uchar i;
for(i = 0; i < number; i++)
{
TxUart1(ptr[i]);
}
//SEI(); //re-enable interrupts
}
/*******************************************
向串口1发送单个数据,查询方式
void TxUart1(unsigned char i)
{
//CLI(); //disable all interrupts
while (!(UCSR1A & (1<<UDRE1))); //等待发送缓冲器为空
UDR1 = i; //发送数据
//SEI(); //re-enable interrupts
}
/*******************************************
向串口0发送数组,查询方式
参数1:数组指针;
参数2:数组长度;
void TxArrayUart1(unsigned char *ptr,unsigned char number)
{
//CLI(); //disable all interrupts
uchar i;
for(i = 0; i < number; i++)
{
TxUart1(ptr[i]);
}
//SEI(); //re-enable interrupts
}
/*******************************************
数据接收,等待查询方式
***************************************
/
unsigned char uart_receive1(void)
{
while (!(UCSR1A & (1<<RXC1))); /
等待接收数据
/
return UDR1; /
获取并返回数据
/
}
//UART0 initialize
// desired baud rate: 9600
// actual: baud rate: 9615 (0.2%)
// char size: 8 bit
// parity: Disabled
void uart0_init(void)
{
UCSR0B = 0x00; //disable while setting baud rate
UCSR0A = 0x00;
UCSR0C = 0x06;
UBRR0L = 0x0C; //set baud rate lo
UBRR0H = 0x00; //set baud rate hi
UCSR0B = 0x98;
}
#pragma interrupt_handler uart0_rx_isr:iv_USART0_RXC
void uart0_rx_isr(void)
{
//uart has received a character in UDR
uart1_data = UDR0;
switch (uart1_counter)
{
case 0:
if (uart1_data == 0xaa)
uart1_counter ++;
else
uart1_counter = 0;
break;
case 1:
if ((uart1_data == 0x78) || (uart1_data == 0x79))
uart1_counter ++;
else
uart1_counter = 0;
button_type = uart1_data;
break;
case 2:
if (uart1_data == 0x00)
{
uart1_counter ++;
}
else
uart1_counter = 0;
break;
case 3:
uart1_counter ++;
button = uart1_data;
break;
case 4:
if (uart1_data == 0xcc)
uart1_counter ++;
else
uart1_counter = 0;
break;
case 5:
if (uart1_data == 0x33)
uart1_counter ++;
else
uart1_counter = 0;
break;
case 6:
if (uart1_data == 0xc3)
uart1_counter ++;
else
uart1_counter = 0;
break;
case 7:
uart1_counter = 0;
if (uart1_data == 0x3c)
{
switch(button)
{
case 0x57:
case 0x58:
case 0x63:
if(button_time == 0)
{
button_flag = 1;
button_time = 110;
}
break;
default:
if((button_time == 0) && (button_type == 0x78))
{
button_flag = 1;
}
break;
}
}
break;
default:
uart1_counter = 0;
break;
}
}
/*
#pragma interrupt_handler uart1_rx_isr:iv_USART1_RXC
void uart1_rx_isr(void)
{
//uart has received a character in UDR
uart1_data = UDR1;
switch (uart1_counter)
{
case 0:
if (uart1_data == 0xaa)
uart1_counter ++;
else
uart1_counter = 0;
break;
case 1:
if ((uart1_data == 0x78) || (uart1_data == 0x9b))
uart1_counter ++;
else
uart1_counter = 0;
break;
case 2:
if ((uart1_data == 0x00) || (uart1_data == 0x5a))
{
uart1_counter ++;
if(uart1_data == 0x5a)
time_get = 1;
}
else
uart1_counter = 0;
break;
case 3:
if(time_get)
{
time[time_get – 1] = uart1_data;
if(time_get < 6)
time_get ++;
else
{
//time_get = 0;
uart1_counter ++;
}
}
else
{
uart1_counter ++;
button = uart1_data;
}
break;
case 4:
if (uart1_data == 0xcc)
uart1_counter ++;
else
uart1_counter = 0;
break;
case 5:
if (uart1_data == 0x33)
uart1_counter ++;
else
uart1_counter = 0;
break;
case 6:
if (uart1_data == 0xc3)
uart1_counter ++;
else
uart1_counter = 0;
break;
case 7:
uart1_counter = 0;
if (uart1_data == 0x3c)
{
if(time_get)
{
time_get = 0;
time_flag = 1;
}
else
button_flag = 1;
}
break;
default:
uart1_counter = 0;
break;
}
}*/
//UART1 initialize
// desired baud rate:19200
// actual baud rate:19231 (0.2%)
// char size: 8 bit
// parity: Disabled
void uart1_init(void)
{
UCSR1B = 0x00; //disable while setting baud rate
UCSR1A = 0x00;
UCSR1C = 0x06;
UBRR1L = 0x0C; //set baud rate lo
UBRR1H = 0x00; //set baud rate hi
UCSR1B = 0x98;
}
//TIMER0 initialize – prescale:32
// WGM: Normal
// desired value: 1KHz
// actual value: 1.000KHz (0.0%)
void timer0_init(void)
{
TCCR0 = 0x00; //stop
ASSR = 0x00; //set async mode
TCNT0 = 0x83; //set count
OCR0 = 0x7D;
// TCCR0 = 0x03; //start timer
}
#pragma interrupt_handler timer0_ovf_isr:iv_TIM0_OVF
void timer0_ovf_isr(void)
{
TCNT0 = 0x83; //reload counter value
if(ms)
ms–;
}
//TIMER1 initialize – prescale:64
// WGM: 0) Normal, TOP=0xFFFF
// desired value: 1KHz
// actual value: 1.008KHz (0.8%)
void timer1_init(void)
{
TCCR1B = 0x00; //stop
TCNT1H = 0xFF; //setup
TCNT1L = 0xC2;
OCR1AH = 0x00;
OCR1AL = 0x3E;
OCR1BH = 0x00;
OCR1BL = 0x3E;
OCR1CH = 0x00;
OCR1CL = 0x3E;
ICR1H = 0x00;
ICR1L = 0x3E;
TCCR1A = 0x00;
TCCR1B = 0x03; //start Timer
}
#pragma interrupt_handler timer1_ovf_isr:iv_TIM1_OVF
void timer1_ovf_isr(void)
{
//TIMER1 has overflowed
TCNT1H = 0xFF; //reload counter high value
TCNT1L = 0xC2; //reload counter low value
if(laser_ms)
laser_ms –;
if(button_time)
button_time –;
if(rf_out_time)
{
rf_out_time –;
if(RF_TYPE)
RFRUN_L;
else
RFCTL_L;
}
else
{
//if(RF_TYPE)
RFRUN_H;
//else
RFCTL_H;
}
cold_count = (cold_count < 3) ? (cold_count + 1) : 0;
if(cold_count < cold_max)
COLD_L;
else
COLD_H;
}
//TIMER2 initialize – prescale:1024
// WGM: Normal
// desired value: 20Hz
// actual value: 20.032Hz (0.2%)
void timer2_init(void)
{
TCCR2 = 0x00; //stop
TCNT2 = 0x3D; //setup
OCR2 = 0xC3;
TCCR2 = 0x05; //start
}
#pragma interrupt_handler timer2_ovf_isr:iv_TIM2_OVF
void timer2_ovf_isr(void)
{
TCNT2 = 0x3D; //reload counter value
WDR ();
if(ad_time < 20)
{
ad_time++;
}
else
{
ad_time = 0;
if(miniter == 60)
{
miniter = 0;
total_time ++;
EEPROM_write(0x110,total_time>>16);
EEPROM_write(0x111,(unsigned char)total_time>>8);
EEPROM_write(0x112,(unsigned char)total_time);
}
else
miniter ++;
if(lamp_ok)
{
if(miniter_rdy == 60)
{
miniter_rdy = 0;
total_time ++;
EEPROM_write(0x113,total_time_rdy >> 16);
EEPROM_write(0x114,(unsigned char)total_time_rdy >> 8);
EEPROM_write(0x115,(unsigned char)total_time_rdy);
}
else
miniter_rdy ++;
}
/
每一秒启动一次温度采集
/
ADCSRA = 0xcf;
}
if(beep_time)
{
beep_time–;
BEEP_L;
}
else
BEEP_H;
}
//Watchdog initialize
// prescale: 512K
void watchdog_init(void)
{
WDR (); //this prevents a timeout on enabling
WDTCR |= (1<<WDCE) | (1<<WDE);/* 30-Oct-2006 Umesh*/
WDTCR = 0x0D; //WATCHDOG ENABLED – dont forget to issue WDRs
}
void port_init(void)
{
PORTA = 0xFF;
DDRA = 0xFF;
PORTB = 0xFF;
DDRB = 0xFF;
PORTC = 0x0E; //m103 output only
DDRC = 0x0F;
PORTD = 0x00;
DDRD = 0x93;
PORTE = 0x00;
DDRE = 0x00;
PORTF = 0x01;
DDRF = 0x01;
PORTG = 0x00;
DDRG = 0x13;
}
#pragma interrupt_handler int0_isr:iv_INT0
void int0_isr(void)
{
//external interupt on INT0
}
//ADC initialize
// Conversion time: 16uS
void adc_init(void)
{
ADCSRA = 0x00; //disable adc
ADMUX = 0xc1; //select adc input 1
ACSR = 0x80;
ADCSRA = 0xcf;//|| 0x40;
}
#pragma interrupt_handler adc_isr:iv_ADC
void adc_isr(void)
{
//conversion complete, read value (int) using…
ad_value=ADCL; //Read 8 low bits first (important)
ad_value|=(int)ADCH << 8; //read 2 high bits and shift into top byte
temp_flag = 1;
}
//call this routine to initialize all peripherals
void init_devices(void)
{
//stop errant interrupts until set up
CLI(); //disable all interrupts
XDIV = 0x00; //xtal divider
XMCRA = 0x00; //external memory
port_init();
//watchdog_init();
//adc_init();
//timer0_init();
//timer1_init();
//timer2_init();
uart0_init();
uart1_init();
MCUCR = 0x00;
EICRA = 0x00; //extended ext ints
EICRB = 0x00; //extended ext ints
EIMSK = 0x00;
TIMSK = 0x45; //timer interrupt sources
ETIMSK = 0x00; //extended timer interrupt sources
SEI(); //re-enable interrupts
//all peripherals are now initialized
}
/************************************************
发送需要显示的字符/坐标到液晶控制器;
参数1:坐标X;
参数2:坐标Y;
参数3:字符串数组;
************************************************/
void DisString(unsigned short x,unsigned short y,unsigned int word_color,unsigned int ground_color,unsigned char big,char * string)
{
unsigned char i = 0;
SetColor(word_color,ground_color);
//AA 55 00 00 00 00 49 CC 33 C3 3C
TxUart1(0xaa);
if(big)
TxUart1(0x55);
else
TxUart1(0x6f);
TxUart1( (uchar)((x
EIGHT_SWITCH) >> 8) );
TxUart1( (uchar)(x
EIGHT_SWITCH) );
TxUart1( (uchar)((y
EIGHT_SWITCH) >> 8) );
TxUart1( (uchar)(y
EIGHT_SWITCH) );
while(string[i] != 0)
{
TxUart1(string[i]);
i++;
}
TxUart1(0xcc);
TxUart1(0x33);
TxUart1(0xc3);
TxUart1(0x3c);
}