After a few more hours searching I came across this fork of some code that does exactly what I was after:
This is a useful resource on the topic as well:
I wrote a simple test sketch below.
From the library ButtonCurrent() will return a byte showing 8 debounced button states.
I set 8 pins as inputs with internal pullups (just so I didn't have to set up a board with 8 pull down resistors) and then just used a jumper wire to short each pin to ground, multiple at a time and wiping the ground wire down 8 pins and the code worked perfectly. I tested also with one of my noisy switches and the state change was detected flawlessly.
I think I will use this code to read each 8-bit value from 6 x 74HC165 PISO shift registers unless anyone can tell me otherwise.
I'll grab some shift registers tomorrow to test this via SPI read in of the shift register and also with more than one byte of data, I'll just have to use n x Debouncer objects.
In the final code I will have to change the object to be declared volatile so I can run an ISR from a timer based interrupt of a suitable frequency.
#include <ButtonDebounce.h>
long timer1 = millis();
long timer2 = millis();
byte tempByte;
byte lastButtonState;
byte currentButtonState;
//instantiate the debouncer will all pins using internal pullups
Debouncer port1(0b11111111);
//with external pulldowns it would be
//Debouncer port1();
//Debouncer port2(); etc
void setup() {
Serial.begin(9600);
pinMode(0,INPUT_PULLUP);
pinMode(1,INPUT_PULLUP);
pinMode(2,INPUT_PULLUP);
pinMode(3,INPUT_PULLUP);
pinMode(4,INPUT_PULLUP);
pinMode(5,INPUT_PULLUP);
pinMode(7,INPUT_PULLUP);
pinMode(8,INPUT_PULLUP);
}
void prntBits(byte b)
{
for(int i = 7; i >= 0; i--)
Serial.print(bitRead(b,i));
Serial.println();
}
void loop() {
//read button states every 4ms
//debounce library is chekcing for 8 concurrent button states
//therfore allowing for 24ms bounce
if (millis() - timer1 > 4) {
//generate a byte from 8 digital pin reads to simulate shift register read of one byte
tempByte = digitalRead (0);
tempByte |= digitalRead (1) << 1;
tempByte |= digitalRead (2) << 2;
tempByte |= digitalRead (3) << 3;
tempByte |= digitalRead (4) << 4;
tempByte |= digitalRead (5) << 5;
tempByte |= digitalRead (7) << 6;
tempByte |= digitalRead (8) << 7;
port1.ButtonProcess(tempByte);
timer1 = millis();
}
lastButtonState = currentButtonState;
//read all 8 bits
currentButtonState = port1.ButtonCurrent(0b11111111);
if (lastButtonState ^ currentButtonState ) {
//state for the byte has changed - print it
prntBits(currentButtonState);
}
}