1 /* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
2 /* This Source Code Form is subject to the terms of the Mozilla Public
3 * License, v. 2.0. If a copy of the MPL was not distributed with this
4 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6 #include "nsTableColFrame.h"
7 #include "nsTableFrame.h"
8 #include "nsContainerFrame.h"
9 #include "nsStyleConsts.h"
10 #include "nsPresContext.h"
11 #include "nsGkAtoms.h"
12 #include "nsCSSRendering.h"
13 #include "nsIContent.h"
14 #include "mozilla/ComputedStyle.h"
15 #include "mozilla/PresShell.h"
16 #include "mozilla/StaticPrefs_layout.h"
18 using namespace mozilla
;
20 #define COL_TYPE_BITS \
21 (NS_FRAME_STATE_BIT(28) | NS_FRAME_STATE_BIT(29) | NS_FRAME_STATE_BIT(30) | \
22 NS_FRAME_STATE_BIT(31))
23 #define COL_TYPE_OFFSET 28
25 using namespace mozilla
;
27 nsTableColFrame::nsTableColFrame(ComputedStyle
* aStyle
,
28 nsPresContext
* aPresContext
)
29 : nsSplittableFrame(aStyle
, aPresContext
, kClassID
),
35 mSpanPrefPercent(0.0f
),
38 mIStartBorderWidth(0),
40 mHasSpecifiedCoord(false) {
41 SetColType(eColContent
);
43 ResetSpanIntrinsics();
47 nsTableColFrame::~nsTableColFrame() = default;
49 nsTableColType
nsTableColFrame::GetColType() const {
50 return (nsTableColType
)((GetStateBits() & COL_TYPE_BITS
) >> COL_TYPE_OFFSET
);
53 void nsTableColFrame::SetColType(nsTableColType aType
) {
54 NS_ASSERTION(aType
!= eColAnonymousCol
||
55 (GetPrevContinuation() &&
56 GetPrevContinuation()->GetNextContinuation() == this &&
57 GetPrevContinuation()->GetNextSibling() == this),
58 "spanned content cols must be continuations");
59 uint32_t type
= aType
- eColContent
;
60 RemoveStateBits(COL_TYPE_BITS
);
61 AddStateBits(nsFrameState(type
<< COL_TYPE_OFFSET
));
65 void nsTableColFrame::DidSetComputedStyle(ComputedStyle
* aOldComputedStyle
) {
66 nsSplittableFrame::DidSetComputedStyle(aOldComputedStyle
);
68 if (!aOldComputedStyle
) // avoid this on init
71 nsTableFrame
* tableFrame
= GetTableFrame();
72 if (tableFrame
->IsBorderCollapse() &&
73 tableFrame
->BCRecalcNeeded(aOldComputedStyle
, Style())) {
74 TableArea
damageArea(GetColIndex(), 0, 1, tableFrame
->GetRowCount());
75 tableFrame
->AddBCDamageArea(damageArea
);
79 void nsTableColFrame::Reflow(nsPresContext
* aPresContext
,
80 ReflowOutput
& aDesiredSize
,
81 const ReflowInput
& aReflowInput
,
82 nsReflowStatus
& aStatus
) {
84 DO_GLOBAL_REFLOW_COUNT("nsTableColFrame");
85 DISPLAY_REFLOW(aPresContext
, this, aReflowInput
, aDesiredSize
, aStatus
);
86 MOZ_ASSERT(aStatus
.IsEmpty(), "Caller should pass a fresh reflow status!");
87 aDesiredSize
.ClearSize();
88 const nsStyleVisibility
* colVis
= StyleVisibility();
89 bool collapseCol
= StyleVisibility::Collapse
== colVis
->mVisible
;
91 GetTableFrame()->SetNeedToCollapse(true);
95 void nsTableColFrame::BuildDisplayList(nsDisplayListBuilder
* aBuilder
,
96 const nsDisplayListSet
& aLists
) {
97 // Per https://drafts.csswg.org/css-tables-3/#global-style-overrides:
98 // "All css properties of table-column and table-column-group boxes are
99 // ignored, except when explicitly specified by this specification."
100 // CSS outlines and box-shadows fall into this category, so we skip them
102 MOZ_ASSERT_UNREACHABLE("Cols don't paint themselves");
105 int32_t nsTableColFrame::GetSpan() { return StyleTable()->mXSpan
; }
108 void nsTableColFrame::Dump(int32_t aIndent
) {
109 char* indent
= new char[aIndent
+ 1];
111 for (int32_t i
= 0; i
< aIndent
+ 1; i
++) {
116 printf("%s**START COL DUMP**\n%s colIndex=%d coltype=", indent
, indent
,
118 nsTableColType colType
= GetColType();
123 case eColAnonymousCol
:
124 printf(" anonymous-column ");
126 case eColAnonymousColGroup
:
127 printf(" anonymous-colgroup ");
129 case eColAnonymousCell
:
130 printf(" anonymous-cell ");
133 printf("\nm:%d c:%d(%c) p:%f sm:%d sc:%d sp:%f f:%d", int32_t(mMinCoord
),
134 int32_t(mPrefCoord
), mHasSpecifiedCoord
? 's' : 'u', mPrefPercent
,
135 int32_t(mSpanMinCoord
), int32_t(mSpanPrefCoord
), mSpanPrefPercent
,
136 int32_t(GetFinalISize()));
137 printf("\n%s**END COL DUMP** ", indent
);
141 /* ----- global methods ----- */
143 nsTableColFrame
* NS_NewTableColFrame(PresShell
* aPresShell
,
144 ComputedStyle
* aStyle
) {
145 return new (aPresShell
) nsTableColFrame(aStyle
, aPresShell
->GetPresContext());
148 NS_IMPL_FRAMEARENA_HELPERS(nsTableColFrame
)
150 nsTableColFrame
* nsTableColFrame::GetNextCol() const {
151 nsIFrame
* childFrame
= GetNextSibling();
153 if (childFrame
->IsTableColFrame()) {
154 return (nsTableColFrame
*)childFrame
;
156 childFrame
= childFrame
->GetNextSibling();
161 #ifdef DEBUG_FRAME_DUMP
162 nsresult
nsTableColFrame::GetFrameName(nsAString
& aResult
) const {
163 return MakeFrameName(u
"TableCol"_ns
, aResult
);
167 void nsTableColFrame::InvalidateFrame(uint32_t aDisplayItemKey
,
168 bool aRebuildDisplayItems
) {
169 nsIFrame::InvalidateFrame(aDisplayItemKey
, aRebuildDisplayItems
);
170 if (GetTableFrame()->IsBorderCollapse()) {
171 const bool rebuild
= StaticPrefs::layout_display_list_retain_sc();
172 GetParent()->InvalidateFrameWithRect(InkOverflowRect() + GetPosition(),
173 aDisplayItemKey
, rebuild
);
177 void nsTableColFrame::InvalidateFrameWithRect(const nsRect
& aRect
,
178 uint32_t aDisplayItemKey
,
179 bool aRebuildDisplayItems
) {
180 nsIFrame::InvalidateFrameWithRect(aRect
, aDisplayItemKey
,
181 aRebuildDisplayItems
);
183 // If we have filters applied that would affects our bounds, then
184 // we get an inactive layer created and this is computed
185 // within FrameLayerBuilder
186 GetParent()->InvalidateFrameWithRect(aRect
+ GetPosition(), aDisplayItemKey
,
187 aRebuildDisplayItems
);