Module: Ayril::XMLNode::NodeTraversal

Included in:
Ayril::XMLDocument, Ayril::XMLElement, Ayril::XMLNode
Defined in:
lib/ayril/xml_node/node_traversal.rb

Instance Method Summary collapse

Instance Method Details

#adjacent(*args) ⇒ Object



137
138
139
# File 'lib/ayril/xml_node/node_traversal.rb', line 137

def adjacent(*args)
  Selector.find_child_elements(self.parent, args) - [self]
end

#ancestorsObject

Returns all ancestors of a node.



34
35
36
# File 'lib/ayril/xml_node/node_traversal.rb', line 34

def ancestors
  self.recursively_collect :parent
end

#at(css) ⇒ Object Also known as: %



127
128
129
# File 'lib/ayril/xml_node/node_traversal.rb', line 127

def at(css)
  self.select(css)[0]
end

#contains?(child) ⇒ Boolean

Returns:

  • (Boolean)


153
154
155
# File 'lib/ayril/xml_node/node_traversal.rb', line 153

def contains?(child)
  child.descendant_of? self
end

#descendant_of?(ancestor) ⇒ Boolean

Returns:

  • (Boolean)


145
146
147
148
149
150
151
# File 'lib/ayril/xml_node/node_traversal.rb', line 145

def descendant_of?(ancestor)
  element = self
  while element = element.parent
    return true if element == ancestor
  end
  false
end

#descendantsObject

Returns all descendants of a node, direct or indirect.



39
40
41
# File 'lib/ayril/xml_node/node_traversal.rb', line 39

def descendants
  self.select "*"
end

#down(*args) ⇒ Object Also known as: find, search



98
99
100
101
102
103
# File 'lib/ayril/xml_node/node_traversal.rb', line 98

def down(*args)
  expr, index = args[0..1]
  return self.first_descendant if args.length == 0
  if expr.kind_of? Integer then self.descendants[expr]
  else self.select(expr)[index || 0] end
end

#empty?Boolean

Returns:

  • (Boolean)


141
142
143
# File 'lib/ayril/xml_node/node_traversal.rb', line 141

def empty?
  self.descendants.invoke(:XMLString).join('') == ''
end

#first_descendantObject

Returns the first descendant element of a node.



44
45
46
47
48
49
50
# File 'lib/ayril/xml_node/node_traversal.rb', line 44

def first_descendant
  element = self.childAtIndex 0
  while element and element.kind != NSXMLElementKind
    element = element.nextSibling
  end
  element
end

#immediate_descendantsObject Also known as: child_elements

Returns the direct children of a node.



53
54
55
56
57
58
59
60
# File 'lib/ayril/xml_node/node_traversal.rb', line 53

def immediate_descendants
  return [] unless (element = self.childAtIndex 0)
  while element and element.kind != NSXMLElementKind
    element = element.nextSibling
  end
  return [element] + element.next_siblings unless element.nil?
  []
end

#next(*args) ⇒ Object



114
115
116
117
118
119
# File 'lib/ayril/xml_node/node_traversal.rb', line 114

def next(*args)
  expr, index = args[0..1]
  return self.next_element_sibling if args.length == 0
  expr.kind_of?(Integer) ? self.next_siblings[expr] :
    Selector::find_element(self.next_siblings, expr, index)
end

#next_element_siblingObject



79
80
81
82
83
84
85
# File 'lib/ayril/xml_node/node_traversal.rb', line 79

def next_element_sibling
  element = self.nextSibling
  while element and element.kind != NSXMLElementKind
    element = element.nextSibling
  end
  element
end

#next_siblingsObject



75
76
77
# File 'lib/ayril/xml_node/node_traversal.rb', line 75

def next_siblings
  self.recursively_collect :nextSibling
end

#previous(*args) ⇒ Object



107
108
109
110
111
112
# File 'lib/ayril/xml_node/node_traversal.rb', line 107

def previous(*args)
  expr, index = args[0..1]
  return self.previous_element_sibling if args.length == 0
  expr.kind_of?(Integer) ? self.previous_siblings[expr] : 
    Selector::find_element(self.previous_siblings, expr, index)
end

#previous_element_siblingObject



67
68
69
70
71
72
73
# File 'lib/ayril/xml_node/node_traversal.rb', line 67

def previous_element_sibling
  element = self.previousSibling
  while element and element.kind != NSXMLElementKind
    element = element.previousSibling
  end
  element
end

#previous_siblingsObject



63
64
65
# File 'lib/ayril/xml_node/node_traversal.rb', line 63

def previous_siblings
  self.recursively_collect :previousSibling
end

#recursively_collect(property) ⇒ Object

Recursively collects the results of a method until nil is returned.



25
26
27
28
29
30
31
# File 'lib/ayril/xml_node/node_traversal.rb', line 25

def recursively_collect(property)
  elements = []; element = self
  while element = element.send(property)
    elements << element if element.kind == NSXMLElementKind
  end
  elements
end

#select(css) ⇒ Object Also known as: elements_by_selector, []



121
122
123
# File 'lib/ayril/xml_node/node_traversal.rb', line 121

def select(css)
  self.select_by_xpath(Selector.new(css.to_s).xpath).to_a
end

#select_by_xpath(xpath) ⇒ Object Also known as: /



132
133
134
# File 'lib/ayril/xml_node/node_traversal.rb', line 132

def select_by_xpath(xpath)
  self.nodesForXPath(xpath.to_s, error: nil).to_a
end

#siblingsObject



87
88
89
# File 'lib/ayril/xml_node/node_traversal.rb', line 87

def siblings
  self.previous_siblings.reverse + self.next_siblings
end

#up(*args) ⇒ Object



91
92
93
94
95
96
# File 'lib/ayril/xml_node/node_traversal.rb', line 91

def up(*args)
  expr, index = args[0..1]
  return self.parent if args.length == 0
  if expr.kind_of? Integer then self.ancestors[expr]
  else Selector.find_element(self.ancestors, expr, index) end
end