mirror of
https://github.com/mozilla/gecko-dev.git
synced 2024-11-26 06:11:37 +00:00
Bug 683952. Speed up iterating over the continuations of the frame when scrolling to it. r=roc
This commit is contained in:
parent
8da3fa5aad
commit
73e9ae8488
@ -4044,13 +4044,19 @@ PresShell::ScrollToAnchor()
|
||||
* we should include the top of the line in the added rectangle
|
||||
* @param aRect [inout] rect into which its bounds should be unioned
|
||||
* @param aHaveRect [inout] whether aRect contains data yet
|
||||
* @param aPrevBlock [inout] the block aLines is a line iterator for
|
||||
* @param aLines [inout] the line iterator we're using
|
||||
* @param aCurLine [inout] the line to start looking from in this iterator
|
||||
*/
|
||||
static void
|
||||
AccumulateFrameBounds(nsIFrame* aContainerFrame,
|
||||
nsIFrame* aFrame,
|
||||
PRBool aUseWholeLineHeightForInlines,
|
||||
nsRect& aRect,
|
||||
PRBool& aHaveRect)
|
||||
PRBool& aHaveRect,
|
||||
nsIFrame*& aPrevBlock,
|
||||
nsAutoLineIterator& aLines,
|
||||
PRInt32& aCurLine)
|
||||
{
|
||||
nsRect frameBounds = aFrame->GetRect() +
|
||||
aFrame->GetParent()->GetOffsetTo(aContainerFrame);
|
||||
@ -4073,17 +4079,22 @@ AccumulateFrameBounds(nsIFrame* aContainerFrame,
|
||||
f &&
|
||||
frameType == nsGkAtoms::blockFrame) {
|
||||
// find the line containing aFrame and increase the top of |offset|.
|
||||
nsAutoLineIterator lines = f->GetLineIterator();
|
||||
if (lines) {
|
||||
PRInt32 index = lines->FindLineContaining(prevFrame);
|
||||
if (f != aPrevBlock) {
|
||||
aLines = f->GetLineIterator();
|
||||
aPrevBlock = f;
|
||||
aCurLine = 0;
|
||||
}
|
||||
if (aLines) {
|
||||
PRInt32 index = aLines->FindLineContaining(prevFrame, aCurLine);
|
||||
if (index >= 0) {
|
||||
aCurLine = index;
|
||||
nsIFrame *trash1;
|
||||
PRInt32 trash2;
|
||||
nsRect lineBounds;
|
||||
PRUint32 trash3;
|
||||
|
||||
if (NS_SUCCEEDED(lines->GetLine(index, &trash1, &trash2,
|
||||
lineBounds, &trash3))) {
|
||||
if (NS_SUCCEEDED(aLines->GetLine(index, &trash1, &trash2,
|
||||
lineBounds, &trash3))) {
|
||||
lineBounds += f->GetOffsetTo(aContainerFrame);
|
||||
if (lineBounds.y < frameBounds.y) {
|
||||
frameBounds.height = frameBounds.YMost() - lineBounds.y;
|
||||
@ -4286,9 +4297,16 @@ PresShell::DoScrollContentIntoView(nsIContent* aContent,
|
||||
nsRect frameBounds;
|
||||
PRBool haveRect = PR_FALSE;
|
||||
PRBool useWholeLineHeightForInlines = aVPercent != NS_PRESSHELL_SCROLL_ANYWHERE;
|
||||
// Reuse the same line iterator across calls to AccumulateFrameBounds. We set
|
||||
// it every time we detect a new block (stored in prevBlock).
|
||||
nsIFrame* prevBlock = nsnull;
|
||||
nsAutoLineIterator lines;
|
||||
// The last line we found a continuation on in |lines|. We assume that later
|
||||
// continuations cannot come on earlier lines.
|
||||
PRInt32 curLine = 0;
|
||||
do {
|
||||
AccumulateFrameBounds(container, frame, useWholeLineHeightForInlines,
|
||||
frameBounds, haveRect);
|
||||
frameBounds, haveRect, prevBlock, lines, curLine);
|
||||
} while ((frame = frame->GetNextContinuation()));
|
||||
|
||||
ScrollFrameRectIntoView(container, frameBounds, aVPercent, aHPercent,
|
||||
|
@ -104,9 +104,12 @@ public:
|
||||
|
||||
/**
|
||||
* Given a frame that's a child of the block, find which line its on
|
||||
* and return that line index. Returns -1 if the frame cannot be found.
|
||||
* and return that line index, as long as it's at least as big as
|
||||
* aStartLine. Returns -1 if the frame cannot be found on lines
|
||||
* starting with aStartLine.
|
||||
*/
|
||||
virtual PRInt32 FindLineContaining(nsIFrame* aFrame) = 0;
|
||||
virtual PRInt32 FindLineContaining(nsIFrame* aFrame,
|
||||
PRInt32 aStartLine = 0) = 0;
|
||||
|
||||
// Given a line number and an X coordinate, find the frame on the
|
||||
// line that is nearest to the X coordinate. The
|
||||
|
@ -626,15 +626,16 @@ nsLineIterator::GetLine(PRInt32 aLineNumber,
|
||||
}
|
||||
|
||||
PRInt32
|
||||
nsLineIterator::FindLineContaining(nsIFrame* aFrame)
|
||||
nsLineIterator::FindLineContaining(nsIFrame* aFrame, PRInt32 aStartLine)
|
||||
{
|
||||
nsLineBox* line = mLines[0];
|
||||
PRInt32 lineNumber = 0;
|
||||
NS_PRECONDITION(aStartLine <= mNumLines, "Bogus line numbers");
|
||||
PRInt32 lineNumber = aStartLine;
|
||||
while (lineNumber != mNumLines) {
|
||||
nsLineBox* line = mLines[lineNumber];
|
||||
if (line->Contains(aFrame)) {
|
||||
return lineNumber;
|
||||
}
|
||||
line = mLines[++lineNumber];
|
||||
++lineNumber;
|
||||
}
|
||||
return -1;
|
||||
}
|
||||
|
@ -1581,7 +1581,7 @@ public:
|
||||
PRInt32* aNumFramesOnLine,
|
||||
nsRect& aLineBounds,
|
||||
PRUint32* aLineFlags);
|
||||
virtual PRInt32 FindLineContaining(nsIFrame* aFrame);
|
||||
virtual PRInt32 FindLineContaining(nsIFrame* aFrame, PRInt32 aStartLine = 0);
|
||||
NS_IMETHOD FindFrameAt(PRInt32 aLineNumber,
|
||||
nscoord aX,
|
||||
nsIFrame** aFrameFound,
|
||||
|
@ -1706,14 +1706,16 @@ nsTableRowGroupFrame::GetLine(PRInt32 aLineNumber,
|
||||
}
|
||||
|
||||
PRInt32
|
||||
nsTableRowGroupFrame::FindLineContaining(nsIFrame* aFrame)
|
||||
nsTableRowGroupFrame::FindLineContaining(nsIFrame* aFrame, PRInt32 aStartLine)
|
||||
{
|
||||
NS_ENSURE_ARG_POINTER(aFrame);
|
||||
|
||||
nsTableRowFrame *rowFrame = do_QueryFrame(aFrame);
|
||||
NS_ASSERTION(rowFrame, "RowGroup contains a frame that is not a row");
|
||||
|
||||
return rowFrame->GetRowIndex() - GetStartRowIndex();
|
||||
PRInt32 rowIndexInGroup = rowFrame->GetRowIndex() - GetStartRowIndex();
|
||||
|
||||
return rowIndexInGroup >= aStartLine ? rowIndexInGroup : -1;
|
||||
}
|
||||
|
||||
#ifdef IBMBIDI
|
||||
|
@ -258,10 +258,12 @@ public:
|
||||
|
||||
/** Given a frame that's a child of the rowgroup, find which line its on.
|
||||
* @param aFrame - frame, should be a row
|
||||
* @param aStartLine - minimal index to return
|
||||
* @return row index relative to the row group if this a row
|
||||
* frame. -1 if the frame cannot be found.
|
||||
* frame and the index is at least aStartLine.
|
||||
* -1 if the frame cannot be found.
|
||||
*/
|
||||
virtual PRInt32 FindLineContaining(nsIFrame* aFrame);
|
||||
virtual PRInt32 FindLineContaining(nsIFrame* aFrame, PRInt32 aStartLine = 0);
|
||||
|
||||
/** Find the orginating cell frame on a row that is the nearest to the
|
||||
* coordinate X.
|
||||
|
Loading…
Reference in New Issue
Block a user