Changeset 132764 in webkit
- Timestamp:
- Oct 29, 2012, 12:38:01 AM (13 years ago)
- Location:
- trunk/Source/WebCore
- Files:
-
- 5 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/Source/WebCore/ChangeLog
r132762 r132764 1 2012-10-29 Eric Seidel <eric@webkit.org> 2 3 Make rendering tables with <colgroups> twice as fast by avoiding walking the DOM for colgroups 4 times for each cell 4 https://bugs.webkit.org/show_bug.cgi?id=100630 5 6 Reviewed by Ojan Vafai. 7 8 This is not a complete fix. Our rendering of this large tables still takes 7.8 seconds 9 on my retina MBP (down from 14.3s before this change). 10 It's very expensive to walk the DOM each time we call RenderTable::colElement 11 so this caches the RenderTableCol* in a vector for easier walking. 12 We invalidate the cache any time a RenderTableCol is added or removed from the 13 rendering sub-tree to avoid holding a bad pointer. 14 15 * rendering/RenderTable.cpp: 16 (WebCore::RenderTable::RenderTable): 17 (WebCore::RenderTable::invalidateCachedColumns): 18 (WebCore): 19 (WebCore::RenderTable::addColumn): 20 (WebCore::RenderTable::removeColumn): 21 (WebCore::RenderTable::updateColumnCache): 22 (WebCore::RenderTable::slowColElement): 23 * rendering/RenderTable.h: 24 (RenderTable): 25 * rendering/RenderTableCol.cpp: 26 (WebCore::RenderTableCol::insertedIntoTree): 27 (WebCore): 28 (WebCore::RenderTableCol::willBeRemovedFromTree): 29 * rendering/RenderTableCol.h: 30 1 31 2012-10-28 Kent Tamura <tkent@chromium.org> 2 32 -
trunk/Source/WebCore/rendering/RenderTable.cpp
r132641 r132764 60 60 , m_needsSectionRecalc(false) 61 61 , m_columnLogicalWidthChanged(false) 62 , m_columnRenderersValid(false) 62 63 , m_hSpacing(0) 63 64 , m_vSpacing(0) … … 214 215 } 215 216 217 void RenderTable::invalidateCachedColumns() 218 { 219 m_columnRenderersValid = false; 220 m_columnRenderers.resize(0); 221 } 222 223 void RenderTable::addColumn(const RenderTableCol*) 224 { 225 invalidateCachedColumns(); 226 } 227 228 void RenderTable::removeColumn(const RenderTableCol*) 229 { 230 invalidateCachedColumns(); 231 // We don't really need to recompute our sections, but we need to update our 232 // column count and whether we have a column. Currently, we only have one 233 // size-fit-all flag but we may have to consider splitting it. 234 setNeedsSectionRecalc(); 235 } 236 216 237 void RenderTable::updateLogicalWidth() 217 238 { … … 760 781 } 761 782 762 RenderTableCol* RenderTable::slowColElement(unsigned col, bool* startEdge, bool* endEdge) const783 void RenderTable::updateColumnCache() const 763 784 { 764 785 ASSERT(m_hasColElements); 765 766 unsigned columnCount = 0; 786 ASSERT(m_columnRenderers.isEmpty()); 787 ASSERT(!m_columnRenderersValid); 788 767 789 for (RenderTableCol* columnRenderer = firstColumn(); columnRenderer; columnRenderer = columnRenderer->nextColumn()) { 768 790 if (columnRenderer->isTableColumnGroupWithColumnChildren()) 769 791 continue; 770 792 m_columnRenderers.append(columnRenderer); 793 } 794 m_columnRenderersValid = true; 795 } 796 797 RenderTableCol* RenderTable::slowColElement(unsigned col, bool* startEdge, bool* endEdge) const 798 { 799 ASSERT(m_hasColElements); 800 801 if (!m_columnRenderersValid) 802 updateColumnCache(); 803 804 unsigned columnCount = 0; 805 for (unsigned i = 0; i < m_columnRenderers.size(); i++) { 806 RenderTableCol* columnRenderer = m_columnRenderers[i]; 771 807 unsigned span = columnRenderer->span(); 772 808 unsigned startCol = columnCount; … … 782 818 } 783 819 } 784 785 820 return 0; 786 821 } -
trunk/Source/WebCore/rendering/RenderTable.h
r132112 r132764 46 46 virtual ~RenderTable(); 47 47 48 int getColumnPos(unsigned col) const { return m_columnPos[col]; }49 50 48 // Per CSS 3 writing-mode: "The first and second values of the 'border-spacing' property represent spacing between columns 51 49 // and rows respectively, not necessarily the horizontal and vertical spacing respectively". … … 259 257 void addCaption(const RenderTableCaption*); 260 258 void removeCaption(const RenderTableCaption*); 259 void addColumn(const RenderTableCol*); 260 void removeColumn(const RenderTableCol*); 261 261 262 262 protected: … … 284 284 RenderTableCol* slowColElement(unsigned col, bool* startEdge, bool* endEdge) const; 285 285 286 void updateColumnCache() const; 287 void invalidateCachedColumns(); 288 286 289 virtual RenderBlock* firstLineBlock() const; 287 290 virtual void updateFirstLetter(); … … 306 309 mutable Vector<ColumnStruct> m_columns; 307 310 mutable Vector<RenderTableCaption*> m_captions; 311 mutable Vector<RenderTableCol*> m_columnRenderers; 308 312 309 313 mutable RenderTableSection* m_head; … … 316 320 const CollapsedBorderValue* m_currentBorder; 317 321 bool m_collapsedBordersValid : 1; 318 322 319 323 mutable bool m_hasColElements : 1; 320 324 mutable bool m_needsSectionRecalc : 1; 325 321 326 bool m_columnLogicalWidthChanged : 1; 327 mutable bool m_columnRenderersValid: 1; 322 328 323 329 short m_hSpacing; -
trunk/Source/WebCore/rendering/RenderTableCol.cpp
r132641 r132764 71 71 } 72 72 73 void RenderTableCol::insertedIntoTree() 74 { 75 RenderBox::insertedIntoTree(); 76 table()->addColumn(this); 77 } 78 73 79 void RenderTableCol::willBeRemovedFromTree() 74 80 { 75 81 RenderBox::willBeRemovedFromTree(); 76 77 // We don't really need to recompute our sections, but we need to update our 78 // column count and whether we have a column. Currently, we only have one 79 // size-fit-all flag but we may have to consider splitting it. 80 table()->setNeedsSectionRecalc(); 82 table()->removeColumn(this); 81 83 } 82 84 -
trunk/Source/WebCore/rendering/RenderTableCol.h
r132641 r132764 82 82 virtual void updateFromElement(); 83 83 84 virtual void insertedIntoTree() OVERRIDE; 84 85 virtual void willBeRemovedFromTree() OVERRIDE; 85 86
Note:
See TracChangeset
for help on using the changeset viewer.