114 lines
2.7 KiB
C++
114 lines
2.7 KiB
C++
#include "PCF8574.h"
|
|
|
|
PCF8574::PCF8574(uint8_t address, TwoWire &twc) : _twc(twc), _address(address), _pinConfig(0b11111111), _pddr(0b00000000) //Inputs by default
|
|
{
|
|
|
|
}
|
|
|
|
boolean PCF8574::begin()
|
|
{
|
|
_twc.begin();
|
|
_twc.beginTransmission(_address);
|
|
_twc.write(_pinConfig);
|
|
return _twc.endTransmission() == 0;
|
|
}
|
|
|
|
void PCF8574::pinMode(Pin pin, boolean mode)
|
|
{
|
|
uint8_t mask = mode ? pin : pin; //0 INPUT - 1 OUTPUT
|
|
|
|
if(mode)//OUTPUT
|
|
{
|
|
_pinConfig = _pinConfig | mask;
|
|
_pddr = _pddr | pin;
|
|
}
|
|
else
|
|
{
|
|
_pinConfig = _pinConfig | mask;
|
|
_pddr = _pddr & ~pin;
|
|
}
|
|
|
|
_pinConfig = _pinConfig | mask;
|
|
_twc.beginTransmission(_address);
|
|
_twc.write(_pinConfig);
|
|
_twc.endTransmission();
|
|
}
|
|
|
|
void PCF8574::digitalWrite(Pin pin, boolean mode)
|
|
{
|
|
//We first check that the pin is an output
|
|
if((_pddr & pin) == 0)
|
|
return;
|
|
|
|
uint8_t mask = mode ? pin : ~pin; //0 LOW, 1 HIGH
|
|
if(mode)
|
|
_pinConfig = _pinConfig | mask;
|
|
else
|
|
_pinConfig = _pinConfig & mask;
|
|
|
|
_twc.beginTransmission(_address);
|
|
_twc.write(_pinConfig);
|
|
_twc.endTransmission();
|
|
}
|
|
|
|
void PCF8574::togglePin(Pin pin)
|
|
{
|
|
//We first check that the pin is an output
|
|
if((_pddr & pin) == 0)
|
|
return;
|
|
|
|
_pinConfig = (_pinConfig & pin) == 0 ? _pinConfig | pin : _pinConfig & ~pin;
|
|
|
|
_twc.beginTransmission(_address);
|
|
_twc.write(_pinConfig);
|
|
_twc.endTransmission();
|
|
}
|
|
|
|
boolean PCF8574::digitalRead(Pin pin)
|
|
{
|
|
uint8_t reg = 0b00000000;
|
|
_twc.requestFrom((uint8_t)_address,(uint8_t)1,(uint8_t)true);
|
|
while(_twc.available())reg = _twc.read();
|
|
return (reg & pin) == 0 ? 0 : 1;
|
|
}
|
|
|
|
void PCF8574::digitalReadAll(boolean array[8])
|
|
{
|
|
uint8_t reg = 0b00000000;
|
|
_twc.requestFrom((uint8_t)_address,(uint8_t)1,(uint8_t)true);
|
|
while(_twc.available())reg = _twc.read();
|
|
|
|
array[0] = (reg & P0) == 0 ? 0 : 1;
|
|
array[1] = (reg & P1) == 0 ? 0 : 1;
|
|
array[2] = (reg & P2) == 0 ? 0 : 1;
|
|
array[3] = (reg & P3) == 0 ? 0 : 1;
|
|
array[4] = (reg & P4) == 0 ? 0 : 1;
|
|
array[5] = (reg & P5) == 0 ? 0 : 1;
|
|
array[6] = (reg & P6) == 0 ? 0 : 1;
|
|
array[7] = (reg & P7) == 0 ? 0 : 1;
|
|
}
|
|
|
|
boolean PCF8574::getPinMode(Pin pin)
|
|
{
|
|
return (_pddr & pin) == 0 ? INPUT : OUTPUT;
|
|
}
|
|
|
|
void PCF8574::getPinModeAll(boolean array[8])
|
|
{
|
|
array[0] = (_pddr & P0) == 0 ? INPUT : OUTPUT;
|
|
array[1] = (_pddr & P1) == 0 ? INPUT : OUTPUT;
|
|
array[2] = (_pddr & P2) == 0 ? INPUT : OUTPUT;
|
|
array[3] = (_pddr & P3) == 0 ? INPUT : OUTPUT;
|
|
array[4] = (_pddr & P4) == 0 ? INPUT : OUTPUT;
|
|
array[5] = (_pddr & P5) == 0 ? INPUT : OUTPUT;
|
|
array[6] = (_pddr & P6) == 0 ? INPUT : OUTPUT;
|
|
array[7] = (_pddr & P7) == 0 ? INPUT : OUTPUT;
|
|
}
|
|
|
|
void PCF8574::resetIRQ()
|
|
{
|
|
//We request 1 byte in order to reset the IRQ
|
|
_twc.requestFrom((uint8_t)_address,(uint8_t)1,(uint8_t)true);
|
|
while(_twc.available())_twc.read();
|
|
}
|