forked from ngryman/tree-crawl
-
Notifications
You must be signed in to change notification settings - Fork 0
/
index.js
58 lines (51 loc) · 1.55 KB
/
index.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
import dfsPre from './lib/dfs-pre'
import dfsPost from './lib/dfs-post'
import bfs from './lib/bfs'
/**
* Walk options.
*
* @typedef {Object} Options
* @property {Function} [getChildren] Return a node's children.
* @property {'pre'|'post'|'bfs'} [order=pre] Order of the walk either in DFS pre or post order, or
* BFS.
*
* @example <caption>Traverse a DOM tree.</caption>
* crawl(document.body, doSomeStuff, { getChildren: node => node.childNodes })
*
* @example <caption>BFS traversal</caption>
* crawl(root, doSomeStuff, { order: 'bfs' })
*/
/**
* Called on each node of the tree.
* @callback Iteratee
* @param {Object} node Node being visited.
* @param {Context} context Traversal context
* @see [Traversal context](#traversal-context).
*/
const defaultGetChildren = (node) => node.children
/**
* Walk a tree recursively.
*
* By default `getChildren` will return the `children` property of a node.
*
* @param {Object} root Root node of the tree to be walked.
* @param {Iteratee} iteratee Function invoked on each node.
* @param {Options} [options] Options customizing the walk.
*/
export default function crawl(root, iteratee, options) {
if (null == root) return
options = options || {}
// default options
const order = options.order || 'pre'
const getChildren = options.getChildren || defaultGetChildren
// walk the tree!
if ('pre' === order) {
dfsPre(root, iteratee, getChildren)
}
else if ('post' === order) {
dfsPost(root, iteratee, getChildren)
}
else if ('bfs' === order) {
bfs(root, iteratee, getChildren)
}
}