wrote kf__chord__*__progmem() :)
parent
e036276dd0
commit
2964e68840
|
@ -59,9 +59,8 @@ void kb__led__delay__usb_init (void);
|
|||
void kb__led__logical_on (char led);
|
||||
void kb__led__logical_off (char led);
|
||||
// -------
|
||||
void kb__layout__exec_key ( bool pressed,
|
||||
uint8_t row,
|
||||
uint8_t column );
|
||||
void kb__layout__exec_key_pointer (bool pressed, void * pointer);
|
||||
void kb__layout__exec_key_location (bool pressed, uint8_t row, uint8_t column);
|
||||
|
||||
|
||||
// ----------------------------------------------------------------------------
|
||||
|
@ -240,8 +239,25 @@ void kb__layout__exec_key ( bool pressed,
|
|||
|
||||
// ----------------------------------------------------------------------------
|
||||
|
||||
// === kb__layout__exec_key ===
|
||||
/** functions/kb__layout__exec_key/description
|
||||
// === kb__layout__exec_key_pointer ===
|
||||
/** functions/kb__layout__exec_key_pointer/description
|
||||
* Perform a "press" or "release" of the key pointed to
|
||||
*
|
||||
* Arguments:
|
||||
* - `pressed`:
|
||||
* - `true`: Indicates that the key to be "executed" has been pressed
|
||||
* - `false`: Indicates that the key to be "executed" has been released
|
||||
* - `pointer`: A pointer to the key to execute
|
||||
*
|
||||
* Notes:
|
||||
* - The pointer may be of any type, and to a value in any address space. It
|
||||
* is up to the keyboard implementation to define this. Since this is the
|
||||
* only `exec_key_pointer` function though, all the keys should probably be
|
||||
* in the same address space, wherever they are.
|
||||
*/
|
||||
|
||||
// === kb__layout__exec_key_location ===
|
||||
/** functions/kb__layout__exec_key_location/description
|
||||
* Perform the appropriate actions for a "press" or "release" of the key at the
|
||||
* given position.
|
||||
*
|
||||
|
|
|
@ -25,12 +25,13 @@
|
|||
extern KEY_T layout[][KB__ROWS][KB__COLUMNS];
|
||||
|
||||
// ----------------------------------------------------------------------------
|
||||
void kb__layout__exec_key_pointer(key_t * pointer) { // TODO
|
||||
}
|
||||
|
||||
void kb__layout__exec_key( bool pressed,
|
||||
int8_t layer,
|
||||
int8_t row,
|
||||
int8_t column ) {
|
||||
// TODO
|
||||
void kb__layout__exec_key_location( bool pressed, // TODO
|
||||
int8_t layer,
|
||||
int8_t row,
|
||||
int8_t column ) {
|
||||
// - check for key redefinition in the EEPROM
|
||||
// - if there is one, execute it, according to the appropriate rules
|
||||
// - lookup key in PROGMEM
|
||||
|
|
|
@ -34,23 +34,26 @@
|
|||
2, &kf__press, KEY__LeftShift, \
|
||||
&kf__press, value }; \
|
||||
const uint16_t PROGMEM name##__release[] = { \
|
||||
2, &kf__release, KEY__LeftShift, \
|
||||
&kf__release, value }; \
|
||||
2, &kf__release, value, \
|
||||
&kf__release, KEY__LeftShift }; \
|
||||
KEY_T name = { &kf__macro__progmem, &name##__press, \
|
||||
&kf__macro__progmem, &name##__release }
|
||||
|
||||
|
||||
// other `keys__` macros (in the `keys__` namespace for consistency)
|
||||
|
||||
#define KEYS__TWO_KEYS_CAPSLOCK_PRESS_RELEASE(name, value) \
|
||||
const uint16_t PROGMEM name##__press[] = { \
|
||||
2, &kf__two_keys_capslock, 1, \
|
||||
&kf__press, value }; \
|
||||
const uint16_t PROGMEM name##__release[] = { \
|
||||
2, &kf__two_keys_capslock, 0, \
|
||||
&kf__release, value }; \
|
||||
KEY_T name = { &kf__macro__progmem, &name##__press, \
|
||||
&kf__macro__progmem, &name##release }
|
||||
// TODO: rewrite to reflect: kf__two_keys_capslock() -> kf__toggle_capslock() +
|
||||
// kf__chord__progmem() (or some such thing)
|
||||
// #define KEYS__TWO_KEYS_CAPSLOCK(name, value) \
|
||||
// const uint16_t PROGMEM name##__press[] = { \
|
||||
// 2, &kf__two_keys_capslock, 1, \
|
||||
// &kf__press, value }; \
|
||||
// const uint16_t PROGMEM name##__release[] = { \
|
||||
// 2, &kf__two_keys_capslock, 0, \
|
||||
// &kf__release, value }; \
|
||||
// KEY_T name = { &kf__macro__progmem, &name##__press, \
|
||||
// &kf__macro__progmem, &name##__release }
|
||||
#define KEYS__TWO_KEYS_CAPSLOCK(name, value) KEYS__DEFAULT(name, value)
|
||||
|
||||
// ----------------------------------------------------------------------------
|
||||
|
||||
|
@ -76,10 +79,10 @@ KEYS__DEFAULT( Mute, KEY__Mute );
|
|||
// special function
|
||||
|
||||
// --- Sh2KCapL
|
||||
KEYS__TWO_KEYS_CAPSLOCK_PRESS_RELEASE( Sh2KCapL, KEY__LeftShift );
|
||||
KEYS__TWO_KEYS_CAPSLOCK( Sh2KCapL, KEY__LeftShift );
|
||||
|
||||
// --- Sh2KCapR
|
||||
KEYS__TWO_KEYS_CAPSLOCK_PRESS_RELEASE( Sh2KCapR, KEY__RightShift );
|
||||
KEYS__TWO_KEYS_CAPSLOCK( Sh2KCapR, KEY__RightShift );
|
||||
|
||||
// --- Btldr
|
||||
KEY_T Btldr = { &kf__jump_to_bootloader, 0, NULL, 0 };
|
||||
|
|
|
@ -8,6 +8,10 @@
|
|||
* Some generally useful key-functions, and related definitions
|
||||
*
|
||||
* Prefix: `kf__`
|
||||
*
|
||||
* Notes:
|
||||
* - Several of these functions depend on the fact that (on an AVR) pointers
|
||||
* are 16-bit.
|
||||
*/
|
||||
|
||||
|
||||
|
@ -25,29 +29,17 @@ typedef void (*kf__function_pointer_t)(uint16_t value);
|
|||
// ----------------------------------------------------------------------------
|
||||
|
||||
// basic
|
||||
void kf__press (uint16_t keycode);
|
||||
void kf__release (uint16_t keycode);
|
||||
void kf__toggle (uint16_t keycode);
|
||||
void kf__layer__push (uint16_t id__layer);
|
||||
void kf__layer__pop (uint16_t id__ignore);
|
||||
// void kf__macro__sram (uint16_t pointer); // TODO
|
||||
void kf__macro__progmem (uint16_t pointer);
|
||||
// void kf__macro__eeprom (uint16_t pointer); // TODO
|
||||
void kf__press (uint16_t keycode);
|
||||
void kf__release (uint16_t keycode);
|
||||
void kf__toggle (uint16_t keycode);
|
||||
void kf__layer__push (uint16_t id__layer);
|
||||
void kf__layer__pop (uint16_t id__ignore);
|
||||
// void kf__macro__sram (uint16_t pointer); // TODO
|
||||
void kf__macro__progmem (uint16_t pointer);
|
||||
// void kf__macro__eeprom (uint16_t pointer); // TODO
|
||||
void kf__chord__press__progmem (uint16_t pointer); // TODO: write doc.
|
||||
void kf__chord__release__progmem (uint16_t pointer); // TODO: write doc.
|
||||
|
||||
// TODO: chording
|
||||
//
|
||||
// - consider making a 'kf__chord(uint16_t pointer)' that takes a pointer to an
|
||||
// array containing whatever's needed to specify [ which group of keys it
|
||||
// belongs to; whether to increment or decrement the counter for that group;
|
||||
// the threshold for action for that group; the action (possibly a
|
||||
// layer/row/col tuple for a key to call exec on, or possible just a row/col,
|
||||
// and a layer shift some other way, ...) ]
|
||||
//
|
||||
// - create a auto-resizing array ('flex_array'?) for use with this function,
|
||||
// and probably with the the layer stack functions as well. IDs can be
|
||||
// treated as array indices (the burden being on the user not to use indices
|
||||
// that are too large...)
|
||||
//
|
||||
// TODO: kf__macro__eeprom
|
||||
// - this should probably go into its own little place in 'lib'; it'll need a
|
||||
// function to write the macro to memory, code to keep track of what's
|
||||
|
@ -56,10 +48,6 @@ void kf__macro__progmem (uint16_t pointer);
|
|||
// TODO: kf__macro__sram
|
||||
// - is this necessary? will it be confusing (if we already have
|
||||
// kf__macro__eeprom)? we should probably remove it.
|
||||
//
|
||||
// TODO: rewrite layouts to reflect
|
||||
// - kf__two_keys_capslock() -> kf__toggle_capslock()
|
||||
// - the removal of kf__send()
|
||||
|
||||
// device
|
||||
void kf__jump_to_bootloader (uint16_t ignore);
|
||||
|
|
|
@ -12,12 +12,30 @@
|
|||
#include <stdbool.h>
|
||||
#include <stdint.h>
|
||||
#include <avr/pgmspace.h>
|
||||
#include "../../../../firmware/keyboard.h"
|
||||
#include "../../../../firmware/lib/usb.h"
|
||||
#include "../../../../firmware/lib/layout/layer-stack.h"
|
||||
#include "../key-functions.h"
|
||||
|
||||
// ----------------------------------------------------------------------------
|
||||
|
||||
static void _chord__progmem(bool pressed, void * pointer) { // TODO: test
|
||||
uint8_t * count = (uint8_t *) pgm_read_word( pointer );
|
||||
uint16_t threshold = (uint16_t) pgm_read_word( pointer+2 );
|
||||
void * key_pointer = (void *) pgm_read_word( pointer+4 );
|
||||
|
||||
if (pressed)
|
||||
*count++;
|
||||
|
||||
if (*count == threshold)
|
||||
kb__layout__exec_key_pointer(key_pointer);
|
||||
|
||||
if (!pressed)
|
||||
*count--;
|
||||
}
|
||||
|
||||
// ----------------------------------------------------------------------------
|
||||
|
||||
void kf__press(uint16_t keycode) {
|
||||
usb__kb__set_key(true, keycode);
|
||||
usb__kb__send_report();
|
||||
|
@ -59,36 +77,6 @@ void kf__macro__progmem(uint16_t pointer) { // TODO: test
|
|||
}
|
||||
}
|
||||
|
||||
// TODO: write documentation for this function
|
||||
// TODO: this is a mistakenly written function; i'm going to change it. what
|
||||
// we really want is a way to generate a "press" above a certain
|
||||
// threshold, and "release" going back the other way; this function would
|
||||
// make that possible, since it's quite general, but difficult and
|
||||
// space-consuming.
|
||||
static void _chord__progmem(bool pressed, uint16_t pointer) { // TODO: test
|
||||
#define funptr kf__function_pointer_t
|
||||
uint8_t * count = (uint8_t *) pgm_read_word( pointer );
|
||||
uint16_t threshold = (uint16_t) pgm_read_word( pointer+2 );
|
||||
funptr function = (funptr) pgm_read_word( pointer+4 );
|
||||
uint16_t argument = (uint16_t) pgm_read_word( pointer+6 );
|
||||
uint16_t direction__comparison = (uint16_t) pgm_read_word( pointer+8 );
|
||||
#undef funptr
|
||||
|
||||
char direction = ((char)(behavior >> 8));
|
||||
char comparison = ((char)(behavior & 0xff));
|
||||
|
||||
if (pressed) *count++;
|
||||
else *count--;
|
||||
|
||||
if ( (pressed && direction == 'p') ||
|
||||
(!pressed && direction == 'r') )
|
||||
if ( (comparison == '=' && *count == threshold) ||
|
||||
(comparison == '<' && *count < threshold) ||
|
||||
(comparison == '>' && *count > threshold) )
|
||||
if (function)
|
||||
(*function)();
|
||||
}
|
||||
|
||||
void kf__chord__press__progmem(uint16_t pointer) {
|
||||
_chord__progmem(true, pointer);
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue