Простые часы на ИВ-28А (Arduino IDE)

ИВ-28А — индикатор цифровой 9-и разряджный вакуумный люминесцентный предназначен для отображения информации в виде цифр от 0 до 9.

Основные параметры индикатора ИВ-28А:

  • Яркость свечения одного разряда  ≥150 кд/м²
  • Угол обзора  ≥80°
  • Ток накала  35+5 мА
  • Ток анодов-сегментов одного цифрового разряда суммарный в импульсном режиме 1,5-2,5 мА
  • Ток сетки одного разряда в импульсном режиме 2-3 мА
  • Напряжение накала — 2,4±0,25 В
  • Напряжения анодов и сетки в импульсном режиме 27-50 В

На базе индикатора ИВ-28А можно собрать простые часы, которые будут отображать часы, минуты, секунды и десятые доли секунд. Для установки текущего времени используются три кнопки. При нажатии кнопки SET начинают мигать индикаторы часов, кнопками UP и DW можно изменить показания часов, при повторном нажатии кнопки SET можно изменить время минут, если нажать кнопку третий раз можно сбросить показания секунд.

Часы собраны на микроконтроллере Atmega8 с частотой кварцевого резонатора 12 МГц. Таймер 1 используется для получения точного интервала времени 0,1 с, таймер 2 управляет динамической индикацией.

// ATMEGA8 12MHz
 
#define G8_B PB1 
#define G7_B PB3 
#define G6_B PB5
#define G5_C PC1
#define G4_B PB0
#define G3_D PD7
#define G2_D PD5
#define G1_D PD3
#define G0_D PD1
 
#define A_D PD0
#define B_D PD2
#define C_D PD4
#define D_C PC2
#define E_C PC0
#define F_B PB2 
#define G_B PB4
#define DP_D PD6
 
#define SET PC3
#define UP  PC4
#define DW  PC5
 
#include <avr/io.h>
#include <util/delay.h>
 
byte a[9],an,segm,i;
int set,msec,sec,min=20,hour=10;
 
 
int main() {
  cli();
// (12000000/((18749+1)x64))=10 Hz
  OCR1A = 18749;
  TCCR1B |= (1 << WGM12);
// Prescaler 64
  TCCR1B |= (1 << CS11) | (1 << CS10);
  TIMSK |= (1 << OCIE1A);
// (12000000/((186+1)x128))=501.33689839572 Hz
  OCR2 = 186;
  TCCR2 |= (1 << WGM21); 
// Prescaler 128
  TCCR2 |= (1 << CS22) | (1 << CS20);
  TIMSK |= (1 << OCIE2);
  sei();
  DDRB|=(1<<G8_B)|(1<<F_B)|(1<<G7_B)|(1<<G_B)|(1<<G6_B)|(1<<G4_B);
  DDRC|=(1<<E_C)|(1<<G5_C)|(1<<D_C);
  DDRD|=(1<<G3_D)|(1<<DP_D)|(1<<G2_D)|(1<<C_D)|(1<<G1_D)|(1<<B_D)|(1<<G0_D)|(1<<A_D);
  DDRC&=~(1<<PC3)|(1<<PC4)|(1<<PC5);
  PORTC|=(1<<PC3)|(1<<PC4)|(1<<PC5);
 
 
while(1) {
  if(((PINC >> SET) & 1) == 0){set++;if(set>3){set=0;}_delay_ms(300);}
  if(((PINC >> UP) & 1) == 0 && set==1){hour++;if(hour>23){hour=23;}_delay_ms(300);}
  if(((PINC >> DW) & 1) == 0 && set==1){hour--;if(hour<0){hour=0;}_delay_ms(300);}
 
  if(((PINC >> UP) & 1) == 0 && set==2){min++;if(min>59){min=59;}_delay_ms(300);}
  if(((PINC >> DW) & 1) == 0 && set==2){min--;if(min<0){min=0;}_delay_ms(300);}
 
  if(((PINC >> UP) & 1) == 0 && set==3){sec=0;msec=0;_delay_ms(300);}
  if(((PINC >> DW) & 1) == 0 && set==3){sec=0;msec=0;_delay_ms(300);}
 
    if(set==1&&(msec==0||msec==5)){a[8]=10;}else{a[8]=hour/10;}
    if(set==1&&(msec==0||msec==5)){a[7]=10;}else{a[7]=hour%10;}
     a[6]=11;
    if(set==2&&(msec==0||msec==5)){a[5]=10;}else{a[5]=min/10;}
    if(set==2&&(msec==0||msec==5)){a[4]=10;}else{a[4]=min%10;}
     a[3]=11;
    if(set==3&&(msec==0||msec==5)){a[2]=10;}else{a[2]=sec/10;}
    if(set==3&&(msec==0||msec==5)){a[1]=10;}else{a[1]=sec%10;}
     a[0]=msec;
 _delay_ms(10);
 
}}
 
ISR(TIMER2_COMP_vect){
    switch(i){
    case 0:  segm=a[0];  an=16;  anod(); _delay_us(1);  if(a[0]==10)an=16;else an=0;  anod();segment(); break;
    case 1:  segm=a[1];  an=16;  anod(); _delay_us(1);  if(a[1]==10)an=16;else an=1;  anod();segment(); break;
    case 2:  segm=a[2];  an=16;  anod(); _delay_us(1);  if(a[2]==10)an=16;else an=2;  anod();segment(); break;
    case 3:  segm=a[3];  an=16;  anod(); _delay_us(1);  if(a[3]==10)an=16;else an=3;  anod();segment(); break;
    case 4:  segm=a[4];  an=16;  anod(); _delay_us(1);  if(a[4]==10)an=16;else an=4;  anod();segment();  break;
    case 5:  segm=a[5];  an=16;  anod(); _delay_us(1);  if(a[5]==10)an=16;else an=5;  anod();segment(); break;
    case 6:  segm=a[6];  an=16;  anod(); _delay_us(1);  if(a[6]==10)an=16;else an=6;  anod();segment(); break;
    case 7:  segm=a[7];  an=16;  anod(); _delay_us(1);  if(a[7]==10)an=16;else an=7;  anod();segment(); break;
    case 8:  segm=a[8];  an=16;  anod(); _delay_us(1);  if(a[8]==10)an=16;else an=8;  anod();segment(); break;
    }i++;if(i>8){i=0;}
  }
 
void segment(){                                                                
   switch(segm){                                                                 
    case 0: PORTD &=~(1<<A_D);PORTD &=~(1<<B_D);PORTD &=~(1<<C_D);PORTC &=~(1<<D_C);PORTC &=~(1<<E_C);PORTB &=~(1<<F_B);PORTB |=(1<<G_B);PORTD |=(1<<DP_D);break;
    case 1: PORTD |=(1<<A_D);PORTD &=~(1<<B_D);PORTD &=~(1<<C_D);PORTC |=(1<<D_C);PORTC |=(1<<E_C);PORTB |=(1<<F_B);PORTB |=(1<<G_B);PORTD |=(1<<DP_D);break; 
    case 2: PORTD &=~(1<<A_D);PORTD &=~(1<<B_D);PORTD |=(1<<C_D);PORTC &=~(1<<D_C);PORTC &=~(1<<E_C);PORTB |=(1<<F_B);PORTB &=~(1<<G_B);PORTD |=(1<<DP_D);break;
    case 3: PORTD &=~(1<<A_D);PORTD &=~(1<<B_D);PORTD &=~(1<<C_D);PORTC &=~(1<<D_C);PORTC |=(1<<E_C);PORTB |=(1<<F_B);PORTB &=~(1<<G_B);PORTD |=(1<<DP_D);break;
    case 4: PORTD |=(1<<A_D);PORTD &=~(1<<B_D);PORTD &=~(1<<C_D);PORTC |=(1<<D_C);PORTC |=(1<<E_C);PORTB &=~(1<<F_B);PORTB &=~(1<<G_B);PORTD |=(1<<DP_D);break;   
    case 5: PORTD &=~(1<<A_D);PORTD |=(1<<B_D);PORTD &=~(1<<C_D);PORTC &=~(1<<D_C);PORTC |=(1<<E_C);PORTB &=~(1<<F_B);PORTB &=~(1<<G_B);PORTD |=(1<<DP_D);break;
    case 6: PORTD &=~(1<<A_D);PORTD |=(1<<B_D);PORTD &=~(1<<C_D);PORTC &=~(1<<D_C);PORTC &=~(1<<E_C);PORTB &=~(1<<F_B);PORTB &=~(1<<G_B);PORTD |=(1<<DP_D);break;
    case 7: PORTD &=~(1<<A_D);PORTD &=~(1<<B_D);PORTD &=~(1<<C_D);PORTC |=(1<<D_C);PORTC |=(1<<E_C);PORTB |=(1<<F_B);PORTB |=(1<<G_B);PORTD |=(1<<DP_D);break;
    case 8: PORTD &=~(1<<A_D);PORTD &=~(1<<B_D);PORTD &=~(1<<C_D);PORTC &=~(1<<D_C);PORTC &=~(1<<E_C);PORTB &=~(1<<F_B);PORTB &=~(1<<G_B);PORTD |=(1<<DP_D);break; 
    case 9: PORTD &=~(1<<A_D);PORTD &=~(1<<B_D);PORTD &=~(1<<C_D);PORTC &=~(1<<D_C);PORTC |=(1<<E_C);PORTB &=~(1<<F_B);PORTB &=~(1<<G_B);PORTD |=(1<<DP_D);break;
    case 11: PORTD |=(1<<A_D);PORTD |=(1<<B_D);PORTD |=(1<<C_D);PORTC |=(1<<D_C);PORTC |=(1<<E_C);PORTB |=(1<<F_B);PORTB &=~(1<<G_B);PORTD |=(1<<DP_D);break;//-
  }
  if(an==1){PORTD &=~(1<<DP_D);}
  }
 
void anod(){
 switch(an){                                                             
    case 0: PORTB |=(1<<G8_B);PORTD &=~(1<<G0_D);break;
    case 1: PORTD |=(1<<G0_D);PORTD &=~(1<<G1_D);break; 
    case 2: PORTD |=(1<<G1_D);PORTD &=~(1<<G2_D);break; 
    case 3: PORTD |=(1<<G2_D);PORTD &=~(1<<G3_D);break; 
    case 4: PORTD |=(1<<G3_D);PORTB &=~(1<<G4_B);break; 
    case 5: PORTB |=(1<<G4_B);PORTC &=~(1<<G5_C);break; 
    case 6: PORTC |=(1<<G5_C);PORTB &=~(1<<G6_B);break; 
    case 7: PORTB |=(1<<G6_B);PORTB &=~(1<<G7_B);break;  
    case 8: PORTB |=(1<<G7_B);PORTB &=~(1<<G8_B);break;
 
   case 16: PORTD |=(1<<G0_D);PORTD |=(1<<G1_D);PORTD |=(1<<G2_D);PORTD |=(1<<G3_D);PORTB |=(1<<G4_B);PORTC |=(1<<G5_C);PORTB |=(1<<G6_B);PORTB |=(1<<G7_B);PORTB |=(1<<G8_B);break;                                                     
  }}   
 
ISR(TIMER1_COMPA_vect){
  msec++;
  if(msec>9){msec=0;sec++;}
  if(sec>59){sec=0;min++;}
  if(min>59){min=0;hour++;}
  if(hour>23){hour=0;}
  }

Форум — http://forum.rcl-radio.ru/viewtopic.php?pid=5438#p5438

Добавить комментарий

Войти с помощью: