|
|
|
#include "Kaleidoscope.h"
|
Rework the hook handling
We can't register hooks from constructors, because there is no guaranteed order
in which the objects will be created. So it may well happen that the Keyboardio
object gets created later, and zeroes out everything. Or it gets created first,
and registers the default handler as the first one, making all the others
pointless.
Instead, we create a KeyboardioPlugin class, that has a `begin` method. This is
responsible for setting up the hooks and whatnot. To make things simpler (for
some values of simple), a `Keyboardio.use` method is introduced, which, when
given a NULL-terminated list of plugin object pointers, will call the begin
method of each.
All LED effects and other plugins that used to register a static object now use
an extern, and had their initialization moved to the `begin` method.
The end result is not the nicest thing, but it works. We can try figuring out
something nicer later.
Signed-off-by: Gergely Nagy <algernon@madhouse-project.org>
8 years ago
|
|
|
#include <stdarg.h>
|
|
|
|
|
|
|
|
Kaleidoscope_::eventHandlerHook Kaleidoscope_::eventHandlers[HOOK_MAX];
|
|
|
|
Kaleidoscope_::loopHook Kaleidoscope_::loopHooks[HOOK_MAX];
|
|
|
|
|
|
|
|
Kaleidoscope_::Kaleidoscope_(void) {
|
|
|
|
}
|
|
|
|
|
|
|
|
void
|
|
|
|
Kaleidoscope_::setup(void) {
|
|
|
|
KeyboardHardware.setup();
|
|
|
|
|
|
|
|
kaleidoscope::hid::initializeKeyboard();
|
|
|
|
kaleidoscope::hid::initializeConsumerControl();
|
|
|
|
kaleidoscope::hid::initializeSystemControl();
|
|
|
|
|
|
|
|
// A workaround, so that the compiler does not optimize handleKeyswitchEvent out...
|
|
|
|
// This is a no-op, but tricks the compiler into not being too helpful
|
|
|
|
// TODO(anyone): figure out how to hint the compiler in a more reasonable way
|
|
|
|
handleKeyswitchEvent(Key_NoKey, 255, 255, 0);
|
|
|
|
|
|
|
|
// Update the keymap cache, so we start with a non-empty state.
|
|
|
|
Layer.updateActiveLayers();
|
|
|
|
for (byte row = 0; row < ROWS; row++) {
|
|
|
|
for (byte col = 0; col < COLS; col++) {
|
|
|
|
Layer.updateLiveCompositeKeymap(row, col);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
void
|
|
|
|
Kaleidoscope_::loop(void) {
|
|
|
|
KeyboardHardware.scanMatrix();
|
|
|
|
|
|
|
|
for (byte i = 0; loopHooks[i] != NULL && i < HOOK_MAX; i++) {
|
|
|
|
loopHook hook = loopHooks[i];
|
|
|
|
(*hook)(false);
|
|
|
|
}
|
|
|
|
|
|
|
|
kaleidoscope::hid::sendKeyboardReport();
|
|
|
|
kaleidoscope::hid::releaseAllKeys();
|
|
|
|
|
|
|
|
for (byte i = 0; loopHooks[i] != NULL && i < HOOK_MAX; i++) {
|
|
|
|
loopHook hook = loopHooks[i];
|
|
|
|
(*hook)(true);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
void
|
|
|
|
Kaleidoscope_::replaceEventHandlerHook(eventHandlerHook oldHook, eventHandlerHook newHook) {
|
|
|
|
for (byte i = 0; i < HOOK_MAX; i++) {
|
|
|
|
if (eventHandlers[i] == oldHook) {
|
|
|
|
eventHandlers[i] = newHook;
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
void
|
|
|
|
Kaleidoscope_::appendEventHandlerHook(eventHandlerHook hook) {
|
|
|
|
replaceEventHandlerHook((eventHandlerHook)NULL, hook);
|
|
|
|
}
|
|
|
|
|
|
|
|
void
|
|
|
|
Kaleidoscope_::useEventHandlerHook(eventHandlerHook hook) {
|
|
|
|
for (byte i = 0; i < HOOK_MAX; i++) {
|
|
|
|
if (eventHandlers[i] == hook)
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
appendEventHandlerHook(hook);
|
|
|
|
}
|
|
|
|
|
|
|
|
void
|
|
|
|
Kaleidoscope_::replaceLoopHook(loopHook oldHook, loopHook newHook) {
|
|
|
|
for (byte i = 0; i < HOOK_MAX; i++) {
|
|
|
|
if (loopHooks[i] == oldHook) {
|
|
|
|
loopHooks[i] = newHook;
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
void
|
|
|
|
Kaleidoscope_::appendLoopHook(loopHook hook) {
|
|
|
|
replaceLoopHook((loopHook)NULL, hook);
|
|
|
|
}
|
|
|
|
|
|
|
|
void
|
|
|
|
Kaleidoscope_::useLoopHook(loopHook hook) {
|
|
|
|
for (byte i = 0; i < HOOK_MAX; i++) {
|
|
|
|
if (loopHooks[i] == hook)
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
appendLoopHook(hook);
|
|
|
|
}
|
|
|
|
|
|
|
|
bool
|
|
|
|
Kaleidoscope_::focusHook(const char *command) {
|
|
|
|
enum {
|
|
|
|
ON,
|
|
|
|
OFF,
|
|
|
|
GETSTATE,
|
|
|
|
} subCommand;
|
|
|
|
|
|
|
|
if (strncmp_P(command, PSTR("layer."), 6) != 0)
|
|
|
|
return false;
|
|
|
|
|
|
|
|
if (strcmp_P(command + 6, PSTR("on")) == 0)
|
|
|
|
subCommand = ON;
|
|
|
|
else if (strcmp_P(command + 6, PSTR("off")) == 0)
|
|
|
|
subCommand = OFF;
|
|
|
|
else if (strcmp_P(command + 6, PSTR("getState")) == 0)
|
|
|
|
subCommand = GETSTATE;
|
|
|
|
else
|
|
|
|
return false;
|
|
|
|
|
|
|
|
switch (subCommand) {
|
|
|
|
case ON: {
|
|
|
|
uint8_t layer = Serial.parseInt();
|
|
|
|
Layer.on(layer);
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
|
|
|
|
case OFF: {
|
|
|
|
uint8_t layer = Serial.parseInt();
|
|
|
|
Layer.off(layer);
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
|
|
|
|
case GETSTATE:
|
|
|
|
Serial.println(Layer.getLayerState(), BIN);
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
|
|
|
|
return true;
|
|
|
|
}
|
|
|
|
|
|
|
|
Kaleidoscope_ Kaleidoscope;
|
|
|
|
|
|
|
|
/* Deprecated functions */
|
|
|
|
|
|
|
|
void event_handler_hook_use(Kaleidoscope_::eventHandlerHook hook) {
|
|
|
|
Kaleidoscope.useEventHandlerHook(hook);
|
|
|
|
}
|
|
|
|
|
|
|
|
void loop_hook_use(Kaleidoscope_::loopHook hook) {
|
|
|
|
Kaleidoscope.useLoopHook(hook);
|
|
|
|
}
|
|
|
|
|
|
|
|
void __USE_PLUGINS(KaleidoscopePlugin *plugin, ...) {
|
|
|
|
va_list ap;
|
|
|
|
|
|
|
|
Kaleidoscope.use(plugin);
|
|
|
|
|
|
|
|
va_start(ap, plugin);
|
|
|
|
while ((plugin = (KaleidoscopePlugin *)va_arg(ap, KaleidoscopePlugin *)) != NULL)
|
|
|
|
Kaleidoscope.use(plugin);
|
|
|
|
va_end(ap);
|
|
|
|
}
|