Merge backout.
Merge backout.
--- a/accessible/src/base/nsTextAttrs.cpp
+++ b/accessible/src/base/nsTextAttrs.cpp
@@ -521,18 +521,18 @@ nsBGColorTextAttr::Format(const nscolor&
aFormattedValue = value;
}
PRBool
nsBGColorTextAttr::GetColor(nsIFrame *aFrame, nscolor *aColor)
{
const nsStyleBackground *styleBackground = aFrame->GetStyleBackground();
- if (NS_GET_A(styleBackground->mFallbackBackgroundColor) > 0) {
- *aColor = styleBackground->mFallbackBackgroundColor;
+ if (!styleBackground->IsTransparent()) {
+ *aColor = styleBackground->mBackgroundColor;
return PR_TRUE;
}
nsIFrame *parentFrame = aFrame->GetParent();
if (!parentFrame) {
*aColor = aFrame->PresContext()->DefaultBackgroundColor();
return PR_TRUE;
}
--- a/content/canvas/src/nsCanvasRenderingContext2D.cpp
+++ b/content/canvas/src/nsCanvasRenderingContext2D.cpp
@@ -665,18 +665,17 @@ NS_NewCanvasRenderingContext2D(nsIDOMCan
return NS_ERROR_OUT_OF_MEMORY;
*aResult = ctx.forget().get();
return NS_OK;
}
nsCanvasRenderingContext2D::nsCanvasRenderingContext2D()
: mValid(PR_FALSE), mOpaque(PR_FALSE), mCanvasElement(nsnull),
- mSaveCount(0), mIsFrameInvalid(PR_FALSE), mLastStyle(STYLE_MAX),
- mStyleStack(20)
+ mSaveCount(0), mIsFrameInvalid(PR_FALSE), mStyleStack(20)
{
}
nsCanvasRenderingContext2D::~nsCanvasRenderingContext2D()
{
Destroy();
}
--- a/content/events/src/nsDOMDataContainerEvent.h
+++ b/content/events/src/nsDOMDataContainerEvent.h
@@ -36,17 +36,16 @@
*
* ***** END LICENSE BLOCK ***** */
#ifndef nsDOMDataContainerEvent_h___
#define nsDOMDataContainerEvent_h___
#include "nsIDOMDataContainerEvent.h"
#include "nsDOMEvent.h"
-#include "nsInterfaceHashtable.h"
class nsDOMDataContainerEvent : public nsDOMEvent,
public nsIDOMDataContainerEvent
{
public:
nsDOMDataContainerEvent(nsPresContext* aPresContext, nsEvent* aEvent);
NS_DECL_ISUPPORTS_INHERITED
--- a/content/html/content/src/nsGenericHTMLElement.cpp
+++ b/content/html/content/src/nsGenericHTMLElement.cpp
@@ -1936,17 +1936,18 @@ nsGenericHTMLElement::MapImageBorderAttr
void
nsGenericHTMLElement::MapBackgroundInto(const nsMappedAttributes* aAttributes,
nsRuleData* aData)
{
if (!(aData->mSIDs & NS_STYLE_INHERIT_BIT(Background)))
return;
nsPresContext* presContext = aData->mPresContext;
- if (!aData->mColorData->mBackImage && presContext->UseDocumentColors()) {
+ if (aData->mColorData->mBackImage.GetUnit() == eCSSUnit_Null &&
+ presContext->UseDocumentColors()) {
// background
const nsAttrValue* value = aAttributes->GetAttr(nsGkAtoms::background);
if (value && value->Type() == nsAttrValue::eString) {
const nsString& spec = value->GetStringValue();
if (!spec.IsEmpty()) {
// Resolve url to an absolute url
// XXX this breaks if the HTML element has an xml:base
// attribute (the xml:base will not be taken into account)
@@ -1966,54 +1967,43 @@ nsGenericHTMLElement::MapBackgroundInto(
// XXXbz it would be nice to assert that doc->NodePrincipal() is
// the same as the principal of the node (which we'd need to store
// in the mapped attrs or something?)
nsCSSValue::Image *img =
new nsCSSValue::Image(uri, buffer, doc->GetDocumentURI(),
doc->NodePrincipal(), doc);
buffer->Release();
if (NS_LIKELY(img != 0)) {
- // Use nsRuleDataColor's temporary mTempBackImage to
- // make a value list.
- aData->mColorData->mTempBackImage.mValue.SetImageValue(img);
- aData->mColorData->mBackImage =
- &aData->mColorData->mTempBackImage;
+ aData->mColorData->mBackImage.SetImageValue(img);
}
}
}
}
else if (presContext->CompatibilityMode() == eCompatibility_NavQuirks) {
// in NavQuirks mode, allow the empty string to set the
// background to empty
- // Use nsRuleDataColor's temporary mTempBackImage to make a value list.
- aData->mColorData->mBackImage = nsnull;
- aData->mColorData->mTempBackImage.mValue.SetNoneValue();
- aData->mColorData->mBackImage = &aData->mColorData->mTempBackImage;
+ aData->mColorData->mBackImage.SetNoneValue();
}
}
}
}
void
nsGenericHTMLElement::MapBGColorInto(const nsMappedAttributes* aAttributes,
nsRuleData* aData)
{
if (!(aData->mSIDs & NS_STYLE_INHERIT_BIT(Background)))
return;
- if (aData->mColorData->mBackColor.mXValue.GetUnit() == eCSSUnit_Null &&
+ if (aData->mColorData->mBackColor.GetUnit() == eCSSUnit_Null &&
aData->mPresContext->UseDocumentColors()) {
- NS_ASSERTION(aData->mColorData->mBackColor.mYValue.GetUnit() ==
- eCSSUnit_Null,
- "half a property?");
const nsAttrValue* value = aAttributes->GetAttr(nsGkAtoms::bgcolor);
nscolor color;
if (value && value->GetColorValue(color)) {
- aData->mColorData->mBackColor.mXValue.SetColorValue(color);
- aData->mColorData->mBackColor.mYValue.SetColorValue(color);
+ aData->mColorData->mBackColor.SetColorValue(color);
}
}
}
void
nsGenericHTMLElement::MapBackgroundAttributesInto(const nsMappedAttributes* aAttributes,
nsRuleData* aData)
{
--- a/content/mathml/content/src/nsMathMLElement.cpp
+++ b/content/mathml/content/src/nsMathMLElement.cpp
@@ -372,25 +372,20 @@ nsMathMLElement::MapMathMLAttributesInto
}
if (aData->mSIDs & NS_STYLE_INHERIT_BIT(Background)) {
const nsAttrValue* value =
aAttributes->GetAttr(nsGkAtoms::mathbackground_);
if (!value) {
value = aAttributes->GetAttr(nsGkAtoms::background);
}
- if (value &&
- aData->mColorData->mBackColor.mXValue.GetUnit() == eCSSUnit_Null) {
- NS_ASSERTION(aData->mColorData->mBackColor.mYValue.GetUnit()
- == eCSSUnit_Null,
- "half a property?");
+ if (value && aData->mColorData->mBackColor.GetUnit() == eCSSUnit_Null) {
nscolor color;
if (value->GetColorValue(color)) {
- aData->mColorData->mBackColor.mXValue.SetColorValue(color);
- aData->mColorData->mBackColor.mYValue.SetColorValue(color);
+ aData->mColorData->mBackColor.SetColorValue(color);
}
}
}
if (aData->mSIDs & NS_STYLE_INHERIT_BIT(Color)) {
const nsAttrValue* value = aAttributes->GetAttr(nsGkAtoms::mathcolor_);
if (!value) {
value = aAttributes->GetAttr(nsGkAtoms::color);
--- a/gfx/thebes/public/gfxContext.h
+++ b/gfx/thebes/public/gfxContext.h
@@ -671,26 +671,16 @@ public:
}
void SetContext(gfxContext *aContext) {
NS_ASSERTION(!mContext, "Not going to call Restore() on some context!!!");
mContext = aContext;
mContext->Save();
}
- void Reset(gfxContext *aContext) {
- // Do the equivalent of destroying and re-creating this object.
- NS_PRECONDITION(aContext, "must provide a context");
- if (mContext) {
- mContext->Restore();
- }
- mContext = aContext;
- mContext->Save();
- }
-
private:
gfxContext *mContext;
};
/**
* Sentry helper class for functions with multiple return points that need to
* back up the current path of a context and have it automatically restored
* before they return. This class assumes that the transformation matrix will
--- a/layout/base/nsCSSRendering.cpp
+++ b/layout/base/nsCSSRendering.cpp
@@ -257,27 +257,16 @@ protected:
PRBool isValid1, isValid2;
nsBlockInFlowLineIterator it1(mBlockFrame, aFrame1, &isValid1);
nsBlockInFlowLineIterator it2(mBlockFrame, aFrame2, &isValid2);
return isValid1 && isValid2 && it1.GetLine() == it2.GetLine();
}
};
/* Local functions */
-static void PaintBackgroundLayer(nsPresContext* aPresContext,
- nsIRenderingContext& aRenderingContext,
- nsIFrame* aForFrame,
- const nsRect& aDirtyRect,
- const nsRect& aBorderArea,
- const nsRect& aBGClipRect,
- const nsStyleBackground& aBackground,
- const nsStyleBackground::Layer& aLayer,
- const nsStyleBorder& aBorder,
- PRBool aUsePrintSettings);
-
static void DrawBorderImage(nsPresContext* aPresContext,
nsIRenderingContext& aRenderingContext,
nsIFrame* aForFrame,
const nsRect& aBorderArea,
const nsStyleBorder& aBorderStyle,
const nsRect& aDirtyRect);
static void DrawBorderImageComponent(nsIRenderingContext& aRenderingContext,
@@ -806,38 +795,44 @@ nsCSSRendering::PaintFocus(nsPresContext
* nsLayoutUtils::DrawImage. This is the same as aTopLeft, unless CSS
* specifies a percentage (including 'right' or 'bottom'), in which case
* it's that percentage within of aOriginBounds. So 'right' would set
* aAnchorPoint.x to aOriginBounds.XMost().
*
* Points are returned relative to aOriginBounds.
*/
static void
-ComputeBackgroundAnchorPoint(const nsStyleBackground::Layer& aLayer,
+ComputeBackgroundAnchorPoint(const nsStyleBackground& aColor,
const nsSize& aOriginBounds,
const nsSize& aImageSize,
nsPoint* aTopLeft,
nsPoint* aAnchorPoint)
{
- if (!aLayer.mPosition.mXIsPercent) {
- aTopLeft->x = aAnchorPoint->x = aLayer.mPosition.mXPosition.mCoord;
+ if (NS_STYLE_BG_X_POSITION_LENGTH & aColor.mBackgroundFlags) {
+ aTopLeft->x = aAnchorPoint->x = aColor.mBackgroundXPosition.mCoord;
}
- else {
- double percent = aLayer.mPosition.mXPosition.mFloat;
+ else if (NS_STYLE_BG_X_POSITION_PERCENT & aColor.mBackgroundFlags) {
+ double percent = aColor.mBackgroundXPosition.mFloat;
aAnchorPoint->x = NSToCoordRound(percent*aOriginBounds.width);
aTopLeft->x = NSToCoordRound(percent*(aOriginBounds.width - aImageSize.width));
}
+ else {
+ aTopLeft->x = aAnchorPoint->x = 0;
+ }
- if (!aLayer.mPosition.mYIsPercent) {
- aTopLeft->y = aAnchorPoint->y = aLayer.mPosition.mYPosition.mCoord;
+ if (NS_STYLE_BG_Y_POSITION_LENGTH & aColor.mBackgroundFlags) {
+ aTopLeft->y = aAnchorPoint->y = aColor.mBackgroundYPosition.mCoord;
+ }
+ else if (NS_STYLE_BG_Y_POSITION_PERCENT & aColor.mBackgroundFlags) {
+ double percent = aColor.mBackgroundYPosition.mFloat;
+ aAnchorPoint->y = NSToCoordRound(percent*aOriginBounds.height);
+ aTopLeft->y = NSToCoordRound(percent*(aOriginBounds.height - aImageSize.height));
}
else {
- double percent = aLayer.mPosition.mYPosition.mFloat;
- aAnchorPoint->y = NSToCoordRound(percent*aOriginBounds.height);
- aTopLeft->y = NSToCoordRound(percent*(aOriginBounds.height - aImageSize.height));
+ aTopLeft->y = aAnchorPoint->y = 0;
}
}
nsStyleContext*
nsCSSRendering::FindNonTransparentBackground(nsStyleContext* aContext,
PRBool aStartAtParent /*= PR_FALSE*/)
{
NS_ASSERTION(aContext, "Cannot find NonTransparentBackground in a null context" );
@@ -1342,106 +1337,16 @@ IsSolidBorder(const nsStyleBorder& aBord
return PR_FALSE;
for (PRUint32 i = 0; i < 4; ++i) {
if (!IsSolidBorderEdge(aBorder, i))
return PR_FALSE;
}
return PR_TRUE;
}
-static PRBool
-UseImageRequestForBackground(imgIRequest *aRequest)
-{
- if (!aRequest)
- return PR_FALSE;
-
- PRUint32 status = imgIRequest::STATUS_ERROR;
- aRequest->GetImageStatus(&status);
-
- return (status & imgIRequest::STATUS_FRAME_COMPLETE) &&
- (status & imgIRequest::STATUS_SIZE_AVAILABLE);
-}
-
-static inline void
-SetupDirtyRects(const nsRect& aBGClipArea, const nsRect& aCallerDirtyRect,
- nscoord aAppUnitsPerPixel,
- /* OUT: */
- nsRect* aDirtyRect, gfxRect* aDirtyRectGfx)
-{
- aDirtyRect->IntersectRect(aBGClipArea, aCallerDirtyRect);
-
- // Compute the Thebes equivalent of the dirtyRect.
- *aDirtyRectGfx = RectToGfxRect(*aDirtyRect, aAppUnitsPerPixel);
- NS_WARN_IF_FALSE(aDirtyRect->IsEmpty() || !aDirtyRectGfx->IsEmpty(),
- "converted dirty rect should not be empty");
- NS_ABORT_IF_FALSE(!aDirtyRect->IsEmpty() || aDirtyRectGfx->IsEmpty(),
- "second should be empty if first is");
-}
-
-static void
-SetupBackgroundClip(gfxContext *aCtx, PRUint8 aBackgroundClip,
- nsIFrame* aForFrame, const nsRect& aBorderArea,
- const nsRect& aCallerDirtyRect, PRBool aHaveRoundedCorners,
- const gfxCornerSizes& aBGRadii, nscoord aAppUnitsPerPixel,
- gfxContextAutoSaveRestore* aAutoSR,
- /* OUT: */
- nsRect* aBGClipArea, nsRect* aDirtyRect,
- gfxRect* aDirtyRectGfx)
-{
- *aBGClipArea = aBorderArea;
- PRBool radiiAreOuter = PR_TRUE;
- gfxCornerSizes clippedRadii = aBGRadii;
- if (aBackgroundClip != NS_STYLE_BG_CLIP_BORDER) {
- NS_ASSERTION(aBackgroundClip == NS_STYLE_BG_CLIP_PADDING,
- "unexpected background-clip");
- nsMargin border = aForFrame->GetUsedBorder();
- aForFrame->ApplySkipSides(border);
- aBGClipArea->Deflate(border);
-
- if (aHaveRoundedCorners) {
- gfxFloat borderSizes[4] = {
- border.top / aAppUnitsPerPixel, border.right / aAppUnitsPerPixel,
- border.bottom / aAppUnitsPerPixel, border.left / aAppUnitsPerPixel
- };
- nsCSSBorderRenderer::ComputeInnerRadii(aBGRadii, borderSizes,
- &clippedRadii);
- radiiAreOuter = PR_FALSE;
- }
- }
-
- SetupDirtyRects(*aBGClipArea, aCallerDirtyRect, aAppUnitsPerPixel,
- aDirtyRect, aDirtyRectGfx);
-
- if (aDirtyRectGfx->IsEmpty()) {
- // Our caller won't draw anything under this condition, so no need
- // to set more up.
- return;
- }
-
- // If we have rounded corners, clip all subsequent drawing to the
- // rounded rectangle defined by bgArea and bgRadii (we don't know
- // whether the rounded corners intrude on the dirtyRect or not).
- // Do not do this if we have a caller-provided clip rect --
- // as above with bgArea, arguably a bug, but table painting seems
- // to depend on it.
-
- if (aHaveRoundedCorners) {
- gfxRect bgAreaGfx(RectToGfxRect(*aBGClipArea, aAppUnitsPerPixel));
- bgAreaGfx.Round();
- bgAreaGfx.Condition();
- NS_ABORT_IF_FALSE(!bgAreaGfx.IsEmpty(),
- "should have returned early after aDirtyRectGfx test");
-
- aAutoSR->Reset(aCtx);
- aCtx->NewPath();
- aCtx->RoundedRectangle(bgAreaGfx, clippedRadii, radiiAreOuter);
- aCtx->Clip();
- }
-}
-
void
nsCSSRendering::PaintBackgroundWithSC(nsPresContext* aPresContext,
nsIRenderingContext& aRenderingContext,
nsIFrame* aForFrame,
const nsRect& aDirtyRect,
const nsRect& aBorderArea,
const nsStyleBackground& aColor,
const nsStyleBorder& aBorder,
@@ -1472,36 +1377,30 @@ nsCSSRendering::PaintBackgroundWithSC(ns
PRBool drawBackgroundImage = PR_TRUE;
PRBool drawBackgroundColor = PR_TRUE;
if (aUsePrintSettings) {
drawBackgroundImage = aPresContext->GetBackgroundImageDraw();
drawBackgroundColor = aPresContext->GetBackgroundColorDraw();
}
- nsStyleBackground::Image bottomImage(aColor.BottomLayer().mImage);
- PRBool useFallbackColor = PR_FALSE;
- if (bottomImage.mSpecified) {
- if (!drawBackgroundImage ||
- !UseImageRequestForBackground(bottomImage.mRequest)) {
- bottomImage.mRequest = nsnull;
- }
- useFallbackColor = bottomImage.mRequest == nsnull;
- } else {
- NS_ASSERTION(bottomImage.mRequest == nsnull, "malformed image struct");
+ if ((aColor.mBackgroundFlags & NS_STYLE_BG_IMAGE_NONE) ||
+ !aColor.mBackgroundImage) {
+ NS_ASSERTION((aColor.mBackgroundFlags & NS_STYLE_BG_IMAGE_NONE) &&
+ !aColor.mBackgroundImage, "background flags/image mismatch");
+ drawBackgroundImage = PR_FALSE;
}
// If GetBackgroundColorDraw() is false, we are still expected to
// draw color in the background of any frame that's not completely
// transparent, but we are expected to use white instead of whatever
// color was specified.
nscolor bgColor;
if (drawBackgroundColor) {
- bgColor = useFallbackColor ? aColor.mFallbackBackgroundColor
- : aColor.mBackgroundColor;
+ bgColor = aColor.mBackgroundColor;
if (NS_GET_A(bgColor) == 0)
drawBackgroundColor = PR_FALSE;
} else {
bgColor = NS_RGB(255, 255, 255);
if (drawBackgroundImage || !aColor.IsTransparent())
drawBackgroundColor = PR_TRUE;
}
@@ -1511,163 +1410,139 @@ nsCSSRendering::PaintBackgroundWithSC(ns
if (!drawBackgroundImage && !drawBackgroundColor)
return;
// Compute the outermost boundary of the area that might be painted.
gfxContext *ctx = aRenderingContext.ThebesContext();
nscoord appUnitsPerPixel = aPresContext->AppUnitsPerDevPixel();
// Same coordinate space as aBorderArea & aBGClipRect
+ nsRect bgArea;
gfxCornerSizes bgRadii;
PRBool haveRoundedCorners;
+ PRBool radiiAreOuter = PR_TRUE;
{
nscoord radii[8];
haveRoundedCorners =
GetBorderRadiusTwips(aBorder.mBorderRadius, aForFrame->GetSize().width,
radii);
if (haveRoundedCorners)
ComputePixelRadii(radii, aBorderArea, aForFrame->GetSkipSides(),
appUnitsPerPixel, &bgRadii);
}
+ // The background is rendered over the 'background-clip' area,
+ // which is normally equal to the border area but may be reduced
+ // to the padding area by CSS. Also, if the border is solid, we
+ // don't need to draw outside the padding area. In either case,
+ // if the borders are rounded, make sure we use the same inner
+ // radii as the border code will.
+ bgArea = aBorderArea;
+ if (aColor.mBackgroundClip != NS_STYLE_BG_CLIP_BORDER ||
+ IsSolidBorder(aBorder)) {
+ nsMargin border = aForFrame->GetUsedBorder();
+ aForFrame->ApplySkipSides(border);
+ bgArea.Deflate(border);
+ if (haveRoundedCorners) {
+ gfxCornerSizes outerRadii = bgRadii;
+ gfxFloat borderSizes[4] = {
+ border.top / appUnitsPerPixel, border.right / appUnitsPerPixel,
+ border.bottom / appUnitsPerPixel, border.left / appUnitsPerPixel
+ };
+ nsCSSBorderRenderer::ComputeInnerRadii(outerRadii, borderSizes,
+ &bgRadii);
+ radiiAreOuter = PR_FALSE;
+ }
+ }
+
// The 'bgClipArea' (used only by the image tiling logic, far below)
- // is the caller-provided aBGClipRect if any, or else the area
- // determined by the value of 'background-clip' in
- // SetupCurrentBackgroundClip. (Arguably it should be the
- // intersection, but that breaks the table painter -- in particular,
- // taking the intersection breaks reftests/bugs/403429-1[ab].)
- nsRect bgClipArea, dirtyRect;
- gfxRect dirtyRectGfx;
- PRUint8 currentBackgroundClip;
- PRBool isSolidBorder;
- gfxContextAutoSaveRestore autoSR;
- if (aBGClipRect) {
+ // is the caller-provided aBGClipRect if any, or else the bgArea
+ // computed above. (Arguably it should be the intersection, but
+ // that breaks the table painter -- in particular, honoring the
+ // bgArea when we have aBGClipRect breaks reftests/bugs/403429-1[ab].)
+ // The dirtyRect is the intersection of that rectangle with the
+ // caller-provided aDirtyRect. If the dirtyRect is empty there is
+ // nothing to draw.
+
+ nsRect bgClipArea;
+ if (aBGClipRect)
bgClipArea = *aBGClipRect;
- SetupDirtyRects(bgClipArea, aDirtyRect, appUnitsPerPixel,
- &dirtyRect, &dirtyRectGfx);
- } else {
- // The background is rendered over the 'background-clip' area,
- // which is normally equal to the border area but may be reduced
- // to the padding area by CSS. Also, if the border is solid, we
- // don't need to draw outside the padding area. In either case,
- // if the borders are rounded, make sure we use the same inner
- // radii as the border code will.
- // The background-color is drawn based on the bottom
- // background-clip.
- currentBackgroundClip = aColor.BottomLayer().mClip;
- isSolidBorder = IsSolidBorder(aBorder);
- if (isSolidBorder)
- currentBackgroundClip = NS_STYLE_BG_CLIP_PADDING;
- SetupBackgroundClip(ctx, currentBackgroundClip, aForFrame,
- aBorderArea, aDirtyRect, haveRoundedCorners,
- bgRadii, appUnitsPerPixel, &autoSR,
- &bgClipArea, &dirtyRect, &dirtyRectGfx);
+ else
+ bgClipArea = bgArea;
+
+ nsRect dirtyRect;
+ dirtyRect.IntersectRect(bgClipArea, aDirtyRect);
+
+ if (dirtyRect.IsEmpty())
+ return;
+
+ // Compute the Thebes equivalent of the dirtyRect.
+ gfxRect dirtyRectGfx(RectToGfxRect(dirtyRect, appUnitsPerPixel));
+ if (dirtyRectGfx.IsEmpty()) {
+ NS_WARNING("converted dirty rect should not be empty");
+ return;
+ }
+
+ // If we have rounded corners, clip all subsequent drawing to the
+ // rounded rectangle defined by bgArea and bgRadii (we don't know
+ // whether the rounded corners intrude on the dirtyRect or not).
+ // Do not do this if we have a caller-provided clip rect --
+ // as above with bgArea, arguably a bug, but table painting seems
+ // to depend on it.
+
+ gfxContextAutoSaveRestore autoSR;
+ if (haveRoundedCorners && !aBGClipRect) {
+ gfxRect bgAreaGfx(RectToGfxRect(bgArea, appUnitsPerPixel));
+ bgAreaGfx.Round();
+ bgAreaGfx.Condition();
+ if (bgAreaGfx.IsEmpty()) {
+ NS_WARNING("converted background area should not be empty");
+ return;
+ }
+
+ autoSR.SetContext(ctx);
+ ctx->NewPath();
+ ctx->RoundedRectangle(bgAreaGfx, bgRadii, radiiAreOuter);
+ ctx->Clip();
}
// If we might be using a background color, go ahead and set it now.
if (drawBackgroundColor)
ctx->SetColor(gfxRGBA(bgColor));
// If there is no background image, draw a color. (If there is
// neither a background image nor a color, we wouldn't have gotten
// this far.)
if (!drawBackgroundImage) {
- if (!dirtyRectGfx.IsEmpty()) {
+ ctx->NewPath();
+ ctx->Rectangle(dirtyRectGfx, PR_TRUE);
+ ctx->Fill();
+ return;
+ }
+
+ // Lookup the image
+ imgIRequest *req = aPresContext->LoadImage(aColor.mBackgroundImage,
+ aForFrame);
+
+ PRUint32 status = imgIRequest::STATUS_ERROR;
+ if (req)
+ req->GetImageStatus(&status);
+
+ // While waiting for the image, draw a color, if any.
+ if (!req ||
+ !(status & imgIRequest::STATUS_FRAME_COMPLETE) ||
+ !(status & imgIRequest::STATUS_SIZE_AVAILABLE)) {
+ if (drawBackgroundColor) {
ctx->NewPath();
ctx->Rectangle(dirtyRectGfx, PR_TRUE);
ctx->Fill();
}
return;
}
- // Ensure we get invalidated for loads of the image. We need to do
- // this here because this might be the only code that knows about the
- // association of the style data with the frame.
- aPresContext->SetupBackgroundImageLoaders(aForFrame, &aColor);
-
- if (bottomImage.mRequest &&
- aColor.BottomLayer().mRepeat == NS_STYLE_BG_REPEAT_XY &&
- drawBackgroundColor) {
- nsCOMPtr<imgIContainer> image;
- bottomImage.mRequest->GetImage(getter_AddRefs(image));
- // If the image is completely opaque, we may not need to paint
- // the background color.
- nsCOMPtr<gfxIImageFrame> gfxImgFrame;
- image->GetCurrentFrame(getter_AddRefs(gfxImgFrame));
- if (gfxImgFrame) {
- gfxImgFrame->GetNeedsBackground(&drawBackgroundColor);
- if (!drawBackgroundColor) {
- // If the current frame is smaller than its container, we
- // need to paint the background color even if the frame
- // itself is opaque.
- nsIntSize iSize;
- image->GetWidth(&iSize.width);
- image->GetHeight(&iSize.height);
- nsIntRect iframeRect;
- gfxImgFrame->GetRect(iframeRect);
- if (iSize.width != iframeRect.width ||
- iSize.height != iframeRect.height) {
- drawBackgroundColor = PR_TRUE;
- }
- }
- }
- }
-
- // The background color is rendered over the entire dirty area,
- // even if the image isn't.
- if (drawBackgroundColor) {
- if (!dirtyRectGfx.IsEmpty()) {
- ctx->NewPath();
- ctx->Rectangle(dirtyRectGfx, PR_TRUE);
- ctx->Fill();
- }
- }
-
- if (drawBackgroundImage) {
- NS_FOR_VISIBLE_BACKGROUND_LAYERS_BACK_TO_FRONT(i, &aColor) {
- const nsStyleBackground::Layer &layer = aColor.mLayers[i];
- if (!aBGClipRect) {
- PRUint8 newBackgroundClip =
- isSolidBorder ? NS_STYLE_BG_CLIP_PADDING : layer.mClip;
- if (currentBackgroundClip != newBackgroundClip) {
- currentBackgroundClip = newBackgroundClip;
- SetupBackgroundClip(ctx, currentBackgroundClip, aForFrame,
- aBorderArea, aDirtyRect, haveRoundedCorners,
- bgRadii, appUnitsPerPixel, &autoSR,
- &bgClipArea, &dirtyRect, &dirtyRectGfx);
- }
- }
- if (!dirtyRectGfx.IsEmpty()) {
- PaintBackgroundLayer(aPresContext, aRenderingContext, aForFrame,
- dirtyRect, aBorderArea, bgClipArea, aColor,
- layer, aBorder, aUsePrintSettings);
- }
- }
- }
-}
-
-static void
-PaintBackgroundLayer(nsPresContext* aPresContext,
- nsIRenderingContext& aRenderingContext,
- nsIFrame* aForFrame,
- const nsRect& aDirtyRect, // intersected with aBGClipRect
- const nsRect& aBorderArea,
- const nsRect& aBGClipRect,
- const nsStyleBackground& aBackground,
- const nsStyleBackground::Layer& aLayer,
- const nsStyleBorder& aBorder,
- PRBool aUsePrintSettings)
-{
- // Lookup the image
- imgIRequest *req = aLayer.mImage.mRequest;
- if (!UseImageRequestForBackground(req)) {
- // There's no image or it's not ready to be painted.
- return;
- }
-
nsCOMPtr<imgIContainer> image;
req->GetImage(getter_AddRefs(image));
nsIntSize imageIntSize;
image->GetWidth(&imageIntSize.width);
image->GetHeight(&imageIntSize.height);
nsSize imageSize;
@@ -1678,17 +1553,17 @@ PaintBackgroundLayer(nsPresContext* aPre
// relative to aBorderArea
nsRect bgOriginRect;
nsIAtom* frameType = aForFrame->GetType();
nsIFrame* geometryFrame = aForFrame;
if (frameType == nsGkAtoms::inlineFrame ||
frameType == nsGkAtoms::positionedInlineFrame) {
- switch (aBackground.mBackgroundInlinePolicy) {
+ switch (aColor.mBackgroundInlinePolicy) {
case NS_STYLE_BG_INLINE_POLICY_EACH_BOX:
bgOriginRect = nsRect(nsPoint(0,0), aBorderArea.Size());
break;
case NS_STYLE_BG_INLINE_POLICY_BOUNDING_BOX:
bgOriginRect = gInlineBGData->GetBoundingRect(aForFrame);
break;
default:
NS_ERROR("Unknown background-inline-policy value! "
@@ -1705,35 +1580,81 @@ PaintBackgroundLayer(nsPresContext* aPre
"|:viewport| pseudo-element in |html.css|.");
bgOriginRect = geometryFrame->GetRect();
} else {
bgOriginRect = nsRect(nsPoint(0,0), aBorderArea.Size());
}
// Background images are tiled over the 'background-clip' area
// but the origin of the tiling is based on the 'background-origin' area
- if (aLayer.mOrigin != NS_STYLE_BG_ORIGIN_BORDER) {
+ if (aColor.mBackgroundOrigin != NS_STYLE_BG_ORIGIN_BORDER) {
nsMargin border = geometryFrame->GetUsedBorder();
geometryFrame->ApplySkipSides(border);
bgOriginRect.Deflate(border);
- if (aLayer.mOrigin != NS_STYLE_BG_ORIGIN_PADDING) {
+ if (aColor.mBackgroundOrigin != NS_STYLE_BG_ORIGIN_PADDING) {
nsMargin padding = geometryFrame->GetUsedPadding();
geometryFrame->ApplySkipSides(padding);
bgOriginRect.Deflate(padding);
- NS_ASSERTION(aLayer.mOrigin == NS_STYLE_BG_ORIGIN_CONTENT,
+ NS_ASSERTION(aColor.mBackgroundOrigin == NS_STYLE_BG_ORIGIN_CONTENT,
"unknown background-origin value");
}
}
+ PRIntn repeat = aColor.mBackgroundRepeat;
+ switch (repeat) {
+ case NS_STYLE_BG_REPEAT_X:
+ break;
+ case NS_STYLE_BG_REPEAT_Y:
+ break;
+ case NS_STYLE_BG_REPEAT_XY:
+ if (drawBackgroundColor) {
+ // If the image is completely opaque, we may not need to paint
+ // the background color.
+ nsCOMPtr<gfxIImageFrame> gfxImgFrame;
+ image->GetCurrentFrame(getter_AddRefs(gfxImgFrame));
+ if (gfxImgFrame) {
+ gfxImgFrame->GetNeedsBackground(&drawBackgroundColor);
+ if (!drawBackgroundColor) {
+ // If the current frame is smaller than its container, we
+ // need to paint the background color even if the frame
+ // itself is opaque.
+ nsIntSize iSize;
+ image->GetWidth(&iSize.width);
+ image->GetHeight(&iSize.height);
+ nsIntRect iframeRect;
+ gfxImgFrame->GetRect(iframeRect);
+ if (iSize.width != iframeRect.width ||
+ iSize.height != iframeRect.height) {
+ drawBackgroundColor = PR_TRUE;
+ }
+ }
+ }
+ }
+ break;
+ case NS_STYLE_BG_REPEAT_OFF:
+ default:
+ NS_ASSERTION(repeat == NS_STYLE_BG_REPEAT_OFF,
+ "unknown background-repeat value");
+ break;
+ }
+
+ // The background color is rendered over the entire dirty area,
+ // even if the image isn't.
+ if (drawBackgroundColor) {
+ ctx->NewPath();
+ ctx->Rectangle(dirtyRectGfx, PR_TRUE);
+ ctx->Fill();
+ }
+
// Compute the anchor point.
//
// relative to aBorderArea.TopLeft() (which is where the top-left
// of aForFrame's border-box will be rendered)
nsPoint imageTopLeft, anchor;
- if (NS_STYLE_BG_ATTACHMENT_FIXED == aLayer.mAttachment) {
+ if (NS_STYLE_BG_ATTACHMENT_FIXED == aColor.mBackgroundAttachment) {
// If it's a fixed background attachment, then the image is placed
// relative to the viewport, which is the area of the root frame
// in a screen context or the page content frame in a print context.
// Remember that we've drawn position-varying content in this prescontext
aPresContext->SetRenderedPositionVaryingContent();
nsIFrame* topFrame =
@@ -1757,69 +1678,61 @@ PaintBackgroundLayer(nsPresContext* aPre
aPresContext->PresShell()->GetRootScrollFrameAsScrollable();
if (scrollableFrame) {
nsMargin scrollbars = scrollableFrame->GetActualScrollbarSizes();
viewportArea.Deflate(scrollbars);
}
}
// Get the anchor point, relative to the viewport.
- ComputeBackgroundAnchorPoint(aLayer, viewportArea.Size(), imageSize,
+ ComputeBackgroundAnchorPoint(aColor, viewportArea.Size(), imageSize,
&imageTopLeft, &anchor);
// Convert the anchor point from viewport coordinates to aForFrame
// coordinates.
nsPoint offset = viewportArea.TopLeft() - aForFrame->GetOffsetTo(topFrame);
imageTopLeft += offset;
anchor += offset;
} else {
- ComputeBackgroundAnchorPoint(aLayer, bgOriginRect.Size(), imageSize,
+ ComputeBackgroundAnchorPoint(aColor, bgOriginRect.Size(), imageSize,
&imageTopLeft, &anchor);
imageTopLeft += bgOriginRect.TopLeft();
anchor += bgOriginRect.TopLeft();
}
nsRect destArea(imageTopLeft + aBorderArea.TopLeft(), imageSize);
nsRect fillArea = destArea;
- PRIntn repeat = aLayer.mRepeat;
if (repeat & NS_STYLE_BG_REPEAT_X) {
- fillArea.x = aBGClipRect.x;
- fillArea.width = aBGClipRect.width;
+ fillArea.x = bgClipArea.x;
+ fillArea.width = bgClipArea.width;
}
if (repeat & NS_STYLE_BG_REPEAT_Y) {
- fillArea.y = aBGClipRect.y;
- fillArea.height = aBGClipRect.height;
+ fillArea.y = bgClipArea.y;
+ fillArea.height = bgClipArea.height;
}
- fillArea.IntersectRect(fillArea, aBGClipRect);
+ fillArea.IntersectRect(fillArea, bgClipArea);
nsLayoutUtils::DrawImage(&aRenderingContext, image,
- destArea, fillArea, anchor + aBorderArea.TopLeft(), aDirtyRect);
+ destArea, fillArea, anchor + aBorderArea.TopLeft(), dirtyRect);
}
static void
DrawBorderImage(nsPresContext* aPresContext,
nsIRenderingContext& aRenderingContext,
nsIFrame* aForFrame,
const nsRect& aBorderArea,
const nsStyleBorder& aBorderStyle,
const nsRect& aDirtyRect)
{
if (aDirtyRect.IsEmpty())
return;
- // Ensure we get invalidated for loads and animations of the image.
- // We need to do this here because this might be the only code that
- // knows about the association of the style data with the frame.
- // XXX We shouldn't really... since if anybody is passing in a
- // different style, they'll potentially have the wrong size for the
- // border too.
- aPresContext->SetupBorderImageLoaders(aForFrame, &aBorderStyle);
-
- imgIRequest *req = aBorderStyle.GetBorderImage();
-
+ // Clone the image loader and set up animation notifications.
+ imgIRequest *req =
+ aPresContext->LoadBorderImage(aBorderStyle.GetBorderImage(), aForFrame);
#ifdef DEBUG
{
PRUint32 status = imgIRequest::STATUS_ERROR;
if (req)
req->GetImageStatus(&status);
NS_ASSERTION(req && (status & imgIRequest::STATUS_FRAME_COMPLETE),
"no image to draw");
--- a/layout/base/nsDisplayList.cpp
+++ b/layout/base/nsDisplayList.cpp
@@ -492,37 +492,35 @@ nsDisplayBackground::IsOpaque(nsDisplayL
if (mIsThemed)
return PR_FALSE;
const nsStyleBackground* bg;
PRBool hasBG =
nsCSSRendering::FindBackground(mFrame->PresContext(), mFrame, &bg);
return (hasBG && NS_GET_A(bg->mBackgroundColor) == 255 &&
- // bottom layer's clip is used for the color
- bg->BottomLayer().mClip == NS_STYLE_BG_CLIP_BORDER &&
+ bg->mBackgroundClip == NS_STYLE_BG_CLIP_BORDER &&
!nsLayoutUtils::HasNonZeroCorner(mFrame->GetStyleBorder()->
mBorderRadius));
}
PRBool
nsDisplayBackground::IsUniform(nsDisplayListBuilder* aBuilder) {
// theme background overrides any other background
if (mIsThemed)
return PR_FALSE;
const nsStyleBackground* bg;
PRBool hasBG =
nsCSSRendering::FindBackground(mFrame->PresContext(), mFrame, &bg);
if (!hasBG)
return PR_TRUE;
- if (!bg->BottomLayer().mImage.mRequest &&
- bg->mImageCount == 1 &&
+ if ((bg->mBackgroundFlags & NS_STYLE_BG_IMAGE_NONE) &&
!nsLayoutUtils::HasNonZeroCorner(mFrame->GetStyleBorder()->mBorderRadius) &&
- bg->BottomLayer().mClip == NS_STYLE_BG_CLIP_BORDER)
+ bg->mBackgroundClip == NS_STYLE_BG_CLIP_BORDER)
return PR_TRUE;
return PR_FALSE;
}
PRBool
nsDisplayBackground::IsVaryingRelativeToMovingFrame(nsDisplayListBuilder* aBuilder)
{
NS_ASSERTION(aBuilder->IsMovingFrame(mFrame),
--- a/layout/base/nsFrameManager.cpp
+++ b/layout/base/nsFrameManager.cpp
@@ -86,16 +86,17 @@
#include "nsContentUtils.h"
#include "nsReadableUtils.h"
#include "nsUnicharUtils.h"
#include "nsPrintfCString.h"
#include "nsLayoutErrors.h"
#include "nsLayoutUtils.h"
#include "nsAutoPtr.h"
#include "imgIRequest.h"
+#include "nsStyleStructInlines.h"
#include "nsFrameManager.h"
#ifdef ACCESSIBILITY
#include "nsIAccessibilityService.h"
#include "nsIAccessibleEvent.h"
#endif
#ifdef DEBUG
@@ -1079,16 +1080,34 @@ CaptureChange(nsStyleContext* aOldContex
nsChangeHint ourChange = aOldContext->CalcStyleDifference(aNewContext);
NS_UpdateHint(ourChange, aChangeToAssume);
if (NS_UpdateHint(aMinChange, ourChange)) {
aChangeList->AppendChange(aFrame, aContent, ourChange);
}
return aMinChange;
}
+static PRBool
+ShouldStopImage(imgIRequest *aOldImage, imgIRequest *aNewImage)
+{
+ if (!aOldImage)
+ return PR_FALSE;
+
+ PRBool stopImages = !aNewImage;
+ if (!stopImages) {
+ nsCOMPtr<nsIURI> oldURI, newURI;
+ aOldImage->GetURI(getter_AddRefs(oldURI));
+ aNewImage->GetURI(getter_AddRefs(newURI));
+ PRBool equal;
+ stopImages =
+ NS_FAILED(oldURI->Equals(newURI, &equal)) || !equal;
+ }
+ return stopImages;
+}
+
/**
* Recompute style for aFrame and accumulate changes into aChangeList
* given that aMinChange is already accumulated for an ancestor.
* aParentContent is the content node used to resolve the parent style
* context. This means that, for pseudo-elements, it is the content
* that should be used for selector matching (rather than the fake
* content node attached to the frame).
*/
@@ -1240,16 +1259,43 @@ nsFrameManager::ReResolveStyleContext(ns
if (newContext != oldContext) {
aMinChange = CaptureChange(oldContext, newContext, aFrame,
content, aChangeList, aMinChange,
assumeDifferenceHint);
if (!(aMinChange & nsChangeHint_ReconstructFrame)) {
// if frame gets regenerated, let it keep old context
aFrame->SetStyleContext(newContext);
}
+ // if old context had image and new context does not have the same image,
+ // stop the image load for the frame
+ if (ShouldStopImage(
+ oldContext->GetStyleBackground()->mBackgroundImage,
+ newContext->GetStyleBackground()->mBackgroundImage)) {
+ // stop the image loading for the frame, the image has changed
+ aPresContext->StopBackgroundImageFor(aFrame);
+ }
+
+ imgIRequest *newBorderImage =
+ newContext->GetStyleBorder()->GetBorderImage();
+ if (ShouldStopImage(oldContext->GetStyleBorder()->GetBorderImage(),
+ newBorderImage)) {
+ // stop the image loading for the frame, the image has changed
+ aPresContext->StopBorderImageFor(aFrame);
+ }
+
+ // Since the CalcDifference call depended on the result of
+ // GetActualBorder() and that result depends on whether the
+ // image has loaded, start the image load now so that we'll get
+ // notified when it completes loading and can do a restyle.
+ // Otherwise, the image might finish loading from the network
+ // before we start listening to its notifications, and then
+ // we'll never know that it's finished loading.
+ if (newBorderImage) {
+ aPresContext->LoadBorderImage(newBorderImage, aFrame);
+ }
}
oldContext->Release();
}
else {
NS_ERROR("resolve style context failed");
newContext = oldContext; // new context failed, recover... (take ref)
oldContext = nsnull;
}
--- a/layout/base/nsImageLoader.cpp
+++ b/layout/base/nsImageLoader.cpp
@@ -58,78 +58,79 @@
#include "nsStyleContext.h"
#include "nsGkAtoms.h"
// Paint forcing
#include "prenv.h"
NS_IMPL_ISUPPORTS2(nsImageLoader, imgIDecoderObserver, imgIContainerObserver)
-nsImageLoader::nsImageLoader(nsIFrame *aFrame, PRBool aReflowOnLoad,
- nsImageLoader *aNextLoader)
- : mFrame(aFrame),
- mReflowOnLoad(aReflowOnLoad),
- mNextLoader(aNextLoader)
+nsImageLoader::nsImageLoader() :
+ mFrame(nsnull), mPresContext(nsnull)
{
}
nsImageLoader::~nsImageLoader()
{
mFrame = nsnull;
+ mPresContext = nsnull;
if (mRequest) {
mRequest->CancelAndForgetObserver(NS_ERROR_FAILURE);
}
}
-/* static */ already_AddRefed<nsImageLoader>
-nsImageLoader::Create(nsIFrame *aFrame, imgIRequest *aRequest,
- PRBool aReflowOnLoad, nsImageLoader *aNextLoader)
+
+void
+nsImageLoader::Init(nsIFrame *aFrame, nsPresContext *aPresContext,
+ PRBool aReflowOnLoad)
{
- nsRefPtr<nsImageLoader> loader =
- new nsImageLoader(aFrame, aReflowOnLoad, aNextLoader);
-
- loader->Load(aRequest);
-
- return loader.forget();
+ mFrame = aFrame;
+ mPresContext = aPresContext;
+ mReflowOnLoad = aReflowOnLoad;
}
void
nsImageLoader::Destroy()
{
- // Destroy the chain with only one level of recursion.
- nsRefPtr<nsImageLoader> list = mNextLoader;
- mNextLoader = nsnull;
- while (list) {
- nsRefPtr<nsImageLoader> todestroy = list;
- list = todestroy->mNextLoader;
- todestroy->mNextLoader = nsnull;
- todestroy->Destroy();
- }
-
mFrame = nsnull;
+ mPresContext = nsnull;
if (mRequest) {
mRequest->CancelAndForgetObserver(NS_ERROR_FAILURE);
}
mRequest = nsnull;
}
nsresult
nsImageLoader::Load(imgIRequest *aImage)
{
- NS_ASSERTION(!mRequest, "can't reuse image loaders");
-
if (!mFrame)
return NS_ERROR_NOT_INITIALIZED;
if (!aImage)
return NS_ERROR_FAILURE;
+ if (mRequest) {
+ nsCOMPtr<nsIURI> oldURI;
+ mRequest->GetURI(getter_AddRefs(oldURI));
+ nsCOMPtr<nsIURI> newURI;
+ aImage->GetURI(getter_AddRefs(newURI));
+ PRBool eq = PR_FALSE;
+ nsresult rv = newURI->Equals(oldURI, &eq);
+ if (NS_SUCCEEDED(rv) && eq) {
+ return NS_OK;
+ }
+
+ // Now cancel the old request so it won't hold a stale ref to us.
+ mRequest->CancelAndForgetObserver(NS_ERROR_FAILURE);
+ mRequest = nsnull;
+ }
+
// Make sure to clone into a temporary, then set mRequest, since
// cloning may notify and we don't want to trigger paints from this
// code.
nsCOMPtr<imgIRequest> newRequest;
nsresult rv = aImage->Clone(this, getter_AddRefs(newRequest));
mRequest.swap(newRequest);
return rv;
}
@@ -141,17 +142,17 @@ NS_IMETHODIMP nsImageLoader::OnStartCont
{
if (aImage)
{
/* Get requested animation policy from the pres context:
* normal = 0
* one frame = 1
* one loop = 2
*/
- aImage->SetAnimationMode(mFrame->PresContext()->ImageAnimationMode());
+ aImage->SetAnimationMode(mPresContext->ImageAnimationMode());
// Ensure the animation (if any) is started.
aImage->StartAnimation();
}
return NS_OK;
}
NS_IMETHODIMP nsImageLoader::OnStopFrame(imgIRequest *aRequest,
gfxIImageFrame *aFrame)
@@ -200,17 +201,17 @@ NS_IMETHODIMP nsImageLoader::FrameChange
return NS_OK;
}
void
nsImageLoader::RedrawDirtyFrame(const nsRect* aDamageRect)
{
if (mReflowOnLoad) {
- nsIPresShell *shell = mFrame->PresContext()->GetPresShell();
+ nsIPresShell *shell = mPresContext->GetPresShell();
#ifdef DEBUG
nsresult rv =
#endif
shell->FrameNeedsReflow(mFrame, nsIPresShell::eStyleChange, NS_FRAME_IS_DIRTY);
NS_WARN_IF_FALSE(NS_SUCCEEDED(rv), "Could not reflow after loading border-image");
// The reflow might not do all the invalidation we need, so continue
// on with the invalidation codepath.
}
--- a/layout/base/nsImageLoader.h
+++ b/layout/base/nsImageLoader.h
@@ -32,66 +32,58 @@
* use your version of this file under the terms of the MPL, indicate your
* decision by deleting the provisions above and replace them with the notice
* and other provisions required by the GPL or the LGPL. If you do not delete
* the provisions above, a recipient may use your version of this file under
* the terms of any one of the MPL, the GPL or the LGPL.
*
* ***** END LICENSE BLOCK ***** */
-/* class to notify frames of background and border image loads */
+/* class to notify frames of background image loads */
#include "nsStubImageDecoderObserver.h"
+class nsPresContext;
class nsIFrame;
class nsIURI;
#include "imgIRequest.h"
#include "nsCOMPtr.h"
-#include "nsAutoPtr.h"
-/**
- * Image loaders pass notifications for background and border image
- * loading and animation on to the frames.
- *
- * Each frame's image loaders form a linked list.
- */
class nsImageLoader : public nsStubImageDecoderObserver
{
-private:
- nsImageLoader(nsIFrame *aFrame, PRBool aReflowOnLoad,
- nsImageLoader *aNextLoader);
+public:
+ nsImageLoader();
virtual ~nsImageLoader();
-public:
- static already_AddRefed<nsImageLoader>
- Create(nsIFrame *aFrame, imgIRequest *aRequest,
- PRBool aReflowOnLoad, nsImageLoader *aNextLoader);
-
NS_DECL_ISUPPORTS
// imgIDecoderObserver (override nsStubImageDecoderObserver)
NS_IMETHOD OnStartContainer(imgIRequest *aRequest, imgIContainer *aImage);
NS_IMETHOD OnStopFrame(imgIRequest *aRequest, gfxIImageFrame *aFrame);
// Do not override OnDataAvailable since background images are not
// displayed incrementally; they are displayed after the entire image
// has been loaded.
// Note: Images referenced by the <img> element are displayed
// incrementally in nsImageFrame.cpp.
// imgIContainerObserver (override nsStubImageDecoderObserver)
NS_IMETHOD FrameChanged(imgIContainer *aContainer, gfxIImageFrame *newframe,
nsIntRect *dirtyRect);
+ void Init(nsIFrame *aFrame, nsPresContext *aPresContext,
+ PRBool aReflowOnLoad);
+ nsresult Load(imgIRequest *aImage);
+
void Destroy();
+ nsIFrame *GetFrame() { return mFrame; }
imgIRequest *GetRequest() { return mRequest; }
- nsImageLoader *GetNextLoader() { return mNextLoader; }
private:
- nsresult Load(imgIRequest *aImage);
void RedrawDirtyFrame(const nsRect* aDamageRect);
+private:
nsIFrame *mFrame;
+ nsPresContext *mPresContext;
nsCOMPtr<imgIRequest> mRequest;
PRBool mReflowOnLoad;
- nsRefPtr<nsImageLoader> mNextLoader;
};
--- a/layout/base/nsLayoutUtils.cpp
+++ b/layout/base/nsLayoutUtils.cpp
@@ -3061,20 +3061,19 @@ nsLayoutUtils::GetFrameTransparency(nsIF
if (aFrame->GetType() == nsGkAtoms::viewportFrame &&
!aFrame->GetFirstChild(nsnull)) {
return eTransparencyOpaque;
}
const nsStyleBackground* bg;
if (!nsCSSRendering::FindBackground(aFrame->PresContext(), aFrame, &bg))
return eTransparencyTransparent;
- if (NS_GET_A(bg->mBackgroundColor) < 255 ||
- NS_GET_A(bg->mFallbackBackgroundColor) < 255 ||
- // bottom layer's clip is used for the color
- bg->BottomLayer().mClip != NS_STYLE_BG_CLIP_BORDER)
+ if (NS_GET_A(bg->mBackgroundColor) < 255)
+ return eTransparencyTransparent;
+ if (bg->mBackgroundClip != NS_STYLE_BG_CLIP_BORDER)
return eTransparencyTransparent;
return eTransparencyOpaque;
}
static PRBool
IsNonzeroCoord(const nsStyleCoord& aCoord)
{
if (eStyleUnit_Coord == aCoord.GetUnit())
--- a/layout/base/nsPresContext.cpp
+++ b/layout/base/nsPresContext.cpp
@@ -84,17 +84,16 @@
#include "nsStyleChangeList.h"
#include "nsRuleNode.h"
#include "nsEventDispatcher.h"
#include "gfxUserFontSet.h"
#include "gfxPlatform.h"
#include "nsCSSRules.h"
#include "nsFontFaceLoader.h"
#include "nsIEventListenerManager.h"
-#include "nsStyleStructInlines.h"
#ifdef MOZ_SMIL
#include "nsSMILAnimationController.h"
#endif // MOZ_SMIL
#ifdef IBMBIDI
#include "nsBidiPresUtils.h"
#endif // IBMBIDI
@@ -155,17 +154,17 @@ IsVisualCharset(const nsCString& aCharse
else {
return PR_FALSE; // logical text type
}
}
#endif // IBMBIDI
static PLDHashOperator
-destroy_loads(const void * aKey, nsRefPtr<nsImageLoader>& aData, void* closure)
+destroy_loads(const void * aKey, nsCOMPtr<nsImageLoader>& aData, void* closure)
{
aData->Destroy();
return PL_DHASH_NEXT;
}
static NS_DEFINE_CID(kLookAndFeelCID, NS_LOOKANDFEEL_CID);
#include "nsContentCID.h"
@@ -242,18 +241,18 @@ nsPresContext::nsPresContext(nsIDocument
}
NS_ASSERTION(mDocument, "Null document");
mUserFontSet = nsnull;
mUserFontSetDirty = PR_TRUE;
}
nsPresContext::~nsPresContext()
{
- for (PRUint32 i = 0; i < IMAGE_LOAD_TYPE_COUNT; ++i)
- mImageLoaders[i].Enumerate(destroy_loads, nsnull);
+ mImageLoaders.Enumerate(destroy_loads, nsnull);
+ mBorderImageLoaders.Enumerate(destroy_loads, nsnull);
NS_PRECONDITION(!mShell, "Presshell forgot to clear our mShell pointer");
SetShell(nsnull);
if (mEventManager) {
// unclear if these are needed, but can't hurt
mEventManager->NotifyDestroyPresContext(this);
mEventManager->SetPresContext(nsnull);
@@ -309,17 +308,17 @@ NS_INTERFACE_MAP_BEGIN_CYCLE_COLLECTION(
NS_INTERFACE_MAP_ENTRY_AMBIGUOUS(nsISupports, nsIObserver)
NS_INTERFACE_MAP_ENTRY(nsIObserver)
NS_INTERFACE_MAP_END
NS_IMPL_CYCLE_COLLECTING_ADDREF(nsPresContext)
NS_IMPL_CYCLE_COLLECTING_RELEASE(nsPresContext)
static PLDHashOperator
-TraverseImageLoader(const void * aKey, nsRefPtr<nsImageLoader>& aData,
+TraverseImageLoader(const void * aKey, nsCOMPtr<nsImageLoader>& aData,
void* aClosure)
{
nsCycleCollectionTraversalCallback *cb =
static_cast<nsCycleCollectionTraversalCallback*>(aClosure);
cb->NoteXPCOMChild(aData);
return PL_DHASH_NEXT;
@@ -327,18 +326,18 @@ TraverseImageLoader(const void * aKey, n
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_BEGIN(nsPresContext)
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_NSCOMPTR(mDocument);
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_RAWPTR(mDeviceContext); // worth bothering?
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_RAWPTR(mEventManager);
// NS_IMPL_CYCLE_COLLECTION_TRAVERSE_RAWPTR(mLookAndFeel); // a service
// NS_IMPL_CYCLE_COLLECTION_TRAVERSE_RAWPTR(mLangGroup); // an atom
- for (PRUint32 i = 0; i < IMAGE_LOAD_TYPE_COUNT; ++i)
- tmp->mImageLoaders[i].Enumerate(TraverseImageLoader, &cb);
+ tmp->mImageLoaders.Enumerate(TraverseImageLoader, &cb);
+ tmp->mBorderImageLoaders.Enumerate(TraverseImageLoader, &cb);
// NS_IMPL_CYCLE_COLLECTION_TRAVERSE_NSCOMPTR(mTheme); // a service
// NS_IMPL_CYCLE_COLLECTION_TRAVERSE_NSCOMPTR(mLangService); // a service
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_NSCOMPTR(mPrintSettings);
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_NSCOMPTR(mPrefChangedTimer);
NS_IMPL_CYCLE_COLLECTION_TRAVERSE_END
NS_IMPL_CYCLE_COLLECTION_UNLINK_BEGIN(nsPresContext)
@@ -350,20 +349,20 @@ NS_IMPL_CYCLE_COLLECTION_UNLINK_BEGIN(ns
tmp->mEventManager->SetPresContext(nsnull);
NS_RELEASE(tmp->mEventManager);
}
// NS_RELEASE(tmp->mLookAndFeel); // a service
// NS_RELEASE(tmp->mLangGroup); // an atom
- for (PRUint32 i = 0; i < IMAGE_LOAD_TYPE_COUNT; ++i) {
- tmp->mImageLoaders[i].Enumerate(destroy_loads, nsnull);
- tmp->mImageLoaders[i].Clear();
- }
+ tmp->mImageLoaders.Enumerate(destroy_loads, nsnull);
+ tmp->mImageLoaders.Clear();
+ tmp->mBorderImageLoaders.Enumerate(destroy_loads, nsnull);
+ tmp->mBorderImageLoaders.Clear();
// NS_IMPL_CYCLE_COLLECTION_UNLINK_NSCOMPTR(mTheme); // a service
// NS_IMPL_CYCLE_COLLECTION_UNLINK_NSCOMPTR(mLangService); // a service
NS_IMPL_CYCLE_COLLECTION_UNLINK_NSCOMPTR(mPrintSettings);
if (tmp->mPrefChangedTimer)
{
tmp->mPrefChangedTimer->Cancel();
tmp->mPrefChangedTimer = nsnull;
@@ -833,19 +832,21 @@ nsPresContext::Init(nsIDeviceContext* aD
mDeviceContext = aDeviceContext;
NS_ADDREF(mDeviceContext);
if (mDeviceContext->SetPixelScale(mFullZoom))
mDeviceContext->FlushFontCache();
mCurAppUnitsPerDevPixel = AppUnitsPerDevPixel();
- for (PRUint32 i = 0; i < IMAGE_LOAD_TYPE_COUNT; ++i)
- if (!mImageLoaders[i].Init())
- return NS_ERROR_OUT_OF_MEMORY;
+ if (!mImageLoaders.Init())
+ return NS_ERROR_OUT_OF_MEMORY;
+
+ if (!mBorderImageLoaders.Init())
+ return NS_ERROR_OUT_OF_MEMORY;
// Get the look and feel service here; default colors will be initialized
// from calling GetUserPreferences() when we get a presshell.
nsresult rv = CallGetService(kLookAndFeelCID, &mLookAndFeel);
if (NS_FAILED(rv)) {
NS_ERROR("LookAndFeel service must be implemented for this toolkit");
return rv;
}
@@ -1052,23 +1053,20 @@ static void SetImgAnimModeOnImgReq(imgIR
if (imgCon) {
imgCon->SetAnimationMode(aMode);
}
}
}
// Enumeration call back for HashTable
static PLDHashOperator
-set_animation_mode(const void * aKey, nsRefPtr<nsImageLoader>& aData, void* closure)
+set_animation_mode(const void * aKey, nsCOMPtr<nsImageLoader>& aData, void* closure)
{
- for (nsImageLoader *loader = aData; loader;
- loader = loader->GetNextLoader()) {
- imgIRequest* imgReq = loader->GetRequest();
- SetImgAnimModeOnImgReq(imgReq, (PRUint16)NS_PTR_TO_INT32(closure));
- }
+ imgIRequest* imgReq = aData->GetRequest();
+ SetImgAnimModeOnImgReq(imgReq, (PRUint16)NS_PTR_TO_INT32(closure));
return PL_DHASH_NEXT;
}
// IMPORTANT: Assumption is that all images for a Presentation
// have the same Animation Mode (pavlov said this was OK)
//
// Walks content and set the animation mode
// this is a way to turn on/off image animations
@@ -1119,18 +1117,18 @@ nsPresContext::SetImageAnimationModeInte
aMode == imgIContainer::kDontAnimMode ||
aMode == imgIContainer::kLoopOnceAnimMode, "Wrong Animation Mode is being set!");
// Image animation mode cannot be changed when rendering to a printer.
if (!IsDynamic())
return;
// Set the mode on the image loaders.
- for (PRUint32 i = 0; i < IMAGE_LOAD_TYPE_COUNT; ++i)
- mImageLoaders[i].Enumerate(set_animation_mode, NS_INT32_TO_PTR(aMode));
+ mImageLoaders.Enumerate(set_animation_mode, NS_INT32_TO_PTR(aMode));
+ mBorderImageLoaders.Enumerate(set_animation_mode, NS_INT32_TO_PTR(aMode));
// Now walk the content tree and set the animation mode
// on all the images.
if (mShell != nsnull) {
nsIDocument *doc = mShell->GetDocument();
if (doc) {
nsIContent *rootContent = doc->GetRootContent();
if (rootContent) {
@@ -1225,64 +1223,77 @@ nsPresContext::SetFullZoom(float aZoom)
RebuildAllStyleData(NS_STYLE_HINT_REFLOW);
}
mSupressResizeReflow = PR_FALSE;
mCurAppUnitsPerDevPixel = AppUnitsPerDevPixel();
}
-void
-nsPresContext::SetImageLoaders(nsIFrame* aTargetFrame,
- ImageLoadType aType,
- nsImageLoader* aImageLoaders)
+imgIRequest*
+nsPresContext::DoLoadImage(nsPresContext::ImageLoaderTable& aTable,
+ imgIRequest* aImage,
+ nsIFrame* aTargetFrame,
+ PRBool aReflowOnLoad)
{
- nsRefPtr<nsImageLoader> oldLoaders;
- mImageLoaders[aType].Get(aTargetFrame, getter_AddRefs(oldLoaders));
+ // look and see if we have a loader for the target frame.
+ nsCOMPtr<nsImageLoader> loader;
+ aTable.Get(aTargetFrame, getter_AddRefs(loader));
- if (aImageLoaders) {
- mImageLoaders[aType].Put(aTargetFrame, aImageLoaders);
- } else if (oldLoaders) {
- mImageLoaders[aType].Remove(aTargetFrame);
+ if (!loader) {
+ loader = new nsImageLoader();
+ if (!loader)
+ return nsnull;
+
+ loader->Init(aTargetFrame, this, aReflowOnLoad);
+ aTable.Put(aTargetFrame, loader);
}
- if (oldLoaders)
- oldLoaders->Destroy();
+ loader->Load(aImage);
+
+ imgIRequest *request = loader->GetRequest();
+
+ return request;
}
-void
-nsPresContext::SetupBackgroundImageLoaders(nsIFrame* aFrame,
- const nsStyleBackground* aStyleBackground)
+imgIRequest*
+nsPresContext::LoadImage(imgIRequest* aImage, nsIFrame* aTargetFrame)
{
- nsRefPtr<nsImageLoader> loaders;
- NS_FOR_VISIBLE_BACKGROUND_LAYERS_BACK_TO_FRONT(i, aStyleBackground) {
- imgIRequest *image = aStyleBackground->mLayers[i].mImage.mRequest;
- loaders = nsImageLoader::Create(aFrame, image, PR_FALSE, loaders);
- }
- SetImageLoaders(aFrame, BACKGROUND_IMAGE, loaders);
+ return DoLoadImage(mImageLoaders, aImage, aTargetFrame, PR_FALSE);
}
-void
-nsPresContext::SetupBorderImageLoaders(nsIFrame* aFrame,
- const nsStyleBorder* aStyleBorder)
+imgIRequest*
+nsPresContext::LoadBorderImage(imgIRequest* aImage, nsIFrame* aTargetFrame)
{
- nsRefPtr<nsImageLoader> loader =
- nsImageLoader::Create(aFrame, aStyleBorder->GetBorderImage(),
- aStyleBorder->ImageBorderDiffers(), nsnull);
- SetImageLoaders(aFrame, BORDER_IMAGE, loader);
+ return DoLoadImage(mBorderImageLoaders, aImage, aTargetFrame,
+ aTargetFrame->GetStyleBorder()->ImageBorderDiffers());
}
void
nsPresContext::StopImagesFor(nsIFrame* aTargetFrame)
{
- for (PRUint32 i = 0; i < IMAGE_LOAD_TYPE_COUNT; ++i)
- SetImageLoaders(aTargetFrame, ImageLoadType(i), nsnull);
+ StopBackgroundImageFor(aTargetFrame);
+ StopBorderImageFor(aTargetFrame);
}
void
+nsPresContext::DoStopImageFor(nsPresContext::ImageLoaderTable& aTable,
+ nsIFrame* aTargetFrame)
+{
+ nsCOMPtr<nsImageLoader> loader;
+ aTable.Get(aTargetFrame, getter_AddRefs(loader));
+
+ if (loader) {
+ loader->Destroy();
+
+ aTable.Remove(aTargetFrame);
+ }
+}
+
+void
nsPresContext::SetContainer(nsISupports* aHandler)
{
mContainer = do_GetWeakReference(aHandler);
if (mContainer) {
GetDocumentColorPreferences();
}
}
--- a/layout/base/nsPresContext.h
+++ b/layout/base/nsPresContext.h
@@ -55,17 +55,17 @@
#include "nsILanguageAtomService.h"
#include "nsIObserver.h"
#include "nsITimer.h"
#include "nsCRT.h"
#include "nsIPrintSettings.h"
#include "nsPropertyTable.h"
#include "nsGkAtoms.h"
#include "nsIDocument.h"
-#include "nsRefPtrHashtable.h"
+#include "nsInterfaceHashtable.h"
#include "nsCycleCollectionParticipant.h"
#include "nsChangeHint.h"
// This also pulls in gfxTypes.h, which we cannot include directly.
#include "gfxRect.h"
#include "nsRegion.h"
#include "nsTArray.h"
#include "nsAutoPtr.h"
#include "nsThreadUtils.h"
@@ -88,17 +88,16 @@ class nsILinkHandler;
class nsStyleContext;
class nsIAtom;
class nsIEventStateManager;
class nsIURI;
class nsILookAndFeel;
class nsICSSPseudoComparator;
class nsIAtom;
struct nsStyleBackground;
-struct nsStyleBorder;
class nsIRunnable;
class gfxUserFontSet;
class nsUserFontSet;
struct nsFontFaceRuleContainer;
#ifdef MOZ_REFLOW_PERF
class nsIRenderingContext;
#endif
@@ -374,56 +373,51 @@ public:
const nscolor FocusBackgroundColor() const { return mFocusBackgroundColor; }
const nscolor FocusTextColor() const { return mFocusTextColor; }
PRBool GetUseFocusColors() const { return mUseFocusColors; }
PRUint8 FocusRingWidth() const { return mFocusRingWidth; }
PRBool GetFocusRingOnAnything() const { return mFocusRingOnAnything; }
PRUint8 GetFocusRingStyle() const { return mFocusRingStyle; }
- /**
- * The types of image load types that the pres context needs image
- * loaders to track invalidation for.
- */
- enum ImageLoadType {
- BACKGROUND_IMAGE,
- BORDER_IMAGE,
- IMAGE_LOAD_TYPE_COUNT
- };
/**
- * Set the list of image loaders that track invalidation for a
- * specific frame and type of image. This list will replace any
- * previous list for that frame and image type (and null will remove
- * any previous list).
+ * Set up observers so that aTargetFrame will be invalidated when
+ * aImage loads, where aImage is its background image. Only a single
+ * image will be tracked per frame.
*/
- NS_HIDDEN_(void) SetImageLoaders(nsIFrame* aTargetFrame,
- ImageLoadType aType,
- nsImageLoader* aImageLoaders);
-
+ NS_HIDDEN_(imgIRequest*) LoadImage(imgIRequest* aImage,
+ nsIFrame* aTargetFrame);
/**
- * Make an appropriate SetImageLoaders call (including potentially
- * with null aImageLoaders) given that aFrame draws its background
- * based on aStyleBackground.
+ * Set up observers so that aTargetFrame will be invalidated or
+ * reflowed (as appropriate) when aImage loads, where aImage is its
+ * *border* image. Only a single image will be tracked per frame.
*/
- NS_HIDDEN_(void) SetupBackgroundImageLoaders(nsIFrame* aFrame,
- const nsStyleBackground*
- aStyleBackground);
+ NS_HIDDEN_(imgIRequest*) LoadBorderImage(imgIRequest* aImage,
+ nsIFrame* aTargetFrame);
+
+private:
+ typedef nsInterfaceHashtable<nsVoidPtrHashKey, nsImageLoader> ImageLoaderTable;
- /**
- * Make an appropriate SetImageLoaders call (including potentially
- * with null aImageLoaders) given that aFrame draws its border
- * based on aStyleBorder.
- */
- NS_HIDDEN_(void) SetupBorderImageLoaders(nsIFrame* aFrame,
- const nsStyleBorder* aStyleBorder);
+ NS_HIDDEN_(imgIRequest*) DoLoadImage(ImageLoaderTable& aTable,
+ imgIRequest* aImage,
+ nsIFrame* aTargetFrame,
+ PRBool aReflowOnLoad);
+ NS_HIDDEN_(void) DoStopImageFor(ImageLoaderTable& aTable,
+ nsIFrame* aTargetFrame);
+public:
+
+ NS_HIDDEN_(void) StopBackgroundImageFor(nsIFrame* aTargetFrame)
+ { DoStopImageFor(mImageLoaders, aTargetFrame); }
+ NS_HIDDEN_(void) StopBorderImageFor(nsIFrame* aTargetFrame)
+ { DoStopImageFor(mBorderImageLoaders, aTargetFrame); }
/**
* This method is called when a frame is being destroyed to
- * ensure that the image loads get disassociated from the prescontext
+ * ensure that the image load gets disassociated from the prescontext
*/
NS_HIDDEN_(void) StopImagesFor(nsIFrame* aTargetFrame);
NS_HIDDEN_(void) SetContainer(nsISupports* aContainer);
virtual NS_HIDDEN_(already_AddRefed<nsISupports>) GetContainerExternal() const;
NS_HIDDEN_(already_AddRefed<nsISupports>) GetContainerInternal() const;
#ifdef _IMPL_NS_LAYOUT
@@ -848,19 +842,18 @@ protected:
nsIEventStateManager* mEventManager; // [STRONG]
nsILookAndFeel* mLookAndFeel; // [STRONG]
nsIAtom* mMedium; // initialized by subclass ctors;
// weak pointer to static atom
nsILinkHandler* mLinkHandler; // [WEAK]
nsIAtom* mLangGroup; // [STRONG]
- nsRefPtrHashtable<nsVoidPtrHashKey, nsImageLoader>
- mImageLoaders[IMAGE_LOAD_TYPE_COUNT];
-
+ ImageLoaderTable mImageLoaders;
+ ImageLoaderTable mBorderImageLoaders;
nsWeakPtr mContainer;
float mTextZoom; // Text zoom, defaults to 1.0
float mFullZoom; // Page zoom, defaults to 1.0
PRInt32 mCurAppUnitsPerDevPixel;
PRInt32 mAutoQualityMinFontSizePixelsPref;
--- a/layout/base/nsStyleConsts.h
+++ b/layout/base/nsStyleConsts.h
@@ -238,33 +238,37 @@
// See nsStyleColor
#define NS_COLOR_MOZ_HYPERLINKTEXT -1
#define NS_COLOR_MOZ_VISITEDHYPERLINKTEXT -2
#define NS_COLOR_MOZ_ACTIVEHYPERLINKTEXT -3
#define NS_COLOR_CURRENTCOLOR -4
// See nsStyleBackground
+// 0x01 was background-color:transparent
+#define NS_STYLE_BG_IMAGE_NONE 0x02
+#define NS_STYLE_BG_X_POSITION_PERCENT 0x04
+#define NS_STYLE_BG_X_POSITION_LENGTH 0x08
+#define NS_STYLE_BG_Y_POSITION_PERCENT 0x10
+#define NS_STYLE_BG_Y_POSITION_LENGTH 0x20
+
+// See nsStyleBackground
#define NS_STYLE_BG_ATTACHMENT_SCROLL 0
#define NS_STYLE_BG_ATTACHMENT_FIXED 1
// See nsStyleBackground
-// Code depends on these constants having the same values as BG_ORIGIN_*
#define NS_STYLE_BG_CLIP_BORDER 0
#define NS_STYLE_BG_CLIP_PADDING 1
-// When we add NS_STYLE_BG_CLIP_CONTENT, we should add the PR_STATIC_ASSERTs
-// to the places that assert equality for BORDER and PADDING.
// See nsStyleBackground
#define NS_STYLE_BG_INLINE_POLICY_EACH_BOX 0
#define NS_STYLE_BG_INLINE_POLICY_CONTINUOUS 1
#define NS_STYLE_BG_INLINE_POLICY_BOUNDING_BOX 2
// See nsStyleBackground
-// Code depends on these constants having the same values as BG_CLIP_*
#define NS_STYLE_BG_ORIGIN_BORDER 0
#define NS_STYLE_BG_ORIGIN_PADDING 1
#define NS_STYLE_BG_ORIGIN_CONTENT 2
// See nsStyleBackground
// The parser code depends on |ing these values together.
#define NS_STYLE_BG_POSITION_CENTER (1<<0)
#define NS_STYLE_BG_POSITION_TOP (1<<1)
--- a/layout/generic/nsFrame.cpp
+++ b/layout/generic/nsFrame.cpp
@@ -513,79 +513,29 @@ nsFrame::Destroy()
NS_IMETHODIMP
nsFrame::GetOffsets(PRInt32 &aStart, PRInt32 &aEnd) const
{
aStart = 0;
aEnd = 0;
return NS_OK;
}
-static PRBool
-EqualImages(imgIRequest *aOldImage, imgIRequest *aNewImage)
-{
- if (aOldImage == aNewImage)
- return PR_TRUE;
-
- if (!aOldImage || !aNewImage)
- return PR_FALSE;
-
- nsCOMPtr<nsIURI> oldURI, newURI;
- aOldImage->GetURI(getter_AddRefs(oldURI));
- aNewImage->GetURI(getter_AddRefs(newURI));
- PRBool equal;
- return NS_SUCCEEDED(oldURI->Equals(newURI, &equal)) && equal;
-}
-
// Subclass hook for style post processing
/* virtual */ void
nsFrame::DidSetStyleContext(nsStyleContext* aOldStyleContext)
{
- if (aOldStyleContext) {
- // If the old context had a background image image and new context
- // does not have the same image, clear the image load notifier
- // (which keeps the image loading, if it still is) for the frame.
- // We want to do this conservatively because some frames paint their
- // backgrounds from some other frame's style data, and we don't want
- // to clear those notifiers unless we have to. (They'll be reset
- // when we paint, although we could miss a notification in that
- // interval.)
- const nsStyleBackground *oldBG = aOldStyleContext->GetStyleBackground();
- const nsStyleBackground *newBG = GetStyleBackground();
- NS_FOR_VISIBLE_BACKGROUND_LAYERS_BACK_TO_FRONT(i, oldBG) {
- imgIRequest *oldImage = oldBG->mLayers[i].mImage.mRequest;
- imgIRequest *newImage =
- (i < newBG->mImageCount) ? newBG->mLayers[i].mImage.mRequest : nsnull;
- if (oldImage && !EqualImages(oldImage, newImage)) {
- // stop the image loading for the frame, the image has changed
- PresContext()->SetImageLoaders(this,
- nsPresContext::BACKGROUND_IMAGE, nsnull);
- break;
- }
- }
- }
-
- imgIRequest *oldBorderImage = aOldStyleContext
- ? aOldStyleContext->GetStyleBorder()->GetBorderImage()
- : nsnull;
- // For border-images, we can't be as conservative (we need to set the
- // new loaders if there has been any change) since the CalcDifference
- // call depended on the result of GetActualBorder() and that result
- // depends on whether the image has loaded, start the image load now
- // so that we'll get notified when it completes loading and can do a
- // restyle. Otherwise, the image might finish loading from the
- // network before we start listening to its notifications, and then
- // we'll never know that it's finished loading. Likewise, we want to
- // do this for freshly-created frames to prevent a similar race if the
- // image loads between reflow (which can depend on whether the image
- // is loaded) and paint. We also don't really care about any callers
- // who try to paint borders with a different style context, because
- // they won't have the correct size for the border either.
- if (!EqualImages(oldBorderImage, GetStyleBorder()->GetBorderImage())) {
- // stop and restart the image loading/notification
- PresContext()->SetupBorderImageLoaders(this, GetStyleBorder());
+ // We have to start loading the border image before or during reflow,
+ // because the border-image's width overrides only apply once the
+ // image is loaded. Starting the load of the image means we'll get a
+ // reflow when the image loads. (Otherwise, if the image loads
+ // between reflow and paint, we never get the notification and our
+ // size ends up wrong.)
+ imgIRequest *borderImage = GetStyleBorder()->GetBorderImage();
+ if (borderImage) {
+ PresContext()->LoadBorderImage(borderImage, this);
}
}
/* virtual */ nsMargin
nsIFrame::GetUsedMargin() const
{
NS_ASSERTION(nsLayoutUtils::sDisableGetUsedXAssertions ||
!NS_SUBTREE_DIRTY(this) ||
@@ -4024,24 +3974,21 @@ nsIFrame::CheckInvalidateSizeChange(cons
if (border->GetActualBorderWidth(side) != 0) {
Invalidate(nsRect(0, 0, aOldRect.width, aOldRect.height));
return;
}
}
// Invalidate the old frame background if the frame has a background
// whose position depends on the size of the frame
- const nsStyleBackground *bg = GetStyleBackground();
- NS_FOR_VISIBLE_BACKGROUND_LAYERS_BACK_TO_FRONT(i, bg) {
- const nsStyleBackground::Layer &layer = bg->mLayers[i];
- if (layer.mImage.mRequest &&
- (layer.mPosition.mXIsPercent || layer.mPosition.mYIsPercent)) {
- Invalidate(nsRect(0, 0, aOldRect.width, aOldRect.height));
- return;
- }
+ const nsStyleBackground* background = GetStyleBackground();
+ if (background->mBackgroundFlags &
+ (NS_STYLE_BG_X_POSITION_PERCENT | NS_STYLE_BG_Y_POSITION_PERCENT)) {
+ Invalidate(nsRect(0, 0, aOldRect.width, aOldRect.height));
+ return;
}
}
// Define the MAX_FRAME_DEPTH to be the ContentSink's MAX_REFLOW_DEPTH plus
// 4 for the frames above the document's frames:
// the Viewport, GFXScroll, ScrollPort, and Canvas
#define MAX_FRAME_DEPTH (MAX_REFLOW_DEPTH+4)
--- a/layout/generic/nsLineLayout.cpp
+++ b/layout/generic/nsLineLayout.cpp
@@ -784,16 +784,17 @@ nsLineLayout::ReflowFrame(nsIFrame* aFra
if (reflowState.ComputedWidth() == NS_UNCONSTRAINEDSIZE)
reflowState.availableWidth = psd->mRightEdge - psd->mX;
// Stash copies of some of the computed state away for later
// (vertical alignment, for example)
pfd->mFrame = aFrame;
pfd->mMargin = reflowState.mComputedMargin;
pfd->mBorderPadding = reflowState.mComputedBorderPadding;
+ pfd->mFrameType = reflowState.mFrameType;
pfd->SetFlag(PFD_RELATIVEPOS,
(reflowState.mStyleDisplay->mPosition == NS_STYLE_POSITION_RELATIVE));
if (pfd->GetFlag(PFD_RELATIVEPOS)) {
pfd->mOffsets = reflowState.mComputedOffsets;
}
// NOTE: While the x coordinate remains relative to the parent span,
// the y coordinate is fixed at the top edge for the line. During
@@ -1328,16 +1329,17 @@ nsLineLayout::AddBulletFrame(nsIFrame* a
PerFrameData* pfd;
nsresult rv = NewPerFrameData(&pfd);
if (NS_SUCCEEDED(rv)) {
mRootSpan->AppendFrame(pfd);
pfd->mFrame = aFrame;
pfd->mMargin.SizeTo(0, 0, 0, 0);
pfd->mBorderPadding.SizeTo(0, 0, 0, 0);
+ pfd->mFrameType = NS_FRAME_REPLACED(NS_CSS_FRAME_TYPE_INLINE);
pfd->mFlags = 0; // all flags default to false
pfd->SetFlag(PFD_ISBULLET, PR_TRUE);
if (aMetrics.ascent == nsHTMLReflowMetrics::ASK_FOR_BASELINE)
pfd->mAscent = aFrame->GetBaseline();
else
pfd->mAscent = aMetrics.ascent;
// Note: y value will be updated during vertical alignment
@@ -1373,16 +1375,17 @@ nsLineLayout::DumpPerSpanData(PerSpanDat
#define VALIGN_BOTTOM 2
void
nsLineLayout::VerticalAlignLine()
{
// Synthesize a PerFrameData for the block frame
PerFrameData rootPFD;
rootPFD.mFrame = mBlockReflowState->frame;
+ rootPFD.mFrameType = mBlockReflowState->mFrameType;
rootPFD.mAscent = 0;
mRootSpan->mFrame = &rootPFD;
// Partially place the children of the block frame. The baseline for
// this operation is set to zero so that the y coordinates for all
// of the placed children will be relative to there.
PerSpanData* psd = mRootSpan;
VerticalAlignFrames(psd);
--- a/layout/generic/nsLineLayout.h
+++ b/layout/generic/nsLineLayout.h
@@ -438,18 +438,19 @@ protected:
struct PerFrameData {
// link to next/prev frame in same span
PerFrameData* mNext;
PerFrameData* mPrev;
// pointer to child span data if this is an inline container frame
PerSpanData* mSpan;
- // The frame
+ // The frame and its type
nsIFrame* mFrame;
+ nsCSSFrameType mFrameType;
// From metrics
nscoord mAscent;
nsRect mBounds;
nsRect mCombinedArea;
// From reflow-state
nsMargin mMargin;
deleted file mode 100644
index 7de00c8f79c983562e0c03af031a3a8c348612a4..0000000000000000000000000000000000000000
GIT binary patch
literal 0
Hc$@<O00001
deleted file mode 100644
index deefd19b2ac53bef91c82ed2f6f4ea5f53a9e34f..0000000000000000000000000000000000000000
GIT binary patch
literal 0
Hc$@<O00001
deleted file mode 100644
--- a/layout/reftests/backgrounds/fallback-color-1.xhtml
+++ /dev/null
@@ -1,25 +0,0 @@
-<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN" "http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
-<html xmlns="http://www.w3.org/1999/xhtml">
- <head>
- <title>css3-background: fallback colors</title>
- <link rel="author" title="L. David Baron" href="http://dbaron.org/" />
- <link rel="author" title="Mozilla Corporation" href="http://mozilla.com/" />
- <link rel="help" href="http://dev.w3.org/csswg/css3-background/#background-color" />
- <meta name="flags" content="" />
- <meta name="assert" content="Fallback color only applied when there is an image." />
- <style type="text/css"><![CDATA[
-
- div {
- width: 100px;
- height: 100px;
- background: lime red;
- }
-
- ]]></style>
- </head>
- <body>
-
- <div></div>
-
- </body>
-</html>
deleted file mode 100644
--- a/layout/reftests/backgrounds/fallback-color-2.xhtml
+++ /dev/null
@@ -1,25 +0,0 @@
-<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN" "http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
-<html xmlns="http://www.w3.org/1999/xhtml">
- <head>
- <title>css3-background: fallback colors</title>
- <link rel="author" title="L. David Baron" href="http://dbaron.org/" />
- <link rel="author" title="Mozilla Corporation" href="http://mozilla.com/" />
- <link rel="help" href="http://dev.w3.org/csswg/css3-background/#background-color" />
- <meta name="flags" content="" />
- <meta name="assert" content="Fallback color only applied when there is an image." />
- <style type="text/css"><![CDATA[
-
- div {
- width: 100px;
- height: 100px;
- background-color: lime red;
- }
-
- ]]></style>
- </head>
- <body>
-
- <div></div>
-
- </body>
-</html>
deleted file mode 100644
--- a/layout/reftests/backgrounds/fallback-color-3.xhtml
+++ /dev/null
@@ -1,25 +0,0 @@
-<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN" "http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
-<html xmlns="http://www.w3.org/1999/xhtml">
- <head>
- <title>css3-background: fallback colors</title>
- <link rel="author" title="L. David Baron" href="http://dbaron.org/" />
- <link rel="author" title="Mozilla Corporation" href="http://mozilla.com/" />
- <link rel="help" href="http://dev.w3.org/csswg/css3-background/#background-color" />
- <meta name="flags" content="" />
- <meta name="assert" content="Fallback color not applied when background image loads successfully." />
- <style type="text/css"><![CDATA[
-
- div {
- width: 100px;
- height: 100px;
- background: url(transparent-32x32.png) lime red;
- }
-
- ]]></style>
- </head>
- <body>
-
- <div></div>
-
- </body>
-</html>
deleted file mode 100644
--- a/layout/reftests/backgrounds/fallback-color-4.xhtml
+++ /dev/null
@@ -1,25 +0,0 @@
-<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN" "http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
-<html xmlns="http://www.w3.org/1999/xhtml">
- <head>
- <title>css3-background: fallback colors</title>
- <link rel="author" title="L. David Baron" href="http://dbaron.org/" />
- <link rel="author" title="Mozilla Corporation" href="http://mozilla.com/" />
- <link rel="help" href="http://dev.w3.org/csswg/css3-background/#background-color" />
- <meta name="flags" content="" />
- <meta name="assert" content="Fallback color applied when background image corrupted." />
- <style type="text/css"><![CDATA[
-
- div {
- width: 100px;
- height: 100px;
- background: url(malformed.png) red lime;
- }
-
- ]]></style>
- </head>
- <body>
-
- <div></div>
-
- </body>
-</html>
deleted file mode 100644
--- a/layout/reftests/backgrounds/fallback-color-5.xhtml
+++ /dev/null
@@ -1,25 +0,0 @@
-<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN" "http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
-<html xmlns="http://www.w3.org/1999/xhtml">
- <head>
- <title>css3-background: fallback colors</title>
- <link rel="author" title="L. David Baron" href="http://dbaron.org/" />
- <link rel="author" title="Mozilla Corporation" href="http://mozilla.com/" />
- <link rel="help" href="http://dev.w3.org/csswg/css3-background/#background-color" />
- <meta name="flags" content="" />
- <meta name="assert" content="Fallback color applied when background image missing." />
- <style type="text/css"><![CDATA[
-
- div {
- width: 100px;
- height: 100px;
- background: url(404.png) red lime;
- }
-
- ]]></style>
- </head>
- <body>
-
- <div></div>
-
- </body>
-</html>
deleted file mode 100644
--- a/layout/reftests/backgrounds/fallback-color-6.xhtml
+++ /dev/null
@@ -1,25 +0,0 @@
-<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN" "http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
-<html xmlns="http://www.w3.org/1999/xhtml">
- <head>
- <title>css3-background: fallback colors</title>
- <link rel="author" title="L. David Baron" href="http://dbaron.org/" />
- <link rel="author" title="Mozilla Corporation" href="http://mozilla.com/" />
- <link rel="help" href="http://dev.w3.org/csswg/css3-background/#background-color" />
- <meta name="flags" content="" />
- <meta name="assert" content="Fallback color is based on whether the *bottom-most* image is corrupted." />
- <style type="text/css"><![CDATA[
-
- div {
- width: 100px;
- height: 100px;
- background: url(transparent-32x32.png), url(malformed.png) red lime;
- }
-
- ]]></style>
- </head>
- <body>
-
- <div></div>
-
- </body>
-</html>
deleted file mode 100644
--- a/layout/reftests/backgrounds/fallback-color-7.xhtml
+++ /dev/null
@@ -1,25 +0,0 @@
-<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN" "http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
-<html xmlns="http://www.w3.org/1999/xhtml">
- <head>
- <title>css3-background: fallback colors</title>
- <link rel="author" title="L. David Baron" href="http://dbaron.org/" />
- <link rel="author" title="Mozilla Corporation" href="http://mozilla.com/" />
- <link rel="help" href="http://dev.w3.org/csswg/css3-background/#background-color" />
- <meta name="flags" content="" />
- <meta name="assert" content="Fallback color is based on whether the *bottom-most* image is corrupted." />
- <style type="text/css"><![CDATA[
-
- div {
- width: 100px;
- height: 100px;
- background: url(malformed.png), url(transparent-32x32.png) lime red;
- }
-
- ]]></style>
- </head>
- <body>
-
- <div></div>
-
- </body>
-</html>
deleted file mode 100644
--- a/layout/reftests/backgrounds/fallback-color-8.xhtml
+++ /dev/null
@@ -1,25 +0,0 @@
-<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN" "http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
-<html xmlns="http://www.w3.org/1999/xhtml">
- <head>
- <title>css3-background: fallback colors</title>
- <link rel="author" title="L. David Baron" href="http://dbaron.org/" />
- <link rel="author" title="Mozilla Corporation" href="http://mozilla.com/" />
- <link rel="help" href="http://dev.w3.org/csswg/css3-background/#background-color" />
- <meta name="flags" content="" />
- <meta name="assert" content="Fallback color is based on whether the *bottom-most* image is missing." />
- <style type="text/css"><![CDATA[
-
- div {
- width: 100px;
- height: 100px;
- background: url(transparent-32x32.png), url(404.png) red lime;
- }
-
- ]]></style>
- </head>
- <body>
-
- <div></div>
-
- </body>
-</html>
deleted file mode 100644
--- a/layout/reftests/backgrounds/fallback-color-9.xhtml
+++ /dev/null
@@ -1,25 +0,0 @@
-<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN" "http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
-<html xmlns="http://www.w3.org/1999/xhtml">
- <head>
- <title>css3-background: fallback colors</title>
- <link rel="author" title="L. David Baron" href="http://dbaron.org/" />
- <link rel="author" title="Mozilla Corporation" href="http://mozilla.com/" />
- <link rel="help" href="http://dev.w3.org/csswg/css3-background/#background-color" />
- <meta name="flags" content="" />
- <meta name="assert" content="Fallback color is based on whether the *bottom-most* image is missing." />
- <style type="text/css"><![CDATA[
-
- div {
- width: 100px;
- height: 100px;
- background: url(404.png), url(transparent-32x32.png) lime red;
- }
-
- ]]></style>
- </head>
- <body>
-
- <div></div>
-
- </body>
-</html>
deleted file mode 100644
--- a/layout/reftests/backgrounds/fallback-color-ref.xhtml
+++ /dev/null
@@ -1,24 +0,0 @@
-<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN" "http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
-<html xmlns="http://www.w3.org/1999/xhtml">
- <head>
- <title>css3-background: fallback colors</title>
- <link rel="author" title="L. David Baron" href="http://dbaron.org/" />
- <link rel="author" title="Mozilla Corporation" href="http://mozilla.com/" />
- <link rel="help" href="http://dev.w3.org/csswg/css3-background/#background-color" />
- <meta name="flags" content="" />
- <style type="text/css"><![CDATA[
-
- div {
- width: 100px;
- height: 100px;
- background: url(lime-32x32.png);
- }
-
- ]]></style>
- </head>
- <body>
-
- <div></div>
-
- </body>
-</html>
deleted file mode 100644
index 7902bc31e09b58fbe224fb8047e84332eb132cce..0000000000000000000000000000000000000000
GIT binary patch
literal 0
Hc$@<O00001
deleted file mode 100644
--- a/layout/reftests/backgrounds/layers-layer-count-1-ref.xhtml
+++ /dev/null
@@ -1,35 +0,0 @@
-<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN" "http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
-<html xmlns="http://www.w3.org/1999/xhtml">
- <head>
- <title>css3-background: number of background layers determined by background-image</title>
- <link rel="author" title="L. David Baron" href="http://dbaron.org/" />
- <link rel="author" title="Mozilla Corporation" href="http://mozilla.com/" />
- <link rel="help" href="http://dev.w3.org/csswg/css3-background/#layering" />
- <meta name="flags" content="" />
- <style type="text/css"><![CDATA[
-
- div {
- position: relative; height: 100px; width: 100px;
- }
-
- ]]></style>
- </head>
- <body>
-
- <div>
- <img style="position: absolute; left: 10px; top: 10px" src="aqua-32x32.png" />
- </div>
- <div>
- <img style="position: absolute; left: 15px; top: 15px" src="fuchsia-32x32.png" />
- <img style="position: absolute; left: 20px; top: 20px" src="blue-32x32.png" />
- <img style="position: absolute; left: 5px; top: 5px" src="aqua-32x32.png" />
- <img style="position: absolute; left: 10px; top: 10px" src="yellow-32x32.png" />
- </div>
- <div>
- <img style="position: absolute; left: 20px; top: 20px" src="fuchsia-32x32.png" />
- <img style="position: absolute; left: 5px; top: 5px" src="yellow-32x32.png" />
- <img style="position: absolute; left: 10px; top: 10px" src="blue-32x32.png" />
- </div>
-
- </body>
-</html>
deleted file mode 100644
--- a/layout/reftests/backgrounds/layers-layer-count-2-ref.xhtml
+++ /dev/null
@@ -1,35 +0,0 @@
-<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN" "http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
-<html xmlns="http://www.w3.org/1999/xhtml">
- <head>
- <title>css3-background: number of background layers determined by background-image</title>
- <link rel="author" title="L. David Baron" href="http://dbaron.org/" />
- <link rel="author" title="Mozilla Corporation" href="http://mozilla.com/" />
- <link rel="help" href="http://dev.w3.org/csswg/css3-background/#layering" />
- <meta name="flags" content="" />
- <style type="text/css"><![CDATA[
-
- div {
- position: relative; height: 100px; width: 100px;
- }
-
- ]]></style>
- </head>
- <body>
-
- <div>
- <img style="position: absolute; left: 10px; top: 10px" src="yellow-32x32.png" />
- </div>
- <div>
- <img style="position: absolute; left: 15px; top: 15px" src="fuchsia-32x32.png" />
- <img style="position: absolute; left: 20px; top: 20px" src="blue-32x32.png" />
- <img style="position: absolute; left: 0px; top: 0px" src="aqua-32x32.png" />
- <img style="position: absolute; left: 5px; top: 5px" src="yellow-32x32.png" />
- </div>
- <div>
- <img style="position: absolute; left: 20px; top: 20px" src="blue-32x32.png" />
- <img style="position: absolute; left: 5px; top: 5px" src="aqua-32x32.png" />
- <img style="position: absolute; left: 10px; top: 10px" src="yellow-32x32.png" />
- </div>
-
- </body>
-</html>
deleted file mode 100644
--- a/layout/reftests/backgrounds/layers-layer-count-cascade-1.xhtml
+++ /dev/null
@@ -1,36 +0,0 @@
-<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN" "http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
-<html xmlns="http://www.w3.org/1999/xhtml">
- <head>
- <title>css3-background: number of background layers determined by background-image</title>
- <link rel="author" title="L. David Baron" href="http://dbaron.org/" />
- <link rel="author" title="Mozilla Corporation" href="http://mozilla.com/" />
- <link rel="help" href="http://dev.w3.org/csswg/css3-background/#layering" />
- <meta name="flags" content="" />
- <style type="text/css"><![CDATA[
-
- div {
- position: relative; height: 100px; width: 100px;
- background-repeat: no-repeat;
- background-position: 10px 10px, 5px 5px, 20px 20px, 15px 15px;
- background-image: url(aqua-32x32.png);
- }
-
- div.withclass {
- background-image: url(yellow-32x32.png), url(aqua-32x32.png), url(blue-32x32.png), url(fuchsia-32x32.png), url(red-32x32.png);
- }
-
- div#withid {
- background-image: url(blue-32x32.png), url(yellow-32x32.png), url(fuchsia-32x32.png);
- }
-
-
- ]]></style>
- </head>
- <body>
-
- <div></div>
- <div class="withclass"></div>
- <div class="withclass" id="withid"></div>
-
- </body>
-</html>
deleted file mode 100644
--- a/layout/reftests/backgrounds/layers-layer-count-cascade-2.xhtml
+++ /dev/null
@@ -1,36 +0,0 @@
-<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN" "http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
-<html xmlns="http://www.w3.org/1999/xhtml">
- <head>
- <title>css3-background: number of background layers determined by background-image</title>
- <link rel="author" title="L. David Baron" href="http://dbaron.org/" />
- <link rel="author" title="Mozilla Corporation" href="http://mozilla.com/" />
- <link rel="help" href="http://dev.w3.org/csswg/css3-background/#layering" />
- <meta name="flags" content="" />
- <style type="text/css"><![CDATA[
-
- div {
- position: relative; height: 100px; width: 100px;
- background-repeat: no-repeat;
- background-position: 10px 10px;
- background-image: url(yellow-32x32.png), url(aqua-32x32.png), url(blue-32x32.png), url(fuchsia-32x32.png), url(red-32x32.png);
- }
-
- div.withclass {
- background-position: 5px 5px, 0px 0px, 20px 20px, 15px 15px;
- }
-
- div#withid {
- background-position: 10px 10px, 5px 5px, 20px 20px;
- }
-
-
- ]]></style>
- </head>
- <body>
-
- <div></div>
- <div class="withclass"></div>
- <div class="withclass" id="withid"></div>
-
- </body>
-</html>
deleted file mode 100644
--- a/layout/reftests/backgrounds/layers-layer-count-inheritance-1.xhtml
+++ /dev/null
@@ -1,39 +0,0 @@
-<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN" "http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
-<html xmlns="http://www.w3.org/1999/xhtml">
- <head>
- <title>css3-background: number of background layers determined by background-image</title>
- <link rel="author" title="L. David Baron" href="http://dbaron.org/" />
- <link rel="author" title="Mozilla Corporation" href="http://mozilla.com/" />
- <link rel="help" href="http://dev.w3.org/csswg/css3-background/#layering" />
- <meta name="flags" content="" />
- <style type="text/css"><![CDATA[
-
- body > div {
- position: relative; height: 300px; width: 100px;
- background-repeat: no-repeat;
- background-position: 10px 10px, 5px 5px, 20px 20px, 15px 15px;
- background-image: url(aqua-32x32.png);
- }
-
- body > div > div {
- position: absolute; height: 200px; width: 100px; top: 100px; left: 0;
- background-repeat: no-repeat;
- background-position: inherit;
- background-image: url(yellow-32x32.png), url(aqua-32x32.png), url(blue-32x32.png), url(fuchsia-32x32.png), url(red-32x32.png);
- }
-
- body > div > div > div {
- position: absolute; height: 100px; width: 100px; top: 100px; left: 0;
- background: inherit;
- background-image: url(blue-32x32.png), url(yellow-32x32.png), url(fuchsia-32x32.png);
- }
-
-
- ]]></style>
- </head>
- <body>
-
- <div><div><div></div></div></div>
-
- </body>
-</html>
deleted file mode 100644
--- a/layout/reftests/backgrounds/layers-layer-count-inheritance-2.xhtml
+++ /dev/null
@@ -1,39 +0,0 @@
-<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN" "http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
-<html xmlns="http://www.w3.org/1999/xhtml">
- <head>
- <title>css3-background: number of background layers determined by background-image</title>
- <link rel="author" title="L. David Baron" href="http://dbaron.org/" />
- <link rel="author" title="Mozilla Corporation" href="http://mozilla.com/" />
- <link rel="help" href="http://dev.w3.org/csswg/css3-background/#layering" />
- <meta name="flags" content="" />
- <style type="text/css"><![CDATA[
-
- body > div {
- position: relative; height: 300px; width: 100px;
- background-repeat: no-repeat;
- background-position: 10px 10px;
- background-image: url(yellow-32x32.png), url(aqua-32x32.png), url(blue-32x32.png), url(fuchsia-32x32.png), url(red-32x32.png);
- }
-
- body > div > div {
- position: absolute; height: 200px; width: 100px; top: 100px; left: 0;
- background: inherit;
- background-position: 5px 5px, 0px 0px, 20px 20px, 15px 15px;
- }
-
- body > div > div > div {
- position: absolute; height: 100px; width: 100px; top: 100px; left: 0;
- background-image: inherit;
- background-repeat: inherit;
- background-position: 10px 10px, 5px 5px, 20px 20px;
- }
-
-
- ]]></style>
- </head>
- <body>
-
- <div><div><div></div></div></div>
-
- </body>
-</html>
deleted file mode 100644
--- a/layout/reftests/backgrounds/layers-stacking-order-ref.xhtml
+++ /dev/null
@@ -1,28 +0,0 @@
-<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN" "http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
-<html xmlns="http://www.w3.org/1999/xhtml">
- <head>
- <title>css3-background: stacking order of layers</title>
- <link rel="author" title="L. David Baron" href="http://dbaron.org/" />
- <link rel="author" title="Mozilla Corporation" href="http://mozilla.com/" />
- <link rel="help" href="http://dev.w3.org/csswg/css3-background/#layering" />
- <meta name="flags" content="" />
- <style type="text/css"><![CDATA[
-
- div#test {
- position: relative; height: 100px; width: 100px;
- }
-
-
- ]]></style>
- </head>
- <body>
-
- <div id="test">
- <img src="aqua-32x32.png" style="position: absolute; left: 20px; top: 20px" />
- <img src="fuchsia-32x32.png" style="position: absolute; left: 10px; top: 10px" />
- <img src="yellow-32x32.png" style="position: absolute; left: 15px; top: 15px" />
- <img src="blue-32x32.png" style="position: absolute; left: 5px; top: 5px" />
- </div>
-
- </body>
-</html>
deleted file mode 100644
--- a/layout/reftests/backgrounds/layers-stacking-order.xhtml
+++ /dev/null
@@ -1,27 +0,0 @@
-<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN" "http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd">
-<html xmlns="http://www.w3.org/1999/xhtml">
- <head>
- <title>css3-background: stacking order of layers</title>
- <link rel="author" title="L. David Baron" href="http://dbaron.org/" />
- <link rel="author" title="Mozilla Corporation" href="http://mozilla.com/" />
- <link rel="help" href="http://dev.w3.org/csswg/css3-background/#layering" />
- <meta name="flags" content="" />
- <style type="text/css"><![CDATA[
-
- div#test {
- position: relative; height: 100px; width: 100px;
- background: url(blue-32x32.png) 5px 5px no-repeat,
- url(yellow-32x32.png) 15px 15px no-repeat,
- url(fuchsia-32x32.png) 10px 10px no-repeat,
- url(aqua-32x32.png) 20px 20px no-repeat;
- }
-
-
- ]]></style>
- </head>
- <body>
-
- <div id="test"></div>
-
- </body>
-</html>
deleted file mode 100644
index c85b56ca8e2fd27b73d5e0ea3cacad5ed093643a..0000000000000000000000000000000000000000
GIT binary patch
literal 0
Hc$@<O00001
deleted file mode 100644
--- a/layout/reftests/backgrounds/malformed.png
+++ /dev/null
@@ -1,1 +0,0 @@
-This is not a PNG file.
deleted file mode 100644
index 191e13ea11d03f0446f6f3bc185d7ef2ab2946be..0000000000000000000000000000000000000000
GIT binary patch
literal 0
Hc$@<O00001
deleted file mode 100644
--- a/layout/reftests/backgrounds/reftest.list
+++ /dev/null
@@ -1,15 +0,0 @@
-== fallback-color-1.xhtml fallback-color-ref.xhtml
-== fallback-color-2.xhtml fallback-color-ref.xhtml
-== fallback-color-3.xhtml fallback-color-ref.xhtml
-== fallback-color-4.xhtml fallback-color-ref.xhtml
-== fallback-color-5.xhtml fallback-color-ref.xhtml
-== fallback-color-6.xhtml fallback-color-ref.xhtml
-== fallback-color-7.xhtml fallback-color-ref.xhtml
-== fallback-color-8.xhtml fallback-color-ref.xhtml
-== fallback-color-9.xhtml fallback-color-ref.xhtml
-!= fallback-color-ref.xhtml about:blank
-== layers-stacking-order.xhtml layers-stacking-order-ref.xhtml
-== layers-layer-count-cascade-1.xhtml layers-layer-count-1-ref.xhtml
-== layers-layer-count-inheritance-1.xhtml layers-layer-count-1-ref.xhtml
-== layers-layer-count-cascade-2.xhtml layers-layer-count-2-ref.xhtml
-== layers-layer-count-inheritance-2.xhtml layers-layer-count-2-ref.xhtml
deleted file mode 100644
index 62b1906cc970f5d2fe3d04af22c0098da2e8f55e..0000000000000000000000000000000000000000
GIT binary patch
literal 0
Hc$@<O00001
deleted file mode 100644
index a45f8111b446ceaea47b2ef50c46742333c177b1..0000000000000000000000000000000000000000
GIT binary patch
literal 0
Hc$@<O00001
--- a/layout/reftests/reftest.list
+++ b/layout/reftests/reftest.list
@@ -6,19 +6,16 @@
# for something to not be in order.
# verify the tests work
include reftest-sanity/reftest.list
# images (if libpr0n is busted, could result in weird failures in other tests)
include ../../modules/libpr0n/test/reftest/reftest.list
-# backgrounds/
-include backgrounds/reftest.list
-
# bidi/
include bidi/reftest.list
# border-image
include border-image/reftest.list
# border-radius/
include border-radius/reftest.list
--- a/layout/style/nsCSSDataBlock.cpp
+++ b/layout/style/nsCSSDataBlock.cpp
@@ -191,17 +191,18 @@ nsCSSCompressedDataBlock::MapRuleInfoInt
void *prop =
nsCSSExpandedDataBlock::RuleDataPropertyAt(aRuleData, iProp);
switch (nsCSSProps::kTypeTable[iProp]) {
case eCSSType_Value: {
nsCSSValue* target = static_cast<nsCSSValue*>(prop);
if (target->GetUnit() == eCSSUnit_Null) {
const nsCSSValue *val = ValueAtCursor(cursor);
NS_ASSERTION(val->GetUnit() != eCSSUnit_Null, "oops");
- if (iProp == eCSSProperty_list_style_image) {
+ if (iProp == eCSSProperty_background_image ||
+ iProp == eCSSProperty_list_style_image) {
if (val->GetUnit() == eCSSUnit_URL) {
val->StartImageLoad(
aRuleData->mPresContext->Document());
}
} else if (iProp == eCSSProperty_border_image) {
if (val->GetUnit() == eCSSUnit_Array) {
nsCSSValue::Array *array = val->GetArrayValue();
if (array->Item(0).GetUnit() == eCSSUnit_URL) {
@@ -211,29 +212,55 @@ nsCSSCompressedDataBlock::MapRuleInfoInt
}
}
*target = *val;
if (iProp == eCSSProperty_font_family) {
// XXX Are there other things like this?
aRuleData->mFontData->mFamilyFromHTML = PR_FALSE;
}
else if (iProp == eCSSProperty_color ||
+ iProp == eCSSProperty_background_color ||
+ iProp == eCSSProperty_background_image ||
iProp == eCSSProperty_border_top_color ||
iProp == eCSSProperty_border_right_color_value ||
iProp == eCSSProperty_border_right_color_ltr_source ||
iProp == eCSSProperty_border_right_color_rtl_source ||
iProp == eCSSProperty_border_bottom_color ||
iProp == eCSSProperty_border_left_color_value ||
iProp == eCSSProperty_border_left_color_ltr_source ||
iProp == eCSSProperty_border_left_color_rtl_source ||
iProp == eCSSProperty__moz_column_rule_color ||
iProp == eCSSProperty_outline_color) {
if (ShouldIgnoreColors(aRuleData)) {
- // Ignore 'color', 'border-*-color', etc.
- *target = nsCSSValue();
+ if (iProp == eCSSProperty_background_color) {
+ // Force non-'transparent' background
+ // colors to the user's default.
+ // We have the value in the form it was
+ // specified at this point, so we have to
+ // look for both the keyword 'transparent'
+ // and its equivalent in rgba notation.
+ nsCSSUnit u = target->GetUnit();
+ nsDependentString buf;
+
+ if ((u == eCSSUnit_Color &&
+ NS_GET_A(target->GetColorValue())
+ > 0) ||
+ (u == eCSSUnit_String &&
+ !nsGkAtoms::transparent->
+ Equals(target->GetStringValue(buf))) ||
+ (u == eCSSUnit_EnumColor)) {
+ target->SetColorValue(aRuleData->
+ mPresContext->
+ DefaultBackgroundColor());
+ }
+ } else {
+ // Ignore 'color', 'border-*-color', and
+ // 'background-image'
+ *target = nsCSSValue();
+ }
}
}
}
cursor += CDBValueStorage_advance;
} break;
case eCSSType_Rect: {
const nsCSSRect* val = RectAtCursor(cursor);
@@ -250,60 +277,25 @@ nsCSSCompressedDataBlock::MapRuleInfoInt
cursor += CDBRectStorage_advance;
} break;
case eCSSType_ValuePair: {
const nsCSSValuePair* val = ValuePairAtCursor(cursor);
NS_ASSERTION(val->mXValue.GetUnit() != eCSSUnit_Null ||
val->mYValue.GetUnit() != eCSSUnit_Null, "oops");
nsCSSValuePair* target = static_cast<nsCSSValuePair*>(prop);
- NS_ASSERTION((target->mXValue.GetUnit() == eCSSUnit_Null)
- == (target->mYValue.GetUnit() == eCSSUnit_Null),
- "half a property?");
- if (target->mXValue.GetUnit() == eCSSUnit_Null) {
+ if (target->mXValue.GetUnit() == eCSSUnit_Null)
target->mXValue = val->mXValue;
+ if (target->mYValue.GetUnit() == eCSSUnit_Null)
target->mYValue = val->mYValue;
- if (iProp == eCSSProperty_background_color &&
- ShouldIgnoreColors(aRuleData)) {
- // Force non-'transparent' background colors
- // to the user's default. We have the value
- // in the form it was specified at this
- // point, so we have to look for both the
- // keyword 'transparent' and its equivalent
- // in rgba notation.
- nsCSSValue &colorVal = target->mXValue;
- nsCSSUnit u = colorVal.GetUnit();
- nsDependentString buf;
-
- if ((u == eCSSUnit_Color &&
- NS_GET_A(colorVal.GetColorValue())
- > 0) ||
- (u == eCSSUnit_String &&
- !nsGkAtoms::transparent->
- Equals(colorVal.GetStringValue(buf))) ||
- (u == eCSSUnit_EnumColor)) {
- colorVal.SetColorValue(aRuleData->
- mPresContext->
- DefaultBackgroundColor());
- }
- // We could consider using the fallback
- // background color for both values, but it
- // might not make sense if the author didn't
- // specify an image. But since we're
- // dropping author images, we'll just use
- // the non-fallback for both.
- target->mYValue = target->mXValue;
- }
- }
cursor += CDBValuePairStorage_advance;
} break;
case eCSSType_ValueList:
- if (iProp == eCSSProperty_background_image ||
- iProp == eCSSProperty_content) {
+ if (iProp == eCSSProperty_content) {
for (nsCSSValueList* l = ValueListAtCursor(cursor);
l; l = l->mNext)
if (l->mValue.GetUnit() == eCSSUnit_URL)
l->mValue.StartImageLoad(
aRuleData->mPresContext->Document());
} else if (iProp == eCSSProperty_cursor) {
for (nsCSSValueList* l = ValueListAtCursor(cursor);
l; l = l->mNext)
@@ -320,18 +312,17 @@ nsCSSCompressedDataBlock::MapRuleInfoInt
// fall through
case eCSSType_ValuePairList: {
void** target = static_cast<void**>(prop);
if (!*target) {
void* val = PointerAtCursor(cursor);
NS_ASSERTION(val, "oops");
*target = val;
- if (iProp == eCSSProperty_background_image ||
- iProp == eCSSProperty_border_top_colors ||
+ if (iProp == eCSSProperty_border_top_colors ||
iProp == eCSSProperty_border_right_colors ||
iProp == eCSSProperty_border_bottom_colors ||
iProp == eCSSProperty_border_left_colors) {
if (ShouldIgnoreColors(aRuleData)) {
*target = nsnull;
}
}
}
--- a/layout/style/nsCSSDeclaration.cpp
+++ b/layout/style/nsCSSDeclaration.cpp
@@ -204,27 +204,22 @@ PRBool nsCSSDeclaration::AppendValueToSt
} break;
case eCSSType_ValuePairList: {
const nsCSSValuePairList* item =
*static_cast<nsCSSValuePairList*const*>(storage);
do {
NS_ASSERTION(item->mXValue.GetUnit() != eCSSUnit_Null,
"unexpected null unit");
AppendCSSValueToString(aProperty, item->mXValue, aResult);
- if (item->mXValue.GetUnit() != eCSSUnit_Inherit &&
- item->mXValue.GetUnit() != eCSSUnit_Initial &&
- item->mYValue.GetUnit() != eCSSUnit_Null) {
+ if (item->mYValue.GetUnit() != eCSSUnit_Null) {
aResult.Append(PRUnichar(' '));
AppendCSSValueToString(aProperty, item->mYValue, aResult);
}
item = item->mNext;
if (item) {
- if (nsCSSProps::PropHasFlags(aProperty,
- CSS_PROPERTY_VALUE_LIST_USES_COMMAS))
- aResult.Append(PRUnichar(','));
aResult.Append(PRUnichar(' '));
}
} while (item);
} break;
}
}
return storage != nsnull;
}
@@ -761,107 +756,60 @@ nsCSSDeclaration::GetValue(nsCSSProperty
const nsCSSProperty* subprops =
nsCSSProps::SubpropertyEntryFor(aProperty);
NS_ASSERTION(subprops[3] == eCSSProperty_UNKNOWN,
"not box property with physical vs. logical cascading");
AppendValueToString(subprops[0], aValue);
break;
}
case eCSSProperty_background: {
- // We know from above that all subproperties were specified.
- // However, we still can't represent that in the shorthand unless
- // they're all lists of the same length. So if they're different
- // lengths, we need to bail out.
- // We also need to bail out if an item has background-clip and
- // background-origin that are different and not the default
- // values. (We omit them if they're both default.)
- const nsCSSValueList *image =
- * data->ValueListStorageFor(eCSSProperty_background_image);
- const nsCSSValueList *repeat =
- * data->ValueListStorageFor(eCSSProperty_background_repeat);
- const nsCSSValueList *attachment =
- * data->ValueListStorageFor(eCSSProperty_background_attachment);
- const nsCSSValuePairList *position =
- * data->ValuePairListStorageFor(eCSSProperty_background_position);
- const nsCSSValueList *clip =
- * data->ValueListStorageFor(eCSSProperty__moz_background_clip);
- const nsCSSValueList *origin =
- * data->ValueListStorageFor(eCSSProperty__moz_background_origin);
- for (;;) {
- AppendCSSValueToString(eCSSProperty_background_image,
- image->mValue, aValue);
- aValue.Append(PRUnichar(' '));
- AppendCSSValueToString(eCSSProperty_background_repeat,
- repeat->mValue, aValue);
- aValue.Append(PRUnichar(' '));
- AppendCSSValueToString(eCSSProperty_background_attachment,
- attachment->mValue, aValue);
- aValue.Append(PRUnichar(' '));
- AppendCSSValueToString(eCSSProperty_background_position,
- position->mXValue, aValue);
- aValue.Append(PRUnichar(' '));
- AppendCSSValueToString(eCSSProperty_background_position,
- position->mYValue, aValue);
- NS_ASSERTION(clip->mValue.GetUnit() == eCSSUnit_Enumerated &&
- origin->mValue.GetUnit() == eCSSUnit_Enumerated,
- "should not be inherit/initial within list and "
- "should have returned early for real inherit/initial");
- if (clip->mValue.GetIntValue() != NS_STYLE_BG_CLIP_BORDER ||
- origin->mValue.GetIntValue() != NS_STYLE_BG_ORIGIN_PADDING) {
-#if 0
- // This is commented out for now until we change
- // -moz-background-clip to background-clip, -moz-background-origin
- // to background-origin, change their value names to *-box, and add
- // support for content-box on background-clip.
- PR_STATIC_ASSERT(NS_STYLE_BG_CLIP_BORDER ==
- NS_STYLE_BG_ORIGIN_BORDER);
- PR_STATIC_ASSERT(NS_STYLE_BG_CLIP_PADDING ==
- NS_STYLE_BG_ORIGIN_PADDING);
- // PR_STATIC_ASSERT(NS_STYLE_BG_CLIP_CONTENT == /* does not exist */
- // NS_STYLE_BG_ORIGIN_CONTENT);
- if (clip->mValue != origin->mValue) {
- aValue.Truncate();
- return NS_OK;
- }
-
- aValue.Append(PRUnichar(' '));
- AppendCSSValueToString(eCSSProperty__moz_background_clip,
- clip->mValue, aValue);
-#else
- aValue.Truncate();
- return NS_OK;
-#endif
- }
-
- image = image->mNext;
- repeat = repeat->mNext;
- attachment = attachment->mNext;
- position = position->mNext;
- clip = clip->mNext;
- origin = origin->mNext;
-
- if (!image) {
- if (repeat || attachment || position || clip || origin) {
- // Uneven length lists, so can't be serialized as shorthand.
- aValue.Truncate();
- return NS_OK;
- }
- break;
- }
- if (!repeat || !attachment || !position || !clip || !origin) {
- // Uneven length lists, so can't be serialized as shorthand.
- aValue.Truncate();
- return NS_OK;
- }
- aValue.Append(PRUnichar(','));
+ // The -moz-background-clip, -moz-background-origin, and
+ // -moz-background-inline-policy properties are reset by this
+ // shorthand property to their initial values, but can't be
+ // represented in its syntax.
+ const nsCSSValue *clipValue = static_cast<const nsCSSValue*>(
+ data->StorageFor(eCSSProperty__moz_background_clip));
+ const nsCSSValue *originValue = static_cast<const nsCSSValue*>(
+ data->StorageFor(eCSSProperty__moz_background_origin));
+ const nsCSSValue *inlinePolicyValue = static_cast<const nsCSSValue*>(
+ data->StorageFor(eCSSProperty__moz_background_inline_policy));
+ if (*clipValue !=
+ nsCSSValue(NS_STYLE_BG_CLIP_BORDER, eCSSUnit_Enumerated) ||
+ *originValue !=
+ nsCSSValue(NS_STYLE_BG_ORIGIN_PADDING, eCSSUnit_Enumerated) ||
+ *inlinePolicyValue !=
+ nsCSSValue(NS_STYLE_BG_INLINE_POLICY_CONTINUOUS,
+ eCSSUnit_Enumerated)) {
+ return NS_OK;
+ }
+
+ PRBool appendedSomething = PR_FALSE;
+ if (AppendValueToString(eCSSProperty_background_color, aValue)) {
+ appendedSomething = PR_TRUE;
aValue.Append(PRUnichar(' '));
}
-
- aValue.Append(PRUnichar(' '));
- AppendValueToString(eCSSProperty_background_color, aValue);
+ if (AppendValueToString(eCSSProperty_background_image, aValue)) {
+ aValue.Append(PRUnichar(' '));
+ appendedSomething = PR_TRUE;
+ }
+ if (AppendValueToString(eCSSProperty_background_repeat, aValue)) {
+ aValue.Append(PRUnichar(' '));
+ appendedSomething = PR_TRUE;
+ }
+ if (AppendValueToString(eCSSProperty_background_attachment, aValue)) {
+ aValue.Append(PRUnichar(' '));
+ appendedSomething = PR_TRUE;
+ }
+ if (!AppendValueToString(eCSSProperty_background_position, aValue) &&
+ appendedSomething) {
+ NS_ASSERTION(!aValue.IsEmpty() && aValue.Last() == PRUnichar(' '),
+ "We appended a space before!");
+ // We appended an extra space. Let's get rid of it
+ aValue.Truncate(aValue.Length() - 1);
+ }
break;
}
case eCSSProperty_cue: {
if (AppendValueToString(eCSSProperty_cue_before, aValue)) {
aValue.Append(PRUnichar(' '));
if (!AppendValueToString(eCSSProperty_cue_after, aValue))
aValue.Truncate();
}
@@ -1093,40 +1041,38 @@ nsCSSDeclaration::ToString(nsAString& aS
shorthandsUsed.AppendElement(shorthand);
doneProperty = PR_TRUE;
break;
}
NS_ASSERTION(shorthand != eCSSProperty_font ||
*(shorthands + 1) == eCSSProperty_UNKNOWN,
"font should always be the only containing shorthand");
- if (shorthand == eCSSProperty_font) {
- if (haveSystemFont && !didSystemFont) {
+ if (shorthand == eCSSProperty_font && haveSystemFont) {
+ if (!didSystemFont) {
// Output the shorthand font declaration that we will
// partially override later. But don't add it to
// |shorthandsUsed|, since we will have to override it.
AppendCSSValueToString(eCSSProperty__x_system_font, *systemFont,
value);
AppendPropertyAndValueToString(eCSSProperty_font, value, aString);
value.Truncate();
didSystemFont = PR_TRUE;
}
// That we output the system font is enough for this property if:
- // (1) it's the hidden system font subproperty (which either
- // means we output it or we don't have it), or
+ // (1) it's the hidden system font subproperty, or
// (2) its value is the hidden system font value and it matches
- // the hidden system font subproperty in importance, and
- // we output the system font subproperty.
+ // the hidden system font subproperty in importance.
NS_ASSERTION(nsCSSProps::kTypeTable[property] == eCSSType_Value,
"not a value typed subproperty");
const nsCSSValue *val =
systemFontData->ValueStorageFor(property);
if (property == eCSSProperty__x_system_font ||
- (haveSystemFont && val && val->GetUnit() == eCSSUnit_System_Font)) {
+ (val && val->GetUnit() == eCSSUnit_System_Font)) {
doneProperty = PR_TRUE;
}
}
}
if (doneProperty)
continue;
NS_ASSERTION(value.IsEmpty(), "value should be empty now");
--- a/layout/style/nsCSSParser.cpp
+++ b/layout/style/nsCSSParser.cpp
@@ -79,17 +79,16 @@
#include "nsStyleUtil.h"
#include "nsIPrincipal.h"
#include "prprf.h"
#include "math.h"
#include "nsContentUtils.h"
#include "nsDOMError.h"
#include "nsAutoPtr.h"
#include "nsTArray.h"
-#include "prlog.h"
// Flags for ParseVariant method
#define VARIANT_KEYWORD 0x000001 // K
#define VARIANT_LENGTH 0x000002 // L
#define VARIANT_PERCENT 0x000004 // P
#define VARIANT_COLOR 0x000008 // C eCSSUnit_Color, eCSSUnit_String (e.g. "red")
#define VARIANT_URL 0x000010 // U
#define VARIANT_NUMBER 0x000020 // N
@@ -386,40 +385,19 @@ protected:
PRBool ParseTreePseudoElement(nsCSSSelector& aSelector);
#endif
void InitBoxPropsAsPhysical(const nsCSSProperty *aSourceProperties);
// Property specific parsing routines
PRBool ParseAzimuth(nsCSSValue& aValue);
PRBool ParseBackground();
-
- struct BackgroundItem;
- friend struct BackgroundItem;
- struct BackgroundItem {
- nsCSSValue mImage;
- nsCSSValue mRepeat;
- nsCSSValue mAttachment;
- nsCSSValuePair mPosition;
- nsCSSValue mClip;
- nsCSSValue mOrigin;
- // The background-color is set as a side-effect, and if so, mLastItem
- // is set to true.
- PRBool mLastItem;
- };
- struct BackgroundItemSimpleValueInfo {
- nsCSSValue BackgroundItem::*member;
- nsCSSProperty propID;
- };
-
- PRBool ParseBackgroundItem(BackgroundItem& aItem, PRBool aFirstItem);
-
- PRBool ParseBackgroundList(nsCSSProperty aPropID); // a single value prop-id
- PRBool ParseBackgroundColor(PRBool aInShorthand);
PRBool ParseBackgroundPosition();
+ PRBool ParseBackgroundPositionValues();
+ PRBool ParseBoxPosition(nsCSSValuePair& aOut);
PRBool ParseBoxPositionValues(nsCSSValuePair& aOut);
PRBool ParseBorderColor();
PRBool ParseBorderColors(nsCSSValueList** aResult,
nsCSSProperty aProperty);
PRBool ParseBorderImage();
PRBool ParseBorderSpacing();
PRBool ParseBorderSide(const nsCSSProperty aPropIDs[],
PRBool aSetAllSides);
@@ -4957,26 +4935,18 @@ static const nsCSSProperty kOutlineRadiu
PRBool
CSSParserImpl::ParseProperty(nsCSSProperty aPropID)
{
NS_ASSERTION(aPropID < eCSSProperty_COUNT, "index out of range");
switch (aPropID) { // handle shorthand or multiple properties
case eCSSProperty_background:
return ParseBackground();
- case eCSSProperty_background_color:
- return ParseBackgroundColor(PR_FALSE);
case eCSSProperty_background_position:
return ParseBackgroundPosition();
- case eCSSProperty_background_attachment:
- case eCSSProperty__moz_background_clip:
- case eCSSProperty_background_image:
- case eCSSProperty__moz_background_origin:
- case eCSSProperty_background_repeat:
- return ParseBackgroundList(aPropID);
case eCSSProperty_border:
return ParseBorderSide(kBorderTopIDs, PR_TRUE);
case eCSSProperty_border_color:
return ParseBorderColor();
case eCSSProperty_border_spacing:
return ParseBorderSpacing();
case eCSSProperty_border_style:
return ParseBorderStyle();
@@ -5218,17 +5188,16 @@ CSSParserImpl::ParseProperty(nsCSSProper
PRBool
CSSParserImpl::ParseSingleValueProperty(nsCSSValue& aValue,
nsCSSProperty aPropID)
{
switch (aPropID) {
case eCSSProperty_UNKNOWN:
case eCSSProperty_background:
- case eCSSProperty_background_color:
case eCSSProperty_background_position:
case eCSSProperty_border:
case eCSSProperty_border_color:
case eCSSProperty_border_bottom_colors:
case eCSSProperty_border_image:
case eCSSProperty_border_left_colors:
case eCSSProperty_border_right_colors:
case eCSSProperty_border_end_color:
@@ -5331,35 +5300,32 @@ CSSParserImpl::ParseSingleValueProperty(
return PR_FALSE;
case eCSSProperty_appearance:
return ParseVariant(aValue, VARIANT_HK,
nsCSSProps::kAppearanceKTable);
case eCSSProperty_azimuth:
return ParseAzimuth(aValue);
case eCSSProperty_background_attachment:
- // Used only internally.
return ParseVariant(aValue, VARIANT_HK,
nsCSSProps::kBackgroundAttachmentKTable);
case eCSSProperty__moz_background_clip:
- // Used only internally.
return ParseVariant(aValue, VARIANT_HK,
nsCSSProps::kBackgroundClipKTable);
+ case eCSSProperty_background_color:
+ return ParseVariant(aValue, VARIANT_HC, nsnull);
case eCSSProperty_background_image:
- // Used only internally.
return ParseVariant(aValue, VARIANT_HUO, nsnull);
case eCSSProperty__moz_background_inline_policy:
return ParseVariant(aValue, VARIANT_HK,
nsCSSProps::kBackgroundInlinePolicyKTable);
case eCSSProperty__moz_background_origin:
- // Used only internally.
return ParseVariant(aValue, VARIANT_HK,
nsCSSProps::kBackgroundOriginKTable);
case eCSSProperty_background_repeat:
- // Used only internally.
return ParseVariant(aValue, VARIANT_HK,
nsCSSProps::kBackgroundRepeatKTable);
case eCSSProperty_binding:
return ParseVariant(aValue, VARIANT_HUO, nsnull);
case eCSSProperty_border_collapse:
return ParseVariant(aValue, VARIANT_HK,
nsCSSProps::kBorderCollapseKTable);
case eCSSProperty_border_bottom_color:
@@ -5887,380 +5853,196 @@ BoxPositionMaskToCSSValue(PRInt32 aMask,
return nsCSSValue(val, eCSSUnit_Enumerated);
}
PRBool
CSSParserImpl::ParseBackground()
{
nsAutoParseCompoundProperty compound(this);
- // These two are set through side-effects of ParseBackgroundItem.
- mTempData.mColor.mBackColor.mXValue.SetColorValue(NS_RGBA(0, 0, 0, 0));
- mTempData.mColor.mBackColor.mYValue.SetColorValue(NS_RGBA(0, 0, 0, 0));
-
- BackgroundItem bgitem;
- nsCSSValuePairList *positionHead = nsnull, **positionTail = &positionHead;
- static const BackgroundItemSimpleValueInfo simpleValues[] = {
- { &BackgroundItem::mImage, eCSSProperty_background_image },
- { &BackgroundItem::mRepeat, eCSSProperty_background_repeat },
- { &BackgroundItem::mAttachment, eCSSProperty_background_attachment },
- { &BackgroundItem::mClip, eCSSProperty__moz_background_clip },
- { &BackgroundItem::mOrigin, eCSSProperty__moz_background_origin }
- };
- nsCSSValueList *simpleHeads[NS_ARRAY_LENGTH(simpleValues)];
- nsCSSValueList **simpleTails[NS_ARRAY_LENGTH(simpleValues)];
- for (PRUint32 i = 0; i < NS_ARRAY_LENGTH(simpleValues); ++i) {
- simpleHeads[i] = nsnull;
- simpleTails[i] = &simpleHeads[i];
- }
- for (;;) {
- if (!ParseBackgroundItem(bgitem, !positionHead)) {
- break;
- }
- nsCSSValuePairList *positionItem = new nsCSSValuePairList;
- if (!positionItem) {
- mScanner.SetLowLevelError(NS_ERROR_OUT_OF_MEMORY);
- break;
- }
- positionItem->mXValue = bgitem.mPosition.mXValue;
- positionItem->mYValue = bgitem.mPosition.mYValue;
- *positionTail = positionItem;
- positionTail = &positionItem->mNext;
-
- PRBool fail = PR_FALSE;
- for (PRUint32 i = 0; i < NS_ARRAY_LENGTH(simpleValues); ++i) {
- nsCSSValueList *item = new nsCSSValueList;
- if (!item) {
- mScanner.SetLowLevelError(NS_ERROR_OUT_OF_MEMORY);
- fail = PR_TRUE;
- break;
- }
- item->mValue = bgitem.*(simpleValues[i].member);
- *simpleTails[i] = item;
- simpleTails[i] = &item->mNext;
- }
- if (fail) {
- break;
- }
-
- if (!bgitem.mLastItem && ExpectSymbol(',', PR_TRUE)) {
- continue;
- }
- if (!ExpectEndProperty()) {
- break;
- }
-
- mTempData.mColor.mBackPosition = positionHead;
- for (PRUint32 i = 0; i < NS_ARRAY_LENGTH(simpleValues); ++i) {
- nsCSSValueList **source = static_cast<nsCSSValueList**>(
- mTempData.PropertyAt(simpleValues[i].propID));
- *source = simpleHeads[i];
- }
-
- mTempData.SetPropertyBit(eCSSProperty_background_color);
- mTempData.SetPropertyBit(eCSSProperty_background_image);
- mTempData.SetPropertyBit(eCSSProperty_background_repeat);
- mTempData.SetPropertyBit(eCSSProperty_background_attachment);
- mTempData.SetPropertyBit(eCSSProperty_background_position);
- mTempData.SetPropertyBit(eCSSProperty__moz_background_clip);
- mTempData.SetPropertyBit(eCSSProperty__moz_background_origin);
- return PR_TRUE;
- }
- delete positionHead;
- for (PRUint32 i = 0; i < NS_ARRAY_LENGTH(simpleValues); ++i) {
- delete simpleHeads[i];
- }
- return PR_FALSE;
-}
-
-// Parse one item of the background shorthand property.
-PRBool
-CSSParserImpl::ParseBackgroundItem(CSSParserImpl::BackgroundItem& aItem,
- PRBool aFirstItem)
-{
// Fill in the values that the shorthand will set if we don't find
// other values.
- aItem.mImage.SetNoneValue();
- aItem.mRepeat.SetIntValue(NS_STYLE_BG_REPEAT_XY, eCSSUnit_Enumerated);
- aItem.mAttachment.SetIntValue(NS_STYLE_BG_ATTACHMENT_SCROLL,
- eCSSUnit_Enumerated);
- aItem.mPosition.mXValue.SetPercentValue(0.0f);
- aItem.mPosition.mYValue.SetPercentValue(0.0f);
- aItem.mClip.SetIntValue(NS_STYLE_BG_CLIP_BORDER, eCSSUnit_Enumerated);
- aItem.mOrigin.SetIntValue(NS_STYLE_BG_ORIGIN_PADDING, eCSSUnit_Enumerated);
- aItem.mLastItem = PR_FALSE;
+ mTempData.mColor.mBackColor.SetColorValue(NS_RGBA(0, 0, 0, 0));
+ mTempData.SetPropertyBit(eCSSProperty_background_color);
+ mTempData.mColor.mBackImage.SetNoneValue();
+ mTempData.SetPropertyBit(eCSSProperty_background_image);
+ mTempData.mColor.mBackRepeat.SetIntValue(NS_STYLE_BG_REPEAT_XY,
+ eCSSUnit_Enumerated);
+ mTempData.SetPropertyBit(eCSSProperty_background_repeat);
+ mTempData.mColor.mBackAttachment.SetIntValue(NS_STYLE_BG_ATTACHMENT_SCROLL,
+ eCSSUnit_Enumerated);
+ mTempData.SetPropertyBit(eCSSProperty_background_attachment);
+ mTempData.mColor.mBackPosition.mXValue.SetPercentValue(0.0f);
+ mTempData.mColor.mBackPosition.mYValue.SetPercentValue(0.0f);
+ mTempData.SetPropertyBit(eCSSProperty_background_position);
+ // including the ones that we can't set from the shorthand.
+ mTempData.mColor.mBackClip.SetIntValue(NS_STYLE_BG_CLIP_BORDER,
+ eCSSUnit_Enumerated);
+ mTempData.SetPropertyBit(eCSSProperty__moz_background_clip);
+ mTempData.mColor.mBackOrigin.SetIntValue(NS_STYLE_BG_ORIGIN_PADDING,
+ eCSSUnit_Enumerated);
+ mTempData.SetPropertyBit(eCSSProperty__moz_background_origin);
+ mTempData.mColor.mBackInlinePolicy.SetIntValue(
+ NS_STYLE_BG_INLINE_POLICY_CONTINUOUS, eCSSUnit_Enumerated);
+ mTempData.SetPropertyBit(eCSSProperty__moz_background_inline_policy);
+
+ // XXX If ParseSingleValueProperty were table-driven (bug 376079) and
+ // automatically filled in the right field of mTempData, we could move
+ // ParseBackgroundPosition to it (as a special case) and switch back
+ // to using ParseChoice here.
PRBool haveColor = PR_FALSE,
haveImage = PR_FALSE,
haveRepeat = PR_FALSE,
haveAttach = PR_FALSE,
- havePosition = PR_FALSE,
- haveSomething = PR_FALSE;
+ havePosition = PR_FALSE;
while (GetToken(PR_TRUE)) {
nsCSSTokenType tt = mToken.mType;
UngetToken(); // ...but we'll still cheat and use mToken
if (tt == eCSSToken_Symbol) {
// ExpectEndProperty only looks for symbols, and nothing else will
// show up as one.
break;
}
if (tt == eCSSToken_Ident) {
nsCSSKeyword keyword = nsCSSKeywords::LookupKeyword(mToken.mIdent);
PRInt32 dummy;
if (keyword == eCSSKeyword_inherit ||
keyword == eCSSKeyword__moz_initial) {
- if (haveSomething || !aFirstItem)
+ if (haveColor || haveImage || haveRepeat || haveAttach || havePosition)
return PR_FALSE;
haveColor = haveImage = haveRepeat = haveAttach = havePosition =
PR_TRUE;
GetToken(PR_TRUE); // undo the UngetToken above
nsCSSValue val;
if (keyword == eCSSKeyword_inherit) {
val.SetInheritValue();
} else {
val.SetInitialValue();
}
- mTempData.mColor.mBackColor.SetBothValuesTo(val);
- aItem.mImage = val;
- aItem.mRepeat = val;
- aItem.mAttachment = val;
- aItem.mPosition.SetBothValuesTo(val);
- aItem.mClip = val;
- aItem.mOrigin = val;
- aItem.mLastItem = PR_TRUE;
- haveSomething = PR_TRUE;
+ mTempData.mColor.mBackColor = val;
+ mTempData.mColor.mBackImage = val;
+ mTempData.mColor.mBackRepeat = val;
+ mTempData.mColor.mBackAttachment = val;
+ mTempData.mColor.mBackPosition.mXValue = val;
+ mTempData.mColor.mBackPosition.mYValue = val;
+ // Reset (for 'inherit') the 3 properties that can't be
+ // specified, although it's not entirely clear in the spec:
+ // http://lists.w3.org/Archives/Public/www-style/2007Mar/0110
+ mTempData.mColor.mBackClip = val;
+ mTempData.mColor.mBackOrigin = val;
+ mTempData.mColor.mBackInlinePolicy = val;
break;
} else if (keyword == eCSSKeyword_none) {
if (haveImage)
return PR_FALSE;
haveImage = PR_TRUE;
- if (!ParseSingleValueProperty(aItem.mImage,
+ if (!ParseSingleValueProperty(mTempData.mColor.mBackImage,
eCSSProperty_background_image)) {
NS_NOTREACHED("should be able to parse");
return PR_FALSE;
}
} else if (nsCSSProps::FindKeyword(keyword,
nsCSSProps::kBackgroundAttachmentKTable, dummy)) {
if (haveAttach)
return PR_FALSE;
haveAttach = PR_TRUE;
- if (!ParseSingleValueProperty(aItem.mAttachment,
+ if (!ParseSingleValueProperty(mTempData.mColor.mBackAttachment,
eCSSProperty_background_attachment)) {
NS_NOTREACHED("should be able to parse");
return PR_FALSE;
}
} else if (nsCSSProps::FindKeyword(keyword,
nsCSSProps::kBackgroundRepeatKTable, dummy)) {
if (haveRepeat)
return PR_FALSE;
haveRepeat = PR_TRUE;
- if (!ParseSingleValueProperty(aItem.mRepeat,
+ if (!ParseSingleValueProperty(mTempData.mColor.mBackRepeat,
eCSSProperty_background_repeat)) {
NS_NOTREACHED("should be able to parse");
return PR_FALSE;
}
} else if (nsCSSProps::FindKeyword(keyword,
nsCSSProps::kBackgroundPositionKTable, dummy)) {
if (havePosition)
return PR_FALSE;
havePosition = PR_TRUE;
- if (!ParseBoxPositionValues(aItem.mPosition)) {
+ if (!ParseBackgroundPositionValues()) {
return PR_FALSE;
}
-#if 0
- // This is commented out for now until we change
- // -moz-background-clip to background-clip, -moz-background-origin
- // to background-origin, change their value names to *-box, and add
- // support for content-box on background-clip.
- } else if (nsCSSProps::FindKeyword(keyword,
- nsCSSProps::kBackgroundClipKTable, dummy)) {
- // For now, we use the background-clip table, because we don't
- // support 'content' on background-clip. But that's dangerous
- // if we eventually support no-clip.
- NS_ASSERTION(
- nsCSSProps::kBackgroundClipKTable[0] == eCSSKeyword_border &&
- nsCSSProps::kBackgroundClipKTable[2] == eCSSKeyword_padding &&
- nsCSSProps::kBackgroundClipKTable[4] == eCSSKeyword_UNKNOWN,
- "need to rewrite this code");
- if (haveOrigin)
- return PR_FALSE;
- haveOrigin = PR_TRUE;
- if (!ParseSingleValueProperty(aItem.mOrigin,
- eCSSProperty__moz_background_origin)) {
- NS_NOTREACHED("should be able to parse");
- return PR_FALSE;
- }
- PR_STATIC_ASSERT(NS_STYLE_BG_CLIP_BORDER ==
- NS_STYLE_BG_ORIGIN_BORDER);
- PR_STATIC_ASSERT(NS_STYLE_BG_CLIP_PADDING ==
- NS_STYLE_BG_ORIGIN_PADDING);
- // PR_STATIC_ASSERT(NS_STYLE_BG_CLIP_CONTENT == /* does not exist */
- // NS_STYLE_BG_ORIGIN_CONTENT);
- // When we support 'no-clip', this needs to be conditional on haveClip:
- aItem.mClip = aItem.mOrigin;
- // We'd support 'no-clip' as an additional |else| here.
-#endif
} else {
if (haveColor)
return PR_FALSE;
haveColor = PR_TRUE;
- if (!ParseBackgroundColor(PR_TRUE)) {
+ if (!ParseSingleValueProperty(mTempData.mColor.mBackColor,
+ eCSSProperty_background_color)) {
return PR_FALSE;
}
- aItem.mLastItem = PR_TRUE;
}
} else if (eCSSToken_Function == tt &&
mToken.mIdent.LowerCaseEqualsLiteral("url")) {
if (haveImage)
return PR_FALSE;
haveImage = PR_TRUE;
- if (!ParseSingleValueProperty(aItem.mImage,
+ if (!ParseSingleValueProperty(mTempData.mColor.mBackImage,
eCSSProperty_background_image)) {
return PR_FALSE;
}
} else if (mToken.IsDimension() || tt == eCSSToken_Percentage) {
if (havePosition)
return PR_FALSE;
havePosition = PR_TRUE;
- if (!ParseBoxPositionValues(aItem.mPosition)) {
+ if (!ParseBackgroundPositionValues()) {
return PR_FALSE;
}
} else {
if (haveColor)
return PR_FALSE;
haveColor = PR_TRUE;
- // Note: ParseBackgroundColor parses 'inherit' and 'initial', but
- // we've already checked for them, so it's ok.
- if (!ParseBackgroundColor(PR_TRUE)) {
+ if (!ParseSingleValueProperty(mTempData.mColor.mBackColor,
+ eCSSProperty_background_color)) {
return PR_FALSE;
}
- aItem.mLastItem = PR_TRUE;
- }
- haveSomething = PR_TRUE;
- }
-
- return haveSomething;
-}
-
-// This function is very similar to ParseBackgroundPosition.
-PRBool
-CSSParserImpl::ParseBackgroundList(nsCSSProperty aPropID)
-{
- // aPropID is a single value prop-id
- nsCSSValue value;
- nsCSSValueList *head = nsnull, **tail = &head;
- for (;;) {
- if (!ParseSingleValueProperty(value, aPropID)) {
- break;
- }
- PRBool inheritOrInitial = value.GetUnit() == eCSSUnit_Inherit ||
- value.GetUnit() == eCSSUnit_Initial;
- if (inheritOrInitial && head) {
- // inherit and initial are only allowed on their own
- break;
- }
- nsCSSValueList *item = new nsCSSValueList;
- if (!item) {
- mScanner.SetLowLevelError(NS_ERROR_OUT_OF_MEMORY);
- break;
- }
- item->mValue = value;
- *tail = item;
- tail = &item->mNext;
- if (!inheritOrInitial && ExpectSymbol(',', PR_TRUE)) {
- continue;
- }
- if (!ExpectEndProperty()) {
- break;
- }
- nsCSSValueList **source =
- static_cast<nsCSSValueList**>(mTempData.PropertyAt(aPropID));
- *source = head;
- mTempData.SetPropertyBit(aPropID);
- return PR_TRUE;
- }
- delete head;
- return PR_FALSE;
+ }
+ }
+
+ return ExpectEndProperty() &&
+ (haveColor || haveImage || haveRepeat || haveAttach || havePosition);
}
PRBool
-CSSParserImpl::ParseBackgroundColor(PRBool aInShorthand)
-{
- nsCSSValuePair &backColor = mTempData.mColor.mBackColor;
- mTempData.SetPropertyBit(eCSSProperty_background_color);
- if (!ParseVariant(backColor.mXValue,
- aInShorthand ? VARIANT_COLOR : VARIANT_HC, nsnull)) {
+CSSParserImpl::ParseBackgroundPosition()
+{
+ if (!ParseBoxPosition(mTempData.mColor.mBackPosition))
return PR_FALSE;
- }
- backColor.mYValue = backColor.mXValue;
- switch (backColor.mXValue.GetUnit()) {
- case eCSSUnit_Inherit:
- case eCSSUnit_Initial:
- NS_ASSERTION(!aInShorthand,
- "should not get inherit or initial in shorthand");
- return ExpectEndProperty(); // we're done
- default:
- break;
- }
-
- // Ignore success, since the value is optional.
- ParseVariant(backColor.mYValue, VARIANT_COLOR, nsnull);
-
- return aInShorthand || ExpectEndProperty();
-}
-
-// This function is very similar to ParseBackgroundList.
+ mTempData.SetPropertyBit(eCSSProperty_background_position);
+ return PR_TRUE;
+}
+
PRBool
-CSSParserImpl::ParseBackgroundPosition()
-{
- // aPropID is a single value prop-id
- nsCSSValuePair valuePair;
- nsCSSValuePairList *head = nsnull, **tail = &head;
- for (;;) {
- if (!ParseBoxPositionValues(valuePair)) {
- break;
- }
- PRBool inheritOrInitial = valuePair.mXValue.GetUnit() == eCSSUnit_Inherit ||
- valuePair.mXValue.GetUnit() == eCSSUnit_Initial;
- if (inheritOrInitial && head) {
- // inherit and initial are only allowed on their own
- break;
- }
- nsCSSValuePairList *item = new nsCSSValuePairList;
- if (!item) {
- mScanner.SetLowLevelError(NS_ERROR_OUT_OF_MEMORY);
- break;
- }
- item->mXValue = valuePair.mXValue;
- item->mYValue = valuePair.mYValue;
- *tail = item;
- tail = &item->mNext;
- if (!inheritOrInitial && ExpectSymbol(',', PR_TRUE)) {
- continue;
- }
- if (!ExpectEndProperty()) {
- break;
- }
- mTempData.mColor.mBackPosition = head;
- mTempData.SetPropertyBit(eCSSProperty_background_position);
- return PR_TRUE;
- }
- delete head;
- return PR_FALSE;
+CSSParserImpl::ParseBackgroundPositionValues()
+{
+ return ParseBoxPositionValues(mTempData.mColor.mBackPosition);
}
/**
* Parses two values that correspond to positions in a box. These can be
* values corresponding to percentages of the box, raw offsets, or keywords
* like "top," "left center," etc.
*
* @param aOut The nsCSSValuePair where to place the result.
* @return Whether or not the operation succeeded.
*/
+PRBool CSSParserImpl::ParseBoxPosition(nsCSSValuePair &aOut)
+{
+ // Need to read the box positions and the end of the property.
+ return ParseBoxPositionValues(aOut) && ExpectEndProperty();
+}
+
PRBool CSSParserImpl::ParseBoxPositionValues(nsCSSValuePair &aOut)
{
// First try a percentage or a length value
nsCSSValue &xValue = aOut.mXValue,
&yValue = aOut.mYValue;
if (ParseVariant(xValue, VARIANT_HLP, nsnull)) {
if (eCSSUnit_Inherit == xValue.GetUnit() ||
eCSSUnit_Initial == xValue.GetUnit()) { // both are inherited or both are set to initial
@@ -7427,18 +7209,17 @@ PRBool CSSParserImpl::ParseMozTransform(
mTempData.mDisplay.mTransform = transformList;
return PR_TRUE;
}
PRBool CSSParserImpl::ParseMozTransformOrigin()
{
/* Read in a box position, fail if we can't. */
- if (!ParseBoxPositionValues(mTempData.mDisplay.mTransformOrigin) ||
- !ExpectEndProperty())
+ if (!ParseBoxPosition(mTempData.mDisplay.mTransformOrigin))
return PR_FALSE;
/* Set the property bit and return. */
mTempData.SetPropertyBit(eCSSProperty__moz_transform_origin);
return PR_TRUE;
}
PRBool
--- a/layout/style/nsCSSPropList.h
+++ b/layout/style/nsCSSPropList.h
@@ -292,24 +292,24 @@ CSS_PROP_OUTLINE(-moz-outline-radius-top
CSS_PROP_OUTLINE(-moz-outline-radius-topright, _moz_outline_radius_topRight, MozOutlineRadiusTopright, 0, Margin, mOutlineRadius.mTopRight, eCSSType_ValuePair, nsnull)
CSS_PROP_OUTLINE(-moz-outline-radius-bottomright, _moz_outline_radius_bottomRight, MozOutlineRadiusBottomright, 0, Margin, mOutlineRadius.mBottomRight, eCSSType_ValuePair, nsnull)
CSS_PROP_OUTLINE(-moz-outline-radius-bottomleft, _moz_outline_radius_bottomLeft, MozOutlineRadiusBottomleft, 0, Margin, mOutlineRadius.mBottomLeft, eCSSType_ValuePair, nsnull)
#ifndef CSS_PROP_LIST_EXCLUDE_INTERNAL
CSS_PROP_FONT(-x-system-font, _x_system_font, X, CSS_PROPERTY_APPLIES_TO_FIRST_LETTER_AND_FIRST_LINE, Font, mSystemFont, eCSSType_Value, kFontKTable)
#endif
CSS_PROP_BACKENDONLY(azimuth, azimuth, Azimuth, 0, Aural, mAzimuth, eCSSType_Value, kAzimuthKTable)
CSS_PROP_SHORTHAND(background, background, Background, 0)
-CSS_PROP_BACKGROUND(background-attachment, background_attachment, BackgroundAttachment, CSS_PROPERTY_APPLIES_TO_FIRST_LETTER_AND_FIRST_LINE | CSS_PROPERTY_VALUE_LIST_USES_COMMAS, Color, mBackAttachment, eCSSType_ValueList, kBackgroundAttachmentKTable)
-CSS_PROP_BACKGROUND(-moz-background-clip, _moz_background_clip, MozBackgroundClip, CSS_PROPERTY_APPLIES_TO_FIRST_LETTER_AND_FIRST_LINE | CSS_PROPERTY_VALUE_LIST_USES_COMMAS, Color, mBackClip, eCSSType_ValueList, kBackgroundClipKTable)
-CSS_PROP_BACKGROUND(background-color, background_color, BackgroundColor, CSS_PROPERTY_APPLIES_TO_FIRST_LETTER_AND_FIRST_LINE, Color, mBackColor, eCSSType_ValuePair, nsnull)
-CSS_PROP_BACKGROUND(background-image, background_image, BackgroundImage, CSS_PROPERTY_APPLIES_TO_FIRST_LETTER_AND_FIRST_LINE | CSS_PROPERTY_VALUE_LIST_USES_COMMAS, Color, mBackImage, eCSSType_ValueList, nsnull)
+CSS_PROP_BACKGROUND(background-attachment, background_attachment, BackgroundAttachment, CSS_PROPERTY_APPLIES_TO_FIRST_LETTER_AND_FIRST_LINE, Color, mBackAttachment, eCSSType_Value, kBackgroundAttachmentKTable)
+CSS_PROP_BACKGROUND(-moz-background-clip, _moz_background_clip, MozBackgroundClip, CSS_PROPERTY_APPLIES_TO_FIRST_LETTER_AND_FIRST_LINE, Color, mBackClip, eCSSType_Value, kBackgroundClipKTable)
+CSS_PROP_BACKGROUND(background-color, background_color, BackgroundColor, CSS_PROPERTY_APPLIES_TO_FIRST_LETTER_AND_FIRST_LINE, Color, mBackColor, eCSSType_Value, nsnull)
+CSS_PROP_BACKGROUND(background-image, background_image, BackgroundImage, CSS_PROPERTY_APPLIES_TO_FIRST_LETTER_AND_FIRST_LINE, Color, mBackImage, eCSSType_Value, nsnull)
CSS_PROP_BACKGROUND(-moz-background-inline-policy, _moz_background_inline_policy, MozBackgroundInlinePolicy, CSS_PROPERTY_APPLIES_TO_FIRST_LETTER_AND_FIRST_LINE, Color, mBackInlinePolicy, eCSSType_Value, kBackgroundInlinePolicyKTable)
-CSS_PROP_BACKGROUND(-moz-background-origin, _moz_background_origin, MozBackgroundOrigin, CSS_PROPERTY_APPLIES_TO_FIRST_LETTER_AND_FIRST_LINE | CSS_PROPERTY_VALUE_LIST_USES_COMMAS, Color, mBackOrigin, eCSSType_ValueList, kBackgroundOriginKTable)
-CSS_PROP_BACKGROUND(background-position, background_position, BackgroundPosition, CSS_PROPERTY_APPLIES_TO_FIRST_LETTER_AND_FIRST_LINE | CSS_PROPERTY_VALUE_LIST_USES_COMMAS, Color, mBackPosition, eCSSType_ValuePairList, kBackgroundPositionKTable)
-CSS_PROP_BACKGROUND(background-repeat, background_repeat, BackgroundRepeat, CSS_PROPERTY_APPLIES_TO_FIRST_LETTER_AND_FIRST_LINE | CSS_PROPERTY_VALUE_LIST_USES_COMMAS, Color, mBackRepeat, eCSSType_ValueList, kBackgroundRepeatKTable)
+CSS_PROP_BACKGROUND(-moz-background-origin, _moz_background_origin, MozBackgroundOrigin, CSS_PROPERTY_APPLIES_TO_FIRST_LETTER_AND_FIRST_LINE, Color, mBackOrigin, eCSSType_Value, kBackgroundOriginKTable)
+CSS_PROP_BACKGROUND(background-position, background_position, BackgroundPosition, CSS_PROPERTY_APPLIES_TO_FIRST_LETTER_AND_FIRST_LINE, Color, mBackPosition, eCSSType_ValuePair, kBackgroundPositionKTable)
+CSS_PROP_BACKGROUND(background-repeat, background_repeat, BackgroundRepeat, CSS_PROPERTY_APPLIES_TO_FIRST_LETTER_AND_FIRST_LINE, Color, mBackRepeat, eCSSType_Value, kBackgroundRepeatKTable)
CSS_PROP_DISPLAY(-moz-binding, binding, MozBinding, 0, Display, mBinding, eCSSType_Value, nsnull) // XXX bug 3935
CSS_PROP_SHORTHAND(border, border, Border, 0)
CSS_PROP_SHORTHAND(border-bottom, border_bottom, BorderBottom, 0)
CSS_PROP_BORDER(border-bottom-color, border_bottom_color, BorderBottomColor, CSS_PROPERTY_APPLIES_TO_FIRST_LETTER, Margin, mBorderColor.mBottom, eCSSType_Value, kBorderColorKTable)
CSS_PROP_BORDER(-moz-border-bottom-colors, border_bottom_colors, MozBorderBottomColors, CSS_PROPERTY_APPLIES_TO_FIRST_LETTER, Margin, mBorderColors.mBottom, eCSSType_ValueList, nsnull)
CSS_PROP_BORDER(border-bottom-style, border_bottom_style, BorderBottomStyle, CSS_PROPERTY_APPLIES_TO_FIRST_LETTER, Margin, mBorderStyle.mBottom, eCSSType_Value, kBorderStyleKTable) // on/off will need reflow
CSS_PROP_BORDER(border-bottom-width, border_bottom_width, BorderBottomWidth, CSS_PROPERTY_APPLIES_TO_FIRST_LETTER, Margin, mBorderWidth.mBottom, eCSSType_Value, kBorderWidthKTable)
CSS_PROP_TABLEBORDER(border-collapse, border_collapse, BorderCollapse, 0, Table, mBorderCollapse, eCSSType_Value, kBorderCollapseKTable)
--- a/layout/style/nsCSSProps.cpp
+++ b/layout/style/nsCSSProps.cpp
@@ -1484,18 +1484,19 @@ static const nsCSSProperty gMozOutlineRa
};
static const nsCSSProperty gBackgroundSubpropTable[] = {
eCSSProperty_background_color,
eCSSProperty_background_image,
eCSSProperty_background_repeat,
eCSSProperty_background_attachment,
eCSSProperty_background_position,
- eCSSProperty__moz_background_clip,
- eCSSProperty__moz_background_origin,
+ eCSSProperty__moz_background_clip, // XXX Added LDB.
+ eCSSProperty__moz_background_origin, // XXX Added LDB.
+ eCSSProperty__moz_background_inline_policy, // XXX Added LDB.
eCSSProperty_UNKNOWN
};
static const nsCSSProperty gBorderSubpropTable[] = {
eCSSProperty_border_top_width,
eCSSProperty_border_right_width_value,
eCSSProperty_border_right_width_ltr_source,
eCSSProperty_border_right_width_rtl_source,
--- a/layout/style/nsCSSStruct.cpp
+++ b/layout/style/nsCSSStruct.cpp
@@ -101,36 +101,23 @@ nsCSSValueList::Equal(nsCSSValueList* aL
return PR_FALSE;
}
return !p1 && !p2; // true if same length, false otherwise
}
// --- nsCSSColor -----------------
nsCSSColor::nsCSSColor(void)
- : mBackImage(nsnull)
- , mBackRepeat(nsnull)
- , mBackAttachment(nsnull)
- , mBackPosition(nsnull)
- , mBackClip(nsnull)
- , mBackOrigin(nsnull)
{
MOZ_COUNT_CTOR(nsCSSColor);
}
nsCSSColor::~nsCSSColor(void)
{
MOZ_COUNT_DTOR(nsCSSColor);
-
- delete mBackImage;
- delete mBackRepeat;
- delete mBackAttachment;
- delete mBackPosition;
- delete mBackClip;
- delete mBackOrigin;
}
// --- nsCSSText -----------------
nsCSSText::nsCSSText(void)
: mTextShadow(nsnull)
{
MOZ_COUNT_CTOR(nsCSSText);
--- a/layout/style/nsCSSStruct.h
+++ b/layout/style/nsCSSStruct.h
@@ -302,35 +302,30 @@ private:
nsRuleDataFont(const nsRuleDataFont& aOther); // NOT IMPLEMENTED
};
struct nsCSSColor : public nsCSSStruct {
nsCSSColor(void);
~nsCSSColor(void);
nsCSSValue mColor;
- nsCSSValuePair mBackColor;
- nsCSSValueList* mBackImage;
- nsCSSValueList* mBackRepeat;
- nsCSSValueList* mBackAttachment;
- nsCSSValuePairList* mBackPosition;
- nsCSSValueList* mBackClip;
- nsCSSValueList* mBackOrigin;
+ nsCSSValue mBackColor;
+ nsCSSValue mBackImage;
+ nsCSSValue mBackRepeat;
+ nsCSSValue mBackAttachment;
+ nsCSSValuePair mBackPosition;
+ nsCSSValue mBackClip;
+ nsCSSValue mBackOrigin;
nsCSSValue mBackInlinePolicy;
private:
nsCSSColor(const nsCSSColor& aOther); // NOT IMPLEMENTED
};
struct nsRuleDataColor : public nsCSSColor {
nsRuleDataColor() {}
-
- // A little bit of a hack here: now that background-image is
- // represented by a value list, attribute mapping code needs a place
- // to store one item in a value list in order to map a simple value.
- nsCSSValueList mTempBackImage;
private:
nsRuleDataColor(const nsRuleDataColor& aOther); // NOT IMPLEMENTED
};
struct nsCSSText : public nsCSSStruct {
nsCSSText(void);
~nsCSSText(void);
--- a/layout/style/nsCSSStyleRule.cpp
+++ b/layout/style/nsCSSStyleRule.cpp
@@ -70,17 +70,16 @@
#include "nsXMLNameSpaceMap.h"
#include "nsILookAndFeel.h"
#include "nsRuleNode.h"
#include "nsUnicharUtils.h"
#include "nsCSSPseudoElements.h"
#include "nsIPrincipal.h"
#include "nsComponentManagerUtils.h"
#include "nsCSSPseudoClasses.h"
-#include "nsTArray.h"
#include "nsContentUtils.h"
#include "nsContentErrors.h"
#include "mozAutoDocUpdate.h"
#define NS_IF_CLONE(member_) \
PR_BEGIN_MACRO \
if (member_) { \
@@ -464,78 +463,53 @@ static PRBool IsPseudoElement(nsIAtom* a
const char* str;
aAtom->GetUTF8String(&str);
return str && (*str == ':');
}
return PR_FALSE;
}
+void nsCSSSelector::AppendNegationToString(nsAString& aString)
+{
+ aString.AppendLiteral(":not(");
+}
+
//
// Builds the textual representation of a selector. Called by DOM 2 CSS
// StyleRule:selectorText
//
void
nsCSSSelector::ToString(nsAString& aString, nsICSSStyleSheet* aSheet,
PRBool aAppend) const
{
if (!aAppend)
aString.Truncate();
-
- // selectors are linked from right-to-left, so the next selector in
- // the linked list actually precedes this one in the resulting string
- nsAutoTArray<const nsCSSSelector*, 8> stack;
- for (const nsCSSSelector *s = this; s; s = s->mNext) {
- stack.AppendElement(s);
- }
- while (!stack.IsEmpty()) {
- PRUint32 index = stack.Length() - 1;
- const nsCSSSelector *s = stack.ElementAt(index);
- stack.RemoveElementAt(index);
-
- s->AppendToStringWithoutCombinators(aString, aSheet);
-
- // Append the combinator, if needed.
- if (!stack.IsEmpty()) {
- const nsCSSSelector *next = stack.ElementAt(index - 1);
- if (!IsPseudoElement(next->mTag)) {
- aString.Append(PRUnichar(' '));
- PRUnichar oper = s->mOperator;
- if (oper != PRUnichar(0)) {
- aString.Append(oper);
- aString.Append(PRUnichar(' '));
- }
- }
- }
- }
+ ToStringInternal(aString, aSheet, IsPseudoElement(mTag), PR_FALSE);
}
-void
-nsCSSSelector::AppendToStringWithoutCombinators
- (nsAString& aString, nsICSSStyleSheet* aSheet) const
-{
- AppendToStringWithoutCombinatorsOrNegations(aString, aSheet, PR_FALSE);
-
- for (const nsCSSSelector* negation = mNegations; negation;
- negation = negation->mNegations) {
- aString.AppendLiteral(":not(");
- negation->AppendToStringWithoutCombinatorsOrNegations(aString, aSheet,
- PR_TRUE);
- aString.Append(PRUnichar(')'));
- }
-}
-
-void
-nsCSSSelector::AppendToStringWithoutCombinatorsOrNegations
- (nsAString& aString, nsICSSStyleSheet* aSheet,
- PRBool aIsNegated) const
+void nsCSSSelector::ToStringInternal(nsAString& aString,
+ nsICSSStyleSheet* aSheet,
+ PRBool aIsPseudoElem,
+ PRBool aIsNegated) const
{
nsAutoString temp;
PRBool isPseudoElement = IsPseudoElement(mTag);
+
+ // selectors are linked from right-to-left, so the next selector in the linked list
+ // actually precedes this one in the resulting string
+ if (mNext) {
+ mNext->ToStringInternal(aString, aSheet, IsPseudoElement(mTag), 0);
+ if (!aIsNegated && !isPseudoElement) {
+ // don't add a leading whitespace if we have a pseudo-element
+ // or a negated simple selector
+ aString.Append(PRUnichar(' '));
+ }
+ }
// For non-pseudo-element selectors or for lone pseudo-elements, deal with
// namespace prefixes.
PRBool wroteNamespace = PR_FALSE;
if (!isPseudoElement || !mNext) {
// append the namespace prefix if needed
nsXMLNameSpaceMap *sheetNS = aSheet ? aSheet->GetNameSpaceMap() : nsnull;
@@ -552,21 +526,16 @@ nsCSSSelector::AppendToStringWithoutComb
wroteNamespace = PR_TRUE;
}
} else if (sheetNS->FindNameSpaceID(nsnull) == mNameSpace) {
// We have the default namespace (possibly including the wildcard
// namespace). Do nothing.
NS_ASSERTION(mNameSpace == kNameSpaceID_Unknown ||
CanBeNamespaced(aIsNegated),
"How did we end up with this namespace?");
- } else if (mNameSpace == kNameSpaceID_None) {
- NS_ASSERTION(CanBeNamespaced(aIsNegated),
- "How did we end up with this namespace?");
- aString.Append(PRUnichar('|'));
- wroteNamespace = PR_TRUE;
} else if (mNameSpace != kNameSpaceID_Unknown) {
NS_ASSERTION(CanBeNamespaced(aIsNegated),
"How did we end up with this namespace?");
nsIAtom *prefixAtom = sheetNS->FindPrefix(mNameSpace);
NS_ASSERTION(prefixAtom, "how'd we get a non-default namespace "
"without a prefix?");
nsAutoString prefix;
prefixAtom->ToString(prefix);
@@ -718,16 +687,32 @@ nsCSSSelector::AppendToStringWithoutComb
}
aString.Append(temp);
}
aString.Append(PRUnichar(')'));
}
list = list->mNext;
}
}
+
+ if (!aIsNegated) {
+ for (nsCSSSelector* negation = mNegations; negation;
+ negation = negation->mNegations) {
+ aString.AppendLiteral(":not(");
+ negation->ToStringInternal(aString, aSheet, PR_FALSE, PR_TRUE);
+ aString.Append(PRUnichar(')'));
+ }
+ }
+
+ // Append the operator only if the selector is not negated and is not
+ // a pseudo-element
+ if (!aIsNegated && mOperator && !aIsPseudoElem) {
+ aString.Append(PRUnichar(' '));
+ aString.Append(mOperator);
+ }
}
PRBool
nsCSSSelector::CanBeNamespaced(PRBool aIsNegated) const
{
return !aIsNegated ||
(!mIDList && !mClassList && !mPseudoClassList && !mAttrList);
}
--- a/layout/style/nsComputedDOMStyle.cpp
+++ b/layout/style/nsComputedDOMStyle.cpp
@@ -1161,126 +1161,78 @@ nsComputedDOMStyle::GetFontVariant(nsIDO
} else {
val->SetIdent(eCSSKeyword_normal);
}
return CallQueryInterface(val, aValue);
}
nsresult
-nsComputedDOMStyle::GetBackgroundList(PRUint8 nsStyleBackground::Layer::* aMember,
- PRUint32 nsStyleBackground::* aCount,
- const PRInt32 aTable[],
- nsIDOMCSSValue** aResult)
-{
- const nsStyleBackground* bg = GetStyleBackground();
-
- nsDOMCSSValueList *valueList = GetROCSSValueList(PR_TRUE);
- NS_ENSURE_TRUE(valueList, NS_ERROR_OUT_OF_MEMORY);
-
- for (PRUint32 i = 0, i_end = bg->*aCount; i < i_end; ++i) {
- nsROCSSPrimitiveValue *val = GetROCSSPrimitiveValue();
- if (!val || !valueList->AppendCSSValue(val)) {
- delete val;
- delete valueList;
- return NS_ERROR_OUT_OF_MEMORY;
- }
- val->SetIdent(nsCSSProps::ValueToKeywordEnum(bg->mLayers[i].*aMember,
- aTable));
- }
-
- return CallQueryInterface(valueList, aResult);
-}
-
-nsresult
nsComputedDOMStyle::GetBackgroundAttachment(nsIDOMCSSValue** aValue)
{
- return GetBackgroundList(&nsStyleBackground::Layer::mAttachment,
- &nsStyleBackground::mAttachmentCount,
- nsCSSProps::kBackgroundAttachmentKTable,
- aValue);
+ nsROCSSPrimitiveValue *val = GetROCSSPrimitiveValue();
+ NS_ENSURE_TRUE(val, NS_ERROR_OUT_OF_MEMORY);
+
+ const nsStyleBackground *background = GetStyleBackground();
+
+ val->SetIdent(
+ nsCSSProps::ValueToKeywordEnum(background->mBackgroundAttachment,
+ nsCSSProps::kBackgroundAttachmentKTable));
+
+ return CallQueryInterface(val, aValue);
}
nsresult
nsComputedDOMStyle::GetBackgroundClip(nsIDOMCSSValue** aValue)
{
- return GetBackgroundList(&nsStyleBackground::Layer::mClip,
- &nsStyleBackground::mClipCount,
- nsCSSProps::kBackgroundClipKTable,
- aValue);
+ nsROCSSPrimitiveValue *val = GetROCSSPrimitiveValue();
+ NS_ENSURE_TRUE(val, NS_ERROR_OUT_OF_MEMORY);
+
+ val->SetIdent(
+ nsCSSProps::ValueToKeywordEnum(GetStyleBackground()->mBackgroundClip,
+ nsCSSProps::kBackgroundClipKTable));
+
+ return CallQueryInterface(val, aValue);
}
nsresult
nsComputedDOMStyle::GetBackgroundColor(nsIDOMCSSValue** aValue)
{
- const nsStyleBackground* bg = GetStyleBackground();
- nsresult rv;
-
- if (bg->mBackgroundColor == bg->mFallbackBackgroundColor) {
- nsROCSSPrimitiveValue* val = GetROCSSPrimitiveValue();
- NS_ENSURE_TRUE(val, NS_ERROR_OUT_OF_MEMORY);
-
- rv = SetToRGBAColor(val, bg->mBackgroundColor);
- if (NS_FAILED(rv)) {
- delete val;
- return rv;
- }
- rv = CallQueryInterface(val, aValue);
- } else {
- nsDOMCSSValueList *valueList = GetROCSSValueList(PR_FALSE);
- NS_ENSURE_TRUE(valueList, NS_ERROR_OUT_OF_MEMORY);
-
- for (PRUint32 i = 0; i < 2; ++i) {
- nsROCSSPrimitiveValue* val = GetROCSSPrimitiveValue();
- if (!val || !valueList->AppendCSSValue(val)) {
- delete val;
- delete valueList;
- return NS_ERROR_OUT_OF_MEMORY;
- }
-
- rv = SetToRGBAColor(val, (i == 0) ? bg->mBackgroundColor
- : bg->mFallbackBackgroundColor);
- if (NS_FAILED(rv)) {
- delete valueList;
- return rv;
- }
- }
- rv = CallQueryInterface(valueList, aValue);
+ nsROCSSPrimitiveValue* val = GetROCSSPrimitiveValue();
+ NS_ENSURE_TRUE(val, NS_ERROR_OUT_OF_MEMORY);
+
+ const nsStyleBackground* color = GetStyleBackground();
+ nsresult rv = SetToRGBAColor(val, color->mBackgroundColor);
+ if (NS_FAILED(rv)) {
+ delete val;
+ return rv;
}
- return rv;
+ return CallQueryInterface(val, aValue);
}
nsresult
nsComputedDOMStyle::GetBackgroundImage(nsIDOMCSSValue** aValue)
{
- const nsStyleBackground* bg = GetStyleBackground();
-
- nsDOMCSSValueList *valueList = GetROCSSValueList(PR_TRUE);
- NS_ENSURE_TRUE(valueList, NS_ERROR_OUT_OF_MEMORY);
-
- for (PRUint32 i = 0, i_end = bg->mImageCount; i < i_end; ++i) {
- nsROCSSPrimitiveValue *val = GetROCSSPrimitiveValue();
- if (!val || !valueList->AppendCSSValue(val)) {
- delete val;
- delete valueList;
- return NS_ERROR_OUT_OF_MEMORY;
+ nsROCSSPrimitiveValue* val = GetROCSSPrimitiveValue();
+ NS_ENSURE_TRUE(val, NS_ERROR_OUT_OF_MEMORY);
+
+ const nsStyleBackground* color = GetStyleBackground();
+
+ if (color->mBackgroundFlags & NS_STYLE_BG_IMAGE_NONE) {
+ val->SetIdent(eCSSKeyword_none);
+ } else {
+ nsCOMPtr<nsIURI> uri;
+ if (color->mBackgroundImage) {
+ color->mBackgroundImage->GetURI(getter_AddRefs(uri));
}
-
- imgIRequest *image = bg->mLayers[i].mImage.mRequest;
- if (!image) {
- val->SetIdent(eCSSKeyword_none);
- } else {
- nsCOMPtr<nsIURI> uri;
- image->GetURI(getter_AddRefs(uri));
- val->SetURI(uri);
- }
+ val->SetURI(uri);
}
- return CallQueryInterface(valueList, aValue);
+ return CallQueryInterface(val, aValue);
}
nsresult
nsComputedDOMStyle::GetBackgroundInlinePolicy(nsIDOMCSSValue** aValue)
{
nsROCSSPrimitiveValue *val = GetROCSSPrimitiveValue();
NS_ENSURE_TRUE(val, NS_ERROR_OUT_OF_MEMORY);
@@ -1289,77 +1241,82 @@ nsComputedDOMStyle::GetBackgroundInlineP
nsCSSProps::kBackgroundInlinePolicyKTable));
return CallQueryInterface(val, aValue);
}
nsresult
nsComputedDOMStyle::GetBackgroundOrigin(nsIDOMCSSValue** aValue)
{
- return GetBackgroundList(&nsStyleBackground::Layer::mOrigin,
- &nsStyleBackground::mOriginCount,
- nsCSSProps::kBackgroundOriginKTable,
- aValue);
+ nsROCSSPrimitiveValue *val = GetROCSSPrimitiveValue();
+ NS_ENSURE_TRUE(val, NS_ERROR_OUT_OF_MEMORY);
+
+ val->SetIdent(
+ nsCSSProps::ValueToKeywordEnum(GetStyleBackground()->mBackgroundOrigin,
+ nsCSSProps::kBackgroundOriginKTable));
+
+ return CallQueryInterface(val, aValue);
}
nsresult
nsComputedDOMStyle::GetBackgroundPosition(nsIDOMCSSValue** aValue)
{
- const nsStyleBackground* bg = GetStyleBackground();
-
- nsDOMCSSValueList *valueList = GetROCSSValueList(PR_TRUE);
+ nsDOMCSSValueList *valueList = GetROCSSValueList(PR_FALSE);
NS_ENSURE_TRUE(valueList, NS_ERROR_OUT_OF_MEMORY);
- for (PRUint32 i = 0, i_end = bg->mPositionCount; i < i_end; ++i) {
- nsDOMCSSValueList *itemList = GetROCSSValueList(PR_FALSE);
- if (!itemList || !valueList->AppendCSSValue(itemList)) {
- delete valueList;
- delete itemList;
- return NS_ERROR_OUT_OF_MEMORY;
- }
-
- nsROCSSPrimitiveValue *valX = GetROCSSPrimitiveValue();
- if (!valX || !itemList->AppendCSSValue(valX)) {
- delete valueList;
- delete valX;
- return NS_ERROR_OUT_OF_MEMORY;
- }
-
- nsROCSSPrimitiveValue *valY = GetROCSSPrimitiveValue();
- if (!valY || !itemList->AppendCSSValue(valY)) {
- delete valueList;
- delete valY;
- return NS_ERROR_OUT_OF_MEMORY;
- }
-
- const nsStyleBackground::Position &pos = bg->mLayers[i].mPosition;
-
- if (pos.mXIsPercent) {
- valX->SetPercent(pos.mXPosition.mFloat);
- } else {
- valX->SetAppUnits(pos.mXPosition.mCoord);
- }
-
- if (pos.mYIsPercent) {
- valY->SetPercent(pos.mYPosition.mFloat);
- } else {
- valY->SetAppUnits(pos.mYPosition.mCoord);
- }
+ nsROCSSPrimitiveValue *valX = GetROCSSPrimitiveValue();
+ if (!valX || !valueList->AppendCSSValue(valX)) {
+ delete valueList;
+ delete valX;
+ return NS_ERROR_OUT_OF_MEMORY;
+ }
+
+ nsROCSSPrimitiveValue *valY = GetROCSSPrimitiveValue();
+ if (!valY || !valueList->AppendCSSValue(valY)) {
+ delete valueList;
+ delete valY;
+ return NS_ERROR_OUT_OF_MEMORY;
+ }
+
+ const nsStyleBackground *bg = GetStyleBackground();
+
+ if (NS_STYLE_BG_X_POSITION_LENGTH & bg->mBackgroundFlags) {
+ valX->SetAppUnits(bg->mBackgroundXPosition.mCoord);
+ }
+ else if (NS_STYLE_BG_X_POSITION_PERCENT & bg->mBackgroundFlags) {
+ valX->SetPercent(bg->mBackgroundXPosition.mFloat);
+ }
+ else {
+ valX->SetPercent(0.0f);
+ }
+
+ if (NS_STYLE_BG_Y_POSITION_LENGTH & bg->mBackgroundFlags) {
+ valY->SetAppUnits(bg->mBackgroundYPosition.mCoord);
+ }
+ else if (NS_STYLE_BG_Y_POSITION_PERCENT & bg->mBackgroundFlags) {
+ valY->SetPercent(bg->mBackgroundYPosition.mFloat);
+ }
+ else {
+ valY->SetPercent(0.0f);
}
return CallQueryInterface(valueList, aValue);
}
nsresult
nsComputedDOMStyle::GetBackgroundRepeat(nsIDOMCSSValue** aValue)
{
- return GetBackgroundList(&nsStyleBackground::Layer::mRepeat,
- &nsStyleBackground::mRepeatCount,
- nsCSSProps::kBackgroundRepeatKTable,
- aValue);
+ nsROCSSPrimitiveValue *val = GetROCSSPrimitiveValue();
+ NS_ENSURE_TRUE(val, NS_ERROR_OUT_OF_MEMORY);
+
+ val->SetIdent(
+ nsCSSProps::ValueToKeywordEnum(GetStyleBackground()->mBackgroundRepeat,
+ nsCSSProps::kBackgroundRepeatKTable));
+
+ return CallQueryInterface(val, aValue);
}
nsresult
nsComputedDOMStyle::GetPadding(nsIDOMCSSValue** aValue)
{
// return null per spec.
aValue = nsnull;
@@ -1869,17 +1826,17 @@ nsComputedDOMStyle::GetCSSShadowArray(ns
shadowValues = shadowValuesNoSpread;
shadowValuesLength = NS_ARRAY_LENGTH(shadowValuesNoSpread);
}
nsDOMCSSValueList *valueList = GetROCSSValueList(PR_TRUE);
NS_ENSURE_TRUE(valueList, NS_ERROR_OUT_OF_MEMORY);
for (nsCSSShadowItem *item = aArray->ShadowAt(0),
- *item_end = item + aArray->Length();
+ *item_end = item + aArray->Length();
item < item_end; ++item) {
nsDOMCSSValueList *itemList = GetROCSSValueList(PR_FALSE);
if (!itemList || !valueList->AppendCSSValue(itemList)) {
delete itemList;
delete valueList;
return NS_ERROR_OUT_OF_MEMORY;
}
--- a/layout/style/nsComputedDOMStyle.h
+++ b/layout/style/nsComputedDOMStyle.h
@@ -50,17 +50,16 @@
#include "nsCSSProps.h"
#include "nsIPresShell.h"
#include "nsIContent.h"
#include "nsIFrame.h"
#include "nsCOMPtr.h"
#include "nsWeakReference.h"
#include "nsAutoPtr.h"
-#include "nsStyleStruct.h"
class nsComputedDOMStyle : public nsIComputedDOMStyle
{
public:
NS_DECL_CYCLE_COLLECTING_ISUPPORTS
NS_DECL_CYCLE_COLLECTION_CLASS(nsComputedDOMStyle)
NS_IMETHOD Init(nsIDOMElement *aElement,
@@ -112,21 +111,16 @@ private:
PRBool GetLineHeightCoord(nscoord& aCoord);
nsresult GetCSSShadowArray(nsCSSShadowArray* aArray,
const nscolor& aDefaultColor,
PRBool aIsBoxShadow,
nsIDOMCSSValue** aValue);
- nsresult GetBackgroundList(PRUint8 nsStyleBackground::Layer::* aMember,
- PRUint32 nsStyleBackground::* aCount,
- const PRInt32 aTable[],
- nsIDOMCSSValue** aResult);
-
/* Properties Queryable as CSSValues */
nsresult GetAppearance(nsIDOMCSSValue** aValue);
/* Box properties */
nsresult GetBoxAlign(nsIDOMCSSValue** aValue);
nsresult GetBoxDirection(nsIDOMCSSValue** aValue);
nsresult GetBoxFlex(nsIDOMCSSValue** aValue);
--- a/layout/style/nsICSSStyleRule.h
+++ b/layout/style/nsICSSStyleRule.h
@@ -168,22 +168,20 @@ public:
void ToString(nsAString& aString, nsICSSStyleSheet* aSheet,
PRBool aAppend = PR_FALSE) const;
private:
void AddPseudoClassInternal(nsPseudoClassList *aPseudoClass);
nsCSSSelector* Clone(PRBool aDeepNext, PRBool aDeepNegations) const;
- void AppendToStringWithoutCombinators(nsAString& aString,
- nsICSSStyleSheet* aSheet) const;
- void AppendToStringWithoutCombinatorsOrNegations(nsAString& aString,
- nsICSSStyleSheet* aSheet,
- PRBool aIsNegated)
- const;
+ void AppendNegationToString(nsAString& aString);
+ void ToStringInternal(nsAString& aString, nsICSSStyleSheet* aSheet,
+ PRBool aIsPseudoElem,
+ PRBool aIsNegated) const;
// Returns true if this selector can have a namespace specified (which
// happens if and only if the default namespace would apply to this
// selector).
PRBool CanBeNamespaced(PRBool aIsNegated) const;
// Calculate the specificity of this selector (not including its mNext
// or its mNegations).
PRInt32 CalcWeightWithoutNegations() const;
--- a/layout/style/nsRuleNode.cpp
+++ b/layout/style/nsRuleNode.cpp
@@ -1415,17 +1415,18 @@ nsRuleNode::GetUserInterfaceData(nsStyle
const void*
nsRuleNode::GetUIResetData(nsStyleContext* aContext)
{
nsRuleDataUserInterface uiData; // Declare a struct with null CSS values.
nsRuleData ruleData(NS_STYLE_INHERIT_BIT(UIReset), mPresContext, aContext);
ruleData.mUserInterfaceData = &uiData;
- return WalkRuleTree(eStyleStruct_UIReset, aContext, &ruleData, &uiData);
+ const void* res = WalkRuleTree(eStyleStruct_UIReset, aContext, &ruleData, &uiData);
+ return res;
}
const void*
nsRuleNode::GetFontData(nsStyleContext* aContext)
{
nsRuleDataFont fontData; // Declare a struct with null CSS values.
nsRuleData ruleData(NS_STYLE_INHERIT_BIT(Font), mPresContext, aContext);
ruleData.mFontData = &fontData;
@@ -1449,27 +1450,17 @@ nsRuleNode::GetBackgroundData(nsStyleCon
nsRuleDataColor colorData; // Declare a struct with null CSS values.
nsRuleData ruleData(NS_STYLE_INHERIT_BIT(Background), mPresContext, aContext);
ruleData.mColorData = &colorData;
// If any members need to be set to null here, they must also be set to
// null in HasAuthorSpecifiedRules (look at mBoxShadow in GetBorderData
// and HasAuthorSpecifiedRules).
- const void *res = WalkRuleTree(eStyleStruct_Background, aContext, &ruleData, &colorData);
-
- // We are sharing with some style rule. It really owns the data.
- colorData.mBackImage = nsnull;
- colorData.mBackRepeat = nsnull;
- colorData.mBackAttachment = nsnull;
- colorData.mBackPosition = nsnull;
- colorData.mBackClip = nsnull;
- colorData.mBackOrigin = nsnull;
-
- return res;
+ return WalkRuleTree(eStyleStruct_Background, aContext, &ruleData, &colorData);
}
const void*
nsRuleNode::GetMarginData(nsStyleContext* aContext)
{
nsRuleDataMargin marginData; // Declare a struct with null CSS values.
nsRuleData ruleData(NS_STYLE_INHERIT_BIT(Margin), mPresContext, aContext);
ruleData.mMarginData = &marginData;
@@ -3775,299 +3766,139 @@ nsRuleNode::ComputeColorData(void* aStar
else {
SetColor(colorData.mColor, parentColor->mColor, mPresContext, aContext,
color->mColor, canStoreInRuleTree);
}
COMPUTE_END_INHERITED(Color, color)
}
-// information about how to compute values for background-* properties
-template <class SpecifiedValueItem>
-struct InitialInheritLocationFor {
-};
-
-NS_SPECIALIZE_TEMPLATE
-struct InitialInheritLocationFor<nsCSSValueList> {
- static nsCSSValue nsCSSValueList::* Location() {
- return &nsCSSValueList::mValue;
- }
-};
-
-NS_SPECIALIZE_TEMPLATE
-struct InitialInheritLocationFor<nsCSSValuePairList> {
- static nsCSSValue nsCSSValuePairList::* Location() {
- return &nsCSSValuePairList::mXValue;
- }
-};
-
-template <class SpecifiedValueItem, class ComputedValueItem>
-struct BackgroundItemComputer {
-};
-
-NS_SPECIALIZE_TEMPLATE
-struct BackgroundItemComputer<nsCSSValueList, PRUint8>
-{
- static void ComputeValue(nsStyleContext* aStyleContext,
- const nsCSSValueList* aSpecifiedValue,
- PRUint8& aComputedValue,
- PRBool& aCanStoreInRuleTree)
- {
- SetDiscrete(aSpecifiedValue->mValue, aComputedValue, aCanStoreInRuleTree,
- SETDSC_ENUMERATED, PRUint8(0), 0, 0, 0, 0, 0);
- }
-};
-
-NS_SPECIALIZE_TEMPLATE
-struct BackgroundItemComputer<nsCSSValueList, nsStyleBackground::Image>
-{
- static void ComputeValue(nsStyleContext* aStyleContext,
- const nsCSSValueList* aSpecifiedValue,
- nsStyleBackground::Image& aComputedValue,
- PRBool& aCanStoreInRuleTree)
- {
- const nsCSSValue &value = aSpecifiedValue->mValue;
- if (eCSSUnit_Image == value.GetUnit()) {
- aComputedValue.mRequest = value.GetImageValue();
- aComputedValue.mSpecified = PR_TRUE;
- }
- else {
- NS_ASSERTION(eCSSUnit_None == value.GetUnit(), "unexpected unit");
- aComputedValue.mRequest = nsnull;
- aComputedValue.mSpecified = PR_FALSE;
- }
- }
-};
-
-struct BackgroundPositionAxis {
- nsCSSValue nsCSSValuePairList::*specified;
- nsStyleBackground::Position::PositionCoord
- nsStyleBackground::Position::*result;
- PRPackedBool nsStyleBackground::Position::*isPercent;
-};
-
-static const BackgroundPositionAxis gBGPosAxes[] = {
- { &nsCSSValuePairList::mXValue,
- &nsStyleBackground::Position::mXPosition,
- &nsStyleBackground::Position::mXIsPercent },
- { &nsCSSValuePairList::mYValue,
- &nsStyleBackground::Position::mYPosition,
- &nsStyleBackground::Position::mYIsPercent }
-};
-
-NS_SPECIALIZE_TEMPLATE
-struct BackgroundItemComputer<nsCSSValuePairList, nsStyleBackground::Position>
-{
- static void ComputeValue(nsStyleContext* aStyleContext,
- const nsCSSValuePairList* aSpecifiedValue,
- nsStyleBackground::Position& aComputedValue,
- PRBool& aCanStoreInRuleTree)
- {
- nsStyleBackground::Position &position = aComputedValue;
- for (const BackgroundPositionAxis *axis = gBGPosAxes,
- *axis_end = gBGPosAxes + NS_ARRAY_LENGTH(gBGPosAxes);
- axis != axis_end; ++axis) {
- const nsCSSValue &specified = aSpecifiedValue->*(axis->specified);
- if (eCSSUnit_Percent == specified.GetUnit()) {
- (position.*(axis->result)).mFloat = specified.GetPercentValue();
- position.*(axis->isPercent) = PR_TRUE;
- }
- else if (specified.IsLengthUnit()) {
- (position.*(axis->result)).mCoord =
- CalcLength(specified, aStyleContext, aStyleContext->PresContext(),
- aCanStoreInRuleTree);
- position.*(axis->isPercent) = PR_FALSE;
- }
- else if (eCSSUnit_Enumerated == specified.GetUnit()) {
- (position.*(axis->result)).mFloat =
- GetFloatFromBoxPosition(specified.GetIntValue());
- position.*(axis->isPercent) = PR_TRUE;
- } else {
- NS_NOTREACHED("unexpected unit");
- }
- }
- }
-};
-
-
-template <class SpecifiedValueItem, class ComputedValueItem>
-static void
-SetBackgroundList(nsStyleContext* aStyleContext,
- const SpecifiedValueItem* aValueList,
- nsAutoTArray< nsStyleBackground::Layer, 1> &aLayers,
- const nsAutoTArray<nsStyleBackground::Layer, 1>
- &aParentLayers,
- ComputedValueItem nsStyleBackground::Layer::* aResultLocation,
- ComputedValueItem aInitialValue,
- PRUint32 aParentItemCount,
- PRUint32& aItemCount,
- PRUint32& aMaxItemCount,
- PRBool& aRebuild,
- PRBool& aCanStoreInRuleTree)
-{
- if (aValueList) {
- aRebuild = PR_TRUE;
- nsCSSValue SpecifiedValueItem::* initialInherit =
- InitialInheritLocationFor<SpecifiedValueItem>::Location();
- if (eCSSUnit_Inherit == (aValueList->*initialInherit).GetUnit()) {
- NS_ASSERTION(!aValueList->mNext, "should have only one value");
- aCanStoreInRuleTree = PR_FALSE;
- if (!aLayers.EnsureLengthAtLeast(aParentItemCount)) {
- NS_WARNING("out of memory");
- aParentItemCount = aLayers.Length();
- }
- aItemCount = aParentItemCount;
- for (PRUint32 i = 0; i < aParentItemCount; ++i) {
- aLayers[i].*aResultLocation = aParentLayers[i].*aResultLocation;
- }
- } else if (eCSSUnit_Initial == (aValueList->*initialInherit).GetUnit()) {
- NS_ASSERTION(!aValueList->mNext, "should have only one value");
- aItemCount = 1;
- aLayers[0].*aResultLocation = aInitialValue;
- } else {
- const SpecifiedValueItem *item = aValueList;
- aItemCount = 0;
- do {
- NS_ASSERTION((item->*initialInherit).GetUnit() != eCSSUnit_Inherit &&
- (item->*initialInherit).GetUnit() != eCSSUnit_Initial,
- "unexpected unit");
- ++aItemCount;
- if (!aLayers.EnsureLengthAtLeast(aItemCount)) {
- NS_WARNING("out of memory");
- --aItemCount;
- break;
- }
- BackgroundItemComputer<SpecifiedValueItem, ComputedValueItem>
- ::ComputeValue(aStyleContext, item,
- aLayers[aItemCount-1].*aResultLocation,
- aCanStoreInRuleTree);
- item = item->mNext;
- } while (item);
- }
- }
-
- if (aItemCount > aMaxItemCount)
- aMaxItemCount = aItemCount;
-}
-
-template <class ComputedValueItem>
-static void
-FillBackgroundList(nsAutoTArray< nsStyleBackground::Layer, 1> &aLayers,
- ComputedValueItem nsStyleBackground::Layer::* aResultLocation,
- PRUint32 aItemCount, PRUint32 aFillCount)
-{
- NS_PRECONDITION(aFillCount <= aLayers.Length(), "unexpected array length");
- for (PRUint32 sourceLayer = 0, destLayer = aItemCount;
- destLayer < aFillCount;
- ++sourceLayer, ++destLayer) {
- aLayers[destLayer].*aResultLocation =
- aLayers[sourceLayer].*aResultLocation;
- }
-}
-
const void*
nsRuleNode::ComputeBackgroundData(void* aStartStruct,
const nsRuleDataStruct& aData,
nsStyleContext* aContext,
nsRuleNode* aHighestNode,
const RuleDetail aRuleDetail,
const PRBool aCanStoreInRuleTree)
{
COMPUTE_START_RESET(Background, (), bg, parentBG, Color, colorData)
- // background-color: color, string, inherit [pair]
- if (eCSSUnit_Initial == colorData.mBackColor.mXValue.GetUnit()) {
+ // save parentFlags in case bg == parentBG and we clobber them later
+ PRUint8 parentFlags = parentBG->mBackgroundFlags;
+
+ // background-color: color, string, inherit
+ if (eCSSUnit_Initial == colorData.mBackColor.GetUnit()) {
bg->mBackgroundColor = NS_RGBA(0, 0, 0, 0);
- } else if (!SetColor(colorData.mBackColor.mXValue,
- parentBG->mBackgroundColor, mPresContext,
- aContext, bg->mBackgroundColor, canStoreInRuleTree)) {
- NS_ASSERTION(eCSSUnit_Null == colorData.mBackColor.mXValue.GetUnit(),
- "unexpected color unit");
- }
-
- if (eCSSUnit_Initial == colorData.mBackColor.mYValue.GetUnit()) {
- bg->mFallbackBackgroundColor = NS_RGBA(0, 0, 0, 0);
- } else if (!SetColor(colorData.mBackColor.mYValue,
- parentBG->mFallbackBackgroundColor, mPresContext,
- aContext, bg->mFallbackBackgroundColor,
+ } else if (!SetColor(colorData.mBackColor, parentBG->mBackgroundColor,
+ mPresContext, aContext, bg->mBackgroundColor,
canStoreInRuleTree)) {
- NS_ASSERTION(eCSSUnit_Null == colorData.mBackColor.mYValue.GetUnit(),
+ NS_ASSERTION(eCSSUnit_Null == colorData.mBackColor.GetUnit(),
"unexpected color unit");
}
- PRUint32 maxItemCount = 1;
- PRBool rebuild = PR_FALSE;
-
- // background-image: url (stored as image), none, inherit [list]
- SetBackgroundList(aContext, colorData.mBackImage, bg->mLayers,
- parentBG->mLayers, &nsStyleBackground::Layer::mImage,
- nsStyleBackground::Image(), parentBG->mImageCount,
- bg->mImageCount, maxItemCount, rebuild, canStoreInRuleTree);
-
- // background-repeat: enum, inherit, initial [list]
- SetBackgroundList(aContext, colorData.mBackRepeat, bg->mLayers,
- parentBG->mLayers, &nsStyleBackground::Layer::mRepeat,
- PRUint8(NS_STYLE_BG_REPEAT_XY), parentBG->mRepeatCount,
- bg->mRepeatCount, maxItemCount, rebuild, canStoreInRuleTree);
-
- // background-attachment: enum, inherit, initial [list]
- SetBackgroundList(aContext, colorData.mBackAttachment, bg->mLayers,
- parentBG->mLayers,
- &nsStyleBackground::Layer::mAttachment,
- PRUint8(NS_STYLE_BG_ATTACHMENT_SCROLL),
- parentBG->mAttachmentCount,
- bg->mAttachmentCount, maxItemCount, rebuild,
- canStoreInRuleTree);
-
- // background-clip: enum, inherit, initial [list]
- SetBackgroundList(aContext, colorData.mBackClip, bg->mLayers,
- parentBG->mLayers, &nsStyleBackground::Layer::mClip,
- PRUint8(NS_STYLE_BG_CLIP_BORDER), parentBG->mClipCount,
- bg->mClipCount, maxItemCount, rebuild, canStoreInRuleTree);
+ // background-image: url (stored as image), none, inherit
+ if (eCSSUnit_Image == colorData.mBackImage.GetUnit()) {
+ bg->mBackgroundImage = colorData.mBackImage.GetImageValue();
+ }
+ else if (eCSSUnit_None == colorData.mBackImage.GetUnit() ||
+ eCSSUnit_Initial == colorData.mBackImage.GetUnit()) {
+ bg->mBackgroundImage = nsnull;
+ }
+ else if (eCSSUnit_Inherit == colorData.mBackImage.GetUnit()) {
+ canStoreInRuleTree = PR_FALSE;
+ bg->mBackgroundImage = parentBG->mBackgroundImage;
+ }
+
+ if (bg->mBackgroundImage) {
+ bg->mBackgroundFlags &= ~NS_STYLE_BG_IMAGE_NONE;
+ } else {
+ bg->mBackgroundFlags |= NS_STYLE_BG_IMAGE_NONE;
+ }
+
+ // background-repeat: enum, inherit, initial
+ SetDiscrete(colorData.mBackRepeat, bg->mBackgroundRepeat, canStoreInRuleTree,
+ SETDSC_ENUMERATED, parentBG->mBackgroundRepeat,
+ NS_STYLE_BG_REPEAT_XY, 0, 0, 0, 0);
+
+ // background-attachment: enum, inherit, initial
+ SetDiscrete(colorData.mBackAttachment, bg->mBackgroundAttachment, canStoreInRuleTree,
+ SETDSC_ENUMERATED, parentBG->mBackgroundAttachment,
+ NS_STYLE_BG_ATTACHMENT_SCROLL, 0, 0, 0, 0);
+
+ // background-clip: enum, inherit, initial
+ SetDiscrete(colorData.mBackClip, bg->mBackgroundClip, canStoreInRuleTree,
+ SETDSC_ENUMERATED, parentBG->mBackgroundClip,
+ NS_STYLE_BG_CLIP_BORDER, 0, 0, 0, 0);
// background-inline-policy: enum, inherit, initial
SetDiscrete(colorData.mBackInlinePolicy, bg->mBackgroundInlinePolicy,
canStoreInRuleTree, SETDSC_ENUMERATED,
parentBG->mBackgroundInlinePolicy,
NS_STYLE_BG_INLINE_POLICY_CONTINUOUS, 0, 0, 0, 0);
- // background-origin: enum, inherit, initial [list]
- SetBackgroundList(aContext, colorData.mBackOrigin, bg->mLayers,
- parentBG->mLayers, &nsStyleBackground::Layer::mOrigin,
- PRUint8(NS_STYLE_BG_ORIGIN_PADDING), parentBG->mOriginCount,
- bg->mOriginCount, maxItemCount, rebuild,
- canStoreInRuleTree);
-
- // background-position: enum, length, percent (flags), inherit [pair list]
- nsStyleBackground::Position initialPosition;
- initialPosition.SetInitialValues();
- SetBackgroundList(aContext, colorData.mBackPosition, bg->mLayers,
- parentBG->mLayers, &nsStyleBackground::Layer::mPosition,
- initialPosition, parentBG->mPositionCount,
- bg->mPositionCount, maxItemCount, rebuild,
- canStoreInRuleTree);
-
- if (rebuild) {
- // Delete any extra items. We need to keep layers in which any
- // property was specified.
- bg->mLayers.TruncateLength(maxItemCount);
-
- PRUint32 fillCount = bg->mImageCount;
- FillBackgroundList(bg->mLayers, &nsStyleBackground::Layer::mImage,
- bg->mImageCount, fillCount);
- FillBackgroundList(bg->mLayers, &nsStyleBackground::Layer::mRepeat,
- bg->mRepeatCount, fillCount);
- FillBackgroundList(bg->mLayers, &nsStyleBackground::Layer::mAttachment,
- bg->mAttachmentCount, fillCount);
- FillBackgroundList(bg->mLayers, &nsStyleBackground::Layer::mClip,
- bg->mClipCount, fillCount);
- FillBackgroundList(bg->mLayers, &nsStyleBackground::Layer::mOrigin,
- bg->mOriginCount, fillCount);
- FillBackgroundList(bg->mLayers, &nsStyleBackground::Layer::mPosition,
- bg->mPositionCount, fillCount);
+ // background-origin: enum, inherit, initial
+ SetDiscrete(colorData.mBackOrigin, bg->mBackgroundOrigin, canStoreInRuleTree,
+ SETDSC_ENUMERATED, parentBG->mBackgroundOrigin,
+ NS_STYLE_BG_ORIGIN_PADDING, 0, 0, 0, 0);
+
+ // background-position: enum, length, percent (flags), inherit
+ if (eCSSUnit_Percent == colorData.mBackPosition.mXValue.GetUnit()) {
+ bg->mBackgroundXPosition.mFloat = colorData.mBackPosition.mXValue.GetPercentValue();
+ bg->mBackgroundFlags |= NS_STYLE_BG_X_POSITION_PERCENT;
+ bg->mBackgroundFlags &= ~NS_STYLE_BG_X_POSITION_LENGTH;
+ }
+ else if (colorData.mBackPosition.mXValue.IsLengthUnit()) {
+ bg->mBackgroundXPosition.mCoord = CalcLength(colorData.mBackPosition.mXValue,
+ aContext, mPresContext, canStoreInRuleTree);
+ bg->mBackgroundFlags |= NS_STYLE_BG_X_POSITION_LENGTH;
+ bg->mBackgroundFlags &= ~NS_STYLE_BG_X_POSITION_PERCENT;
+ }
+ else if (eCSSUnit_Enumerated == colorData.mBackPosition.mXValue.GetUnit()) {
+ bg->mBackgroundXPosition.mFloat =
+ GetFloatFromBoxPosition(colorData.mBackPosition.mXValue.GetIntValue());
+
+ bg->mBackgroundFlags |= NS_STYLE_BG_X_POSITION_PERCENT;
+ bg->mBackgroundFlags &= ~NS_STYLE_BG_X_POSITION_LENGTH;
+ }
+ else if (eCSSUnit_Inherit == colorData.mBackPosition.mXValue.GetUnit()) {
+ canStoreInRuleTree = PR_FALSE;
+ bg->mBackgroundXPosition = parentBG->mBackgroundXPosition;
+ bg->mBackgroundFlags &= ~(NS_STYLE_BG_X_POSITION_LENGTH | NS_STYLE_BG_X_POSITION_PERCENT);
+ bg->mBackgroundFlags |= (parentFlags & (NS_STYLE_BG_X_POSITION_LENGTH | NS_STYLE_BG_X_POSITION_PERCENT));
+ }
+ else if (eCSSUnit_Initial == colorData.mBackPosition.mXValue.GetUnit()) {
+ bg->mBackgroundFlags &= ~(NS_STYLE_BG_X_POSITION_LENGTH | NS_STYLE_BG_X_POSITION_PERCENT);
+ }
+
+ if (eCSSUnit_Percent == colorData.mBackPosition.mYValue.GetUnit()) {
+ bg->mBackgroundYPosition.mFloat = colorData.mBackPosition.mYValue.GetPercentValue();
+ bg->mBackgroundFlags |= NS_STYLE_BG_Y_POSITION_PERCENT;
+ bg->mBackgroundFlags &= ~NS_STYLE_BG_Y_POSITION_LENGTH;
+ }
+ else if (colorData.mBackPosition.mYValue.IsLengthUnit()) {
+ bg->mBackgroundYPosition.mCoord = CalcLength(colorData.mBackPosition.mYValue,
+ aContext, mPresContext, canStoreInRuleTree);
+ bg->mBackgroundFlags |= NS_STYLE_BG_Y_POSITION_LENGTH;
+ bg->mBackgroundFlags &= ~NS_STYLE_BG_Y_POSITION_PERCENT;
+ }
+ else if (eCSSUnit_Enumerated == colorData.mBackPosition.mYValue.GetUnit()) {
+ bg->mBackgroundYPosition.mFloat =
+ GetFloatFromBoxPosition(colorData.mBackPosition.mYValue.GetIntValue());
+
+ bg->mBackgroundFlags |= NS_STYLE_BG_Y_POSITION_PERCENT;
+ bg->mBackgroundFlags &= ~NS_STYLE_BG_Y_POSITION_LENGTH;
+ }
+ else if (eCSSUnit_Inherit == colorData.mBackPosition.mYValue.GetUnit()) {
+ canStoreInRuleTree = PR_FALSE;
+ bg->mBackgroundYPosition = parentBG->mBackgroundYPosition;
+ bg->mBackgroundFlags &= ~(NS_STYLE_BG_Y_POSITION_LENGTH | NS_STYLE_BG_Y_POSITION_PERCENT);
+ bg->mBackgroundFlags |= (parentFlags & (NS_STYLE_BG_Y_POSITION_LENGTH | NS_STYLE_BG_Y_POSITION_PERCENT));
+ }
+ else if (eCSSUnit_Initial == colorData.mBackPosition.mYValue.GetUnit()) {
+ bg->mBackgroundFlags &= ~(NS_STYLE_BG_Y_POSITION_LENGTH | NS_STYLE_BG_Y_POSITION_PERCENT);
}
COMPUTE_END_RESET(Background, bg)
}
const void*
nsRuleNode::ComputeMarginData(void* aStartStruct,
const nsRuleDataStruct& aData,
@@ -5663,17 +5494,16 @@ nsRuleNode::Sweep()
}
/* static */ PRBool
nsRuleNode::HasAuthorSpecifiedRules(nsStyleContext* aStyleContext,
PRUint32 ruleTypeMask)
{
nsRuleDataColor colorData;
nsRuleDataMargin marginData;
- nsCSSValue firstBackgroundImage;
PRUint32 nValues = 0;
PRUint32 inheritBits = 0;
if (ruleTypeMask & NS_AUTHOR_SPECIFIED_BACKGROUND)
inheritBits |= NS_STYLE_INHERIT_BIT(Background);
if (ruleTypeMask & NS_AUTHOR_SPECIFIED_BORDER)
inheritBits |= NS_STYLE_INHERIT_BIT(Border);
@@ -5683,19 +5513,18 @@ nsRuleNode::HasAuthorSpecifiedRules(nsSt
/* We're relying on the use of |aStyleContext| not mutating it! */
nsRuleData ruleData(inheritBits,
aStyleContext->PresContext(), aStyleContext);
ruleData.mColorData = &colorData;
ruleData.mMarginData = &marginData;
nsCSSValue* backgroundValues[] = {
- &colorData.mBackColor.mXValue,
- &colorData.mBackColor.mYValue,
- &firstBackgroundImage
+ &colorData.mBackColor,
+ &colorData.mBackImage
};
nsCSSValue* borderValues[] = {
&marginData.mBorderColor.mTop,
&marginData.mBorderStyle.mTop,
&marginData.mBorderWidth.mTop,
&marginData.mBorderColor.mRight,
&marginData.mBorderStyle.mRight,
@@ -5749,35 +5578,21 @@ nsRuleNode::HasAuthorSpecifiedRules(nsSt
do {
haveExplicitUAInherit = PR_FALSE;
for (nsRuleNode* ruleNode = styleContext->GetRuleNode(); ruleNode;
ruleNode = ruleNode->GetParent()) {
nsIStyleRule *rule = ruleNode->GetRule();
if (rule) {
ruleData.mLevel = ruleNode->GetLevel();
ruleData.mIsImportantRule = ruleNode->IsImportantRule();
-
rule->MapRuleInfoInto(&ruleData);
-
- if ((ruleTypeMask & NS_AUTHOR_SPECIFIED_BACKGROUND) &&
- colorData.mBackImage &&
- firstBackgroundImage.GetUnit() == eCSSUnit_Null) {
- // Handle background-image being a value list
- firstBackgroundImage = colorData.mBackImage->mValue;
- }
// Do the same nulling out as in GetBorderData, GetBackgroundData
// or GetPaddingData.
// We are sharing with some style rule. It really owns the data.
marginData.mBoxShadow = nsnull;
- colorData.mBackImage = nsnull;
- colorData.mBackRepeat = nsnull;
- colorData.mBackAttachment = nsnull;
- colorData.mBackPosition = nsnull;
- colorData.mBackClip = nsnull;
- colorData.mBackOrigin = nsnull;
if (ruleData.mLevel == nsStyleSet::eAgentSheet ||
ruleData.mLevel == nsStyleSet::eUserSheet) {
// This is a rule whose effect we want to ignore, so if any of
// the properties we care about were set, set them to the dummy
// value that they'll never otherwise get.
for (PRUint32 i = 0; i < nValues; ++i) {
nsCSSUnit unit = values[i]->GetUnit();
--- a/layout/style/nsStyleStruct.cpp
+++ b/layout/style/nsStyleStruct.cpp
@@ -1202,161 +1202,78 @@ nsChangeHint nsStyleColor::MaxDifference
}
#endif
// --------------------
// nsStyleBackground
//
nsStyleBackground::nsStyleBackground()
- : mAttachmentCount(1)
- , mClipCount(1)
- , mOriginCount(1)
- , mRepeatCount(1)
- , mPositionCount(1)
- , mImageCount(1)
- , mBackgroundColor(NS_RGBA(0, 0, 0, 0))
- , mFallbackBackgroundColor(NS_RGBA(0, 0, 0, 0))
- , mBackgroundInlinePolicy(NS_STYLE_BG_INLINE_POLICY_CONTINUOUS)
+ : mBackgroundFlags(NS_STYLE_BG_IMAGE_NONE),
+ mBackgroundAttachment(NS_STYLE_BG_ATTACHMENT_SCROLL),
+ mBackgroundClip(NS_STYLE_BG_CLIP_BORDER),
+ mBackgroundInlinePolicy(NS_STYLE_BG_INLINE_POLICY_CONTINUOUS),
+ mBackgroundOrigin(NS_STYLE_BG_ORIGIN_PADDING),
+ mBackgroundRepeat(NS_STYLE_BG_REPEAT_XY),
+ mBackgroundColor(NS_RGBA(0, 0, 0, 0))
{
- Layer *onlyLayer = mLayers.AppendElement();
- NS_ASSERTION(onlyLayer, "auto array must have room for 1 element");
- onlyLayer->SetInitialValues();
}
nsStyleBackground::nsStyleBackground(const nsStyleBackground& aSource)
- : mAttachmentCount(aSource.mAttachmentCount)
- , mClipCount(aSource.mClipCount)
- , mOriginCount(aSource.mOriginCount)
- , mRepeatCount(aSource.mRepeatCount)
- , mPositionCount(aSource.mPositionCount)
- , mImageCount(aSource.mImageCount)
- , mLayers(aSource.mLayers) // deep copy
- , mBackgroundColor(aSource.mBackgroundColor)
- , mFallbackBackgroundColor(aSource.mFallbackBackgroundColor)
- , mBackgroundInlinePolicy(aSource.mBackgroundInlinePolicy)
+ : mBackgroundFlags(aSource.mBackgroundFlags),
+ mBackgroundAttachment(aSource.mBackgroundAttachment),
+ mBackgroundClip(aSource.mBackgroundClip),
+ mBackgroundInlinePolicy(aSource.mBackgroundInlinePolicy),
+ mBackgroundOrigin(aSource.mBackgroundOrigin),
+ mBackgroundRepeat(aSource.mBackgroundRepeat),
+ mBackgroundXPosition(aSource.mBackgroundXPosition),
+ mBackgroundYPosition(aSource.mBackgroundYPosition),
+ mBackgroundColor(aSource.mBackgroundColor),
+ mBackgroundImage(aSource.mBackgroundImage)
{
- // If the deep copy of mLayers failed, truncate the counts.
- PRUint32 count = mLayers.Length();
- if (count != aSource.mLayers.Length()) {
- NS_WARNING("truncating counts due to out-of-memory");
- mAttachmentCount = PR_MAX(mAttachmentCount, count);
- mClipCount = PR_MAX(mClipCount, count);
- mOriginCount = PR_MAX(mOriginCount, count);
- mRepeatCount = PR_MAX(mRepeatCount, count);
- mPositionCount = PR_MAX(mPositionCount, count);
- mImageCount = PR_MAX(mImageCount, count);
- }
}
nsStyleBackground::~nsStyleBackground()
{
}
nsChangeHint nsStyleBackground::CalcDifference(const nsStyleBackground& aOther) const
{
- if (mBackgroundColor != aOther.mBackgroundColor ||
- mFallbackBackgroundColor != aOther.mFallbackBackgroundColor ||
- mBackgroundInlinePolicy != aOther.mBackgroundInlinePolicy ||
- mImageCount != aOther.mImageCount)
- return NS_STYLE_HINT_VISUAL;
-
- // We checked the image count above.
- NS_FOR_VISIBLE_BACKGROUND_LAYERS_BACK_TO_FRONT(i, this) {
- if (mLayers[i] != aOther.mLayers[i])
- return NS_STYLE_HINT_VISUAL;
- }
-
- return NS_STYLE_HINT_NONE;
+ if ((mBackgroundAttachment == aOther.mBackgroundAttachment) &&
+ (mBackgroundFlags == aOther.mBackgroundFlags) &&
+ (mBackgroundRepeat == aOther.mBackgroundRepeat) &&
+ (mBackgroundColor == aOther.mBackgroundColor) &&
+ (mBackgroundClip == aOther.mBackgroundClip) &&
+ (mBackgroundInlinePolicy == aOther.mBackgroundInlinePolicy) &&
+ (mBackgroundOrigin == aOther.mBackgroundOrigin) &&
+ EqualImages(mBackgroundImage, aOther.mBackgroundImage) &&
+ ((!(mBackgroundFlags & NS_STYLE_BG_X_POSITION_PERCENT) ||
+ (mBackgroundXPosition.mFloat == aOther.mBackgroundXPosition.mFloat)) &&
+ (!(mBackgroundFlags & NS_STYLE_BG_X_POSITION_LENGTH) ||
+ (mBackgroundXPosition.mCoord == aOther.mBackgroundXPosition.mCoord))) &&
+ ((!(mBackgroundFlags & NS_STYLE_BG_Y_POSITION_PERCENT) ||
+ (mBackgroundYPosition.mFloat == aOther.mBackgroundYPosition.mFloat)) &&
+ (!(mBackgroundFlags & NS_STYLE_BG_Y_POSITION_LENGTH) ||
+ (mBackgroundYPosition.mCoord == aOther.mBackgroundYPosition.mCoord))))
+ return NS_STYLE_HINT_NONE;
+ return NS_STYLE_HINT_VISUAL;
}
#ifdef DEBUG
/* static */
nsChangeHint nsStyleBackground::MaxDifference()
{
return NS_STYLE_HINT_VISUAL;
}
#endif
PRBool nsStyleBackground::HasFixedBackground() const
{
- NS_FOR_VISIBLE_BACKGROUND_LAYERS_BACK_TO_FRONT(i, this) {
- const Layer &layer = mLayers[i];
- if (layer.mAttachment == NS_STYLE_BG_ATTACHMENT_FIXED &&
- layer.mImage.mRequest) {
- return PR_TRUE;
- }
- }
- return PR_FALSE;
-}
-
-PRBool nsStyleBackground::IsTransparent() const
-{
- return !BottomLayer().mImage.mRequest && mImageCount == 1 &&
- NS_GET_A(mBackgroundColor) == 0;
-}
-
-void
-nsStyleBackground::Position::SetInitialValues()
-{
- mXPosition.mFloat = 0.0f;
- mYPosition.mFloat = 0.0f;
- mXIsPercent = PR_TRUE;
- mYIsPercent = PR_TRUE;
-}
-
-// Initialize to initial values
-nsStyleBackground::Image::Image()
-{
- SetInitialValues();
-}
-
-nsStyleBackground::Image::~Image()
-{
-}
-
-void nsStyleBackground::Image::SetInitialValues()
-{
- mRequest = nsnull;
- mSpecified = PR_FALSE;
-}
-
-PRBool nsStyleBackground::Image::operator==(const Image& aOther) const
-{
- return mSpecified == aOther.mSpecified &&
- EqualImages(mRequest, aOther.mRequest);
-}
-
-nsStyleBackground::Layer::Layer()
-{
-}
-
-nsStyleBackground::Layer::~Layer()
-{
-}
-
-void
-nsStyleBackground::Layer::SetInitialValues()
-{
- mAttachment = NS_STYLE_BG_ATTACHMENT_SCROLL;
- mClip = NS_STYLE_BG_CLIP_BORDER;
- mOrigin = NS_STYLE_BG_ORIGIN_PADDING;
- mRepeat = NS_STYLE_BG_REPEAT_XY;
- mPosition.SetInitialValues();
- mImage.SetInitialValues();
-}
-
-PRBool nsStyleBackground::Layer::operator==(const Layer& aOther) const
-{
- return mAttachment == aOther.mAttachment &&
- mClip == aOther.mClip &&
- mOrigin == aOther.mOrigin &&
- mRepeat == aOther.mRepeat &&
- mPosition == aOther.mPosition &&
- mImage == aOther.mImage;
+ return mBackgroundAttachment == NS_STYLE_BG_ATTACHMENT_FIXED &&
+ mBackgroundImage;
}
// --------------------
// nsStyleDisplay
//
nsStyleDisplay::nsStyleDisplay()
{
--- a/layout/style/nsStyleStruct.h
+++ b/layout/style/nsStyleStruct.h
@@ -53,17 +53,16 @@
#include "nsFont.h"
#include "nsStyleCoord.h"
#include "nsStyleConsts.h"
#include "nsChangeHint.h"
#include "nsPresContext.h"
#include "nsIPresShell.h"
#include "nsCOMPtr.h"
#include "nsCOMArray.h"
-#include "nsTArray.h"
#include "nsIAtom.h"
#include "nsIURI.h"
#include "nsCSSValue.h"
#include "nsStyleTransformMatrix.h"
class nsIFrame;
class imgIRequest;
@@ -160,132 +159,40 @@ struct nsStyleBackground {
aContext->FreeToShell(sizeof(nsStyleBackground), this);
}
nsChangeHint CalcDifference(const nsStyleBackground& aOther) const;
#ifdef DEBUG
static nsChangeHint MaxDifference();
#endif
- struct Position;
- friend struct Position;
- struct Position {
- typedef union {
- nscoord mCoord; // for lengths
- float mFloat; // for percents
- } PositionCoord;
- PositionCoord mXPosition, mYPosition;
- PRPackedBool mXIsPercent, mYIsPercent;
-
- // Initialize nothing
- Position() {}
-
- // Initialize to initial values
- void SetInitialValues();
-
- PRBool operator==(const Position& aOther) const {
- return mXIsPercent == aOther.mXIsPercent &&
- (mXIsPercent ? (mXPosition.mFloat == aOther.mXPosition.mFloat)
- : (mXPosition.mCoord == aOther.mXPosition.mCoord)) &&
- mYIsPercent == aOther.mYIsPercent &&
- (mYIsPercent ? (mYPosition.mFloat == aOther.mYPosition.mFloat)
- : (mYPosition.mCoord == aOther.mYPosition.mCoord));
- }
- PRBool operator!=(const Position& aOther) const {
- return !(*this == aOther);
- }
- };
-
- /**
- * We represent images as as struct because we need to distinguish the
- * case where the imgIRequest is null because the winning
- * background-image declaration specified no image from the case where
- * the imgIRequest is null because the image that was specified was
- * blocked or missing (e.g., missing file).
- */
- struct Image;
- friend struct Image;
- struct Image {
- nsCOMPtr<imgIRequest> mRequest;
- PRBool mSpecified; // if false, mRequest is guaranteed to be null
-
- // These are not inline so that we can avoid #include "imgIRequest.h"
-
- // Initialize to initial values
- Image();
- ~Image();
- void SetInitialValues();
+ PRUint8 mBackgroundFlags; // [reset] See nsStyleConsts.h
+ PRUint8 mBackgroundAttachment; // [reset] See nsStyleConsts.h
+ PRUint8 mBackgroundClip; // [reset] See nsStyleConsts.h
+ PRUint8 mBackgroundInlinePolicy; // [reset] See nsStyleConsts.h
+ PRUint8 mBackgroundOrigin; // [reset] See nsStyleConsts.h
+ PRUint8 mBackgroundRepeat; // [reset] See nsStyleConsts.h
- // An equality operator that compares the images using URL-equality
- // rather than pointer-equality.
- PRBool operator==(const Image& aOther) const;
- PRBool operator!=(const Image& aOther) const {
- return !(*this == aOther);
- }
- };
-
- struct Layer;
- friend struct Layer;
- struct Layer {
- PRUint8 mAttachment; // [reset] See nsStyleConsts.h
- PRUint8 mClip; // [reset] See nsStyleConsts.h
- PRUint8 mOrigin; // [reset] See nsStyleConsts.h
- PRUint8 mRepeat; // [reset] See nsStyleConsts.h
- Position mPosition; // [reset]
- Image mImage; // [reset]
-
- // Initializes only mImage
- Layer();
- ~Layer();
-
- void SetInitialValues();
-
- // An equality operator that compares the images using URL-equality
- // rather than pointer-equality.
- PRBool operator==(const Layer& aOther) const;
- PRBool operator!=(const Layer& aOther) const {
- return !(*this == aOther);
- }
- };
-
- // The (positive) number of computed values of each property, since
- // the lengths of the lists are independent.
- PRUint32 mAttachmentCount,
- mClipCount,
- mOriginCount,
- mRepeatCount,
- mPositionCount,
- mImageCount;
- // Layers are stored in an array, matching the top-to-bottom order in
- // which they are specified in CSS. The number of layers to be used
- // should come from the background-image property. We create
- // additional |Layer| objects for *any* property, not just
- // background-image. This means that the bottommost layer that
- // callers in layout care about (which is also the one whose
- // background-clip applies to the background-color) may not be last
- // layer. In layers below the bottom layer, properties will be
- // unitialized unless their count, above, indicates that they are
- // present.
- nsAutoTArray<Layer, 1> mLayers;
-
- const Layer& BottomLayer() const { return mLayers[mImageCount - 1]; }
-
- #define NS_FOR_VISIBLE_BACKGROUND_LAYERS_BACK_TO_FRONT(var_, stylebg_) \
- for (PRUint32 var_ = (stylebg_)->mImageCount; var_-- != 0; )
+ // Note: a member of this union is valid IFF the appropriate bit flag
+ // is set in mBackgroundFlags.
+ union {
+ nscoord mCoord;
+ float mFloat;
+ } mBackgroundXPosition, // [reset]
+ mBackgroundYPosition; // [reset]
nscolor mBackgroundColor; // [reset]
- nscolor mFallbackBackgroundColor; // [reset]
-
- // FIXME: This (now background-break in css3-background) should
- // probably move into a different struct so that everything in
- // nsStyleBackground is set by the background shorthand.
- PRUint8 mBackgroundInlinePolicy; // [reset] See nsStyleConsts.h
+ nsCOMPtr<imgIRequest> mBackgroundImage; // [reset]
// True if this background is completely transparent.
- PRBool IsTransparent() const;
+ PRBool IsTransparent() const
+ {
+ return (NS_GET_A(mBackgroundColor) == 0 &&
+ (mBackgroundFlags & NS_STYLE_BG_IMAGE_NONE));
+ }
// We have to take slower codepaths for fixed background attachment,
// but we don't want to do that when there's no image.
// Not inline because it uses an nsCOMPtr<imgIRequest>
// FIXME: Should be in nsStyleStructInlines.h.
PRBool HasFixedBackground() const;
};
--- a/layout/style/test/property_database.js
+++ b/layout/style/test/property_database.js
@@ -67,43 +67,38 @@ var gCSSProperties = {
domProp: "MozAppearance",
inherited: false,
type: CSS_TYPE_LONGHAND,
initial_values: [ "none" ],
other_values: [ "radio", "menulist" ],
invalid_values: []
},
"-moz-background-clip": {
- /*
- * When we rename this to 'background-clip', we also
- * need to rename the values to match the spec.
- */
domProp: "MozBackgroundClip",
inherited: false,
type: CSS_TYPE_LONGHAND,
- /* XXX Need to add support for "content" -- important for symmetry when handling background shorthand */
initial_values: [ "border" ],
- other_values: [ "padding", "border, padding", "padding, padding, padding", "border, border" ],
- invalid_values: [ "content", "margin", "border border" ]
+ other_values: [ "padding" ],
+ invalid_values: [ "content", "margin" ]
},
"-moz-background-inline-policy": {
domProp: "MozBackgroundInlinePolicy",
inherited: false,
type: CSS_TYPE_LONGHAND,
initial_values: [ "continuous" ],
other_values: ["bounding-box", "each-box" ],
invalid_values: []
},
"-moz-background-origin": {
domProp: "MozBackgroundOrigin",
inherited: false,
type: CSS_TYPE_LONGHAND,
initial_values: [ "padding" ],
- other_values: [ "border", "content", "border, padding", "padding, padding, padding", "border, border" ],
- invalid_values: [ "margin", "padding padding" ]
+ other_values: [ "border", "content" ],
+ invalid_values: [ "margin" ]
},
"-moz-binding": {
domProp: "MozBinding",
inherited: false,
type: CSS_TYPE_LONGHAND,
initial_values: [ "none" ],
other_values: [ "url(foo.xml)" ],
invalid_values: []
@@ -608,108 +603,65 @@ var gCSSProperties = {
initial_values: [ "center", "0deg" ],
other_values: [ "center behind", "behind far-right", "left-side", "73deg", "90.1deg", "0.1deg" ],
invalid_values: [ "0deg behind", "behind 0deg", "90deg behind", "behind 90deg" ]
},
"background": {
domProp: "background",
inherited: false,
type: CSS_TYPE_TRUE_SHORTHAND,
- subproperties: [ "background-attachment", "background-color", "background-image", "background-position", "background-repeat", "-moz-background-clip", "-moz-background-origin" ],
+ subproperties: [ "background-attachment", "background-color", "background-image", "background-position", "background-repeat", "-moz-background-clip", "-moz-background-inline-policy", "-moz-background-origin" ],
initial_values: [ "transparent", "none", "repeat", "scroll", "0% 0%", "top left", "left top", "transparent none", "top left none", "left top none", "none left top", "none top left", "none 0% 0%", "transparent none repeat scroll top left", "left top repeat none scroll transparent"],
- other_values: [
- /* without multiple backgrounds */
- "green", "none green repeat scroll left top", "url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAACAAAAAgCAIAAAD8GO2jAAAAKElEQVR42u3NQQ0AAAgEoNP+nTWFDzcoQE1udQQCgUAgEAgEAsGTYAGjxAE/G/Q2tQAAAABJRU5ErkJggg==)", "repeat url('data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAACAAAAAgCAIAAAD8GO2jAAAAKElEQVR42u3NQQ0AAAgEoNP+nTWFDzcoQE1udQQCgUAgEAgEAsGTYAGjxAE/G/Q2tQAAAABJRU5ErkJggg==') transparent left top scroll", "repeat-x", "repeat-y", "no-repeat", "none repeat-y transparent scroll 0% 0%", "fixed", "0% top transparent fixed repeat none", "top", "left", "50% 50%", "center", "bottom right scroll none transparent repeat", "50% transparent", "transparent 50%", "50%",
- /* multiple backgrounds */
- "url(404.png), url(404.png)",
- "url(404.png), url(404.png) transparent",
- "url(404.png), url(404.png) transparent red",
- "repeat-x, fixed, none",
- "0% top url(404.png), url(404.png) 0% top",
- "fixed repeat-y top left url(404.png), repeat-x green",
- /* test cases with clip+origin in the shorthand */
- // This is commented out for now until we change
- // -moz-background-clip to background-clip, -moz-background-origin
- // to background-origin, change their value names to *-box, and add
- // support for content-box on background-clip.
- /*
- "url(404.png) green padding-box",
- "url(404.png) border-box transparent",
- "content-box url(404.png) blue",
- */
- ],
+ other_values: [ "green", "none green repeat scroll left top", "url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAACAAAAAgCAIAAAD8GO2jAAAAKElEQVR42u3NQQ0AAAgEoNP+nTWFDzcoQE1udQQCgUAgEAgEAsGTYAGjxAE/G/Q2tQAAAABJRU5ErkJggg==)", "repeat url('data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAACAAAAAgCAIAAAD8GO2jAAAAKElEQVR42u3NQQ0AAAgEoNP+nTWFDzcoQE1udQQCgUAgEAgEAsGTYAGjxAE/G/Q2tQAAAABJRU5ErkJggg==') transparent left top scroll", "repeat-x", "repeat-y", "no-repeat", "none repeat-y transparent scroll 0% 0%", "fixed", "0% top transparent fixed repeat none", "top", "left", "50% 50%", "center", "bottom right scroll none transparent repeat", "50% transparent", "transparent 50%", "50%" ],
invalid_values: [
/* mixes with keywords have to be in correct order */
"50% left", "top 50%",
/* bug 258080: don't accept background-position separated */
- "left url(404.png) top", "top url(404.png) left",
- /* not allowed to have color in non-bottom layer */
- "url(404.png) transparent, url(404.png)",
- "url(404.png) red, url(404.png)",
- "url(404.png) transparent, url(404.png) transparent",
- "url(404.png) transparent red, url(404.png) transparent red",
- "url(404.png) red, url(404.png) red",
- "url(404.png) rgba(0, 0, 0, 0), url(404.png)",
- "url(404.png) rgb(255, 0, 0), url(404.png)",
- "url(404.png) rgba(0, 0, 0, 0), url(404.png) rgba(0, 0, 0, 0)",
- "url(404.png) rgba(0, 0, 0, 0) rgb(255, 0, 0), url(404.png) rgba(0, 0, 0, 0) rgb(255, 0, 0)",
- "url(404.png) rgb(255, 0, 0), url(404.png) rgb(255, 0, 0)",
+ "left url(404.png) top", "top url(404.png) left"
]
},
"background-attachment": {
domProp: "backgroundAttachment",
inherited: false,
type: CSS_TYPE_LONGHAND,
initial_values: [ "scroll" ],
- other_values: [ "fixed", "scroll,scroll", "fixed, scroll", "scroll, fixed, scroll", "fixed, fixed" ],
+ other_values: [ "fixed" ],
invalid_values: []
},
"background-color": {
domProp: "backgroundColor",
inherited: false,
type: CSS_TYPE_LONGHAND,
- initial_values: [ "transparent", "transparent transparent", "rgba(255, 127, 15, 0)", "hsla(240, 97%, 50%, 0.0)", "rgba(0, 0, 0, 0)", "rgba(255,255,255,-3.7)" ],
- other_values: [ "green", "rgb(255, 0, 128)", "#fc2", "#96ed2a", "black", "rgba(255,255,0,3)", "transparent green", "green transparent", "blue fuchsia", "rgb(3,4,5) hsl(240, 50%, 50%)" ],
+ initial_values: [ "transparent", "rgba(255, 127, 15, 0)", "hsla(240, 97%, 50%, 0.0)", "rgba(0, 0, 0, 0)", "rgba(255,255,255,-3.7)" ],
+ other_values: [ "green", "rgb(255, 0, 128)", "#fc2", "#96ed2a", "black", "rgba(255,255,0,3)" ],
invalid_values: [ "#0", "#00", "#0000", "#00000", "#0000000", "#00000000", "#000000000", "rgb(255.0,0.387,3489)" ]
},
"background-image": {
domProp: "backgroundImage",
inherited: false,
type: CSS_TYPE_LONGHAND,
initial_values: [ "none" ],
- other_values: [ "url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAACAAAAAgCAIAAAD8GO2jAAAAKElEQVR42u3NQQ0AAAgEoNP+nTWFDzcoQE1udQQCgUAgEAgEAsGTYAGjxAE/G/Q2tQAAAABJRU5ErkJggg==)", "url('data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAACAAAAAgCAIAAAD8GO2jAAAAKElEQVR42u3NQQ0AAAgEoNP+nTWFDzcoQE1udQQCgUAgEAgEAsGTYAGjxAE/G/Q2tQAAAABJRU5ErkJggg==')", 'url("data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAACAAAAAgCAIAAAD8GO2jAAAAKElEQVR42u3NQQ0AAAgEoNP+nTWFDzcoQE1udQQCgUAgEAgEAsGTYAGjxAE/G/Q2tQAAAABJRU5ErkJggg==")',
- "none, none",
- "none, none, none, none, none",
- "url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAACAAAAAgCAIAAAD8GO2jAAAAKElEQVR42u3NQQ0AAAgEoNP+nTWFDzcoQE1udQQCgUAgEAgEAsGTYAGjxAE/G/Q2tQAAAABJRU5ErkJggg==), none",
- "none, url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAACAAAAAgCAIAAAD8GO2jAAAAKElEQVR42u3NQQ0AAAgEoNP+nTWFDzcoQE1udQQCgUAgEAgEAsGTYAGjxAE/G/Q2tQAAAABJRU5ErkJggg==), none",
- "url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAACAAAAAgCAIAAAD8GO2jAAAAKElEQVR42u3NQQ0AAAgEoNP+nTWFDzcoQE1udQQCgUAgEAgEAsGTYAGjxAE/G/Q2tQAAAABJRU5ErkJggg==), url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAACAAAAAgCAIAAAD8GO2jAAAAKElEQVR42u3NQQ0AAAgEoNP+nTWFDzcoQE1udQQCgUAgEAgEAsGTYAGjxAE/G/Q2tQAAAABJRU5ErkJggg==)"
- ],
+ other_values: [ "url(data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAACAAAAAgCAIAAAD8GO2jAAAAKElEQVR42u3NQQ0AAAgEoNP+nTWFDzcoQE1udQQCgUAgEAgEAsGTYAGjxAE/G/Q2tQAAAABJRU5ErkJggg==)", "url('data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAACAAAAAgCAIAAAD8GO2jAAAAKElEQVR42u3NQQ0AAAgEoNP+nTWFDzcoQE1udQQCgUAgEAgEAsGTYAGjxAE/G/Q2tQAAAABJRU5ErkJggg==')", 'url("data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAACAAAAAgCAIAAAD8GO2jAAAAKElEQVR42u3NQQ0AAAgEoNP+nTWFDzcoQE1udQQCgUAgEAgEAsGTYAGjxAE/G/Q2tQAAAABJRU5ErkJggg==")', ],
invalid_values: []
},
"background-position": {
domProp: "backgroundPosition",
inherited: false,
type: CSS_TYPE_LONGHAND,
- /* is "0px 0px" an initial value or not? */
initial_values: [ "top left", "left top", "0% 0%", "0% top", "left 0%" ],
- other_values: [ "top", "left", "right", "bottom", "center", "center bottom", "bottom center", "center right", "right center", "center top", "top center", "center left", "left center", "right bottom", "bottom right", "50%", "top left, top left", "top left, top right", "top right, top left", "left top, 0% 0%", "10% 20%, 30%, 40%", "top left, bottom right", "right bottom, left top", "0%", "0px", "30px", "0%, 10%, 20%, 30%", "top, top, top, top, top" ],
+ other_values: [ "top", "left", "right", "bottom", "center", "center bottom", "bottom center", "center right", "right center", "center top", "top center", "center left", "left center", "right bottom", "bottom right", "50%" ],
invalid_values: [ "50% left", "top 50%" ]
},
"background-repeat": {
domProp: "backgroundRepeat",
inherited: false,
type: CSS_TYPE_LONGHAND,
initial_values: [ "repeat" ],
- other_values: [ "repeat-x", "repeat-y", "no-repeat",
- "repeat-x, repeat-x",
- "repeat, no-repeat",
- "repeat-y, no-repeat, repeat-y",
- "repeat, repeat, repeat"
- ],
- invalid_values: [ "repeat repeat" ]
+ other_values: [ "repeat-x", "repeat-y", "no-repeat" ],
+ invalid_values: []
},
"border": {
domProp: "border",
inherited: false,
type: CSS_TYPE_TRUE_SHORTHAND,
subproperties: [ "border-bottom-color", "border-bottom-style", "border-bottom-width", "border-left-color", "border-left-style", "border-left-width", "border-right-color", "border-right-style", "border-right-width", "border-top-color", "border-top-style", "border-top-width" ],
initial_values: [ "none", "medium", "currentColor", "thin", "none medium currentcolor" ],
other_values: [ "solid", "medium solid", "green solid", "10px solid", "thick solid" ],
--- a/layout/style/test/test_selectors.html
+++ b/layout/style/test/test_selectors.html
@@ -34,32 +34,28 @@ function run() {
/*
* selector: the selector to test
* body_contents: what to set the body's innerHTML to
* match_fn: a function that, given the document object into which
* body_contents has been inserted, produces an array of nodes that
* should match selector
* notmatch_fn: likewise, but for nodes that should not match
- * namespaces (optional): @namespace rules to be included in the sheet
*/
- function test_selector_in_html(selector, body_contents, match_fn, notmatch_fn, namespaces)
+ function test_selector_in_html(selector, body_contents, match_fn, notmatch_fn)
{
var zi = ++gCounter;
if (typeof(body_contents) == "string") {
ifdoc.body.innerHTML = body_contents;
} else {
// It's a function.
ifdoc.body.innerHTML = "";
body_contents(ifdoc.body);
}
- if (!namespaces) {
- namespaces = "";
- }
- style_text.data = namespaces + selector + "{ z-index: " + zi + " }";
+ style_text.data = selector + "{ z-index: " + zi + " }";
var should_match = match_fn(ifdoc);
var should_not_match = notmatch_fn(ifdoc);
if (should_match.length + should_not_match.length == 0) {
ok(false, "nothing to check");
}
for (var i = 0; i < should_match.length; ++i) {
var e = should_match[i];
@@ -72,54 +68,41 @@ function run() {
"element in " + body_contents + " did not match " + selector);
}
// Now, since we're here, may as well make sure serialization
// works correctly. It need not produce the exact same text,
// but it should produce a selector that matches the same
// elements.
zi = ++gCounter;
- var idx = style_text.parentNode.sheet.cssRules.length - 1;
- if (namespaces == "") {
- is(idx, 0, "unexpected rule index");
- }
- var ser1 = style_text.parentNode.sheet.cssRules[idx].selectorText;
- style_text.data = namespaces + ser1 + "{ z-index: " + zi + " }";
+ var ser1 = style_text.parentNode.sheet.cssRules[0].selectorText;
+ style_text.data = ser1 + "{ z-index: " + zi + " }";
for (var i = 0; i < should_match.length; ++i) {
var e = should_match[i];
is(ifwin.getComputedStyle(e, "").zIndex, zi,
"element in " + body_contents + " matched " + ser1 +
" which is the reserialization of " + selector);
}
for (var i = 0; i < should_not_match.length; ++i) {
var e = should_not_match[i];
is(ifwin.getComputedStyle(e, "").zIndex, "auto",
"element in " + body_contents + " did not match " + ser1 +
" which is the reserialization of " + selector);
}
// But when we serialize the serialized result, we should get
// the same text.
- var ser2 = style_text.parentNode.sheet.cssRules[idx].selectorText;
+ var ser2 = style_text.parentNode.sheet.cssRules[0].selectorText;
is(ser2, ser1, "parse+serialize of selector \"" + selector +
"\" is idempotent");
ifdoc.body.innerHTML = "";
style_text.data = "";
}
- function should_serialize_to(selector, serialization)
- {
- style_text.data = selector + "{ z-index: 0 }";
- is(style_text.parentNode.sheet.cssRules[0].selectorText,
- serialization,
- "selector '" + selector + "' should serialize to '" +
- serialization + "'.");
- }
-
function test_parseable(selector)
{
var zi = ++gCounter;
ifdoc.body.innerHTML = "<p></p>";
style_text.data = "p, " + selector + "{ z-index: " + zi + " }";
var should_match = ifdoc.getElementsByTagName("p")[0];
is(ifwin.getComputedStyle(should_match, "").zIndex, zi,
"selector " + selector + " was parsed");
@@ -471,86 +454,16 @@ function run() {
pdaset([2], [2], []));
test_selector_in_html(":nth-of-type(2n-0)", mixed_elements,
pdaset([2], [2], []),
pdaset([1, 3, 4], [1], [1, 2]));
test_selector_in_html(":nth-last-of-type(even)", mixed_elements,
pdaset([2], [1], []),
pdaset([1, 3, 4], [2], [1, 2]));
- // Test greediness of descendant combinators.
- var four_children="<div id='a'><div id='b'><div id='c'><div id='d'><\/div><\/div><\/div><\/div>";
- test_selector_in_html("#a > div div", four_children,
- idset(["c", "d"]), idset(["a", "b"]));
- test_selector_in_html("#a > #b div", four_children,
- idset(["c", "d"]), idset(["a", "b"]));
- test_selector_in_html("#a div > div", four_children,
- idset(["c", "d"]), idset(["a", "b"]));
- test_selector_in_html("#a #b > div", four_children,
- idset(["c"]), idset(["a", "b", "d"]));
- test_selector_in_html("#a > #b div", four_children,
- idset(["c", "d"]), idset(["a", "b"]));
- test_selector_in_html("#a #c > div", four_children,
- idset(["d"]), idset(["a", "b", "c"]));
- test_selector_in_html("#a > #c div", four_children,
- idset([]), idset(["a", "b", "c", "d"]));
-
- // Test serialization of pseudo-elements.
- should_serialize_to("p:first-letter", "p:first-letter");
- should_serialize_to("div>p:first-letter", "div > p:first-letter");
- should_serialize_to("span +div:first-line", "span + div:first-line");
-
- // Test default namespaces, including inside :not().
- var html_default_ns = "@namespace url(http://www.w3.org/1999/xhtml);";
- var html_ns = "@namespace html url(http://www.w3.org/1999/xhtml);";
- var xul_default_ns = "@namespace url(http://www.mozilla.org/keymaster/gatekeeper/there.is.only.xul);";
- var single_a = "<a id='a' href='data:text/plain,this_better_be_unvisited'></a>";
- var set_single = idset(['a']);
- var empty_set = idset([]);
- test_selector_in_html("a", single_a, set_single, empty_set,
- html_default_ns);
- test_selector_in_html("a", single_a, empty_set, set_single,
- xul_default_ns);
- test_selector_in_html("*|a", single_a, set_single, empty_set,
- xul_default_ns);
- test_selector_in_html("html|a", single_a, set_single, empty_set,
- xul_default_ns + html_ns);
- // Type selectors inside :not() bring in default namespaces, but
- // non-type selectors don't.
- test_selector_in_html("*|a:not(*)", single_a, set_single, empty_set,
- xul_default_ns);
- test_selector_in_html("*|a:not(a)", single_a, set_single, empty_set,
- xul_default_ns);
- test_selector_in_html("*|a:not(*|*)", single_a, empty_set, set_single,
- xul_default_ns);
- test_selector_in_html("*|a:not(*|a)", single_a, empty_set, set_single,
- xul_default_ns);
- test_selector_in_html("*|a:not(:link)", single_a + "<a id='b'></a>",
- idset(["b"]), set_single,
- xul_default_ns);
- test_selector_in_html("*|a:not(:visited)", single_a + "<a id='b'></a>",
- idset(["a", "b"]), empty_set,
- xul_default_ns);
- test_selector_in_html("*|a:not(html|*)", single_a, empty_set, set_single,
- xul_default_ns + html_ns);
- test_selector_in_html("*|a:not(html|a)", single_a, empty_set, set_single,
- xul_default_ns + html_ns);
- test_selector_in_html("*|a:not(|*)", single_a, set_single, empty_set,
- xul_default_ns + html_ns);
- test_selector_in_html("*|a:not(|a)", single_a, set_single, empty_set,
- xul_default_ns + html_ns);
- test_selector_in_html("html|a:not(|*)", single_a, set_single, empty_set,
- xul_default_ns + html_ns);
- test_selector_in_html("html|a:not(|a)", single_a, set_single, empty_set,
- xul_default_ns + html_ns);
- test_selector_in_html("html|a:not(*|*)", single_a, empty_set, set_single,
- xul_default_ns + html_ns);
- test_selector_in_html("html|a:not(*|a)", single_a, empty_set, set_single,
- xul_default_ns + html_ns);
-
SimpleTest.finish();
}
</script>
</pre>
</body>
</html>
--- a/layout/style/test/test_shorthand_property_getters.html
+++ b/layout/style/test/test_shorthand_property_getters.html
@@ -101,31 +101,21 @@ is(e.style.cssText, "border-style: ridge
// shorthand syntax are present.
e.setAttribute("style", "font: medium serif");
isnot(e.style.font, "", "should have font shorthand");
e.setAttribute("style", "font: medium serif; font-size-adjust: 0.45");
is(e.style.font, "", "should not have font shorthand");
e.setAttribute("style", "font: medium serif; font-stretch: condensed");
is(e.style.font, "", "should not have font shorthand");
-// For background, we can only express the value as a shorthand if
-// origin and clip are both their default, or if they're both the same.
-// ... or at least we will once we support them in the shorthand.
e.setAttribute("style", "background: red");
isnot(e.style.background, "", "should have background shorthand");
e.setAttribute("style", "background: red; -moz-background-origin: border");
-is(e.style.background, "", "should not have background shorthand (origin:border)");
+is(e.style.background, "", "should not have background shorthand");
e.setAttribute("style", "background: red; -moz-background-clip: padding");
-is(e.style.background, "", "should not have background shorthand (clip:padding)");
-e.setAttribute("style", "background: red; -moz-background-origin: content");
-is(e.style.background, "", "should not have background shorthand (origin:content)");
-// -moz-background-clip:content not yet supported
-//e.setAttribute("style", "background: red; -moz-background-clip: content");
-//is(e.style.background, "", "should not have background shorthand (clip:content)");
-//e.setAttribute("style", "background: red; -moz-background-clip: content; -moz-background-origin: content;");
-//isnot(e.style.background, "", "should have background shorthand (clip:content;origin:content)");
+is(e.style.background, "", "should not have background shorthand");
e.setAttribute("style", "background: red; -moz-background-inline-policy: each-box");
-isnot(e.style.background, "", "should have background shorthand (-moz-background-inline-policy not relevant)");
+is(e.style.background, "", "should not have background shorthand");
</script>
</pre>
</body>
</html>
--- a/layout/style/test/test_system_font_serialization.html
+++ b/layout/style/test/test_system_font_serialization.html
@@ -42,16 +42,12 @@ is(e.style.font, "", "font getter should
e.setAttribute("style", "font: menu; font-weight: -moz-use-system-font");
is(e.style.cssText, "font: menu;", "serialize system font alone");
is(e.style.font, "menu", "font getter returns value");
e.setAttribute("style", "font: menu; font-weight: -moz-use-system-font ! important");
is(e.style.cssText, "font: menu; font-weight: -moz-use-system-font ! important;", "serialize system font and subproperty that is important");
is(e.style.font, "", "font getter returns nothing");
-e.setAttribute("style", "font: inherit; font-family: Helvetica;");
-is(e.style.cssText, "font-style: inherit; font-variant: inherit; font-weight: inherit; font-size: inherit; line-height: inherit; font-size-adjust: inherit; font-stretch: inherit; font-family: Helvetica;", "don't serialize system font for font:inherit");
-is(e.style.font, "", "font getter returns nothing");
-
</script>
</pre>
</body>
</html>
--- a/layout/tables/nsTablePainter.cpp
+++ b/layout/tables/nsTablePainter.cpp
@@ -192,25 +192,17 @@ TableBackgroundPainter::TableBackgroundD
SetFrame(aFrame);
SetData();
}
inline PRBool
TableBackgroundPainter::TableBackgroundData::ShouldSetBCBorder()
{
/* we only need accurate border data when positioning background images*/
- if (!mBackground) {
- return PR_FALSE;
- }
-
- NS_FOR_VISIBLE_BACKGROUND_LAYERS_BACK_TO_FRONT(i, mBackground) {
- if (mBackground->mLayers[i].mImage.mRequest)
- return PR_TRUE;
- }
- return PR_FALSE;
+ return mBackground && !(mBackground->mBackgroundFlags & NS_STYLE_BG_IMAGE_NONE);
}
nsresult
TableBackgroundPainter::TableBackgroundData::SetBCBorder(nsMargin& aBorder,
TableBackgroundPainter* aPainter)
{
NS_PRECONDITION(aPainter, "null painter");
if (!mSynthBorder) {
--- a/layout/xul/base/src/tree/src/nsTreeBodyFrame.cpp
+++ b/layout/xul/base/src/tree/src/nsTreeBodyFrame.cpp
@@ -4109,19 +4109,17 @@ nsTreeBodyFrame::ScrollInternal(const Sc
return NS_OK;
}
mTopRowIndex += delta;
// See if we have a transparent background or a background image.
// If we do, then we cannot blit.
const nsStyleBackground* background = GetStyleBackground();
- if (background->BottomLayer().mImage.mRequest ||
- background->mImageCount > 1 ||
- NS_GET_A(background->mBackgroundColor) < 255 ||
+ if (background->mBackgroundImage || background->IsTransparent() ||
PR_ABS(delta)*mRowHeight >= mRect.height) {
Invalidate();
} else {
nsIWidget* widget = nsLeafBoxFrame::GetView()->GetWidget();
if (widget) {
nscoord rowHeightAsPixels =
PresContext()->AppUnitsToDevPixels(mRowHeight);
widget->Scroll(0, -delta*rowHeightAsPixels, nsnull);
@@ -4146,22 +4144,19 @@ nsTreeBodyFrame::ScrollHorzInternal(cons
nsRect bounds = aParts.mColumnsFrame->GetRect();
if (aPosition > (mHorzWidth - bounds.width))
aPosition = mHorzWidth - bounds.width;
PRInt32 delta = aPosition - mHorzPosition;
mHorzPosition = aPosition;
- // See if we have a transparent background or a background image.
- // If we do, then we cannot blit.
+ // See if we have a background image. If we do, then we cannot blit.
const nsStyleBackground* background = GetStyleBackground();
- if (background->BottomLayer().mImage.mRequest ||
- background->mImageCount > 1 ||
- NS_GET_A(background->mBackgroundColor) < 255 ||
+ if (background->mBackgroundImage || background->IsTransparent() ||
PR_ABS(delta) >= mRect.width) {
Invalidate();
} else {
nsIWidget* widget = nsLeafBoxFrame::GetView()->GetWidget();
if (widget) {
widget->Scroll(PresContext()->AppUnitsToDevPixels(-delta), 0, nsnull);
}
}
--- a/widget/src/gtk2/nsScreenManagerGtk.cpp
+++ b/widget/src/gtk2/nsScreenManagerGtk.cpp
@@ -192,22 +192,22 @@ nsScreenManagerGtk :: Init()
_XnrmQueryScreens_fn _XnrmQueryScreens = (_XnrmQueryScreens_fn)
PR_FindFunctionSymbol(mXineramalib, "XineramaQueryScreens");
// get the number of screens via xinerama
if (_XnrmIsActive && _XnrmQueryScreens &&
_XnrmIsActive(GDK_DISPLAY())) {
screenInfo = _XnrmQueryScreens(GDK_DISPLAY(), &numScreens);
-
- // remember for the destructor, if we are really working with Xinerama
- mXineramaIsActive = numScreens > 0;
}
}
+ // remember for the destructor, if we are really working with Xinerama
+ mXineramaIsActive = numScreens > 0;
+
// screenInfo == NULL if either Xinerama couldn't be loaded or
// isn't running on the current display
if (!screenInfo || numScreens == 1) {
numScreens = 1;
#endif
nsRefPtr<nsScreenGtk> screen;
if (mCachedScreenArray.Count() > 0) {
--- a/xpcom/glue/nsTArray.h
+++ b/xpcom/glue/nsTArray.h
@@ -680,29 +680,16 @@ class nsTArray : public nsTArray_base {
// @param newLen The desired length of this array.
void TruncateLength(size_type newLen) {
size_type oldLen = Length();
NS_ABORT_IF_FALSE(newLen <= oldLen,
"caller should use SetLength instead");
RemoveElementsAt(newLen, oldLen - newLen);
}
- // This method ensures that the array has length at least the given
- // length. If the current length is shorter than the given length,
- // then new elements will be constructed using elem_type's default
- // constructor.
- // @param minLen The desired minimum length of this array.
- // @return True if the operation succeeded; false otherwise.
- PRBool EnsureLengthAtLeast(size_type minLen) {
- size_type oldLen = Length();
- if (minLen > oldLen) {
- return InsertElementsAt(oldLen, minLen - oldLen) != nsnull;
- }
- }
-
// This method inserts elements into the array, constructing
// them using elem_type's default constructor.
// @param index the place to insert the new elements. This must be no
// greater than the current length of the array.
// @param count the number of elements to insert
elem_type *InsertElementsAt(index_type index, size_type count) {
if (!nsTArray_base::InsertSlotsAt(index, count, sizeof(elem_type))) {
return nsnull;