From 562b840a02a7589050feb69739b93772620bd439 Mon Sep 17 00:00:00 2001 From: Mats Palmgren Date: Tue, 20 Dec 2016 23:56:35 +0100 Subject: [PATCH] Bug 1312379 part 3 - [css-align][css-tables] Add methods for CSS Alignment first/last baseline of the table container. r=dholbert --- layout/tables/nsTableFrame.cpp | 61 +++++++++++++++++--------- layout/tables/nsTableFrame.h | 4 ++ layout/tables/nsTableRowGroupFrame.cpp | 14 +++++- layout/tables/nsTableRowGroupFrame.h | 1 + layout/tables/nsTableWrapperFrame.h | 19 ++++++++ 5 files changed, 77 insertions(+), 22 deletions(-) diff --git a/layout/tables/nsTableFrame.cpp b/layout/tables/nsTableFrame.cpp index 6eb1be777f06..6f98dd65e934 100644 --- a/layout/tables/nsTableFrame.cpp +++ b/layout/tables/nsTableFrame.cpp @@ -3805,35 +3805,54 @@ nsTableFrame::GetRowSpacing(int32_t aStartRowIndex, } /* virtual */ nscoord -nsTableFrame::GetLogicalBaseline(WritingMode aWritingMode) const +nsTableFrame::GetLogicalBaseline(WritingMode aWM) const +{ + nscoord baseline; + if (!GetNaturalBaselineBOffset(aWM, BaselineSharingGroup::eFirst, &baseline)) { + baseline = BSize(aWM); + } + return baseline; +} + +/* virtual */ bool +nsTableFrame::GetNaturalBaselineBOffset(WritingMode aWM, + BaselineSharingGroup aBaselineGroup, + nscoord* aBaseline) const { - nscoord ascent = 0; RowGroupArray orderedRowGroups; OrderRowGroups(orderedRowGroups); - nsTableRowFrame* firstRow = nullptr; // XXX not sure if this should be the size of the containing block instead. nsSize containerSize = mRect.Size(); - for (uint32_t rgIndex = 0; rgIndex < orderedRowGroups.Length(); rgIndex++) { - nsTableRowGroupFrame* rgFrame = orderedRowGroups[rgIndex]; - if (rgFrame->GetRowCount()) { - firstRow = rgFrame->GetFirstRow(); - - nscoord rgNormalBStart = - LogicalRect(aWritingMode, rgFrame->GetNormalRect(), containerSize) - .Origin(aWritingMode).B(aWritingMode); - nscoord firstRowNormalBStart = - LogicalRect(aWritingMode, firstRow->GetNormalRect(), containerSize) - .Origin(aWritingMode).B(aWritingMode); - - ascent = rgNormalBStart + firstRowNormalBStart + - firstRow->GetRowBaseline(aWritingMode); - break; + auto TableBaseline = [aWM, containerSize] (nsTableRowGroupFrame* aRowGroup, + nsTableRowFrame* aRow) { + nscoord rgBStart = LogicalRect(aWM, aRowGroup->GetNormalRect(), + containerSize).BStart(aWM); + nscoord rowBStart = LogicalRect(aWM, aRow->GetNormalRect(), + containerSize).BStart(aWM); + return rgBStart + rowBStart + aRow->GetRowBaseline(aWM); + }; + if (aBaselineGroup == BaselineSharingGroup::eFirst) { + for (uint32_t rgIndex = 0; rgIndex < orderedRowGroups.Length(); rgIndex++) { + nsTableRowGroupFrame* rgFrame = orderedRowGroups[rgIndex]; + nsTableRowFrame* row = rgFrame->GetFirstRow(); + if (row) { + *aBaseline = TableBaseline(rgFrame, row); + return true; + } + } + } else { + for (uint32_t rgIndex = orderedRowGroups.Length(); rgIndex-- > 0;) { + nsTableRowGroupFrame* rgFrame = orderedRowGroups[rgIndex]; + nsTableRowFrame* row = rgFrame->GetLastRow(); + if (row) { + *aBaseline = BSize(aWM) - TableBaseline(rgFrame, row); + return true; + } } } - if (!firstRow) - ascent = BSize(aWritingMode); - return ascent; + return false; } + /* ----- global methods ----- */ nsTableFrame* diff --git a/layout/tables/nsTableFrame.h b/layout/tables/nsTableFrame.h index e97679a8d9cb..6b216689a249 100644 --- a/layout/tables/nsTableFrame.h +++ b/layout/tables/nsTableFrame.h @@ -465,6 +465,10 @@ private: public: virtual nscoord GetLogicalBaseline(mozilla::WritingMode aWritingMode) const override; + bool GetNaturalBaselineBOffset(mozilla::WritingMode aWM, + BaselineSharingGroup aBaselineGroup, + nscoord* aBaseline) const override; + /** return the row span of a cell, taking into account row span magic at the bottom * of a table. The row span equals the number of rows spanned by aCell starting at * aStartRowIndex, and can be smaller if aStartRowIndex is greater than the row diff --git a/layout/tables/nsTableRowGroupFrame.cpp b/layout/tables/nsTableRowGroupFrame.cpp index 781dabaf88a6..60596f12b07d 100644 --- a/layout/tables/nsTableRowGroupFrame.cpp +++ b/layout/tables/nsTableRowGroupFrame.cpp @@ -507,7 +507,19 @@ nsTableRowFrame* nsTableRowGroupFrame::GetFirstRow() { for (nsIFrame* childFrame : mFrames) { - nsTableRowFrame *rowFrame = do_QueryFrame(childFrame); + nsTableRowFrame* rowFrame = do_QueryFrame(childFrame); + if (rowFrame) { + return rowFrame; + } + } + return nullptr; +} + +nsTableRowFrame* +nsTableRowGroupFrame::GetLastRow() +{ + for (auto iter = mFrames.rbegin(), end = mFrames.rend(); iter != end; ++iter) { + nsTableRowFrame* rowFrame = do_QueryFrame(*iter); if (rowFrame) { return rowFrame; } diff --git a/layout/tables/nsTableRowGroupFrame.h b/layout/tables/nsTableRowGroupFrame.h index 3feb3b245471..7abdd4b74bfd 100644 --- a/layout/tables/nsTableRowGroupFrame.h +++ b/layout/tables/nsTableRowGroupFrame.h @@ -103,6 +103,7 @@ public: virtual nsIAtom* GetType() const override; nsTableRowFrame* GetFirstRow(); + nsTableRowFrame* GetLastRow(); #ifdef DEBUG_FRAME_DUMP virtual nsresult GetFrameName(nsAString& aResult) const override; diff --git a/layout/tables/nsTableWrapperFrame.h b/layout/tables/nsTableWrapperFrame.h index 73de6b604181..45d7c33e412b 100644 --- a/layout/tables/nsTableWrapperFrame.h +++ b/layout/tables/nsTableWrapperFrame.h @@ -68,6 +68,25 @@ public: virtual nscoord GetLogicalBaseline(mozilla::WritingMode aWritingMode) const override; + bool GetNaturalBaselineBOffset(mozilla::WritingMode aWM, + BaselineSharingGroup aBaselineGroup, + nscoord* aBaseline) const override + { + auto innerTable = InnerTableFrame(); + nscoord offset; + if (innerTable->GetNaturalBaselineBOffset(aWM, aBaselineGroup, &offset)) { + auto bStart = innerTable->BStart(aWM, mRect.Size()); + if (aBaselineGroup == BaselineSharingGroup::eFirst) { + *aBaseline = offset + bStart; + } else { + auto bEnd = bStart + innerTable->BSize(aWM); + *aBaseline = BSize(aWM) - (bEnd - offset); + } + return true; + } + return false; + } + virtual nscoord GetMinISize(nsRenderingContext *aRenderingContext) override; virtual nscoord GetPrefISize(nsRenderingContext *aRenderingContext) override;