aboutsummaryrefslogtreecommitdiff
path: root/lib
diff options
context:
space:
mode:
Diffstat (limited to 'lib')
-rw-r--r--lib/python/qmk/cli/__init__.py1
-rwxr-xr-xlib/python/qmk/cli/generate/config_h.py4
-rwxr-xr-xlib/python/qmk/cli/generate/keyboard_c.py38
-rw-r--r--lib/python/qmk/cli/generate/keymap_h.py51
-rw-r--r--lib/python/qmk/commands.py4
-rw-r--r--lib/python/qmk/constants.py2
-rw-r--r--lib/python/qmk/info.py19
-rw-r--r--lib/python/qmk/keymap.py34
8 files changed, 114 insertions, 39 deletions
diff --git a/lib/python/qmk/cli/__init__.py b/lib/python/qmk/cli/__init__.py
index f331445870..0baf19a629 100644
--- a/lib/python/qmk/cli/__init__.py
+++ b/lib/python/qmk/cli/__init__.py
@@ -58,6 +58,7 @@ subcommands = [
'qmk.cli.generate.keyboard_h',
'qmk.cli.generate.keycodes',
'qmk.cli.generate.keycodes_tests',
+ 'qmk.cli.generate.keymap_h',
'qmk.cli.generate.make_dependencies',
'qmk.cli.generate.rgb_breathe_table',
'qmk.cli.generate.rules_mk',
diff --git a/lib/python/qmk/cli/generate/config_h.py b/lib/python/qmk/cli/generate/config_h.py
index fc681300a3..d613f7b92c 100755
--- a/lib/python/qmk/cli/generate/config_h.py
+++ b/lib/python/qmk/cli/generate/config_h.py
@@ -135,8 +135,8 @@ def generate_encoder_config(encoder_json, config_h_lines, postfix=''):
b_pads.append(encoder["pin_b"])
resolutions.append(encoder.get("resolution", None))
- config_h_lines.append(generate_define(f'ENCODERS_PAD_A{postfix}', f'{{ {", ".join(a_pads)} }}'))
- config_h_lines.append(generate_define(f'ENCODERS_PAD_B{postfix}', f'{{ {", ".join(b_pads)} }}'))
+ config_h_lines.append(generate_define(f'ENCODER_A_PINS{postfix}', f'{{ {", ".join(a_pads)} }}'))
+ config_h_lines.append(generate_define(f'ENCODER_B_PINS{postfix}', f'{{ {", ".join(b_pads)} }}'))
if None in resolutions:
cli.log.debug(f"Unable to generate ENCODER_RESOLUTION{postfix} configuration")
diff --git a/lib/python/qmk/cli/generate/keyboard_c.py b/lib/python/qmk/cli/generate/keyboard_c.py
index 5a6c967486..228b320942 100755
--- a/lib/python/qmk/cli/generate/keyboard_c.py
+++ b/lib/python/qmk/cli/generate/keyboard_c.py
@@ -6,7 +6,7 @@ from qmk.info import info_json
from qmk.commands import dump_lines
from qmk.keyboard import keyboard_completer, keyboard_folder
from qmk.path import normpath
-from qmk.constants import GPL2_HEADER_C_LIKE, GENERATED_HEADER_C_LIKE
+from qmk.constants import GPL2_HEADER_C_LIKE, GENERATED_HEADER_C_LIKE, JOYSTICK_AXES
def _gen_led_configs(info_data):
@@ -91,6 +91,41 @@ def _gen_matrix_mask(info_data):
return lines
+def _gen_joystick_axes(info_data):
+ """Convert info.json content to joystick_axes
+ """
+ if 'axes' not in info_data.get('joystick', {}):
+ return []
+
+ axes = info_data['joystick']['axes']
+ axes_keys = list(axes.keys())
+
+ lines = []
+ lines.append('#ifdef JOYSTICK_ENABLE')
+ lines.append('joystick_config_t joystick_axes[JOYSTICK_AXIS_COUNT] = {')
+
+ # loop over all available axes - injecting virtual axis for those not specified
+ for index, cur in enumerate(JOYSTICK_AXES):
+ # bail out if we have generated all requested axis
+ if len(axes_keys) == 0:
+ break
+
+ axis = 'virtual'
+ if cur in axes:
+ axis = axes[cur]
+ axes_keys.remove(cur)
+
+ if axis == 'virtual':
+ lines.append(f" [{index}] = JOYSTICK_AXIS_VIRTUAL,")
+ else:
+ lines.append(f" [{index}] = JOYSTICK_AXIS_IN({axis['input_pin']}, {axis['low']}, {axis['rest']}, {axis['high']}),")
+
+ lines.append('};')
+ lines.append('#endif')
+
+ return lines
+
+
@cli.argument('-o', '--output', arg_only=True, type=normpath, help='File to write to')
@cli.argument('-q', '--quiet', arg_only=True, action='store_true', help="Quiet mode, only output error messages")
@cli.argument('-kb', '--keyboard', arg_only=True, type=keyboard_folder, completer=keyboard_completer, required=True, help='Keyboard to generate keyboard.c for.')
@@ -105,6 +140,7 @@ def generate_keyboard_c(cli):
keyboard_h_lines.extend(_gen_led_configs(kb_info_json))
keyboard_h_lines.extend(_gen_matrix_mask(kb_info_json))
+ keyboard_h_lines.extend(_gen_joystick_axes(kb_info_json))
# Show the results
dump_lines(cli.args.output, keyboard_h_lines, cli.args.quiet)
diff --git a/lib/python/qmk/cli/generate/keymap_h.py b/lib/python/qmk/cli/generate/keymap_h.py
new file mode 100644
index 0000000000..a3aaa405c0
--- /dev/null
+++ b/lib/python/qmk/cli/generate/keymap_h.py
@@ -0,0 +1,51 @@
+from argcomplete.completers import FilesCompleter
+
+from milc import cli
+
+import qmk.path
+from qmk.commands import dump_lines
+from qmk.commands import parse_configurator_json
+from qmk.constants import GPL2_HEADER_C_LIKE, GENERATED_HEADER_C_LIKE
+
+
+def _generate_keycodes_function(keymap_json):
+ """Generates keymap level keycodes.
+ """
+ lines = []
+ lines.append('enum keymap_keycodes {')
+
+ for index, item in enumerate(keymap_json.get('keycodes', [])):
+ key = item["key"]
+ if index == 0:
+ lines.append(f' {key} = QK_USER_0,')
+ else:
+ lines.append(f' {key},')
+
+ lines.append('};')
+
+ for item in keymap_json.get('keycodes', []):
+ key = item["key"]
+ for alias in item.get("aliases", []):
+ lines.append(f'#define {alias} {key}')
+
+ return lines
+
+
[email protected]('-o', '--output', arg_only=True, type=qmk.path.normpath, help='File to write to')
[email protected]('-q', '--quiet', arg_only=True, action='store_true', help="Quiet mode, only output error messages")
[email protected]('filename', type=qmk.path.FileType('r'), arg_only=True, completer=FilesCompleter('.json'), help='Configurator JSON file')
[email protected]('Creates a keymap.h from a QMK Configurator export.')
+def generate_keymap_h(cli):
+ """Creates a keymap.h from a QMK Configurator export
+ """
+ if cli.args.output and cli.args.output.name == '-':
+ cli.args.output = None
+
+ keymap_h_lines = [GPL2_HEADER_C_LIKE, GENERATED_HEADER_C_LIKE, '#pragma once', '// clang-format off']
+
+ keymap_json = parse_configurator_json(cli.args.filename)
+
+ if 'keycodes' in keymap_json and keymap_json['keycodes'] is not None:
+ keymap_h_lines += _generate_keycodes_function(keymap_json)
+
+ dump_lines(cli.args.output, keymap_h_lines, cli.args.quiet)
diff --git a/lib/python/qmk/commands.py b/lib/python/qmk/commands.py
index 3db8353bfd..873380c28b 100644
--- a/lib/python/qmk/commands.py
+++ b/lib/python/qmk/commands.py
@@ -102,7 +102,9 @@ def dump_lines(output_file, lines, quiet=True):
output_file.parent.mkdir(parents=True, exist_ok=True)
if output_file.exists():
output_file.replace(output_file.parent / (output_file.name + '.bak'))
- output_file.write_text(generated, encoding='utf-8')
+ with open(output_file, 'w', encoding='utf-8', newline='\n') as f:
+ f.write(generated)
+ # output_file.write_text(generated, encoding='utf-8', newline='\n') # `newline` needs Python 3.10
if not quiet:
cli.log.info(f'Wrote {output_file.name} to {output_file}.')
diff --git a/lib/python/qmk/constants.py b/lib/python/qmk/constants.py
index 90e4452f2b..b6f46180b2 100644
--- a/lib/python/qmk/constants.py
+++ b/lib/python/qmk/constants.py
@@ -320,3 +320,5 @@ LICENSE_TEXTS = [
you may not use this file except in compliance with the License.
"""]),
]
+
+JOYSTICK_AXES = ['x', 'y', 'z', 'rx', 'ry', 'rz']
diff --git a/lib/python/qmk/info.py b/lib/python/qmk/info.py
index 833271c09c..5b3b249015 100644
--- a/lib/python/qmk/info.py
+++ b/lib/python/qmk/info.py
@@ -7,7 +7,7 @@ from dotty_dict import dotty
from milc import cli
-from qmk.constants import COL_LETTERS, ROW_LETTERS, CHIBIOS_PROCESSORS, LUFA_PROCESSORS, VUSB_PROCESSORS
+from qmk.constants import COL_LETTERS, ROW_LETTERS, CHIBIOS_PROCESSORS, LUFA_PROCESSORS, VUSB_PROCESSORS, JOYSTICK_AXES
from qmk.c_parse import find_layouts, parse_config_h_file, find_led_config
from qmk.json_schema import deep_update, json_load, validate
from qmk.keyboard import config_h, rules_mk
@@ -249,8 +249,9 @@ def info_json(keyboard):
info_data = _extract_rules_mk(info_data, rules_mk(str(keyboard)))
info_data = _extract_config_h(info_data, config_h(str(keyboard)))
- # Ensure that we have matrix row and column counts
+ # Ensure that we have various calculated values
info_data = _matrix_size(info_data)
+ info_data = _joystick_axis_count(info_data)
# Merge in data from <keyboard.c>
info_data = _extract_led_config(info_data, str(keyboard))
@@ -374,8 +375,8 @@ def _extract_audio(info_data, config_c):
def _extract_encoders_values(config_c, postfix=''):
"""Common encoder extraction logic
"""
- a_pad = config_c.get(f'ENCODERS_PAD_A{postfix}', '').replace(' ', '')[1:-1]
- b_pad = config_c.get(f'ENCODERS_PAD_B{postfix}', '').replace(' ', '')[1:-1]
+ a_pad = config_c.get(f'ENCODER_A_PINS{postfix}', '').replace(' ', '')[1:-1]
+ b_pad = config_c.get(f'ENCODER_B_PINS{postfix}', '').replace(' ', '')[1:-1]
resolutions = config_c.get(f'ENCODER_RESOLUTIONS{postfix}', '').replace(' ', '')[1:-1]
default_resolution = config_c.get('ENCODER_RESOLUTION', None)
@@ -800,6 +801,16 @@ def _matrix_size(info_data):
return info_data
+def _joystick_axis_count(info_data):
+ """Add info_data['joystick.axis_count'] if required
+ """
+ if 'axes' in info_data.get('joystick', {}):
+ axes_keys = info_data['joystick']['axes'].keys()
+ info_data['joystick']['axis_count'] = max(JOYSTICK_AXES.index(a) for a in axes_keys) + 1 if axes_keys else 0
+
+ return info_data
+
+
def _check_matrix(info_data):
"""Check the matrix to ensure that row/column count is consistent.
"""
diff --git a/lib/python/qmk/keymap.py b/lib/python/qmk/keymap.py
index b7bf897377..ca76f1b288 100644
--- a/lib/python/qmk/keymap.py
+++ b/lib/python/qmk/keymap.py
@@ -19,6 +19,9 @@ from qmk.info import info_json
# The `keymap.c` template to use when a keyboard doesn't have its own
DEFAULT_KEYMAP_C = """#include QMK_KEYBOARD_H
+#if __has_include("keymap.h")
+# include "keymap.h"
+#endif
__INCLUDES__
/* THIS FILE WAS GENERATED!
@@ -26,8 +29,6 @@ __INCLUDES__
* This file was generated by qmk json2c. You may or may not want to
* edit it directly.
*/
-__KEYCODE_OUTPUT_GOES_HERE__
-
const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
__KEYMAP_GOES_HERE__
};
@@ -125,29 +126,6 @@ def _generate_macros_function(keymap_json):
return macro_txt
-def _generate_keycodes_function(keymap_json):
- """Generates keymap level keycodes.
- """
- lines = []
- lines.append('enum keymap_keycodes {')
-
- for index, item in enumerate(keymap_json.get('keycodes', [])):
- key = item["key"]
- if index == 0:
- lines.append(f' {key} = QK_USER_0,')
- else:
- lines.append(f' {key},')
-
- lines.append('};')
-
- for item in keymap_json.get('keycodes', []):
- key = item["key"]
- for alias in item.get("aliases", []):
- lines.append(f'#define {alias} {key}')
-
- return lines
-
-
def template_json(keyboard):
"""Returns a `keymap.json` template for a keyboard.
@@ -350,12 +328,6 @@ def generate_c(keymap_json):
hostlang = f'#include "keymap_{keymap_json["host_language"]}.h"\n#include "sendstring_{keymap_json["host_language"]}.h"\n'
new_keymap = new_keymap.replace('__INCLUDES__', hostlang)
- keycodes = ''
- if 'keycodes' in keymap_json and keymap_json['keycodes'] is not None:
- keycodes_txt = _generate_keycodes_function(keymap_json)
- keycodes = '\n'.join(keycodes_txt)
- new_keymap = new_keymap.replace('__KEYCODE_OUTPUT_GOES_HERE__', keycodes)
-
return new_keymap