mirror of
https://gitlab.winehq.org/wine/wine-gecko.git
synced 2024-09-13 09:24:08 -07:00
Backing out patches for bug 385270 (mostly --- due to other checkins in the meantime, the GetContent*() helper functions need to stay) to fix regressions. a=schrep
This commit is contained in:
parent
e50a443cd2
commit
9009ef6bb7
@ -883,6 +883,16 @@ nsLineLayout::ReflowFrame(nsIFrame* aFrame,
|
||||
nscoord ty = y - psd->mReflowState->mComputedBorderPadding.top;
|
||||
mSpaceManager->Translate(tx, ty);
|
||||
|
||||
#ifdef IBMBIDI
|
||||
PRInt32 start, end;
|
||||
|
||||
if (mPresContext->BidiEnabled()) {
|
||||
if (aFrame->GetStateBits() & NS_FRAME_IS_BIDI) {
|
||||
aFrame->GetOffsets(start, end);
|
||||
}
|
||||
}
|
||||
#endif // IBMBIDI
|
||||
|
||||
nsIAtom* frameType = aFrame->GetType();
|
||||
PRInt32 savedOptionalBreakOffset;
|
||||
nsIContent* savedOptionalBreakContent =
|
||||
@ -1076,6 +1086,24 @@ nsLineLayout::ReflowFrame(nsIFrame* aFrame,
|
||||
printf(" status=%x\n", aReflowStatus);
|
||||
#endif
|
||||
|
||||
if (aFrame->GetStateBits() & NS_FRAME_IS_BIDI) {
|
||||
// Since aReflowStatus may change, check it at the end
|
||||
if (NS_INLINE_IS_BREAK_BEFORE(aReflowStatus) ) {
|
||||
aFrame->AdjustOffsetsForBidi(start, end);
|
||||
}
|
||||
else if (!NS_FRAME_IS_COMPLETE(aReflowStatus) ) {
|
||||
PRInt32 newEnd;
|
||||
aFrame->GetOffsets(start, newEnd);
|
||||
if (newEnd != end) {
|
||||
nsIFrame* nextInFlow = aFrame->GetNextInFlow();
|
||||
if (nextInFlow) {
|
||||
nextInFlow->GetOffsets(start, end);
|
||||
nextInFlow->AdjustOffsetsForBidi(newEnd, end);
|
||||
} // nextInFlow
|
||||
} // newEnd != end
|
||||
} // !NS_FRAME_IS_COMPLETE(aReflowStatus)
|
||||
} // isBidiFrame
|
||||
|
||||
return rv;
|
||||
}
|
||||
|
||||
|
@ -138,10 +138,16 @@
|
||||
// This bit is set on frames that trimmed trailing whitespace characters when
|
||||
// calculating their width during reflow.
|
||||
#define TEXT_TRIMMED_TRAILING_WHITESPACE 0x01000000
|
||||
// Set when the frame's text may have a different style from its in-flow
|
||||
// brethren (e.g. the frame is in first-letter or first-line), so text runs
|
||||
// may need to be reconstructed when the frame's content offset/length changes.
|
||||
// We set this on the frame that has in first-letter or first-line, but not
|
||||
// in-flow siblings outside first-letter or first-line.
|
||||
#define TEXT_RUN_LAYOUT_DEPENDENT 0x02000000
|
||||
|
||||
#define TEXT_REFLOW_FLAGS \
|
||||
(TEXT_FIRST_LETTER|TEXT_START_OF_LINE|TEXT_END_OF_LINE|TEXT_HYPHEN_BREAK| \
|
||||
TEXT_TRIMMED_TRAILING_WHITESPACE)
|
||||
TEXT_TRIMMED_TRAILING_WHITESPACE|TEXT_RUN_LAYOUT_DEPENDENT)
|
||||
|
||||
// Cache bits for IsEmpty().
|
||||
// Set this bit if the textframe is known to be only collapsible whitespace.
|
||||
@ -498,15 +504,6 @@ public:
|
||||
PRInt32 GetContentLength() const { return mContentLength; }
|
||||
PRInt32 GetContentEnd() const { return mContentOffset + mContentLength; }
|
||||
|
||||
/**
|
||||
* Fix up the content offsets for all next-in-flows so that they do not
|
||||
* overlap this frame's content.
|
||||
* @param aClearTextRuns if true, then any next-in-flows whose content
|
||||
* offsets changed have their textruns cleared (as would be necessary
|
||||
* if this frame could have a different style to those frames)
|
||||
*/
|
||||
void AdjustNextInFlowContentOffsetsForGrowth(PRBool aClearTextRuns);
|
||||
|
||||
// Compute the length of the content mapped by this frame
|
||||
// and all its in-flow siblings. Basically this means starting at mContentOffset
|
||||
// and going to the end of the text node or the next bidi continuation
|
||||
@ -562,6 +559,8 @@ protected:
|
||||
PRBool isRTLChars,
|
||||
PRBool isOddLevel,
|
||||
PRBool isBidiSystem);
|
||||
|
||||
void SetOffsets(PRInt32 start, PRInt32 end);
|
||||
};
|
||||
|
||||
static void
|
||||
@ -1339,9 +1338,12 @@ void BuildTextRunsScanner::ScanFrame(nsIFrame* aFrame)
|
||||
!HasTerminalNewline(mLastFrame)) {
|
||||
nsTextFrame* frame = static_cast<nsTextFrame*>(aFrame);
|
||||
mappedFlow->mEndFrame = static_cast<nsTextFrame*>(frame->GetNextInFlow());
|
||||
NS_ASSERTION(mappedFlow->mContentEndOffset <= frame->GetContentOffset(),
|
||||
"frame offsets overlap!");
|
||||
mappedFlow->mContentEndOffset = frame->GetContentEnd();
|
||||
// Frames in the same flow can overlap at least temporarily
|
||||
// (e.g. when first-line builds its textrun, we need to have it suck
|
||||
// up all the in-flow content because we don't know how long the line
|
||||
// is going to be).
|
||||
mappedFlow->mContentEndOffset =
|
||||
PR_MAX(mappedFlow->mContentEndOffset, frame->GetContentEnd());
|
||||
AccumulateRunInfo(frame);
|
||||
return;
|
||||
}
|
||||
@ -1563,8 +1565,12 @@ BuildTextRunsScanner::BuildTextRunForFrames(void* aTextBuffer)
|
||||
PRInt32 contentLength = contentEnd - contentStart;
|
||||
|
||||
if (content == lastContent) {
|
||||
NS_ASSERTION(endOfLastContent == contentStart,
|
||||
"Gap in textframes mapping content, or overlap?!");
|
||||
NS_ASSERTION(endOfLastContent >= contentStart,
|
||||
"Gap in textframes mapping content?!");
|
||||
// Text frames can overlap (see comment in ScanFrame below)
|
||||
contentStart = PR_MAX(contentStart, endOfLastContent);
|
||||
if (contentStart >= contentEnd)
|
||||
continue;
|
||||
userData->mMappedFlows[finalMappedFlowCount - 1].mContentLength += contentLength;
|
||||
} else {
|
||||
TextRunMappedFlow* newFlow = &userData->mMappedFlows[finalMappedFlowCount];
|
||||
@ -3268,18 +3274,18 @@ nsContinuingTextFrame::Init(nsIContent* aContent,
|
||||
// NOTE: bypassing nsTextFrame::Init!!!
|
||||
nsresult rv = nsFrame::Init(aContent, aParent, aPrevInFlow);
|
||||
|
||||
nsIFrame* nextContinuation = aPrevInFlow->GetNextContinuation();
|
||||
// Hook the frame into the flow
|
||||
SetPrevInFlow(aPrevInFlow);
|
||||
aPrevInFlow->SetNextInFlow(this);
|
||||
nsTextFrame* prev = static_cast<nsTextFrame*>(aPrevInFlow);
|
||||
nsTextFrame* nextContinuation = static_cast<nsTextFrame*>
|
||||
(prev->GetNextContinuation());
|
||||
SetPrevInFlow(prev);
|
||||
prev->SetNextInFlow(this);
|
||||
|
||||
mTextRun = prev->GetTextRun();
|
||||
mContentOffset = prev->GetContentEnd();
|
||||
mContentLength = mContent->TextLength() - mContentOffset;
|
||||
#ifdef IBMBIDI
|
||||
if (prev->GetStateBits() & NS_FRAME_IS_BIDI) {
|
||||
if (aPrevInFlow->GetStateBits() & NS_FRAME_IS_BIDI) {
|
||||
PRInt32 start, end;
|
||||
aPrevInFlow->GetOffsets(start, mContentOffset);
|
||||
|
||||
nsPropertyTable *propTable = PresContext()->PropertyTable();
|
||||
propTable->SetProperty(this, nsGkAtoms::embeddingLevel,
|
||||
propTable->GetProperty(aPrevInFlow, nsGkAtoms::embeddingLevel),
|
||||
@ -3290,13 +3296,11 @@ nsContinuingTextFrame::Init(nsIContent* aContent,
|
||||
propTable->SetProperty(this, nsGkAtoms::charType,
|
||||
propTable->GetProperty(aPrevInFlow, nsGkAtoms::charType),
|
||||
nsnull, nsnull);
|
||||
|
||||
if (nextContinuation) {
|
||||
SetNextContinuation(nextContinuation);
|
||||
nextContinuation->SetPrevContinuation(this);
|
||||
NS_ASSERTION(mContentOffset <= nextContinuation->GetContentOffset(),
|
||||
"Overlapping text ranges!");
|
||||
mContentLength = nextContinuation->GetContentOffset() - mContentOffset;
|
||||
nextContinuation->GetOffsets(start, end);
|
||||
mContentLength = PR_MAX(1, start - mContentOffset);
|
||||
}
|
||||
mState |= NS_FRAME_IS_BIDI;
|
||||
} // prev frame is bidi
|
||||
@ -5158,26 +5162,6 @@ HasSoftHyphenBefore(const nsTextFragment* aFrag, gfxTextRun* aTextRun,
|
||||
return PR_FALSE;
|
||||
}
|
||||
|
||||
void
|
||||
nsTextFrame::AdjustNextInFlowContentOffsetsForGrowth(PRBool aClearTextRuns)
|
||||
{
|
||||
PRInt32 end = GetContentEnd();
|
||||
nsTextFrame* f = this;
|
||||
NS_ASSERTION(!GetNextInFlow() ||
|
||||
static_cast<nsTextFrame*>(GetNextInFlow())->GetContentOffset() <= GetContentEnd(),
|
||||
"We shrunk, this should not be called");
|
||||
while (PR_TRUE) {
|
||||
f = static_cast<nsTextFrame*>(f->GetNextInFlow());
|
||||
if (!f || f->GetContentOffset() >= end)
|
||||
break;
|
||||
f->mContentLength = PR_MAX(end, f->GetContentEnd()) - end;
|
||||
f->mContentOffset = end;
|
||||
if (aClearTextRuns) {
|
||||
f->ClearTextRun();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsTextFrame::Reflow(nsPresContext* aPresContext,
|
||||
nsHTMLReflowMetrics& aMetrics,
|
||||
@ -5201,16 +5185,25 @@ nsTextFrame::Reflow(nsPresContext* aPresContext,
|
||||
// can change whether the frame maps whitespace-only text or not.
|
||||
RemoveStateBits(TEXT_REFLOW_FLAGS | TEXT_WHITESPACE_FLAGS);
|
||||
|
||||
NS_ASSERTION(!GetPrevInFlow() ||
|
||||
static_cast<nsTextFrame*>(GetPrevInFlow())->GetContentEnd() == mContentOffset,
|
||||
"Discontinuous content offsets!");
|
||||
nsTextFrame* prevInFlow = static_cast<nsTextFrame*>(GetPrevInFlow());
|
||||
if (prevInFlow) {
|
||||
// Our mContentOffset may be out of date due to our prev-in-flow growing or
|
||||
// shrinking. Update it.
|
||||
mContentOffset = prevInFlow->GetContentEnd();
|
||||
}
|
||||
|
||||
// Temporarily map all possible content while we construct our new textrun.
|
||||
// so that when doing reflow our styles prevail over any part of the
|
||||
// textrun we look at. Note that next-in-flows may be mapping the same
|
||||
// content; gfxTextRun construction logic will ensure that we take priority.
|
||||
PRInt32 maxContentLength = GetInFlowContentLength();
|
||||
mContentLength = maxContentLength;
|
||||
|
||||
// XXX If there's no line layout, we shouldn't even have created this
|
||||
// frame. This may happen if, for example, this is text inside a table
|
||||
// but not inside a cell. For now, just don't reflow. We also don't need to
|
||||
// reflow if there is no content.
|
||||
if (!aReflowState.mLineLayout || !maxContentLength) {
|
||||
if (!aReflowState.mLineLayout || !mContentLength) {
|
||||
ClearMetrics(aMetrics);
|
||||
aStatus = NS_FRAME_COMPLETE;
|
||||
return NS_OK;
|
||||
@ -5249,15 +5242,11 @@ nsTextFrame::Reflow(nsPresContext* aPresContext,
|
||||
PRBool layoutDependentTextRun =
|
||||
lineLayout.GetFirstLetterStyleOK() || lineLayout.GetInFirstLine();
|
||||
if (layoutDependentTextRun) {
|
||||
AddStateBits(TEXT_RUN_LAYOUT_DEPENDENT);
|
||||
}
|
||||
if (layoutDependentTextRun ||
|
||||
(prevInFlow && (prevInFlow->GetStateBits() & TEXT_RUN_LAYOUT_DEPENDENT))) {
|
||||
ClearTextRun();
|
||||
// Temporarily map all possible content while we construct our new textrun.
|
||||
// so that when doing reflow our styles prevail over any part of the
|
||||
// textrun we look at.
|
||||
mContentLength = maxContentLength;
|
||||
// The following loop is going to traverse all in-flow frames, which could
|
||||
// be kinda slow, but we're going to have to rebuild all their text runs
|
||||
// anyway so this shouldn't be any worse
|
||||
AdjustNextInFlowContentOffsetsForGrowth(PR_TRUE);
|
||||
}
|
||||
|
||||
PRUint32 flowEndInTextRun;
|
||||
@ -5276,7 +5265,7 @@ nsTextFrame::Reflow(nsPresContext* aPresContext,
|
||||
// DOM offsets of the text range we need to measure, after trimming
|
||||
// whitespace, restricting to first-letter, and restricting preformatted text
|
||||
// to nearest newline
|
||||
PRInt32 length = maxContentLength;
|
||||
PRInt32 length = mContentLength;
|
||||
PRInt32 offset = mContentOffset;
|
||||
|
||||
// Restrict preformatted text to the nearest newline
|
||||
@ -5430,27 +5419,6 @@ nsTextFrame::Reflow(nsPresContext* aPresContext,
|
||||
AddStateBits(TEXT_TRIMMED_TRAILING_WHITESPACE);
|
||||
}
|
||||
mContentLength = offset + charsFit - mContentOffset;
|
||||
|
||||
// Now fix up content offsets/lengths for in-flows
|
||||
nsTextFrame* f = static_cast<nsTextFrame*>(GetNextInFlow());
|
||||
if (f) {
|
||||
if (f->GetContentOffset() > GetContentEnd()) {
|
||||
// We must have shrunk. Add the leftover text to the start of f.
|
||||
f->mContentLength = f->GetContentEnd() - GetContentEnd();
|
||||
f->mContentOffset = GetContentEnd();
|
||||
if (layoutDependentTextRun) {
|
||||
// f's textrun may need to change since the text style may be
|
||||
// different.
|
||||
f->ClearTextRun();
|
||||
}
|
||||
} else if (f->GetContentOffset() < GetContentEnd()) {
|
||||
// We must have grown. Remove the text from f and possibly its
|
||||
// continuations.
|
||||
NS_ASSERTION(!layoutDependentTextRun,
|
||||
"We should have grown up above and be shrinking here!");
|
||||
AdjustNextInFlowContentOffsetsForGrowth(layoutDependentTextRun);
|
||||
}
|
||||
}
|
||||
|
||||
/////////////////////////////////////////////////////////////////////
|
||||
// Compute output metrics
|
||||
@ -5619,9 +5587,9 @@ nsTextFrame::TrimTrailingWhiteSpace(nsPresContext* aPresContext,
|
||||
|
||||
if (GetStateBits() & TEXT_TRIMMED_TRAILING_WHITESPACE) {
|
||||
aLastCharIsJustifiable = PR_TRUE;
|
||||
} else if (trimmed.mStart + trimmed.mLength < GetContentEnd()) {
|
||||
} else if (trimmed.mStart + trimmed.mLength < mContentOffset + mContentLength) {
|
||||
gfxSkipCharsIterator end = iter;
|
||||
PRUint32 endOffset = end.ConvertOriginalToSkipped(GetContentEnd());
|
||||
PRUint32 endOffset = end.ConvertOriginalToSkipped(mContentOffset + mContentLength);
|
||||
if (trimmedEnd < endOffset) {
|
||||
// We can't be dealing with tabs here ... they wouldn't be trimmed. So it's
|
||||
// OK to pass null for the line container.
|
||||
@ -5896,24 +5864,20 @@ void
|
||||
nsTextFrame::AdjustOffsetsForBidi(PRInt32 aStart, PRInt32 aEnd)
|
||||
{
|
||||
AddStateBits(NS_FRAME_IS_BIDI);
|
||||
SetOffsets(aStart, aEnd);
|
||||
/*
|
||||
* After Bidi resolution we may need to reassign text runs.
|
||||
* This is called during bidi resolution from the block container, so we
|
||||
* shouldn't be holding a local reference to a textrun anywhere.
|
||||
*/
|
||||
ClearTextRun();
|
||||
}
|
||||
|
||||
void
|
||||
nsTextFrame::SetOffsets(PRInt32 aStart, PRInt32 aEnd)
|
||||
{
|
||||
mContentOffset = aStart;
|
||||
mContentLength = aEnd - aStart;
|
||||
nsTextFrame* f = this;
|
||||
// We were just assigned all the content for this in-flow run, so unmap all
|
||||
// next-in-flows
|
||||
while (PR_TRUE) {
|
||||
/*
|
||||
* After Bidi resolution we may need to reassign text runs.
|
||||
* This is called during bidi resolution from the block container, so we
|
||||
* shouldn't be holding a local reference to a textrun anywhere.
|
||||
*/
|
||||
f->ClearTextRun();
|
||||
f = static_cast<nsTextFrame*>(f->GetNextInFlow());
|
||||
if (!f)
|
||||
break;
|
||||
f->mContentOffset = aEnd;
|
||||
f->mContentLength = 0;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
|
Loading…
Reference in New Issue
Block a user