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

Unified Diff: third_party/WebKit/Source/core/layout/ng/ng_line_builder.cc

Issue 2745973002: [LayoutNG] Implement atomic inlines for LayoutNGInline (Closed)
Patch Set: WIP Created 3 years, 9 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 side-by-side diff with in-line comments
Download patch
Index: third_party/WebKit/Source/core/layout/ng/ng_line_builder.cc
diff --git a/third_party/WebKit/Source/core/layout/ng/ng_line_builder.cc b/third_party/WebKit/Source/core/layout/ng/ng_line_builder.cc
index 070fa6a6f2bee865e8a17c4e8d63e789a8ecddc1..de846ef179f1766d1e78db0945a24c4e63c80361 100644
--- a/third_party/WebKit/Source/core/layout/ng/ng_line_builder.cc
+++ b/third_party/WebKit/Source/core/layout/ng/ng_line_builder.cc
@@ -218,19 +218,28 @@ void NGLineBuilder::PlaceItems(
if (!item.GetLayoutObject())
continue;
- LayoutUnit top, height;
+ LayoutUnit top;
const ComputedStyle* style = item.Style();
if (style) {
+ DCHECK(item.GetLayoutObject()->isText());
// |InlineTextBoxPainter| sets the baseline at |top +
// ascent-of-primary-font|. Compute |top| to match.
InlineItemMetrics metrics(*style, baseline_type_);
top = estimated_baseline - LayoutUnit(metrics.ascent);
- height = LayoutUnit(metrics.ascent + metrics.descent);
+ LayoutUnit height = LayoutUnit(metrics.ascent + metrics.descent);
line_box_data.UpdateMaxAscentAndDescent(metrics);
// Take all used fonts into account if 'line-height: normal'.
if (style->lineHeight().isNegative())
AccumulateUsedFonts(item, line_item_chunk, &line_box_data);
+
+ // The direction of a fragment is the CSS direction to resolve logical
+ // properties, not the resolved bidi direction.
+ text_builder.SetDirection(style->direction())
+ .SetInlineSize(line_item_chunk.inline_size)
+ .SetInlineOverflow(line_item_chunk.inline_size)
+ .SetBlockSize(height)
+ .SetBlockOverflow(height);
} else {
LayoutObject* layout_object = item.GetLayoutObject();
if (layout_object->isOutOfFlowPositioned()) {
@@ -249,19 +258,10 @@ void NGLineBuilder::PlaceItems(
layout_object->clearNeedsLayout();
continue;
}
- DCHECK(layout_object->isAtomicInlineLevel());
- // TODO(kojii): Implement atomic inline.
- style = layout_object->style();
- top = content_size_;
+ top = PlaceAtomicInline(item, estimated_baseline, &line_box_data,
+ &text_builder);
}
- // The direction of a fragment is the CSS direction to resolve logical
- // properties, not the resolved bidi direction.
- text_builder.SetDirection(style->direction())
- .SetInlineSize(line_item_chunk.inline_size)
- .SetInlineOverflow(line_item_chunk.inline_size)
- .SetBlockSize(height)
- .SetBlockOverflow(height);
RefPtr<NGPhysicalTextFragment> text_fragment = text_builder.ToTextFragment(
line_item_chunk.index, line_item_chunk.start_offset,
line_item_chunk.end_offset);
@@ -352,6 +352,54 @@ void NGLineBuilder::AccumulateUsedFonts(const NGLayoutInlineItem& item,
}
}
+LayoutUnit NGLineBuilder::PlaceAtomicInline(const NGLayoutInlineItem& item,
+ LayoutUnit estimated_baseline,
+ LineBoxData* line_box_data,
+ NGFragmentBuilder* text_builder) {
+ LayoutObject* layout_object = item.GetLayoutObject();
+ DCHECK(layout_object && layout_object->isAtomicInlineLevel());
+ const NGLayoutResult* layout_result = item.GetLayoutResult();
+ DCHECK(layout_result);
+ RefPtr<NGPhysicalFragment> fragment = layout_result->PhysicalFragment();
+ bool is_horizontal_writing_mode =
+ IsHorizontalWritingMode(ConstraintSpace().WritingMode());
+ LayoutUnit height;
+ // TODO(kojii): Try to eliminate the text fragment and use the |fragment|
+ // directly. Currently |CopyFragmentDataToLayoutBlockFlow| requires a text
+ // fragment.
+ // TODO(kojii): Margin and border in block progression not implemented yet.
+ if (is_horizontal_writing_mode) {
+ height = fragment->Height();
+ text_builder->SetInlineSize(fragment->Width())
+ .SetInlineOverflow(fragment->WidthOverflow())
+ .SetBlockSize(height)
+ .SetBlockOverflow(fragment->HeightOverflow());
+ } else {
+ height = fragment->Width();
+ text_builder->SetInlineSize(fragment->Height())
+ .SetInlineOverflow(fragment->HeightOverflow())
+ .SetBlockSize(height)
+ .SetBlockOverflow(fragment->WidthOverflow());
+ }
+
+ // TODO(kojii): Add baseline position to NGPhysicalFragment.
+ LayoutBox* box = toLayoutBox(layout_object);
+ LineDirectionMode line_direction_mode =
+ is_horizontal_writing_mode ? LineDirectionMode::HorizontalLine
+ : LineDirectionMode::VerticalLine;
+ bool is_first_line = line_box_data_list_.size() == 1;
+ int baseline_offset =
+ box->baselinePosition(baseline_type_, is_first_line, line_direction_mode);
+ LayoutUnit top = estimated_baseline - baseline_offset;
+
+ line_box_data->max_ascent_and_leading =
+ std::max<float>(baseline_offset, line_box_data->max_ascent_and_leading);
+ line_box_data->max_descent_and_leading = std::max<float>(
+ height - baseline_offset, line_box_data->max_descent_and_leading);
+
+ return top;
+}
+
void NGLineBuilder::FindNextLayoutOpportunity() {
NGLogicalOffset iter_offset = constraint_space_->BfcOffset();
iter_offset.block_offset += content_size_;
@@ -417,8 +465,6 @@ void NGLineBuilder::CopyFragmentDataToLayoutBlockFlow() {
DCHECK(layout_object->isAtomicInlineLevel());
run =
new BidiRun(0, 1, item.BidiLevel(), LineLayoutItem(layout_object));
- // TODO(kojii): Temporarily clearNeedsLayout() for not to assert.
- layout_object->clearNeedsLayout();
}
bidi_runs.addRun(run);
fragments_for_bidi_runs.push_back(text_fragment);
@@ -443,12 +489,17 @@ void NGLineBuilder::CopyFragmentDataToLayoutBlockFlow() {
inline_box->setLogicalWidth(fragment.InlineSize());
inline_box->setLogicalLeft(fragment.InlineOffset());
inline_box->setLogicalTop(fragment.BlockOffset());
+ if (inline_box->getLineLayoutItem().isBox()) {
+ LineLayoutBox box(inline_box->getLineLayoutItem());
+ box.setLocation(inline_box->location());
+ }
run = run->next();
}
DCHECK(!run);
// Copy LineBoxData to RootInlineBox.
line_box->setLogicalWidth(line_box_data.inline_size);
+ line_box->setLogicalTop(line_box_data.top_with_leading);
LayoutUnit baseline_position =
line_box_data.top_with_leading +
LayoutUnit(line_box_data.max_ascent_and_leading);

Powered by Google App Engine
This is Rietveld 408576698