зеркало из https://github.com/mozilla/gecko-dev.git
Bug 328168: Horizontal paddings, borders and margins on multi-frame bidi inlines appear in the wrong places. Patch by Haamed Gheibi <gheibi@gmail.com>. r=roc+uriber, sr=roc.
This commit is contained in:
Родитель
d82d580d5d
Коммит
ab53025882
|
@ -21,6 +21,7 @@
|
|||
*
|
||||
* Contributor(s):
|
||||
* Uri Bernstein <uriber@gmail.com>
|
||||
* Haamed Gheibi <gheibi@metanetworking.com>
|
||||
*
|
||||
* Alternatively, the contents of this file may be used under the terms of
|
||||
* either of the GNU General Public License Version 2 or later (the "GPL"),
|
||||
|
@ -51,6 +52,9 @@
|
|||
#include "nsCSSFrameConstructor.h"
|
||||
#include "nsHTMLContainerFrame.h"
|
||||
#include "nsLayoutUtils.h"
|
||||
#include "nsInlineFrame.h"
|
||||
|
||||
static NS_DEFINE_IID(kInlineFrameCID, NS_INLINE_FRAME_CID);
|
||||
|
||||
static const PRUnichar kSpace = 0x0020;
|
||||
static const PRUnichar kLineSeparator = 0x2028;
|
||||
|
@ -714,24 +718,179 @@ nsBidiPresUtils::GetFrameBaseLevel(nsIFrame* aFrame)
|
|||
return NS_GET_BASE_LEVEL(firstLeaf);
|
||||
}
|
||||
|
||||
static void
|
||||
ReverseChildFramesPositioning(nsIFrame* aFirstChild)
|
||||
void
|
||||
nsBidiPresUtils::IsLeftOrRightMost(nsIFrame* aFrame,
|
||||
nsContinuationStates* aContinuationStates,
|
||||
PRBool& aIsLeftMost /* out */,
|
||||
PRBool& aIsRightMost /* out */) const
|
||||
{
|
||||
if (!aFirstChild)
|
||||
const nsStyleVisibility* vis = aFrame->GetStyleVisibility();
|
||||
PRBool isLTR = (NS_STYLE_DIRECTION_LTR == vis->mDirection);
|
||||
|
||||
/*
|
||||
* Since we lay out frames from left to right (in both LTR and RTL), visiting a
|
||||
* frame with 'mFirstVisualFrame == nsnull', means it's the first appearance of
|
||||
* one of its continuation chain frames on the line.
|
||||
* To determine if it's the last visual frame of its continuation chain on the line
|
||||
* or not, we count the number of frames of the chain on the line, and then reduce
|
||||
* it when we lay out a frame of the chain. If this value becomes 1 it means
|
||||
* that it's the last visual frame of its continuation chain on this line.
|
||||
*/
|
||||
|
||||
nsFrameContinuationState* frameState = aContinuationStates->GetEntry(aFrame);
|
||||
nsFrameContinuationState* firstFrameState;
|
||||
|
||||
if (!frameState->mFirstVisualFrame) {
|
||||
// aFrame is the first visual frame of its continuation chain
|
||||
nsFrameContinuationState* contState;
|
||||
nsIFrame* frame;
|
||||
|
||||
frameState->mFrameCount = 1;
|
||||
frameState->mFirstVisualFrame = aFrame;
|
||||
|
||||
/**
|
||||
* Traverse continuation chain of aFrame in both backward and forward
|
||||
* directions while the frames are on this line. Count the frames and
|
||||
* set their mFirstVisualFrame to aFrame.
|
||||
*/
|
||||
// Traverse continuation chain backward
|
||||
for (frame = aFrame->GetPrevContinuation();
|
||||
frame && (contState = aContinuationStates->GetEntry(frame));
|
||||
frame = frame->GetPrevContinuation()) {
|
||||
frameState->mFrameCount++;
|
||||
contState->mFirstVisualFrame = aFrame;
|
||||
}
|
||||
frameState->mHasContOnPrevLines = (frame != nsnull);
|
||||
|
||||
// Traverse continuation chain forward
|
||||
for (frame = aFrame->GetNextContinuation();
|
||||
frame && (contState = aContinuationStates->GetEntry(frame));
|
||||
frame = frame->GetNextContinuation()) {
|
||||
frameState->mFrameCount++;
|
||||
contState->mFirstVisualFrame = aFrame;
|
||||
}
|
||||
frameState->mHasContOnNextLines = (frame != nsnull);
|
||||
|
||||
aIsLeftMost = isLTR ? !frameState->mHasContOnPrevLines
|
||||
: !frameState->mHasContOnNextLines;
|
||||
firstFrameState = frameState;
|
||||
} else {
|
||||
// aFrame is not the first visual frame of its continuation chain
|
||||
aIsLeftMost = PR_FALSE;
|
||||
firstFrameState = aContinuationStates->GetEntry(frameState->mFirstVisualFrame);
|
||||
}
|
||||
|
||||
aIsRightMost = (firstFrameState->mFrameCount == 1) &&
|
||||
(isLTR ? !firstFrameState->mHasContOnNextLines
|
||||
: !firstFrameState->mHasContOnPrevLines);
|
||||
|
||||
// Reduce number of remaining frames of the continuation chain on the line.
|
||||
firstFrameState->mFrameCount--;
|
||||
}
|
||||
|
||||
void
|
||||
nsBidiPresUtils::RepositionFrame(nsIFrame* aFrame,
|
||||
PRBool aIsOddLevel,
|
||||
nscoord& aLeft,
|
||||
nsContinuationStates* aContinuationStates) const
|
||||
{
|
||||
if (!aFrame)
|
||||
return;
|
||||
|
||||
// Get the right edge of the last sibling
|
||||
nsIFrame* lastSibling;
|
||||
for (lastSibling = aFirstChild; lastSibling->GetNextSibling(); lastSibling = lastSibling->GetNextSibling())
|
||||
;
|
||||
nscoord right = lastSibling->GetRect().XMost();
|
||||
|
||||
|
||||
PRBool isLeftMost, isRightMost;
|
||||
IsLeftOrRightMost(aFrame,
|
||||
aContinuationStates,
|
||||
isLeftMost /* out */,
|
||||
isRightMost /* out */);
|
||||
|
||||
nsIFrame* testFrame;
|
||||
aFrame->QueryInterface(kInlineFrameCID, (void**)&testFrame);
|
||||
|
||||
if (testFrame) {
|
||||
aFrame->AddStateBits(NS_INLINE_FRAME_BIDI_VISUAL_STATE_IS_SET);
|
||||
|
||||
if (isLeftMost)
|
||||
aFrame->AddStateBits(NS_INLINE_FRAME_BIDI_VISUAL_IS_LEFT_MOST);
|
||||
else
|
||||
aFrame->RemoveStateBits(NS_INLINE_FRAME_BIDI_VISUAL_IS_LEFT_MOST);
|
||||
|
||||
if (isRightMost)
|
||||
aFrame->AddStateBits(NS_INLINE_FRAME_BIDI_VISUAL_IS_RIGHT_MOST);
|
||||
else
|
||||
aFrame->RemoveStateBits(NS_INLINE_FRAME_BIDI_VISUAL_IS_RIGHT_MOST);
|
||||
}
|
||||
nsMargin margin;
|
||||
aFrame->GetMargin(margin);
|
||||
if (isLeftMost)
|
||||
aLeft += margin.left;
|
||||
|
||||
nscoord start = aLeft;
|
||||
|
||||
if (!IsBidiLeaf(aFrame))
|
||||
{
|
||||
nscoord x = 0;
|
||||
nsMargin borderPadding;
|
||||
aFrame->GetBorderAndPadding(borderPadding);
|
||||
if (isLeftMost) {
|
||||
x += borderPadding.left;
|
||||
}
|
||||
|
||||
// If aIsOddLevel is true, so we need to traverse the child list
|
||||
// in reverse order, to make it O(n) we store the list locally and
|
||||
// iterate the list reversely
|
||||
nsVoidArray childList;
|
||||
nsIFrame *frame = aFrame->GetFirstChild(nsnull);
|
||||
if (frame && aIsOddLevel) {
|
||||
childList.AppendElement(nsnull);
|
||||
while (frame) {
|
||||
childList.AppendElement(frame);
|
||||
frame = frame->GetNextSibling();
|
||||
}
|
||||
frame = (nsIFrame*)childList[childList.Count() - 1];
|
||||
}
|
||||
|
||||
// Reposition the child frames
|
||||
PRInt32 index = 0;
|
||||
while (frame) {
|
||||
RepositionFrame(frame,
|
||||
aIsOddLevel,
|
||||
x,
|
||||
aContinuationStates);
|
||||
index++;
|
||||
frame = aIsOddLevel ?
|
||||
(nsIFrame*)childList[childList.Count() - index - 1] :
|
||||
frame->GetNextSibling();
|
||||
}
|
||||
|
||||
if (isRightMost) {
|
||||
x += borderPadding.right;
|
||||
}
|
||||
aLeft += x;
|
||||
} else {
|
||||
aLeft += aFrame->GetSize().width;
|
||||
}
|
||||
nsRect rect = aFrame->GetRect();
|
||||
aFrame->SetRect(nsRect(start, rect.y, aLeft - start, rect.height));
|
||||
|
||||
if (isRightMost)
|
||||
aLeft += margin.right;
|
||||
}
|
||||
|
||||
void
|
||||
nsBidiPresUtils::InitContinuationStates(nsIFrame* aFrame,
|
||||
nsContinuationStates* aContinuationStates) const
|
||||
{
|
||||
nsFrameContinuationState* state = aContinuationStates->PutEntry(aFrame);
|
||||
state->mFirstVisualFrame = nsnull;
|
||||
state->mFrameCount = 0;
|
||||
|
||||
// Continue for child frames
|
||||
nsIFrame* frame;
|
||||
for (frame = aFirstChild; frame; frame = frame->GetNextSibling()) {
|
||||
right -= frame->GetRect().width;
|
||||
frame->SetPosition(nsPoint(right, frame->GetPosition().y));
|
||||
if (!IsBidiLeaf(frame))
|
||||
ReverseChildFramesPositioning(frame->GetFirstChild(nsnull));
|
||||
for (frame = aFrame->GetFirstChild(nsnull);
|
||||
frame;
|
||||
frame = frame->GetNextSibling()) {
|
||||
InitContinuationStates(frame,
|
||||
aContinuationStates);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -741,19 +900,37 @@ nsBidiPresUtils::RepositionInlineFrames(nsPresContext* aPresContext,
|
|||
nsIFrame* aFirstChild,
|
||||
PRBool aReordered) const
|
||||
{
|
||||
PRInt32 count = mVisualFrames.Count();
|
||||
nscoord left = aFirstChild->GetPosition().x;
|
||||
nsIFrame* frame;
|
||||
|
||||
for (PRInt32 i = 0; i < count; i++) {
|
||||
frame = (nsIFrame*) (mVisualFrames[i]);
|
||||
if (aReordered) // Don't touch positioning if no reordering was done, to avoid killing margins.
|
||||
frame->SetPosition(nsPoint(left, frame->GetPosition().y));
|
||||
left += frame->GetRect().width;
|
||||
nsMargin margin;
|
||||
const nsStyleVisibility* vis = aFirstChild->GetStyleVisibility();
|
||||
PRBool isLTR = (NS_STYLE_DIRECTION_LTR == vis->mDirection);
|
||||
nscoord leftSpace = 0;
|
||||
|
||||
// If this is an odd-level frame, reverse the positioning of its childern
|
||||
if ((mLevels[mIndexMap[i]] & 1) && !IsBidiLeaf(frame))
|
||||
ReverseChildFramesPositioning(frame->GetFirstChild(nsnull));
|
||||
aFirstChild->GetMargin(margin);
|
||||
if (!aFirstChild->GetPrevContinuation())
|
||||
leftSpace = isLTR ? margin.left : margin.right;
|
||||
|
||||
nscoord left = aFirstChild->GetPosition().x - leftSpace;
|
||||
nsIFrame* frame;
|
||||
PRInt32 count = mVisualFrames.Count();
|
||||
PRInt32 index;
|
||||
nsContinuationStates continuationStates;
|
||||
|
||||
continuationStates.Init();
|
||||
|
||||
// Initialize continuation states to (nsnull, 0) for
|
||||
// each frame on the line.
|
||||
for (index = 0; index < count; index++) {
|
||||
InitContinuationStates((nsIFrame*)mVisualFrames[index],
|
||||
&continuationStates);
|
||||
}
|
||||
|
||||
// Reposition frames in visual order
|
||||
for (index = 0; index < count; index++) {
|
||||
frame = (nsIFrame*) (mVisualFrames[index]);
|
||||
RepositionFrame(frame,
|
||||
(mLevels[mIndexMap[index]] & 1),
|
||||
left,
|
||||
&continuationStates);
|
||||
} // for
|
||||
}
|
||||
|
||||
|
|
|
@ -49,6 +49,46 @@
|
|||
#include "nsCOMPtr.h"
|
||||
#include "nsDataHashtable.h"
|
||||
#include "nsBlockFrame.h"
|
||||
#include "nsTHashtable.h"
|
||||
|
||||
/**
|
||||
* A structure representing some continuation state for each frame on the line,
|
||||
* used to determine the first and the last continuation frame for each
|
||||
* continuation chain on the line.
|
||||
*/
|
||||
struct nsFrameContinuationState : public nsVoidPtrHashKey
|
||||
{
|
||||
nsFrameContinuationState(const void *aFrame) : nsVoidPtrHashKey(aFrame) {}
|
||||
|
||||
/**
|
||||
* The first visual frame in the continuation chain containing this frame, or
|
||||
* nsnull if this frame is the first visual frame in the chain.
|
||||
*/
|
||||
nsIFrame* mFirstVisualFrame;
|
||||
|
||||
/**
|
||||
* The number of frames in the continuation chain containing this frame, if
|
||||
* this frame is the first visual frame of the chain, or 0 otherwise.
|
||||
*/
|
||||
PRUint32 mFrameCount;
|
||||
|
||||
/**
|
||||
* TRUE if this frame is the first visual frame of its continuation chain on
|
||||
* this line and the chain has some frames on the previous lines.
|
||||
*/
|
||||
PRPackedBool mHasContOnPrevLines;
|
||||
|
||||
/**
|
||||
* TRUE if this frame is the first visual frame of its continuation chain on
|
||||
* this line and the chain has some frames left for next lines.
|
||||
*/
|
||||
PRPackedBool mHasContOnNextLines;
|
||||
};
|
||||
|
||||
/*
|
||||
* Following type is used to pass needed hashtable to reordering methods
|
||||
*/
|
||||
typedef nsTHashtable<nsFrameContinuationState> nsContinuationStates;
|
||||
|
||||
/**
|
||||
* A structure representing a logical position which should be resolved
|
||||
|
@ -238,6 +278,55 @@ private:
|
|||
*/
|
||||
nsresult Reorder(PRBool& aReordered, PRBool& aHasRTLFrames);
|
||||
|
||||
/*
|
||||
* Position aFrame and it's descendants to their visual places. Also if aFrame
|
||||
* is not leaf, resize it to embrace it's children.
|
||||
*
|
||||
* @param aFrame The frame which itself and its children are going
|
||||
* to be repositioned
|
||||
* @param aIsOddLevel TRUE means the embedding level of this frame is odd
|
||||
* @param[in,out] aLeft IN value is the starting position of aFrame(without
|
||||
* considering its left margin)
|
||||
* OUT value will be the ending position of aFrame(after
|
||||
* adding its right margin)
|
||||
* @param aContinuationStates A map from nsIFrame* to nsFrameContinuationState
|
||||
*/
|
||||
void RepositionFrame(nsIFrame* aFrame,
|
||||
PRBool aIsOddLevel,
|
||||
nscoord& aLeft,
|
||||
nsContinuationStates* aContinuationStates) const;
|
||||
|
||||
/*
|
||||
* Initialize the continuation state(nsFrameContinuationState) to
|
||||
* (nsnull, 0) for aFrame and its descendants.
|
||||
*
|
||||
* @param aFrame The frame which itself and its descendants will
|
||||
* be initialized
|
||||
* @param aContinuationStates A map from nsIFrame* to nsFrameContinuationState
|
||||
*/
|
||||
void InitContinuationStates(nsIFrame* aFrame,
|
||||
nsContinuationStates* aContinuationStates) const;
|
||||
|
||||
/*
|
||||
* Determine if aFrame is leftmost or rightmost, and set aIsLeftMost and
|
||||
* aIsRightMost values. Also set continuation states of aContinuationStates.
|
||||
*
|
||||
* A frame is leftmost if it's the first appearance of its continuation chain
|
||||
* on the line and the chain is on its first line if it's LTR or the chain is
|
||||
* on its last line if it's RTL.
|
||||
* A frame is rightmost if it's the last appearance of its continuation chain
|
||||
* on the line and the chain is on its first line if it's RTL or the chain is
|
||||
* on its last line if it's LTR.
|
||||
*
|
||||
* @param aContinuationStates A map from nsIFrame* to nsFrameContinuationState
|
||||
* @param[out] aIsLeftMost TRUE means aFrame is leftmost frame or continuation
|
||||
* @param[out] aIsRightMost TRUE means aFrame is rightmost frame or continuation
|
||||
*/
|
||||
void IsLeftOrRightMost(nsIFrame* aFrame,
|
||||
nsContinuationStates* aContinuationStates,
|
||||
PRBool& aIsLeftMost /* out */,
|
||||
PRBool& aIsRightMost /* out */) const;
|
||||
|
||||
/**
|
||||
* Adjust frame positions following their visual order
|
||||
*
|
||||
|
@ -250,10 +339,6 @@ private:
|
|||
nsIFrame* aFirstChild,
|
||||
PRBool aReordered) const;
|
||||
|
||||
void RepositionContainerFrame(nsPresContext* aPresContext,
|
||||
nsIFrame* aContainer,
|
||||
PRInt32& aMinX,
|
||||
PRInt32& aMaxX) const;
|
||||
/**
|
||||
* Helper method for Resolve()
|
||||
* Truncate a text frame and possibly create a continuation frame with the
|
||||
|
|
|
@ -438,15 +438,18 @@ nsInlineFrame::ReflowFrames(nsPresContext* aPresContext,
|
|||
aStatus = NS_FRAME_COMPLETE;
|
||||
|
||||
nsLineLayout* lineLayout = aReflowState.mLineLayout;
|
||||
PRBool ltr = (NS_STYLE_DIRECTION_LTR == aReflowState.mStyleVisibility->mDirection);
|
||||
nscoord leftEdge = 0;
|
||||
if (nsnull == GetPrevContinuation()) {
|
||||
leftEdge = aReflowState.mComputedBorderPadding.left;
|
||||
leftEdge = ltr ? aReflowState.mComputedBorderPadding.left
|
||||
: aReflowState.mComputedBorderPadding.right;
|
||||
}
|
||||
nscoord availableWidth = aReflowState.availableWidth;
|
||||
if (NS_UNCONSTRAINEDSIZE != availableWidth) {
|
||||
// Subtract off left and right border+padding from availableWidth
|
||||
availableWidth -= leftEdge;
|
||||
availableWidth -= aReflowState.mComputedBorderPadding.right;
|
||||
availableWidth -= ltr ? aReflowState.mComputedBorderPadding.right
|
||||
: aReflowState.mComputedBorderPadding.left;
|
||||
availableWidth = PR_MAX(0, availableWidth);
|
||||
}
|
||||
lineLayout->BeginSpan(this, &aReflowState, leftEdge, leftEdge + availableWidth);
|
||||
|
@ -552,10 +555,12 @@ nsInlineFrame::ReflowFrames(nsPresContext* aPresContext,
|
|||
// Compute final width
|
||||
aMetrics.width = size.width;
|
||||
if (nsnull == GetPrevContinuation()) {
|
||||
aMetrics.width += aReflowState.mComputedBorderPadding.left;
|
||||
aMetrics.width += ltr ? aReflowState.mComputedBorderPadding.left
|
||||
: aReflowState.mComputedBorderPadding.right;
|
||||
}
|
||||
if (NS_FRAME_IS_COMPLETE(aStatus) && (!GetNextContinuation() || GetNextInFlow())) {
|
||||
aMetrics.width += aReflowState.mComputedBorderPadding.right;
|
||||
aMetrics.width += ltr ? aReflowState.mComputedBorderPadding.right
|
||||
: aReflowState.mComputedBorderPadding.left;
|
||||
}
|
||||
|
||||
SetFontFromStyle(aReflowState.rendContext, mStyleContext);
|
||||
|
@ -783,9 +788,10 @@ PRIntn
|
|||
nsInlineFrame::GetSkipSides() const
|
||||
{
|
||||
PRIntn skip = 0;
|
||||
if (nsnull != GetPrevContinuation()) {
|
||||
if (!IsLeftMost()) {
|
||||
nsInlineFrame* prev = (nsInlineFrame*) GetPrevContinuation();
|
||||
if (prev->mRect.height || prev->mRect.width) {
|
||||
if ((GetStateBits() & NS_INLINE_FRAME_BIDI_VISUAL_STATE_IS_SET) ||
|
||||
(prev && (prev->mRect.height || prev->mRect.width))) {
|
||||
// Prev continuation is not empty therefore we don't render our left
|
||||
// border edge.
|
||||
skip |= 1 << NS_SIDE_LEFT;
|
||||
|
@ -795,9 +801,10 @@ nsInlineFrame::GetSkipSides() const
|
|||
// edge border render.
|
||||
}
|
||||
}
|
||||
if (nsnull != GetNextContinuation()) {
|
||||
if (!IsRightMost()) {
|
||||
nsInlineFrame* next = (nsInlineFrame*) GetNextContinuation();
|
||||
if (next->mRect.height || next->mRect.width) {
|
||||
if ((GetStateBits() & NS_INLINE_FRAME_BIDI_VISUAL_STATE_IS_SET) ||
|
||||
(next && (next->mRect.height || next->mRect.width))) {
|
||||
// Next continuation is not empty therefore we don't render our right
|
||||
// border edge.
|
||||
skip |= 1 << NS_SIDE_RIGHT;
|
||||
|
|
|
@ -62,6 +62,17 @@ class nsAnonymousBlockFrame;
|
|||
|
||||
#define NS_INLINE_FRAME_HARD_TEXT_OFFSETS 0x00200000
|
||||
|
||||
/** In Bidi left (or right) margin/padding/border should be applied to left
|
||||
* (or right) most frame (or a continuation frame).
|
||||
* This state value shows if this frame is left (or right) most continuation
|
||||
* or not.
|
||||
*/
|
||||
#define NS_INLINE_FRAME_BIDI_VISUAL_STATE_IS_SET 0x00400000
|
||||
|
||||
#define NS_INLINE_FRAME_BIDI_VISUAL_IS_LEFT_MOST 0x00800000
|
||||
|
||||
#define NS_INLINE_FRAME_BIDI_VISUAL_IS_RIGHT_MOST 0x01000000
|
||||
|
||||
/**
|
||||
* Inline frame class.
|
||||
*
|
||||
|
@ -115,6 +126,28 @@ public:
|
|||
mFrames.SetFrames(nsnull);
|
||||
}
|
||||
|
||||
/**
|
||||
* Return true if the frame is leftmost frame or continuation.
|
||||
*/
|
||||
PRBool IsLeftMost() const {
|
||||
// If the frame's bidi visual state is set, return is-leftmost state
|
||||
// else return true if it's the first continuation.
|
||||
return (GetStateBits() & NS_INLINE_FRAME_BIDI_VISUAL_STATE_IS_SET)
|
||||
? (GetStateBits() & NS_INLINE_FRAME_BIDI_VISUAL_IS_LEFT_MOST)
|
||||
: (!GetPrevInFlow());
|
||||
}
|
||||
|
||||
/**
|
||||
* Return true if the frame is rightmost frame or continuation.
|
||||
*/
|
||||
PRBool IsRightMost() const {
|
||||
// If the frame's bidi visual state is set, return is-rightmost state
|
||||
// else return true if it's the last continuation.
|
||||
return (GetStateBits() & NS_INLINE_FRAME_BIDI_VISUAL_STATE_IS_SET)
|
||||
? (GetStateBits() & NS_INLINE_FRAME_BIDI_VISUAL_IS_RIGHT_MOST)
|
||||
: (!GetNextInFlow());
|
||||
}
|
||||
|
||||
protected:
|
||||
// Additional reflow state used during our reflow methods
|
||||
struct InlineReflowState {
|
||||
|
|
|
@ -1239,16 +1239,16 @@ nsLineLayout::ApplyStartMargin(PerFrameData* pfd,
|
|||
else
|
||||
pfd->mMargin.right = 0;
|
||||
}
|
||||
else {
|
||||
pfd->mBounds.x += ltr ? pfd->mMargin.left : pfd->mMargin.right;
|
||||
|
||||
if (NS_UNCONSTRAINEDSIZE != aReflowState.availableWidth){
|
||||
// Adjust available width to account for the left margin. The
|
||||
// right margin will be accounted for when we finish flowing the
|
||||
// frame.
|
||||
aReflowState.availableWidth -= ltr ? pfd->mMargin.left : pfd->mMargin.right;
|
||||
if (NS_UNCONSTRAINEDSIZE != aReflowState.availableWidth){
|
||||
// Adjust available width to account for the left margin. The
|
||||
// right margin will be accounted for when we finish flowing the
|
||||
// frame.
|
||||
aReflowState.availableWidth -= ltr ? pfd->mMargin.left : pfd->mMargin.right;
|
||||
}
|
||||
}
|
||||
|
||||
if (ltr)
|
||||
pfd->mBounds.x += pfd->mMargin.left;
|
||||
}
|
||||
|
||||
/**
|
||||
|
@ -1314,7 +1314,8 @@ nsLineLayout::CanPlaceFrame(PerFrameData* pfd,
|
|||
|
||||
// Set outside to PR_TRUE if the result of the reflow leads to the
|
||||
// frame sticking outside of our available area.
|
||||
PRBool outside = pfd->mBounds.XMost() + pfd->mMargin.right > psd->mRightEdge;
|
||||
PRBool ltr = (NS_STYLE_DIRECTION_LTR == aReflowState.mStyleVisibility->mDirection);
|
||||
PRBool outside = pfd->mBounds.XMost() + (ltr ? pfd->mMargin.right : pfd->mMargin.left) > psd->mRightEdge;
|
||||
if (!outside) {
|
||||
// If it fits, it fits
|
||||
#ifdef NOISY_CAN_PLACE_FRAME
|
||||
|
@ -1474,8 +1475,9 @@ nsLineLayout::PlaceFrame(PerFrameData* pfd, nsHTMLReflowMetrics& aMetrics)
|
|||
SetFlag(LL_UPDATEDBAND, PR_FALSE);
|
||||
}
|
||||
|
||||
PRBool ltr = (NS_STYLE_DIRECTION_LTR == pfd->mFrame->GetStyleVisibility()->mDirection);
|
||||
// Advance to next X coordinate
|
||||
psd->mX = pfd->mBounds.XMost() + pfd->mMargin.right;
|
||||
psd->mX = pfd->mBounds.XMost() + (ltr ? pfd->mMargin.right : pfd->mMargin.left);
|
||||
|
||||
// If the frame is a not aware of white-space and it takes up some
|
||||
// width, disable leading white-space compression for the next frame
|
||||
|
|
Загрузка…
Ссылка в новой задаче