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

Side by Side Diff: third_party/WebKit/Source/core/layout/LayoutTableSection.cpp

Issue 2433403002: Pay attention to tall rowspanned cells in the first layout pass. (Closed)
Patch Set: Created 4 years, 2 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
« no previous file with comments | « third_party/WebKit/LayoutTests/fragmentation/table-overlapping-rowspan-expected.txt ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 /* 1 /*
2 * Copyright (C) 1997 Martin Jones (mjones@kde.org) 2 * Copyright (C) 1997 Martin Jones (mjones@kde.org)
3 * (C) 1997 Torben Weis (weis@kde.org) 3 * (C) 1997 Torben Weis (weis@kde.org)
4 * (C) 1998 Waldo Bastian (bastian@kde.org) 4 * (C) 1998 Waldo Bastian (bastian@kde.org)
5 * (C) 1999 Lars Knoll (knoll@kde.org) 5 * (C) 1999 Lars Knoll (knoll@kde.org)
6 * (C) 1999 Antti Koivisto (koivisto@kde.org) 6 * (C) 1999 Antti Koivisto (koivisto@kde.org)
7 * Copyright (C) 2003, 2004, 2005, 2006, 2008, 2009, 2010, 2013 Apple Inc. 7 * Copyright (C) 2003, 2004, 2005, 2006, 2008, 2009, 2010, 2013 Apple Inc.
8 * All rights reserved. 8 * All rights reserved.
9 * Copyright (C) 2006 Alexey Proskuryakov (ap@nypop.com) 9 * Copyright (C) 2006 Alexey Proskuryakov (ap@nypop.com)
10 * 10 *
(...skipping 838 matching lines...) Expand 10 before | Expand all | Expand 10 after
849 if (this == table()->topSection()) 849 if (this == table()->topSection())
850 m_rowPos[0] = table()->vBorderSpacing(); 850 m_rowPos[0] = table()->vBorderSpacing();
851 else 851 else
852 m_rowPos[0] = 0; 852 m_rowPos[0] = 0;
853 853
854 SpanningLayoutTableCells rowSpanCells; 854 SpanningLayoutTableCells rowSpanCells;
855 #if ENABLE(ASSERT) 855 #if ENABLE(ASSERT)
856 HashSet<const LayoutTableCell*> uniqueCells; 856 HashSet<const LayoutTableCell*> uniqueCells;
857 #endif 857 #endif
858 858
859 // At fragmentainer breaks we need to prevent rowspanned cells (and whatever
860 // else) from distributing their extra height requirements over the rows that
861 // it spans. Otherwise we'd need to refragment afterwards.
862 unsigned indexOfFirstStretchableRow = 0;
863
859 for (unsigned r = 0; r < m_grid.size(); r++) { 864 for (unsigned r = 0; r < m_grid.size(); r++) {
860 m_grid[r].baseline = -1; 865 m_grid[r].baseline = -1;
861 int baselineDescent = 0; 866 int baselineDescent = 0;
862 867
863 if (state.isPaginated() && m_grid[r].rowLayoutObject) 868 if (state.isPaginated() && m_grid[r].rowLayoutObject)
864 m_rowPos[r] += m_grid[r].rowLayoutObject->paginationStrut().ceil(); 869 m_rowPos[r] += m_grid[r].rowLayoutObject->paginationStrut().ceil();
865 870
866 if (m_grid[r].logicalHeight.isSpecified()) { 871 if (m_grid[r].logicalHeight.isSpecified()) {
867 // Our base size is the biggest logical height from our cells' styles 872 // Our base size is the biggest logical height from our cells' styles
868 // (excluding row spanning cells). 873 // (excluding row spanning cells).
(...skipping 12 matching lines...) Expand all
881 unsigned totalCols = row.size(); 886 unsigned totalCols = row.size();
882 LayoutTableCell* lastRowSpanCell = nullptr; 887 LayoutTableCell* lastRowSpanCell = nullptr;
883 888
884 for (unsigned c = 0; c < totalCols; c++) { 889 for (unsigned c = 0; c < totalCols; c++) {
885 CellStruct& current = cellAt(r, c); 890 CellStruct& current = cellAt(r, c);
886 for (unsigned i = 0; i < current.cells.size(); i++) { 891 for (unsigned i = 0; i < current.cells.size(); i++) {
887 cell = current.cells[i]; 892 cell = current.cells[i];
888 if (current.inColSpan && cell->rowSpan() == 1) 893 if (current.inColSpan && cell->rowSpan() == 1)
889 continue; 894 continue;
890 895
891 if (cell->rowSpan() > 1) { 896 if (r < indexOfFirstStretchableRow ||
897 (state.isPaginated() &&
898 crossesPageBoundary(
899 LayoutUnit(m_rowPos[cell->rowIndex()]),
900 LayoutUnit(cell->logicalHeightForRowSizing())))) {
901 // Entering or extending a range of unstretchable rows. We enter this
902 // mode when a cell in a row crosses a fragmentainer boundary, and
903 // we'll stay in this mode until we get to a row where we're past all
904 // rowspanned cells that we encountered while in this mode.
905 DCHECK(state.isPaginated());
906 unsigned rowIndexBelowCell = cell->rowIndex() + cell->rowSpan();
907 indexOfFirstStretchableRow =
908 std::max(indexOfFirstStretchableRow, rowIndexBelowCell);
909 } else if (cell->rowSpan() > 1) {
892 // For row spanning cells, we only handle them for the first row they 910 // For row spanning cells, we only handle them for the first row they
893 // span. This ensures we take their baseline into account. 911 // span. This ensures we take their baseline into account.
894 if (lastRowSpanCell != cell && cell->rowIndex() == r) { 912 if (lastRowSpanCell != cell && cell->rowIndex() == r) {
895 #if ENABLE(ASSERT) 913 #if ENABLE(ASSERT)
896 ASSERT(!uniqueCells.contains(cell)); 914 ASSERT(!uniqueCells.contains(cell));
897 uniqueCells.add(cell); 915 uniqueCells.add(cell);
898 #endif 916 #endif
899 917
900 rowSpanCells.append(cell); 918 rowSpanCells.append(cell);
901 lastRowSpanCell = cell; 919 lastRowSpanCell = cell;
(...skipping 10 matching lines...) Expand all
912 m_rowPos[r + 1] = std::max( 930 m_rowPos[r + 1] = std::max(
913 m_rowPos[r + 1], m_rowPos[r] + cell->logicalHeightForRowSizing()); 931 m_rowPos[r + 1], m_rowPos[r] + cell->logicalHeightForRowSizing());
914 932
915 // Find out the baseline. The baseline is set on the first row in a 933 // Find out the baseline. The baseline is set on the first row in a
916 // rowSpan. 934 // rowSpan.
917 if (cell->rowIndex() == r) 935 if (cell->rowIndex() == r)
918 updateBaselineForCell(cell, r, baselineDescent); 936 updateBaselineForCell(cell, r, baselineDescent);
919 } 937 }
920 } 938 }
921 939
940 if (r < indexOfFirstStretchableRow && m_grid[r].rowLayoutObject) {
941 // We're not allowed to resize this row. Just scratch what we've
942 // calculated so far, and use the height that we got during initial
943 // layout instead.
944 m_rowPos[r + 1] =
945 m_rowPos[r] + m_grid[r].rowLayoutObject->logicalHeight().toInt();
946 }
947
922 // Add the border-spacing to our final position. 948 // Add the border-spacing to our final position.
923 m_rowPos[r + 1] += borderSpacingForRow(r); 949 m_rowPos[r + 1] += borderSpacingForRow(r);
924 m_rowPos[r + 1] = std::max(m_rowPos[r + 1], m_rowPos[r]); 950 m_rowPos[r + 1] = std::max(m_rowPos[r + 1], m_rowPos[r]);
925 } 951 }
926 952
927 if (!rowSpanCells.isEmpty()) 953 if (!rowSpanCells.isEmpty())
928 distributeRowSpanHeightToRows(rowSpanCells); 954 distributeRowSpanHeightToRows(rowSpanCells);
929 955
930 ASSERT(!needsLayout()); 956 ASSERT(!needsLayout());
931 957
(...skipping 1035 matching lines...) Expand 10 before | Expand all | Expand 10 after
1967 unsigned rowIndex = rowObject.rowIndex(); 1993 unsigned rowIndex = rowObject.rowIndex();
1968 DCHECK(rowIndex < m_grid.size()); 1994 DCHECK(rowIndex < m_grid.size());
1969 int logicalHeight = 0; 1995 int logicalHeight = 0;
1970 const Row& row = m_grid[rowIndex].row; 1996 const Row& row = m_grid[rowIndex].row;
1971 unsigned cols = row.size(); 1997 unsigned cols = row.size();
1972 for (unsigned colIndex = 0; colIndex < cols; colIndex++) { 1998 for (unsigned colIndex = 0; colIndex < cols; colIndex++) {
1973 const CellStruct& cellStruct = cellAt(rowIndex, colIndex); 1999 const CellStruct& cellStruct = cellAt(rowIndex, colIndex);
1974 const LayoutTableCell* cell = cellStruct.primaryCell(); 2000 const LayoutTableCell* cell = cellStruct.primaryCell();
1975 if (!cell || cellStruct.inColSpan) 2001 if (!cell || cellStruct.inColSpan)
1976 continue; 2002 continue;
1977 // TODO(mstensho): Rowspanned cells also need to contribute to row heights 2003 unsigned rowSpan = cell->rowSpan();
1978 // during the first layout pass, in order to get fragmentation right. 2004 if (rowSpan == 1) {
1979 if (cell->rowSpan() == 1) {
1980 logicalHeight = 2005 logicalHeight =
1981 std::max(logicalHeight, cell->logicalHeightForRowSizing()); 2006 std::max(logicalHeight, cell->logicalHeightForRowSizing());
2007 continue;
2008 }
2009 unsigned rowIndexForCell = cell->rowIndex();
2010 if (rowIndex == m_grid.size() - 1 ||
2011 (rowSpan > 1 && rowIndex - rowIndexForCell == rowSpan - 1)) {
2012 // This is the last row of the rowspanned cell. Add extra height if
2013 // needed.
2014 if (LayoutTableRow* firstRowForCell =
2015 m_grid[rowIndexForCell].rowLayoutObject) {
2016 int rowLogicalTop = rowObject.logicalTop().round();
2017
2018 int minLogicalHeight = cell->logicalHeightForRowSizing();
2019 // Subtract space provided by previous rows.
2020 minLogicalHeight -=
2021 rowLogicalTop - firstRowForCell->logicalTop().toInt();
eae 2016/10/20 16:53:58 Above you round the logicalTop and here you floor
mstensho (USE GERRIT) 2016/10/20 19:05:56 Better use toInt() everywhere, unless there are go
2022
2023 logicalHeight = std::max(logicalHeight, minLogicalHeight);
2024 }
1982 } 2025 }
1983 } 2026 }
1984 2027
1985 if (m_grid[rowIndex].logicalHeight.isSpecified()) { 2028 if (m_grid[rowIndex].logicalHeight.isSpecified()) {
1986 LayoutUnit specifiedLogicalHeight = 2029 LayoutUnit specifiedLogicalHeight =
1987 minimumValueForLength(m_grid[rowIndex].logicalHeight, LayoutUnit()); 2030 minimumValueForLength(m_grid[rowIndex].logicalHeight, LayoutUnit());
1988 logicalHeight = std::max(logicalHeight, specifiedLogicalHeight.toInt()); 2031 logicalHeight = std::max(logicalHeight, specifiedLogicalHeight.toInt());
1989 } 2032 }
1990 return logicalHeight; 2033 return logicalHeight;
1991 } 2034 }
(...skipping 82 matching lines...) Expand 10 before | Expand all | Expand 10 after
2074 // the header in all columns. 2117 // the header in all columns.
2075 // Note that this is in flow thread coordinates, not visual coordinates. The 2118 // Note that this is in flow thread coordinates, not visual coordinates. The
2076 // enclosing LayoutFlowThread will convert to visual coordinates. 2119 // enclosing LayoutFlowThread will convert to visual coordinates.
2077 if (table()->header() == this && isRepeatingHeaderGroup()) 2120 if (table()->header() == this && isRepeatingHeaderGroup())
2078 rect.setHeight(table()->logicalHeight()); 2121 rect.setHeight(table()->logicalHeight());
2079 return LayoutTableBoxComponent::mapToVisualRectInAncestorSpace(ancestor, rect, 2122 return LayoutTableBoxComponent::mapToVisualRectInAncestorSpace(ancestor, rect,
2080 flags); 2123 flags);
2081 } 2124 }
2082 2125
2083 } // namespace blink 2126 } // namespace blink
OLDNEW
« no previous file with comments | « third_party/WebKit/LayoutTests/fragmentation/table-overlapping-rowspan-expected.txt ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698