document
This commit is contained in:
parent
2b856afa26
commit
fcaa6d06e9
@ -7,6 +7,25 @@ keybrd version 1.0.0 will be released when the public API is stable.
|
|||||||
|
|
||||||
## [Unreleased][unreleased]
|
## [Unreleased][unreleased]
|
||||||
|
|
||||||
|
## [0.3.2] - 2016-06-10
|
||||||
|
### Changed
|
||||||
|
* Changed uC from scanning port arrays to scanning Arduino pins.
|
||||||
|
Thereby added support for Arduino boards, Teensy 3, and Teensy LC micro controllers.
|
||||||
|
* Changed IOE from scanning port arrays to scanning single ports.
|
||||||
|
* Moved scanner and debouncer into their own classes.
|
||||||
|
|
||||||
|
### Added
|
||||||
|
* Row_uC
|
||||||
|
* Row_IOE
|
||||||
|
* RowScannerInterface
|
||||||
|
* RowScanner_PinsArray
|
||||||
|
* RowScanner_PinsBitwise
|
||||||
|
* DebouncerInterface
|
||||||
|
* Debouncer_4Samples
|
||||||
|
|
||||||
|
### Removed
|
||||||
|
* Port arrays
|
||||||
|
|
||||||
## [0.3.1] - 2016-06-02
|
## [0.3.1] - 2016-06-02
|
||||||
### Added
|
### Added
|
||||||
* RowBase class
|
* RowBase class
|
||||||
|
@ -8,8 +8,8 @@ The most common reason for new classes are:
|
|||||||
|
|
||||||
## Who this guide is for
|
## Who this guide is for
|
||||||
This guide is for the maintainers and developers of the keybrd library and it's extensions.
|
This guide is for the maintainers and developers of the keybrd library and it's extensions.
|
||||||
It is assumed the reader is familiar with C++ language including pointers, objects, classes, static class variables, aggregation, inheritance, polymorphism, and enum.
|
It is assumed the reader is familiar with C++ language including pointers, objects, classes, static class variables, composition, aggregation, inheritance, polymorphism, and enum.
|
||||||
Some classes use bit manipulation.
|
Debouncer and I/O expander use bit manipulation.
|
||||||
|
|
||||||
## Class inheritance diagrams
|
## Class inheritance diagrams
|
||||||
|
|
||||||
@ -18,8 +18,13 @@ Keybrd library class inheritance diagram
|
|||||||
Matrix
|
Matrix
|
||||||
|
|
||||||
RowBase
|
RowBase
|
||||||
|
|
/ \
|
||||||
Row
|
Row_uC Row_IOE
|
||||||
|
|
||||||
|
RowScannerInterface
|
||||||
|
/ \
|
||||||
|
RowScanner_PinsArray RowScanner_PinsBitwise
|
||||||
|
|
||||||
|
|
||||||
IOExpanderPort
|
IOExpanderPort
|
||||||
|
|
||||||
@ -36,6 +41,11 @@ Keybrd library class inheritance diagram
|
|||||||
LED_AVR LED_MCP23018 LED_PCA9655E (one LED class for each type of IC)
|
LED_AVR LED_MCP23018 LED_PCA9655E (one LED class for each type of IC)
|
||||||
|
|
||||||
|
|
||||||
|
DebouncerInterface
|
||||||
|
|
|
||||||
|
Debouncer_4Samples
|
||||||
|
|
||||||
|
|
||||||
LayerStateInterface
|
LayerStateInterface
|
||||||
|
|
|
|
||||||
LayerState
|
LayerState
|
||||||
@ -66,32 +76,70 @@ Keybrd library class inheritance diagram
|
|||||||
|
|
||||||
## Dependency diagrams
|
## Dependency diagrams
|
||||||
|
|
||||||
single-layer dependency diagram with LEDs
|
Example single-layer dependency diagram with LEDs
|
||||||
```
|
```
|
||||||
matrix[1..*]
|
matrix[1..*]
|
||||||
|
|
|
|
||||||
row[1..*]_____________________________
|
___ row_uC[1..*] ________
|
||||||
| \ \ \
|
/ \ \
|
||||||
rowPort[1] rowPin[1] colPort[1] keys[1]
|
RowScanner_PinsArray debouncer keys[1..*]
|
||||||
| |
|
/ \ |
|
||||||
colPins[1..*] code[1..*]
|
strobePin[1] readPins[1..*] code[1..*]
|
||||||
|
|
|
|
||||||
LED[1]
|
LED[1]
|
||||||
|
|
||||||
```
|
```
|
||||||
|
|
||||||
multi-layer dependency diagram with LEDs and I/O Expander
|
Example single-layer dependency diagram I/O Expander
|
||||||
```
|
```
|
||||||
matrix[1..*]
|
________ row_uC[1..*] _________
|
||||||
| layerStates[1..*]
|
/ \ \
|
||||||
row[1..*]_________________________________________/__ | \
|
RowScanner_PinsArray[1] debouncer[1] keys[1..*]
|
||||||
| \ \ \ / \ | \
|
/ \ |
|
||||||
rowPort[1] rowPin[1] colPort[1] keys[1] / code_layer[1..*] LED[0..*]
|
strobePin[1] readPins[1..*] code[1..*]
|
||||||
\ / \ | / /
|
|
||||||
\ / colPins[1..*] key[1..*] /
|
|
||||||
\ / | /
|
___ row_IOE[1..*] _________
|
||||||
\ / code[1..*] /
|
/ \ \
|
||||||
\ / ______________________________________/
|
RowScanner_PinsBitwise[1] debouncer[1] keys[1..*]
|
||||||
|
/ | \ |
|
||||||
|
rowPort[1] rowPin[1] colPort[1] code[1..*]
|
||||||
|
\ / \
|
||||||
|
\ / colPins[1..*]
|
||||||
|
\ /
|
||||||
|
IOExpanderPort[0..*]
|
||||||
|
|
||||||
|
```
|
||||||
|
|
||||||
|
Example multi-layer dependency diagram with layer LEDs
|
||||||
|
```
|
||||||
|
layerStates[1..*]
|
||||||
|
________ row_uC[1..*] _____________________/__ | \
|
||||||
|
/ \ \ / \ | \
|
||||||
|
RowScanner_PinsArray[1] debouncer[1] keys[1..*] / code_layer[1..*] LED[0..*]
|
||||||
|
/ \ | /
|
||||||
|
strobePin[1] readPins[1..*] code[1..*]
|
||||||
|
|
||||||
|
```
|
||||||
|
|
||||||
|
Example multi-layer dependency diagram with I/O Expander
|
||||||
|
```
|
||||||
|
|
||||||
|
________ row_uC[1..*] ________________________ _______layerStates[1..*]
|
||||||
|
/ \ \ \ / |
|
||||||
|
RowScanner_PinsArray[1] debouncer[1] keys[1..*] code_layer[1..*] |
|
||||||
|
/ \ | ________________________|
|
||||||
|
strobePin[1] readPins[1..*] code[1..*] |
|
||||||
|
|
|
||||||
|
|
|
||||||
|
___ row_IOE[1..*] _________ __________|
|
||||||
|
/ \ \ / |
|
||||||
|
RowScanner_PinsBitwise[1] debouncer[1] keys[1..*] code_layer[1..*] |
|
||||||
|
/ | \ | _____________________|
|
||||||
|
rowPort[1] rowPin[1] colPort[1] code[1..*]
|
||||||
|
\ / \
|
||||||
|
\ / colPins[1..*]
|
||||||
|
\ /
|
||||||
IOExpanderPort[0..*]
|
IOExpanderPort[0..*]
|
||||||
|
|
||||||
```
|
```
|
||||||
@ -162,23 +210,19 @@ Following the style guide makes it easier for the next programmer to understand
|
|||||||
## Trace of keybrd scan
|
## Trace of keybrd scan
|
||||||
Arduino does not have a debugger.
|
Arduino does not have a debugger.
|
||||||
So here is the next best thing; a list of functions in the order that they are called.
|
So here is the next best thing; a list of functions in the order that they are called.
|
||||||
|
The trace is of a single-layer keybrd scan (no LEDs and no I/O expander).
|
||||||
Refer to it like a table of contents while reading the keybrd library.
|
Refer to it like a table of contents while reading the keybrd library.
|
||||||
|
|
||||||
```
|
```
|
||||||
Matrix::scan() for each row
|
Matrix::scan() for each row
|
||||||
Row::process()
|
RowBase::process()
|
||||||
Row::wait()
|
RowBase::wait() delay time for debounce
|
||||||
Row::scan()
|
RowScanner_PinsArray::scan() strobe row on
|
||||||
RowPort_*::setActivePin*() strobe row on
|
for each readPin
|
||||||
for each col port
|
|
||||||
ColPort_*::read() read col port
|
|
||||||
RowPort_*::setActivePin*() strobe row off
|
|
||||||
Row::getRowState() for each col port
|
|
||||||
for each connected col pin
|
|
||||||
if key is pressed
|
|
||||||
set rowState bit
|
set rowState bit
|
||||||
Row::debounce() debounce
|
strobe row off
|
||||||
Row::pressRelease() for each key in row
|
Debouncer_4Samples::debounce() debounce
|
||||||
|
RowBase::pressRelease() for each key in row
|
||||||
if falling edge
|
if falling edge
|
||||||
Key_*::release() scanCode->release()
|
Key_*::release() scanCode->release()
|
||||||
Code_*::release() Keyboard.release(scancode)
|
Code_*::release() Keyboard.release(scancode)
|
||||||
|
@ -2,19 +2,19 @@ planned_features is a view of where the keybrd project is headed.
|
|||||||
|
|
||||||
Top priority
|
Top priority
|
||||||
============
|
============
|
||||||
Redesign elements of debouncer.
|
Add support for shift registers, for compact split keyboards up to 32 keys per matrix.
|
||||||
|
|
||||||
Med priority
|
Med priority
|
||||||
============
|
============
|
||||||
Add support for Teensy LC micro controller
|
|
||||||
|
|
||||||
Add 16x16 matrix capability (currently limited to 8x8 matrices)
|
Add 16x16 matrix capability (currently limited to 8x8 matrices)
|
||||||
|
|
||||||
Low priority
|
Low priority
|
||||||
============
|
============
|
||||||
Add matrix-to-layout mapping array (to decouple matrix from layout)
|
Add matrix-to-layout mapping array (to decouple matrix from layout)
|
||||||
|
|
||||||
Change tutorial sketches from teensy 2.0 and PCA9655E-D IOE to Teensy LC and MCP23018 IOE
|
Update tutorials:
|
||||||
|
* Currently tutorial sketches are obsolete and won't compile
|
||||||
|
* Change tutorial sketches from teensy 2.0 and PCA9655E-D IOE to Teensy LC and MCP23018 IOE
|
||||||
|
|
||||||
Add more tutorials:
|
Add more tutorials:
|
||||||
* tutorial_5_LEDs.md
|
* tutorial_5_LEDs.md
|
||||||
|
@ -24,7 +24,7 @@ For fastest response time, wait() should be placed before scan() or after pressR
|
|||||||
A keyboard with a faster scan rate responds faster.
|
A keyboard with a faster scan rate responds faster.
|
||||||
Follow these step to tune DELAY_MICROSECONDS for maximum scan rate for a given SAMPLE_COUNT:
|
Follow these step to tune DELAY_MICROSECONDS for maximum scan rate for a given SAMPLE_COUNT:
|
||||||
Initialize DELAY_MICROSECONDS in your sketch:
|
Initialize DELAY_MICROSECONDS in your sketch:
|
||||||
const unsigned int Row::DELAY_MICROSECONDS = 1000;
|
const unsigned int RowBase::DELAY_MICROSECONDS = 1000;
|
||||||
Add this to the sketch's loop() function:
|
Add this to the sketch's loop() function:
|
||||||
debug.print_microseconds_per_scan();
|
debug.print_microseconds_per_scan();
|
||||||
Compile and load the sketch into the microcontroller; microseconds_per_scan is printed every second.
|
Compile and load the sketch into the microcontroller; microseconds_per_scan is printed every second.
|
||||||
@ -42,12 +42,7 @@ Avoid sampling the switch input at a rate synchronous to events in the environme
|
|||||||
The largest allowable DELAY_MICROSECONDS is 65535 (.065535 seconds).
|
The largest allowable DELAY_MICROSECONDS is 65535 (.065535 seconds).
|
||||||
|
|
||||||
Polling I2C may slow the scan rate enough so that no additional delay is needed:
|
Polling I2C may slow the scan rate enough so that no additional delay is needed:
|
||||||
const unsigned int Row::DELAY_MICROSECONDS = 0;
|
const unsigned int RowBase::DELAY_MICROSECONDS = 0;
|
||||||
|
|
||||||
Slow-scan trick for debug messages that print too fast and not aligned, add this to sketch loop():
|
|
||||||
delay(500);
|
|
||||||
Keyboard.println(F(""));
|
|
||||||
That way debug messages are printed at a managable rate, and each scan starts a new line.
|
|
||||||
*/
|
*/
|
||||||
void RowBase::wait()
|
void RowBase::wait()
|
||||||
{
|
{
|
||||||
|
@ -5,9 +5,6 @@
|
|||||||
#include <Key.h>
|
#include <Key.h>
|
||||||
|
|
||||||
/* RowBase is an abstract base class.
|
/* RowBase is an abstract base class.
|
||||||
|
|
||||||
Define and initilize DELAY_MICROSECONDS in sketch.
|
|
||||||
const unsigned int RowBase::DELAY_MICROSECONDS = 0;
|
|
||||||
*/
|
*/
|
||||||
class RowBase
|
class RowBase
|
||||||
{
|
{
|
||||||
|
@ -1,11 +1,6 @@
|
|||||||
#ifndef ROWSCANNERINTERFACE_H
|
#ifndef ROWSCANNERINTERFACE_H
|
||||||
#define ROWSCANNERINTERFACE_H
|
#define ROWSCANNERINTERFACE_H
|
||||||
|
|
||||||
/* RowScannerInterface is an interface class.
|
|
||||||
Sets rowEnd and returns rowState.
|
|
||||||
rowEnd is bitwise, where 1 bit corrsiponds to place immediatly after last key of row.
|
|
||||||
rowEnd and rowMask are larger type than portMask so that they can not overflow.
|
|
||||||
*/
|
|
||||||
#include <Arduino.h>
|
#include <Arduino.h>
|
||||||
#include <inttypes.h>
|
#include <inttypes.h>
|
||||||
|
|
||||||
|
@ -1,7 +1,7 @@
|
|||||||
#include "RowScanner_PinsBitwise.h"
|
#include "RowScanner_PinsBitwise.h"
|
||||||
/*
|
/*
|
||||||
Strobes the row and reads the columns.
|
Strobes the row and reads the columns.
|
||||||
Strobe is on for shortest possible time to preserve IR LED on DodoHand's optic switch.
|
Sets rowEnd and returns rowState.
|
||||||
*/
|
*/
|
||||||
uint8_t RowScanner_PinsBitwise::scan(uint16_t& rowEnd)
|
uint8_t RowScanner_PinsBitwise::scan(uint16_t& rowEnd)
|
||||||
{
|
{
|
||||||
@ -16,13 +16,9 @@ uint8_t RowScanner_PinsBitwise::scan(uint16_t& rowEnd)
|
|||||||
}
|
}
|
||||||
delayMicroseconds(3); //time to stablize voltage
|
delayMicroseconds(3); //time to stablize voltage
|
||||||
|
|
||||||
//read all the port pins
|
//read the port pins
|
||||||
refColPort.read();
|
refColPort.read();
|
||||||
/* shows strobing pin 1 and 2, but realy stobing 0 and 1 todo
|
|
||||||
Keyboard.print(F(" strobePin="));
|
|
||||||
Keyboard.print(strobePin);
|
|
||||||
Keyboard.print(F(", "));
|
|
||||||
*/
|
|
||||||
//strobe row off
|
//strobe row off
|
||||||
if (activeHigh)
|
if (activeHigh)
|
||||||
{
|
{
|
||||||
|
@ -5,14 +5,29 @@
|
|||||||
#include <RowScanner_PinsBitwise.h>
|
#include <RowScanner_PinsBitwise.h>
|
||||||
#include <Debouncer_4Samples.h>
|
#include <Debouncer_4Samples.h>
|
||||||
|
|
||||||
/*
|
/* Row_DH_IOE is a row connected to an Input/Output Expander.
|
||||||
Simlar to Row but using RowScanner_PinsBitwise.
|
|
||||||
|
|
||||||
Configuration
|
Configuration
|
||||||
-------------
|
-------------
|
||||||
|
Define and initilize DELAY_MICROSECONDS in sketch. Detailed how to is in RowBase.cpp.
|
||||||
|
|
||||||
Instantiation
|
Instantiation
|
||||||
-------------
|
-------------
|
||||||
|
Example instantiation of a row:
|
||||||
|
const uint8_t IOExpanderPort::ADDR = 0x18;
|
||||||
|
|
||||||
|
IOExpanderPort port1(1, 0);
|
||||||
|
RowPort_PCA9655E rowPort1(port1);
|
||||||
|
|
||||||
|
IOExpanderPort port0(0, 0);
|
||||||
|
ColPort_PCA9655E colPort0(port0, 1<<0 | 1<<1 | 1<<2 | 1<<3 | 1<<4 | 1<<5 );
|
||||||
|
|
||||||
|
Key* const ptrsKeys_0[] = { &k_00, &k_01, &k_02, &k_03, &k_04, &k_05 };
|
||||||
|
Row_IOE row_0(rowPort1, 1<<0, colPort0, ptrsKeys_0);
|
||||||
|
|
||||||
|
Number of pins in colPort0 should equal number of keys in ptrsKeys_0[] array.
|
||||||
|
if a pin is missing, a key will be unresposive
|
||||||
|
if a Key pointer is missing, the keyboard will fail in an unprdictable way
|
||||||
*/
|
*/
|
||||||
class Row_IOE : public RowBase
|
class Row_IOE : public RowBase
|
||||||
{
|
{
|
||||||
|
15
src/Row_uC.h
15
src/Row_uC.h
@ -5,13 +5,24 @@
|
|||||||
#include <RowScanner_PinsArray.h>
|
#include <RowScanner_PinsArray.h>
|
||||||
#include <Debouncer_4Samples.h>
|
#include <Debouncer_4Samples.h>
|
||||||
|
|
||||||
/*
|
/* Row_uC is a row connected to a micro controller.
|
||||||
Configuration
|
Configuration
|
||||||
-------------
|
-------------
|
||||||
|
Define and initilize DELAY_MICROSECONDS in sketch. Detailed how to is in RowBase.cpp.
|
||||||
|
|
||||||
Instantiation
|
Instantiation
|
||||||
-------------
|
-------------
|
||||||
todo - see RowDH
|
Example instantiation of a row:
|
||||||
|
|
||||||
|
const uint8_t colPins[] = {0,1,2,3,7,8};
|
||||||
|
const uint8_t COL_PIN_COUNT = sizeof(colPins)/sizeof(*colPins);
|
||||||
|
|
||||||
|
Key* const ptrsKeys_0[] = { &k_00, &k_01, &k_02, &k_03, &k_04, &k_05 };
|
||||||
|
Row_DH_uC row_0(21, colPins, COL_PIN_COUNT, ptrsKeys_0);
|
||||||
|
|
||||||
|
Number of colPins should equal number of keys in ptrsKeys_0[] array.
|
||||||
|
if a colPin is missing, a key will be unresposive
|
||||||
|
if a Key pointer is missing, the keyboard will fail in an unprdictable way
|
||||||
*/
|
*/
|
||||||
class Row_uC : public RowBase
|
class Row_uC : public RowBase
|
||||||
{
|
{
|
||||||
|
Binary file not shown.
@ -19,7 +19,7 @@ The tutorials assume the reader:
|
|||||||
* is new to Arduino, firmware, controllers, and the internal workings of keyboards
|
* is new to Arduino, firmware, controllers, and the internal workings of keyboards
|
||||||
|
|
||||||
<!-- todo -->
|
<!-- todo -->
|
||||||
> All the tutorial sketches are tested on teensy 2.0 and PCA9655E-D I/O expander
|
> Most of the tutorial sketches are obsolete and will not compile. Will be updated soon.
|
||||||
|
|
||||||
> The tutorial sketches will be changed to Teensy LC and MCP23018 I/O expander
|
> The tutorial sketches will be changed to Teensy LC and MCP23018 I/O expander
|
||||||
|
|
||||||
|
Reference in New Issue
Block a user