selector-engine.js 1.9 KB
Newer Older
Johann-S's avatar
Johann-S committed
1
2
/**
 * --------------------------------------------------------------------------
3
 * Bootstrap (v4.3.1): dom/selector-engine.js
Johann-S's avatar
Johann-S committed
4
5
6
7
 * Licensed under MIT (https://github.com/twbs/bootstrap/blob/master/LICENSE)
 * --------------------------------------------------------------------------
 */

Johann-S's avatar
Johann-S committed
8
import { find as findFn, findOne } from './polyfill'
9

10
11
12
13
14
/**
 * ------------------------------------------------------------------------
 * Constants
 * ------------------------------------------------------------------------
 */
Johann-S's avatar
Johann-S committed
15

16
const NODE_TEXT = 3
Johann-S's avatar
Johann-S committed
17

18
19
const SelectorEngine = {
  matches(element, selector) {
Johann-S's avatar
Johann-S committed
20
    return element.matches(selector)
21
  },
Johann-S's avatar
Johann-S committed
22

23
  find(selector, element = document.documentElement) {
24
    return [].concat(...findFn.call(element, selector))
25
26
27
28
29
  },

  findOne(selector, element = document.documentElement) {
    return findOne.call(element, selector)
  },
Johann-S's avatar
Johann-S committed
30

31
  children(element, selector) {
32
    const children = [].concat(...element.children)
33

34
    return children.filter(child => child.matches(selector))
35
  },
36

37
38
  parents(element, selector) {
    const parents = []
39

40
    let ancestor = element.parentNode
41
42

    while (ancestor && ancestor.nodeType === Node.ELEMENT_NODE && ancestor.nodeType !== NODE_TEXT) {
43
44
      if (this.matches(ancestor, selector)) {
        parents.push(ancestor)
45
46
      }

47
48
      ancestor = ancestor.parentNode
    }
49

50
51
    return parents
  },
52

53
  closest(element, selector) {
Johann-S's avatar
Johann-S committed
54
    return element.closest(selector)
55
  },
56

57
  prev(element, selector) {
58
    let previous = element.previousElementSibling
59

60
    while (previous) {
61
      if (previous.matches(selector)) {
62
        return [previous]
63
64
      }

65
      previous = previous.previousElementSibling
Johann-S's avatar
Johann-S committed
66
    }
67

68
69
70
71
72
73
74
75
76
77
78
79
80
81
    return []
  },

  next(element, selector) {
    let next = element.nextElementSibling

    while (next) {
      if (this.matches(next, selector)) {
        return [next]
      }

      next = next.nextElementSibling
    }

82
    return []
Johann-S's avatar
Johann-S committed
83
  }
84
}
Johann-S's avatar
Johann-S committed
85
86

export default SelectorEngine