diff options
author | Moonchild <moonchild@palemoon.org> | 2020-10-03 12:45:27 +0000 |
---|---|---|
committer | Moonchild <moonchild@palemoon.org> | 2020-10-06 09:31:40 +0000 |
commit | abf1d5a099ea8c3fbd6912ff7b199791994cb932 (patch) | |
tree | cba4982ed3a2bc5edf4e4b7a83540c3319480bf0 | |
parent | b7dac18c0e70c6f0e825ce2a7d44fdaa2cc2ad70 (diff) | |
download | UXP-abf1d5a099ea8c3fbd6912ff7b199791994cb932.tar UXP-abf1d5a099ea8c3fbd6912ff7b199791994cb932.tar.gz UXP-abf1d5a099ea8c3fbd6912ff7b199791994cb932.tar.lz UXP-abf1d5a099ea8c3fbd6912ff7b199791994cb932.tar.xz UXP-abf1d5a099ea8c3fbd6912ff7b199791994cb932.zip |
Issue #1665 - Take overflow-wrap into account when calculating min-content intrinsic size.
-rw-r--r-- | gfx/thebes/gfxTextRun.cpp | 28 | ||||
-rw-r--r-- | gfx/thebes/gfxTextRun.h | 6 | ||||
-rw-r--r-- | layout/generic/nsTextFrame.cpp | 10 |
3 files changed, 44 insertions, 0 deletions
diff --git a/gfx/thebes/gfxTextRun.cpp b/gfx/thebes/gfxTextRun.cpp index 2e2a0d239..d6cb1bdb2 100644 --- a/gfx/thebes/gfxTextRun.cpp +++ b/gfx/thebes/gfxTextRun.cpp @@ -1072,6 +1072,34 @@ gfxTextRun::GetAdvanceWidth(Range aRange, PropertyProvider *aProvider, return result + GetAdvanceForGlyphs(ligatureRange); } +gfxFloat +gfxTextRun::GetMinAdvanceWidth(Range aRange) +{ + MOZ_ASSERT(aRange.end <= GetLength(), "Substring out of range"); + + Range ligatureRange = aRange; + ShrinkToLigatureBoundaries(&ligatureRange); + + gfxFloat result = std::max( + ComputePartialLigatureWidth(Range(aRange.start, ligatureRange.start), + nullptr), + ComputePartialLigatureWidth(Range(ligatureRange.end, aRange.end), + nullptr)); + + // XXX Do we need to take spacing into account? When each grapheme cluster + // takes its own line, we shouldn't be adding spacings around them. + gfxFloat clusterAdvance = 0; + for (uint32_t i = ligatureRange.start; i < ligatureRange.end; ++i) { + clusterAdvance += GetAdvanceForGlyph(i); + if (i + 1 == ligatureRange.end || IsClusterStart(i + 1)) { + result = std::max(result, clusterAdvance); + clusterAdvance = 0; + } + } + + return result; +} + bool gfxTextRun::SetLineBreaks(Range aRange, bool aLineBreakBefore, bool aLineBreakAfter, diff --git a/gfx/thebes/gfxTextRun.h b/gfx/thebes/gfxTextRun.h index 3c9ded1dc..a565075cd 100644 --- a/gfx/thebes/gfxTextRun.h +++ b/gfx/thebes/gfxTextRun.h @@ -299,6 +299,12 @@ public: } /** + * Computes the minimum advance width for a substring assuming line + * breaking is allowed everywhere. + */ + gfxFloat GetMinAdvanceWidth(Range aRange); + + /** * Clear all stored line breaks for the given range (both before and after), * and then set the line-break state before aRange.start to aBreakBefore and * after the last cluster to aBreakAfter. diff --git a/layout/generic/nsTextFrame.cpp b/layout/generic/nsTextFrame.cpp index 4bc542626..a9ed168fb 100644 --- a/layout/generic/nsTextFrame.cpp +++ b/layout/generic/nsTextFrame.cpp @@ -8245,6 +8245,16 @@ nsTextFrame::AddInlineMinISizeForFlow(nsRenderingContext *aRenderingContext, return; } + // If overflow-wrap is break-word, we can wrap everywhere. + if (textStyle->WordCanWrap(this)) { + aData->OptionallyBreak(); + aData->mCurrentLine += + textRun->GetMinAdvanceWidth(Range(start, flowEndInTextRun)); + aData->mTrailingWhitespace = 0; + aData->OptionallyBreak(); + return; + } + AutoTArray<bool,BIG_TEXT_NODE_SIZE> hyphBuffer; bool *hyphBreakBefore = nullptr; if (hyphenating) { |