Arduino ve PCF8574 LCD modülünü dijital pim çoklayıcı olarak kullanma.

Bu yazıda karşılaşacağınız konular.
1- Arduino
wire kütüphanesi kullanılması, ve PICBASIC ile I2C haberleşmesi
2-
PCF8574 ve PCF8574A entegreli I2C LCD Modül adreslemesi,
3-
Aynı modülün I2C dijital I/O port çoklayıcı olarak kullanılması.

Arduino ile PCF8574 I2C LCD modülün, I/O port genişletici olarak kullanılması.

Neden I/O port genişleticiye ihtiyaç duyarız. Dijital pimlerimiz bazen yetmez. Bundan dolayı ihtiyaç duyarız bazen de yeni bir deneme yapmak istediğimizde kısa devre tehlikesi varsa mikrokontrolcü yanmasın diyorsak, denemede gerekirse diğer ucuz entegre yansın diyorsak, yine bu tip çoklayıcılara ihtiyaç duyarız.
İngilizce olarak expander diye geçer. Anlamı genişletici demektir. Bu tip devrelere bizler çoklayıcı diyebiliriz.

Bu tip devreler için bir çok entegre var. (TCA9539:16 I/O, MCP2317: 16 I/O, PCF8575: 16I/O, TCA6424A: 24 I/O, PCF8574A: 8 I/O, PCF8574 : 8 I/O ) Bu yazıda avantajlarından dolayı PCF8574 entegresini seçtim. Her amatör arkadaş bir adet çoklayıcı bir adet de LCD kontrol modülü bulundurmasın diye bu entegrenin kullanıldığı modülü temel aldım.

Bu çoklayıcılar sadece dijital çoklayıcıdır. Şayet analog çoklayıcı isterseniz, bu yazımı okumanızı öneririm.

Bu modül aynı zamanda LCD kontrol modülü olarak satılıyor. Bizler bu modülü dijital I/O port çoklayıcı olarak rahatlıkla kullanabiliriz. I2C olduğu için 2 kablo kullanarak 8 dijital pim daha kazanırız. İstersek PCF8575 kullanıp 16 pim kazanma şansımız da var tabii ki. Ayrıca bir den fazla modül kullanarak aynı SDA ve SCL ile ve modül adreslerini ayarlayarak 7 modül kullanabiliriz. Bu da 56 dijital I/O port fazladan kullanabiliriz demektir.  8 Bacaklı bir entegre ile 56 adet röle sürdüğünüzü hayal edin. 

Bu modülün çalışma şekli bazılarınıza ters gelebilir. Mesela bir led yakmak istediğimizde, genellikle dijital pime 1 direnç bir led bağlarız. Ledin katod ucunu ise şaseye bağlarız ve bu şekilde kullanırız. Bu modülde Hem input hem output yapıyoruz. Fakat INPUT kısmını Pim HIGH olduğunda kontrol edeceğinden, bizim ledlerimiz LOW durumunda çalışmalı.  Bu entegreyi kullanıyorsanız SAĞDAKİ gibi ACTIVE LOW çalışmasını seçmelisiniz. 

Çalışma şeklini anlatmadan önce fiyatlarından da bahsetmek gerekir. Bu modülün avantajlarından biri LCD de kullanılmasının yanı sıra hiç değişiklik yapmadan dijital çoklayıcı olarak da kullanılması. Ayrıca diğer avantajı da fiyatıdır. Çok üretildiğinden modülü 5TL civarına alabiliyorsunuz. Tek başına entegre alayım deseniz 9Tl civarındadır. Yani fiyat avantajı da bulunmaktadır. Bir LCD modül bir de çoklayıcı modül alayım deseniz en az 15TL.

Şimdi de piyasadaki çoklayıcı modüllere göre dezavantajını görelim. Normal dijital çoklayıcıda bulunan INT bacağı LCD modülde kullanılmadığı için entegre bacağı boş bırakılmış. İhtiyaç duyarsanız bir kablo lehimleyip alabilirsiniz. Bunun dışında bir fark yoktur. Bu uç sadece INPUT olarak kullanmak istediğinizde kullanılabilir. O da isteğe bağlıdır. Programda rutin olarak INPUT kontrolü yapıyorsanız buna gerek kalmayabilir.

Öncelikle ARDUINO WIRE kütüphanesinin nasıl çalıştığına bakalım. I2C için bu kütüphane kullanılmak zorundadır. Gelişmiş programcılar I2C sinyalini kendileri oluşturabilirler. Fakat bizler bunu kütüphane olarak kullanmalıyız. Bu modülü LCD de kullanırken, kullandığınız gibi bir kütüphane kullanmanıza da gerek yok. Sadece I2C için wire kütüphanesi yeterlidir.
Ayrıca önemli bir nokta SDA ve SCL pimlerine PULL UP direnç bağlanmasıdır. Bu, modülünüzde yoksa siz bağlamak zorundasınız. Bunun değeri 4K7 -10K arasındadır. Yavaş bir haberleşme hızı seçildiyse 10K, daha hızlı bir haberleşme seçildiyse 4K7 direnç kullanabilirsiniz. ( LCD modül üzerinde bu dirençler yer aldığı için bu modülü kullanırken ayrıca direnç kullanmanıza gerek yoktur. )
Bu kütüphane A4 ve A5 SDA,SCL pimlerine göre çalışır. Bir değişken değeri gönderip almak için 3 satırlık dizilim vardır.

Bilgi göndermek için :
Wire.beginTransmission(32); // transmit to device #4  ( 32 bağlantı kurulacak cihazın adresidir )
Wire.write(B00001111);              // sends one byte
Wire.endTransmission();    // stop transmitting
ya da
Wire.beginTransmission(0x20); // transmit to device #4 ( 0x20  bağlantı kurulacak cihazın HEX adresidir ) isterseniz desimal ya da HEX olarak verebilirsiniz.
Wire.write(TEMP);              // sends one byte TEMP değişken olarak önceden tanımlanmalı.
Wire.endTransmission();    // stop transmitting

Bilgi almak için :
Wire.requestFrom(0x20, 1);  // istek yapılıyor adres bilgisiyle 1= 1 Byte okumak için. Birden fazla  byte da okuyabilirsiniz.
temp1 = Wire.read();           // Temp1 değişkeni önceden tanımlanmalı
Wire.endTransmission();   // Durdurma  Bu satıra alırken gerek olmasa da ben yazdım isteğe bağlı.

WIRE kütüphanesini kullanmak bu kadar basittir.
Detaylı bilgi : https://www.arduino.cc/en/Reference/Wire

PICBASIC  te I2C kullanmak isterseniz Aşağıdaki gibi kullanabilirsiniz. Örnek sayfa için buraya bakabilirsiniz. (https://melabs.com/samples/PBP-mixed/i2c.htm)

DPIN= SDA , CPIN=SCLK $A0=adres  , B0= Cihaz içindeki register adresi , [B0] Alınacak ya da yazılacak veridir.
I2CWRITE DPIN,CPIN,$A0,B0,[B0]    bilgi göndermek için. B0 2 kez kullanılmıştır. Birincisi cihaz içerisindeki adresi belirtmek içindir. Bazı cihazlarda hem cihaz adresini vermelisiniz hem de cihaz içindeki bilgi yazacağınız adresi göndermeniz gerekebilir. İhtiyaç yoksa buraya sadece , koyarsınız.
I2CREAD DPIN,CPIN,$A0,B0,[B1,B2]   bilgi almak için. [B1,B2]:  B0 registerinden itibaren 2 adet değişken okunacağını ve gelen verilerin bu değişkenlere aktarılacağını belirtir.

Adresleme : 
[(D=data) D7:MSB (en yüksek bit) D0=LSB (en düşük bit) temsil eder. ]

Adreslemesi ise cihaza özel olmakla birlikte, D7-D1 arasındakiler değişse bile D0 özeldir. Bu tüm cihazlar için böyledir. Bundan dolayı WIRE kütüphanesi, göndermek ve almak için D0 bitini otomatik değiştirir. Bizler adres olarak sadece 7 bitlik D7-D1 arasındaki kodu veririz. Desimal ( DEC ) ya da HEX olarak verebiliriz. Wire kütüphanesi okuyacaksa D0 bitini 1 yapar. Yazma işleminde ise 0 yapar.
Aşağıdaki tabloda PCF8574 ve PCF8574A adresleme bitleri görünmektedir.

Aradaki farkı görmeniz için PCF8574A entegresi de verilmiştir. Bu tip modüllerin bazıları PCF8574 entegresiyle, bazı modüller ise PCF8574A entegresiyle yapılmış olabilir. Elinizdeki modülün entegresine bakarak adreslemesini ayarlayabilirsiniz. Buradaki fark sabit yazılan slave adresin 4.5.6. bitlerinin farkıdır. Bu şekilde adres farklılığı ortaya çıkmaktadır. Adres verirken sayı sanki 7 bitlik bir sayı gibi düşüneceğiz. Yukarıdaki PCF8574 adreslemesine baktığımızda 0100xxx sayısını görebiliriz. en sağdaki biti biz değil wire kütüphanesi yazma ve okumaya göre değiştirecektir.
Örnek verelim. mesela A1,A2,A3 uçlarını GND ye bağladık diyelim. Sayımız Binary olarak 0100000 = 32 (desimal Olarak ) 0x20 (Hex olarak) karşımıza çıkar. Kütüphane Yazma konumunda en sağdaki biti de 0 yaptığında 8 bitlik sayımız şu şekilde olur. 01000000= 64 (Hex 0x40) olacaktır. Okuma yapmak istersek Kütüphane en sağdaki biti 1 yapacaktır. sayımız 01000001 = 65 (Hex 0x41) olacaktır.  Aşağıda adres olarak entegrelere göre vereceğiniz değerler yer almıştır. Burada 7 bit üzerinden hesaplayıp verdiğimiz cihaz adresi vardır. yazma okuma biti kütüphanenin işi olduğundan direkt bu değerleri A1,A2,A3 girişlerinin durumuna göre verebilirsiniz.

Benim kullandığım modülde adresler bu şekildedir. Kendi modülünüze göre programlardaki adresleri ayarlayabilirsiniz.

 

PCF8574 modülün çalışmasının nasıl olduğuna bakalım.
Öncelikle INT ucundan başlayalım. Ne işe yarıyor. Bu pim, input verildiğinde mikrokontrolcüyü uyarmak için bir değişim yaratır. Normalde Pull Up direncinden dolayı HIGH durumundadır. INPUT geldiğinde bir süre için LOW duruma geçer. Bu şekilde mikrokontrolcüyü uyarır. Biz devamlı INT ucunu kontrol ederiz. O değiştiğinde birileri butona basmış demektir. Biz de butonların hangisi basıldı diye kontrol ederiz.  Neden Pull up dirence ihtiyaç var. Çünkü entegrenin bu çıkışı Open Drain denilen bir çıkıştır. Sizin 10K ile buraya +Vcc gerilimini vermeniz gerekir. Bu durumda devamlı 1 durumunda kalacak. INT, LOW olduğunda sıfıra düşecektir. ( Bu bacak LCD modülde hiç bir yere bağlanmamıştır. Kendiniz bir tel lehimleyip alabilirsiniz )

Open drain çalışma şekli bu şekildedir. R1 pull up direnci konulması zorunludur.

P0-P7 pimleri input/output  (I/O) pimleridir. SDA ve SCL pimleri I2C pimleridir. INT pimi interrupt (kesme) pimidir. A0-A2 pimleri de cihaz adresleme pimleridir.
Bu modülde 3 adet kontak bırakılmıştır. Bu üç kontağı, altında bulunan GND kontaklarına bağlayarak adres seçimi yapılır. Aynı hatta bir başka I2C cihaz ya da devre yoksa bu adreslemeyi ellemeyebilirsiniz.
Adresleme tablosuna göre adresinizi seçersiniz. Şayet kontakları GND ye birleştirirseniz 0 olarak kabul etmelisiniz. Açık bırakırsanız ya da VCC ye bağlarsanız 1 olarak kabul edip yukarıdaki adresleme tablosuna göre adresinizi seçebilirsiniz.

Bazı kişiler adresi bulmak için program çalıştırmayı önerirler. Fakat bu modülde her şey görünür olduğundan tabloya göre adresinizi belirlersiniz. Bakacağınız yer sadece A0-A2 noktaları bir de entegrenin PCF8574 ya da PCF8574A olup olmadığıdır.

Adres de tamam olduğuna göre artık Led yakmaya başlayabiliriz. Şayet Led yakmak istiyorsak yani çıkış olarak kontrol etmek istiyorsak, Port pimini 1 yaptığımızda Ledi yakacak akımı sağlayamazsınız. Burada Ledi yakmak için Port pimini 0 yapmanız gerekir.

Ledlerin bağlantısı sağdaki bağlantı gibi olmalı. Yani +Vcc den gelip entegrenin bacağına bağlanmalı.
Genelde Arduino veya diğer entegrelerde INPUT ve OUTPUT olmasını register (Yazmaç) ayarıyla yaptığımızdan OUTPUT yaptıktan sonra port pimine bir direnç koyup Ledin anot ucunu dirence bağlayıp katot ucunu ise GND ye bağlarız.
Fakat bu entegrede INPUT ve OUTPUT için ayrı bir register (yazmaç) yoktur. Bundan dolayı okumak için port pimini 1 yaparak okuruz. Bu belki dezavantaj olarak düşünülebilir ama bazen de ikili kullanımda avantaja dönüşür. Proteus devresinde ve gerçek devrede bu durumu görebilirsiniz.
Hem Led hem de Buton aynı pime bağlı olabiliyor. Beraber çalışabiliyorlar.

İki ayrı Arduino programı var. Birinci programda basılan butonların karşılığı olan ledin durum değişmesidir.  ikinci Arduino program ise yürüyen ışık gibi bir animasyon dur.  Programlarda adres bağlantıları farklıdır gerekirse düzeltiniz. 

Modül içerisinde P3 bağlantısı bu şekildedir. siz Ledin katodunu buraya bağladığınızda P3 Transistörü, Transistör de Ledinizi kontrol edecektir.

Gerçek devre de sarı Led p3 portunun Ledidir. Ayrı olmasının sebebi ise LCD modülde P3 portunun LCD aydınlatma Ledi olarak ayrıldığı içindir. Bundan dolayı modülde LCD pim sıralamasının sonunda yer alan K yazan katot ucudur. Bu zaten Led aç ve kapat işleminde kullanıldığından siz de bu ucu P3 olarak kullanabilirsiniz. Devre şemasında P3 yerini takip ettiğinizde transistor ün BASE bacağını LOW ve HIGH yapmak için kullanılır. LOW yaptığında Transistör çalışmaz ve LED yanmaz. Bundan dolayı K ucundan bilgi aldığınızda Diğer portlara göre ters çalışacaktır. Yani diğer portlar LOW olduğunda Led yanarken P3 piminde HIGH olduğunda LED yanar. Hepsi beraber aynı formatta yansın diyorsanız K ucundan değil de 4K7 direncinin P3 ucundan bir kablo bağlarsanız bu da aynı olacaktır.
Sakın yeni lehimleyeceğiniz hatları, Kullanılmadığını düşündüğünüz LCD tarafındaki D0-D4 uçlarına bağlamayın. Modül tarafında kullanılmasa bile LCD tarafında bir yerlere bağlı olduğundan LCD yi şaşırtabilir.

P3 ucuyla INT uçlarını pcb üzerinde bir yere yapıştırabileceğiniz sokete aktarabilirsiniz. Bunları da breadboard üzerinde deneme yaparken rahatlıkla kullanabilirsiniz.

Buton bağlarken normal devrelerde pull up direnç kullanıyorduk. Burada buna da gerek yok. Sadece GND ye direkt bağlayacağınız bir buton iş görecektir.

Not: Benim aldığım 2 adet modülde Led aydınlatma için 2 li pim ve bir jumper kullanılmış. Fakat zaten pimler birbirine kısa devre olduğundan jumper’a gerek kalmıyor. Tüm modüller böyle olmayabilir. Kendi modülünüzde bu şekilde olup olmadığını ölçebilirsiniz. Siz devreyi açmak için jumper’ı çıkardığınızda devre hala çalışıyor olabilir.

Bir başka aklınızda bulunsun diyeceğim not ise röle bağlantısı nasıl yapılacağı. Bunun için yine LCD aydınlatma ledinin bulunduğu transistör devresini göz önünde bulundurun. Buradaki K ucu ledin yanmasını sağlıyorsa K ucuna bağlanacak Röle de çalışabilecektir. Ya da Bu uca optokuplörün Ledini bağlarsanız izolasyonlu bir röle kontrol devresi de elde edebileceksiniz. Bununla bir entegreyi High olarak tetikleyebilir miyim dediğinizde elbette bu bağlantıyla HIGH olarak tetikleyebilirsiniz. Bunun için K ucuna pull up direnç bağlayın ve OUT ucundan çıkış alın.
Tabloda A yerine P3 olarak varsayın.


Ben bu modüle göre anlatmaya çalıştım. Piyasadan başka tip görünse bile PCF8574 ya da PCF8574A, I2C expander modül aldıysanız kütüphane kullanmanıza gerek yok. Rahatlıkla bu bilgilerle onu da kullanabilirsiniz.

Tüm dosyalara bu linkten ulaşabilirsiniz.

Not: Sitemde ABONELİK yok. Fakat isterseniz Video üzerindeki Ş butonuna basarak ve ABONE OL butonuna basarak kolaylıkla YOUTUBE üzerinden ABONE olabilirsiniz. Yazılar ilk gün YOUTUBE üzerinde yayınlanacak sonrasında diğer ortamlarda paylaşılacak.  Yazılarımdan anında haberdar olmak isteyenler, ABONE olabilirler. 

2 Comments

  1. Merhaba, güzel bir anlatım olmuş teşekkürler.
    Benim bir sorum olacak;
    LCD üzerinde pin bağlantılarını ters yönde lehimledim (1-2-3-4-…15-16 dizilimi yerine 16-15…3-2-1 şeklinde düşünü), bu yüzden görüntü alamadım. Ana arduino ile modül haberleşebiliyor, adres bilgisini okuyabiliyor vesaire.. Lehimleri sökmektense, kod kısmında çıkış yönünü değiştirebileceğim bir seçenek varmı acaba. tesekkürler.

  2. Sadece data olsaydı kütüphane kullanmadan LCD programınızı kendiniz yazabilirdiniz ama arka ışık ve beslemeler ters olduğundan bu şekilde kullanılamaz. mecburen sökülecek.

Bir cevap yazın

E-posta hesabınız yayımlanmayacak.