uint8_t portState; //bit pattern | uint8_t portState; //bit pattern | ||||
SPI.beginTransaction( SPISettings(5000000, MSBFIRST, SPI_MODE0) ); //control SPI bus, 5 MHz | SPI.beginTransaction( SPISettings(5000000, MSBFIRST, SPI_MODE0) ); //control SPI bus, 5 MHz | ||||
digitalWrite(SS, LOW); //enable Slave Select | |||||
digitalWrite(slaveSelect, LOW); //enable Slave Select | |||||
SPI.transfer(command); //write or read command | SPI.transfer(command); //write or read command | ||||
SPI.transfer(registerAddr); //register address to write data to | SPI.transfer(registerAddr); //register address to write data to | ||||
portState = SPI.transfer(data); //write data, read portState | portState = SPI.transfer(data); //write data, read portState | ||||
digitalWrite(SS, HIGH); //disable Slave Select | |||||
digitalWrite(slaveSelect, HIGH); //disable Slave Select | |||||
SPI.endTransaction(); | SPI.endTransaction(); | ||||
return portState; | return portState; | ||||
*/ | */ | ||||
void Port_MCP23S17::beginProtocol() | void Port_MCP23S17::beginProtocol() | ||||
{ | { | ||||
pinMode(SS, OUTPUT); //configure controller's Slave Select pin to output | |||||
digitalWrite(SS, HIGH); //disable Slave Select | |||||
pinMode(slaveSelect, OUTPUT); //configure controller's Slave Select pin to output | |||||
digitalWrite(slaveSelect, HIGH); //disable Slave Select | |||||
SPI.begin(); | SPI.begin(); | ||||
} | } | ||||
{ | { | ||||
uint8_t pullUp; //bits, GPPU 0=pull-up disabled, 1=pull-up enabled | uint8_t pullUp; //bits, GPPU 0=pull-up disabled, 1=pull-up enabled | ||||
if (activeState == LOW) //if active low | |||||
if (activeState == LOW) //if active low | |||||
{ | { | ||||
pullUp = readPins; //0=pull-up disabled (for LED), 1=pull-up enabled (for read) | |||||
pullUp = readPins; //0=pull-up disabled (for LED), 1=pull-up enabled (for read) | |||||
} | } | ||||
else //if active high | else //if active high | ||||
{ | { | ||||
pullUp = 0; //0=pull-up disabled (for external pull-down resistors) | |||||
pullUp = 0; //0=pull-up disabled (for external pull-down resistors) | |||||
} | } | ||||
transfer(deviceAddr << 1, portNum, readPins); //configure IODIR | transfer(deviceAddr << 1, portNum, readPins); //configure IODIR | ||||
*/ | */ | ||||
void Port_MCP23S17::writeLow(const uint8_t pin) | void Port_MCP23S17::writeLow(const uint8_t pin) | ||||
{ | { | ||||
outputVal &= ~pin; //set pin output to low | |||||
outputVal &= ~pin; //set pin output to low | |||||
transfer(deviceAddr << 1, portNum + 0x12, outputVal); //set GPIO port to outputVal | transfer(deviceAddr << 1, portNum + 0x12, outputVal); //set GPIO port to outputVal | ||||
} | } | ||||
*/ | */ | ||||
void Port_MCP23S17::writeHigh(const uint8_t pin) | void Port_MCP23S17::writeHigh(const uint8_t pin) | ||||
{ | { | ||||
outputVal |= pin; //set pin output to high | |||||
outputVal |= pin; //set pin output to high | |||||
transfer(deviceAddr << 1, portNum + 0x12, outputVal); //set GPIO port to outputVal | transfer(deviceAddr << 1, portNum + 0x12, outputVal); //set GPIO port to outputVal | ||||
} | } | ||||
write pins are connected to matrix Row (strobe pin) or LED. | write pins are connected to matrix Row (strobe pin) or LED. | ||||
readPins are connected to matrix column to read which keys are pressed. | readPins are connected to matrix column to read which keys are pressed. | ||||
Slave Select is hardcoded to Arduino Pin 10. | |||||
Arduino Pin 10 avoids the speed penalty of digitalWrite. | |||||
slaveSelect is Arduino-pin number connected to pin 11 (CS a.k.a. SS). | |||||
Instantiation | Instantiation | ||||
------------ | ------------ | ||||
class Port_MCP23S17 : public PortInterface | class Port_MCP23S17 : public PortInterface | ||||
{ | { | ||||
private: | private: | ||||
const uint8_t slaveSelect; //controller-pin number | |||||
const uint8_t deviceAddr; | const uint8_t deviceAddr; | ||||
const uint8_t portNum; //port identification number | const uint8_t portNum; //port identification number | ||||
uint8_t outputVal; //bit pattern for strobe and LEDs | uint8_t outputVal; //bit pattern for strobe and LEDs | ||||
const uint8_t readPins; //bit pattern, IODIR 0=output, 1=input | const uint8_t readPins; //bit pattern, IODIR 0=output, 1=input | ||||
uint8_t transfer(const uint8_t command, const uint8_t registerAddr, const uint8_t data); | uint8_t transfer(const uint8_t command, const uint8_t registerAddr, const uint8_t data); | ||||
public: | public: | ||||
Port_MCP23S17(const uint8_t deviceAddr, const uint8_t portNum, const uint8_t readPins) | |||||
: deviceAddr(deviceAddr), portNum(portNum), outputVal(0), readPins(readPins) {} | |||||
Port_MCP23S17(const uint8_t slaveSelect, const uint8_t deviceAddr, const uint8_t portNum, const uint8_t readPins) | |||||
: slaveSelect(slaveSelect), deviceAddr(deviceAddr), portNum(portNum), outputVal(0), readPins(readPins) {} | |||||
void beginProtocol(); | void beginProtocol(); | ||||
void begin(const uint8_t activeState); | void begin(const uint8_t activeState); | ||||
virtual void writeLow(const uint8_t pin); | virtual void writeLow(const uint8_t pin); |
#include <PortWriteInterface.h> | #include <PortWriteInterface.h> | ||||
/* Port_ShiftRegs | /* Port_ShiftRegs | ||||
slaveSelect is controller-pin number connected to shift register RCLK pin a.k.a. SS or ST | |||||
slaveSelect is Arduino-pin number connected to shift register RCLK pin a.k.a. SS or ST | |||||
*/ | */ | ||||
class Port_ShiftRegs : public PortWriteInterface | class Port_ShiftRegs : public PortWriteInterface | ||||
{ | { |
// --------------- RIGHT SCANNER --------------- | // --------------- RIGHT SCANNER --------------- | ||||
const uint8_t IOE_ADDR = 0x20; //MCP23S17 address, all 3 ADDR pins are grounded | const uint8_t IOE_ADDR = 0x20; //MCP23S17 address, all 3 ADDR pins are grounded | ||||
Port_MCP23S17 portA(IOE_ADDR, 0, 1<<0 | 1<<1 ); //for read | |||||
Port_MCP23S17 portB(IOE_ADDR, 1, 0); //for strobe | |||||
const uint8_t slaveSelect = 10; | |||||
Port_MCP23S17 portA(slaveSelect , IOE_ADDR, 0, 1<<0 | 1<<1 ); //for read | |||||
Port_MCP23S17 portB(slaveSelect , IOE_ADDR, 1, 0); //for strobe | |||||
Scanner_IOE scanner_R(LOW, portB, portA); | Scanner_IOE scanner_R(LOW, portB, portA); | ||||