blob: b7a839bfd2c2d84eaeaa7f685815a986f52bdaa9 [file] [log] [blame]
reed@google.comac10a2d2010-12-22 21:39:39 +00001/*
2 Copyright 2010 Google Inc.
3
4 Licensed under the Apache License, Version 2.0 (the "License");
5 you may not use this file except in compliance with the License.
6 You may obtain a copy of the License at
7
8 http://www.apache.org/licenses/LICENSE-2.0
9
10 Unless required by applicable law or agreed to in writing, software
11 distributed under the License is distributed on an "AS IS" BASIS,
12 WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 See the License for the specific language governing permissions and
14 limitations under the License.
15 */
16
17
18#include "GrClip.h"
19
20GrClip::GrClip() {
21 fBounds.setEmpty();
22 this->validate();
23}
24
25GrClip::GrClip(const GrClip& src) {
26 *this = src;
27}
28
29GrClip::GrClip(GrClipIterator* iter) {
30 fBounds.setEmpty();
31 this->setFromIterator(iter);
32}
33
34GrClip::~GrClip() {}
35
36GrClip& GrClip::operator=(const GrClip& src) {
37 fList = src.fList;
38 fBounds = src.fBounds;
39 this->validate();
40 return *this;
41}
42
43void GrClip::setEmpty() {
44 fList.reset();
45 fBounds.setEmpty();
46 this->validate();
47}
48
49void GrClip::setRect(const GrIRect& r) {
50 fList.reset();
51
52 // we need a canonical "empty" rect, so that our operator== will behave
53 // correctly with two empty clips.
54 if (r.isEmpty()) {
55 fBounds.setEmpty();
56 } else {
57 fBounds = r;
58 }
59 this->validate();
60}
61
62void GrClip::addRect(const GrIRect& r) {
63 if (!r.isEmpty()) {
64 this->validate();
65 if (this->isEmpty()) {
66 GrAssert(fList.count() == 0);
67 fBounds = r;
68 } else {
69 if (this->isRect()) {
70 *fList.append() = fBounds;
71 }
72 *fList.append() = r;
73 fBounds.unionWith(r);
74 }
75 this->validate();
76 }
77}
78
79void GrClip::setFromIterator(GrClipIterator* iter) {
80 this->setEmpty();
81 if (iter) {
82 for (iter->rewind(); !iter->isDone(); iter->next()) {
83 GrIRect r;
84 iter->getRect(&r);
85 this->addRect(r);
86 }
87 }
88}
89
90///////////////////////////////////////////////////////////////////////////////
91
92void GrClipIter::reset(const GrClip& clip) { fClip = &clip; fIndex = 0; }
93
94bool GrClipIter::isDone() {
95 return (NULL == fClip) || (fIndex >= fClip->countRects());
96}
97
98void GrClipIter::rewind() { fIndex = 0; }
99void GrClipIter::getRect(GrIRect* r) { *r = fClip->getRects()[fIndex]; }
100void GrClipIter::next() { fIndex += 1; }
101void GrClipIter::computeBounds(GrIRect* r) {
102 if (NULL == fClip) {
103 r->setEmpty();
104 } else {
105 *r = fClip->getBounds();
106 }
107}
108
109///////////////////////////////////////////////////////////////////////////////
110
111#if GR_DEBUG
112
113void GrClip::validate() const {
114 if (fBounds.isEmpty()) {
115 GrAssert(0 == fBounds.fLeft);
116 GrAssert(0 == fBounds.fTop);
117 GrAssert(0 == fBounds.fRight);
118 GrAssert(0 == fBounds.fBottom);
119 GrAssert(0 == fList.count());
120 } else {
121 int count = fList.count();
122 if (count > 0) {
123 GrAssert(count > 1);
124 GrAssert(!fList[0].isEmpty());
125 GrIRect bounds = fList[0];
126 for (int i = 1; i < count; i++) {
127 GrAssert(!fList[i].isEmpty());
128 bounds.unionWith(fList[i]);
129 }
130 GrAssert(fBounds == bounds);
131 }
132 }
133}
134
135#endif
136