зеркало из https://github.com/mozilla/pjs.git
273 строки
8.4 KiB
C++
273 строки
8.4 KiB
C++
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*-
|
|
*
|
|
* The contents of this file are subject to the Netscape Public
|
|
* License Version 1.1 (the "License"); you may not use this file
|
|
* except in compliance with the License. You may obtain a copy of
|
|
* the License at http://www.mozilla.org/NPL/
|
|
*
|
|
* Software distributed under the License is distributed on an "AS
|
|
* IS" basis, WITHOUT WARRANTY OF ANY KIND, either express or
|
|
* implied. See the License for the specific language governing
|
|
* rights and limitations under the License.
|
|
*
|
|
* The Original Code is Mozilla Communicator client code.
|
|
*
|
|
* The Initial Developer of the Original Code is Netscape Communications
|
|
* Corporation. Portions created by Netscape are
|
|
* Copyright (C) 1998 Netscape Communications Corporation. All
|
|
* Rights Reserved.
|
|
*
|
|
* Contributor(s):
|
|
* Steve Clark <buster@netscape.com>
|
|
* Robert O'Callahan <roc+moz@cs.cmu.edu>
|
|
* L. David Baron <dbaron@fas.harvard.edu>
|
|
*/
|
|
|
|
#ifndef nsBlockReflowState_h__
|
|
#define nsBlockReflowState_h__
|
|
|
|
#include "nsBlockBandData.h"
|
|
#include "nsLineBox.h"
|
|
|
|
class nsBlockFrame;
|
|
|
|
class nsBlockReflowState {
|
|
public:
|
|
nsBlockReflowState(const nsHTMLReflowState& aReflowState,
|
|
nsIPresContext* aPresContext,
|
|
nsBlockFrame* aFrame,
|
|
const nsHTMLReflowMetrics& aMetrics,
|
|
PRBool aBlockMarginRoot);
|
|
|
|
~nsBlockReflowState();
|
|
|
|
/**
|
|
* Update our state when aLine is skipped over during incremental
|
|
* reflow.
|
|
*/
|
|
void RecoverStateFrom(nsLineBox* aLine, PRBool aPrevLineWasClean);
|
|
|
|
/**
|
|
* Get the available reflow space for the current y coordinate. The
|
|
* available space is relative to our coordinate system (0,0) is our
|
|
* upper left corner.
|
|
*/
|
|
void GetAvailableSpace() {
|
|
GetAvailableSpace(mY);
|
|
}
|
|
|
|
void GetAvailableSpace(nscoord aY);
|
|
|
|
void InitFloater(nsLineLayout& aLineLayout,
|
|
nsPlaceholderFrame* aPlaceholderFrame);
|
|
|
|
void AddFloater(nsLineLayout& aLineLayout,
|
|
nsPlaceholderFrame* aPlaceholderFrame,
|
|
PRBool aInitialReflow);
|
|
|
|
PRBool CanPlaceFloater(const nsRect& aFloaterRect, PRUint8 aFloats);
|
|
|
|
void FlowAndPlaceFloater(nsFloaterCache* aFloaterCache,
|
|
PRBool* aIsLeftFloater);
|
|
|
|
void PlaceBelowCurrentLineFloaters(nsFloaterCacheList& aFloaters);
|
|
|
|
void ClearFloaters(nscoord aY, PRUint8 aBreakType);
|
|
|
|
PRBool ClearPastFloaters(PRUint8 aBreakType);
|
|
|
|
PRBool IsAdjacentWithTop() const {
|
|
return mY == mReflowState.mComputedBorderPadding.top;
|
|
}
|
|
|
|
const nsMargin& BorderPadding() const {
|
|
return mReflowState.mComputedBorderPadding;
|
|
}
|
|
|
|
const nsMargin& Margin() const {
|
|
return mReflowState.mComputedMargin;
|
|
}
|
|
|
|
void UpdateMaxElementSize(const nsSize& aMaxElementSize);
|
|
|
|
void UpdateMaximumWidth(nscoord aMaximumWidth);
|
|
|
|
void RecoverVerticalMargins(nsLineBox* aLine,
|
|
PRBool aApplyTopMargin,
|
|
nscoord* aTopMarginResult,
|
|
nscoord* aBottomMarginResult);
|
|
|
|
void ComputeBlockAvailSpace(nsIFrame* aFrame,
|
|
nsSplittableType aSplitType,
|
|
const nsStyleDisplay* aDisplay,
|
|
nsRect& aResult);
|
|
|
|
void RecoverStateFrom(nsLineBox* aLine,
|
|
PRBool aApplyTopMargin,
|
|
nsRect* aDamageRect);
|
|
|
|
void AdvanceToNextLine() {
|
|
mLineNumber++;
|
|
}
|
|
|
|
PRBool IsImpactedByFloater() const;
|
|
|
|
nsLineBox* NewLineBox(nsIFrame* aFrame, PRInt32 aCount, PRBool aIsBlock);
|
|
|
|
void FreeLineBox(nsLineBox* aLine);
|
|
|
|
void StoreMaxElementSize(nsIFrame* aFloater, const nsSize& aSize) {
|
|
mBand.StoreMaxElementSize(mPresContext, aFloater, aSize);
|
|
}
|
|
|
|
//----------------------------------------
|
|
|
|
// This state is the "global" state computed once for the reflow of
|
|
// the block.
|
|
|
|
// The block frame that is using this object
|
|
nsBlockFrame* mBlock;
|
|
|
|
nsIPresContext* mPresContext;
|
|
|
|
const nsHTMLReflowState& mReflowState;
|
|
|
|
nsISpaceManager* mSpaceManager;
|
|
|
|
// The coordinates within the spacemanager where the block is being
|
|
// placed <b>after</b> taking into account the blocks border and
|
|
// padding. This, therefore, represents the inner "content area" (in
|
|
// spacemanager coordinates) where child frames will be placed,
|
|
// including child blocks and floaters.
|
|
nscoord mSpaceManagerX, mSpaceManagerY;
|
|
|
|
// XXX get rid of this
|
|
nsReflowStatus mReflowStatus;
|
|
|
|
nscoord mBottomEdge;
|
|
|
|
// The content area to reflow child frames within. The x/y
|
|
// coordinates are known to be mBorderPadding.left and
|
|
// mBorderPadding.top. The width/height may be NS_UNCONSTRAINEDSIZE
|
|
// if the container reflowing this frame has given the frame an
|
|
// unconstrained area.
|
|
nsSize mContentArea;
|
|
|
|
//----------------------------------------
|
|
|
|
// This state is "running" state updated by the reflow of each line
|
|
// in the block. This same state is "recovered" when a line is not
|
|
// dirty and is passed over during incremental reflow.
|
|
|
|
// The current line being reflowed
|
|
nsLineBox* mCurrentLine;
|
|
|
|
// The previous line just reflowed
|
|
nsLineBox* mPrevLine;
|
|
|
|
// The current Y coordinate in the block
|
|
nscoord mY;
|
|
|
|
// The available space within the current band.
|
|
nsRect mAvailSpaceRect;
|
|
|
|
// The maximum x-most of each line
|
|
nscoord mKidXMost;
|
|
|
|
// The combined area of all floaters placed so far
|
|
nsRect mFloaterCombinedArea;
|
|
|
|
// The y-coordinate of the last floater placed. We keep this around
|
|
// to enforce 9.5.1 rule [2]
|
|
nscoord mLastFloaterY;
|
|
|
|
// For unconstained-width reflow, we keep the right floaters
|
|
// combined area stored seperately.
|
|
PRBool mHaveRightFloaters;
|
|
nsRect mRightFloaterCombinedArea;
|
|
|
|
nsFloaterCacheFreeList mFloaterCacheFreeList;
|
|
|
|
// Previous child. This is used when pulling up a frame to update
|
|
// the sibling list.
|
|
nsIFrame* mPrevChild;
|
|
|
|
// The next immediate child frame that is the target of an
|
|
// incremental reflow command. Once that child has been reflowed we
|
|
// null this slot out.
|
|
nsIFrame* mNextRCFrame;
|
|
|
|
// The previous child frames collapsed bottom margin value.
|
|
nscoord mPrevBottomMargin;
|
|
|
|
// The current next-in-flow for the block. When lines are pulled
|
|
// from a next-in-flow, this is used to know which next-in-flow to
|
|
// pull from. When a next-in-flow is emptied of lines, we advance
|
|
// this to the next next-in-flow.
|
|
nsBlockFrame* mNextInFlow;
|
|
|
|
// The current band data for the current Y coordinate
|
|
nsBlockBandData mBand;
|
|
|
|
//----------------------------------------
|
|
|
|
// Temporary line-reflow state. This state is used during the reflow
|
|
// of a given line, but doesn't have meaning before or after.
|
|
|
|
// The list of floaters that are "current-line" floaters. These are
|
|
// added to the line after the line has been reflowed, to keep the
|
|
// list fiddling from being N^2.
|
|
nsFloaterCacheFreeList mCurrentLineFloaters;
|
|
|
|
// The list of floaters which are "below current-line"
|
|
// floaters. These are reflowed/placed after the line is reflowed
|
|
// and placed. Again, this is done to keep the list fiddling from
|
|
// being N^2.
|
|
nsFloaterCacheFreeList mBelowCurrentLineFloaters;
|
|
|
|
nsSize mMaxElementSize;
|
|
nscoord mMaximumWidth;
|
|
|
|
nscoord mMinLineHeight;
|
|
|
|
PRInt32 mLineNumber;
|
|
|
|
// block reflow state flags
|
|
#define BRS_UNCONSTRAINEDWIDTH 0x00000001
|
|
#define BRS_UNCONSTRAINEDHEIGHT 0x00000002
|
|
#define BRS_SHRINKWRAPWIDTH 0x00000004
|
|
#define BRS_NEEDRESIZEREFLOW 0x00000008
|
|
#define BRS_ISINLINEINCRREFLOW 0x00000010
|
|
#define BRS_NOWRAP 0x00000020
|
|
#define BRS_ISTOPMARGINROOT 0x00000040 // Is this frame a root for top/bottom margin collapsing?
|
|
#define BRS_ISBOTTOMMARGINROOT 0x00000080
|
|
#define BRS_APPLYTOPMARGIN 0x00000100 // See ShouldApplyTopMargin
|
|
#define BRS_COMPUTEMAXELEMENTSIZE 0x00000200
|
|
#define BRS_COMPUTEMAXWIDTH 0x00000400
|
|
#define BRS_LASTFLAG BRS_COMPUTEMAXWIDTH
|
|
|
|
PRInt16 mFlags;
|
|
|
|
void SetFlag(PRUint32 aFlag, PRBool aValue)
|
|
{
|
|
NS_ASSERTION(aFlag<=BRS_LASTFLAG, "bad flag");
|
|
NS_ASSERTION(aValue==PR_FALSE || aValue==PR_TRUE, "bad value");
|
|
if (aValue) { // set flag
|
|
mFlags |= aFlag;
|
|
}
|
|
else { // unset flag
|
|
mFlags &= ~aFlag;
|
|
}
|
|
}
|
|
|
|
PRBool GetFlag(PRUint32 aFlag) const
|
|
{
|
|
NS_ASSERTION(aFlag<=BRS_LASTFLAG, "bad flag");
|
|
PRBool result = (mFlags & aFlag);
|
|
if (result) return PR_TRUE;
|
|
return PR_FALSE;
|
|
}
|
|
};
|
|
|
|
#endif // nsBlockReflowState_h__
|