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

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

Issue 288263002: [New Multicolumn] Rebalance properly when child content changes. (Closed) Base URL: https://chromium.googlesource.com/chromium/blink.git@master
Patch Set: More cleanup; avoid bool arguments. Get rid of layout() override. Created 6 years, 7 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
OLDNEW
1 /* 1 /*
2 * Copyright (C) 2012 Apple Inc. All rights reserved. 2 * Copyright (C) 2012 Apple Inc. All rights reserved.
3 * 3 *
4 * Redistribution and use in source and binary forms, with or without 4 * Redistribution and use in source and binary forms, with or without
5 * modification, are permitted provided that the following conditions 5 * modification, are permitted provided that the following conditions
6 * are met: 6 * are met:
7 * 1. Redistributions of source code must retain the above copyright 7 * 1. Redistributions of source code must retain the above copyright
8 * notice, this list of conditions and the following disclaimer. 8 * notice, this list of conditions and the following disclaimer.
9 * 2. Redistributions in binary form must reproduce the above copyright 9 * 2. Redistributions in binary form must reproduce the above copyright
10 * notice, this list of conditions and the following disclaimer in the 10 * notice, this list of conditions and the following disclaimer in the
(...skipping 45 matching lines...) Expand 10 before | Expand all | Expand 10 after
56 56
57 RenderMultiColumnSet* RenderMultiColumnSet::nextSiblingMultiColumnSet() const 57 RenderMultiColumnSet* RenderMultiColumnSet::nextSiblingMultiColumnSet() const
58 { 58 {
59 for (RenderObject* sibling = nextSibling(); sibling; sibling = sibling->next Sibling()) { 59 for (RenderObject* sibling = nextSibling(); sibling; sibling = sibling->next Sibling()) {
60 if (sibling->isRenderMultiColumnSet()) 60 if (sibling->isRenderMultiColumnSet())
61 return toRenderMultiColumnSet(sibling); 61 return toRenderMultiColumnSet(sibling);
62 } 62 }
63 return 0; 63 return 0;
64 } 64 }
65 65
66 RenderMultiColumnSet* RenderMultiColumnSet::previousSiblingMultiColumnSet() cons t
67 {
68 for (RenderObject* sibling = previousSibling(); sibling; sibling = sibling-> previousSibling()) {
69 if (sibling->isRenderMultiColumnSet())
70 return toRenderMultiColumnSet(sibling);
71 }
72 return 0;
73 }
74
66 LayoutSize RenderMultiColumnSet::flowThreadTranslationAtOffset(LayoutUnit blockO ffset) const 75 LayoutSize RenderMultiColumnSet::flowThreadTranslationAtOffset(LayoutUnit blockO ffset) const
67 { 76 {
68 unsigned columnIndex = columnIndexAtOffset(blockOffset); 77 unsigned columnIndex = columnIndexAtOffset(blockOffset);
69 LayoutRect portionRect(flowThreadPortionRectAt(columnIndex)); 78 LayoutRect portionRect(flowThreadPortionRectAt(columnIndex));
70 flipForWritingMode(portionRect); 79 flipForWritingMode(portionRect);
71 LayoutRect columnRect(columnRectAt(columnIndex)); 80 LayoutRect columnRect(columnRectAt(columnIndex));
72 flipForWritingMode(columnRect); 81 flipForWritingMode(columnRect);
73 return contentBoxRect().location() + columnRect.location() - portionRect.loc ation(); 82 return contentBoxRect().location() + columnRect.location() - portionRect.loc ation();
74 } 83 }
75 84
76 LayoutUnit RenderMultiColumnSet::heightAdjustedForSetOffset(LayoutUnit height) c onst 85 LayoutUnit RenderMultiColumnSet::heightAdjustedForSetOffset(LayoutUnit height) c onst
77 { 86 {
78 RenderBlockFlow* multicolBlock = multiColumnBlockFlow(); 87 // Adjust for the top offset within the content box of the multicol containe r (containing
79 LayoutUnit contentLogicalTop = logicalTop() - multicolBlock->borderBefore() - multicolBlock->paddingBefore(); 88 // block), unless this is the first set. We know that the top offset for the first set will be
80 89 // zero, but if the multicol container has non-zero top border or padding, t he set's top offset
81 height -= contentLogicalTop; 90 // (initially being 0 and relative to the border box) will be negative until it has been laid
91 // out. Had we used this bogus offset, we would calculate the wrong height, and risk performing
92 // a wasted layout iteration. Of course all other sets (if any) have this pr oblem in the first
93 // layout pass too, but there's really nothing we can do there until the flo w thread has been
94 // laid out anyway.
95 if (previousSiblingMultiColumnSet()) {
96 RenderBlockFlow* multicolBlock = multiColumnBlockFlow();
97 LayoutUnit contentLogicalTop = logicalTop() - multicolBlock->borderBefor e() - multicolBlock->paddingBefore();
Julien - ping for review 2014/05/23 09:07:54 This can be shortened using borderAndPaddingBefore
mstensho (USE GERRIT) 2014/05/23 11:46:09 Done.
98 height -= contentLogicalTop;
99 }
82 return max(height, LayoutUnit(1)); // Let's avoid zero height, as that would probably cause an infinite amount of columns to be created. 100 return max(height, LayoutUnit(1)); // Let's avoid zero height, as that would probably cause an infinite amount of columns to be created.
83 } 101 }
84 102
85 LayoutUnit RenderMultiColumnSet::pageLogicalTopForOffset(LayoutUnit offset) cons t 103 LayoutUnit RenderMultiColumnSet::pageLogicalTopForOffset(LayoutUnit offset) cons t
86 { 104 {
87 LayoutUnit portionLogicalTop = (isHorizontalWritingMode() ? flowThreadPortio nRect().y() : flowThreadPortionRect().x());
88 unsigned columnIndex = columnIndexAtOffset(offset, AssumeNewColumns); 105 unsigned columnIndex = columnIndexAtOffset(offset, AssumeNewColumns);
89 return portionLogicalTop + columnIndex * computedColumnHeight(); 106 return logicalTopInFlowThread() + columnIndex * computedColumnHeight();
90 } 107 }
91 108
92 void RenderMultiColumnSet::setAndConstrainColumnHeight(LayoutUnit newHeight) 109 void RenderMultiColumnSet::setAndConstrainColumnHeight(LayoutUnit newHeight)
93 { 110 {
94 m_computedColumnHeight = newHeight; 111 m_computedColumnHeight = newHeight;
95 if (m_computedColumnHeight > m_maxColumnHeight) 112 if (m_computedColumnHeight > m_maxColumnHeight)
96 m_computedColumnHeight = m_maxColumnHeight; 113 m_computedColumnHeight = m_maxColumnHeight;
97 // FIXME: the height may also be affected by the enclosing pagination contex t, if any. 114 // FIXME: the height may also be affected by the enclosing pagination contex t, if any.
98 } 115 }
99 116
(...skipping 35 matching lines...) Expand 10 before | Expand all | Expand 10 after
135 // column count by one and shrink its columns' height. Repeat until we have the desired total 152 // column count by one and shrink its columns' height. Repeat until we have the desired total
136 // number of breaks. The largest column height among the runs will then be t he initial column 153 // number of breaks. The largest column height among the runs will then be t he initial column
137 // height for the balancer to use. 154 // height for the balancer to use.
138 while (columnCount < m_computedColumnCount) { 155 while (columnCount < m_computedColumnCount) {
139 unsigned index = findRunWithTallestColumns(); 156 unsigned index = findRunWithTallestColumns();
140 m_contentRuns[index].assumeAnotherImplicitBreak(); 157 m_contentRuns[index].assumeAnotherImplicitBreak();
141 columnCount++; 158 columnCount++;
142 } 159 }
143 } 160 }
144 161
145 LayoutUnit RenderMultiColumnSet::calculateColumnHeight(bool initial) const 162 LayoutUnit RenderMultiColumnSet::calculateColumnHeight(BalancedHeightCalculation calculationMode) const
146 { 163 {
147 if (initial) { 164 if (calculationMode == GuessFromFlowThreadPortion) {
148 // Start with the lowest imaginable column height. We use the tallest co ntent run (after 165 // Initial balancing. Start with the lowest imaginable column height. We use the tallest
149 // having "inserted" implicit breaks), and find its start offset (by loo king at the previous 166 // content run (after having "inserted" implicit breaks), and find its s tart offset (by
150 // run's end offset, or, if there's no previous run, the set's start off set in the flow 167 // looking at the previous run's end offset, or, if there's no previous run, the set's start
151 // thread). 168 // offset in the flow thread).
152 unsigned index = findRunWithTallestColumns(); 169 unsigned index = findRunWithTallestColumns();
153 LayoutUnit startOffset = index > 0 ? m_contentRuns[index - 1].breakOffse t() : logicalTopInFlowThread(); 170 LayoutUnit startOffset = index > 0 ? m_contentRuns[index - 1].breakOffse t() : logicalTopInFlowThread();
154 return std::max<LayoutUnit>(m_contentRuns[index].columnLogicalHeight(sta rtOffset), m_minimumColumnHeight); 171 return std::max<LayoutUnit>(m_contentRuns[index].columnLogicalHeight(sta rtOffset), m_minimumColumnHeight);
155 } 172 }
156 173
157 if (columnCount() <= computedColumnCount()) { 174 if (columnCount() <= computedColumnCount()) {
158 // With the current column height, the content fits without creating ove rflowing columns. We're done. 175 // With the current column height, the content fits without creating ove rflowing columns. We're done.
159 return m_computedColumnHeight; 176 return m_computedColumnHeight;
160 } 177 }
161 178
(...skipping 19 matching lines...) Expand all
181 if (!multiColumnFlowThread()->requiresBalancing()) 198 if (!multiColumnFlowThread()->requiresBalancing())
182 return; 199 return;
183 if (!m_contentRuns.isEmpty() && endOffsetFromFirstPage <= m_contentRuns.last ().breakOffset()) 200 if (!m_contentRuns.isEmpty() && endOffsetFromFirstPage <= m_contentRuns.last ().breakOffset())
184 return; 201 return;
185 // Append another item as long as we haven't exceeded used column count. Wha t ends up in the 202 // Append another item as long as we haven't exceeded used column count. Wha t ends up in the
186 // overflow area shouldn't affect column balancing. 203 // overflow area shouldn't affect column balancing.
187 if (m_contentRuns.size() < m_computedColumnCount) 204 if (m_contentRuns.size() < m_computedColumnCount)
188 m_contentRuns.append(ContentRun(endOffsetFromFirstPage)); 205 m_contentRuns.append(ContentRun(endOffsetFromFirstPage));
189 } 206 }
190 207
191 bool RenderMultiColumnSet::recalculateColumnHeight(bool initial) 208 bool RenderMultiColumnSet::recalculateColumnHeight(BalancedHeightCalculation cal culationMode)
192 { 209 {
193 ASSERT(multiColumnFlowThread()->requiresBalancing()); 210 ASSERT(multiColumnFlowThread()->requiresBalancing());
194 211
195 LayoutUnit oldColumnHeight = m_computedColumnHeight; 212 LayoutUnit oldColumnHeight = m_computedColumnHeight;
196 if (initial) { 213 if (calculationMode == GuessFromFlowThreadPortion) {
197 // Post-process the content runs and find out where the implicit breaks will occur. 214 // Post-process the content runs and find out where the implicit breaks will occur.
198 distributeImplicitBreaks(); 215 distributeImplicitBreaks();
199 } 216 }
200 LayoutUnit newColumnHeight = calculateColumnHeight(initial); 217 LayoutUnit newColumnHeight = calculateColumnHeight(calculationMode);
201 setAndConstrainColumnHeight(newColumnHeight); 218 setAndConstrainColumnHeight(newColumnHeight);
202 219
203 // After having calculated an initial column height, the multicol container typically needs at 220 // After having calculated an initial column height, the multicol container typically needs at
204 // least one more layout pass with a new column height, but if a height was specified, we only 221 // least one more layout pass with a new column height, but if a height was specified, we only
205 // need to do this if we think that we need less space than specified. Conve rsely, if we 222 // need to do this if we think that we need less space than specified. Conve rsely, if we
206 // determined that the columns need to be as tall as the specified height of the container, we 223 // determined that the columns need to be as tall as the specified height of the container, we
207 // have already laid it out correctly, and there's no need for another pass. 224 // have already laid it out correctly, and there's no need for another pass.
208 225
226 // We can get rid of the content runs now, if we haven't already done so. Th ey are only needed
227 // to calculate the initial balanced column height. In fact, we have to get rid of them before
228 // the next layout pass, since each pass will rebuild this.
229 m_contentRuns.clear();
230
209 if (m_computedColumnHeight == oldColumnHeight) 231 if (m_computedColumnHeight == oldColumnHeight)
210 return false; // No change. We're done. 232 return false; // No change. We're done.
211 233
212 m_minSpaceShortage = RenderFlowThread::maxLogicalHeight(); 234 m_minSpaceShortage = RenderFlowThread::maxLogicalHeight();
213 m_contentRuns.clear();
214 return true; // Need another pass. 235 return true; // Need another pass.
215 } 236 }
216 237
217 void RenderMultiColumnSet::recordSpaceShortage(LayoutUnit spaceShortage) 238 void RenderMultiColumnSet::recordSpaceShortage(LayoutUnit spaceShortage)
218 { 239 {
219 if (spaceShortage >= m_minSpaceShortage) 240 if (spaceShortage >= m_minSpaceShortage)
220 return; 241 return;
221 242
222 // The space shortage is what we use as our stretch amount. We need a positi ve number here in 243 // The space shortage is what we use as our stretch amount. We need a positi ve number here in
223 // order to get anywhere. 244 // order to get anywhere.
224 ASSERT(spaceShortage > 0); 245 ASSERT(spaceShortage > 0);
225 246
226 m_minSpaceShortage = spaceShortage; 247 m_minSpaceShortage = spaceShortage;
227 } 248 }
228 249
229 void RenderMultiColumnSet::updateLogicalWidth() 250 void RenderMultiColumnSet::resetColumnHeight()
Julien - ping for review 2014/05/23 09:07:54 Could you explain why we don't need this override
mstensho (USE GERRIT) 2014/05/23 11:46:09 A column set always has the same width as its cont
230 { 251 {
231 RenderMultiColumnFlowThread* flowThread = multiColumnFlowThread();
232 setComputedColumnWidthAndCount(flowThread->columnWidth(), flowThread->column Count());
233
234 // FIXME: When we add regions support, we'll start it off at the width of th e multi-column
235 // block in that particular region.
236 setLogicalWidth(parentBox()->contentLogicalWidth());
237
238 // If we overflow, increase our logical width.
239 unsigned colCount = columnCount();
240 LayoutUnit colGap = columnGap();
241 LayoutUnit minimumContentLogicalWidth = colCount * computedColumnWidth() + ( colCount - 1) * colGap;
242 LayoutUnit currentContentLogicalWidth = contentLogicalWidth();
243 LayoutUnit delta = max(LayoutUnit(), minimumContentLogicalWidth - currentCon tentLogicalWidth);
244 if (!delta)
245 return;
246
247 // Increase our logical width by the delta.
248 setLogicalWidth(logicalWidth() + delta);
249 }
250
251 void RenderMultiColumnSet::prepareForLayout()
252 {
253 RenderBlockFlow* multicolBlock = multiColumnBlockFlow();
254 RenderStyle* multicolStyle = multicolBlock->style();
255
256 // Set box logical top.
257 ASSERT(!previousSiblingBox() || !previousSiblingBox()->isRenderMultiColumnSe t()); // FIXME: multiple set not implemented; need to examine previous set to ca lculate the correct logical top.
258 setLogicalTop(multicolBlock->borderBefore() + multicolBlock->paddingBefore() );
259
260 // Set box width.
261 updateLogicalWidth();
262
263 if (multiColumnFlowThread()->requiresBalancing()) {
264 // Set maximum column height. We will not stretch beyond this.
265 m_maxColumnHeight = RenderFlowThread::maxLogicalHeight();
266 if (!multicolStyle->logicalHeight().isAuto()) {
267 m_maxColumnHeight = multicolBlock->computeContentLogicalHeight(multi colStyle->logicalHeight(), -1);
268 if (m_maxColumnHeight == -1)
269 m_maxColumnHeight = RenderFlowThread::maxLogicalHeight();
270 }
271 if (!multicolStyle->logicalMaxHeight().isUndefined()) {
272 LayoutUnit logicalMaxHeight = multicolBlock->computeContentLogicalHe ight(multicolStyle->logicalMaxHeight(), -1);
273 if (logicalMaxHeight != -1 && m_maxColumnHeight > logicalMaxHeight)
274 m_maxColumnHeight = logicalMaxHeight;
275 }
276 m_maxColumnHeight = heightAdjustedForSetOffset(m_maxColumnHeight);
277 m_computedColumnHeight = 0; // Restart balancing.
278 } else {
279 setAndConstrainColumnHeight(heightAdjustedForSetOffset(multiColumnFlowTh read()->columnHeightAvailable()));
280 }
281
282 m_contentRuns.clear();
283
284 // Nuke previously stored minimum column height. Contents may have changed f or all we know. 252 // Nuke previously stored minimum column height. Contents may have changed f or all we know.
285 m_minimumColumnHeight = 0; 253 m_minimumColumnHeight = 0;
254
255 m_maxColumnHeight = calculateMaxColumnHeight();
256
257 LayoutUnit oldColumnHeight = computedColumnHeight();
258
259 if (multiColumnFlowThread()->requiresBalancing())
260 m_computedColumnHeight = 0;
261 else
262 setAndConstrainColumnHeight(heightAdjustedForSetOffset(multiColumnFlowTh read()->columnHeightAvailable()));
263
264 if (computedColumnHeight() != oldColumnHeight)
265 setChildNeedsLayout(MarkOnlyThis);
266
267 // Content runs are only needed in the initial layout pass, in order to find an initial column
268 // height, and should have been deleted afterwards. We're about to rebuild t he content runs, so
269 // the list needs to be empty.
270 ASSERT(m_contentRuns.isEmpty());
286 } 271 }
287 272
288 void RenderMultiColumnSet::expandToEncompassFlowThreadContentsIfNeeded() 273 void RenderMultiColumnSet::expandToEncompassFlowThreadContentsIfNeeded()
289 { 274 {
290 ASSERT(multiColumnFlowThread()->lastMultiColumnSet() == this); 275 ASSERT(multiColumnFlowThread()->lastMultiColumnSet() == this);
291 LayoutRect rect(flowThreadPortionRect()); 276 LayoutRect rect(flowThreadPortionRect());
292 277
293 // Get the offset within the flow thread in its block progression direction. Then get the 278 // Get the offset within the flow thread in its block progression direction. Then get the
294 // flow thread's remaining logical height including its overflow and expand our rect 279 // flow thread's remaining logical height including its overflow and expand our rect
295 // to encompass that remaining height and overflow. The idea is that we will generate 280 // to encompass that remaining height and overflow. The idea is that we will generate
296 // additional columns and pages to hold that overflow, since people do write bad 281 // additional columns and pages to hold that overflow, since people do write bad
297 // content like <body style="height:0px"> in multi-column layouts. 282 // content like <body style="height:0px"> in multi-column layouts.
298 bool isHorizontal = flowThread()->isHorizontalWritingMode(); 283 bool isHorizontal = flowThread()->isHorizontalWritingMode();
299 LayoutUnit logicalTopOffset = isHorizontal ? rect.y() : rect.x(); 284 LayoutUnit logicalTopOffset = isHorizontal ? rect.y() : rect.x();
300 LayoutRect layoutRect = flowThread()->layoutOverflowRect(); 285 LayoutRect layoutRect = flowThread()->layoutOverflowRect();
301 LayoutUnit logicalHeightWithOverflow = (isHorizontal ? layoutRect.maxY() : l ayoutRect.maxX()) - logicalTopOffset; 286 LayoutUnit logicalHeightWithOverflow = (isHorizontal ? layoutRect.maxY() : l ayoutRect.maxX()) - logicalTopOffset;
302 setFlowThreadPortionRect(LayoutRect(rect.x(), rect.y(), isHorizontal ? rect. width() : logicalHeightWithOverflow, isHorizontal ? logicalHeightWithOverflow : rect.height())); 287 setFlowThreadPortionRect(LayoutRect(rect.x(), rect.y(), isHorizontal ? rect. width() : logicalHeightWithOverflow, isHorizontal ? logicalHeightWithOverflow : rect.height()));
303 } 288 }
304 289
305 void RenderMultiColumnSet::layout()
306 {
307 RenderRegion::layout();
308
309 if (!nextSiblingMultiColumnSet()) {
310 // This is the last set, i.e. the last region. Seize the opportunity to validate them.
311 multiColumnFlowThread()->validateRegions();
312 }
313 }
314
315 void RenderMultiColumnSet::computeLogicalHeight(LayoutUnit, LayoutUnit logicalTo p, LogicalExtentComputedValues& computedValues) const 290 void RenderMultiColumnSet::computeLogicalHeight(LayoutUnit, LayoutUnit logicalTo p, LogicalExtentComputedValues& computedValues) const
316 { 291 {
317 computedValues.m_extent = m_computedColumnHeight; 292 computedValues.m_extent = m_computedColumnHeight;
318 computedValues.m_position = logicalTop; 293 computedValues.m_position = logicalTop;
319 } 294 }
320 295
296 LayoutUnit RenderMultiColumnSet::calculateMaxColumnHeight() const
297 {
298 RenderBlockFlow* multicolBlock = multiColumnBlockFlow();
299 RenderStyle* multicolStyle = multicolBlock->style();
300 LayoutUnit availableHeight = multiColumnFlowThread()->columnHeightAvailable( );
301 LayoutUnit maxColumnHeight = availableHeight ? availableHeight : RenderFlowT hread::maxLogicalHeight();
302 if (!multicolStyle->logicalMaxHeight().isUndefined()) {
303 LayoutUnit logicalMaxHeight = multicolBlock->computeContentLogicalHeight (multicolStyle->logicalMaxHeight(), -1);
304 if (logicalMaxHeight != -1 && maxColumnHeight > logicalMaxHeight)
305 maxColumnHeight = logicalMaxHeight;
306 }
307 return heightAdjustedForSetOffset(maxColumnHeight);
308 }
309
321 LayoutUnit RenderMultiColumnSet::columnGap() const 310 LayoutUnit RenderMultiColumnSet::columnGap() const
322 { 311 {
323 RenderBlockFlow* parentBlock = multiColumnBlockFlow(); 312 RenderBlockFlow* parentBlock = multiColumnBlockFlow();
324 if (parentBlock->style()->hasNormalColumnGap()) 313 if (parentBlock->style()->hasNormalColumnGap())
325 return parentBlock->style()->fontDescription().computedPixelSize(); // " 1em" is recommended as the normal gap setting. Matches <p> margins. 314 return parentBlock->style()->fontDescription().computedPixelSize(); // " 1em" is recommended as the normal gap setting. Matches <p> margins.
326 return parentBlock->style()->columnGap(); 315 return parentBlock->style()->columnGap();
327 } 316 }
328 317
329 unsigned RenderMultiColumnSet::columnCount() const 318 unsigned RenderMultiColumnSet::columnCount() const
330 { 319 {
(...skipping 293 matching lines...) Expand 10 before | Expand all | Expand 10 after
624 fragment.paginationOffset = translationOffset; 613 fragment.paginationOffset = translationOffset;
625 614
626 LayoutRect flippedFlowThreadOverflowPortion(flowThreadOverflowPortion); 615 LayoutRect flippedFlowThreadOverflowPortion(flowThreadOverflowPortion);
627 // Flip it into more a physical (RenderLayer-style) rectangle. 616 // Flip it into more a physical (RenderLayer-style) rectangle.
628 flowThread()->flipForWritingMode(flippedFlowThreadOverflowPortion); 617 flowThread()->flipForWritingMode(flippedFlowThreadOverflowPortion);
629 fragment.paginationClip = flippedFlowThreadOverflowPortion; 618 fragment.paginationClip = flippedFlowThreadOverflowPortion;
630 fragments.append(fragment); 619 fragments.append(fragment);
631 } 620 }
632 } 621 }
633 622
623 void RenderMultiColumnSet::addOverflowFromChildren()
624 {
625 unsigned colCount = columnCount();
626 if (!colCount)
627 return;
628
629 LayoutRect lastRect = columnRectAt(colCount - 1);
630 addLayoutOverflow(lastRect);
631 if (!hasOverflowClip())
632 addVisualOverflow(lastRect);
633 }
634
634 const char* RenderMultiColumnSet::renderName() const 635 const char* RenderMultiColumnSet::renderName() const
635 { 636 {
636 return "RenderMultiColumnSet"; 637 return "RenderMultiColumnSet";
637 } 638 }
638 639
639 } 640 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698