Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(581)

Side by Side Diff: cc/base/simple_enclosed_region.cc

Issue 202523002: cc: Replace Region with SimpleEnclosedRegion for occlusion tracking (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/src
Patch Set: simpleregion: . Created 6 years, 4 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
OLDNEW
(Empty)
1 // Copyright (c) 2014 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4
5 #include "cc/base/simple_enclosed_region.h"
6
7 #include "base/logging.h"
8 #include "cc/base/region.h"
9
10 namespace cc {
11
12 static bool RectIsLargerArea(const gfx::Rect& a, const gfx::Rect b) {
13 int64 a_area = static_cast<int64>(a.width()) * a.height();
14 int64 b_area = static_cast<int64>(b.width()) * b.height();
15 return a_area > b_area;
16 }
17
18 SimpleEnclosedRegion::SimpleEnclosedRegion(const Region& region) {
19 for (Region::Iterator it(region); it.has_rect(); it.next())
20 Union(it.rect());
21 }
22
23 SimpleEnclosedRegion::~SimpleEnclosedRegion() {
24 }
25
26 void SimpleEnclosedRegion::Subtract(const gfx::Rect& sub_rect) {
27 // We want to keep as much of the current rect as we can, so find the one
28 // largest rectangle inside |rect_| that does not intersect with |sub_rect|.
29 if (!rect_.Intersects(sub_rect))
30 return;
31 if (sub_rect.Contains(rect_)) {
32 rect_ = gfx::Rect();
33 return;
34 }
35
36 int left = rect_.x();
37 int right = rect_.right();
38 int top = rect_.y();
39 int bottom = rect_.bottom();
40
41 int delta_left = sub_rect.x() - left;
42 int delta_right = right - sub_rect.right();
43 int delta_top = sub_rect.y() - top;
44 int delta_bottom = bottom - sub_rect.bottom();
45
46 // The horizontal rect is the larger of the two rectangles above or below
47 // |sub_rect| and inside rect_.
48 int horizontal_top = top;
49 int horizontal_bottom = bottom;
50 if (delta_top > delta_bottom)
51 horizontal_bottom = sub_rect.y();
52 else
53 horizontal_top = sub_rect.bottom();
54 // The vertical rect is the larger of the two rectangles to the left or the
55 // right of |sub_rect| and inside rect_.
56 int vertical_left = left;
57 int vertical_right = right;
58 if (delta_left > delta_right)
59 vertical_right = sub_rect.x();
60 else
61 vertical_left = sub_rect.right();
62
63 rect_.SetRect(
64 left, horizontal_top, right - left, horizontal_bottom - horizontal_top);
65
66 gfx::Rect vertical_rect(
67 vertical_left, top, vertical_right - vertical_left, bottom - top);
68 if (RectIsLargerArea(vertical_rect, rect_))
69 rect_ = vertical_rect;
70 }
71
72 void SimpleEnclosedRegion::Union(const gfx::Rect& new_rect) {
73 // We want to keep track of a region but bound its complexity at a constant
74 // size. We keep track of the largest rectangle seen by area. If we can add
75 // the |new_rect| to this rectangle then we do that, as that is the cheapest
76 // way to increase the area returned without increasing the complexity.
77 if (new_rect.IsEmpty())
78 return;
79 if (rect_.Contains(new_rect))
80 return;
81 if (new_rect.Contains(rect_)) {
82 rect_ = new_rect;
83 return;
84 }
85
86 int left = rect_.x();
87 int top = rect_.y();
88 int right = rect_.right();
89 int bottom = rect_.bottom();
90
91 int new_left = new_rect.x();
92 int new_top = new_rect.y();
93 int new_right = new_rect.right();
94 int new_bottom = new_rect.bottom();
95
96 if (new_top <= top && new_bottom >= bottom) {
enne (OOO) 2014/08/21 20:48:05 So many conditionals. O_O Could you leave a brie
danakj 2014/08/21 21:15:31 I think that would regress the case of two rectang
enne (OOO) 2014/08/21 21:19:40 Aha, ok. That case makes sense.
97 if (new_left < left && new_right >= left)
98 left = new_left;
99 if (new_right > right && new_left <= right)
100 right = new_right;
101 } else if (new_left <= left && new_right >= right) {
102 if (new_top < top && new_bottom >= top)
103 top = new_top;
104 if (new_bottom > bottom && new_top <= bottom)
105 bottom = new_bottom;
106 } else if (top <= new_top && bottom >= new_bottom) {
107 if (left < new_left && right >= new_left)
108 new_left = left;
109 if (right > new_right && left <= new_right)
110 new_right = right;
111 } else if (left <= new_left && right >= new_right) {
112 if (top < new_top && bottom >= new_top)
113 new_top = top;
114 if (bottom > new_bottom && top <= new_bottom)
115 new_bottom = bottom;
116 }
117
118 rect_.SetRect(left, top, right - left, bottom - top);
119
120 gfx::Rect adjusted_new_rect(
121 new_left, new_top, new_right - new_left, new_bottom - new_top);
122 if (RectIsLargerArea(adjusted_new_rect, rect_))
123 rect_ = adjusted_new_rect;
124 }
125
126 gfx::Rect SimpleEnclosedRegion::GetRect(size_t i) const {
127 DCHECK_LT(i, GetRegionComplexity());
128 return rect_;
129 }
130
131 } // namespace cc
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698