Skip to main content

ZMK keyboard layout manipulation library with fluent API

Project description

ZMK Layout Library

A standalone Python library for manipulating ZMK keyboard layouts with a modern fluent API. Extracted from the glovebox project to enable ecosystem growth while maintaining full backward compatibility.

Project Status

Work in progress

Features

  • Fluent API: Intuitive, chainable interface for layout operations
  • Type Safety: Comprehensive type hints with mypy strict mode support
  • Provider Pattern: Clean abstraction allows integration with any keyboard framework
  • Optional Dependencies: Core functionality with optional templating, display, and parsing features
  • High Performance: <1 second for all operations, minimal memory footprint
  • Comprehensive: Full ZMK layout support including behaviors, combos, macros, and more
  • Round-trip Support: Parse → Modify → Save with perfect fidelity

Quick Start

from zmk_layout import Layout

# Load and modify a layout
layout = Layout("keyboard.keymap")
layout.layers.add("gaming")
layout.layers.get("gaming").set(0, "&kp W").set(1, "&kp A").set(2, "&kp S").set(3, "&kp D")
layout.save("modified.keymap")

# Fluent interface for complex operations
(layout.layers
    .add("nav")
    .get("nav")
    .set_range(0, 4, ["&kp UP", "&kp DOWN", "&kp LEFT", "&kp RIGHT"])
    .copy_from("default"))

# Add behaviors
layout.behaviors.add_hold_tap("ht_balanced", tap="&kp A", hold="&kp LCTRL")
layout.behaviors.add_combo("copy", keys=[0, 1], binding="&kp LC(C)")
layout.behaviors.add_macro("hello", sequence=["&kp H", "&kp E", "&kp L", "&kp L", "&kp O"])

Installation

From PyPI (Coming Soon)

# Core library
pip install zmk-layout

# With all optional features
pip install zmk-layout[full]

# Specific feature sets
pip install zmk-layout[templating]  # Jinja2 template support
pip install zmk-layout[display]     # Rich display formatting
pip install zmk-layout[parsing]     # Lark parser for devicetree files

Development Installation

# Clone the repository
git clone https://github.com/CaddyGlow/zmk-layout.git
cd zmk-layout

# Install with development dependencies using uv
uv sync --all-extras --dev

# Or use make
make install

# Run all checks (ruff, mypy, tests)
make check

# Auto-fix and format code
make fix

# Run tests only
make test

# Build packages
make build

# Clean build artifacts
make clean

API Examples

Basic Layout Operations

from zmk_layout import Layout

# Create empty layout
layout = Layout.create_empty(size=36)

# Load from file
layout = Layout.from_keymap("keyboard.keymap")
layout = Layout.from_json("layout.json")

# Layer management
layout.layers.add("symbols", position=1)
layout.layers.remove("gaming")
layout.layers.move("nav", position=0)
layout.layers.reorder(["default", "nav", "symbols"])

# Query layers
gaming_layers = layout.find_layers(lambda name: "gaming" in name)
all_layers = layout.layers.list()

Advanced Features

# Context manager with auto-save
with Layout("keyboard.keymap") as layout:
    layout.layers.add("test")
    # Automatically saves on exit

# Batch operations
layout.batch_operation([
    lambda l: l.layers.add("layer1"),
    lambda l: l.layers.add("layer2"),
    lambda l: l.behaviors.add_macro("test", ["&kp T"])
])

# Statistics and analysis
stats = layout.get_statistics()
print(f"Layers: {stats['layer_count']}")
print(f"Behaviors: {stats['behavior_count']}")

# Validation
layout.validate()  # Raises exception if invalid

Provider Pattern

from zmk_layout import Layout
from zmk_layout.providers import LayoutProviders

# Custom provider implementation
class MyConfigProvider:
    def get_behavior_definitions(self):
        return [...]

    def get_validation_rules(self):
        return {...}

# Use custom providers
providers = LayoutProviders(
    configuration=MyConfigProvider(),
    template=MyTemplateProvider(),
    logger=MyLogger(),
    file=MyFileAdapter()
)

layout = Layout("keyboard.keymap", providers=providers)

Architecture

The library uses a clean, modular architecture:

zmk_layout/
├── core/           # Core layout classes and fluent API
├── models/         # Pydantic models for layout data
├── parsers/        # Keymap and devicetree parsing
├── generators/     # ZMK code generation
├── providers/      # Provider interfaces for external dependencies
└── utils/          # Utilities and helpers

Key Design Patterns

  • Provider Pattern: Abstracts external dependencies for maximum flexibility
  • Fluent Interface: Chainable methods for intuitive API usage
  • Strategy Pattern: Pluggable parsing and generation strategies
  • Factory Pattern: Consistent object creation throughout

Testing

Comprehensive test coverage with 200+ tests:

# Run all tests with coverage
make test

# Run all checks (ruff, mypy, tests)
make check

# Run specific test categories
pytest tests/core/ -v        # Core functionality tests
pytest tests/fluent/ -v      # Fluent API tests
pytest tests/parsers/ -v     # Parser tests
pytest tests/models/ -v      # Model tests

Performance

All operations complete in <1 second with minimal memory footprint:

  • Layout loading: ~50ms
  • Layer operations: <1ms each
  • Full compilation: ~100ms
  • Memory usage: <10MB for typical layouts

Contributing

We welcome contributions! Please see our Contributing Guidelines for details.

Development Workflow

  1. Fork the repository
  2. Create a feature branch (git checkout -b feature/amazing-feature)
  3. Make your changes with tests
  4. Ensure quality gates pass:
    make fix    # Auto-fix and format code
    make check  # Run all checks (must pass)
    
  5. Commit your changes (git commit -m 'feat: add amazing feature')
  6. Push to your fork (git push origin feature/amazing-feature)
  7. Open a Pull Request

Code Style

  • We use ruff for formatting and linting
  • Type hints are required (mypy strict mode)
  • Tests are required for new features
  • Documentation updates for API changes

License

MIT License - see LICENSE file for details.

Acknowledgments

  • Extracted from the glovebox project
  • Built for the ZMK firmware ecosystem
  • Inspired by modern Python library design patterns

Links


Note: This library is in active development.

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

zmk_layout-0.0.2.tar.gz (299.7 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

zmk_layout-0.0.2-py3-none-any.whl (153.0 kB view details)

Uploaded Python 3

File details

Details for the file zmk_layout-0.0.2.tar.gz.

File metadata

  • Download URL: zmk_layout-0.0.2.tar.gz
  • Upload date:
  • Size: 299.7 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/6.1.0 CPython/3.12.9

File hashes

Hashes for zmk_layout-0.0.2.tar.gz
Algorithm Hash digest
SHA256 bde4b56ba7c1ab4a9dbeb8a509eb1908178ba85488dabc267872ebcbf9d3f880
MD5 a1afd6196ca1729d5154e3273be935f7
BLAKE2b-256 6da4c924ad2a630730d8ddf19078b89d0a71e539e3c861189a526856c8b0dda5

See more details on using hashes here.

Provenance

The following attestation bundles were made for zmk_layout-0.0.2.tar.gz:

Publisher: publish.yml on CaddyGlow/zmk-layout

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file zmk_layout-0.0.2-py3-none-any.whl.

File metadata

  • Download URL: zmk_layout-0.0.2-py3-none-any.whl
  • Upload date:
  • Size: 153.0 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/6.1.0 CPython/3.12.9

File hashes

Hashes for zmk_layout-0.0.2-py3-none-any.whl
Algorithm Hash digest
SHA256 1ab3199483c03c5c10e17e2403bd03c2b343d73f6eb19bdb102a94c06415fc5a
MD5 8be76f418cc2e940401f7ccdaa146918
BLAKE2b-256 4bcf39eeffa5dccb2f1ad247df8ee51f3dde7872c0825d1a8b1fb51223e28b02

See more details on using hashes here.

Provenance

The following attestation bundles were made for zmk_layout-0.0.2-py3-none-any.whl:

Publisher: publish.yml on CaddyGlow/zmk-layout

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page