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

Side by Side Diff: third_party/WebKit/Source/core/layout/ng/inline/ng_inline_layout_algorithm.cc

Issue 2921463004: [LayoutNG] PODify NGLayoutInputNode and sub-classes. (Closed)
Patch Set: new ng-bot expectations Created 3 years, 6 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
OLDNEW
1 // Copyright 2016 The Chromium Authors. All rights reserved. 1 // Copyright 2016 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be 2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file. 3 // found in the LICENSE file.
4 4
5 #include "core/layout/ng/inline/ng_inline_layout_algorithm.h" 5 #include "core/layout/ng/inline/ng_inline_layout_algorithm.h"
6 6
7 #include "core/layout/ng/inline/ng_bidi_paragraph.h" 7 #include "core/layout/ng/inline/ng_bidi_paragraph.h"
8 #include "core/layout/ng/inline/ng_inline_break_token.h" 8 #include "core/layout/ng/inline/ng_inline_break_token.h"
9 #include "core/layout/ng/inline/ng_inline_node.h" 9 #include "core/layout/ng/inline/ng_inline_node.h"
10 #include "core/layout/ng/inline/ng_line_box_fragment.h" 10 #include "core/layout/ng/inline/ng_line_box_fragment.h"
(...skipping 22 matching lines...) Expand all
33 const NGLogicalOffset& container_bfc_offset, 33 const NGLogicalOffset& container_bfc_offset,
34 LayoutUnit content_size) { 34 LayoutUnit content_size) {
35 NGLogicalOffset origin_point = container_bfc_offset; 35 NGLogicalOffset origin_point = container_bfc_offset;
36 origin_point.block_offset += content_size; 36 origin_point.block_offset += content_size;
37 return origin_point; 37 return origin_point;
38 } 38 }
39 39
40 } // namespace 40 } // namespace
41 41
42 NGInlineLayoutAlgorithm::NGInlineLayoutAlgorithm( 42 NGInlineLayoutAlgorithm::NGInlineLayoutAlgorithm(
43 NGInlineNode* inline_node, 43 NGInlineNode inline_node,
44 NGConstraintSpace* space, 44 NGConstraintSpace* space,
45 NGInlineBreakToken* break_token) 45 NGInlineBreakToken* break_token)
46 : NGLayoutAlgorithm(inline_node, space, break_token), 46 : NGLayoutAlgorithm(inline_node, space, break_token),
47 is_horizontal_writing_mode_( 47 is_horizontal_writing_mode_(
48 blink::IsHorizontalWritingMode(space->WritingMode())), 48 blink::IsHorizontalWritingMode(space->WritingMode())),
49 disallow_first_line_rules_(false), 49 disallow_first_line_rules_(false),
50 space_builder_(space) 50 space_builder_(space) {
51 {
52 container_builder_.MutableUnpositionedFloats() = space->UnpositionedFloats(); 51 container_builder_.MutableUnpositionedFloats() = space->UnpositionedFloats();
53 52
54 // TODO(crbug.com/716930): We may be an empty LayoutInline due to splitting. 53 // TODO(crbug.com/716930): We may be an empty LayoutInline due to splitting.
55 // Only resolve our BFC offset if we know that we are non-empty as we may 54 // Only resolve our BFC offset if we know that we are non-empty as we may
56 // need to pass through our margin strut. 55 // need to pass through our margin strut.
57 if (!inline_node->Items().IsEmpty()) { 56 if (!inline_node.Items().IsEmpty()) {
58 LayoutUnit bfc_block_offset = ConstraintSpace().BfcOffset().block_offset; 57 LayoutUnit bfc_block_offset = ConstraintSpace().BfcOffset().block_offset;
59 bfc_block_offset += ConstraintSpace().MarginStrut().Sum(); 58 bfc_block_offset += ConstraintSpace().MarginStrut().Sum();
60 MaybeUpdateFragmentBfcOffset(ConstraintSpace(), bfc_block_offset, 59 MaybeUpdateFragmentBfcOffset(ConstraintSpace(), bfc_block_offset,
61 &container_builder_); 60 &container_builder_);
62 PositionPendingFloats(bfc_block_offset, &container_builder_, 61 PositionPendingFloats(bfc_block_offset, &container_builder_,
63 MutableConstraintSpace()); 62 MutableConstraintSpace());
64 } 63 }
65 64
66 if (!is_horizontal_writing_mode_) 65 if (!is_horizontal_writing_mode_)
67 baseline_type_ = FontBaseline::kIdeographicBaseline; 66 baseline_type_ = FontBaseline::kIdeographicBaseline;
68 67
69 border_and_padding_ = ComputeBorders(ConstraintSpace(), Style()) + 68 border_and_padding_ = ComputeBorders(ConstraintSpace(), Style()) +
70 ComputePadding(ConstraintSpace(), Style()); 69 ComputePadding(ConstraintSpace(), Style());
71 70
72 if (break_token) { 71 if (break_token) {
73 // If a break_token is given, we're re-starting layout for 2nd or later 72 // If a break_token is given, we're re-starting layout for 2nd or later
74 // lines, and that the first line we create should not use the first line 73 // lines, and that the first line we create should not use the first line
75 // rules. 74 // rules.
76 DCHECK(!break_token->IsFinished()); 75 DCHECK(!break_token->IsFinished());
77 DCHECK(break_token->TextOffset() || break_token->ItemIndex()); 76 DCHECK(break_token->TextOffset() || break_token->ItemIndex());
78 disallow_first_line_rules_ = true; 77 disallow_first_line_rules_ = true;
79 } else { 78 } else {
80 auto& engine = Node()->GetLayoutObject()->GetDocument().GetStyleEngine(); 79 auto& engine = Node().GetLayoutObject()->GetDocument().GetStyleEngine();
81 disallow_first_line_rules_ = !engine.UsesFirstLineRules(); 80 disallow_first_line_rules_ = !engine.UsesFirstLineRules();
82 } 81 }
83 82
84 FindNextLayoutOpportunity(); 83 FindNextLayoutOpportunity();
85 } 84 }
86 85
87 bool NGInlineLayoutAlgorithm::IsFirstLine() const { 86 bool NGInlineLayoutAlgorithm::IsFirstLine() const {
88 return !disallow_first_line_rules_ && container_builder_.Children().IsEmpty(); 87 return !disallow_first_line_rules_ && container_builder_.Children().IsEmpty();
89 } 88 }
90 89
91 const ComputedStyle& NGInlineLayoutAlgorithm::FirstLineStyle() const { 90 const ComputedStyle& NGInlineLayoutAlgorithm::FirstLineStyle() const {
92 return Node()->GetLayoutObject()->FirstLineStyleRef(); 91 return Node().GetLayoutObject()->FirstLineStyleRef();
93 } 92 }
94 93
95 const ComputedStyle& NGInlineLayoutAlgorithm::LineStyle() const { 94 const ComputedStyle& NGInlineLayoutAlgorithm::LineStyle() const {
96 return IsFirstLine() ? FirstLineStyle() : Style(); 95 return IsFirstLine() ? FirstLineStyle() : Style();
97 } 96 }
98 97
99 LayoutUnit NGInlineLayoutAlgorithm::AvailableWidth() const { 98 LayoutUnit NGInlineLayoutAlgorithm::AvailableWidth() const {
100 return current_opportunity_.InlineSize(); 99 return current_opportunity_.InlineSize();
101 } 100 }
102 101
103 // The offset of 'line-left' side. 102 // The offset of 'line-left' side.
104 // https://drafts.csswg.org/css-writing-modes/#line-left 103 // https://drafts.csswg.org/css-writing-modes/#line-left
105 LayoutUnit NGInlineLayoutAlgorithm::LogicalLeftOffset() const { 104 LayoutUnit NGInlineLayoutAlgorithm::LogicalLeftOffset() const {
106 // TODO(kojii): We need to convert 'line start' to 'line left'. They're 105 // TODO(kojii): We need to convert 'line start' to 'line left'. They're
107 // different in RTL. Maybe there are more where start and left are misused. 106 // different in RTL. Maybe there are more where start and left are misused.
108 return current_opportunity_.InlineStartOffset() - 107 return current_opportunity_.InlineStartOffset() -
109 ConstraintSpace().BfcOffset().inline_offset; 108 ConstraintSpace().BfcOffset().inline_offset;
110 } 109 }
111 110
112 bool NGInlineLayoutAlgorithm::CreateLine( 111 bool NGInlineLayoutAlgorithm::CreateLine(
113 NGInlineItemResults* item_results, 112 NGInlineItemResults* item_results,
114 RefPtr<NGInlineBreakToken> break_token) { 113 RefPtr<NGInlineBreakToken> break_token) {
115 if (Node()->IsBidiEnabled()) 114 if (Node().IsBidiEnabled())
116 BidiReorder(item_results); 115 BidiReorder(item_results);
117 116
118 if (!PlaceItems(item_results, break_token)) 117 if (!PlaceItems(item_results, break_token))
119 return false; 118 return false;
120 119
121 // Prepare for the next line. 120 // Prepare for the next line.
122 NGLogicalOffset origin_point = 121 NGLogicalOffset origin_point =
123 GetOriginPointForFloats(ContainerBfcOffset(), content_size_); 122 GetOriginPointForFloats(ContainerBfcOffset(), content_size_);
124 PositionPendingFloats(origin_point.block_offset, &container_builder_, 123 PositionPendingFloats(origin_point.block_offset, &container_builder_,
125 MutableConstraintSpace()); 124 MutableConstraintSpace());
126 FindNextLayoutOpportunity(); 125 FindNextLayoutOpportunity();
127 return true; 126 return true;
128 } 127 }
129 128
130 void NGInlineLayoutAlgorithm::BidiReorder(NGInlineItemResults* line_items) { 129 void NGInlineLayoutAlgorithm::BidiReorder(NGInlineItemResults* line_items) {
131 // TODO(kojii): UAX#9 L1 is not supported yet. Supporting L1 may change 130 // TODO(kojii): UAX#9 L1 is not supported yet. Supporting L1 may change
132 // embedding levels of parts of runs, which requires to split items. 131 // embedding levels of parts of runs, which requires to split items.
133 // http://unicode.org/reports/tr9/#L1 132 // http://unicode.org/reports/tr9/#L1
134 // BidiResolver does not support L1 crbug.com/316409. 133 // BidiResolver does not support L1 crbug.com/316409.
135 134
136 // Create a list of chunk indices in the visual order. 135 // Create a list of chunk indices in the visual order.
137 // ICU |ubidi_getVisualMap()| works for a run of characters. Since we can 136 // ICU |ubidi_getVisualMap()| works for a run of characters. Since we can
138 // handle the direction of each run, we use |ubidi_reorderVisual()| to reorder 137 // handle the direction of each run, we use |ubidi_reorderVisual()| to reorder
139 // runs instead of characters. 138 // runs instead of characters.
140 Vector<UBiDiLevel, 32> levels; 139 Vector<UBiDiLevel, 32> levels;
141 levels.ReserveInitialCapacity(line_items->size()); 140 levels.ReserveInitialCapacity(line_items->size());
142 const Vector<NGInlineItem>& items = Node()->Items(); 141 const Vector<NGInlineItem>& items = Node().Items();
143 for (const auto& item_result : *line_items) 142 for (const auto& item_result : *line_items)
144 levels.push_back(items[item_result.item_index].BidiLevel()); 143 levels.push_back(items[item_result.item_index].BidiLevel());
145 Vector<int32_t, 32> indices_in_visual_order(line_items->size()); 144 Vector<int32_t, 32> indices_in_visual_order(line_items->size());
146 NGBidiParagraph::IndicesInVisualOrder(levels, &indices_in_visual_order); 145 NGBidiParagraph::IndicesInVisualOrder(levels, &indices_in_visual_order);
147 146
148 // Reorder to the visual order. 147 // Reorder to the visual order.
149 NGInlineItemResults line_items_in_visual_order(line_items->size()); 148 NGInlineItemResults line_items_in_visual_order(line_items->size());
150 for (unsigned visual_index = 0; visual_index < indices_in_visual_order.size(); 149 for (unsigned visual_index = 0; visual_index < indices_in_visual_order.size();
151 visual_index++) { 150 visual_index++) {
152 unsigned logical_index = indices_in_visual_order[visual_index]; 151 unsigned logical_index = indices_in_visual_order[visual_index];
(...skipping 17 matching lines...) Expand all
170 } 169 }
171 } 170 }
172 171
173 line_items->swap(line_items_in_visual_order); 172 line_items->swap(line_items_in_visual_order);
174 } 173 }
175 174
176 // TODO(glebl): Add the support of clearance for inline floats. 175 // TODO(glebl): Add the support of clearance for inline floats.
177 void NGInlineLayoutAlgorithm::LayoutAndPositionFloat( 176 void NGInlineLayoutAlgorithm::LayoutAndPositionFloat(
178 LayoutUnit end_position, 177 LayoutUnit end_position,
179 LayoutObject* layout_object) { 178 LayoutObject* layout_object) {
180 NGBlockNode* node = new NGBlockNode(layout_object); 179 NGBlockNode node(ToLayoutBox(layout_object));
181 180
182 NGLogicalOffset origin_offset = 181 NGLogicalOffset origin_offset =
183 GetOriginPointForFloats(ContainerBfcOffset(), content_size_); 182 GetOriginPointForFloats(ContainerBfcOffset(), content_size_);
184 const ComputedStyle& float_style = node->Style(); 183 const ComputedStyle& float_style = node.Style();
185 NGBoxStrut margins = ComputeMargins(ConstraintSpace(), float_style, 184 NGBoxStrut margins = ComputeMargins(ConstraintSpace(), float_style,
186 ConstraintSpace().WritingMode(), 185 ConstraintSpace().WritingMode(),
187 ConstraintSpace().Direction()); 186 ConstraintSpace().Direction());
188 187
189 // TODO(ikilpatrick): Add support for float break tokens inside an inline 188 // TODO(ikilpatrick): Add support for float break tokens inside an inline
190 // layout context. 189 // layout context.
191 RefPtr<NGUnpositionedFloat> unpositioned_float = NGUnpositionedFloat::Create( 190 RefPtr<NGUnpositionedFloat> unpositioned_float = NGUnpositionedFloat::Create(
192 current_opportunity_.size, ConstraintSpace().PercentageResolutionSize(), 191 current_opportunity_.size, ConstraintSpace().PercentageResolutionSize(),
193 origin_offset, ContainerBfcOffset(), margins, node, 192 origin_offset, ContainerBfcOffset(), margins, node,
194 /* break_token */ nullptr); 193 /* break_token */ nullptr);
(...skipping 13 matching lines...) Expand all
208 } else { 207 } else {
209 container_builder_.AddPositionedFloat( 208 container_builder_.AddPositionedFloat(
210 PositionFloat(unpositioned_float.Get(), MutableConstraintSpace())); 209 PositionFloat(unpositioned_float.Get(), MutableConstraintSpace()));
211 FindNextLayoutOpportunity(); 210 FindNextLayoutOpportunity();
212 } 211 }
213 } 212 }
214 213
215 bool NGInlineLayoutAlgorithm::PlaceItems( 214 bool NGInlineLayoutAlgorithm::PlaceItems(
216 NGInlineItemResults* line_items, 215 NGInlineItemResults* line_items,
217 RefPtr<NGInlineBreakToken> break_token) { 216 RefPtr<NGInlineBreakToken> break_token) {
218 const Vector<NGInlineItem>& items = Node()->Items(); 217 const Vector<NGInlineItem>& items = Node().Items();
219 218
220 const ComputedStyle& line_style = LineStyle(); 219 const ComputedStyle& line_style = LineStyle();
221 NGLineHeightMetrics line_metrics(line_style, baseline_type_); 220 NGLineHeightMetrics line_metrics(line_style, baseline_type_);
222 NGLineHeightMetrics line_metrics_with_leading = line_metrics; 221 NGLineHeightMetrics line_metrics_with_leading = line_metrics;
223 line_metrics_with_leading.AddLeading(line_style.ComputedLineHeightAsFixed()); 222 line_metrics_with_leading.AddLeading(line_style.ComputedLineHeightAsFixed());
224 NGLineBoxFragmentBuilder line_box(Node()); 223 NGLineBoxFragmentBuilder line_box(Node());
225 line_box.SetWritingMode(ConstraintSpace().WritingMode()); 224 line_box.SetWritingMode(ConstraintSpace().WritingMode());
226 225
227 // Compute heights of all inline items by placing the dominant baseline at 0. 226 // Compute heights of all inline items by placing the dominant baseline at 0.
228 // The baseline is adjusted after the height of the line box is computed. 227 // The baseline is adjusted after the height of the line box is computed.
(...skipping 49 matching lines...) Expand 10 before | Expand all | Expand 10 after
278 } else if (item.Type() == NGInlineItem::kAtomicInline) { 277 } else if (item.Type() == NGInlineItem::kAtomicInline) {
279 box = PlaceAtomicInline(item, &item_result, position, &line_box, 278 box = PlaceAtomicInline(item, &item_result, position, &line_box,
280 &text_builder); 279 &text_builder);
281 } else if (item.Type() == NGInlineItem::kOutOfFlowPositioned) { 280 } else if (item.Type() == NGInlineItem::kOutOfFlowPositioned) {
282 // TODO(layout-dev): Report the correct static position for the out of 281 // TODO(layout-dev): Report the correct static position for the out of
283 // flow descendant. We can't do this here yet as it doesn't know the 282 // flow descendant. We can't do this here yet as it doesn't know the
284 // size of the line box. 283 // size of the line box.
285 container_builder_.AddOutOfFlowDescendant( 284 container_builder_.AddOutOfFlowDescendant(
286 // Absolute positioning blockifies the box's display type. 285 // Absolute positioning blockifies the box's display type.
287 // https://drafts.csswg.org/css-display/#transformations 286 // https://drafts.csswg.org/css-display/#transformations
288 new NGBlockNode(item.GetLayoutObject()), 287 NGBlockNode(ToLayoutBox(item.GetLayoutObject())),
289 NGStaticPosition::Create(ConstraintSpace().WritingMode(), 288 NGStaticPosition::Create(ConstraintSpace().WritingMode(),
290 ConstraintSpace().Direction(), 289 ConstraintSpace().Direction(),
291 NGPhysicalOffset())); 290 NGPhysicalOffset()));
292 continue; 291 continue;
293 } else { 292 } else {
294 continue; 293 continue;
295 } 294 }
296 295
297 position += item_result.inline_size; 296 position += item_result.inline_size;
298 } 297 }
(...skipping 157 matching lines...) Expand 10 before | Expand all | Expand 10 after
456 // Margin struts shouldn't need to be passed through like this once we've 455 // Margin struts shouldn't need to be passed through like this once we've
457 // removed LayoutInline splitting. 456 // removed LayoutInline splitting.
458 if (!container_builder_.BfcOffset()) { 457 if (!container_builder_.BfcOffset()) {
459 container_builder_.SetEndMarginStrut(ConstraintSpace().MarginStrut()); 458 container_builder_.SetEndMarginStrut(ConstraintSpace().MarginStrut());
460 } 459 }
461 460
462 return container_builder_.ToBoxFragment(); 461 return container_builder_.ToBoxFragment();
463 } 462 }
464 463
465 } // namespace blink 464 } // namespace blink
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698