mirror of
https://gitlab.winehq.org/wine/wine-gecko.git
synced 2024-09-13 09:24:08 -07:00
Bug 1120313 - Fix nested ruby inside ruby annotation. r=dbaron
--HG-- extra : source : ea44dcc7bf0e008d6669a00d107529a97ab1c84d
This commit is contained in:
parent
fccbdc4b77
commit
59a6f1fedb
@ -58,7 +58,7 @@ nsLineLayout::nsLineLayout(nsPresContext* aPresContext,
|
||||
: mPresContext(aPresContext),
|
||||
mFloatManager(aFloatManager),
|
||||
mBlockReflowState(aOuterReflowState),
|
||||
mBaseLineLayout(aBaseLineLayout ? aBaseLineLayout->mBaseLineLayout : this),
|
||||
mBaseLineLayout(aBaseLineLayout),
|
||||
mLastOptionalBreakFrame(nullptr),
|
||||
mForceBreakFrame(nullptr),
|
||||
mBlockRS(nullptr),/* XXX temporary */
|
||||
@ -87,6 +87,11 @@ nsLineLayout::nsLineLayout(nsPresContext* aPresContext,
|
||||
NS_ASSERTION(aFloatManager || aOuterReflowState->frame->GetType() ==
|
||||
nsGkAtoms::letterFrame,
|
||||
"float manager should be present");
|
||||
MOZ_ASSERT((!!mBaseLineLayout) ==
|
||||
(aOuterReflowState->frame->GetType() ==
|
||||
nsGkAtoms::rubyTextContainerFrame),
|
||||
"Only ruby text container frames have "
|
||||
"a different base line layout");
|
||||
MOZ_COUNT_CTOR(nsLineLayout);
|
||||
|
||||
// Stash away some style data that we need
|
||||
@ -182,7 +187,7 @@ nsLineLayout::BeginLineReflow(nscoord aICoord, nscoord aBCoord,
|
||||
mIsTopOfPage = aIsTopOfPage;
|
||||
mImpactedByFloats = aImpactedByFloats;
|
||||
mTotalPlacedFrames = 0;
|
||||
if (mBaseLineLayout == this) {
|
||||
if (!mBaseLineLayout) {
|
||||
mLineIsEmpty = true;
|
||||
mLineAtStart = true;
|
||||
} else {
|
||||
@ -263,7 +268,7 @@ nsLineLayout::EndLineReflow()
|
||||
printf(": EndLineReflow: width=%d\n", mRootSpan->mICoord - mRootSpan->mIStart);
|
||||
#endif
|
||||
|
||||
NS_ASSERTION(mBaseLineLayout == this ||
|
||||
NS_ASSERTION(!mBaseLineLayout ||
|
||||
(!mSpansAllocated && !mSpansFreed && !mSpanFreeList &&
|
||||
!mFramesAllocated && !mFramesFreed && !mFrameFreeList),
|
||||
"Allocated frames or spans on non-base line layout?");
|
||||
@ -386,18 +391,19 @@ nsLineLayout::UpdateBand(WritingMode aWM,
|
||||
nsLineLayout::PerSpanData*
|
||||
nsLineLayout::NewPerSpanData()
|
||||
{
|
||||
PerSpanData* psd = mBaseLineLayout->mSpanFreeList;
|
||||
nsLineLayout* outerLineLayout = GetOutermostLineLayout();
|
||||
PerSpanData* psd = outerLineLayout->mSpanFreeList;
|
||||
if (!psd) {
|
||||
void *mem;
|
||||
size_t sz = sizeof(PerSpanData);
|
||||
PL_ARENA_ALLOCATE(mem, &mBaseLineLayout->mArena, sz);
|
||||
PL_ARENA_ALLOCATE(mem, &outerLineLayout->mArena, sz);
|
||||
if (!mem) {
|
||||
NS_ABORT_OOM(sz);
|
||||
}
|
||||
psd = reinterpret_cast<PerSpanData*>(mem);
|
||||
}
|
||||
else {
|
||||
mBaseLineLayout->mSpanFreeList = psd->mNextFreeSpan;
|
||||
outerLineLayout->mSpanFreeList = psd->mNextFreeSpan;
|
||||
}
|
||||
psd->mParent = nullptr;
|
||||
psd->mFrame = nullptr;
|
||||
@ -408,7 +414,7 @@ nsLineLayout::NewPerSpanData()
|
||||
psd->mHasNonemptyContent = false;
|
||||
|
||||
#ifdef DEBUG
|
||||
mBaseLineLayout->mSpansAllocated++;
|
||||
outerLineLayout->mSpansAllocated++;
|
||||
#endif
|
||||
return psd;
|
||||
}
|
||||
@ -473,13 +479,21 @@ nsLineLayout::EndSpan(nsIFrame* aFrame)
|
||||
void
|
||||
nsLineLayout::AttachFrameToBaseLineLayout(PerFrameData* aFrame)
|
||||
{
|
||||
NS_PRECONDITION(this != mBaseLineLayout,
|
||||
NS_PRECONDITION(mBaseLineLayout,
|
||||
"This method must not be called in a base line layout.");
|
||||
|
||||
PerFrameData* baseFrame = mBaseLineLayout->LastFrame();
|
||||
MOZ_ASSERT(aFrame && baseFrame);
|
||||
MOZ_ASSERT(!aFrame->mIsLinkedToBase,
|
||||
"The frame must not have been linked with the base");
|
||||
#ifdef DEBUG
|
||||
nsIAtom* baseType = baseFrame->mFrame->GetType();
|
||||
nsIAtom* annotationType = aFrame->mFrame->GetType();
|
||||
MOZ_ASSERT((baseType == nsGkAtoms::rubyBaseContainerFrame &&
|
||||
annotationType == nsGkAtoms::rubyTextContainerFrame) ||
|
||||
(baseType == nsGkAtoms::rubyBaseFrame &&
|
||||
annotationType == nsGkAtoms::rubyTextFrame));
|
||||
#endif
|
||||
|
||||
aFrame->mNextAnnotation = baseFrame->mNextAnnotation;
|
||||
baseFrame->mNextAnnotation = aFrame;
|
||||
@ -603,10 +617,11 @@ nsLineLayout::FreeFrame(PerFrameData* pfd)
|
||||
if (nullptr != pfd->mSpan) {
|
||||
FreeSpan(pfd->mSpan);
|
||||
}
|
||||
pfd->mNext = mBaseLineLayout->mFrameFreeList;
|
||||
mBaseLineLayout->mFrameFreeList = pfd;
|
||||
nsLineLayout* outerLineLayout = GetOutermostLineLayout();
|
||||
pfd->mNext = outerLineLayout->mFrameFreeList;
|
||||
outerLineLayout->mFrameFreeList = pfd;
|
||||
#ifdef DEBUG
|
||||
mBaseLineLayout->mFramesFreed++;
|
||||
outerLineLayout->mFramesFreed++;
|
||||
#endif
|
||||
}
|
||||
|
||||
@ -616,11 +631,12 @@ nsLineLayout::FreeSpan(PerSpanData* psd)
|
||||
// Unlink its frames
|
||||
UnlinkFrame(psd->mFirstFrame);
|
||||
|
||||
nsLineLayout* outerLineLayout = GetOutermostLineLayout();
|
||||
// Now put the span on the free list since it's free too
|
||||
psd->mNextFreeSpan = mBaseLineLayout->mSpanFreeList;
|
||||
mBaseLineLayout->mSpanFreeList = psd;
|
||||
psd->mNextFreeSpan = outerLineLayout->mSpanFreeList;
|
||||
outerLineLayout->mSpanFreeList = psd;
|
||||
#ifdef DEBUG
|
||||
mBaseLineLayout->mSpansFreed++;
|
||||
outerLineLayout->mSpansFreed++;
|
||||
#endif
|
||||
}
|
||||
|
||||
@ -641,18 +657,19 @@ nsLineLayout::IsZeroBSize()
|
||||
nsLineLayout::PerFrameData*
|
||||
nsLineLayout::NewPerFrameData(nsIFrame* aFrame)
|
||||
{
|
||||
PerFrameData* pfd = mBaseLineLayout->mFrameFreeList;
|
||||
nsLineLayout* outerLineLayout = GetOutermostLineLayout();
|
||||
PerFrameData* pfd = outerLineLayout->mFrameFreeList;
|
||||
if (!pfd) {
|
||||
void *mem;
|
||||
size_t sz = sizeof(PerFrameData);
|
||||
PL_ARENA_ALLOCATE(mem, &mBaseLineLayout->mArena, sz);
|
||||
PL_ARENA_ALLOCATE(mem, &outerLineLayout->mArena, sz);
|
||||
if (!mem) {
|
||||
NS_ABORT_OOM(sz);
|
||||
}
|
||||
pfd = reinterpret_cast<PerFrameData*>(mem);
|
||||
}
|
||||
else {
|
||||
mBaseLineLayout->mFrameFreeList = pfd->mNext;
|
||||
outerLineLayout->mFrameFreeList = pfd->mNext;
|
||||
}
|
||||
pfd->mSpan = nullptr;
|
||||
pfd->mNext = nullptr;
|
||||
@ -684,7 +701,7 @@ nsLineLayout::NewPerFrameData(nsIFrame* aFrame)
|
||||
|
||||
#ifdef DEBUG
|
||||
pfd->mBlockDirAlign = 0xFF;
|
||||
mBaseLineLayout->mFramesAllocated++;
|
||||
outerLineLayout->mFramesAllocated++;
|
||||
#endif
|
||||
return pfd;
|
||||
}
|
||||
@ -970,7 +987,8 @@ nsLineLayout::ReflowFrame(nsIFrame* aFrame,
|
||||
// We might as well allow zero-width floats to be placed, though.
|
||||
availableISize = 0;
|
||||
}
|
||||
placedFloat = mBaseLineLayout->AddFloat(outOfFlowFrame, availableISize);
|
||||
placedFloat = GetOutermostLineLayout()->
|
||||
AddFloat(outOfFlowFrame, availableISize);
|
||||
NS_ASSERTION(!(outOfFlowFrame->GetType() == nsGkAtoms::letterFrame &&
|
||||
GetFirstLetterStyleOK()),
|
||||
"FirstLetterStyle set on line with floating first letter");
|
||||
|
@ -385,14 +385,23 @@ protected:
|
||||
const nsStyleText* mStyleText; // for the block
|
||||
const nsHTMLReflowState* mBlockReflowState;
|
||||
|
||||
// The line layout for the base text. It is usually same as |this|.
|
||||
// It becomes different when the current line layout is for ruby
|
||||
// annotations. All line layouts share the same base line layout
|
||||
// when they are associated. The base line layout is responsible
|
||||
// for managing the life cycle of per-frame data and per-span data,
|
||||
// and handling floats.
|
||||
// The line layout for the base text. It is usually nullptr.
|
||||
// It becomes not null when the current line layout is for ruby
|
||||
// annotations. When there is nested ruby inside annotation, it
|
||||
// forms a linked list from the inner annotation to the outermost
|
||||
// line layout. The outermost line layout, which has this member
|
||||
// being nullptr, is responsible for managing the life cycle of
|
||||
// per-frame data and per-span data, and handling floats.
|
||||
nsLineLayout* const mBaseLineLayout;
|
||||
|
||||
nsLineLayout* GetOutermostLineLayout() {
|
||||
nsLineLayout* lineLayout = this;
|
||||
while (lineLayout->mBaseLineLayout) {
|
||||
lineLayout = lineLayout->mBaseLineLayout;
|
||||
}
|
||||
return lineLayout;
|
||||
}
|
||||
|
||||
nsIFrame* mLastOptionalBreakFrame;
|
||||
nsIFrame* mForceBreakFrame;
|
||||
|
||||
|
19
layout/reftests/css-ruby/nested-ruby-1.html
Normal file
19
layout/reftests/css-ruby/nested-ruby-1.html
Normal file
@ -0,0 +1,19 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="UTF-8">
|
||||
<title>Bug 1120313 - Nested ruby inside ruby annotation</title>
|
||||
<link rel="stylesheet" href="common.css">
|
||||
</head>
|
||||
<body>
|
||||
<ruby>
|
||||
<rb>base1</rb>
|
||||
<rt>
|
||||
<ruby>
|
||||
<rb>base2</rb>
|
||||
<rt>text</rt>
|
||||
</ruby>
|
||||
</rt>
|
||||
</ruby>
|
||||
</body>
|
||||
</html>
|
@ -27,6 +27,7 @@ fuzzy-if(winWidget,35,1) == dynamic-removal-3.html dynamic-removal-3-ref.html #
|
||||
== justification-2.html justification-2-ref.html
|
||||
== line-height-1.html line-height-1-ref.html
|
||||
== line-height-2.html line-height-2-ref.html
|
||||
load nested-ruby-1.html
|
||||
== line-height-3.html line-height-3-ref.html
|
||||
== ruby-span-1.html ruby-span-1-ref.html
|
||||
== ruby-whitespace-1.html ruby-whitespace-1-ref.html
|
||||
|
Loading…
Reference in New Issue
Block a user