attiny13做的手电仿真可以实现,焊接实物后按键换挡没有作用。
先上电路图:http://cache.amobbs.com/bbs_upload782111/files_35/ourdev_607597CFFLLR.png
(原文件名:SD.png)
程序如下:
/*****************
接线说明: PB0: PWM输出, 控制模式
PB1: (档位切换)按键输入检测, 平时为高电平, 有按键时变为低电平
熔丝位设置 :
1: SPIEN = 0 SPI下载使能
2: EESAVE = 1 芯片擦除时EEPROM擦除
3: WDTON = 1 开门狗禁用
4: CKDIV8 = 0 时钟不8分频
5: SUT1:0 = 00 快速上电
6: CKSEL1:0 = 10 使用内部9.6MHZ频率
7: SELFPRGEN = 0
8: DWEN = 0
9: BODLEVEL1:0= 10 BOD触发电平1.8V
10: RSTDISBL = 0; 外部复位禁用
*****************/
#include <inavr.h>
#include <iotiny13.h>
volatile unsigned int flash_sign = 0x00;
volatile unsigned int key_pattern = 0x00;
volatile unsigned int sos_count1 = 0x00;
volatile unsigned int sos_count2 = 0x00;
/****************
功能与切换状态的设置
****************/
#define Dis_Min 1 //低亮10%
#define Dis_Mid 2 //中亮30%
#define Dis_Max 3 //高亮100%
#define Dis_Flash 4 //暴闪
#define Dis_Sos 5
//SOS求救信号(3短3长3短)
//长的时间是三个短的时间
//短和短,长和长之间的间隔为一个短的时间
//短和长之间的间隔是三个短的时间
//两次发送间隔是7个短的时间
#define Dis_top 5 //支持模式最大值
/****************
占空比设置
****************/
#define Stack_min0xe0
#define Stack_mid0xa0
#define Stack_max0x01
#define Stack_flash0xd0
#define Stack_sos 0xb0
/***************
Use_eeprom=1 亮度记忆功能
Use_eeprom=0 没有亮度记忆功能
***************/
#define Use_eeprom 0
/****************
PB0为PWM模式输出;
PB1为按键信号检测,控制模式切换
****************/
void IO_init(void)
{
DDRB = 0x1d; //0001 1101
PORTB = 0x02;//0000 0010
}
void Inter_pwm(void)
{
TCCR0B = 0x00; //关T/C0
PORTB &= 0xfe;
TCNT0 = 0x00; //设置TC0计数寄存器初值
TCCR0A = 0xc3; //比较匹配时set OC0A;TOP时clr OC0A
TIMSK0 &= 0xf1; //屏蔽OCIE0A与TOIE0中断
TCCR0B = 0x01; //开T/C0;开T/C0;不预分频
}
void Inter_ctc(void)
{
TCCR0B = 0x00; //关T/C0
PORTB &= 0xfe;
TCNT0 = 0x00; //设置TC0计数寄存器初值
TCCR0A = 0x02; //CTC模式
TIMSK0 |= 0x0f; //输出比较匹配OCIE0A 中断使能
SREG |= 0x80; //开启全局中断I
TCCR0B = 0x05; //开T/C0;1024分频
}
void Display_status(unsigned int Dis_st)
{
if(Dis_st == Dis_Flash)
flash_sign = 0x01;
else
flash_sign = 0x00;
switch(Dis_st)
{
case Dis_Min: OCR0A = Stack_min;
Inter_pwm();
break;
case Dis_Mid: OCR0A = Stack_mid;
Inter_pwm();
break;
case Dis_Max: OCR0A = Stack_max;
Inter_pwm();
break;
case Dis_Flash: OCR0A = Stack_flash;
Inter_ctc();
break;
case Dis_Sos: OCR0A = Stack_sos;
sos_count1 = 0x00;
sos_count2 = 0x00;
Inter_ctc();
break;
}
}
#if Use_eeprom
#define ER_address 0x00//设置数据在EEPROM中存储地址
void EEPROM_write(unsigned char Address, unsigned char Data)
{
SREG &= 0x7f; //关全局中断;防止写操作有中断产生
while(EECR & 0x02); //等待上一次写操作结束
EECR &= 0x0f; //设置编程模式
EEAR = Address;
EEDR = Data; //设置地址与数据寄存器
EECR |= 0x04;
EECR |= 0x02; //启动写操作
SREG |= 0x80; //开全局中断
}
void EEPROM_read(unsigned char Address)
{
while(EECR & 0x02); //等待上一次写操作结束
EEAR = Address;
EECR |= 0x01; //启动读操作
key_pattern = EECR;
Display_status(key_pattern);
}
#endif
void Key_check(void)
{
static unsigned int key_sign = 0x00;
static unsigned int i = 0x00;
#if Use_eeprom
static unsigned int j = 0x00;
if(key_sign==0x01)
{
if(++j>100)
{
EEPROM_write(ER_address, key_pattern);
j = 0x00;
}
}
#endif
if((PINB&0x02)==0x00)
{
i++;
if(i>200)
key_sign = 0x01;
}
if(key_sign == 0x01)
{
i = 0x00;
if((PINB&0x02)==0x02)
{
PORTB ^= 0x04; //test
if((++key_pattern)>Dis_top)
key_pattern= 0x01;
Display_status(key_pattern);
key_sign = 0x00;
}
}
}
#pragmavector = TIM0_COMPA_vect
__interrupt void CTC_COMPA(void)
{
TIFR0 &= 0xfa; //清除 OCF0A输出比较标志位
if((TCCR0A & 0x02) == 0x02)
{
if(flash_sign == 0x01)
PORTB ^= 0x01;
else
{
if(sos_count1 > 0)
sos_count1--;
else
{
PORTB ^= 0x01;
switch(++sos_count2)
{
case 0x06: sos_count1 = 0x02;
break;
case 0x07: sos_count1 = 0x02;
break;
case 0x09: sos_count1 = 0x02;
break;
case 0x0b: sos_count1 = 0x02;
break;
case 0x0c: sos_count1 = 0x02;
break;
case 0x12: sos_count1 = 0x06;
sos_count2 = 0x00;
return;
}
}
}
}
}
void main(void)
{
IO_init();
#if Use_eeprom
EEPROM_read(ER_address);
#else
key_pattern = Dis_Sos;
Display_status(key_pattern);
#endif
while(1)
{
Key_check();
}
}
这个程序用POTUES仿真可以,但是我用实物仿真的时候开关电后档位不会发生变化;即使我把PB1口设置为按键输入直接拉低 档位也不会变化。。。。小弟第一次学写程序 希望各位前辈指点指点 。。。。先在此谢谢过。。。 听我的建议,对于初学者,不要使用什么“仿真”,从简单的DD开始,实物练习。
等你具备了一定的水平和能力后,才知道如何真正使用仿真。
一根接线接错了,二极管装反了,溶丝位设置不对,这个你能“仿真”出来吗?这种查错的能力不是仿出来的,只能在实际的做中得到锻炼和经验。 1楼说的很对啊!
看了楼主(代表了当前大部分的“好学生”,因为“坏学生”们都去“不务正业”了)的描述,我也很感慨的:
这也是我们教育的问题,很严重的问题:理论和实践的严重脱节!
我想对楼主说,你到大学学习,更重要的是要学会分析问题和解决问题的能力,可很遗憾,在你的言论中我看得出,你还不具备。
例如,上述的电路,其实可以分成两个相互独立的单元,分别进行调试的。一块是LED驱动,一块是PWM。可是你却只是抛出一整个大问题,全部的电路,加上全部的程序,丢给大家来解决,这怎么行呢?
然后,就是仿真。仿真只是验证你设计阶段的想法的一个手段。特别是在试制成本非常高的时候(比如IC设计),这是有用的手段。但是,并非仿真就一定等于实际。有时候仿真过了,实际的通不过;甚至会发生仿真通不过而实际可用的情况。
最后我要感慨一下不少人对“科学”二字的认识。比如前段时间的中_医(伪)科学之争。我看倒一个能左右大众思想言论的学者,竟然抛出这样的话语,很是伤心!
什么是科学?能验证的是科学吗?“中”医是不能用现阶段的科学理论来验证的,那它就是不科学的,就该废除吗?
恰恰相反,科学是探索,是发现,是否定,是证伪。 十分感谢 machao 和 Cliff 的建议和指点。。。程序中问题已经解决, 同时验证了仿真有时候不一定可靠。 mark 我也在学习
请问最后问题在那!谢谢! LZ不就问个小问题。。。。真能扯。。。
页:
[1]