More os modes

This commit is contained in:
2026-03-15 16:46:06 -07:00
parent 8431906337
commit bd821448f2
4 changed files with 100 additions and 62 deletions

View File

@@ -1,10 +1,10 @@
#include QMK_KEYBOARD_H
#include "keymap_introspection.h"
#include "dynamic_keymap.h"
#include "mac_mode.h"
#include "os_mode.h"
enum custom_keycodes {
CK_MCMD = SAFE_RANGE, // toggle mac-command mode
CK_OSMODE = SAFE_RANGE, // cycle OS mode
};
typedef struct {
@@ -121,7 +121,7 @@ ________________________________________________________________________________
*/
[1] = LAYOUT(
QK_BOOT, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, CK_MCMD, KC_MPLY,
QK_BOOT, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, CK_OSMODE, KC_MPLY,
KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, RGB_TOG, RGB_VAD, RGB_VAI, KC_TRNS, KC_VOLU,
KC_PSCR, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_HOME, KC_PGDN, KC_PGUP, KC_END, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_VOLD,
KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_LEFT, KC_DOWN, KC_UP, KC_RGHT, KC_TRNS, KC_TRNS, KC_TRNS, KC_MUTE,
@@ -130,7 +130,7 @@ ________________________________________________________________________________
),
[2] = LAYOUT(
KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS,
KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS,
KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS,
KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS,
KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS,
@@ -139,7 +139,7 @@ ________________________________________________________________________________
),
[3] = LAYOUT(
KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS,
KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS,
KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS,
KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS,
KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS,
@@ -148,62 +148,65 @@ ________________________________________________________________________________
),
};
// Override layer resolution: in mac mode, any modifier forces layer 0 (ignores FN)
// Override layer resolution: any modifier forces layer 0 (ignores FN)
uint16_t keymap_key_to_keycode(uint8_t layer, keypos_t key) {
if (mac_mode && (get_mods() & (MOD_MASK_CTRL | MOD_MASK_SHIFT | MOD_MASK_ALT | MOD_MASK_GUI))) {
if (os_mode != OS_MODE_NONE && get_mods()) {
layer = 0;
}
if (key.row < MATRIX_ROWS && key.col < MATRIX_COLS) {
return keycode_at_keymap_location(layer, key.row, key.col);
}
return KC_NO;
return keycode_at_keymap_location(layer, key.row, key.col);
}
static bool gui_tapped = false;
static bool super_tapped = false;
bool process_record_user(uint16_t keycode, keyrecord_t *record) {
// Cycle OS mode (FN+Del)
if (keycode == CK_OSMODE) {
if (record->event.pressed) {
os_mode = (os_mode + 1) % 4;
os_mode_manual = true;
rgb_matrix_mode_noeeprom(RGB_MATRIX_SOLID_COLOR);
switch (os_mode) {
case OS_MODE_NONE: rgb_matrix_sethsv_noeeprom(HSV_RED); break;
case OS_MODE_LINUX: rgb_matrix_sethsv_noeeprom(HSV_GREEN); break;
case OS_MODE_MAC: rgb_matrix_sethsv_noeeprom(HSV_YELLOW); break;
case OS_MODE_WINDOWS: rgb_matrix_sethsv_noeeprom(HSV_BLUE); break;
}
}
return false;
}
// No rewrites in none mode
if (os_mode == OS_MODE_NONE) return true;
// Any other key pressed while GUI held means it's being used as a modifier
if (record->event.pressed && keycode != KC_LGUI) {
gui_tapped = false;
super_tapped = false;
}
switch (keycode) {
// Mac mode: tap Super -> Cmd+Space (Spotlight)
// Linux: tap Super passes through normally (KDE app menu)
// Linux/Windows: tap Super passes through normally (KDE app menu)
case KC_LGUI:
if (mac_mode) {
if (os_mode == OS_MODE_MAC) {
if (record->event.pressed) {
gui_tapped = true;
super_tapped = true;
register_mods(MOD_BIT(KC_LGUI));
} else {
if (gui_tapped) {
if (super_tapped) {
tap_code(KC_SPC); // GUI still held, sends Super+Space
gui_tapped = false;
super_tapped = false;
}
unregister_mods(MOD_BIT(KC_LGUI));
}
return false;
}
break;
case CK_MCMD:
if (record->event.pressed) {
mac_mode = !mac_mode;
mac_mode_manual = true;
// Flash LEDs to indicate mode: green = mac, red = normal
rgb_matrix_mode_noeeprom(RGB_MATRIX_SOLID_COLOR);
if (mac_mode) {
rgb_matrix_sethsv_noeeprom(HSV_GREEN);
} else {
rgb_matrix_sethsv_noeeprom(HSV_BLUE);
}
}
return false;
// Mac mode rewrites:
// Ctrl+C/V -> Super+C/V (copy/paste)
// Ctrl+Shift+C/V -> Super+C/V (terminal copy/paste)
case KC_C:
case KC_V:
if (mac_mode && record->event.pressed) {
if (os_mode == OS_MODE_MAC && record->event.pressed) {
if (rewrite_mods(keycode, CTRL_TO_SUPER)) return false;
if (rewrite_mods(keycode, CTRL_SHIFT_TO_SUPER)) return false;
}
@@ -218,7 +221,7 @@ bool process_record_user(uint16_t keycode, keyrecord_t *record) {
case KC_W:
case KC_L:
case KC_R:
if (mac_mode && record->event.pressed) {
if (os_mode == OS_MODE_MAC && record->event.pressed) {
if (rewrite_mods(keycode, CTRL_TO_SUPER)) return false;
}
break;
@@ -228,7 +231,7 @@ bool process_record_user(uint16_t keycode, keyrecord_t *record) {
case KC_Z:
case KC_T:
case KC_N:
if (mac_mode && record->event.pressed) {
if (os_mode == OS_MODE_MAC && record->event.pressed) {
if (rewrite_mods(keycode, CTRL_TO_SUPER)) return false;
if (rewrite_mods(keycode, CTRL_SHIFT_TO_CMD_SHIFT)) return false;
}
@@ -238,7 +241,7 @@ bool process_record_user(uint16_t keycode, keyrecord_t *record) {
// Ctrl+Left/Right -> Alt+Left/Right (word navigation)
case KC_LEFT:
case KC_RGHT:
if (mac_mode && record->event.pressed) {
if (os_mode == OS_MODE_MAC && record->event.pressed) {
if (rewrite_mods(keycode, CTRL_ALT_TO_CTRL)) return false;
if (rewrite_mods(keycode, CTRL_TO_ALT)) return false;
}
@@ -246,7 +249,7 @@ bool process_record_user(uint16_t keycode, keyrecord_t *record) {
// Mac mode rewrites:
// Ctrl+Backspace -> Alt+Backspace (delete word backward)
case KC_BSPC:
if (mac_mode && record->event.pressed) {
if (os_mode == OS_MODE_MAC && record->event.pressed) {
if (rewrite_mods(keycode, CTRL_TO_ALT)) return false;
}
break;
@@ -254,38 +257,41 @@ bool process_record_user(uint16_t keycode, keyrecord_t *record) {
// Home -> Super+Left (line start)
// End -> Super+Right (line end)
case KC_HOME:
if (mac_mode && record->event.pressed) {
if (os_mode == OS_MODE_MAC && record->event.pressed) {
if (rewrite_mods_and_key(NONE_TO_SUPER, KC_LEFT)) return false;
}
break;
case KC_END:
if (mac_mode && record->event.pressed) {
if (os_mode == OS_MODE_MAC && record->event.pressed) {
if (rewrite_mods_and_key(NONE_TO_SUPER, KC_RGHT)) return false;
}
break;
// Mac mode rewrites:
// Alt+F4 -> Super+Q (quit app)
case KC_F4:
if (mac_mode && record->event.pressed) {
if (os_mode == OS_MODE_MAC && record->event.pressed) {
if (rewrite_mods_and_key(ALT_TO_SUPER, KC_Q)) return false;
}
break;
// Mac mode rewrites:
// Alt+Tab -> Super+Tab (app switcher)
case KC_TAB:
if (mac_mode && record->event.pressed) {
if (os_mode == OS_MODE_MAC && record->event.pressed) {
if (rewrite_mods(keycode, ALT_TO_SUPER)) return false;
}
break;
// Workspace overview (both modes):
// Super+Up -> Super+W (KDE overview, linux)
// Super+Up -> Ctrl+Up (Mission Control, mac)
// Workspace overview:
// Super+Up -> Super+W (KDE overview, linux)
// Super+Up -> Ctrl+Up (Mission Control, mac)
// Super+Up -> Super+Tab (Task View, windows)
case KC_UP:
if (record->event.pressed) {
if (mac_mode) {
if (os_mode == OS_MODE_MAC) {
if (rewrite_mods(keycode, SUPER_TO_CTRL)) return false;
} else {
} else if (os_mode == OS_MODE_LINUX) {
if (rewrite_mods_and_key(SUPER_TO_SUPER, KC_W)) return false;
} else if (os_mode == OS_MODE_WINDOWS) {
if (rewrite_mods_and_key(SUPER_TO_SUPER, KC_TAB)) return false;
}
}
break;