77
88#include " skia/platform_view_rtree.h"
99
10- SkRTree::SkRTree () : fCount(0 ) {}
10+ PlatformViewRTree::PlatformViewRTree () : fCount(0 ) {}
1111
12- void SkRTree ::insert (const SkRect boundsArray[],
12+ void PlatformViewRTree ::insert (const SkRect boundsArray[],
1313 const SkBBoxHierarchy::Metadata metadata[],
1414 int N) {
1515 SkASSERT (0 == fCount );
@@ -30,6 +30,7 @@ void SkRTree::insert(const SkRect boundsArray[],
3030 Branch b;
3131 b.fBounds = bounds;
3232 b.fOpIndex = i;
33+ b.isDraw = (metadata == nullptr ) ? false : metadata[i].isDraw ;
3334 branches.push_back (b);
3435}
3536
@@ -48,11 +49,11 @@ if (fCount) {
4849 }
4950}
5051
51- void SkRTree ::insert (const SkRect boundsArray[], int N) {
52+ void PlatformViewRTree ::insert (const SkRect boundsArray[], int N) {
5253 insert (boundsArray, nullptr , N);
5354}
5455
55- SkRTree ::Node* SkRTree ::allocateNodeAtLevel (uint16_t level) {
56+ PlatformViewRTree ::Node* PlatformViewRTree ::allocateNodeAtLevel (uint16_t level) {
5657 SkDEBUGCODE (Node* p = fNodes .data ());
5758 fNodes .push_back (Node{});
5859 Node& out = fNodes .back ();
@@ -64,7 +65,7 @@ SkRTree::Node* SkRTree::allocateNodeAtLevel(uint16_t level) {
6465
6566// This function parallels bulkLoad, but just counts how many nodes bulkLoad
6667// would allocate.
67- int SkRTree ::CountNodes (int branches) {
68+ int PlatformViewRTree ::CountNodes (int branches) {
6869 if (branches == 1 ) {
6970 return 1 ;
7071 }
@@ -100,7 +101,7 @@ int SkRTree::CountNodes(int branches) {
100101 return nodes + CountNodes (nodes);
101102}
102103
103- SkRTree ::Branch SkRTree ::bulkLoad (std::vector<Branch>* branches, int level) {
104+ PlatformViewRTree ::Branch PlatformViewRTree ::bulkLoad (std::vector<Branch>* branches, int level) {
104105 if (branches->size () == 1 ) { // Only one branch. It will be the root.
105106 return (*branches)[0 ];
106107 }
@@ -156,13 +157,13 @@ SkRTree::Branch SkRTree::bulkLoad(std::vector<Branch>* branches, int level) {
156157 return this ->bulkLoad (branches, level + 1 );
157158}
158159
159- void SkRTree ::search (const SkRect& query, std::vector<int >* results) const {
160+ void PlatformViewRTree ::search (const SkRect& query, std::vector<int >* results) const {
160161 if (fCount > 0 && SkRect::Intersects (fRoot .fBounds , query)) {
161162 this ->search (fRoot .fSubtree , query, results);
162163 }
163164}
164165
165- void SkRTree ::search (Node* node, const SkRect& query, std::vector<int >* results) const {
166+ void PlatformViewRTree ::search (Node* node, const SkRect& query, std::vector<int >* results) const {
166167 for (int i = 0 ; i < node->fNumChildren ; ++i) {
167168 if (!SkRect::Intersects (node->fChildren [i].fBounds , query)) {
168169 continue ;
@@ -175,8 +176,74 @@ void SkRTree::search(Node* node, const SkRect& query, std::vector<int>* results)
175176 }
176177}
177178
178- size_t SkRTree::bytesUsed () const {
179- size_t byteCount = sizeof (SkRTree);
179+ void PlatformViewRTree::searchRects (const SkRect& query, std::vector<SkRect*>* results) const {
180+ if (fCount > 0 && SkRect::Intersects (fRoot .fBounds , query)) {
181+ this ->searchRects (fRoot .fSubtree , query, results);
182+ }
183+ }
184+
185+ void PlatformViewRTree::searchRects (Node* node,
186+ const SkRect& query,
187+ std::vector<SkRect*>* results) const {
188+ if (!SkRect::Intersects (fRoot .fBounds , query)) {
189+ return ;
190+ }
191+ for (int i = 0 ; i < node->fNumChildren ; ++i) {
192+ if (!SkRect::Intersects (node->fChildren [i].fBounds , query)) {
193+ continue ;
194+ }
195+ // Non-leaf node
196+ if (0 != node->fLevel ) {
197+ this ->searchRects (node->fChildren [i].fSubtree , query, results);
198+ continue ;
199+ }
200+ // Ignore records that don't draw anything.
201+ if (!node->fChildren [i].isDraw ) {
202+ continue ;
203+ }
204+ SkRect* currentRecordRect = &node->fChildren [i].fBounds ;
205+ std::vector<SkRect*> currentResults = *results;
206+ bool replacedExistingRect = false ;
207+ // If the current record rect intersects with any of the rects in the
208+ // result vector, then join them, and update the rect in results.
209+ size_t joiningRectIdx = currentResults.size ();
210+ size_t resultIdx = 0 ;
211+ while (resultIdx < results->size ()) {
212+ if (SkRect::Intersects (*currentResults[resultIdx], *currentRecordRect)) {
213+ joiningRectIdx = resultIdx;
214+ replacedExistingRect = true ;
215+ currentResults[joiningRectIdx]->join (*currentRecordRect);
216+ break ;
217+ }
218+ resultIdx++;
219+ }
220+ resultIdx = joiningRectIdx + 1 ;
221+ // It's possible that after joining rects will result in duplicated
222+ // rects in the results vector. For example, consider a result vector
223+ // that contains rects A, B. If a new rect C is a superset of A and B,
224+ // then A and B are the same set after the merge. As a result, find such
225+ // cases and remove them from the result vector.
226+ while (replacedExistingRect && resultIdx < results->size ()) {
227+ if (SkRect::Intersects (*currentResults[resultIdx], *currentResults[joiningRectIdx])) {
228+ currentResults[joiningRectIdx]->join (*currentResults[resultIdx]);
229+ results->erase (results->begin () + resultIdx);
230+ } else {
231+ resultIdx++;
232+ }
233+ }
234+ if (!replacedExistingRect) {
235+ results->push_back (currentRecordRect);
236+ }
237+ }
238+ }
239+
240+ size_t PlatformViewRTree::bytesUsed () const {
241+ size_t byteCount = sizeof (PlatformViewRTree);
180242 byteCount += fNodes .capacity () * sizeof (Node);
181243 return byteCount;
182244}
245+
246+ PlatformViewRTreeFactory::PlatformViewRTreeFactory (sk_sp<PlatformViewRTree>& r_tree)
247+ : r_tree_(r_tree) {}
248+
249+ sk_sp<SkBBoxHierarchy> PlatformViewRTreeFactory::operator ()() const { return r_tree_; }
0 commit comments