Pic ile DTMF Kontrol

Başlatan ercanatnr, 14 Ekim 2015, 00:53:15

ercanatnr

Merhaba başlıkta da belirttiğim gibi pic ile DTMF kontrol devresi yapmaya çalışıyorum. Aşağıdaki kodlar ile

1 Nolu tuşa basınca 1.Röle Çekiyor.
2 Nolu tuşa basınca 1.Röle Bırakıyor.

3 Nolu tuşa basınca 2.Röle Çekiyor
4 Nolu tuşa basınca 2.Röle Bırakıyor.

Bahsettiğim kodlar aşağıda (tek buton ile komut verilen)
#include <16F628A.h>

#FUSES NOWDT //No Watch Dog Timer
#FUSES INTRC //Internal RC Osc
#FUSES NOMCLR //Master Clear pin used for I/O
#FUSES NOBROWNOUT //No brownout reset
#FUSES NOLVP //No low voltage prgming, B3(PIC16) or B5(PIC18) used for I/O

#use delay(int=4000000)

#int_EXT
void EXT_isr(void) 
{
if(input(pin_b1)==1 && input(pin_b2)==0 && input(pin_b3)==0 && input(pin_b4)==0)
{
output_high(pin_a0);
}
if(input(pin_b1)==0 && input(pin_b2)==1 && input(pin_b3)==0 && input(pin_b4)==0)
{
output_low(pin_a0);
}
if(input(pin_b1)==1 && input(pin_b2)==1 && input(pin_b3)==0 && input(pin_b4)==0)
{
output_high(pin_a1);
} 
if(input(pin_b1)==0 && input(pin_b2)==0 && input(pin_b3)==1 && input(pin_b4)==0)
{
output_low(pin_a1);
}
}

 

void main() {
enable_interrupts(INT_EXT);
enable_interrupts(GLOBAL);
setup_oscillator(OSC_4MHZ);

while(TRUE){
//TODO: User Code
}

}


Bu kodlarda herhangi bir sıkıntım yok. Ancak benim yapmak istediğim devre şu şekilde çalışmalı mesela röleleri 2 tuşla kontrol etmeliyim.
ÖRN:

*1 ile 1. röle çeksin
#1ile 1. röle bıraksın

Bunu yapmak istedim ancak yapamadım. Pice gelen bu 2 bilgiyi nasıl okumalıyım. Aklıma if içine başka bir if fonksiyonu açmak geldi ama sağlıksız olur gibime geldi yardımcı olursanız sevinirim.

t2

#1
iki değişken olsun. Tus1, Tus2.

Bir tuş basılınca süre baslasin. Süre 3sn diyelim. ilk okunan Tus1e esitleniyor. 3saniye içinde tekrar basilirsa Tus2 okunmuş oluyor.
Tus1 okunduysa, yeni okunan tuş, Tus2ye eşitlenecek.

ilk tustan 3saniye Sonra karar verilir.  2tuş da okunduysa 3saniye dolsun diye beklemek gerekmez. Hemen karar aşamasına geçilir.

KARAR!

Süre icinde 2 tane tus basilmadiysa islem yok. Tek tuş basildi süre bitti. Tus1 ve Tus2 sifirlanir.

Tus1=* Tus2=1 ise role çeksin
Tus1=# Tus2=1 ise role bıraksın
......

gibi

ercanatnr

Evet tamda istediğim mantık bunu koda dökmem gerekiyor. Zaten takıldığım noktada orası o konuda bir fikriniz var mı?

ercanatnr

Alıntı yapılan: t2 - 14 Ekim 2015, 09:22:32
iki değişken olsun. Tus1, Tus2.

Bir tuş basılınca süre baslasin. Süre 3sn diyelim. ilk okunan Tus1e esitleniyor. 3saniye içinde tekrar basilirsa Tus2 okunmuş oluyor.
Tus1 okunduysa, yeni okunan tuş, Tus2ye eşitlenecek.

ilk tustan 3saniye Sonra karar verilir.  2tuş da okunduysa 3saniye dolsun diye beklemek gerekmez. Hemen karar aşamasına geçilir.

KARAR!

Süre icinde 2 tane tus basilmadiysa islem yok. Tek tuş basildi süre bitti. Tus1 ve Tus2 sifirlanir.

Tus1=* Tus2=1 ise role çeksin
Tus1=# Tus2=1 ise role bıraksın
......

gibi

Söyledikleriniz doğrultusunda şu şekilde bir kod yazdım. 2 tuşlama arasına 3 sn zaman koydum eğer ki 3 sn i geçerse program başa dönüyor. Herhangi bir yanlışım var mı inceler misiniz simülasyonunu yapamadım. ISIS te CM8870 malesef yok.
#include <16F628A.h>

#FUSES NOWDT                    //No Watch Dog Timer
#FUSES NOMCLR                   //Master Clear pin used for I/O
#FUSES NOBROWNOUT               //No brownout reset
#FUSES NOLVP                    //No low voltage prgming, B3(PIC16) or B5(PIC18) used for I/O
#use delay(internal=4000000)
#define StD pin_b0

int sifre[2],kontrol=0,i,zaman;

#INT_TIMER0
void  TIMER0_isr(void) 
{
zaman++;
if(zaman>70) kontrol=1;
set_timer0(60);
}

void main()
{
   setup_timer_0(RTCC_INTERNAL|RTCC_DIV_256);
   
sifreoku:
{
   zaman=0; //buton gecikme süresini 0 la
   
for(i=0;i<2;i++)
{
   kontrol=0; //buton gecikme kontrol degiskenini 0 la
   set_timer0(60);   
   
   enable_interrupts(INT_TIMER0);
   enable_interrupts(GLOBAL);
   
while(StD==0) //Tuşa basılmadı ise kontrol et
{
if(kontrol==1)  //buton gecikme süresini aşmışsa başa dön
   {
   goto sifreoku;
   } 
}
   
   disable_interrupts(INT_TIMER0);// tuşa basılmış ise timer0 ı durdur    
   disable_interrupts(GLOBAL);
   //zaman degiskenini 0 la böylece yaklaşık 3 sn ek süre kazanılmış olur.
   zaman=0;
   
   sifre[i]=input_a(); //a portunu tümüyle oku sifre degişkenine yaz.
   
while(StD==1); // tuşa basılı ise bekle
 
 } //for parantezi
 } //sifreoku parantezi
   
// Şifre Kontrol 
if(sifre[0]==12 && sifre[1]==1)  //Eğer şifre #1 ise çalıştır
   
   {
   output_high(pin_b0); //1. Röleyi Çek
   delay_ms(300);       //300ms bekle
   output_low(pin_b0);  //1. Röleyi Bırak
   }
   
if(sifre[0]==12 && sifre[1]==2) //Eğer şifre #2 ise çalıştır.
   
   {
   output_high(pin_b1); //2. Röleyi Çek
   delay_ms(300);       //300ms bekle
   output_low(pin_b1);  //2. Röleyi Bırak
   }
   
   
   else        //şifre dogru degil ise şifre okumaya dön
   {
   goto sifreoku;
   }
 
 }

t2

proteusta deneyemediyseniz gerçek devrede deneseniz?

"tamam güzel olmuş " desek bile anlamı olmaz. denenmesi gerek.

ilave bilgi :  CCS C bilmiyorum. kullanmıyorum. kod yanlışsa bile, anlamam.

ercanatnr

Alıntı yapılan: t2 - 15 Ekim 2015, 21:49:12
proteusta deneyemediyseniz gerçek devrede deneseniz?

"tamam güzel olmuş " desek bile anlamı olmaz. denenmesi gerek.

ilave bilgi :  CCS C bilmiyorum. kullanmıyorum. kod yanlışsa bile, anlamam.

Gerçek devrede deneyeceğim ancak bu aralar fazla vaktim yok. CCS C bilmediğinizi bilmiyordum sadece göze çarpan hata var mı onu sormak istedim. İlginiz için teşekkürler.

datax

ercanatnr kardeşim kodlarını gercek devrede deneme imkanın oldu mu  ?

Emre MERMİ

#7
merhaba, arada bekleme koymadan. Yani tuşları 2 şerli gruplayarak şöyle yapıyordum. Belki fikir verir.

#include <16F628A.h>
#use delay(internal=4MHz)



#FUSES NOBROWNOUT               //No brownout reset
#FUSES NOMCLR                   //Master Clear pin used for I/O
#FUSES NOLVP                    //No low voltage prgming, B3(PIC16) or B5(PIC18) used for I/O
#fuses INTRC_IO

 int16 a=0,b=0,c=0;

#INT_EXT
void  EXT_isr(void) 
{
a=a+1;

if(a==3){
a=1;
c=0;
}


if(input(pin_b4)==1 && input(pin_b3)==0 && input(pin_b2)==0 && input(pin_b1)==0)  // 1 e basıldıysa
 {
 
b=1;
 }
if(input(pin_b4)==0 && input(pin_b3)==1 && input(pin_b2)==0 && input(pin_b1)==0)  // 2 ye basıldıysa
 {

b=2;
 }
 if(input(pin_b4)==1 && input(pin_b3)==1 && input(pin_b2)==0 && input(pin_b1)==0)  // 3 e basıldıysa
 {

b=3;
 }
 if(input(pin_b4)==0 && input(pin_b3)==0 && input(pin_b2)==1 && input(pin_b1)==0)  // 4 e basıldıysa
 {
b=4;
 }
 if(input(pin_b4)==1 && input(pin_b3)==0 && input(pin_b2)==1 && input(pin_b1)==0)  // 5 e basıldıysa
 {
b=5;
 }
 if(input(pin_b4)==0 && input(pin_b3)==1 && input(pin_b2)==1 && input(pin_b1)==0)  // 6 ya basıldıysa
 {
b=6;
 }
 if(input(pin_b4)==1 && input(pin_b3)==1 && input(pin_b2)==1 && input(pin_b1)==0)  // 7 e basıldıysa
 {
b=7;
 }
 if(input(pin_b4)==0 && input(pin_b3)==0 && input(pin_b2)==0 && input(pin_b1)==1)  // 8 e basıldıysa
 {
b=8;
 }
 if(input(pin_b4)==1 && input(pin_b3)==0 && input(pin_b2)==0 && input(pin_b1)==1)  // 9 a basıldıysa
 {
b=9;
 }
if(input(pin_b4)==1 && input(pin_b3)==1 && input(pin_b2)==0 && input(pin_b1)==1)  // * a basıldıysa
 {

b=11;
 }
  if(input(pin_b4)==0 && input(pin_b3)==0 && input(pin_b2)==1 && input(pin_b1)==1)  // # ye basıldıysa
 {

b=12;
 }
 
  if(a==1){
 c=c+(b*10);
 

 }
  if(a==2){
 c=c+b;
 

  }
  
} 


void main()
{
setup_oscillator(OSC_4MHZ);
delay_ms(50);
 enable_interrupts(INT_EXT);
   enable_interrupts(GLOBAL);
   ext_int_edge( L_TO_H );

set_tris_a(0x00);
delay_ms(50);
output_a(0x00);
delay_ms(50);
   set_tris_b(0xFF);
delay_ms(50);
 
  
   
 
   while(TRUE)
   {

  
        if(c==111){
 output_high(pin_a6);



c=0;

 }
        if(c==121){
 output_low(pin_a6);

c=0;

 }
        if(c==112){
 output_high(pin_a7);


c=0;

 }
        if(c==122){
 output_low(pin_a7);


c=0;

 }
        if(c==113){
 output_high(pin_a0);


c=0;

 }      
        if(c==123){
 output_low(pin_a0);


 c=0;

 }      if(c==114){
 output_high(pin_a1);


c=0; 

 }     
        if(c==124){
 output_low(pin_a1);

c=0;

 }
        if(c==115){
 output_high(pin_a0);
 output_high(pin_a1);
 output_high(pin_a6);
 output_high(pin_a7);

 c=0;

 }
        if(c==125){
 output_low(pin_a0);
 output_low(pin_a1);
 output_low(pin_a6);
 output_low(pin_a7);

c=0;

 }
 

}

}


Burada mantık çözülen kodun sayı olarak karşılığını yazıp ilk sayıyı 10 ile çarpıp ikinci sayı ile toplamak. Toplam da neye eşitse ona göre röle tetiklemek. Tuşlamalar 2 şerli gruplanarak yapılmıştır. Umarım yardımcı olur. Kodlar kendi kullandığım kodlar.

mesaj birleştirme:: 02 Eylül 2016, 19:54:01

Bu arada ilk mesajı yeni fark ettim baya eskiymiş konu. Umarım konuyu hortlatan arkadaşın işine yarar :D