OLD | NEW |
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/ng_box.h" | 5 #include "core/layout/ng/ng_box.h" |
6 | 6 |
7 #include "core/layout/LayoutObject.h" | 7 #include "core/layout/LayoutObject.h" |
8 #include "core/layout/ng/layout_ng_block_flow.h" | 8 #include "core/layout/ng/layout_ng_block_flow.h" |
9 #include "core/layout/ng/ng_block_layout_algorithm.h" | 9 #include "core/layout/ng/ng_block_layout_algorithm.h" |
10 #include "core/layout/ng/ng_box_iterator.h" | |
11 #include "core/layout/ng/ng_constraint_space.h" | 10 #include "core/layout/ng/ng_constraint_space.h" |
12 #include "core/layout/ng/ng_fragment.h" | 11 #include "core/layout/ng/ng_fragment.h" |
13 #include "core/layout/ng/ng_fragment_builder.h" | 12 #include "core/layout/ng/ng_fragment_builder.h" |
14 #include "core/layout/ng/ng_writing_mode.h" | 13 #include "core/layout/ng/ng_writing_mode.h" |
15 #include "core/layout/LayoutBlockFlow.h" | 14 #include "core/layout/LayoutBlockFlow.h" |
16 #include "core/layout/LayoutBox.h" | 15 #include "core/layout/LayoutBox.h" |
17 | 16 |
18 namespace blink { | 17 namespace blink { |
| 18 NGBox::NGBox(LayoutObject* layout_object) |
| 19 : layout_box_(toLayoutBox(layout_object)) { |
| 20 DCHECK(layout_box_); |
| 21 } |
19 | 22 |
20 bool NGBox::Layout(const NGConstraintSpace* constraint_space, | 23 bool NGBox::Layout(const NGConstraintSpace* constraint_space, |
21 NGFragment** out) { | 24 NGFragment** out) { |
22 // We can either use the new layout code to do the layout and then copy the | 25 // We can either use the new layout code to do the layout and then copy the |
23 // resulting size to the LayoutObject, or use the old layout code and | 26 // resulting size to the LayoutObject, or use the old layout code and |
24 // synthesize a fragment. | 27 // synthesize a fragment. |
25 NGFragment* fragment = nullptr; | 28 NGFragment* fragment = nullptr; |
26 if (canUseNewLayout()) { | 29 if (CanUseNewLayout()) { |
27 NGBlockLayoutAlgorithm algorithm(style(), childIterator()); | 30 if (!algorithm_) |
28 | 31 algorithm_ = new NGBlockLayoutAlgorithm(Style(), FirstChild()); |
29 // Change the coordinate system of the constraint space. | 32 // Change the coordinate system of the constraint space. |
30 NGConstraintSpace* child_constraint_space = new NGConstraintSpace( | 33 NGConstraintSpace* child_constraint_space = new NGConstraintSpace( |
31 FromPlatformWritingMode(style()->getWritingMode()), constraint_space); | 34 FromPlatformWritingMode(Style()->getWritingMode()), constraint_space); |
32 | 35 |
33 if (!algorithm.Layout(child_constraint_space, &fragment)) | 36 if (!algorithm_->Layout(child_constraint_space, &fragment)) |
34 return false; | 37 return false; |
35 m_layoutBox->setLogicalWidth(fragment->InlineSize()); | 38 layout_box_->setLogicalWidth(fragment->InlineSize()); |
36 m_layoutBox->setLogicalHeight(fragment->BlockSize()); | 39 layout_box_->setLogicalHeight(fragment->BlockSize()); |
37 if (m_layoutBox->isLayoutBlock()) | 40 if (layout_box_->isLayoutBlock()) |
38 toLayoutBlock(m_layoutBox)->layoutPositionedObjects(true); | 41 toLayoutBlock(layout_box_)->layoutPositionedObjects(true); |
39 m_layoutBox->clearNeedsLayout(); | 42 layout_box_->clearNeedsLayout(); |
40 } else { | 43 } else { |
41 // TODO(layout-ng): If fixedSize is true, set the override width/height too | 44 // TODO(layout-ng): If fixedSize is true, set the override width/height too |
42 NGLogicalSize container_size = constraint_space->ContainerSize(); | 45 NGLogicalSize container_size = constraint_space->ContainerSize(); |
43 m_layoutBox->setOverrideContainingBlockContentLogicalWidth( | 46 layout_box_->setOverrideContainingBlockContentLogicalWidth( |
44 container_size.inline_size); | 47 container_size.inline_size); |
45 m_layoutBox->setOverrideContainingBlockContentLogicalHeight( | 48 layout_box_->setOverrideContainingBlockContentLogicalHeight( |
46 container_size.block_size); | 49 container_size.block_size); |
47 if (m_layoutBox->isLayoutNGBlockFlow() && m_layoutBox->needsLayout()) { | 50 if (layout_box_->isLayoutNGBlockFlow() && layout_box_->needsLayout()) { |
48 toLayoutNGBlockFlow(m_layoutBox)->LayoutBlockFlow::layoutBlock(true); | 51 toLayoutNGBlockFlow(layout_box_)->LayoutBlockFlow::layoutBlock(true); |
49 } else { | 52 } else { |
50 m_layoutBox->layoutIfNeeded(); | 53 layout_box_->layoutIfNeeded(); |
51 } | 54 } |
52 LayoutRect overflow = m_layoutBox->layoutOverflowRect(); | 55 LayoutRect overflow = layout_box_->layoutOverflowRect(); |
53 // TODO(layout-ng): This does not handle writing modes correctly (for | 56 // TODO(layout-ng): This does not handle writing modes correctly (for |
54 // overflow & the enums) | 57 // overflow & the enums) |
55 NGFragmentBuilder builder(NGFragmentBase::FragmentBox); | 58 NGFragmentBuilder builder(NGFragmentBase::FragmentBox); |
56 builder.SetInlineSize(m_layoutBox->logicalWidth()) | 59 builder.SetInlineSize(layout_box_->logicalWidth()) |
57 .SetBlockSize(m_layoutBox->logicalHeight()) | 60 .SetBlockSize(layout_box_->logicalHeight()) |
58 .SetInlineOverflow(overflow.width()) | 61 .SetInlineOverflow(overflow.width()) |
59 .SetBlockOverflow(overflow.height()); | 62 .SetBlockOverflow(overflow.height()); |
60 fragment = builder.ToFragment(); | 63 fragment = builder.ToFragment(); |
61 } | 64 } |
62 *out = fragment; | 65 *out = fragment; |
| 66 // Reset algorithm for future use |
| 67 algorithm_ = nullptr; |
63 return true; | 68 return true; |
64 } | 69 } |
65 | 70 |
66 const ComputedStyle* NGBox::style() const { | 71 const ComputedStyle* NGBox::Style() const { |
67 return m_layoutBox->style(); | 72 return layout_box_->style(); |
68 } | 73 } |
69 | 74 |
70 NGBoxIterator NGBox::childIterator() { | 75 NGBox* NGBox::NextSibling() const { |
71 return NGBoxIterator(firstChild()); | 76 LayoutObject* next_sibling = layout_box_->nextSibling(); |
| 77 return next_sibling ? new NGBox(next_sibling) : nullptr; |
72 } | 78 } |
73 | 79 |
74 NGBox NGBox::nextSibling() const { | 80 NGBox* NGBox::FirstChild() const { |
75 return m_layoutBox ? NGBox(m_layoutBox->nextSibling()) : NGBox(); | 81 LayoutObject* child = layout_box_->slowFirstChild(); |
| 82 return child ? new NGBox(child) : nullptr; |
76 } | 83 } |
77 | 84 |
78 NGBox NGBox::firstChild() const { | 85 void NGBox::PositionUpdated(const NGFragment& fragment) { |
79 return m_layoutBox ? NGBox(m_layoutBox->slowFirstChild()) : NGBox(); | 86 layout_box_->setLogicalLeft(fragment.InlineOffset()); |
| 87 layout_box_->setLogicalTop(fragment.BlockOffset()); |
80 } | 88 } |
81 | 89 |
82 void NGBox::positionUpdated(const NGFragment& fragment) { | 90 bool NGBox::CanUseNewLayout() { |
83 m_layoutBox->setLogicalLeft(fragment.InlineOffset()); | 91 if (!layout_box_) |
84 m_layoutBox->setLogicalTop(fragment.BlockOffset()); | |
85 } | |
86 | |
87 bool NGBox::canUseNewLayout() { | |
88 if (!m_layoutBox) | |
89 return true; | 92 return true; |
90 if (m_layoutBox->isLayoutBlockFlow() && !m_layoutBox->childrenInline()) | 93 if (layout_box_->isLayoutBlockFlow() && !layout_box_->childrenInline()) |
91 return true; | 94 return true; |
92 return false; | 95 return false; |
93 } | 96 } |
94 } // namespace blink | 97 } // namespace blink |
OLD | NEW |