1 package goquery
2
3 import "golang.org/x/net/html"
4
5
6
7 func (s *Selection) Filter(selector string) *Selection {
8 return s.FilterMatcher(compileMatcher(selector))
9 }
10
11
12
13
14 func (s *Selection) FilterMatcher(m Matcher) *Selection {
15 return pushStack(s, winnow(s, m, true))
16 }
17
18
19
20 func (s *Selection) Not(selector string) *Selection {
21 return s.NotMatcher(compileMatcher(selector))
22 }
23
24
25
26 func (s *Selection) NotMatcher(m Matcher) *Selection {
27 return pushStack(s, winnow(s, m, false))
28 }
29
30
31
32 func (s *Selection) FilterFunction(f func(int, *Selection) bool) *Selection {
33 return pushStack(s, winnowFunction(s, f, true))
34 }
35
36
37
38 func (s *Selection) NotFunction(f func(int, *Selection) bool) *Selection {
39 return pushStack(s, winnowFunction(s, f, false))
40 }
41
42
43
44 func (s *Selection) FilterNodes(nodes ...*html.Node) *Selection {
45 return pushStack(s, winnowNodes(s, nodes, true))
46 }
47
48
49
50 func (s *Selection) NotNodes(nodes ...*html.Node) *Selection {
51 return pushStack(s, winnowNodes(s, nodes, false))
52 }
53
54
55
56
57 func (s *Selection) FilterSelection(sel *Selection) *Selection {
58 if sel == nil {
59 return pushStack(s, winnowNodes(s, nil, true))
60 }
61 return pushStack(s, winnowNodes(s, sel.Nodes, true))
62 }
63
64
65
66 func (s *Selection) NotSelection(sel *Selection) *Selection {
67 if sel == nil {
68 return pushStack(s, winnowNodes(s, nil, false))
69 }
70 return pushStack(s, winnowNodes(s, sel.Nodes, false))
71 }
72
73
74 func (s *Selection) Intersection(sel *Selection) *Selection {
75 return s.FilterSelection(sel)
76 }
77
78
79
80
81 func (s *Selection) Has(selector string) *Selection {
82 return s.HasSelection(s.document.Find(selector))
83 }
84
85
86
87
88 func (s *Selection) HasMatcher(m Matcher) *Selection {
89 return s.HasSelection(s.document.FindMatcher(m))
90 }
91
92
93
94
95 func (s *Selection) HasNodes(nodes ...*html.Node) *Selection {
96 return s.FilterFunction(func(_ int, sel *Selection) bool {
97
98 for _, n := range nodes {
99 if sel.Contains(n) {
100 return true
101 }
102 }
103 return false
104 })
105 }
106
107
108
109
110 func (s *Selection) HasSelection(sel *Selection) *Selection {
111 if sel == nil {
112 return s.HasNodes()
113 }
114 return s.HasNodes(sel.Nodes...)
115 }
116
117
118
119 func (s *Selection) End() *Selection {
120 if s.prevSel != nil {
121 return s.prevSel
122 }
123 return newEmptySelection(s.document)
124 }
125
126
127
128 func winnow(sel *Selection, m Matcher, keep bool) []*html.Node {
129
130 if keep {
131 return m.Filter(sel.Nodes)
132 }
133
134 return grep(sel, func(i int, s *Selection) bool {
135 return !m.Match(s.Get(0))
136 })
137 }
138
139
140
141 func winnowNodes(sel *Selection, nodes []*html.Node, keep bool) []*html.Node {
142 if len(nodes)+len(sel.Nodes) < minNodesForSet {
143 return grep(sel, func(i int, s *Selection) bool {
144 return isInSlice(nodes, s.Get(0)) == keep
145 })
146 }
147
148 set := make(map[*html.Node]bool)
149 for _, n := range nodes {
150 set[n] = true
151 }
152 return grep(sel, func(i int, s *Selection) bool {
153 return set[s.Get(0)] == keep
154 })
155 }
156
157
158
159 func winnowFunction(sel *Selection, f func(int, *Selection) bool, keep bool) []*html.Node {
160 return grep(sel, func(i int, s *Selection) bool {
161 return f(i, s) == keep
162 })
163 }
164
View as plain text