Workspace
Diff viewer
Two sources compared, tinted by change
@@ -1,8 +1,9 @@
11import { clamp } from "./math";
22
-3/** A cart's order total, before tax. */
+3/** A cart's order total, with tax. */
-4export function total(items) {
+4export function total(items, tax) {
-5 return items.reduce((sum, item) => sum + item.price, 0);
+5 const base = items.reduce((sum, item) => sum + item.price, 0);
+6 return base + tax;
67}
78
89/** A line total, rounded to cents. */
@@ -14,7 +15,7 @@
1415export function discounted(items, rate) {
1516 return items.map((item) => ({
1617 ...item,
-17 price: item.price * (1 - rate)
+18 price: clamp(item.price * (1 - rate), 0, item.price)
1819 }));
1920}
2021
Usage
import { DiffViewer } from "@gpuixui/editor";
<DiffViewer before={before} after={after} mode="unified" />;API
| Prop | Type | Default | Notes |
|---|---|---|---|
before | string | — | The before source. |
after | string | — | The after source. |
mode | "unified" | "split" | "unified" | One merged column, or two. A stored name that is neither reads as the default. |
contextLines | number | 3 | Unchanged rows kept either side of a change before the diff skips to a hunk heading. A negative or non-numeric value reads as the default. |
lineNumbers | boolean | true | Number the rows on both sides. |
wordDiff | boolean | true | In split mode, mark the words that changed inside a paired line. |
ink | "tone" | "code" | "tone" | code keeps the text neutral and shows the change with the tint and a bar. |
annotations | ReadonlyArray<{ line, height, content }> | [] | A review note under an after-side line; the before side keeps a spacer, so rows stay level. |
wrapColumns | number | — | In split mode, wrap at this many characters and grow both cells of the row together. |
language | string | — | With ink="code", colour the code by syntax, and break wrapped lines after a space or punctuation. |
firstLine | { before?, after? } | 1 | The line number each side's numbering starts from, for an excerpt of a longer file. |
label | string | "Diff" | The accessible name; a blank or non-text name reads as the default (the rows are presentational, so this is the whole surface's name). |
className | string | — | A Tailwind class string, merged last. |
style | StateStyle<DiffViewerState> | — | The surface, or a function of { changed }. |
testId | string | "diff-viewer" | The address an automation host locates the diff by. A unified line appends -row-<index>; a split line appends -row-<index>-before and -row-<index>-after; a hunk heading appends -hunk-<index>. |
The row model
The viewer paints data, not decisions. diff/logic exports the whole script:
hunks(numbered, context)groups the numbered script into hunks, keepscontextunchanged rows either side of a change, and names the lines a skip dropped (@@ -beforeStart,count +afterStart,count @@). Two changes within2·contextrows share a hunk, so their context windows abut and no change is shown twice.rows(numbered, context)is the unified sequence: a hunk heading, then each changed pair with the removal and the addition it became adjacent, then every context row once.pairs(numbered, context)is the split sequence: the same hunks zipped across the divider, with a blank cell on the side that ran out. A heading pairs with nothing on the right, so a split viewer paints it once across both columns.
Split mode
mode="split" puts a changed line and its replacement on one row: the two
equal columns share a row height, so a pair sits level across the divider. Each
column carries its own line-number gutter and its own horizontal scroller; a
long line scrolls inside the column it belongs to instead of pushing or clipping
its neighbour. A one-line edit is therefore one row with the old line on the
left and the new one on the right, not a removal and an addition stacked apart.
Edit this page on GitHubpackages/editor/docs/diff-viewer.mdx