Bug 812822 part 1: Add flag 'eSkipFlexItemStyleFixup' to let our nsStyleContext creation functions skip the flex-item-specific chunk of ApplyStyleFixups(). r=bz
authorDaniel Holbert <dholbert@cs.stanford.edu>
Wed, 20 Feb 2013 23:34:58 -0800
changeset 122521 1ac9186392e6c3391d696cebc5981ffdaaad282a
parent 122520 393bed39e9abea9d16eb6ed22b22b68b71d754da
child 122522 4caff5d7a8f0e937b31aca57b1642a00effa5e1d
push id24342
push userryanvm@gmail.com
push dateThu, 21 Feb 2013 13:05:06 +0000
treeherdermozilla-central@702d2814efbf [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersbz
bugs812822
milestone22.0a1
first release with
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
last release without
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
Bug 812822 part 1: Add flag 'eSkipFlexItemStyleFixup' to let our nsStyleContext creation functions skip the flex-item-specific chunk of ApplyStyleFixups(). r=bz
layout/style/nsStyleContext.cpp
layout/style/nsStyleContext.h
layout/style/nsStyleSet.cpp
layout/style/nsStyleSet.h
--- a/layout/style/nsStyleContext.cpp
+++ b/layout/style/nsStyleContext.cpp
@@ -29,17 +29,18 @@
 using namespace mozilla;
 
 //----------------------------------------------------------------------
 
 
 nsStyleContext::nsStyleContext(nsStyleContext* aParent,
                                nsIAtom* aPseudoTag,
                                nsCSSPseudoElements::Type aPseudoType,
-                               nsRuleNode* aRuleNode)
+                               nsRuleNode* aRuleNode,
+                               bool aSkipFlexItemStyleFixup)
   : mParent(aParent),
     mChild(nullptr),
     mEmptyChild(nullptr),
     mPseudoTag(aPseudoTag),
     mRuleNode(aRuleNode),
     mAllocations(nullptr),
     mCachedResetData(nullptr),
     mBits(((uint32_t)aPseudoType) << NS_STYLE_CONTEXT_TYPE_SHIFT),
@@ -65,17 +66,17 @@ nsStyleContext::nsStyleContext(nsStyleCo
       r2 = r2->GetParent();
     NS_ASSERTION(r1 == r2, "must be in the same rule tree as parent");
 #endif
   }
 
   mRuleNode->AddRef();
   mRuleNode->SetUsedDirectly(); // before ApplyStyleFixups()!
 
-  ApplyStyleFixups();
+  ApplyStyleFixups(aSkipFlexItemStyleFixup);
 
   #define eStyleStruct_LastItem (nsStyleStructID_Length - 1)
   NS_ASSERTION(NS_STYLE_INHERIT_MASK & NS_STYLE_INHERIT_BIT(LastItem),
                "NS_STYLE_INHERIT_MASK must be bigger, and other bits shifted");
   #undef eStyleStruct_LastItem
 }
 
 nsStyleContext::~nsStyleContext()
@@ -288,17 +289,17 @@ nsStyleContext::SetStyle(nsStyleStructID
     dataSlot = &mCachedInheritedData.mStyleStructs[aSID];
   }
   NS_ASSERTION(!*dataSlot || (mBits & nsCachedStyleData::GetBitForSID(aSID)),
                "Going to leak style data");
   *dataSlot = aStruct;
 }
 
 void
-nsStyleContext::ApplyStyleFixups()
+nsStyleContext::ApplyStyleFixups(bool aSkipFlexItemStyleFixup)
 {
   // See if we have any text decorations.
   // First see if our parent has text decorations.  If our parent does, then we inherit the bit.
   if (mParent && mParent->HasTextDecorationLines()) {
     mBits |= NS_STYLE_HAS_TEXT_DECORATION_LINES;
   } else {
     // We might have defined a decoration.
     const nsStyleTextReset* text = StyleTextReset();
@@ -357,17 +358,17 @@ nsStyleContext::ApplyStyleFixups()
   }
 
   // Adjust the "display" values of flex items (but not for raw text,
   // placeholders, or table-parts). CSS3 Flexbox section 4 says:
   //   # The computed 'display' of a flex item is determined
   //   # by applying the table in CSS 2.1 Chapter 9.7.
   // ...which converts inline-level elements to their block-level equivalents.
 #ifdef MOZ_FLEXBOX
-  if (mParent) {
+  if (!aSkipFlexItemStyleFixup && mParent) {
     const nsStyleDisplay* parentDisp = mParent->StyleDisplay();
     if ((parentDisp->mDisplay == NS_STYLE_DISPLAY_FLEX ||
          parentDisp->mDisplay == NS_STYLE_DISPLAY_INLINE_FLEX) &&
         GetPseudo() != nsCSSAnonBoxes::mozNonElement) {
       uint8_t displayVal = disp->mDisplay;
       // Skip table parts.
       // NOTE: This list needs to be kept in sync with
       // nsCSSFrameConstructor.cpp's "sDisplayData" array -- specifically,
@@ -711,21 +712,23 @@ nsStyleContext::Destroy()
   // instead. Don't call the global operator delete.
   presContext->PresShell()->FreeByObjectID(nsPresArena::nsStyleContext_id, this);
 }
 
 already_AddRefed<nsStyleContext>
 NS_NewStyleContext(nsStyleContext* aParentContext,
                    nsIAtom* aPseudoTag,
                    nsCSSPseudoElements::Type aPseudoType,
-                   nsRuleNode* aRuleNode)
+                   nsRuleNode* aRuleNode,
+                   bool aSkipFlexItemStyleFixup)
 {
   nsStyleContext* context =
     new (aRuleNode->PresContext())
-      nsStyleContext(aParentContext, aPseudoTag, aPseudoType, aRuleNode);
+    nsStyleContext(aParentContext, aPseudoTag, aPseudoType, aRuleNode,
+                   aSkipFlexItemStyleFixup);
   context->AddRef();
   return context;
 }
 
 static inline void
 ExtractAnimationValue(nsCSSProperty aProperty,
                       nsStyleContext* aStyleContext,
                       nsStyleAnimation::Value& aResult)
--- a/layout/style/nsStyleContext.h
+++ b/layout/style/nsStyleContext.h
@@ -51,20 +51,25 @@ public:
    * @param aPseudoTag  The pseudo-element or anonymous box for which
    *                    this style context represents style.  Null if
    *                    this style context is for a normal DOM element.
    * @param aPseudoType  Must match aPseudoTag.
    * @param aRuleNode  A rule node representing the ordered sequence of
    *                   rules that any element, pseudo-element, or
    *                   anonymous box that this style context is for
    *                   matches.  See |nsRuleNode| and |nsIStyleRule|.
+   * @param aSkipFlexItemStyleFixup
+   *                 If set, this flag indicates that we should skip
+   *                 the chunk of ApplyStyleFixups() that modifies flex
+   *                 items' display values.
    */
   nsStyleContext(nsStyleContext* aParent, nsIAtom* aPseudoTag,
                  nsCSSPseudoElements::Type aPseudoType,
-                 nsRuleNode* aRuleNode);
+                 nsRuleNode* aRuleNode,
+                 bool aSkipFlexItemStyleFixup);
   ~nsStyleContext();
 
   void* operator new(size_t sz, nsPresContext* aPresContext) CPP_THROW_NEW;
   void Destroy();
 
   nsrefcnt AddRef() {
     if (mRefCnt == UINT32_MAX) {
       NS_WARNING("refcount overflow, leaking object");
@@ -336,17 +341,17 @@ public:
 #ifdef DEBUG
   void List(FILE* out, int32_t aIndent);
 #endif
 
 protected:
   void AddChild(nsStyleContext* aChild);
   void RemoveChild(nsStyleContext* aChild);
 
-  void ApplyStyleFixups();
+  void ApplyStyleFixups(bool aSkipFlexItemStyleFixup);
 
   void FreeAllocations(nsPresContext* aPresContext);
 
   // Helper function that GetStyleData and GetUniqueStyleData use.  Only
   // returns the structs we cache ourselves; never consults the ruletree.
   inline const void* GetCachedStyleData(nsStyleStructID aSID);
 
   // Helper functions for GetStyle* and PeekStyle*
@@ -429,10 +434,11 @@ protected:
                                  // parent context or owned by mRuleNode.
   uint32_t                mRefCnt;
 };
 
 already_AddRefed<nsStyleContext>
 NS_NewStyleContext(nsStyleContext* aParentContext,
                    nsIAtom* aPseudoTag,
                    nsCSSPseudoElements::Type aPseudoType,
-                   nsRuleNode* aRuleNode);
+                   nsRuleNode* aRuleNode,
+                   bool aSkipFlexItemStyleFixup);
 #endif
--- a/layout/style/nsStyleSet.cpp
+++ b/layout/style/nsStyleSet.cpp
@@ -762,23 +762,24 @@ nsStyleSet::GetContext(nsStyleContext* a
   if (result)
     fprintf(stdout, "--- SharedSC %d ---\n", ++gSharedCount);
   else
     fprintf(stdout, "+++ NewSC %d +++\n", ++gNewCount);
 #endif
 
   if (!result) {
     result = NS_NewStyleContext(aParentContext, aPseudoTag, aPseudoType,
-                                aRuleNode);
+                                aRuleNode, aFlags & eSkipFlexItemStyleFixup);
     if (!result)
       return nullptr;
     if (aVisitedRuleNode) {
       nsRefPtr<nsStyleContext> resultIfVisited =
         NS_NewStyleContext(parentIfVisited, aPseudoTag, aPseudoType,
-                           aVisitedRuleNode);
+                           aVisitedRuleNode,
+                           aFlags & eSkipFlexItemStyleFixup);
       if (!resultIfVisited) {
         return nullptr;
       }
       if (!parentIfVisited) {
         mRoots.AppendElement(resultIfVisited);
       }
       resultIfVisited->SetIsStyleIfVisited();
       result->SetStyleIfVisited(resultIfVisited.forget());
--- a/layout/style/nsStyleSet.h
+++ b/layout/style/nsStyleSet.h
@@ -359,17 +359,24 @@ class nsStyleSet
 
   /**
    * Bit-flags that can be passed to GetContext() in its parameter 'aFlags'.
    */
   enum {
     eNoFlags =          0,
     eIsLink =           1 << 0,
     eIsVisitedLink =    1 << 1,
-    eDoAnimation =      1 << 2
+    eDoAnimation =      1 << 2,
+
+    // Indicates that we should skip the flex-item-specific chunk of
+    // ApplyStyleFixups().  This is useful if our parent has "display: flex"
+    // but we can tell it's not going to actually be a flex container (e.g. if
+    // it's the outer frame of a button widget, and we're the inline frame for
+    // the button's label).
+    eSkipFlexItemStyleFixup = 1 << 3
   };
 
   already_AddRefed<nsStyleContext>
   GetContext(nsStyleContext* aParentContext,
              nsRuleNode* aRuleNode,
              nsRuleNode* aVisitedRuleNode,
              nsIAtom* aPseudoTag,
              nsCSSPseudoElements::Type aPseudoType,