Skip to content

ByteBard97/kicad-unshuffle

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

1 Commit
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

kicad-unshuffle

Visual diff, merge, and canonical ordering tools for KiCad


The Problem

Every time KiCad saves a .kicad_pcb or .kicad_sch file, it shuffles the internal element order (due to non-deterministic hash map iteration in KiCad's C++ code). This means:

  • Git diffs are useless — a single component move generates thousands of meaningless line changes
  • Merging is painful — two engineers editing different parts of the same board get massive conflicts
  • Code review is impossible — you can't tell what actually changed

There's an open KiCad bug for this since 2021 with no fix in sight.

What kicad-unshuffle Does

1. Normalize files for clean git diffs

Sort KiCad files into a canonical, deterministic order. Run before every commit — diffs become readable.

# Normalize files in-place
kicad-unshuffle *.kicad_pcb *.kicad_sch *.kicad_sym

# Check mode for CI (exits 1 if files would change)
kicad-unshuffle --check *.kicad_pcb

# Pipe mode for git filter-repo
kicad-unshuffle --stdin --stdout < board.kicad_pcb > sorted.kicad_pcb

2. Visual diff overlay (red/cyan)

See exactly what changed between two versions of a schematic. Identical elements appear white, changes appear in red (version A) and cyan (version B). Pure Rust SVG renderer — no KiCad installation required.

# Render a schematic to SVG
kicad-unshuffle render-svg board.kicad_sch -o board.svg

# Red/cyan diff overlay
kicad-unshuffle diff-svg version_a.kicad_sch version_b.kicad_sch -o diff.svg

3. Desktop app for visual merge resolution

A Tauri desktop app that lets you open a git repo, pick two branches or commits, and visually review every changed KiCad file.

Features:

  • Git repository browser — open a repo, pick two branches/commits, filter by hash or message
  • Side-by-side view — KiCanvas renders both versions with click-to-zoom on any element
  • SVG overlay — red/cyan diff rendered in pure Rust (vector, infinite zoom, no lag)
  • Text diff — syntax-highlighted S-expression diff showing exactly which properties changed
  • Clickable element list — every modified symbol, wire, label listed with click-to-navigate

4. Semantic diff & merge engine

Compare and merge KiCad files at the element level — matching by UUID, not by line number.

# Compare two branches — shows which KiCad files differ
kicad-unshuffle repo-merge --repo /path/to/project main feature-branch

# Git merge driver (register in .gitattributes)
kicad-unshuffle merge-driver %O %A %B

Supported File Types

File Type Extension Normalize Diff/Merge SVG Render
PCB Layout .kicad_pcb Planned
Schematic .kicad_sch
Symbol Library .kicad_sym
Footprint Library .kicad_mod
Project File .kicad_pro
Design Rules .kicad_dru

Installation

From Source

# CLI tool only
cargo install --path crates/cli

# Desktop app (requires Node.js for the Vue frontend)
cd ui
npm install
cargo tauri build

Requirements

  • Rust 1.77+
  • Node.js 18+ (for the desktop app only)
  • KiCad is NOT required — the tool parses and renders files directly

Performance

Tested on real-world hardware projects (32-34MB PCB files, 18 hierarchical schematic sheets):

Operation File Size Time
Normalize PCB 32 MB 0.83s
Normalize PCB 34 MB 0.91s
Merge PCB (33MB × 3 versions) 99 MB total 2.6s
SVG render schematic 72 KB instant
SVG diff overlay 72 + 131 KB instant

All operations are idempotent — running twice produces byte-identical output.

How It Works

Normalization

Parses KiCad's S-expression format, sorts elements using configurable deterministic keys (coordinates for PCBs, reference designators for schematics), and writes back in KiCad-compatible format. The sort strategy is configurable via TOML — choose coordinate-based sorting for merge-friendly PCB diffs, or refdes-based sorting for readable schematic diffs.

Merge Engine

Matches elements across versions by UUID. Classifies each as unchanged, added, deleted, modified, or conflicting. Non-overlapping changes are auto-resolved. Real conflicts (both versions modified the same element differently) are flagged for manual resolution in the desktop app.

SVG Renderer

Pure Rust renderer using the svg crate. Converts .kicad_sch S-expressions directly to SVG: wires, junctions, labels, symbols (with full lib_symbol rendering — rectangles, polylines, circles, arcs, pins), hierarchical sheets, bus entries, and text with alignment. For diff overlay, version A renders in red, version B in cyan, composited with mix-blend-mode: screen — identical geometry cancels to white.

Git Integration

Native git access via the git2 crate — reads files directly from any commit without checkout. The repo-merge command finds the merge base, extracts all three versions of each changed KiCad file, normalizes them, and runs the semantic diff.

Architecture

kicad-unshuffle/
├── crates/
│   ├── core/              # Rust library (zero UI dependencies)
│   │   ├── sexpr/         # S-expression parser and writer
│   │   ├── sort/          # Configurable canonical sort engine
│   │   ├── merge/         # Semantic diff and merge (identity, diff, resolver)
│   │   ├── render/        # SVG renderer (schematic → SVG with tint)
│   │   └── repo/          # Git repository operations (via git2)
│   └── cli/               # Command-line interface
├── ui/
│   ├── src/               # Vue 3 + TypeScript frontend
│   ├── src-tauri/         # Tauri 2 Rust backend
│   └── public/            # KiCanvas bundle for interactive rendering
└── kicanvas-fork/         # Modified KiCanvas with tint shader support

Contributing

This tool was built to solve a real collaboration problem on a hardware project. If you're working with KiCad and git, we'd love feedback and contributions.

License

MIT

About

Visual diff, merge, and canonical ordering tools for KiCad. Normalizes .kicad_pcb and .kicad_sch files for clean git diffs. Red/cyan SVG overlay renderer shows exactly what changed between versions. Tauri desktop app with side-by-side KiCanvas views, clickable element diffs, and semantic merge engine.

Resources

License

Stars

Watchers

Forks

Releases

No releases published

Packages

 
 
 

Contributors