Butona basılı tutunca tavır değiştirme

Başlatan vitruvius, 01 Aralık 2014, 19:30:04

vitruvius

Merhaba,

Bir keypad uygulaması yapıyorum. Tuşlu telefonlardaki yazı yazma işini yapmaya çalışıyorum. Mesela keypad'de 3'e basınca basış sayısına göre D, E, F, 3 karakterlerini lcd ekranda gösteriyorum. Yapmak istediğim şey şu; eğer 3 tuşuna 0.5 sn basılırsa ekrana "3" yazdırmak.

Şu anda ikisi ayrı ayrı çalışıyor fakat bir arada çalıştıramadım. Yani 0.5 sn bekleme işini devre dışı bırakırsam D, E, F, 3 yazıyor; ya da D, E, F yazma işini devre dışı bırakırsam 0.5 basılı tutunca ekrana "3" yazıyor. İkisi de aktifken 0.5 sn bekleyince ledi toggle ediyor ancak lcd'ye "3" yazmıyor.

74C922 kullanıyorum. Butona basınca timer1'i aktif ediyorum. Buton bırakılınca kapatıyorum. Bu yüzden butona basılıp bırakılma anlarını yakalamak için external int içinde yükselen veya düşen kenar tetiklemesini değiştiriyorum. Kodlarım aşağıda.

#include <16F877A.h>
#fuses XT, NOWDT, NOPROTECT, NOBROWNOUT, NOLVP, NOPUT, NOWRT,NODEBUG, NOCPD
#use delay(clock=4000000)

#use fast_io(b)
#use fast_io(c)
#use fast_io(d)

#define  led1  pin_c0

#include <lcd_lib.c>
#include <keypad_lib.c>
#include <textpad_lib.c>

char  key = 0xFF; 
int1  tim1_05sec_flag = 0; 
int1  edge = 1;                  // Rising = 1, Falling = 0
char  chr = " ";

#int_ext
void ext_int ()
{   
   if(edge == 1)                    // Rising edge.
   {
      key = read_key_number ();     // Hangi numarali tusa basildigini veriyor.
      setup_timer_1(T1_INTERNAL | T1_DIV_BY_8);
      set_timer1(3036);             // Timer1 0.5 sn.
      ext_int_edge(H_TO_L);         // Dusen kenar tetiklemeliye gec
      edge = 0;
   }
   
   else if (edge == 0)              // Falling edge.
   {
      setup_timer_1(T1_DISABLED);   // Buton birakildigi icin timerla artik isim yok.
      ext_int_edge(L_TO_H);         // Yukselen kenar tetiklemeliye don
      edge = 1;
   }
}

#int_timer1
void timer1_int ()
{  
   set_timer1(3036);
   
   if (edge == 0)                   // "Edge" yukarda degismisti.
   {                                // O yuzden edge = 0, yukselen kenara denk geliyor.
      tim1_05sec_flag = 1;          // 0.5 sn icin bayrak
      output_toggle(led1);         
      setup_timer_1(T1_DISABLED);
   }
}

void main()
{
   setup_psp (PSP_DISABLED);
   setup_timer_2 (T2_DISABLED,0,1);
   setup_adc_ports (NO_ANALOGS);
   setup_adc (ADC_OFF);
   setup_CCP1 (CCP_OFF);
   setup_CCP2 (CCP_OFF);   

   set_tris_b (0x01);
   set_tris_c (0x00); 
   set_tris_d (0x0F);  
   
   output_c (0x00);
   
   lcd_init();
   
   lcd_send(0x01);
   
   ext_int_edge(L_TO_H);
   
   enable_interrupts(int_timer1);
   enable_interrupts(int_ext);
   enable_interrupts(GLOBAL);
   
   while (1)
   {      
      if (key == 3)
      {                    
         if (tim1_05sec_flag == 1)  // 0.5 sn basili tutulmussa
         {
            chr = "3";
            printf(lcd_write_single,"%c", chr);       
            tim1_05sec_flag = 0;
         }
         
         if (tim1_05sec_flag == 0)  // 0.5 sn basili tutulmamissa
         {
            chr = key_3();    // key_3 () basilma sayisina gore D, E, F, 3 veriyor
            printf(lcd_write_single,"%c", chr);  
         }
         key = 0xFF; // Sonsuz donguden cikmak icin key degiskenini degistiriyorum.
      }
   }   
}


Teşekkürler.

mücahit

#1
#include <16F877A.h>
#fuses XT, NOWDT, NOPROTECT, NOBROWNOUT, NOLVP, NOPUT, NOWRT,NODEBUG, NOCPD
#use delay(clock=4000000)

#use fast_io(b)
#use fast_io(c)
#use fast_io(d)

#define  led1  pin_c0

#include <lcd_lib.c>
#include <keypad_lib.c>
#include <textpad_lib.c>

char  key = 0xFF; 
int1  tim1_05sec_flag = 0; 
int1  edge = 1;                  // Rising = 1, Falling = 0
char  chr = " ";

#int_ext
void ext_int ()
{  
  if(edge == 1)                    // Rising edge.
  {
      key = read_key_number ();    // Hangi numarali tusa basildigini veriyor.
      setup_timer_1(T1_INTERNAL | T1_DIV_BY_8);
      set_timer1(3036);            // Timer1 0.5 sn.
      ext_int_edge(H_TO_L);        // Dusen kenar tetiklemeliye gec
      edge = 0;
  }
  
  else if (edge == 0)              // Falling edge.
  {
      setup_timer_1(T1_DISABLED);  // Buton birakildigi icin timerla artik isim yok.
      ext_int_edge(L_TO_H);        // Yukselen kenar tetiklemeliye don
      edge = 1;
  }
}

#int_timer1
void timer1_int ()
{  
  set_timer1(3036);
  
  if (edge == 0)                  // "Edge" yukarda degismisti.
  {                                // O yuzden edge = 0, yukselen kenara denk geliyor.
      tim1_05sec_flag = 1;          // 0.5 sn icin bayrak
      output_toggle(led1);        
      setup_timer_1(T1_DISABLED);
  }
}

void main()
{
  setup_psp (PSP_DISABLED);
  setup_timer_2 (T2_DISABLED,0,1);
  setup_adc_ports (NO_ANALOGS);
  setup_adc (ADC_OFF);
  setup_CCP1 (CCP_OFF);
  setup_CCP2 (CCP_OFF);  

  set_tris_b (0x01);
  set_tris_c (0x00); 
  set_tris_d (0x0F);  
  
  output_c (0x00);
  
  lcd_init();
  
  lcd_send(0x01);
  
  ext_int_edge(L_TO_H);
  
  enable_interrupts(int_timer1);
  enable_interrupts(int_ext);
  enable_interrupts(GLOBAL);
  
  while (1)
  {      
      if (key == 3)
      {                    
        if (tim1_05sec_flag == 1)  // 0.5 sn basili tutulmussa
        {
            chr = "3";
            printf(lcd_write_single,"%c", chr);      
            tim1_05sec_flag = 0;
        }
        
        else if (tim1_05sec_flag == 0)  // 0.5 sn basili tutulmamissa
        {
            chr = key_3();    // key_3 () basilma sayisina gore D, E, F, 3 veriyor
            printf(lcd_write_single,"%c", chr);  
        }
        key = 0xFF; // Sonsuz donguden cikmak icin key degiskenini degistiriyorum.
      }
  }  
}