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

Side by Side Diff: Source/core/rendering/FloatingObjects.cpp

Issue 22893013: Move Floats out of RenderBlock (Closed) Base URL: svn://svn.chromium.org/blink/trunk
Patch Set: Fix release bot compile error Created 7 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
« no previous file with comments | « Source/core/rendering/FloatingObjects.h ('k') | Source/core/rendering/RenderBlock.h » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
(Empty)
1 /*
2 * Copyright (C) 1999 Lars Knoll (knoll@kde.org)
3 * (C) 1999 Antti Koivisto (koivisto@kde.org)
4 * (C) 2007 David Smith (catfish.man@gmail.com)
5 * Copyright (C) 2003, 2004, 2005, 2006, 2007, 2008, 2009, 2010, 2011 Apple Inc. All rights reserved.
6 * Copyright (C) Research In Motion Limited 2010. All rights reserved.
7 *
8 * This library is free software; you can redistribute it and/or
9 * modify it under the terms of the GNU Library General Public
10 * License as published by the Free Software Foundation; either
11 * version 2 of the License, or (at your option) any later version.
12 *
13 * This library is distributed in the hope that it will be useful,
14 * but WITHOUT ANY WARRANTY; without even the implied warranty of
15 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
16 * Library General Public License for more details.
17 *
18 * You should have received a copy of the GNU Library General Public License
19 * along with this library; see the file COPYING.LIB. If not, write to
20 * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
21 * Boston, MA 02110-1301, USA.
22 */
23
24 #include "config.h"
25 #include "core/rendering/FloatingObjects.h"
26
27 #include "core/rendering/RenderBlock.h"
28 #include "core/rendering/RenderBox.h"
29 #include "core/rendering/RenderView.h"
30
31 using namespace std;
32 using namespace WTF;
33
34 namespace WebCore {
35
36 struct SameSizeAsFloatingObject {
37 void* pointers[2];
38 LayoutRect rect;
39 int paginationStrut;
40 uint32_t bitfields : 8;
41 };
42
43 COMPILE_ASSERT(sizeof(FloatingObject) == sizeof(SameSizeAsFloatingObject), Float ingObject_should_stay_small);
44
45 template <FloatingObject::Type FloatTypeValue>
46 class ComputeFloatOffsetAdapter {
47 public:
48 typedef FloatingObjectInterval IntervalType;
49
50 ComputeFloatOffsetAdapter(const RenderBlock* renderer, int lineTop, int line Bottom, LayoutUnit& offset)
51 : m_renderer(renderer)
52 , m_lineTop(lineTop)
53 , m_lineBottom(lineBottom)
54 , m_offset(offset)
55 , m_outermostFloat(0)
56 {
57 }
58
59 int lowValue() const { return m_lineTop; }
60 int highValue() const { return m_lineBottom; }
61 void collectIfNeeded(const IntervalType&);
62
63 // When computing the offset caused by the floats on a given line, if
64 // the outermost float on that line has a shape-outside, the inline
65 // content that butts up against that float must be positioned using
66 // the contours of the shape, not the margin box of the float.
67 const FloatingObject* outermostFloat() const { return m_outermostFloat; }
68
69 LayoutUnit getHeightRemaining() const;
70
71 private:
72 bool updateOffsetIfNeeded(const FloatingObject*);
73
74 const RenderBlock* m_renderer;
75 int m_lineTop;
76 int m_lineBottom;
77 LayoutUnit& m_offset;
78 const FloatingObject* m_outermostFloat;
79 };
80
81
82 FloatingObjects::~FloatingObjects()
83 {
84 // FIXME: m_set should use OwnPtr instead.
85 deleteAllValues(m_set);
86 }
87 void FloatingObjects::clearLineBoxTreePointers()
88 {
89 // Clear references to originating lines, since the lines are being deleted
90 FloatingObjectSetIterator end = m_set.end();
91 for (FloatingObjectSetIterator it = m_set.begin(); it != end; ++it) {
92 ASSERT(!((*it)->originatingLine()) || (*it)->originatingLine()->renderer () == m_renderer);
93 (*it)->setOriginatingLine(0);
94 }
95 }
96
97 template<>
98 inline bool ComputeFloatOffsetAdapter<FloatingObject::FloatLeft>::updateOffsetIf Needed(const FloatingObject* floatingObject)
99 {
100 LayoutUnit logicalRight = floatingObject->logicalRight(m_renderer->isHorizon talWritingMode());
101 if (logicalRight > m_offset) {
102 m_offset = logicalRight;
103 return true;
104 }
105 return false;
106 }
107
108 FloatingObjects::FloatingObjects(const RenderBlock* renderer, bool horizontalWri tingMode)
109 : m_placedFloatsTree(UninitializedTree)
110 , m_leftObjectsCount(0)
111 , m_rightObjectsCount(0)
112 , m_horizontalWritingMode(horizontalWritingMode)
113 , m_renderer(renderer)
114 {
115 }
116
117 void FloatingObjects::clear()
118 {
119 // FIXME: This should call deleteAllValues, except clearFloats
120 // like to play fast and loose with ownership of these pointers.
121 // If we move to OwnPtr that will fix this ownership oddness.
122 m_set.clear();
123 m_placedFloatsTree.clear();
124 m_leftObjectsCount = 0;
125 m_rightObjectsCount = 0;
126 }
127
128 inline void FloatingObjects::increaseObjectsCount(FloatingObject::Type type)
129 {
130 if (type == FloatingObject::FloatLeft)
131 m_leftObjectsCount++;
132 else
133 m_rightObjectsCount++;
134 }
135
136 inline void FloatingObjects::decreaseObjectsCount(FloatingObject::Type type)
137 {
138 if (type == FloatingObject::FloatLeft)
139 m_leftObjectsCount--;
140 else
141 m_rightObjectsCount--;
142 }
143
144 inline FloatingObjectInterval FloatingObjects::intervalForFloatingObject(Floatin gObject* floatingObject)
145 {
146 if (m_horizontalWritingMode)
147 return FloatingObjectInterval(floatingObject->frameRect().pixelSnappedY( ), floatingObject->frameRect().pixelSnappedMaxY(), floatingObject);
148 return FloatingObjectInterval(floatingObject->frameRect().pixelSnappedX(), f loatingObject->frameRect().pixelSnappedMaxX(), floatingObject);
149 }
150
151 void FloatingObjects::addPlacedObject(FloatingObject* floatingObject)
152 {
153 ASSERT(!floatingObject->isInPlacedTree());
154
155 floatingObject->setIsPlaced(true);
156 if (m_placedFloatsTree.isInitialized())
157 m_placedFloatsTree.add(intervalForFloatingObject(floatingObject));
158
159 #ifndef NDEBUG
160 floatingObject->setIsInPlacedTree(true);
161 #endif
162 }
163
164 void FloatingObjects::removePlacedObject(FloatingObject* floatingObject)
165 {
166 ASSERT(floatingObject->isPlaced() && floatingObject->isInPlacedTree());
167
168 if (m_placedFloatsTree.isInitialized()) {
169 bool removed = m_placedFloatsTree.remove(intervalForFloatingObject(float ingObject));
170 ASSERT_UNUSED(removed, removed);
171 }
172
173 floatingObject->setIsPlaced(false);
174 #ifndef NDEBUG
175 floatingObject->setIsInPlacedTree(false);
176 #endif
177 }
178
179 void FloatingObjects::add(FloatingObject* floatingObject)
180 {
181 increaseObjectsCount(floatingObject->type());
182 m_set.add(floatingObject);
183 if (floatingObject->isPlaced())
184 addPlacedObject(floatingObject);
185 }
186
187 void FloatingObjects::remove(FloatingObject* floatingObject)
188 {
189 decreaseObjectsCount(floatingObject->type());
190 m_set.remove(floatingObject);
191 ASSERT(floatingObject->isPlaced() || !floatingObject->isInPlacedTree());
192 if (floatingObject->isPlaced())
193 removePlacedObject(floatingObject);
194 }
195
196 void FloatingObjects::computePlacedFloatsTree()
197 {
198 ASSERT(!m_placedFloatsTree.isInitialized());
199 if (m_set.isEmpty())
200 return;
201 m_placedFloatsTree.initIfNeeded(m_renderer->view()->intervalArena());
202 FloatingObjectSetIterator it = m_set.begin();
203 FloatingObjectSetIterator end = m_set.end();
204 for (; it != end; ++it) {
205 FloatingObject* floatingObject = *it;
206 if (floatingObject->isPlaced())
207 m_placedFloatsTree.add(intervalForFloatingObject(floatingObject));
208 }
209 }
210
211 LayoutUnit FloatingObjects::logicalLeftOffset(LayoutUnit fixedOffset, LayoutUnit logicalTop, LayoutUnit logicalHeight, ShapeOutsideFloatOffsetMode offsetMode, L ayoutUnit *heightRemaining)
212 {
213 LayoutUnit offset = fixedOffset;
214 ComputeFloatOffsetAdapter<FloatingObject::FloatLeft> adapter(m_renderer, rou ndToInt(logicalTop), roundToInt(logicalTop + logicalHeight), offset);
215 placedFloatsTree().allOverlapsWithAdapter(adapter);
216
217 if (heightRemaining)
218 *heightRemaining = adapter.getHeightRemaining();
219
220 const FloatingObject* outermostFloat = adapter.outermostFloat();
221 if (offsetMode == ShapeOutsideFloatShapeOffset && outermostFloat) {
222 if (ShapeOutsideInfo* shapeOutside = outermostFloat->renderer()->shapeOu tsideInfo()) {
223 shapeOutside->computeSegmentsForContainingBlockLine(logicalTop, oute rmostFloat->logicalTop(m_horizontalWritingMode), logicalHeight);
224 offset += shapeOutside->rightSegmentMarginBoxDelta();
225 }
226 }
227
228 return offset;
229 }
230
231 LayoutUnit FloatingObjects::logicalRightOffset(LayoutUnit fixedOffset, LayoutUni t logicalTop, LayoutUnit logicalHeight, ShapeOutsideFloatOffsetMode offsetMode, LayoutUnit *heightRemaining)
232 {
233 LayoutUnit offset = fixedOffset;
234 ComputeFloatOffsetAdapter<FloatingObject::FloatRight> adapter(m_renderer, ro undToInt(logicalTop), roundToInt(logicalTop + logicalHeight), offset);
235 placedFloatsTree().allOverlapsWithAdapter(adapter);
236
237 if (heightRemaining)
238 *heightRemaining = adapter.getHeightRemaining();
239
240 const FloatingObject* outermostFloat = adapter.outermostFloat();
241 if (offsetMode == ShapeOutsideFloatShapeOffset && outermostFloat) {
242 if (ShapeOutsideInfo* shapeOutside = outermostFloat->renderer()->shapeOu tsideInfo()) {
243 shapeOutside->computeSegmentsForContainingBlockLine(logicalTop, oute rmostFloat->logicalTop(m_horizontalWritingMode), logicalHeight);
244 offset += shapeOutside->leftSegmentMarginBoxDelta();
245 }
246 }
247
248 return min(fixedOffset, offset);
249 }
250
251 inline static bool rangesIntersect(int floatTop, int floatBottom, int objectTop, int objectBottom)
252 {
253 if (objectTop >= floatBottom || objectBottom < floatTop)
254 return false;
255
256 // The top of the object overlaps the float
257 if (objectTop >= floatTop)
258 return true;
259
260 // The object encloses the float
261 if (objectTop < floatTop && objectBottom > floatBottom)
262 return true;
263
264 // The bottom of the object overlaps the float
265 if (objectBottom > objectTop && objectBottom > floatTop && objectBottom <= f loatBottom)
266 return true;
267
268 return false;
269 }
270
271 template<>
272 inline bool ComputeFloatOffsetAdapter<FloatingObject::FloatRight>::updateOffsetI fNeeded(const FloatingObject* floatingObject)
273 {
274 LayoutUnit logicalLeft = floatingObject->logicalLeft(m_renderer->isHorizonta lWritingMode());
275 if (logicalLeft < m_offset) {
276 m_offset = logicalLeft;
277 return true;
278 }
279 return false;
280 }
281
282 template <FloatingObject::Type FloatTypeValue>
283 inline void ComputeFloatOffsetAdapter<FloatTypeValue>::collectIfNeeded(const Int ervalType& interval)
284 {
285 const FloatingObject* floatingObject = interval.data();
286 if (floatingObject->type() != FloatTypeValue || !rangesIntersect(interval.lo w(), interval.high(), m_lineTop, m_lineBottom))
287 return;
288
289 // Make sure the float hasn't changed since it was added to the placed float s tree.
290 ASSERT(floatingObject->isPlaced());
291 ASSERT(interval.low() == floatingObject->pixelSnappedLogicalTop(m_renderer-> isHorizontalWritingMode()));
292 ASSERT(interval.high() == floatingObject->pixelSnappedLogicalBottom(m_render er->isHorizontalWritingMode()));
293
294 bool floatIsNewExtreme = updateOffsetIfNeeded(floatingObject);
295 if (floatIsNewExtreme)
296 m_outermostFloat = floatingObject;
297 }
298
299 template <FloatingObject::Type FloatTypeValue>
300 LayoutUnit ComputeFloatOffsetAdapter<FloatTypeValue>::getHeightRemaining() const
301 {
302 return m_outermostFloat ? m_outermostFloat->logicalBottom(m_renderer->isHori zontalWritingMode()) - m_lineTop : LayoutUnit(1);
303 }
304
305 #ifndef NDEBUG
306 // These helpers are only used by the PODIntervalTree for debugging purposes.
307 String ValueToString<int>::string(const int value)
308 {
309 return String::number(value);
310 }
311
312 String ValueToString<FloatingObject*>::string(const FloatingObject* floatingObje ct)
313 {
314 return String::format("%p (%dx%d %dx%d)", floatingObject, floatingObject->fr ameRect().pixelSnappedX(), floatingObject->frameRect().pixelSnappedY(), floating Object->frameRect().pixelSnappedMaxX(), floatingObject->frameRect().pixelSnapped MaxY());
315 }
316 #endif
317
318
319 } // namespace WebCore
OLDNEW
« no previous file with comments | « Source/core/rendering/FloatingObjects.h ('k') | Source/core/rendering/RenderBlock.h » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698