зеркало из https://github.com/mozilla/pjs.git
Putting back code that was backed out last week.
-a leaf
This commit is contained in:
Родитель
02798c9177
Коммит
7ec518aa59
|
@ -44,7 +44,7 @@
|
|||
#include "nsHTMLAtoms.h"
|
||||
#include "nsXULAtoms.h"
|
||||
|
||||
nsBox::nsBox(nsIPresShell* aShell):mParentBox(nsnull),mNextChild(nsnull),mMouseThrough(sometimes)
|
||||
nsBox::nsBox(nsIPresShell* aShell):mParentBox(nsnull),mNextChild(nsnull),mMouseThrough(unset)
|
||||
{
|
||||
//mX = 0;
|
||||
//mY = 0;
|
||||
|
@ -96,36 +96,69 @@ nsBox::MarkDirty(nsBoxLayoutState& aState)
|
|||
state |= NS_FRAME_IS_DIRTY;
|
||||
frame->SetFrameState(state);
|
||||
|
||||
nsIFrame* parent = nsnull;
|
||||
frame->GetParent(&parent);
|
||||
nsCOMPtr<nsIPresShell> shell;
|
||||
aState.GetPresShell(getter_AddRefs(shell));
|
||||
nsCOMPtr<nsIBoxLayout> layout;
|
||||
GetLayoutManager(getter_AddRefs(layout));
|
||||
if (layout)
|
||||
layout->BecameDirty(this, aState);
|
||||
|
||||
return parent->ReflowDirtyChild(shell, frame);
|
||||
if (state & NS_FRAME_HAS_DIRTY_CHILDREN)
|
||||
return NS_OK;
|
||||
|
||||
nsIBox* parent = nsnull;
|
||||
GetParentBox(&parent);
|
||||
if (parent)
|
||||
return parent->RelayoutDirtyChild(aState, this);
|
||||
else {
|
||||
nsIFrame* parent = nsnull;
|
||||
frame->GetParent(&parent);
|
||||
nsCOMPtr<nsIPresShell> shell;
|
||||
aState.GetPresShell(getter_AddRefs(shell));
|
||||
return parent->ReflowDirtyChild(shell, frame);
|
||||
}
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsBox::MarkDirtyChildren(nsBoxLayoutState& aState)
|
||||
{
|
||||
nsFrameState state;
|
||||
nsIFrame* frame;
|
||||
GetFrame(&frame);
|
||||
frame->GetFrameState(&state);
|
||||
return RelayoutDirtyChild(aState, nsnull);
|
||||
}
|
||||
|
||||
// only reflow if we aren't already dirty.
|
||||
if (state & NS_FRAME_HAS_DIRTY_CHILDREN)
|
||||
return NS_OK;
|
||||
NS_IMETHODIMP
|
||||
nsBox::RelayoutDirtyChild(nsBoxLayoutState& aState, nsIBox* aChild)
|
||||
{
|
||||
nsFrameState state;
|
||||
nsIFrame* frame;
|
||||
GetFrame(&frame);
|
||||
frame->GetFrameState(&state);
|
||||
|
||||
state |= NS_FRAME_HAS_DIRTY_CHILDREN;
|
||||
frame->SetFrameState(state);
|
||||
// if we are not dirty mark ourselves dirty and tell our parent we are dirty too.
|
||||
if (!(state & NS_FRAME_HAS_DIRTY_CHILDREN)) {
|
||||
// Mark yourself as dirty and needing to be recalculated
|
||||
state |= NS_FRAME_HAS_DIRTY_CHILDREN;
|
||||
frame->SetFrameState(state);
|
||||
NeedsRecalc();
|
||||
|
||||
NeedsRecalc();
|
||||
nsIFrame* parent = nsnull;
|
||||
frame->GetParent(&parent);
|
||||
nsCOMPtr<nsIPresShell> shell;
|
||||
aState.GetPresShell(getter_AddRefs(shell));
|
||||
if (aChild != nsnull) {
|
||||
nsCOMPtr<nsIBoxLayout> layout;
|
||||
GetLayoutManager(getter_AddRefs(layout));
|
||||
if (layout)
|
||||
layout->ChildBecameDirty(this, aState, aChild);
|
||||
}
|
||||
|
||||
return parent->ReflowDirtyChild(shell, frame);
|
||||
nsIBox* parent = nsnull;
|
||||
GetParentBox(&parent);
|
||||
if (parent)
|
||||
return parent->RelayoutDirtyChild(aState, this);
|
||||
else {
|
||||
nsIFrame* parent = nsnull;
|
||||
frame->GetParent(&parent);
|
||||
nsCOMPtr<nsIPresShell> shell;
|
||||
aState.GetPresShell(getter_AddRefs(shell));
|
||||
return parent->ReflowDirtyChild(shell, frame);
|
||||
}
|
||||
}
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
|
@ -547,6 +580,7 @@ NS_IMETHODIMP
|
|||
nsBox::GetFlex(nsBoxLayoutState& aState, nscoord& aFlex)
|
||||
{
|
||||
aFlex = 0;
|
||||
GetDefaultFlex(aFlex);
|
||||
PRBool collapsed = PR_FALSE;
|
||||
nsIBox::AddCSSFlex(aState, this, aFlex);
|
||||
|
||||
|
@ -1011,6 +1045,40 @@ nsBox::GetDebug(PRBool& aDebug)
|
|||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsBox::GetMouseThrough(PRBool& aMouseThrough)
|
||||
{
|
||||
switch(mMouseThrough)
|
||||
{
|
||||
case always:
|
||||
aMouseThrough = PR_TRUE;
|
||||
return NS_OK;
|
||||
case never:
|
||||
aMouseThrough = PR_FALSE;
|
||||
return NS_OK;
|
||||
case unset:
|
||||
{
|
||||
nsIBox* parent = nsnull;
|
||||
GetParentBox(&parent);
|
||||
if (parent)
|
||||
return parent->GetMouseThrough(aMouseThrough);
|
||||
else {
|
||||
aMouseThrough = PR_FALSE;
|
||||
return NS_OK;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
PRBool
|
||||
nsBox::GetDefaultFlex(PRInt32& aFlex)
|
||||
{
|
||||
aFlex = 0;
|
||||
return PR_TRUE;
|
||||
}
|
||||
|
||||
// nsISupports
|
||||
NS_IMETHODIMP_(nsrefcnt)
|
||||
nsBox::AddRef(void)
|
||||
|
|
|
@ -73,6 +73,8 @@ public:
|
|||
NS_IMETHOD NeedsRecalc();
|
||||
NS_IMETHOD GetDebugBoxAt(const nsPoint& aPoint, nsIBox** aBox);
|
||||
NS_IMETHOD GetDebug(PRBool& aDebug);
|
||||
NS_IMETHOD RelayoutDirtyChild(nsBoxLayoutState& aState, nsIBox* aChild);
|
||||
NS_IMETHOD GetMouseThrough(PRBool& aMouseThrough);
|
||||
|
||||
// XXX Eventually these will move into nsIFrame.
|
||||
// These methods are used for XBL <children>.
|
||||
|
@ -105,10 +107,11 @@ public:
|
|||
protected:
|
||||
virtual PRBool GetWasCollapsed(nsBoxLayoutState& aState);
|
||||
virtual void SetWasCollapsed(nsBoxLayoutState& aState, PRBool aWas);
|
||||
virtual PRBool GetDefaultFlex(PRInt32& aFlex);
|
||||
|
||||
enum eMouseThrough {
|
||||
unset,
|
||||
never,
|
||||
sometimes,
|
||||
always
|
||||
};
|
||||
|
||||
|
|
|
@ -153,6 +153,8 @@ public:
|
|||
void DrawLine(nsIRenderingContext& aRenderingContext, PRBool aHorizontal, nscoord x1, nscoord y1, nscoord x2, nscoord y2);
|
||||
void FillRect(nsIRenderingContext& aRenderingContext, PRBool aHorizontal, nscoord x, nscoord y, nscoord width, nscoord height);
|
||||
|
||||
nsIBox* GetBoxForFrame(nsIFrame* aFrame, PRBool& aIsAdaptor);
|
||||
|
||||
nsBoxFrame::Halignment GetHAlign();
|
||||
nsBoxFrame::Valignment GetVAlign();
|
||||
|
||||
|
@ -253,7 +255,6 @@ nsBoxFrame::~nsBoxFrame()
|
|||
NS_ASSERTION(mInner == nsnull,"Error Destroy was never called on this Frame!!!");
|
||||
}
|
||||
|
||||
|
||||
NS_IMETHODIMP
|
||||
nsBoxFrame::GetVAlign(Valignment& aAlign)
|
||||
{
|
||||
|
@ -281,7 +282,8 @@ nsBoxFrame::SetInitialChildList(nsIPresContext* aPresContext,
|
|||
nsresult r = nsHTMLContainerFrame::SetInitialChildList(aPresContext, aListName, aChildList);
|
||||
if (r == NS_OK) {
|
||||
// initialize our list of infos.
|
||||
InitChildren(shell, aChildList);
|
||||
nsBoxLayoutState state(shell);
|
||||
InitChildren(state, aChildList);
|
||||
} else {
|
||||
printf("Warning add child failed!!\n");
|
||||
}
|
||||
|
@ -355,7 +357,7 @@ nsBoxFrame::Init(nsIPresContext* aPresContext,
|
|||
mInner->GetDebugPref(aPresContext);
|
||||
|
||||
|
||||
mMouseThrough = always;
|
||||
mMouseThrough = unset;
|
||||
|
||||
if (mContent) {
|
||||
nsAutoString value;
|
||||
|
@ -579,15 +581,10 @@ nsBoxFrame::GetInitialAutoStretch(PRBool& aStretch)
|
|||
NS_IMETHODIMP
|
||||
nsBoxFrame::ReflowDirtyChild(nsIPresShell* aPresShell, nsIFrame* aChild)
|
||||
{
|
||||
// if we are not dirty mark ourselves dirty and tell our parent we are dirty too.
|
||||
if (!(mState & NS_FRAME_HAS_DIRTY_CHILDREN)) {
|
||||
// Mark yourself as dirty and needing to be recalculated
|
||||
mState |= NS_FRAME_HAS_DIRTY_CHILDREN;
|
||||
NeedsRecalc();
|
||||
return mParent->ReflowDirtyChild(aPresShell, this);
|
||||
}
|
||||
|
||||
return NS_OK;
|
||||
nsCOMPtr<nsIPresContext> context;
|
||||
aPresShell->GetPresContext(getter_AddRefs(context));
|
||||
nsBoxLayoutState state(context);
|
||||
return RelayoutDirtyChild(state, this);
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
|
@ -851,7 +848,9 @@ nsBoxFrame::Destroy(nsIPresContext* aPresContext)
|
|||
// if we are root remove 1 from the debug count.
|
||||
if (mState & NS_STATE_IS_ROOT)
|
||||
mInner->GetDebugPref(aPresContext);
|
||||
|
||||
|
||||
SetLayoutManager(nsnull);
|
||||
|
||||
// recycle the Inner via the shell's arena.
|
||||
nsCOMPtr<nsIPresShell> shell;
|
||||
aPresContext->GetShell(getter_AddRefs(shell));
|
||||
|
@ -888,11 +887,13 @@ nsBoxFrame::SetDebug(nsBoxLayoutState& aState, PRBool aDebug)
|
|||
NS_IMETHODIMP
|
||||
nsBoxFrame::NeedsRecalc()
|
||||
{
|
||||
SizeNeedsRecalc(mInner->mPrefSize);
|
||||
SizeNeedsRecalc(mInner->mMinSize);
|
||||
SizeNeedsRecalc(mInner->mMaxSize);
|
||||
CoordNeedsRecalc(mInner->mFlex);
|
||||
CoordNeedsRecalc(mInner->mAscent);
|
||||
if (mInner) {
|
||||
SizeNeedsRecalc(mInner->mPrefSize);
|
||||
SizeNeedsRecalc(mInner->mMinSize);
|
||||
SizeNeedsRecalc(mInner->mMaxSize);
|
||||
CoordNeedsRecalc(mInner->mFlex);
|
||||
CoordNeedsRecalc(mInner->mAscent);
|
||||
}
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
|
@ -910,7 +911,8 @@ nsBoxFrame::RemoveFrame(nsIPresContext* aPresContext,
|
|||
SanityCheck(mFrames);
|
||||
|
||||
// remove child from our info list
|
||||
Remove(&aPresShell, aOldFrame);
|
||||
nsBoxLayoutState state(aPresContext);
|
||||
Remove(state, aOldFrame);
|
||||
|
||||
// remove the child frame
|
||||
mFrames.DestroyFrame(aPresContext, aOldFrame);
|
||||
|
@ -918,7 +920,6 @@ nsBoxFrame::RemoveFrame(nsIPresContext* aPresContext,
|
|||
SanityCheck(mFrames);
|
||||
|
||||
// mark us dirty and generate a reflow command
|
||||
nsBoxLayoutState state(aPresContext);
|
||||
MarkDirtyChildren(state);
|
||||
MarkDirty(state);
|
||||
return NS_OK;
|
||||
|
@ -945,13 +946,12 @@ nsBoxFrame::InsertFrames(nsIPresContext* aPresContext,
|
|||
}
|
||||
|
||||
// insert the frames to our info list
|
||||
Insert(&aPresShell, aPrevFrame, aFrameList);
|
||||
nsBoxLayoutState state(aPresContext);
|
||||
Insert(state, aPrevFrame, aFrameList);
|
||||
|
||||
// insert the frames in out regular frame list
|
||||
mFrames.InsertFrames(this, aPrevFrame, aFrameList);
|
||||
|
||||
nsBoxLayoutState state(aPresContext);
|
||||
|
||||
// if we are in debug make sure our children are in debug as well.
|
||||
if (mState & NS_STATE_CURRENTLY_IN_DEBUG)
|
||||
SetDebugOnChildList(state, mFirstChild, PR_TRUE);
|
||||
|
@ -979,13 +979,12 @@ nsBoxFrame::AppendFrames(nsIPresContext* aPresContext,
|
|||
SanityCheck(mFrames);
|
||||
|
||||
// append them after
|
||||
Append(&aPresShell,aFrameList);
|
||||
nsBoxLayoutState state(aPresContext);
|
||||
Append(state,aFrameList);
|
||||
|
||||
// append in regular frames
|
||||
mFrames.AppendFrames(this, aFrameList);
|
||||
|
||||
nsBoxLayoutState state(aPresContext);
|
||||
|
||||
// if we are in debug make sure our children are in debug as well.
|
||||
if (mState & NS_STATE_CURRENTLY_IN_DEBUG)
|
||||
SetDebugOnChildList(state, mFirstChild, PR_TRUE);
|
||||
|
@ -1429,99 +1428,132 @@ nsBoxFrame::GetFrameForPoint(nsIPresContext* aPresContext,
|
|||
}
|
||||
}
|
||||
|
||||
nsIFrame *kid, *hit = nsnull;
|
||||
nsPoint tmp;
|
||||
|
||||
if (mMouseThrough == never)
|
||||
{
|
||||
*aFrame = this;
|
||||
return NS_OK;
|
||||
FirstChild(aPresContext, nsnull, &kid);
|
||||
*aFrame = nsnull;
|
||||
tmp.MoveTo(aPoint.x - mRect.x, aPoint.y - mRect.y);
|
||||
while (nsnull != kid) {
|
||||
// have we hit a child before
|
||||
PRBool haveKid = (hit != nsnull);
|
||||
nsresult rv = kid->GetFrameForPoint(aPresContext, tmp, aWhichLayer, &hit);
|
||||
|
||||
if (NS_SUCCEEDED(rv) && hit) {
|
||||
if (!haveKid)
|
||||
*aFrame = hit;
|
||||
else
|
||||
{
|
||||
// if the kid had a child before see if this child has mouse
|
||||
// though.
|
||||
nsresult rv = NS_OK;
|
||||
PRBool isAdaptor = PR_FALSE;
|
||||
nsCOMPtr<nsIBox> box = mInner->GetBoxForFrame(hit, isAdaptor);
|
||||
if (box) {
|
||||
PRBool mouseThrough = PR_FALSE;
|
||||
box->GetMouseThrough(mouseThrough);
|
||||
// if the child says it can never mouse though ignore it.
|
||||
if (!mouseThrough)
|
||||
*aFrame = hit;
|
||||
else {
|
||||
/*
|
||||
// otherwise see if it has an opaque parent.
|
||||
nsIFrame* child = hit;
|
||||
while(child) {
|
||||
if (child == this)
|
||||
break;
|
||||
|
||||
const nsStyleColor* color = nsnull;
|
||||
child->GetStyleData(eStyleStruct_Color, (const nsStyleStruct*&)color);
|
||||
PRBool transparentBG = (!color || NS_STYLE_BG_COLOR_TRANSPARENT ==
|
||||
(color->mBackgroundFlags & NS_STYLE_BG_COLOR_TRANSPARENT));
|
||||
|
||||
if (!transparentBG) {
|
||||
*aFrame = hit;
|
||||
break;
|
||||
}
|
||||
child->GetParent(&child);
|
||||
}
|
||||
*/
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
kid->GetNextSibling(&kid);
|
||||
}
|
||||
|
||||
// This won't work.
|
||||
nsresult rv = GetFrameForPointUsing(aPresContext, aPoint, nsnull, aWhichLayer, PR_FALSE, aFrame);
|
||||
|
||||
/*
|
||||
nsRect r(0,0,mRect.width, mRect.height);
|
||||
|
||||
// if it is not inside us fail
|
||||
if (!r.Contains(aPoint)) {
|
||||
return NS_ERROR_FAILURE;
|
||||
if (*aFrame) {
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
// is it inside our border, padding, and debugborder or insets?
|
||||
nsMargin im(0,0,0,0);
|
||||
nsBoxLayoutState state(aPresContext);
|
||||
GetInset(im);
|
||||
nsMargin border(0,0,0,0);
|
||||
GetBorderAndPadding(border);
|
||||
r.Deflate(im);
|
||||
r.Deflate(border);
|
||||
|
||||
// no? Then it must be in our border so return us.
|
||||
if (!r.Contains(aPoint)) {
|
||||
// if no kids were hit then select us
|
||||
const nsStyleDisplay* disp = (const nsStyleDisplay*)
|
||||
mStyleContext->GetStyleData(eStyleStruct_Display);
|
||||
if (disp->IsVisible()) {
|
||||
*aFrame = this;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
// ok lets look throught the children
|
||||
*aFrame = nsnull;
|
||||
nsIBox* child = nsnull;
|
||||
GetChildBox(&child);
|
||||
nsPoint tmp;
|
||||
nsIFrame *frame = nsnull, *hit = nsnull;
|
||||
tmp.MoveTo(aPoint.x - mRect.x, aPoint.y - mRect.y);
|
||||
while(child)
|
||||
{
|
||||
child->GetFrame(&frame);
|
||||
nsresult rv = frame->GetFrameForPoint(aPresContext, tmp, aWhichLayer, &hit);
|
||||
|
||||
if (NS_SUCCEEDED(rv) && hit) {
|
||||
*aFrame = hit;
|
||||
}
|
||||
|
||||
child->GetNextBox(&child);
|
||||
}
|
||||
|
||||
// found it.
|
||||
if (hit)
|
||||
return NS_OK;
|
||||
|
||||
*/
|
||||
|
||||
if (rv != NS_ERROR_FAILURE)
|
||||
return rv;
|
||||
|
||||
// see if it is in our border, padding, or inset
|
||||
nsRect r(mRect);
|
||||
nsMargin m;
|
||||
GetInset(m);
|
||||
r.Deflate(m);
|
||||
GetBorderAndPadding(m);
|
||||
r.Deflate(m);
|
||||
if (!r.Contains(aPoint)) {
|
||||
*aFrame = this;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
if (mMouseThrough == sometimes)
|
||||
{
|
||||
*aFrame = this;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
const nsStyleColor* color = (const nsStyleColor*)
|
||||
mStyleContext->GetStyleData(eStyleStruct_Color);
|
||||
PRBool transparentBG = NS_STYLE_BG_COLOR_TRANSPARENT ==
|
||||
(color->mBackgroundFlags & NS_STYLE_BG_COLOR_TRANSPARENT);
|
||||
|
||||
if (!transparentBG)
|
||||
{
|
||||
*aFrame = this;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
nsIBox*
|
||||
nsBoxFrameInner::GetBoxForFrame(nsIFrame* aFrame, PRBool& aIsAdaptor)
|
||||
{
|
||||
if (aFrame == nsnull)
|
||||
return nsnull;
|
||||
|
||||
nsIBox* ibox = nsnull;
|
||||
if (NS_FAILED(aFrame->QueryInterface(NS_GET_IID(nsIBox), (void**)&ibox))) {
|
||||
aIsAdaptor = PR_TRUE;
|
||||
|
||||
// if we hit a non box. Find the box in out last container
|
||||
// and clear its cache.
|
||||
nsIFrame* parent = nsnull;
|
||||
aFrame->GetParent(&parent);
|
||||
nsIBox* parentBox = nsnull;
|
||||
if (NS_FAILED(parent->QueryInterface(NS_GET_IID(nsIBox), (void**)&parentBox)))
|
||||
return nsnull;
|
||||
|
||||
if (parentBox) {
|
||||
nsIBox* start = nsnull;
|
||||
parentBox->GetChildBox(&start);
|
||||
while (start) {
|
||||
nsIFrame* frame = nsnull;
|
||||
start->GetFrame(&frame);
|
||||
if (frame == aFrame) {
|
||||
ibox = start;
|
||||
break;
|
||||
}
|
||||
|
||||
start->GetNextBox(&start);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return ibox;
|
||||
}
|
||||
|
||||
/*
|
||||
NS_IMETHODIMP
|
||||
nsBoxFrame::GetMouseThrough(PRBool& aMouseThrough)
|
||||
{
|
||||
const nsStyleColor* color = (const nsStyleColor*)
|
||||
mStyleContext->GetStyleData(eStyleStruct_Color);
|
||||
PRBool transparentBG = NS_STYLE_BG_COLOR_TRANSPARENT ==
|
||||
(color->mBackgroundFlags & NS_STYLE_BG_COLOR_TRANSPARENT);
|
||||
|
||||
if (!transparentBG)
|
||||
aMouseThrough = never;
|
||||
else
|
||||
return nsBox::GetMouseThrough(aMouseThrough);
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
*/
|
||||
|
||||
|
||||
|
||||
|
||||
NS_IMETHODIMP
|
||||
|
@ -1619,7 +1651,8 @@ nsBoxFrameInner::operator new(size_t sz, nsIPresShell* aPresShell)
|
|||
void
|
||||
nsBoxFrameInner::Recycle(nsIPresShell* aPresShell)
|
||||
{
|
||||
mOuter->ClearChildren(aPresShell);
|
||||
nsBoxLayoutState state(aPresShell);
|
||||
mOuter->ClearChildren(state);
|
||||
|
||||
delete this;
|
||||
nsBoxLayoutState::RecycleFreedMemory(aPresShell, this);
|
||||
|
|
|
@ -90,6 +90,7 @@ public:
|
|||
NS_IMETHOD GetInset(nsMargin& aInset);
|
||||
NS_IMETHOD Layout(nsBoxLayoutState& aBoxLayoutState);
|
||||
NS_IMETHOD GetDebug(PRBool& aDebug);
|
||||
//NS_IMETHOD GetMouseThrough(PRBool& aMouseThrough);
|
||||
|
||||
// ----- child and sibling operations ---
|
||||
|
||||
|
@ -160,7 +161,6 @@ public:
|
|||
|
||||
virtual PRBool IsHorizontal() const;
|
||||
|
||||
|
||||
virtual ~nsBoxFrame();
|
||||
|
||||
virtual nsresult GetContentOf(nsIContent** aContent);
|
||||
|
|
|
@ -49,6 +49,11 @@ nsBoxLayoutState::nsBoxLayoutState(const nsBoxLayoutState& aState)
|
|||
mMaxElementSize = aState.mMaxElementSize;
|
||||
}
|
||||
|
||||
nsBoxLayoutState::nsBoxLayoutState(nsIPresShell* aShell):mReflowState(nsnull), mMaxElementSize(nsnull)
|
||||
{
|
||||
aShell->GetPresContext(getter_AddRefs(mPresContext));
|
||||
}
|
||||
|
||||
nsBoxLayoutState::nsBoxLayoutState(nsIPresContext* aPresContext, const nsHTMLReflowState& aReflowState, nsHTMLReflowMetrics& aDesiredSize):mReflowState(&aReflowState),mPresContext(aPresContext),mType(Dirty)
|
||||
{
|
||||
mMaxElementSize = aDesiredSize.maxElementSize;
|
||||
|
@ -73,27 +78,6 @@ nsBoxLayoutState::HandleReflow(nsIBox* aRootBox, PRBool aCoelesce)
|
|||
nsIReflowCommand::ReflowType type;
|
||||
mReflowState->reflowCommand->GetType(type);
|
||||
|
||||
// atempt to coelesce style changes and reflows
|
||||
// see if the target is a box
|
||||
/*
|
||||
PRBool isAdaptor = PR_FALSE;
|
||||
nsIBox* box = GetTargetBox(mReflowState->reflowCommand, isAdaptor);
|
||||
// if it is mark it dirty. Generating a dirty reflow targeted at us unless on is already
|
||||
// done.
|
||||
if (box && box != aRootBox) {
|
||||
if (type == nsIReflowCommand::StyleChanged) {
|
||||
// could be a visiblity change need to dirty
|
||||
// parent so it gets redrawn.
|
||||
nsIBox* parent;
|
||||
box->GetParentBox(&parent);
|
||||
parent->MarkDirty(*this);
|
||||
DirtyAllChildren(*this, box);
|
||||
} else
|
||||
box->MarkDirty(*this);
|
||||
return PR_TRUE;
|
||||
}
|
||||
*/
|
||||
|
||||
// ok if the target was not a box. Then unwind it down
|
||||
if (UnWind(mReflowState->reflowCommand, aRootBox, aCoelesce)) {
|
||||
mType = Dirty;
|
||||
|
@ -118,6 +102,11 @@ nsBoxLayoutState::HandleReflow(nsIBox* aRootBox, PRBool aCoelesce)
|
|||
mType = Initial;
|
||||
break;
|
||||
|
||||
case eReflowReason_StyleChange:
|
||||
printf("STYLE CHANGE REFLOW. Blowing away all box caches!!\n");
|
||||
DirtyAllChildren(*this, aRootBox);
|
||||
// fall through to dirty
|
||||
|
||||
default:
|
||||
mType = Dirty;
|
||||
}
|
||||
|
@ -174,11 +163,25 @@ nsBoxLayoutState::UnWind(nsIReflowCommand* aCommand, nsIBox* aBox, PRBool aCoele
|
|||
ibox->MarkDirty(*this);
|
||||
|
||||
if (type == nsIReflowCommand::StyleChanged) {
|
||||
// could be a visiblity change need to dirty
|
||||
// parent so it gets redrawn.
|
||||
// could be a visiblity change. Like collapse so we need to dirty
|
||||
// parent so it gets redrawn. But be carefull we
|
||||
// don't want to just mark dirty that would notify the
|
||||
// box and it would notify its layout manager. This would
|
||||
// be really bad for grid because it would blow away
|
||||
// all is cached infomation for is colums and rows. Because the
|
||||
// our parent is most likely a rows or columns and it will think
|
||||
// its child is getting bigger or something.
|
||||
nsIBox* parent;
|
||||
ibox->GetParentBox(&parent);
|
||||
parent->MarkDirty(*this);
|
||||
if (parent) {
|
||||
nsFrameState parentState;
|
||||
nsIFrame* parentFrame;
|
||||
parent->GetFrame(&parentFrame);
|
||||
parentFrame->GetFrameState(&parentState);
|
||||
parentState |= NS_FRAME_IS_DIRTY;
|
||||
parentFrame->SetFrameState(parentState);
|
||||
}
|
||||
|
||||
DirtyAllChildren(*this, ibox);
|
||||
}
|
||||
|
||||
|
|
|
@ -53,11 +53,12 @@ public:
|
|||
|
||||
nsBoxLayoutState(nsIPresContext* aPresContext, const nsHTMLReflowState& aReflowState, nsHTMLReflowMetrics& aDesiredSize);
|
||||
nsBoxLayoutState(nsIPresContext* aPresContext);
|
||||
nsBoxLayoutState(nsIPresShell* aShell);
|
||||
nsBoxLayoutState(const nsBoxLayoutState& aState);
|
||||
|
||||
virtual PRBool HandleReflow(nsIBox* aRootBox, PRBool aCoalesce);
|
||||
|
||||
virtual nsIPresContext* GetPresContext() { return mPresContext; }
|
||||
virtual nsIPresContext* GetPresContext() { return mPresContext.get(); }
|
||||
virtual nsresult GetPresShell(nsIPresShell** aShell);
|
||||
virtual void GetMaxElementSize(nsSize** aMaxElementSize);
|
||||
|
||||
|
@ -79,7 +80,7 @@ private:
|
|||
nsIBox* GetTargetBox(nsIReflowCommand* mCommand, PRBool& aIsAdaptor);
|
||||
nsIBox* GetBoxForFrame(nsIFrame* aFrame, PRBool& aIsAdaptor);
|
||||
|
||||
nsIPresContext* mPresContext;
|
||||
nsCOMPtr<nsIPresContext> mPresContext;
|
||||
const nsHTMLReflowState* mReflowState;
|
||||
eBoxLayoutReason mType;
|
||||
nsSize* mMaxElementSize;
|
||||
|
|
|
@ -59,6 +59,7 @@ nsBoxToBlockAdaptor::nsBoxToBlockAdaptor(nsIPresShell* aPresShell, nsIFrame* aFr
|
|||
mFrame = aFrame;
|
||||
mSpaceManager = nsnull;
|
||||
mWasCollapsed = PR_FALSE;
|
||||
mCachedMaxElementHeight = 0;
|
||||
NeedsRecalc();
|
||||
}
|
||||
|
||||
|
@ -165,11 +166,16 @@ nsBoxToBlockAdaptor::GetPrefSize(nsBoxLayoutState& aState, nsSize& aSize)
|
|||
NS_INTRINSICSIZE,
|
||||
PR_FALSE);
|
||||
|
||||
if (currentSize) {
|
||||
if (currentSize) {
|
||||
desiredSize.maxElementSize = nsnull;
|
||||
|
||||
if (size.width > currentSize->width)
|
||||
currentSize->width = size.width;
|
||||
|
||||
if (size.height > currentSize->height)
|
||||
currentSize->height = size.height;
|
||||
|
||||
mCachedMaxElementHeight = size.height;
|
||||
}
|
||||
|
||||
nsFrameState frameState = 0;
|
||||
|
@ -310,9 +316,14 @@ nsBoxToBlockAdaptor::Layout(nsBoxLayoutState& aState)
|
|||
desiredSize.maxElementSize = nsnull;
|
||||
|
||||
if (size.width > currentSize->width)
|
||||
currentSize->width = size.width;
|
||||
currentSize->width = size.width;
|
||||
|
||||
if (mCachedMaxElementHeight > currentSize->height) {
|
||||
currentSize->height = mCachedMaxElementHeight;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
mAscent = desiredSize.ascent;
|
||||
mFrame->SizeTo(presContext, desiredSize.width, desiredSize.height);
|
||||
}
|
||||
|
|
|
@ -82,7 +82,7 @@ protected:
|
|||
nsSize mLastSize;
|
||||
nscoord mMinWidth;
|
||||
PRBool mWasCollapsed;
|
||||
|
||||
nscoord mCachedMaxElementHeight;
|
||||
};
|
||||
|
||||
#endif
|
||||
|
|
|
@ -89,15 +89,18 @@ nsContainerBox::GetChildCount()
|
|||
}
|
||||
|
||||
PRInt32
|
||||
nsContainerBox::CreateBoxList(nsIPresShell* aPresShell, nsIFrame* aFrameList, nsIBox*& aFirst, nsIBox*& aLast)
|
||||
nsContainerBox::CreateBoxList(nsBoxLayoutState& aState, nsIFrame* aFrameList, nsIBox*& aFirst, nsIBox*& aLast)
|
||||
{
|
||||
nsCOMPtr<nsIPresShell> shell;
|
||||
aState.GetPresShell(getter_AddRefs(shell));
|
||||
|
||||
PRInt32 count = 0;
|
||||
if (aFrameList) {
|
||||
nsIBox* ibox = nsnull;
|
||||
if (NS_SUCCEEDED(aFrameList->QueryInterface(NS_GET_IID(nsIBox), (void**)&ibox)) && ibox)
|
||||
aFirst = ibox;
|
||||
else
|
||||
aFirst = new (aPresShell) nsBoxToBlockAdaptor(aPresShell, aFrameList);
|
||||
aFirst = new (shell) nsBoxToBlockAdaptor(shell, aFrameList);
|
||||
|
||||
aFirst->SetParentBox(this);
|
||||
|
||||
|
@ -111,7 +114,7 @@ nsContainerBox::CreateBoxList(nsIPresShell* aPresShell, nsIFrame* aFrameList, ns
|
|||
if (NS_SUCCEEDED(aFrameList->QueryInterface(NS_GET_IID(nsIBox), (void**)&ibox)) && ibox)
|
||||
aLast = ibox;
|
||||
else
|
||||
aLast = new (aPresShell) nsBoxToBlockAdaptor(aPresShell, aFrameList);
|
||||
aLast = new (shell) nsBoxToBlockAdaptor(shell, aFrameList);
|
||||
|
||||
aLast->SetParentBox(this);
|
||||
|
||||
|
@ -217,15 +220,15 @@ nsContainerBox::GetIndexOf(nsIBox* aBox)
|
|||
}
|
||||
|
||||
void
|
||||
nsContainerBox::Remove(nsIPresShell* aShell, nsIFrame* aFrame)
|
||||
nsContainerBox::Remove(nsBoxLayoutState& aState, nsIFrame* aFrame)
|
||||
{
|
||||
// get the info before the frame
|
||||
nsIBox* prevBox = GetPrevious(aFrame);
|
||||
RemoveAfter(aShell, prevBox);
|
||||
RemoveAfter(aState, prevBox);
|
||||
}
|
||||
|
||||
void
|
||||
nsContainerBox::Insert(nsIPresShell* aShell, nsIFrame* aPrevFrame, nsIFrame* aFrameList)
|
||||
nsContainerBox::Insert(nsBoxLayoutState& aState, nsIFrame* aPrevFrame, nsIFrame* aFrameList)
|
||||
{
|
||||
nsIBox* prevBox = GetBox(aPrevFrame);
|
||||
//NS_ASSERTION(aPrevFrame == nsnull || prevBox,"Error! The previous frame given is not in our list!");
|
||||
|
@ -234,15 +237,15 @@ nsContainerBox::Insert(nsIPresShell* aShell, nsIFrame* aPrevFrame, nsIFrame* aFr
|
|||
// if no previous frame then we are inserting in front
|
||||
if (prevBox == nsnull) {
|
||||
// prepend them
|
||||
Prepend(aShell, aFrameList);
|
||||
Prepend(aState, aFrameList);
|
||||
} else {
|
||||
// insert insert after previous info
|
||||
InsertAfter(aShell, prevBox, aFrameList);
|
||||
InsertAfter(aState, prevBox, aFrameList);
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
nsContainerBox::RemoveAfter(nsIPresShell* aPresShell, nsIBox* aPrevious)
|
||||
nsContainerBox::RemoveAfter(nsBoxLayoutState& aState, nsIBox* aPrevious)
|
||||
{
|
||||
nsIBox* toDelete = nsnull;
|
||||
|
||||
|
@ -271,15 +274,24 @@ nsContainerBox::RemoveAfter(nsIPresShell* aPresShell, nsIBox* aPrevious)
|
|||
// recycle adaptors
|
||||
nsIBoxToBlockAdaptor* adaptor = nsnull;
|
||||
|
||||
if (NS_SUCCEEDED(toDelete->QueryInterface(NS_GET_IID(nsIBoxToBlockAdaptor), (void**)&adaptor)) && adaptor)
|
||||
adaptor->Recycle(aPresShell);
|
||||
if (NS_SUCCEEDED(toDelete->QueryInterface(NS_GET_IID(nsIBoxToBlockAdaptor), (void**)&adaptor)) && adaptor) {
|
||||
nsCOMPtr<nsIPresShell> shell;
|
||||
aState.GetPresShell(getter_AddRefs(shell));
|
||||
adaptor->Recycle(shell);
|
||||
}
|
||||
|
||||
mChildCount--;
|
||||
|
||||
if (mLayoutManager)
|
||||
mLayoutManager->ChildrenRemoved(this, aState, toDelete);
|
||||
}
|
||||
|
||||
void
|
||||
nsContainerBox::ClearChildren(nsIPresShell* aShell)
|
||||
nsContainerBox::ClearChildren(nsBoxLayoutState& aState)
|
||||
{
|
||||
if (mFirstChild && mLayoutManager)
|
||||
mLayoutManager->ChildrenRemoved(this, aState, mFirstChild);
|
||||
|
||||
nsIBox* box = mFirstChild;
|
||||
while(box) {
|
||||
nsIBox* it = box;
|
||||
|
@ -287,8 +299,11 @@ nsContainerBox::ClearChildren(nsIPresShell* aShell)
|
|||
// recycle adaptors
|
||||
nsIBoxToBlockAdaptor* adaptor = nsnull;
|
||||
|
||||
if (NS_SUCCEEDED(it->QueryInterface(NS_GET_IID(nsIBoxToBlockAdaptor), (void**)&adaptor)) && adaptor)
|
||||
adaptor->Recycle(aShell);
|
||||
if (NS_SUCCEEDED(it->QueryInterface(NS_GET_IID(nsIBoxToBlockAdaptor), (void**)&adaptor)) && adaptor) {
|
||||
nsCOMPtr<nsIPresShell> shell;
|
||||
aState.GetPresShell(getter_AddRefs(shell));
|
||||
adaptor->Recycle(shell);
|
||||
}
|
||||
}
|
||||
|
||||
mFirstChild= nsnull;
|
||||
|
@ -297,52 +312,68 @@ nsContainerBox::ClearChildren(nsIPresShell* aShell)
|
|||
}
|
||||
|
||||
void
|
||||
nsContainerBox::Prepend(nsIPresShell* aPresShell, nsIFrame* aList)
|
||||
nsContainerBox::Prepend(nsBoxLayoutState& aState, nsIFrame* aList)
|
||||
{
|
||||
nsIBox* first;
|
||||
nsIBox* last;
|
||||
mChildCount += CreateBoxList(aPresShell, aList, first, last);
|
||||
mChildCount += CreateBoxList(aState, aList, first, last);
|
||||
if (!mFirstChild)
|
||||
mFirstChild= mLastChild= first;
|
||||
else {
|
||||
last->SetNextBox(mFirstChild);
|
||||
mFirstChild= first;
|
||||
}
|
||||
|
||||
if (mLayoutManager)
|
||||
mLayoutManager->ChildrenInserted(this, aState, nsnull, first);
|
||||
|
||||
}
|
||||
|
||||
void
|
||||
nsContainerBox::Append(nsIPresShell* aPresShell, nsIFrame* aList)
|
||||
nsContainerBox::Append(nsBoxLayoutState& aState, nsIFrame* aList)
|
||||
{
|
||||
nsIBox* first;
|
||||
nsIBox* last;
|
||||
mChildCount += CreateBoxList(aPresShell, aList, first, last);
|
||||
mChildCount += CreateBoxList(aState, aList, first, last);
|
||||
if (!mFirstChild)
|
||||
mFirstChild= first;
|
||||
else
|
||||
mLastChild->SetNextBox(first);
|
||||
|
||||
mLastChild= last;
|
||||
|
||||
if (mLayoutManager)
|
||||
mLayoutManager->ChildrenAppended(this, aState, first);
|
||||
}
|
||||
|
||||
void
|
||||
nsContainerBox::InsertAfter(nsIPresShell* aPresShell, nsIBox* aPrev, nsIFrame* aList)
|
||||
nsContainerBox::InsertAfter(nsBoxLayoutState& aState, nsIBox* aPrev, nsIFrame* aList)
|
||||
{
|
||||
nsIBox* first = nsnull;
|
||||
nsIBox* last = nsnull;
|
||||
mChildCount += CreateBoxList(aPresShell, aList, first, last);
|
||||
mChildCount += CreateBoxList(aState, aList, first, last);
|
||||
nsIBox* next = nsnull;
|
||||
aPrev->GetNextBox(&next);
|
||||
last->SetNextBox(next);
|
||||
aPrev->SetNextBox(first);
|
||||
if (aPrev == mLastChild)
|
||||
mLastChild = last;
|
||||
|
||||
if (mLayoutManager) {
|
||||
mLayoutManager->ChildrenInserted(this, aState, aPrev, first);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
void
|
||||
nsContainerBox::InitChildren(nsIPresShell* aPresShell, nsIFrame* aList)
|
||||
nsContainerBox::InitChildren(nsBoxLayoutState& aState, nsIFrame* aList)
|
||||
{
|
||||
ClearChildren(aPresShell);
|
||||
mChildCount += CreateBoxList(aPresShell, aList, mFirstChild, mLastChild);
|
||||
ClearChildren(aState);
|
||||
mChildCount += CreateBoxList(aState, aList, mFirstChild, mLastChild);
|
||||
|
||||
if (mLayoutManager)
|
||||
mLayoutManager->ChildrenAppended(this, aState, mFirstChild);
|
||||
|
||||
}
|
||||
|
||||
void
|
||||
|
|
|
@ -50,15 +50,15 @@ public:
|
|||
virtual nsIBox* GetBox(nsIFrame* aFrame);
|
||||
virtual PRInt32 GetIndexOf(nsIBox* aBox);
|
||||
virtual PRInt32 GetChildCount();
|
||||
virtual void ClearChildren(nsIPresShell* aShell);
|
||||
virtual PRInt32 CreateBoxList(nsIPresShell* aShell, nsIFrame* aList, nsIBox*& first, nsIBox*& last);
|
||||
virtual void RemoveAfter(nsIPresShell* aShell, nsIBox* aPrev);
|
||||
virtual void Remove(nsIPresShell* aShell, nsIFrame* aChild);
|
||||
virtual void Prepend(nsIPresShell* aShell, nsIFrame* aList);
|
||||
virtual void Append(nsIPresShell* aShell, nsIFrame* aList);
|
||||
virtual void Insert(nsIPresShell* aShell, nsIFrame* aPrevFrame, nsIFrame* aList);
|
||||
virtual void InsertAfter(nsIPresShell* aShell, nsIBox* aPrev, nsIFrame* aList);
|
||||
virtual void InitChildren(nsIPresShell* aShell, nsIFrame* aList);
|
||||
virtual void ClearChildren(nsBoxLayoutState& aState);
|
||||
virtual PRInt32 CreateBoxList(nsBoxLayoutState& aState, nsIFrame* aList, nsIBox*& first, nsIBox*& last);
|
||||
virtual void RemoveAfter(nsBoxLayoutState& aState, nsIBox* aPrev);
|
||||
virtual void Remove(nsBoxLayoutState& aState, nsIFrame* aChild);
|
||||
virtual void Prepend(nsBoxLayoutState& aState, nsIFrame* aList);
|
||||
virtual void Append(nsBoxLayoutState& aState, nsIFrame* aList);
|
||||
virtual void Insert(nsBoxLayoutState& aState, nsIFrame* aPrevFrame, nsIFrame* aList);
|
||||
virtual void InsertAfter(nsBoxLayoutState& aState, nsIBox* aPrev, nsIFrame* aList);
|
||||
virtual void InitChildren(nsBoxLayoutState& aState, nsIFrame* aList);
|
||||
virtual nsIBox* GetPrevious(nsIFrame* aChild);
|
||||
virtual void SanityCheck(nsFrameList& aFrameList);
|
||||
virtual void SetDebugOnChildList(nsBoxLayoutState& aState, nsIBox* aChild, PRBool aDebug);
|
||||
|
|
|
@ -98,6 +98,8 @@ public:
|
|||
NS_IMETHOD Redraw(nsBoxLayoutState& aState, const nsRect* aRect = nsnull, PRBool aImmediate = PR_FALSE)=0;
|
||||
NS_IMETHOD NeedsRecalc()=0;
|
||||
NS_IMETHOD GetDebugBoxAt(const nsPoint& aPoint, nsIBox** aBox)=0;
|
||||
NS_IMETHOD RelayoutDirtyChild(nsBoxLayoutState& aState, nsIBox* aChild)=0;
|
||||
NS_IMETHOD GetMouseThrough(PRBool& aMouseThrough)=0;
|
||||
|
||||
// XXX Eventually these will move into nsIFrame.
|
||||
// These methods are used for XBL <children>.
|
||||
|
|
|
@ -79,7 +79,7 @@ nsLeafBoxFrame::Init(nsIPresContext* aPresContext,
|
|||
{
|
||||
nsresult rv = nsLeafFrame::Init(aPresContext, aContent, aParent, aContext, aPrevInFlow);
|
||||
|
||||
mMouseThrough = sometimes;
|
||||
mMouseThrough = unset;
|
||||
|
||||
if (mContent) {
|
||||
nsAutoString value;
|
||||
|
@ -104,13 +104,8 @@ nsLeafBoxFrame::GetFrameForPoint(nsIPresContext* aPresContext,
|
|||
if (!mRect.Contains(aPoint))
|
||||
return NS_ERROR_FAILURE;
|
||||
|
||||
if (mMouseThrough != never)
|
||||
{
|
||||
*aFrame = this;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
return NS_ERROR_FAILURE;
|
||||
*aFrame = this;
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
|
|
|
@ -240,11 +240,12 @@ nsObeliskLayout::PopulateBoxSizes(nsIBox* aBox, nsBoxLayoutState& aState, nsBoxS
|
|||
nsBoxSize* last = nsnull;
|
||||
temple->BuildBoxSizeList(aTempleBox, aState, first, last);
|
||||
aBoxSizes = first;
|
||||
} else {
|
||||
}/* else { */
|
||||
nsSprocketLayout::PopulateBoxSizes(aBox, aState, aBoxSizes, aComputedBoxSizes, aMinSize, aMaxSize, aFlexes);
|
||||
return;
|
||||
}
|
||||
// return;
|
||||
// }
|
||||
|
||||
/*
|
||||
aMinSize = 0;
|
||||
aMaxSize = NS_INTRINSICSIZE;
|
||||
|
||||
|
@ -254,6 +255,12 @@ nsObeliskLayout::PopulateBoxSizes(nsIBox* aBox, nsBoxLayoutState& aState, nsBoxS
|
|||
|
||||
nsIBox* child = nsnull;
|
||||
aBox->GetChildBox(&child);
|
||||
|
||||
if (child && !aBoxSizes)
|
||||
aBoxSizes = new (aState) nsBoxSize();
|
||||
|
||||
nsBoxSize* childSize = aBoxSizes;
|
||||
|
||||
while(child)
|
||||
{
|
||||
nscoord flex = 0;
|
||||
|
@ -296,7 +303,14 @@ nsObeliskLayout::PopulateBoxSizes(nsIBox* aBox, nsBoxLayoutState& aState, nsBoxS
|
|||
|
||||
|
||||
child->GetNextBox(&child);
|
||||
if (child && !childSize->next)
|
||||
{
|
||||
childSize->next = new (aState) nsBoxSize();
|
||||
childSize = childSize->next;
|
||||
}
|
||||
}
|
||||
*/
|
||||
|
||||
}
|
||||
|
||||
void
|
||||
|
|
|
@ -576,109 +576,141 @@ nsSprocketLayout::PopulateBoxSizes(nsIBox* aBox, nsBoxLayoutState& aState, nsBox
|
|||
|
||||
PRInt32 count = 0;
|
||||
aFlexes = 0;
|
||||
nsBoxSize* currentBox = nsnull;
|
||||
//nsComputedBoxSize* currentComputed = nsnull;
|
||||
nsBoxSize* currentBox = nsnull;
|
||||
|
||||
/*
|
||||
nsBoxSize* start = aBoxSizes;
|
||||
|
||||
while(child)
|
||||
{
|
||||
if (!currentBox) {
|
||||
aBoxSizes = new (aState) nsBoxSize();
|
||||
//aComputedBoxSizes = new (aState) nsComputedBoxSizeSpecial();
|
||||
|
||||
currentBox = aBoxSizes;
|
||||
//currentComputed = aComputedBoxSizes;
|
||||
} else {
|
||||
currentBox->next = new (aState) nsBoxSize();
|
||||
//currentComputed->next = new (aState) nsComputedBoxSizeSpecial();
|
||||
|
||||
currentBox = currentBox->next;
|
||||
//currentComputed = currentComputed->next;
|
||||
}
|
||||
|
||||
// ok if we started with a list move down the list
|
||||
// until we reach the end. Then start looking at childen.
|
||||
// This feature is used extensively for Grid.
|
||||
nscoord flex = 0;
|
||||
child->GetFlex(aState, flex);
|
||||
PRBool collapsed = PR_FALSE;
|
||||
child->IsCollapsed(aState, collapsed);
|
||||
|
||||
currentBox->flex = flex;
|
||||
currentBox->collapsed = collapsed;
|
||||
//currentComputed->resized = PR_FALSE;
|
||||
//currentComputed->size = 0;
|
||||
if (!start) {
|
||||
if (!currentBox) {
|
||||
aBoxSizes = new (aState) nsBoxSize();
|
||||
currentBox = aBoxSizes;
|
||||
} else {
|
||||
currentBox->next = new (aState) nsBoxSize();
|
||||
currentBox = currentBox->next;
|
||||
}
|
||||
|
||||
|
||||
child->GetFlex(aState, flex);
|
||||
PRBool collapsed = PR_FALSE;
|
||||
child->IsCollapsed(aState, collapsed);
|
||||
|
||||
currentBox->flex = flex;
|
||||
currentBox->collapsed = collapsed;
|
||||
} else {
|
||||
flex = start->flex;
|
||||
start = start->next;
|
||||
}
|
||||
|
||||
if (flex > 0)
|
||||
aFlexes++;
|
||||
|
||||
child->GetNextBox(&child);
|
||||
}
|
||||
*/
|
||||
|
||||
// get pref, min, max
|
||||
aBox->GetChildBox(&child);
|
||||
currentBox = aBoxSizes;
|
||||
nsBoxSize* last = nsnull;
|
||||
|
||||
while(child)
|
||||
{
|
||||
nsSize pref(0,0);
|
||||
nsSize min(0,0);
|
||||
nsSize max(0,0);
|
||||
nsSize max(NS_INTRINSICSIZE,NS_INTRINSICSIZE);
|
||||
|
||||
// only one flexible child? Cool we will just make its preferred size
|
||||
// 0 then and not even have to ask for it.
|
||||
//if (flexes != 1) {
|
||||
child->GetPrefSize(aState, pref);
|
||||
child->GetAscent(aState, currentBox->ascent);
|
||||
nsMargin margin;
|
||||
child->GetMargin(margin);
|
||||
currentBox->ascent += margin.top + margin.bottom;
|
||||
//}
|
||||
// only one flexible child? Cool we will just make its preferred size
|
||||
// 0 then and not even have to ask for it.
|
||||
//if (flexes != 1) {
|
||||
nscoord ascent = 0;
|
||||
child->GetPrefSize(aState, pref);
|
||||
child->GetMinSize(aState, min);
|
||||
child->GetMaxSize(aState, max);
|
||||
child->GetAscent(aState, ascent);
|
||||
nsMargin margin;
|
||||
child->GetMargin(margin);
|
||||
ascent += margin.top + margin.bottom;
|
||||
//}
|
||||
|
||||
child->GetMinSize(aState, min);
|
||||
child->GetMaxSize(aState, max);
|
||||
nsBox::BoundsCheck(min, pref, max);
|
||||
nsBox::BoundsCheck(min, pref, max);
|
||||
|
||||
AddMargin(child, pref);
|
||||
AddMargin(child, min);
|
||||
AddMargin(child, max);
|
||||
|
||||
nscoord minWidth = min.width;
|
||||
nscoord maxWidth = max.width;
|
||||
nscoord prefWidth = pref.width;
|
||||
|
||||
if (!isHorizontal) {
|
||||
minWidth = min.height;
|
||||
maxWidth = max.height;
|
||||
prefWidth = pref.height;
|
||||
if (min.width > aMinSize)
|
||||
aMinSize = min.width;
|
||||
|
||||
if (max.width < aMaxSize)
|
||||
aMaxSize = max.width;
|
||||
AddMargin(child, pref);
|
||||
AddMargin(child, min);
|
||||
AddMargin(child, max);
|
||||
|
||||
if (!currentBox) {
|
||||
// create one.
|
||||
currentBox = new (aState) nsBoxSize();
|
||||
if (!aBoxSizes) {
|
||||
aBoxSizes = currentBox;
|
||||
last = aBoxSizes;
|
||||
} else {
|
||||
if (min.height > aMinSize)
|
||||
aMinSize = min.height;
|
||||
|
||||
if (max.height < aMaxSize)
|
||||
aMaxSize = max.height;
|
||||
last->next = currentBox;
|
||||
last = currentBox;
|
||||
}
|
||||
|
||||
nscoord minWidth;
|
||||
nscoord maxWidth;
|
||||
nscoord prefWidth;
|
||||
|
||||
// get sizes from child
|
||||
if (isHorizontal) {
|
||||
minWidth = min.width;
|
||||
maxWidth = max.width;
|
||||
prefWidth = pref.width;
|
||||
} else {
|
||||
minWidth = min.height;
|
||||
maxWidth = max.height;
|
||||
prefWidth = pref.height;
|
||||
}
|
||||
|
||||
nscoord flex = 0;
|
||||
child->GetFlex(aState, flex);
|
||||
PRBool collapsed = PR_FALSE;
|
||||
child->IsCollapsed(aState, collapsed);
|
||||
|
||||
// set them
|
||||
currentBox->flex = flex;
|
||||
currentBox->collapsed = collapsed;
|
||||
currentBox->pref = prefWidth;
|
||||
currentBox->min = minWidth;
|
||||
currentBox->max = maxWidth;
|
||||
|
||||
NS_ASSERTION(minWidth <= prefWidth && prefWidth <= maxWidth,"Bad min, pref, max widths!");
|
||||
|
||||
/*
|
||||
if (minWidth > maxWidth)
|
||||
minWidth = maxWidth;
|
||||
}
|
||||
|
||||
if (prefWidth > maxWidth)
|
||||
prefWidth = maxWidth;
|
||||
if (!isHorizontal) {
|
||||
if (min.width > aMinSize)
|
||||
aMinSize = min.width;
|
||||
|
||||
if (prefWidth < minWidth)
|
||||
prefWidth = minWidth;
|
||||
*/
|
||||
if (max.width < aMaxSize)
|
||||
aMaxSize = max.width;
|
||||
|
||||
currentBox->pref = prefWidth;
|
||||
currentBox->min = minWidth;
|
||||
currentBox->max = maxWidth;
|
||||
} else {
|
||||
if (min.height > aMinSize)
|
||||
aMinSize = min.height;
|
||||
|
||||
if (max.height < aMaxSize)
|
||||
aMaxSize = max.height;
|
||||
}
|
||||
|
||||
currentBox->ascent = ascent;
|
||||
aFlexes += currentBox->flex;
|
||||
|
||||
child->GetNextBox(&child);
|
||||
|
||||
last = currentBox;
|
||||
currentBox = currentBox->next;
|
||||
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -221,6 +221,8 @@ nsStackLayout::Layout(nsIBox* aBox, nsBoxLayoutState& aState)
|
|||
nsIBox* child = nsnull;
|
||||
PRBool grow;
|
||||
|
||||
PRInt32 passes = 0;
|
||||
|
||||
do {
|
||||
aBox->GetChildBox(&child);
|
||||
grow = PR_FALSE;
|
||||
|
@ -248,6 +250,8 @@ nsStackLayout::Layout(nsIBox* aBox, nsBoxLayoutState& aState)
|
|||
|
||||
child->GetNextBox(&child);
|
||||
}
|
||||
NS_ASSERTION(passes < 10,"Infinite loop! Someone won't stop growing!!");
|
||||
passes++;
|
||||
} while(grow);
|
||||
|
||||
// if some HTML inside us got bigger we need to force ourselves to
|
||||
|
|
Загрузка…
Ссылка в новой задаче