any 3:2 multi-map group: any pairing of the 3 with the 2 is valid, one is shown
all 3:1 all-to-all group: each of the 3 corresponds to the 1
inserted
deleted
updated
moved
click a highlight to reveal its counterpart
Requires N:M mapping
This mapping has 1 all-to-all group: every node on one side corresponds to every node on the other, and none is deleted or inserted. Each member carries an all N:M badge; selecting one highlights all of its counterparts, in the tree and in the code view alike.
Code view:
A painting is a person's account of this edit as text, recorded independently of the node mapping - a rendering often has several equally defensible answers where the mapping has one. Deletions and insertions carry no position on the opposite side in a painting, so that panel draws no caret for them.
Before
1public class Circle {
2 private double radius;
3
4 public Circle(double radius) {
5 this.radius = radius;
6 }
7
8 public double area() {
9 return 3.14159 * radius * radius;
10 }
11
12 public double circumference() {
13 return 2 * 3.14159 * radius;
14 }
15}
16
After
1public class Circle {
2private static final double PI =3.14159;
3 private double radius;
4
5 public Circle(double radius) {
6 this.radius = radius;
7 }
8
9 public double area() {
10 return PI * radius * radius;
11 }
12
13 public double circumference() {
14 return 2 * PI * radius;
15 }
16}
17
Before
1public class Circle {
2 private double radius;
3
4 public Circle(double radius) {
5 this.radius = radius;
6 }
7
8 public double area() {
9 return 3.14159 * radius * radius;
10 }
11
12 public double circumference() {
13 return 2 * 3.14159 * radius;
14 }
15}
16
After
1public class Circle {
2private static final double PI =3.14159;
3 private double radius;
4
5 public Circle(double radius) {
6 this.radius = radius;
7 }
8
9 public double area() {
10 return PI * radius * radius;
11 }
12
13 public double circumference() {
14 return 2 * PI * radius;
15 }
16}
17
Before
1public class Circle {
2 private double radius;
3
4 public Circle(double radius) {
5 this.radius = radius;
6 }
7
8 public double area() {
9 return 3.14159 * radius * radius;
10 }
11
12 public double circumference() {
13 return 2 * 3.14159 * radius;
14 }
15}
16
After
1public class Circle {
2 private static final double PI = 3.14159;
3 private double radius;
4
5 public Circle(double radius) {
6 this.radius = radius;
7 }
8
9 public double area() {
10 return PI * radius * radius;
11 }
12
13 public double circumference() {
14 return 2 * PI * radius;
15 }
16}
17
Before
programclass_declarationmodifiers
public "public"
class "class"
identifier "Circle"
class_body
{ "{"
field_declarationmodifiers
private "private"
floating_point_type
double "double"
variable_declarator
identifier "radius"
; ";"
constructor_declaration (+23 nodes collapsed)
method_declarationmodifiers
public "public"
floating_point_type
double "double"
identifier "area"
formal_parameters
( "("
) ")"
block
{ "{"
return_statement
return "return"
binary_expressionbinary_expression
decimal_floating_point_literal "3.14159" all 2:1
* "*"
identifier "radius"
* "*"
identifier "radius"
; ";"
} "}"
method_declarationmodifiers
public "public"
floating_point_type
double "double"
identifier "circumference"
formal_parameters
( "("
) ")"
block
{ "{"
return_statement
return "return"
binary_expressionbinary_expression
decimal_integer_literal "2"
* "*"
decimal_floating_point_literal "3.14159" all 2:1
* "*"
identifier "radius"
; ";"
} "}"
} "}"
After
programclass_declarationmodifiers
public "public"
class "class"
identifier "Circle"
class_body
{ "{"
field_declarationmodifiers
private "private"
static "static"
final "final"
floating_point_type
double "double"
variable_declarator
identifier "PI"
= "="
decimal_floating_point_literal "3.14159" all 2:1
; ";"
field_declarationmodifiers
private "private"
floating_point_type
double "double"
variable_declarator
identifier "radius"
; ";"
constructor_declaration (+23 nodes collapsed)
method_declarationmodifiers
public "public"
floating_point_type
double "double"
identifier "area"
formal_parameters
( "("
) ")"
block
{ "{"
return_statement
return "return"
binary_expressionbinary_expression
identifier "PI"
* "*"
identifier "radius"
* "*"
identifier "radius"
; ";"
} "}"
method_declarationmodifiers
public "public"
floating_point_type
double "double"
identifier "circumference"
formal_parameters
( "("
) ")"
block
{ "{"
return_statement
return "return"
binary_expressionbinary_expression
decimal_integer_literal "2"
* "*"
identifier "PI"
* "*"
identifier "radius"
; ";"
} "}"
} "}"
Keybindings
j / k
next / previous visible node (tree panels)
h / l
collapse / expand the focused node
g / G
jump to first / last visible node
Tab
switch focus between Before/After panels
/
search: jump to next node whose text contains a given string
a
jump the other panel to this node's mapped counterpart
i
hide identical matches, showing only inserted/deleted/updated nodes and their ancestors
v
cycle the view: split / code only / tree only
p
cycle what the code view renders: the node mapping, then each human painting
r
mark this fixture as reviewed, or forget the mark (kept in this browser only)