diff --git a/IOE_scan_development/IOE_scan_development.ods b/IOE_scan_development/IOE_scan_development.ods deleted file mode 100644 index 7683b83..0000000 Binary files a/IOE_scan_development/IOE_scan_development.ods and /dev/null differ diff --git a/IOE_scan_development/openDrain_activeLow/back.JPG b/IOE_scan_development/openDrain_activeLow/back.JPG deleted file mode 100644 index 48304c3..0000000 Binary files a/IOE_scan_development/openDrain_activeLow/back.JPG and /dev/null differ diff --git a/IOE_scan_development/openDrain_activeLow/front.JPG b/IOE_scan_development/openDrain_activeLow/front.JPG deleted file mode 100644 index c1997ff..0000000 Binary files a/IOE_scan_development/openDrain_activeLow/front.JPG and /dev/null differ diff --git a/IOE_scan_development/openDrain_activeLow/openDrain_activeLow.ino b/IOE_scan_development/openDrain_activeLow/openDrain_activeLow.ino deleted file mode 100644 index 2fcf51b..0000000 --- a/IOE_scan_development/openDrain_activeLow/openDrain_activeLow.ino +++ /dev/null @@ -1,69 +0,0 @@ -/* simulate one scan of a key martix, on open-drain active-low I/O expander - -BREADBOARD SETUP ******************************* - Teensy LC connected to MCP23018 I/O expander via I2C - 4.7k Ohm pullup resistors on SDA and SCL - use volt meter to measure pin voltages - MCP23018 has open-drain outputs (open-drain can only sink current) - -MCP23018 PIN DIAGRAM *************************** - write port B read port A - GND VSS 1 28 NC - NC 2 27 GPA7 - jumper0 GPB0 3 26 GPA6 - GPB1 4 25 GPA5 - GPB2 5 24 GPA4 jumper4 - GPB3 6 23 GPA3 - jumper4 GPB4 7 22 GPA2 - GPB5 8 21 GPA1 - GPB6 9 20 GPA0 jumper0 - GPB7 10 19 INTA - power VDD 11 18 INTB - SCL SCL 12 17 NC - SDA SDA 13 16 RESET power - NC 14 15 ADDR GND -*/ -#include "Wire.h" - -const uint8_t ADDR = 0x20; //MCP23018 I2C address with ADDR pin grounded - -void setup() -{ - delay(1000); //time for Serial print to work - -// ================= configure ================ - Serial.print("config "); - Wire.begin(); - - Wire.beginTransmission(ADDR); - Wire.write(0x01); //IODIRB Configure - Wire.write(0); //as output - Wire.endTransmission(); - - Wire.beginTransmission(ADDR); - Wire.write(0x00); //IODIRA Configuration - Wire.write(~0); //as input - Wire.endTransmission(); - - Wire.beginTransmission(ADDR); - Wire.write(0x0C); //GPPUA pull-up - Wire.write(~0); //pull-up enabled - Wire.endTransmission(); - -// =================== scan =================== - Serial.println("scan"); - - Wire.beginTransmission(ADDR); - Wire.write(0x13); //GPIOB output - Wire.write(B00001111); //pins 0-3 off, pins 4-7 sink on (strobe, LED on) - Wire.endTransmission(); - - Wire.beginTransmission(ADDR); - Wire.write(0x12); //GPIOA (immediately before requestFrom) - Wire.endTransmission(); - - Wire.requestFrom(ADDR, static_cast(1)); //request one byte from GPIOA read - Serial.print("portA="); - Serial.println(Wire.read(), BIN); //prints portA=11101111 -} -void loop() { } diff --git a/IOE_scan_development/source_activeHigh/DSCF0003.JPG b/IOE_scan_development/source_activeHigh/DSCF0003.JPG deleted file mode 100644 index d7d5891..0000000 Binary files a/IOE_scan_development/source_activeHigh/DSCF0003.JPG and /dev/null differ diff --git a/IOE_scan_development/source_activeHigh/DSCF0004.JPG b/IOE_scan_development/source_activeHigh/DSCF0004.JPG deleted file mode 100644 index f7e8867..0000000 Binary files a/IOE_scan_development/source_activeHigh/DSCF0004.JPG and /dev/null differ diff --git a/IOE_scan_development/source_activeHigh/source_activeHigh.ino b/IOE_scan_development/source_activeHigh/source_activeHigh.ino deleted file mode 100644 index d87abcd..0000000 --- a/IOE_scan_development/source_activeHigh/source_activeHigh.ino +++ /dev/null @@ -1,69 +0,0 @@ -/* simulate one scan of a key martix, on source active-high I/O expander - -BREADBOARD SETUP ******************************* - Teensy LC connected to MCP23017 I/O expander via I2C - 10k Ohm external pulldown resistors on port A - 4.7k Ohm pullup resistors on SDA and SCL - use volt meter to measure pin voltages - -MCP23017 PIN DIAGRAM *************************** - write port B read port A - jumper0 GPB0 1 26 GPA7 pulldown - GPB1 2 25 GPA6 pulldown - GPB2 3 24 GPA5 pulldown - GPB3 4 23 GPA4 pulldown jumper4 - jumper4 GPB4 5 22 GPA3 pulldown - GPB5 6 21 GPA2 pulldown - GPB6 7 20 GPA1 pulldown - GPB7 8 19 GPA0 pulldown jumper0 - power VDD 9 18 INTA - GND VSS 10 28 INTB - NC 11 27 RESET power - SCL SCL 12 17 A2 gnd - SDA SDA 13 16 A1 gnd - NC 14 15 A0 gnd -*/ -#include "Wire.h" - -const uint8_t ADDR = 0x20; //MCP23017 I2C address with all ADDR pins grounded - -void setup() -{ - delay(1000); //time for Serial print to work - -// ================= configure ================ - Serial.print("config "); - Wire.begin(); - - Wire.beginTransmission(ADDR); - Wire.write(0x01); //IODIRB Configure - Wire.write(0); //as output - Wire.endTransmission(); - - Wire.beginTransmission(ADDR); - Wire.write(0x00); //IODIRA Configuration - Wire.write(~0); //as input - Wire.endTransmission(); - - Wire.beginTransmission(ADDR); - Wire.write(0x0C); //GPPUA pull-up - Wire.write(0); //pull-up disabled - Wire.endTransmission(); - -// =================== scan =================== - Serial.println("scan"); - - Wire.beginTransmission(ADDR); - Wire.write(0x13); //GPIOB output - Wire.write(B11110000); //pins 0-3 ground, pins 4-7 power (strobe, LED on) - Wire.endTransmission(); - - Wire.beginTransmission(ADDR); - Wire.write(0x12); //GPIOA (immediately before requestFrom) - Wire.endTransmission(); - - Wire.requestFrom(ADDR, static_cast(1)); //request one byte from GPIOA read - Serial.print("portA="); - Serial.println(Wire.read(), BIN); //prints portA=00010000 -} -void loop() { } diff --git a/IOE_scan_development/source_activeLow/back.JPG b/IOE_scan_development/source_activeLow/back.JPG deleted file mode 100644 index 8b75e70..0000000 Binary files a/IOE_scan_development/source_activeLow/back.JPG and /dev/null differ diff --git a/IOE_scan_development/source_activeLow/front.JPG b/IOE_scan_development/source_activeLow/front.JPG deleted file mode 100644 index 5f6bc96..0000000 Binary files a/IOE_scan_development/source_activeLow/front.JPG and /dev/null differ diff --git a/IOE_scan_development/source_activeLow/source_activeLow.ino b/IOE_scan_development/source_activeLow/source_activeLow.ino deleted file mode 100644 index 40b0a1a..0000000 --- a/IOE_scan_development/source_activeLow/source_activeLow.ino +++ /dev/null @@ -1,68 +0,0 @@ -/* simulate one scan of a key martix, on source active-low I/O expander - -BREADBOARD SETUP ******************************* - Teensy LC connected to MCP23017 I/O expander via I2C - 4.7k Ohm pullup resistors on SDA and SCL - use volt meter to measure pin voltages - -MCP23017 PIN DIAGRAM *************************** - write port B read port A - jumper0 GPB0 1 26 GPA7 - GPB1 2 25 GPA6 - GPB2 3 24 GPA5 - GPB3 4 23 GPA4 jumper4 - jumper4 GPB4 5 22 GPA3 - GPB5 6 21 GPA2 - GPB6 7 20 GPA1 - GPB7 8 19 GPA0 jumper0 - power VDD 9 18 INTA - GND VSS 10 28 INTB - NC 11 27 RESET power - SCL SCL 12 17 A2 gnd - SDA SDA 13 16 A1 gnd - NC 14 15 A0 gnd -*/ -#include "Wire.h" - -const uint8_t ADDR = 0x20; //MCP23017 I2C address with all ADDR pins grounded - -void setup() -{ - delay(1000); //time for Serial print to work - -// ================= configure ================ - Serial.print("config "); - Wire.begin(); - - Wire.beginTransmission(ADDR); - Wire.write(0x01); //IODIRB Configure - Wire.write(0); //as output - Wire.endTransmission(); - - Wire.beginTransmission(ADDR); - Wire.write(0x00); //IODIRA Configuration - Wire.write(~0); //as input - Wire.endTransmission(); - - Wire.beginTransmission(ADDR); - Wire.write(0x0C); //GPPUA pull-up - Wire.write(~0); //pull-up enabled - Wire.endTransmission(); - -// =================== scan =================== - Serial.println("scan"); - - Wire.beginTransmission(ADDR); - Wire.write(0x13); //GPIOB output - Wire.write(B00001111); //pins 0-3 power (strobe, LED on), pins 4-7 ground - Wire.endTransmission(); - - Wire.beginTransmission(ADDR); - Wire.write(0x12); //GPIOA (immediately before requestFrom) - Wire.endTransmission(); - - Wire.requestFrom(ADDR, static_cast(1)); //request one byte from GPIOA read - Serial.print("portA="); - Serial.println(Wire.read(), BIN); //prints portA=11101111 -} -void loop() { } diff --git a/examples/IOE_PCA9655E_development/PCA9655E_1_write_read/PCA9655E_1_write_read.ino b/examples/IOE_PCA9655E_development/PCA9655E_1_write_read/PCA9655E_1_write_read.ino new file mode 100644 index 0000000..f704737 --- /dev/null +++ b/examples/IOE_PCA9655E_development/PCA9655E_1_write_read/PCA9655E_1_write_read.ino @@ -0,0 +1,58 @@ +/* PCA9655E_1_write_read.ino + +set port 1 pins +read and print value of port 0 +measure port 1 pin voltages with a multimeter + +DESTINATION PIN PIN_NUMBER PIN DESTINATION + x INT 1 24 VDD Teensy LC 3.3V + SCL AD1 2 23 SDA Teensy LC 18 + GND AD2 3 22 SCL Teensy LC 19 + GND IO0_0 4 21 AD0 SCL + GND IO0_1 5 20 IO1_6 x + VDD IO0_2 6 19 IO1_5 x + VDD IO0_3 7 18 IO1_4 x + GND IO0_4 8 17 IO1_4 x + GND IO0_5 9 16 IO1_3 x + x IO0_6 10 15 IO1_2 x + x IO0_7 11 14 IO1_1 x + GND VSS 12 13 IO1_0 x +*/ +#include "Wire.h" + +const uint8_t ADDR = 0x18; //I2C address with AD2=GND AD1=SCL AD0=SCL +void setup() +{ + delay(1000); + Serial.print("PCA9655E_read.ino"); + Wire.begin(); + + //Configure port 1 to output + Wire.beginTransmission(ADDR); + Wire.write(7); //configure direction + Wire.write(0); //0=output + Wire.endTransmission(); + + Wire.beginTransmission(ADDR); + Wire.write(3); //command byte 3 = Output Port 1 + Wire.write( 1<<2 | 1<<3); //1=high + Wire.endTransmission(); + + //Configure port 0 to input + Wire.beginTransmission(ADDR); + Wire.write(6); //command byte 6 = Configuration dir Port 0 + Wire.write(~0); //1=input + Wire.endTransmission(); + + Wire.beginTransmission(ADDR); + Wire.write(0); //command byte 0 = Input Port 0 + Wire.endTransmission(false); //PCA9655E needs false to send a restart + + Wire.requestFrom(ADDR, 1u); //request one byte from input port + + Serial.print(" port0_val= "); + uint8_t port0_val = Wire.read(); + Serial.print(port0_val, BIN); //expect xx001100 +} + +void loop() { } diff --git a/examples/IOE_PCA9655E_development/PCA9655E_1_write_read/back.JPG b/examples/IOE_PCA9655E_development/PCA9655E_1_write_read/back.JPG new file mode 100644 index 0000000..be484a6 Binary files /dev/null and b/examples/IOE_PCA9655E_development/PCA9655E_1_write_read/back.JPG differ diff --git a/examples/IOE_PCA9655E_development/PCA9655E_1_write_read/front.JPG b/examples/IOE_PCA9655E_development/PCA9655E_1_write_read/front.JPG new file mode 100644 index 0000000..0ba4f69 Binary files /dev/null and b/examples/IOE_PCA9655E_development/PCA9655E_1_write_read/front.JPG differ diff --git a/examples/IOE_PCA9655E_development/PCA9655E_2_scan/DSCF0001.JPG b/examples/IOE_PCA9655E_development/PCA9655E_2_scan/DSCF0001.JPG new file mode 100644 index 0000000..2f26002 Binary files /dev/null and b/examples/IOE_PCA9655E_development/PCA9655E_2_scan/DSCF0001.JPG differ diff --git a/examples/IOE_PCA9655E_development/PCA9655E_2_scan/DSCF0002.JPG b/examples/IOE_PCA9655E_development/PCA9655E_2_scan/DSCF0002.JPG new file mode 100644 index 0000000..a4485a3 Binary files /dev/null and b/examples/IOE_PCA9655E_development/PCA9655E_2_scan/DSCF0002.JPG differ diff --git a/examples/IOE_PCA9655E_development/PCA9655E_2_scan/PCA9655E_2_scan.ino b/examples/IOE_PCA9655E_development/PCA9655E_2_scan/PCA9655E_2_scan.ino new file mode 100644 index 0000000..b69beba --- /dev/null +++ b/examples/IOE_PCA9655E_development/PCA9655E_2_scan/PCA9655E_2_scan.ino @@ -0,0 +1,56 @@ +/* PCA9655E_2_scan.ino + +power IO0_2 and read IO1_1 (similar to strobe and read on key matrix) + +DESTINATION PIN PIN_NUMBER PIN DESTINATION + x INT 1 24 VDD Teensy LC 3.3V + SCL AD1 2 23 SDA Teensy LC 18 + GND AD2 3 22 SCL Teensy LC 19 + GND IO0_0 4 21 AD0 SCL + GND IO0_1 5 20 IO1_6 x + IO1_1 IO0_2 6 19 IO1_5 x + GND IO0_3 7 18 IO1_4 x + GND IO0_4 8 17 IO1_4 x + GND IO0_5 9 16 IO1_3 x + x IO0_6 10 15 IO1_2 x + x IO0_7 11 14 IO1_1 IO0_2 + GND VSS 12 13 IO1_0 x +*/ +#include "Wire.h" + +const uint8_t ADDR = 0x18; //I2C address with AD2=GND AD1=SCL AD0=SCL +void setup() +{ + delay(1000); + Serial.print("PCA9655E_read.ino"); + Wire.begin(); + + //Configure port 1 to output + Wire.beginTransmission(ADDR); + Wire.write(7); //command byte 7 = Configuration dir Port 1 + Wire.write(0); //0=output + Wire.endTransmission(); + + Wire.beginTransmission(ADDR); + Wire.write(3); //command byte 3 = Output Port 1 + Wire.write( 1<<1 ); //1=high + Wire.endTransmission(); + + //Configure port 0 to input + Wire.beginTransmission(ADDR); + Wire.write(6); //command byte 6 = Configuration dir Port 0 + Wire.write(~0); //1=input + Wire.endTransmission(); + + Wire.beginTransmission(ADDR); + Wire.write(0); //command byte 0 = Input Port 0 + Wire.endTransmission(false); //PCA9655E needs false to send a restart + + Wire.requestFrom(ADDR, 1u); //request one byte from input port + + Serial.print(" port0_val= "); + uint8_t port0_val = Wire.read(); + Serial.print(port0_val, BIN); //expect xx000100 +} + +void loop() { } diff --git a/examples/IOE_PCA9655E_development/PCA9655E_3_scan_lib/PCA9655E_3_scan_lib.ino b/examples/IOE_PCA9655E_development/PCA9655E_3_scan_lib/PCA9655E_3_scan_lib.ino new file mode 100644 index 0000000..be9b691 --- /dev/null +++ b/examples/IOE_PCA9655E_development/PCA9655E_3_scan_lib/PCA9655E_3_scan_lib.ino @@ -0,0 +1,45 @@ +/* PCA9655E_3_scan_lib.ino +does same as PCA9655E_2_scan.ino, but using keybrd library classes +pictures in PCA9655E_2_scan/ + +set port 1 pins +read and print value of port 0 +measure port 1 pin voltages with a multimeter + +DESTINATION PIN PIN_NUMBER PIN DESTINATION + x INT 1 24 VDD Teensy LC 3.3V + SCL AD1 2 23 SDA Teensy LC 18 + GND AD2 3 22 SCL Teensy LC 19 + GND IO0_0 4 21 AD0 SCL + GND IO0_1 5 20 IO1_6 x + IO1_1 IO0_2 6 19 IO1_5 x + GND IO0_3 7 18 IO1_4 x + GND IO0_4 8 17 IO1_4 x + GND IO0_5 9 16 IO1_3 x + x IO0_6 10 15 IO1_2 x + x IO0_7 11 14 IO1_1 IO0_2 strobe pin + GND VSS 12 13 IO1_0 x +*/ +#include +#include + +const uint8_t ADDR = 0x18; //I2C address with AD2=GND AD1=SCL AD0=SCL + +Port_PCA9655E port0(ADDR, 0, ~0); //read all pins +Port_PCA9655E port1(ADDR, 1, 0); //for strobe + +Scanner_IOE scanner_R(HIGH, port1, port0); + +void setup() +{ + delay(6000); + Keyboard.print("PCA9655E_scan.ino"); + + scanner_R.begin(); + + Keyboard.print(" port0_val= "); + uint8_t port0_val = scanner_R.scan(1<<1); //strobe pin 1 + Keyboard.print(port0_val, BIN); //expect xx000100 +} + +void loop() { } diff --git a/examples/IOE_PCA9655E_development/PCA9655E_4_scan_loop/PCA9655E_4_scan_loop.ino b/examples/IOE_PCA9655E_development/PCA9655E_4_scan_loop/PCA9655E_4_scan_loop.ino new file mode 100644 index 0000000..81bf499 --- /dev/null +++ b/examples/IOE_PCA9655E_development/PCA9655E_4_scan_loop/PCA9655E_4_scan_loop.ino @@ -0,0 +1,86 @@ +/* PCA9655E_4_scan_loop.ino +does same as PCA9655E_2_scan.ino, but using keybrd library classes +pictures in PCA9655E_2_scan/ + +set port 1 pins +read and print value of port 0 +measure port 1 pin voltages with a multimeter + +DESTINATION PIN PIN_NUMBER PIN DESTINATION + x INT 1 24 VDD Teensy LC 3.3V + SCL AD1 2 23 SDA Teensy LC 18 + GND AD2 3 22 SCL Teensy LC 19 + GND IO0_0 4 21 AD0 SCL + GND IO0_1 5 20 IO1_6 x + IO1_1 IO0_2 6 19 IO1_5 x + GND IO0_3 7 18 IO1_4 x + GND IO0_4 8 17 IO1_4 x + GND IO0_5 9 16 IO1_3 x + x IO0_6 10 15 IO1_2 x + x IO0_7 11 14 IO1_1 IO0_2 strobe pin + GND VSS 12 13 IO1_0 x +*/ +#include +#include + +const uint8_t ADDR = 0x18; //I2C address with AD2=GND AD1=SCL AD0=SCL + +Port_PCA9655E port0(ADDR, 0, ~0); //read all pins +Port_PCA9655E port1(ADDR, 1, 0); //for strobe + +Scanner_IOE scanner_R(HIGH, port1, port0); + +void setup() +{ + delay(6000); + Keyboard.println("PCA9655E_scan_loop.ino"); + + scanner_R.begin(); +} + +uint8_t port0_val; //bit pattern +uint8_t errorCount = 0; +int loopCount = 0; +int wait = 0; //delayMicroseconds + +void status() +{ + Keyboard.print(" loopCount="); + Keyboard.print(loopCount); + Keyboard.print(" wait="); + Keyboard.println(wait); +}; + +void loop() +{ + port0_val = scanner_R.scan(1<<1); //strobe pin 1 + if ( (B00111111 & port0_val) != B00000100 ) //expect xx000100, where xx float + { + Keyboard.print("port0_val="); + Keyboard.print(port0_val, BIN); + errorCount++; + status(); + } + + loopCount++; + if (loopCount > 32000 || errorCount > 10) + { + Keyboard.print("stop errorCount="); + Keyboard.print(errorCount); + status(); + while(1); + } + + if (loopCount % 1000 == 0) + { + Keyboard.print(" progress"); + status(); + } + + if (loopCount > 22000) + { + wait++; //test other delays + } + + delayMicroseconds(wait); +} diff --git a/examples/IOE_PCA9655E_development/PCA9655E_5_keybrd/back.JPG b/examples/IOE_PCA9655E_development/PCA9655E_5_keybrd/back.JPG new file mode 100644 index 0000000..b987b87 Binary files /dev/null and b/examples/IOE_PCA9655E_development/PCA9655E_5_keybrd/back.JPG differ diff --git a/examples/IOE_PCA9655E_development/PCA9655E_5_keybrd/front.JPG b/examples/IOE_PCA9655E_development/PCA9655E_5_keybrd/front.JPG new file mode 100644 index 0000000..f76d3b8 Binary files /dev/null and b/examples/IOE_PCA9655E_development/PCA9655E_5_keybrd/front.JPG differ diff --git a/examples/keybrd_PCA9655E/keybrd_PCA9655E.ino b/examples/IOE_PCA9655E_development/PCA9655E_5_keybrd/keybrd_PCA9655E.ino similarity index 50% rename from examples/keybrd_PCA9655E/keybrd_PCA9655E.ino rename to examples/IOE_PCA9655E_development/PCA9655E_5_keybrd/keybrd_PCA9655E.ino index da86109..7c997c7 100644 --- a/examples/keybrd_PCA9655E/keybrd_PCA9655E.ino +++ b/examples/IOE_PCA9655E_development/PCA9655E_5_keybrd/keybrd_PCA9655E.ino @@ -1,10 +1,26 @@ /* keybrd_PCA9655E.ino +keyboard layout is same as top-left keys of DH matrices: Controller I/O expander -| Left | **0** | **1** | | Right | **0** | **1** | +| Left | **0** | **1** | | Right | **2** | **3** | |:-----:|-------|-------| |:-----:|-------|-------| -| **1** | 1 | 2 | | **1** | 3 | 4 | -| **0** | a | b | | **0** | c | d | +| **1** | q | w | | **1** | u | i | +| **0** | [ | b | | **0** | h | y | + +PCA9655E pin assignments are compatible with this sketch and keybrd_DH.ino +DESTINATION PIN PIN_NUMBER PIN DESTINATION + x INT 1 24 VDD Teensy LC 3.3V + SCL AD1 2 23 SDA Teensy LC 18 + GND AD2 3 22 SCL Teensy LC 19 + GND IO0_0 4 21 AD0 SCL + GND IO0_1 5 20 IO1_6 x + col2 IO0_2 6 19 IO1_5 x + col3 IO0_3 7 18 IO1_4 x + GND IO0_4 8 17 IO1_4 x + GND IO0_5 9 16 IO1_3 x + x IO0_6 10 15 IO1_2 x + x IO0_7 11 14 IO1_1 row1 + GND VSS 12 13 IO1_0 row2 */ // ################## GLOBAL ################### // ================= INCLUDES ================== @@ -29,55 +45,62 @@ uint8_t readPinCount = sizeof(readPins)/sizeof(*readPins); Scanner_uC scanner_L(HIGH, readPins, readPinCount); // =============== RIGHT SCANNER =============== -const uint8_t IOE_ADDR = 0x18; +const uint8_t IOE_ADDR = 0x18; //AD2=GND AD1=SCL AD0=SCL -Port_PCA9655E port1(IOE_ADDR, 1, 0); //for strobe -Port_PCA9655E port0(IOE_ADDR, 0, 1<<0 | 1<<1 ); //for read +Port_PCA9655E port0(IOE_ADDR, 0, 1<<0 | 1<<1 | 1<<2 | 1<<3 | 1<<4 | 1<<5 ); //for read +Port_PCA9655E port1(IOE_ADDR, 1, 0); //for strobe Scanner_IOE scanner_R(HIGH, port1, port0); // =================== CODES =================== -Code_Sc s_a(KEY_A); -Code_Sc s_b(KEY_B); -Code_Sc s_c(KEY_C); -Code_Sc s_d(KEY_D); +Code_Sc s_B(KEY_B); +Code_Sc s_I(KEY_I); +Code_Sc s_H(KEY_H); +Code_Sc s_Q(KEY_Q); +Code_Sc s_W(KEY_W); +Code_Sc s_U(KEY_U); +Code_Sc s_Y(KEY_Y); +Code_Sc s_0(KEY_0); Code_Sc s_1(KEY_1); -Code_Sc s_2(KEY_2); -Code_Sc s_3(KEY_3); -Code_Sc s_4(KEY_4); +Code_Sc s_leftBracket(KEY_LEFT_BRACE); // =================== ROWS ==================== // ---------------- LEFT ROWS ------------------ -Key* ptrsKeys_L0[] = { &s_1, &s_2 }; +Key* ptrsKeys_L0[] = { &s_Q, &s_W }; uint8_t KEY_COUNT_L0 = sizeof(ptrsKeys_L0)/sizeof(*ptrsKeys_L0); Row row_L0(scanner_L, 21, ptrsKeys_L0, KEY_COUNT_L0); -Key* ptrsKeys_L1[] = { &s_a, &s_b }; +Key* ptrsKeys_L1[] = { &s_leftBracket, &s_B }; uint8_t KEY_COUNT_L1 = sizeof(ptrsKeys_L1)/sizeof(*ptrsKeys_L1); Row row_L1(scanner_L, 20, ptrsKeys_L1, KEY_COUNT_L1); // ---------------- RIGHT ROWS ----------------- -Key* ptrsKeys_R0[] = { &s_3, &s_4 }; +Key* ptrsKeys_R0[] = { &s_0, &s_1, &s_U, &s_I }; uint8_t KEY_COUNT_R0 = sizeof(ptrsKeys_R0)/sizeof(*ptrsKeys_R0); Row row_R0(scanner_R, 1<<0, ptrsKeys_R0, KEY_COUNT_R0); -Key* ptrsKeys_R1[] = { &s_c, &s_d }; +Key* ptrsKeys_R1[] = { &s_0, &s_1, &s_H, &s_Y }; uint8_t KEY_COUNT_R1 = sizeof(ptrsKeys_R1)/sizeof(*ptrsKeys_R1); Row row_R1(scanner_R, 1<<1, ptrsKeys_R1, KEY_COUNT_R1); +/* +*/ // ################### MAIN #################### void setup() { - Keyboard.begin(); + delay(6000); + Keyboard.print("keybrd_PCA9655E.ino "); + + //Keyboard.begin(); not needed ?? it's in DH mainSketch.cpp and keybrd_4c_split_keyboard_with_IOE.ino scanner_R.begin(); } void loop() { - //left matrix - row_L0.process(); - row_L1.process(); + //left matrix (commented because keys are not connected) + //row_L0.process(); + //row_L1.process(); //right matrix row_R0.process(); diff --git a/examples/IOE_PCA9655E_development/README.md b/examples/IOE_PCA9655E_development/README.md new file mode 100644 index 0000000..1cc7994 --- /dev/null +++ b/examples/IOE_PCA9655E_development/README.md @@ -0,0 +1,8 @@ +The series of sketches in this folder where used to develope the Port_PCA9655E class. +The folder numbers are ordered from fundamental to practical. + +Each sketch was tested on a breadboard. Breadboards hold: +* Teensy LC controller +* PCA9655E I/O expander + +Pictures of the breadboard are in the folders. diff --git a/examples/keybrd_MCP23018/keybrd_MCP23018.ino b/examples/keybrd_MCP23018/keybrd_MCP23018.ino index 903ac60..aff64a2 100644 --- a/examples/keybrd_MCP23018/keybrd_MCP23018.ino +++ b/examples/keybrd_MCP23018/keybrd_MCP23018.ino @@ -71,7 +71,7 @@ Code_Sc s_2(KEY_2); Code_Sc s_3(KEY_3); Code_Sc s_4(KEY_4); -Code_LEDLock o_capsLock(KEY_CAPS_LOCK, LED_capsLck);//todo was testing LED, restore s_4 when done +Code_LEDLock o_capsLock(KEY_CAPS_LOCK, LED_capsLck);//was testing LED, restore s_4 when done /* =================== ROWS ==================== Left row names contain the letter 'L', while right row names conatain the letter 'R'. @@ -118,14 +118,9 @@ void loop() //right matrix row_R0.process(); -//Keyboard.println(" 0"); -//delay(2000); row_R1.process(); -//Keyboard.println(" 1"); -//delay(2000); scanDelay.delay(); -//Keyboard.println(" end loop");//todo //debug.print_scans_per_second(); //debug.print_microseconds_per_scan(); } diff --git a/src/LED_uC.cpp b/src/LED_uC.cpp index b43b3c7..78e4098 100644 --- a/src/LED_uC.cpp +++ b/src/LED_uC.cpp @@ -1,5 +1,10 @@ #include "LED_uC.h" +LED_uC::LED_uC(const uint8_t pin) : pin(pin) +{ + pinMode(pin, OUTPUT); +} + void LED_uC::on() { digitalWrite(pin, HIGH); diff --git a/src/LED_uC.h b/src/LED_uC.h index f66598d..de37da9 100644 --- a/src/LED_uC.h +++ b/src/LED_uC.h @@ -9,13 +9,9 @@ class LED_uC: public LEDInterface { private: - const uint8_t pin; //Aduino pin that is connected to an LED - + const uint8_t pin; //Aduino pin number connected to an LED public: - LED_uC(const uint8_t pin): pin(pin) - { - pinMode(pin, OUTPUT);//todo move to .cpp file - } + LED_uC(const uint8_t pin); virtual void on(); virtual void off(); }; diff --git a/src/Port_MCP23018.cpp b/src/Port_MCP23018.cpp index 8275b26..3e83115 100644 --- a/src/Port_MCP23018.cpp +++ b/src/Port_MCP23018.cpp @@ -1,5 +1,4 @@ #include "Port_MCP23018.h" -//todo add Port_MCP23018::write() like Port_MCP23S17::transer() ?? /* beginProtocol() is called from Scanner_IOE::begin(). Initiates I2C bus. @@ -11,7 +10,6 @@ Longer wires require lower clock speeds. void Port_MCP23018::beginProtocol() { Wire.begin(); //initiate I2C bus to 100 kHz - //Wire.setClock(400000L); //set I2C bus to 400 kHz (have not tested 400 kHz) } /* begin() is called from Scanner_IOE::begin(). @@ -51,21 +49,16 @@ void Port_MCP23018::write(const uint8_t pin, const bool logicLevel) if (logicLevel == LOW) { outputVal &= ~pin; //set pin output to low -//Keyboard.print(" low"); } else { outputVal |= pin; //set pin output to high -//Keyboard.print(" high"); } -//Keyboard.print(" outputVal=");//todo -//Keyboard.println(outputVal); Wire.beginTransmission(deviceAddr); Wire.write(portNum + 0x12); //GPIO Wire.write(outputVal); Wire.endTransmission(); -//delay(4000); } /* read() returns portState. diff --git a/src/Port_PCA9655E.cpp b/src/Port_PCA9655E.cpp index 4bb2a63..d9dcec4 100644 --- a/src/Port_PCA9655E.cpp +++ b/src/Port_PCA9655E.cpp @@ -15,12 +15,12 @@ void Port_PCA9655E::beginProtocol() /* begin() is called from Scanner_IOE::begin(). Configures read pins to input. -strobeOn is not used because PCA9655E has no pull-up resistors. +strobeOn is not used because PCA9655E has no internal pull-up resistors. */ void Port_PCA9655E::begin(const uint8_t strobeOn) { Wire.beginTransmission(deviceAddr); - Wire.write(portNum + 6); //configuration byte command + Wire.write(portNum + 6); //configure direction Wire.write(readPins); //0=output (for strobe and LED), 1=input (for read) Wire.endTransmission(); } diff --git a/src/Row.h b/src/Row.h index 4bab68a..a0af168 100644 --- a/src/Row.h +++ b/src/Row.h @@ -11,12 +11,10 @@ /* strobePin has one of two formats: -1. if strobe pin is on uC (Scanner_uC or Scanner_ShiftRegsRead), + * if strobe pin is on uC (strobe for Scanner_uC or Scanner_ShiftRegsRead), then strobePin is an Arduino pin number connected to this row. -2. if strobe pin is on I/O expander (Scanner_IOE), then strobePin is bit pattern, + * if strobe pin is on I/O expander (strobe for Scanner_IOE), then strobePin is bit pattern, 1 indicating the I/O expander pin connected to this row - -todo instantiation examples - here or in Scanner? */ class Row { @@ -31,7 +29,7 @@ class Row protected: const uint8_t keyCount; //number of read pins //Debouncer_Samples debouncer; - Debouncer_Not debouncer; //todo + Debouncer_Not debouncer; //todo restore Debouncer_Samples after testing read_pins_t debounced; //bit pattern, state of keys after debouncing, 1=pressed, 0=released public: Row(ScannerInterface& refScanner, const uint8_t strobePin, diff --git a/src/Scanner_ShiftRegsReadStrobed.cpp b/src/Scanner_ShiftRegsReadStrobed.cpp index 2e0e989..d6965a6 100644 --- a/src/Scanner_ShiftRegsReadStrobed.cpp +++ b/src/Scanner_ShiftRegsReadStrobed.cpp @@ -6,25 +6,20 @@ Scanner_ShiftRegsReadStrobed::Scanner_ShiftRegsReadStrobed(const bool activeStat slaveSelect(slaveSelect), byte_count(byte_count) { pinMode(slaveSelect, OUTPUT); + SPI.begin(); } /* init() is called once for each row from Row constructor. Configures controller to communicate with shift register matrix. + +slaveSelect initialize not needed, only affects first scan, which is before USB is detected by OS. + digitalWrite(slaveSelect, HIGH); */ void Scanner_ShiftRegsReadStrobed::init(const uint8_t strobePin) { pinMode(strobePin, OUTPUT); } -/* begin() should be called once from sketch setup(). -Initializes shift register's shift/load pin. -*/ -void Scanner_ShiftRegsReadStrobed::begin() -{ - digitalWrite(slaveSelect, HIGH); //initialize ??only needed for first scan - SPI.begin(); //todo move this to constructor or init() -} - /* scan() strobes the row's strobePin and returns state of the shift register's input pins. strobePin is Arduino pin number connected to this row. Bit patterns are 1 bit per key. @@ -44,6 +39,7 @@ read_pins_t Scanner_ShiftRegsReadStrobed::scan(const uint8_t strobePin) { read_pins_t readState = 0; //bits, 1 means key is pressed, 0 means released +//strobe off here NOT release continuously digitalWrite(strobePin, activeState); //strobe on //SPI.beginTransaction( SPISettings(5000000, MSBFIRST, SPI_MODE0) ); //control SPI bus, 5 MHz @@ -53,7 +49,7 @@ read_pins_t Scanner_ShiftRegsReadStrobed::scan(const uint8_t strobePin) digitalWrite(slaveSelect, HIGH); //shift the data toward a serial output - digitalWrite(strobePin, !activeState); //strobe off to preserv IR LED life + digitalWrite(strobePin, !activeState); //strobe off to preserve IR LED life SPI.transfer(&readState, byte_count); @@ -61,6 +57,7 @@ read_pins_t Scanner_ShiftRegsReadStrobed::scan(const uint8_t strobePin) digitalWrite(slaveSelect, LOW); //load parallel inputs to registers +//strobe off here still releases continuously return readState; } diff --git a/src/Scanner_ShiftRegsReadStrobed.h b/src/Scanner_ShiftRegsReadStrobed.h index 3d7f767..05f502f 100644 --- a/src/Scanner_ShiftRegsReadStrobed.h +++ b/src/Scanner_ShiftRegsReadStrobed.h @@ -55,7 +55,6 @@ class Scanner_ShiftRegsReadStrobed : public ScannerInterface Scanner_ShiftRegsReadStrobed(const bool activeState, const uint8_t slaveSelect, const uint8_t byte_count); virtual void init(const uint8_t strobePin); - virtual void begin(); virtual read_pins_t scan(const uint8_t strobePin); }; #endif diff --git a/tutorials/keybrd_4c_split_keyboard_with_IOE/keybrd_4c_split_keyboard_with_IOE.ino b/tutorials/keybrd_4c_split_keyboard_with_IOE/keybrd_4c_split_keyboard_with_IOE.ino index b31afad..cb0201e 100644 --- a/tutorials/keybrd_4c_split_keyboard_with_IOE/keybrd_4c_split_keyboard_with_IOE.ino +++ b/tutorials/keybrd_4c_split_keyboard_with_IOE/keybrd_4c_split_keyboard_with_IOE.ino @@ -49,8 +49,8 @@ In portA, the first two pins are set to input for reading. "<<" (bit shift left) and "|" (OR) are bitwise operators. Pin numbers to be read are to the right of "1<<" and delimited by "|". */ -Port_MCP23S17 portA(IOE_ADDR, 0, 1<<0 | 1<<1 ); -Port_MCP23S17 portB(IOE_ADDR, 1, 0); +Port_MCP23S17 portA(IOE_ADDR, 0, 1<<0 | 1<<1 ); //for read +Port_MCP23S17 portB(IOE_ADDR, 1, 0); //for strobe Scanner_IOE scanner_R(LOW, portB, portA); // =================== CODES =================== @@ -69,8 +69,10 @@ Left row names contain the letter 'L', while right row names conatain the letter Row constructor parameters are: scanner, strobePin, ptrsKeys[], keyCount. strobePin has one of two formats: - * if refScanner a Scanner_uC, then strobePin is an Arduino pin number connected to this row - * otherwise strobePin is a bit pattern, 1 indicating an IC pin connected to the row + * if strobe pin is on uC (strobe for Scanner_uC or Scanner_ShiftRegsRead), + then strobePin is an Arduino pin number connected to this row. + * if strobe pin is on I/O expander (strobe for Scanner_IOE), then strobePin is bit pattern, + 1 indicating the I/O expander pin connected to this row */ /* ---------------- LEFT ROWS ------------------ The left rows have a Scanner_uC and Arduino pin numbers to strobe. diff --git a/tutorials/tutorial_10_writing_IOE_port_classes.md b/tutorials/tutorial_10_writing_IOE_port_classes.md index 440c00f..e2f23b7 100644 --- a/tutorials/tutorial_10_writing_IOE_port_classes.md +++ b/tutorials/tutorial_10_writing_IOE_port_classes.md @@ -19,8 +19,8 @@ Steps to writing a new port class: 5. Study other keybrd port classes. * SPI I/O expander port classes: Port_MCP23S17 * I2C I/O expander port classes: Port_PCA9655E -6. Write the port classes for your I/O expander. - Debugging I/O expander code is hard because SPI or I2C protocol adds a level of indirection. +6. Write the port classes for your I/O expander. Debugging I/O expander code is hard because + SPI or I2C protocol, expander configuration, and expander commands.
Creative Commons License
keybrd tutorial by Wolfram Volpi is licensed under a Creative Commons Attribution 4.0 International License.
Permissions beyond the scope of this license may be available at https://github.com/wolfv6/keybrd/issues/new. diff --git a/unit_tests/PortMCP23018_write/PortMCP23018_write.ino b/unit_tests/PortMCP23018_write/PortMCP23018_write.ino deleted file mode 100644 index 72281b8..0000000 --- a/unit_tests/PortMCP23018_write/PortMCP23018_write.ino +++ /dev/null @@ -1,33 +0,0 @@ -/* unit test for Port_MCP23018 -Picture of hardware is in unit_tests/PortMCP23018_read/PortMCP23018_bb.JPG todo -The setup is an MCP23018 I/O expander on a Teensy LC controller. -MCP23018 port-A GPIO pins are not connected to anything. -Port-A GPIO-pin ouputs alternate between 0 and 3.3 volts. -volt meter between pin A1 and power because - MCP23018 has open-drain outputs (open-drain can only sink current) - -Use a volt meter to measure port-A GPIO-pin outputs or red LED. -*/ -#include "Port_MCP23018.h" - -const uint8_t IOE_ADDR = 0x20; //MCP23018 address ADDR pin grounded -Port_MCP23018 portA(IOE_ADDR, 0, 0); - -void setup() -{ - delay(6000); - Keyboard.println("PortMCP23018_write.ino"); - portA.beginProtocol(); - portA.begin(LOW); //HIGH or LOW, not matter if readPins=0 -} - -void loop() -{ - portA.write(~0, HIGH); //set all GPIOA pins HIGH - Keyboard.print("+"); - delay(2000); - - portA.write(~0, LOW); //set all GPIOA pins LOW - Keyboard.print("0"); - delay(2000); -} diff --git a/unit_tests/PortMCP23S17_read/PortMCP23S17_bb.JPG b/unit_tests/PortMCP23S17_read/PortMCP23S17_bb.JPG deleted file mode 100644 index 9153e5c..0000000 Binary files a/unit_tests/PortMCP23S17_read/PortMCP23S17_bb.JPG and /dev/null differ diff --git a/unit_tests/PortMCP23S17_read/PortMCP23S17_read.ino b/unit_tests/PortMCP23S17_read/PortMCP23S17_read.ino deleted file mode 100644 index 87bdea4..0000000 --- a/unit_tests/PortMCP23S17_read/PortMCP23S17_read.ino +++ /dev/null @@ -1,25 +0,0 @@ -/* unit test for PortMCP23S17 -Picture of hardware is in unit_tests/PortMCP23S17_read/PortMCP23S17_bb.JPG -The setup is an MCP23S17 I/O expander on a Teensy LC controller. -MCP23S17 port-B pins are alternately grounded and energized. -output is: 10101010 -*/ - -#include "Port_MCP23S17.h" - -const uint8_t IOE_ADDR = 0x20; //MCP23S17 address, all 3 ADDR pins grounded -Port_MCP23S17 portB(IOE_ADDR, 1, ~0); //read all pins - -void setup() -{ - uint8_t BitPattern; //reading of port B - - delay(6000); - portB.begin(HIGH); //HIGH or LOW, does not matter - - BitPattern = portB.read(); - Keyboard.print("BitPattern = "); - Keyboard.println(BitPattern, BIN); //prints 10101010 -} - -void loop() { } diff --git a/unit_tests/PortMCP23S17_write/PortMCP23S17_write.ino b/unit_tests/PortMCP23S17_write/PortMCP23S17_write.ino deleted file mode 100644 index 35d83ee..0000000 --- a/unit_tests/PortMCP23S17_write/PortMCP23S17_write.ino +++ /dev/null @@ -1,29 +0,0 @@ -/* unit test for Port_MCP23S17 -Picture of hardware is in unit_tests/PortMCP23S17_read/PortMCP23S17_bb.JPG -The setup is an MCP23S17 I/O expander on a Teensy LC controller. -MCP23S17 port-A GPIO pins are not connected to anything. -Port-A GPIO-pin ouputs alternate between 0 and 3.3 volts. - -Use a volt meter to measure port-A GPIO-pin outputs or red LED. -*/ -#include "Port_MCP23S17.h" - -const uint8_t IOE_ADDR = 0x20; //MCP23S17 address, all 3 ADDR pins grounded -Port_MCP23S17 portA(IOE_ADDR , 0, 0); //PortAWrite needed for begin() - -void setup() -{ - delay(6000); - Keyboard.println("start setup"); - portA.begin(LOW); //HIGH or LOW, not matter if readPins=0 - Keyboard.println("start loop"); -} - -void loop() -{ - portA.write(~0, HIGH); //set all GPIOA pins HIGH - delay(2000); - - portA.write(~0, LOW); //set all GPIOA pins LOW - delay(2000); -}