feat: intra-line word-diff highlighting (experimental)#73
feat: intra-line word-diff highlighting (experimental)#73rashpile wants to merge 2 commits intoumputun:masterfrom
Conversation
f46dd33 to
fbddf6d
Compare
|
this looks promising. answering your open questions: worth shipping? the key question is whether it inflates the codebase significantly or adds a lot of ongoing maintenance surface. from what I see the footprint is contained - one new file, reuse of pairing heuristic and threshold the 30% similarity gate is reasonable. I looked at how others solve this:
your greedy matching for unequal runs goes beyond what diff-highlight does, which is fine - just something to watch for false positives. the color themes the hardcoded hex defaults work for bundled themes, but we need a fallback for people who already have custom colors/themes set and won't have these two new keys defined. the word-diff bg should be derived automatically from the existing add/remove bg colors (e.g. lighten the bg by a fixed amount) so it works out of the box. the explicit computational overhead negligible. let's keep iterating on this. the color derivation for custom themes is the main thing I'd want addressed before merging. thx |
Add optional GitHub-style word-level highlighting for paired remove/add lines. Pairs lines within a hunk, runs a token-level diff via sergi/go-diff, and overlays a brighter background on the changed ranges while preserving the existing whole-line add/remove styling. - new W keybind and --word-diff CLI flag (off by default) - two new theme color keys: color-word-add-bg, color-word-remove-bg - 30% similarity threshold suppresses spurious highlights on lines that share only incidental characters - works alongside wrap, search, blame, line-numbers, collapsed modes - --no-colors fallback uses reverse-video markers - status bar icon when active
Remove hardcoded default word-diff colors. When color-word-add-bg or color-word-remove-bg is unset, derive it at runtime by shifting the lightness of the corresponding add-bg/remove-bg by 15% (dark gets lighter, light gets darker). This ensures word-diff works out of the box for custom themes that don't define the two new color keys. Bundled themes ship pre-computed values (via ShiftLightness) so --dump-theme and --dump-config include them. Explicit overrides in config/CLI/theme still take precedence. - add app/ui/colorutil.go with ShiftLightness and HSL utilities - add app/ui/colorutil_test.go with roundtrip and known-value tests - update bundled theme gallery with derived word-diff colors
dcd937f to
f5a2e4f
Compare
Word-Diff Implementation AI Comparison: PR #73 vs PR #74Comparison Table
Pros & ConsPR #73 (rashpile)Pros:
Cons:
PR #74 (daulet)Pros:
Cons:
Verdict: Best of BothThe ideal implementation combines PR #74's algorithm with PR #73's integration work:
This would give #74's clean algorithm in a single ~270 LOC file with no deps, wrapped in #73's production-ready UX (toggle, colors, themes, config, docs). Net result: drop the 1,360 LOC vendor dependency while keeping all the user-facing polish. |
|
thx for this, and especially for the detailed comparison analysis you posted — it made the path forward obvious. merged a combined version in #87 that takes the key ideas from this PR:
paired with @daulet's zero-dependency token-level algorithm from #74 (regex tokenizer + LCS) so we avoided the the final version is always-on (no toggle flag, no W keybinding, no status icon) to keep the surface minimal. closing this one as its ideas shipped in #87. |





Summary
Adds optional GitHub-style intra-line highlighting for paired remove/add lines. Within a hunk, paired
-/+lines run through a token-level diff and only the actually changed spans get a brighter background overlay — the existing whole-line add/remove styling is preserved.Off by default. Toggle with
Wor start with--word-diff.Why
When a line is edited rather than wholly added/removed, the user has to eyeball which tokens changed. This is especially painful in dense refactors and indentation-only changes. Word-level highlights make the actual edit pop.
What's in
app/ui/worddiff.go— pairing, range computation, ANSI insertion helper, andhighlightIntraLineChangesoverlaybuildModifiedSetintopairHunkLines(app/ui/collapsed.go); equal runs zip 1:1, uneven runs match by2*commonPrefix + 2*commonSuffixsimilaritygithub.com/sergi/go-diff/diffmatchpatchwithDiffCleanupSemanticcolor-word-add-bg,color-word-remove-bg(defaults#4a7a1a/#a03838); wired into all 5 bundled themes--word-diffCLI flag andWkeybinding (ActionToggleWordDiff)--no-colorsfallback uses reverse-video markers, matching the search-highlight fallbackextendLineBgand survivesansi.Wrapautomatically)Open questions for review
I can see this helping reviewers quickly spot what changed inside a line, but I'd land it as experimental because:
diffmatchpatch.DiffMainon every paired line)