วันศุกร์ที่ 16 ธันวาคม พ.ศ. 2565

IO EXTENDER MODULE, PCF8574

     

Fig.1 PCF8574 IO extender.

    การเพิ่ม IO ให้กับระบบ มีหลายแนวทาง ใช้ RS485 module ก็ได้ เพิ่มได้บานเบอะเยอะแยะ แต่ที่จะเขียนกันลืมนั้นเป็นบอร์ดที่ใช้เพิ่ม IO ที่ใช้ชิพ PCF8574 ของ NXP (Philips เดิม) สนนราคาอันละ 27บาท(ณ 11/2564)  เพียง 1 บอร์ดจะเพิ่มได้ 8 I/O ทั้งนี้มันสามารถต่อกันได้อีกรวมๆ 8บอร์ด (มันมีสาม DIP switch/jumper ไว้ใช้กำหนดเลข slave 2^3 = 8 เลข) ซึ่งเมื่อต่อกันได้ 8 อันก็จะได้ 64I/O

    มันใช้ I2C protocol ใช้งานเพียง 2 สาย ต่อสาย SDA-A4, SCL-A5 มันต้องมีหมายเลขประจำตัวของใครของมันเรียกว่า address

Fig.2 Setting address.
   

    Address กำหนดได้ด้วย 1 byte แบบนี้ 0b0100 A2 A1 A0  โดยที่ bit A2,1,0 จะมี logic เป็น 0 ถ้าต่อ GND และเป็น 1 ถ้าต่อ Vcc (ย้าย jumper เอา) ถ้าใช้บอร์ดเดียวก็ต่อกราวน์หมด แล้วใช้แอดเดรส 0x20

Fig.3 Available setting address.

    ต่อกราวน์ทั้งหมด ก็จะได้แอดเดรส 20H  การสั่งงานก็ใช้ wire library ช่วย และคำสั่งที่ใช้ก็แค่

    #define <Wire.h>   
    Wire.begin();
    Wire.beginTransmission(0x20);     //0x20 คือแอดเดรสของบอร์ด
    Wire.write(data) ;                        //
โดย data 1 byte เป็น bit ของ portP7....P0
    Wire.endTransmission();

ตัวอย่าง
    data = 0b11111111 หมายถึง P7-P0 จะมี logic High
    data = 0b00000000 หมายถึง P7-P0 จะมี logic Low
    อยากจะเปิด ปิด อันไหนก็เลือกเอา


    ส่วนการอ่านค่า port input (นึกถึงคำสั่ง digitalRead แบบเดียวกันเลย ) จะมีคำสั่งต่างกันนิดหน่อย คำสั่งนี้ทำไปเพื่อดูสถานะของ P7..P0 ว่าเปิดปิดยังไงกันอยู่
ตัวอย่าง
    byte state;
    byte nData = 1;                            //จำนวน 1 byte
    Wire.requestFrom(0x20,nData);      //address 20 จำนวน 1 register 
    if(Wire.available())
      state = Wire.read();                    //เก็บข้อมูลใส่ตัวแปร state จากนั้นจะเอาไปทำไรก็ตามสะดวก
    Serial.println(state,BIN);                //แสดงผลลัพธ์ 

Fig.4 Master read register's status.

ตบท้ายนี้

PCF8574 มันไม่ได้เป็นแค่ Output อย่างเดียว มันทำได้ 4 อย่าง

    1. Input HIGH
    2. Input LOW
    3. Output HIGH
    4. Output LOW

Input HIGH จะกำหนดให้เป็น input ก็กำหนด logic 1 ให้พอร์ตนั้น จากนั้นก็อ่านค่า register เพื่อดูสถานะของพอร์ตนั้นว่า เป็น 1 หรือ 0

Input LOW กำหนด logic 1 ให้พอร์ตนั้น จากนั้นก็อ่านค่า register เพื่อดูสถานะของพอร์ตนั้น ถ้า external ที่ต่อที่พอร์ตนั้นดึงลงกราวน์ หรือมี logic 0 (พอร์ตนี้มีกระแสอ่อนๆ 100uA เป็น source) เมื่ออ่านค่า register ก็จะได้ logic 0

Output HIGH กำหนด logic 1 ให้พอร์ตนั้น เหมือนตัวอย่างข้างต้น

Output LOW กำหนด logic 0 ให้พอร์ตนั้น เหมือนตัวอย่างข้างต้น

เกร็ดเล็กเกร็ดน้อย

    - กระแสที่ออกจากพอร์ตเมื่อเป็น source(ไหลออกพอร์ต) แค่ 100uA เอง หวังจะเอาไปขับโหลดอะไรได้ ทำให้ LED หลายอันติดก็คงลำบาก ตรงนี้ต้องใช้ทรานซิสเตอร์ช่วย
    - ถ้าให้พอร์ตเป็น sink (ไหลเข้าพอร์ต) กระแสทั้งหมดต้องไม่เกิน 80mA และทำได้แค่ 10mA ต่อพอร์ต(ที่ 5V) อยากได้ 20mA ก็ต่อขนาน 2 พอร์ต และเมื่อมีการขนานกัน 5 พอร์ตจะทำได้ 80mA และก็ไม่ควรจะทำงานพร้อมกัน

Fig.5 High current application

ข้อแนะนำ

เอาง่ายๆ ก็หาไบบรารี่มาใช้ หรือไม่ก็ทำเป็นฟังก์ชั่น จะได้เอาเวลาไปทำอย่างอื่น

"เวลาของโปรเซสเซอร์มีค่าน้อยมาก เมื่อเทียบกับเวลาของเรา"
ฝรั่งท่านหนึ่งได้กล่าวเอาไว้

ไม่มีความคิดเห็น:

แสดงความคิดเห็น

MAPs

วันก่อนได้ลองเขียนแบบ แบบตัวนั้นมันต้องแนบแผนที่สังเขปของโครงการ ลองๆ แล้วก็ใช้ snazzymaps แล้วก็เอามาทำต่อใน inkscape มันก็ออกมาดูได้ระดับห...