Merge remote-tracking branch 'upstream/master' into hold-tap

This commit is contained in:
Christian Tu
2021-09-25 11:12:38 +02:00
30 changed files with 126 additions and 106 deletions

View File

@@ -1,4 +1,4 @@
from kmk.kmktime import sleep_ms
from time import sleep
def passthrough(key, keyboard, *args, **kwargs):
@@ -8,9 +8,6 @@ def passthrough(key, keyboard, *args, **kwargs):
def default_pressed(key, keyboard, KC, coord_int=None, coord_raw=None, *args, **kwargs):
keyboard.hid_pending = True
if coord_int is not None:
keyboard._coordkeys_pressed[coord_int] = key
keyboard.keys_pressed.add(key)
return keyboard
@@ -22,10 +19,6 @@ def default_released(
keyboard.hid_pending = True
keyboard.keys_pressed.discard(key)
if coord_int is not None:
keyboard.keys_pressed.discard(keyboard._coordkeys_pressed.get(coord_int, None))
keyboard._coordkeys_pressed[coord_int] = None
return keyboard
@@ -102,7 +95,7 @@ def bkdl_released(key, keyboard, KC, *args, **kwargs):
def sleep_pressed(key, keyboard, KC, *args, **kwargs):
sleep_ms(key.meta.ms)
sleep(key.meta.ms / 1000)
return keyboard

View File

@@ -52,7 +52,7 @@ HID_REPORT_SIZES = {
class AbstractHID:
REPORT_BYTES = 8
def __init__(self):
def __init__(self, **kwargs):
self._evt = bytearray(self.REPORT_BYTES)
self.report_device = memoryview(self._evt)[0:1]
self.report_device[0] = HIDReportTypes.KEYBOARD
@@ -239,11 +239,15 @@ class BLEHID(AbstractHID):
# Hardcoded in CPy
MAX_CONNECTIONS = const(2)
def post_init(self, ble_name=str(getmount('/').label), **kwargs):
def __init__(self, ble_name=str(getmount('/').label), **kwargs):
self.ble_name = ble_name
super().__init__()
def post_init(self):
self.conn_id = -1
self.ble = BLERadio()
self.ble.name = ble_name
self.ble.name = self.ble_name
self.hid = HIDService()
self.hid.protocol_mode = 0 # Boot protocol

View File

@@ -401,10 +401,6 @@ class Key:
self.no_press = bool(no_press)
self.no_release = bool(no_press)
self._pre_press_handlers = []
self._post_press_handlers = []
self._pre_release_handlers = []
self._post_release_handlers = []
self._handle_press = on_press
self._handle_release = on_release
self.meta = meta
@@ -424,26 +420,30 @@ class Key:
return 'Key(code={}, has_modifiers={})'.format(self.code, self.has_modifiers)
def on_press(self, state, coord_int, coord_raw):
for fn in self._pre_press_handlers:
if not fn(self, state, KC, coord_int, coord_raw):
return None
if hasattr(self, '_pre_press_handlers'):
for fn in self._pre_press_handlers:
if not fn(self, state, KC, coord_int, coord_raw):
return None
ret = self._handle_press(self, state, KC, coord_int, coord_raw)
for fn in self._post_press_handlers:
fn(self, state, KC, coord_int, coord_raw)
if hasattr(self, '_post_press_handlers'):
for fn in self._post_press_handlers:
fn(self, state, KC, coord_int, coord_raw)
return ret
def on_release(self, state, coord_int, coord_raw):
for fn in self._pre_release_handlers:
if not fn(self, state, KC, coord_int, coord_raw):
return None
if hasattr(self, '_pre_release_handlers'):
for fn in self._pre_release_handlers:
if not fn(self, state, KC, coord_int, coord_raw):
return None
ret = self._handle_release(self, state, KC, coord_int, coord_raw)
for fn in self._post_release_handlers:
fn(self, state, KC, coord_int, coord_raw)
if hasattr(self, '_post_release_handlers'):
for fn in self._post_release_handlers:
fn(self, state, KC, coord_int, coord_raw)
return ret
@@ -485,6 +485,8 @@ class Key:
calls of this method will be executed before those provided by later calls.
'''
if not hasattr(self, '_pre_press_handlers'):
self._pre_press_handlers = []
self._pre_press_handlers.append(fn)
return self
@@ -508,6 +510,8 @@ class Key:
calls of this method will be executed before those provided by later calls.
'''
if not hasattr(self, '_post_press_handlers'):
self._post_press_handlers = []
self._post_press_handlers.append(fn)
return self
@@ -532,6 +536,8 @@ class Key:
calls of this method will be executed before those provided by later calls.
'''
if not hasattr(self, '_pre_release_handlers'):
self._pre_release_handlers = []
self._pre_release_handlers.append(fn)
return self
@@ -555,6 +561,8 @@ class Key:
calls of this method will be executed before those provided by later calls.
'''
if not hasattr(self, '_post_release_handlers'):
self._post_release_handlers = []
self._post_release_handlers.append(fn)
return self

View File

@@ -1,7 +1,8 @@
from supervisor import ticks_ms
from kmk.consts import KMK_RELEASE, UnicodeMode
from kmk.hid import BLEHID, USBHID, AbstractHID, HIDModes
from kmk.keys import KC
from kmk.kmktime import ticks_ms
from kmk.matrix import MatrixScanner, intify_coordinate
from kmk.types import TapDanceKeyMeta
@@ -42,7 +43,7 @@ class KMKKeyboard:
secondary_hid_type = None
_hid_helper = None
hid_pending = False
state_layer_key = None
current_key = None
matrix_update = None
secondary_matrix_update = None
_matrix_modify = None
@@ -52,6 +53,7 @@ class KMKKeyboard:
_trigger_powersave_enable = False
_trigger_powersave_disable = False
i2c_deinit_count = 0
_go_args = None
# this should almost always be PREpended to, replaces
# former use of reversed_active_layers which had pointless
@@ -119,7 +121,6 @@ class KMKKeyboard:
self.state_changed = True
def _find_key_in_map(self, int_coord, row, col):
self.state_layer_key = None
try:
idx = self.coord_mapping.index(int_coord)
except ValueError:
@@ -133,28 +134,39 @@ class KMKKeyboard:
return None
for layer in self.active_layers:
self.state_layer_key = self.keymap[layer][idx]
layer_key = self.keymap[layer][idx]
if not self.state_layer_key or self.state_layer_key == KC.TRNS:
if not layer_key or layer_key == KC.TRNS:
continue
if self.debug_enabled:
print('KeyResolution(key={})'.format(self.state_layer_key))
print('KeyResolution(key={})'.format(layer_key))
return self.state_layer_key
return layer_key
def _on_matrix_changed(self, row, col, is_pressed):
if self.debug_enabled:
print('MatrixChange(col={} row={} pressed={})'.format(col, row, is_pressed))
int_coord = intify_coordinate(row, col)
kc_changed = self._find_key_in_map(int_coord, row, col)
if not is_pressed:
self.current_key = self._coordkeys_pressed[int_coord]
if self.debug_enabled:
print('PressedKeyResolution(key={})'.format(self.current_key))
if kc_changed is None:
if self.current_key is None:
self.current_key = self._find_key_in_map(int_coord, row, col)
if is_pressed:
self._coordkeys_pressed[int_coord] = self.current_key
else:
self._coordkeys_pressed[int_coord] = None
if self.current_key is None:
print('MatrixUndefinedCoordinate(col={} row={})'.format(col, row))
return self
return self.process_key(kc_changed, is_pressed, int_coord, (row, col))
return self.process_key(self.current_key, is_pressed, int_coord, (row, col))
def process_key(self, key, is_pressed, coord_int=None, coord_raw=None):
if self._tapping and not isinstance(key.meta, TapDanceKeyMeta):
@@ -324,7 +336,7 @@ class KMKKeyboard:
self._hid_helper = BLEHID
else:
self._hid_helper = AbstractHID
self._hid_helper = self._hid_helper()
self._hid_helper = self._hid_helper(**self._go_args)
def _init_matrix(self):
self.matrix = MatrixScanner(
@@ -426,6 +438,7 @@ class KMKKeyboard:
print('Failed to run post hid function in extension: ', err, ext)
def go(self, hid_type=HIDModes.USB, secondary_hid_type=None, **kwargs):
self._go_args = kwargs
self.hid_type = hid_type
self.secondary_hid_type = secondary_hid_type
@@ -444,13 +457,14 @@ class KMKKeyboard:
ext.during_bootup(self)
except Exception:
if self.debug_enabled:
print('Failed to load extention', ext)
print('Failed to load extension', ext)
self._init_matrix()
self._print_debug_cycle(init=True)
while True:
self.current_key = None
self.state_changed = False
self.sandbox.active_layers = self.active_layers.copy()

View File

@@ -1,23 +1,15 @@
import time
from micropython import const
_TICKS_PERIOD = const(1 << 29)
_TICKS_MAX = const(_TICKS_PERIOD - 1)
_TICKS_HALFPERIOD = const(_TICKS_PERIOD // 2)
def sleep_ms(ms):
return time.sleep(ms / 1000)
def ticks_diff(new, start):
diff = (new - start) & _TICKS_MAX
diff = ((diff + _TICKS_HALFPERIOD) & _TICKS_MAX) - _TICKS_HALFPERIOD
return diff
def ticks_ms():
'''Has .25s granularity, but is cheap'''
return time.monotonic() * 1000
def ticks_diff(new, old):
return new - old
def accurate_ticks():
'''Is more expensive, but good for time critical things'''
return time.monotonic_ns()
def accurate_ticks_diff(new, old, ms):
return bool(new - old < ms * 1000000)
def check_deadline(new, start, ms):
return ticks_diff(new, start) < ms

View File

@@ -1,6 +1,6 @@
import digitalio
from supervisor import ticks_ms
from kmk.kmktime import ticks_ms
from kmk.modules import Module

View File

@@ -1,5 +1,6 @@
'''One layer isn't enough. Adds keys to get to more of them'''
from micropython import const
from supervisor import ticks_ms
from kmk.key_validators import layer_key_validator
from kmk.keys import make_argumented_key

View File

@@ -1,3 +1,5 @@
from supervisor import ticks_ms
from kmk.key_validators import mod_tap_validator
from kmk.keys import make_argumented_key
from kmk.modules.holdtap import HoldTap

View File

@@ -1,9 +1,12 @@
import board
import digitalio
from supervisor import ticks_ms
from time import sleep
from kmk.handlers.stock import passthrough as handler_passthrough
from kmk.keys import make_key
from kmk.kmktime import sleep_ms, ticks_diff, ticks_ms
from kmk.kmktime import check_deadline
from kmk.modules import Module
@@ -100,10 +103,10 @@ class Power(Module):
'''
Sleeps longer and longer to save power the more time in between updates.
'''
if ticks_diff(ticks_ms(), self._powersave_start) <= 60000:
sleep_ms(8)
elif ticks_diff(ticks_ms(), self._powersave_start) >= 240000:
sleep_ms(180)
if check_deadline(ticks_ms(), self._powersave_start) <= 60000:
sleep(8 / 1000)
elif check_deadline(ticks_ms(), self._powersave_start) >= 240000:
sleep(180 / 1000)
return
def psave_time_reset(self):
@@ -120,7 +123,7 @@ class Power(Module):
return
def usb_rescan_timer(self):
return bool(ticks_diff(ticks_ms(), self._usb_last_scan) > 5000)
return bool(check_deadline(ticks_ms(), self._usb_last_scan) > 5000)
def usb_time_reset(self):
self._usb_last_scan = ticks_ms()

View File

@@ -1,10 +1,11 @@
'''Enables splitting keyboards wirelessly or wired'''
import busio
from micropython import const
from supervisor import ticks_ms
from storage import getmount
from kmk.kmktime import ticks_diff, ticks_ms
from kmk.kmktime import check_deadline
from kmk.matrix import intify_coordinate
from kmk.modules import Module
@@ -241,7 +242,7 @@ class Split(Module):
def ble_rescan_timer(self):
'''If true, the rescan timer is up'''
return bool(ticks_diff(ticks_ms(), self._ble_last_scan) > 5000)
return bool(check_deadline(ticks_ms(), self._ble_last_scan) > 5000)
def ble_time_reset(self):
'''Resets the rescan timer'''