Arkadaslar Merhaba,
Bir projemde ek fonksiyon olarak eger bir tusa 3 sn basılı tutulursa bir işlemi yaptırılmasıyla alakalı nasıl bir kod yapısı kullanmalıyım.
Selamlar..
herhangi bir timer fonksiyonu icinde tusa basilma sarti ile bir degiskeni 3 ten sifira yada 0 dan 3 e saydirarak yapabilirsin; 3 ten sifira yaparsan tusa basilmazken degiskenine surekli 3 at.0 dan 3 e yaparsanda 0 at.
Merhaba şoyle birşey yaptim ama uygun olurmu arkadaşlar
while(true)
{
if(input(pin_a0))
{
X++;
Delay_ms(100);
}
if(x==10)
{
Output_high(pin_a1);
}
}
Arkadaşlar elinde hazır kodu olan veya mantiğini yazabilirmisiniz
Öyle olmaz. Butona basılı olduğu sürece sistem 100ms kadar çakılı kalacaktır. Programınız bu şekilde manipülasyona açık hale gelir.
Yapmanız gereken basit bir Timer kurmak. 1ms 10ms 100ms hangi çözünürlükte çalışmak istediğinize bağlı olarak değişebilir. Ben 1ms tercih ediyorum.
Timer kesme alt rutininde buton durumunu kontrol edeceksiniz ve eğer butona basılıyorsa Counter değişkeninizi 1 artıracaksınız. Sonra eğer Counter > Threshold ise bir flag değişkeninin durumunu True'ya çekeceksiniz. Daha sonra ana döngü içerisinde bu flag değişkenini kontrol ederek gerekli işlemleri yaptıracaksınız. Butona basılmadığı durumlarda ise Counter değişkenini sıfırlayacaksınız. Ana döngüde çalıştıracağınız kod parçacığının sonunda flag değişkenini temizlemeyi unutmayın.
Bu mantık ile bir butona birden çok işlev yüklemek mümkündür.
Kolay gelsin...
Alıntı yapılan: serkancetin - 04 Aralık 2017, 11:01:39
Arkadaşlar elinde hazır kodu olan veya mantiğini yazabilirmisiniz
hazır kodla yaparsan mantığı kavrayamazsın.
while(true)
{
if(input(pin_a0))
{
X++;
Delay_ms(100);
}
if(x==10)
{
Output_high(pin_a1);
}
}
bu yazdığın kodda eksik ; en başta x=0; diye belirtmelisin bu birincisi;
ikincisi 0.1 saniye geç kalsan x=11 olur ve tine yaptıramazsın.Kısacası şunu diyeyim bu yapmak istediğin olay bu yazdığın mantık doğru gibi gözükebilir ama bu şekilde yapmak yanlış olur.Timerler ile ile yapmak daha mantıklı olacaktır.
Alıntı yapılan: Cemre. - 04 Aralık 2017, 11:09:08
Öyle olmaz. Butona basılı olduğu sürece sistem çakılı kalacaktır. Programınız bu şekilde manipülasyona açık hale gelir.
Yapmanız gereken basit bir Timer kurmak. 1ms 10ms 100ms hangi çözünürlükte çalışmak istediğinize bağlı olarak değişebilir. Ben 1ms tercih ediyorum.
Timer kesme alt rutininde buton durumunu kontrol edeceksiniz ve eğer butona basılıyorsa Counter değişkeninizi 1 artıracaksınız. Sonra eğer Counter > Threshold ise bir flag değişkeninin durumunu True'ya çekeceksiniz. Daha sonra ana döngü içerisinde bu flag değişkenini kontrol ederek gerekli işlemleri yaptıracaksınız. Butona basılmadığı durumlarda ise Counter değişkenini sıfırlayacaksınız. Ana döngüde çalıştıracağınız kod parçacığının sonunda flag değişkenini temizlemeyi unutmayın.
Bu mantık ile bir butona birden çok işlev yüklemek mümkündür.
Kolay gelsin...
Tam olarak
@Cemre. ustanın dediklerini yapacaksın.Senin dediğin halde çok kararsız olur.Olmaz mı olur ama çok kullanışsız olur sürekli hata olur arada bir doğru çalışır falan.
İyi Çalışmalar
Timer ların herhangi birini kullansak olurmu.deneyim ustam. Bazı yerlerde kullaniyorlar 30 sn basili tutun reset atsin veya star versin gibi.
@Teğmen ustam int x=0; onu yazmayi gerek duymadim donguyu göstermek istedim.
@cemre ustam verdigin terimlere uzakım biraz. Araştirayim. Önerdiginiz bir yazi kitap site varsa oraya bakayim. Web sayfalarina baktimda uygun birşey bulamadım
Tamam, adım adım gidelim.
Button_Counter isimli unsigned short tipinde global bir değişken oluşturun.
1ms'de bir interrupt (kesme) üretecek bir Timer kurun. Kesme alt rutininde butonun bağlı olduğu inputun (girişin) durumunu
if(input_xx == 1)
{
Button_Counter++;
}
else
{
Button_Counter = 0;
}
gibi bir kod parçası ile kontrol edip Button_Counter değişkenini artırın.
Debug yaparak bu değişkenin sadece ve sadece butona bastığınız sürece arttığını görün.
Daha sonra gerekli geliştirmeleri yaparak bunu süre kontrollü bir bayrak şeklinde kullanmaya çalışacağız...
@cemre ustam akşam denedigimde yazayim.size olurmu. Çok saolasin
Alıntı yapılan: serkancetin - 04 Aralık 2017, 11:19:26
Timer ların herhangi birini kullansak olurmu.deneyim ustam. Bazı yerlerde kullaniyorlar 30 sn basili tutun reset atsin veya star versin gibi. @Teğmen ustam int x=0; onu yazmayi gerek duymadim donguyu göstermek istedim.@cemre ustam verdigin terimlere uzakım biraz. Araştirayim. Önerdiginiz bir yazi kitap site varsa oraya bakayim. Web sayfalarina baktimda uygun birşey bulamadım
@serkancetin usta hangi, derleyici kullanıyorsunuz CCS C ise onunla ilgili güzel dökümanlar var kitap,pdf v.s
Ccs c kullaniyorum elimde serdar çicek hocanin kitabi var.
@serkancetin usta dökümanlardan Timer uygulamaları kısmını iyice bir inceleyin. Timer yapılarının sayıcı ve zamanlayıcı olarak kullanıldığını anladığınızda çoğu programı yazarken çok kolaylık sağlayacaktır.
#define NULL 0
#define ENTER 1
#define UP 2
#define BUTTON_INTERVAL 400
unsigned short input;
unsigned short buttonUpCounter;
void readButton(void)
{
if(input == NULL)
{
if(BUTTON1 == 0)
{
buttonUpCounter++;
}
else
{
if(buttonUpCounter > BUTTON_INTERVAL)
{
input = ENTER;
buttonUpCounter = 0;
}
else if (buttonUpCounter > 0)
{
input = UP;
buttonUpCounter = 0;
}
}
}
}
bana lazım olmuştu zamanında, şu şekilde birşey yazmıştım. burada, bir timer kurup readButton() fonksiyonunu bu timer interrupt rutini içerisinde çağırıyorsunuz. Buton, koyduğunuz zaman aralığı(BUTTON_INTERVAL) * timer süresi (1ms) kadar basılı tutulursa (ENTER) daha kısa basılı tutulursa (UP) olacak şekilde işlem görüyor. Anlamadığınız nokta olursa sorun, yardımcı olmaya çalışalım.
@foseydon gerekli kod parçasını da paylaşmış. Lütfen işin mantığını anlamaya çalışın. Kesmeler, Timer'lar vs. bunlar bu işin temeli ve olmazsa olmazıdır. Aksi halde LED yak-söndürden öteye geçmek çok zor...
@foseydon'un örneğine ek olarak, buttonUpCounter > 0 demek yerine buraya da 25-50ms gibi bir süre eklenirse "button debounce" fonksiyonu da bu yolla halledilmiş olur. Tadından yenmez :)
@foseydon ustam verdiginiz ornekte pin giriş ve çıkışlari define ilemi belirlicez.onalari nerede kullanacaz. C çaliştim biraz ama derin detaylarini daha ögrenemedim. Çok saolasin ilgilendigin için.
Alıntı yapılan: serkancetin - 04 Aralık 2017, 13:12:57@foseydon ustam verdiginiz ornekte pin giriş ve çıkışlari define ilemi belirlicez.onalari nerede kullanacaz. C çaliştim biraz ama derin detaylarini daha ögrenemedim. Çok saolasin ilgilendigin için.
#define BUTTON1 pin.tanimi olacak eklememisim onu
@foseydon @Teğme
@cemre bu şekilde olurmu sizce.
#include<12f683.h>
#fuses intrc_io,nowdt,nomclr
#use delay(clock = 4m)
int sure;
void main()
{
set_tris_a(0xff);
//set_tris_b(0x00);
SETUP_CCP1(CCP_PWM);
setup_timer_2(T2_DIV_BY_16,255,1);
sure = 0;
while(true)
{
if(input(pin_a0)==1 && sure < 255)
{
set_pwm1_duty(sure);
delay_ms(100);
sure = sure + 1;
if(sure>11)
{
output_high(pin_a4);
}
}
if(input(pin_a1)==1 && sure > 0)
{
set_pwm1_duty(sure);
delay_ms(100);
sure = sure - 1;
if(1>sure)
{
output_low(pin_a4);
sure=0;
}
}
}
}
Xc8 derleyicisi için kullandığım yapıyı aşağıdaki videolarda açıkladım. Ufak değişiklikler ile kodu ccsc de de kullanabilirsiniz. Kodun çalışması için her 1ms de artan bir sayaç yaptım.
https://youtu.be/TYUCASUAMg0
https://youtu.be/Ey1IhsIq2KQ
Alıntı yapılan: serkancetin - 04 Aralık 2017, 20:35:29
@foseydon @Teğme @cemre bu şekilde olurmu sizce.
#include<12f683.h>
#fuses intrc_io,nowdt,nomclr
#use delay(clock = 4m)
int sure;
void main()
{
set_tris_a(0xff);
//set_tris_b(0x00);
SETUP_CCP1(CCP_PWM);
setup_timer_2(T2_DIV_BY_16,255,1);
sure = 0;
while(true)
{
if(input(pin_a0)==1 && sure < 255)
{
set_pwm1_duty(sure);
delay_ms(100);
sure = sure + 1;
if(sure>11)
{
output_high(pin_a4);
}
}
if(input(pin_a1)==1 && sure > 0)
{
set_pwm1_duty(sure);
delay_ms(100);
sure = sure - 1;
if(1>sure)
{
output_low(pin_a4);
sure=0;
}
}
}
}
1. CCS bilmiyorum, bunu dikkate alınız.
2. Kod paylaşırken indent yapmaya özen gösteriniz, ki okunaklı olsun.
3. Kod yazarken makro kullanarak anlamsız tanımlamaları anlamlı hale getirin. Hem değiştirmesi kolay olur, hem okuyan(buna kendinizde dahilsiniz) daha rahat anlar.
Bu şekilde ne olur mu? ben anlamadım. Bu kod ile yapılmak istenen nedir? Onu da söylemeniz gerekiyor ki anlayalım. Benim anladığım kadarı ile pin_a0 bir butona bağlı(buton1) ve pin_a1 diğer butona bağlı(buton2)
buton1'e bastığınız zaman 100ms aralıklarla süreyi artırıyor ve 11den büyükse süreye eşit duty çıkışı veriyor. button2'ye bastığınız zaman 100ms aralıklarla süreyi azaltıyor ve süre 0a eşitlenince duty çıkışını kesiyor.
Alıntı yapılan: serkancetin - 04 Aralık 2017, 20:35:29
@foseydon @Teğme @cemre bu şekilde olurmu sizce.
#include<12f683.h>
#fuses intrc_io,nowdt,nomclr
#use delay(clock = 4m)
int sure;
void main()
{
set_tris_a(0xff);
//set_tris_b(0x00);
SETUP_CCP1(CCP_PWM);
setup_timer_2(T2_DIV_BY_16,255,1);
sure = 0;
while(true)
{
if(input(pin_a0)==1 && sure < 255)
{
set_pwm1_duty(sure);
delay_ms(100);
sure = sure + 1;
if(sure>11)
{
output_high(pin_a4);
}
}
if(input(pin_a1)==1 && sure > 0)
{
set_pwm1_duty(sure);
delay_ms(100);
sure = sure - 1;
if(1>sure)
{
output_low(pin_a4);
sure=0;
}
}
}
}
@serkancetin usta senin yazdığın kod ilk sorduğunla alakalı değil,olsa bile buna gerek yok bu PWM başka bir olay.Sen en başta dökümanlardan timer kısmına çalış sayıcı ve zamanlayıcı nedir bu ikisine bir bak burdan devam edelim.Sindire sindire ilerle
Ustam unceliyorum. Uygun bir örnek yapinca paylaşayim.
#include <16F877A.h>
#device adc=10
#FUSES NOWDT //No Watch Dog Timer
#FUSES XT //Crystal osc <= 4mhz for PCM/PCH , 3mhz to 10 mhz for PCD
#FUSES NOPUT //No Power Up Timer
#FUSES NOPROTECT //Code not protected from reading
#FUSES NODEBUG //No Debug mode for ICD
#FUSES NOBROWNOUT //No brownout reset
#FUSES NOLVP //No low voltage prgming, B3(PIC16) or B5(PIC18) used for I/O
#FUSES NOCPD //No EE protection
//#FUSES WRT_50% //Lower half of Program Memory is Write Protected
#use delay(clock=4000000)
#use rs232(baud=9600,parity=N,xmit=PIN_C6,rcv=PIN_C7,bits=8)
#use fast_io(b)
long zaman=0; //Değişkenlerimiz başlangıç değerleriyle tanımlanmaktadır.
int sayac=0;
#int_timer0 //timer0 kesmesi oluşturuldu.
void zamanlayici() //timer0 fonksiyonu oluşturuldu.
{
set_timer0(60); //Saymaya başlanılacak değer tekrar tanımlandı.
sayac++; //her kesmeye girişte sayac 1 arttırılmaktadır.
//20 kez kesmeye girildiğinde 1 saniye oluşmaktadır ve 1 saniye
//oluşma koşulu test edilektedir.
//if (sayac ==20)
if(input(pin_a4))
{
delay_ms(10);
zaman++; //zaman ifadesi 1 arttırılmaktadır.
//b portunun çıkşına 8 adet led bağlandığından geçen zamanı en fazla 255
//saniye olarak gözlemlediğimizden zaman 257 olduğunda zaman ifadesini
//0(sıfır) değerine çekmekteyiz.
if(zaman==60)
{
output_low(pin_b0);
zaman=0;
}
if(zaman==30) output_high(pin_b0);
//output_b(zaman); //Oluşan zaman ifadesi binary olarak b portunda gösterildi.
sayac=0; //1 saniyeyi tekrar elde etmek için sayacımızı sıfırladık.
}
}
void main()
{
setup_timer_0(rtcc_internal | rtcc_div_256); //timer0 için setup ayarları yapıldı.
set_timer0(60); //Saymaya başlanılacak değer 60 olarak belirlenmektedir
enable_interrupts(int_timer0); //timer0 kesmesi aktif duruma getirildi.
enable_interrupts(global); //timer0 kesmesi global duruma getirildi.
set_tris_b(0x00); //b portundaki pinler çıkış olarak tanımlandı.
output_b(0x00); //b portundaki ledler sönük duruma getirildi.
while(true); //Programın sürekli çalışması için sonsüz döngü oluşturulmaktadır.
}
ustalarım bakarmısnız. buton basma süresi timer0 ın zamanlayıcı olarak kullanıldı
arkadaşlar buton basma süresi yapamadım yapabilen arkadaş var mı. maksadım öğrenmek :(
Kesme icinde iviz zivir isler yapmamalisin. Sayacini arttir gec.
Ana dongu icinde butonun durumuna bakacaksin. Butona basildiginda timer'i baslatacaksin, buton birakildiginda timer'i kapatip sayacini okursun. Sonra gerekli matematiksel islemleri yapar ne kadar zaman gecmis hesaplarsin ve de sayacini bir sonraki butona basma durumu icin sifirlarsin.