OLD | NEW |
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 10 matching lines...) Expand all Loading... |
21 * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT | 21 * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT |
22 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE | 22 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE |
23 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. | 23 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. |
24 */ | 24 */ |
25 | 25 |
26 | 26 |
27 #ifndef RenderMultiColumnFlowThread_h | 27 #ifndef RenderMultiColumnFlowThread_h |
28 #define RenderMultiColumnFlowThread_h | 28 #define RenderMultiColumnFlowThread_h |
29 | 29 |
30 #include "core/rendering/RenderFlowThread.h" | 30 #include "core/rendering/RenderFlowThread.h" |
31 #include "wtf/HashMap.h" | |
32 | 31 |
33 namespace blink { | 32 namespace blink { |
34 | 33 |
35 class RenderMultiColumnSet; | 34 class RenderMultiColumnSet; |
36 class RenderMultiColumnSpannerSet; | 35 class RenderMultiColumnSpannerPlaceholder; |
37 | 36 |
38 // Flow thread implementation for CSS multicol. This will be inserted as an anon
ymous child block of | 37 // Flow thread implementation for CSS multicol. This will be inserted as an anon
ymous child block of |
39 // the actual multicol container (i.e. the RenderBlockFlow whose style computes
to non-auto | 38 // the actual multicol container (i.e. the RenderBlockFlow whose style computes
to non-auto |
40 // column-count and/or column-width). RenderMultiColumnFlowThread is the heart o
f the multicol | 39 // column-count and/or column-width). RenderMultiColumnFlowThread is the heart o
f the multicol |
41 // implementation, and there is only one instance per multicol container. Child
content of the | 40 // implementation, and there is only one instance per multicol container. Child
content of the |
42 // multicol container is parented into the flow thread at the time of renderer i
nsertion. | 41 // multicol container is parented into the flow thread at the time of renderer i
nsertion. |
43 // | 42 // |
44 // Apart from this flow thread child, the multicol container will also have Rend
erMultiColumnSet | 43 // Apart from this flow thread child, the multicol container will also have Rend
erMultiColumnSet |
45 // "region" children, which are used to position the columns visually. The flow
thread is in charge | 44 // "region" children, which are used to position the columns visually. The flow
thread is in charge |
46 // of layout, and, after having calculated the column width, it lays out content
as if everything | 45 // of layout, and, after having calculated the column width, it lays out content
as if everything |
47 // were in one tall single column, except that there will typically be some amou
nt of blank space | 46 // were in one tall single column, except that there will typically be some amou
nt of blank space |
48 // (also known as pagination struts) at the offsets where the actual column boun
daries are. This | 47 // (also known as pagination struts) at the offsets where the actual column boun
daries are. This |
49 // way, content that needs to be preceded by a break will appear at the top of t
he next | 48 // way, content that needs to be preceded by a break will appear at the top of t
he next |
50 // column. Content needs to be preceded by a break when there's a forced break o
r when the content | 49 // column. Content needs to be preceded by a break when there's a forced break o
r when the content |
51 // is unbreakable and cannot fully fit in the same column as the preceding piece
of | 50 // is unbreakable and cannot fully fit in the same column as the preceding piece
of |
52 // content. Although a RenderMultiColumnFlowThread is laid out, it does not take
up any space in its | 51 // content. Although a RenderMultiColumnFlowThread is laid out, it does not take
up any space in its |
53 // container. It's the RenderMultiColumnSet objects that take up the necessary a
mount of space, and | 52 // container. It's the RenderMultiColumnSet objects that take up the necessary a
mount of space, and |
54 // make sure that the columns are painted and hit-tested correctly. | 53 // make sure that the columns are painted and hit-tested correctly. |
55 // | 54 // |
56 // If there is any column content inside the multicol container, we create a | 55 // If there is any column content inside the multicol container, we create a |
57 // RenderMultiColumnSet. We only need to create multiple sets if there are spann
ers | 56 // RenderMultiColumnSet. We only need to create multiple sets if there are spann
ers |
58 // (column-span:all) in the multicol container. When a spanner is inserted, cont
ent preceding it | 57 // (column-span:all) in the multicol container. When a spanner is inserted, cont
ent preceding it |
59 // gets its own set, and content succeeding it will get another set. The spanner
itself will also | 58 // gets its own set, and content succeeding it will get another set. The spanner
itself will also |
60 // get its own set (RenderMultiColumnSpannerSet). | 59 // get its own placeholder between the sets (RenderMultiColumnSpannerPlaceholder
), so that it gets |
| 60 // positioned and sized correctly. The column-span:all element is inside the flo
w thread, but its |
| 61 // containing block is the multicol container. |
61 // | 62 // |
62 // The width of the flow thread is the same as the column width. The width of a
column set is the | 63 // The width of the flow thread is the same as the column width. The width of a
column set is the |
63 // same as the content box width of the multicol container; in other words exact
ly enough to hold | 64 // same as the content box width of the multicol container; in other words exact
ly enough to hold |
64 // the number of columns to be used, stacked horizontally, plus column gaps betw
een them. | 65 // the number of columns to be used, stacked horizontally, plus column gaps betw
een them. |
65 // | 66 // |
66 // Since it's the first child of the multicol container, the flow thread is laid
out first, albeit | 67 // Since it's the first child of the multicol container, the flow thread is laid
out first, albeit |
67 // in a slightly special way, since it's not to take up any space in its ancesto
rs. Afterwards, the | 68 // in a slightly special way, since it's not to take up any space in its ancesto
rs. Afterwards, the |
68 // column sets are laid out. Column sets get their height from the columns that
they hold. In single | 69 // column sets are laid out. Column sets get their height from the columns that
they hold. In single |
69 // column-row constrained height non-balancing cases without spanners this will
simply be the same | 70 // column-row constrained height non-balancing cases without spanners this will
simply be the same |
70 // as the content height of the multicol container itself. In most other cases w
e'll have to | 71 // as the content height of the multicol container itself. In most other cases w
e'll have to |
(...skipping 28 matching lines...) Expand all Loading... |
99 | 100 |
100 static RenderMultiColumnFlowThread* createAnonymous(Document&, RenderStyle*
parentStyle); | 101 static RenderMultiColumnFlowThread* createAnonymous(Document&, RenderStyle*
parentStyle); |
101 | 102 |
102 virtual bool isRenderMultiColumnFlowThread() const override final { return t
rue; } | 103 virtual bool isRenderMultiColumnFlowThread() const override final { return t
rue; } |
103 | 104 |
104 RenderBlockFlow* multiColumnBlockFlow() const { return toRenderBlockFlow(par
ent()); } | 105 RenderBlockFlow* multiColumnBlockFlow() const { return toRenderBlockFlow(par
ent()); } |
105 | 106 |
106 RenderMultiColumnSet* firstMultiColumnSet() const; | 107 RenderMultiColumnSet* firstMultiColumnSet() const; |
107 RenderMultiColumnSet* lastMultiColumnSet() const; | 108 RenderMultiColumnSet* lastMultiColumnSet() const; |
108 | 109 |
109 // Return the spanner set (if any) that contains the specified renderer. Thi
s includes the | 110 // Return the first column set or spanner placeholder. |
110 // renderer for the element that actually establishes the spanner too. | 111 RenderBox* firstMultiColumnBox() const |
111 RenderMultiColumnSpannerSet* containingColumnSpannerSet(const RenderObject*
descendant) const; | 112 { |
| 113 return nextSiblingBox(); |
| 114 } |
| 115 // Return the last column set or spanner placeholder. |
| 116 RenderBox* lastMultiColumnBox() const |
| 117 { |
| 118 RenderBox* lastSiblingBox = multiColumnBlockFlow()->lastChildBox(); |
| 119 // The flow thread is the first child of the multicol container. If the
flow thread is also |
| 120 // the last child, it means that there are no siblings; i.e. we have no
column boxes. |
| 121 return lastSiblingBox != this ? lastSiblingBox : 0; |
| 122 } |
| 123 |
| 124 // Return the spanner placeholder that belongs to the spanner in the contain
ing block chain, if |
| 125 // any. This includes the renderer for the element that actually establishes
the spanner too. |
| 126 RenderMultiColumnSpannerPlaceholder* containingColumnSpannerPlaceholder(cons
t RenderObject* descendant) const; |
112 | 127 |
113 // Populate the flow thread with what's currently its siblings. Called when
a regular block | 128 // Populate the flow thread with what's currently its siblings. Called when
a regular block |
114 // becomes a multicol container. | 129 // becomes a multicol container. |
115 void populate(); | 130 void populate(); |
116 | 131 |
117 // Empty the flow thread by moving everything to the parent. Remove all mult
icol specific | 132 // Empty the flow thread by moving everything to the parent. Remove all mult
icol specific |
118 // renderers. Then destroy the flow thread. Called when a multicol container
becomes a regular | 133 // renderers. Then destroy the flow thread. Called when a multicol container
becomes a regular |
119 // block. | 134 // block. |
120 void evacuateAndDestroy(); | 135 void evacuateAndDestroy(); |
121 | 136 |
(...skipping 14 matching lines...) Expand all Loading... |
136 | 151 |
137 protected: | 152 protected: |
138 RenderMultiColumnFlowThread(); | 153 RenderMultiColumnFlowThread(); |
139 void setProgressionIsInline(bool isInline) { m_progressionIsInline = isInlin
e; } | 154 void setProgressionIsInline(bool isInline) { m_progressionIsInline = isInlin
e; } |
140 | 155 |
141 virtual void layout() override; | 156 virtual void layout() override; |
142 | 157 |
143 private: | 158 private: |
144 void calculateColumnCountAndWidth(LayoutUnit& width, unsigned& count) const; | 159 void calculateColumnCountAndWidth(LayoutUnit& width, unsigned& count) const; |
145 void createAndInsertMultiColumnSet(); | 160 void createAndInsertMultiColumnSet(); |
146 void createAndInsertSpannerSet(RenderBox* spanner); | 161 void createAndInsertSpannerPlaceholder(RenderBox* spanner); |
147 virtual bool descendantIsValidColumnSpanner(RenderObject* descendant) const; | 162 virtual bool descendantIsValidColumnSpanner(RenderObject* descendant) const; |
148 | 163 |
149 virtual const char* renderName() const override; | 164 virtual const char* renderName() const override; |
150 virtual void addRegionToThread(RenderMultiColumnSet*) override; | 165 virtual void addRegionToThread(RenderMultiColumnSet*) override; |
151 virtual void willBeRemovedFromTree() override; | 166 virtual void willBeRemovedFromTree() override; |
152 virtual void flowThreadDescendantWasInserted(RenderObject*) override; | 167 virtual void flowThreadDescendantWasInserted(RenderObject*) override; |
| 168 virtual void flowThreadDescendantWillBeRemoved(RenderObject*) override; |
153 virtual void computeLogicalHeight(LayoutUnit logicalHeight, LayoutUnit logic
alTop, LogicalExtentComputedValues&) const override; | 169 virtual void computeLogicalHeight(LayoutUnit logicalHeight, LayoutUnit logic
alTop, LogicalExtentComputedValues&) const override; |
154 virtual void updateLogicalWidth() override; | 170 virtual void updateLogicalWidth() override; |
155 virtual void setPageBreak(LayoutUnit offset, LayoutUnit spaceShortage) overr
ide; | 171 virtual void setPageBreak(LayoutUnit offset, LayoutUnit spaceShortage) overr
ide; |
156 virtual void updateMinimumPageHeight(LayoutUnit offset, LayoutUnit minHeight
) override; | 172 virtual void updateMinimumPageHeight(LayoutUnit offset, LayoutUnit minHeight
) override; |
157 virtual RenderMultiColumnSet* columnSetAtBlockOffset(LayoutUnit) const overr
ide; | 173 virtual RenderMultiColumnSet* columnSetAtBlockOffset(LayoutUnit) const overr
ide; |
158 virtual bool addForcedRegionBreak(LayoutUnit, RenderObject* breakChild, bool
isBefore, LayoutUnit* offsetBreakAdjustment = 0) override; | 174 virtual bool addForcedRegionBreak(LayoutUnit, RenderObject* breakChild, bool
isBefore, LayoutUnit* offsetBreakAdjustment = 0) override; |
159 virtual bool isPageLogicalHeightKnown() const override; | 175 virtual bool isPageLogicalHeightKnown() const override; |
160 | 176 |
161 typedef HashMap<const RenderObject*, RenderMultiColumnSpannerSet*> SpannerMa
p; | |
162 SpannerMap m_spannerMap; | |
163 | |
164 unsigned m_columnCount; // The used value of column-count | 177 unsigned m_columnCount; // The used value of column-count |
165 LayoutUnit m_columnHeightAvailable; // Total height available to columns, or
0 if auto. | 178 LayoutUnit m_columnHeightAvailable; // Total height available to columns, or
0 if auto. |
166 bool m_inBalancingPass; // Set when relayouting for column balancing. | 179 bool m_inBalancingPass; // Set when relayouting for column balancing. |
167 bool m_needsColumnHeightsRecalculation; // Set when we need to recalculate t
he column set heights after layout. | 180 bool m_needsColumnHeightsRecalculation; // Set when we need to recalculate t
he column set heights after layout. |
168 bool m_progressionIsInline; // Always true for regular multicol. False for p
aged-y overflow. | 181 bool m_progressionIsInline; // Always true for regular multicol. False for p
aged-y overflow. |
| 182 bool m_isBeingEvacuated; |
169 }; | 183 }; |
170 | 184 |
171 } // namespace blink | 185 } // namespace blink |
172 | 186 |
173 #endif // RenderMultiColumnFlowThread_h | 187 #endif // RenderMultiColumnFlowThread_h |
174 | |
OLD | NEW |