mirror of
https://gerrit.wikimedia.org/r/mediawiki/extensions/VisualEditor
synced 2024-09-25 11:16:51 +00:00
Introduce es.DocumentNode.getCommonAncestorPaths(), with tests
This commit is contained in:
parent
6c36ddcbce
commit
6f3c407314
|
@ -69,6 +69,40 @@ es.DocumentNode.traverseUpstream = function( node, callback ) {
|
|||
}
|
||||
};
|
||||
|
||||
/**
|
||||
* Find the common ancestor of two equal-depth nodes, and return the
|
||||
* path from each node to the common ancestor.
|
||||
* @param {es.DocumentNode} node1
|
||||
* @param {es.DocumentNode} node2
|
||||
* @returns {Object|Boolean} Object with keys 'commonAncestor', 'node1Path' and 'node2Path',
|
||||
* or false if there is no common ancestor or if the nodes have unequal depth
|
||||
*/
|
||||
es.DocumentNode.getCommonAncestorPaths = function( node1, node2 ) {
|
||||
var path1 = [],
|
||||
path2 = [],
|
||||
n1 = node1,
|
||||
n2 = node2;
|
||||
|
||||
// Move up from n1 and n2 simultaneously until we find the
|
||||
// common ancestor
|
||||
while ( n1 !== n2 ) {
|
||||
// Add these nodes to their respective paths
|
||||
path1.push( n1 );
|
||||
path2.push( n2 );
|
||||
// Move up
|
||||
n1 = n1.getParent();
|
||||
n2 = n2.getParent();
|
||||
if ( n1 === null || n2 === null ) {
|
||||
// Reached a root, so no common ancestor or unequal depth
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
// If we got here, we've found the common ancestor, and because we did
|
||||
// simultaneous traversal we also know node1 and node2 have the same depth.
|
||||
return { 'commonAncestor': n1, 'node1Path': path1, 'node2Path': path2 };
|
||||
};
|
||||
|
||||
/* Inheritance */
|
||||
|
||||
es.extendClass( es.DocumentNode, es.EventEmitter );
|
||||
|
|
46
tests/es/es.DocumentNode.test.js
Normal file
46
tests/es/es.DocumentNode.test.js
Normal file
|
@ -0,0 +1,46 @@
|
|||
module( 'es/bases' );
|
||||
|
||||
test( 'es.DocumentNode.getCommonAncestorPaths', 14, function() {
|
||||
var documentModel = es.DocumentModel.newFromPlainObject( esTest.obj ), result;
|
||||
|
||||
var list = documentModel.children[1].children[0].children[0].children[1];
|
||||
result = es.DocumentNode.getCommonAncestorPaths( list, list );
|
||||
// Test 1
|
||||
ok( result.commonAncestor == list, 'same nodes (commonAncestor)' );
|
||||
// Test 2
|
||||
ok( es.compareArrays( result.node1Path, [] ), 'adjacent list items (node1Path)' );
|
||||
// Test 3
|
||||
ok( es.compareArrays( result.node2Path, [] ), 'adjacent list items (node2Path)' );
|
||||
|
||||
result = es.DocumentNode.getCommonAncestorPaths( list.children[0], list.children[1] );
|
||||
// Test 4
|
||||
ok( result.commonAncestor == list, 'adjacent list items (commonAncestor)' );
|
||||
// Test 5
|
||||
ok( es.compareArrays( result.node1Path, [ list.children[0] ] ), 'adjacent list items (node1Path)' );
|
||||
// Test 6
|
||||
ok( es.compareArrays( result.node2Path, [ list.children[1] ] ), 'adjacent list items (node2Path)' );
|
||||
|
||||
result = es.DocumentNode.getCommonAncestorPaths( list.children[0], list.children[2] );
|
||||
// Test 7
|
||||
ok( result.commonAncestor == list, 'non-adjacent sibling list items (commonAncestor)' );
|
||||
// Test 8
|
||||
ok( es.compareArrays( result.node1Path, [ list.children[0] ] ), 'non-adjacent sibling list items (node1Path)' );
|
||||
// Test 9
|
||||
ok( es.compareArrays( result.node2Path, [ list.children[2] ] ), 'non-adjacent sibling list items (node2Path)' );
|
||||
|
||||
result = es.DocumentNode.getCommonAncestorPaths( list.children[0].children[0], list.children[2].children[0] );
|
||||
// Test 10
|
||||
ok( result.commonAncestor == list, 'paragraphs inside list items (commonAncestor)' );
|
||||
// Test 11
|
||||
ok( es.compareArrays( result.node1Path, [ list.children[0].children[0], list.children[0] ] ), 'paragraphs inside list items (node1Path)' );
|
||||
// Test 12
|
||||
ok( es.compareArrays( result.node2Path, [ list.children[2].children[0], list.children[2] ] ), 'paragraphs inside list items (node2Path)' );
|
||||
|
||||
result = es.DocumentNode.getCommonAncestorPaths( list.children[0].children[0], list.children[2] );
|
||||
// Test 13
|
||||
equal( result, false, 'nodes of unequal depth' );
|
||||
|
||||
result = es.DocumentNode.getCommonAncestorPaths( list, es.DocumentModel.newFromPlainObject( esTest.obj ).children[1] );
|
||||
// Test 14
|
||||
equal( result, false, 'nodes in different trees' );
|
||||
} );
|
|
@ -46,5 +46,6 @@
|
|||
<script src="es.DocumentBranchNode.test.js"></script>
|
||||
<script src="es.DocumentModelBranchNode.test.js"></script>
|
||||
<script src="es.DocumentModel.test.js"></script>
|
||||
<script src="es.DocumentNode.test.js"></script>
|
||||
</body>
|
||||
</html>
|
||||
|
|
Loading…
Reference in a new issue