1 /* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
2 /* ***** BEGIN LICENSE BLOCK *****
3 * Version: MPL 1.1/GPL 2.0/LGPL 2.1
5 * The contents of this file are subject to the Mozilla Public License Version
6 * 1.1 (the "License"); you may not use this file except in compliance with
7 * the License. You may obtain a copy of the License at
8 * http://www.mozilla.org/MPL/
10 * Software distributed under the License is distributed on an "AS IS" basis,
11 * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
12 * for the specific language governing rights and limitations under the
15 * The Original Code is Mozilla Communicator client code.
17 * The Initial Developer of the Original Code is
18 * Netscape Communications Corporation.
19 * Portions created by the Initial Developer are Copyright (C) 1998
20 * the Initial Developer. All Rights Reserved.
23 * Original Author: David W. Hyatt (hyatt@netscape.com)
24 * L. David Baron <dbaron@dbaron.org>
26 * Alternatively, the contents of this file may be used under the terms of
27 * either of the GNU General Public License Version 2 or later (the "GPL"),
28 * or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
29 * in which case the provisions of the GPL or the LGPL are applicable instead
30 * of those above. If you wish to allow use of your version of this file only
31 * under the terms of either the GPL or the LGPL, and not to allow others to
32 * use your version of this file under the terms of the MPL, indicate your
33 * decision by deleting the provisions above and replace them with the notice
34 * and other provisions required by the GPL or the LGPL. If you do not delete
35 * the provisions above, a recipient may use your version of this file under
36 * the terms of any one of the MPL, the GPL or the LGPL.
38 * ***** END LICENSE BLOCK ***** */
41 * a node in the lexicographic tree of rules that match an element,
42 * responsible for converting the rules' information into computed style
45 #ifndef nsRuleNode_h___
46 #define nsRuleNode_h___
48 #include "nsPresContext.h"
49 #include "nsStyleStruct.h"
53 class nsILanguageAtomService
;
57 struct nsCSSValueList
;
58 // Copy of typedef that's in nsCSSStruct.h, for compilation speed.
59 typedef nsCSSStruct nsRuleDataStruct
;
61 struct nsRuleDataFont
;
67 struct nsInheritedStyleData
70 #define STYLE_STRUCT_INHERITED(name, checkdata_cb, ctor_args) \
71 nsStyle##name * m##name##Data;
72 #define STYLE_STRUCT_RESET(name, checkdata_cb, ctor_args)
74 #include "nsStyleStructList.h"
76 #undef STYLE_STRUCT_INHERITED
77 #undef STYLE_STRUCT_RESET
79 void* operator new(size_t sz
, nsPresContext
* aContext
) CPP_THROW_NEW
{
80 return aContext
->AllocateFromShell(sz
);
83 void DestroyStructs(PRUint32 aBits
, nsPresContext
* aContext
) {
84 #define STYLE_STRUCT_INHERITED(name, checkdata_cb, ctor_args) \
85 if (m##name##Data && !(aBits & NS_STYLE_INHERIT_BIT(name))) \
86 m##name##Data->Destroy(aContext);
87 #define STYLE_STRUCT_RESET(name, checkdata_cb, ctor_args)
89 #include "nsStyleStructList.h"
91 #undef STYLE_STRUCT_INHERITED
92 #undef STYLE_STRUCT_RESET
95 void Destroy(PRUint32 aBits
, nsPresContext
* aContext
) {
96 DestroyStructs(aBits
, aContext
);
97 aContext
->FreeToShell(sizeof(nsInheritedStyleData
), this);
100 nsInheritedStyleData() {
101 #define STYLE_STRUCT_INHERITED(name, checkdata_cb, ctor_args) \
102 m##name##Data = nsnull;
103 #define STYLE_STRUCT_RESET(name, checkdata_cb, ctor_args)
105 #include "nsStyleStructList.h"
107 #undef STYLE_STRUCT_INHERITED
108 #undef STYLE_STRUCT_RESET
113 struct nsResetStyleData
117 #define STYLE_STRUCT_RESET(name, checkdata_cb, ctor_args) \
118 m##name##Data = nsnull;
119 #define STYLE_STRUCT_INHERITED(name, checkdata_cb, ctor_args)
121 #include "nsStyleStructList.h"
123 #undef STYLE_STRUCT_RESET
124 #undef STYLE_STRUCT_INHERITED
127 void* operator new(size_t sz
, nsPresContext
* aContext
) CPP_THROW_NEW
{
128 return aContext
->AllocateFromShell(sz
);
131 void Destroy(PRUint32 aBits
, nsPresContext
* aContext
) {
132 #define STYLE_STRUCT_RESET(name, checkdata_cb, ctor_args) \
133 if (m##name##Data && !(aBits & NS_STYLE_INHERIT_BIT(name))) \
134 m##name##Data->Destroy(aContext);
135 #define STYLE_STRUCT_INHERITED(name, checkdata_cb, ctor_args)
137 #include "nsStyleStructList.h"
139 #undef STYLE_STRUCT_RESET
140 #undef STYLE_STRUCT_INHERITED
142 aContext
->FreeToShell(sizeof(nsResetStyleData
), this);
145 #define STYLE_STRUCT_RESET(name, checkdata_cb, ctor_args) \
146 nsStyle##name * m##name##Data;
147 #define STYLE_STRUCT_INHERITED(name, checkdata_cb, ctor_args)
149 #include "nsStyleStructList.h"
151 #undef STYLE_STRUCT_RESET
152 #undef STYLE_STRUCT_INHERITED
156 struct nsCachedStyleData
158 struct StyleStructInfo
{
159 ptrdiff_t mCachedStyleDataOffset
;
160 ptrdiff_t mInheritResetOffset
;
164 static StyleStructInfo gInfo
[];
166 nsInheritedStyleData
* mInheritedData
;
167 nsResetStyleData
* mResetData
;
169 static PRBool
IsReset(const nsStyleStructID
& aSID
) {
170 return gInfo
[aSID
].mIsReset
;
173 static PRUint32
GetBitForSID(const nsStyleStructID
& aSID
) {
177 void* NS_FASTCALL
GetStyleData(const nsStyleStructID
& aSID
) {
178 // Each struct is stored at this.m##type##Data->m##name##Data where
179 // |type| is either Inherit or Reset, and |name| is the name of the
180 // style struct. The |gInfo| stores the offset of the appropriate
181 // m##type##Data for the struct within nsCachedStyleData (|this|)
182 // and the offset of the appropriate m##name##Data within the
183 // m##type##Data. Note that if we don't have any reset structs,
184 // then mResetData is null, and likewise for mInheritedData. This
185 // saves us from having to go through the long if-else cascade into
186 // which most compilers will turn a case statement.
188 // NOTE: nsStyleContext::SetStyle works roughly the same way.
190 const StyleStructInfo
& info
= gInfo
[aSID
];
192 // Get either &mInheritedData or &mResetData.
193 char* resetOrInheritSlot
= reinterpret_cast<char*>(this) + info
.mCachedStyleDataOffset
;
195 // Get either mInheritedData or mResetData.
196 char* resetOrInherit
= reinterpret_cast<char*>(*reinterpret_cast<void**>(resetOrInheritSlot
));
199 if (resetOrInherit
) {
200 // If we have the mInheritedData or mResetData, then we might have
201 // the struct, so get it.
202 char* dataSlot
= resetOrInherit
+ info
.mInheritResetOffset
;
203 data
= *reinterpret_cast<void**>(dataSlot
);
208 // Typesafe and faster versions of the above
209 #define STYLE_STRUCT_INHERITED(name_, checkdata_cb_, ctor_args_) \
210 nsStyle##name_ * NS_FASTCALL GetStyle##name_ () { \
211 return mInheritedData ? mInheritedData->m##name_##Data : nsnull; \
213 #define STYLE_STRUCT_RESET(name_, checkdata_cb_, ctor_args_) \
214 nsStyle##name_ * NS_FASTCALL GetStyle##name_ () { \
215 return mResetData ? mResetData->m##name_##Data : nsnull; \
217 #include "nsStyleStructList.h"
218 #undef STYLE_STRUCT_RESET
219 #undef STYLE_STRUCT_INHERITED
221 void Destroy(PRUint32 aBits
, nsPresContext
* aContext
) {
223 mResetData
->Destroy(aBits
, aContext
);
225 mInheritedData
->Destroy(aBits
, aContext
);
227 mInheritedData
= nsnull
;
230 nsCachedStyleData() :mInheritedData(nsnull
), mResetData(nsnull
) {}
231 ~nsCachedStyleData() {}
235 * nsRuleNode is a node in a lexicographic tree (the "rule tree")
236 * indexed by style rules (implementations of nsIStyleRule).
238 * The rule tree is owned by the nsStyleSet and is destroyed when the
239 * presentation of the document goes away. It is garbage-collected
240 * (using mark-and-sweep garbage collection) during the lifetime of the
241 * document (when dynamic changes cause the destruction of enough style
242 * contexts). Rule nodes are marked if they are pointed to by a style
243 * context or one of their descendants is.
245 * An nsStyleContext, which represents the computed style data for an
246 * element, points to an nsRuleNode. The path from the root of the rule
247 * tree to the nsStyleContext's mRuleNode gives the list of the rules
248 * matched, from least important in the cascading order to most
249 * important in the cascading order.
251 * The reason for using a lexicographic tree is that it allows for
252 * sharing of style data, which saves both memory (for storing the
253 * computed style data) and time (for computing them). This sharing
254 * depends on the computed style data being stored in structs (nsStyle*)
255 * that contain only properties that are inherited by default
256 * ("inherited structs") or structs that contain only properties that
257 * are not inherited by default ("reset structs"). The optimization
258 * depends on the normal case being that style rules specify relatively
259 * few properties and even that elements generally have relatively few
260 * properties specified. This allows sharing in the following ways:
261 * 1. [mainly reset structs] When a style data struct will contain the
262 * same computed value for any elements that match the same set of
263 * rules (common for reset structs), it can be stored on the
264 * nsRuleNode instead of on the nsStyleContext.
265 * 2. [only? reset structs] When (1) occurs, and an nsRuleNode doesn't
266 * have any rules that change the values in the struct, the
267 * nsRuleNode can share that struct with its parent nsRuleNode.
268 * 3. [mainly inherited structs] When an element doesn't match any
269 * rules that change the value of a property (or, in the edge case,
270 * when all the values specified are 'inherit'), the nsStyleContext
271 * can use the same nsStyle* struct as its parent nsStyleContext.
273 * Since the data represented by an nsIStyleRule are immutable, the data
274 * represented by an nsRuleNode are also immutable.
280 eRuleNone
, // No props have been specified at all.
281 eRulePartialReset
, // At least one prop with a non-"inherit" value
282 // has been specified. No props have been
283 // specified with an "inherit" value. At least
284 // one prop remains unspecified.
285 eRulePartialMixed
, // At least one prop with a non-"inherit" value
286 // has been specified. Some props may also have
287 // been specified with an "inherit" value. At
288 // least one prop remains unspecified.
289 eRulePartialInherited
, // Only props with "inherit" values have
290 // have been specified. At least one prop
291 // remains unspecified.
292 eRuleFullReset
, // All props have been specified. None has an
294 eRuleFullMixed
, // All props have been specified. At least one has
295 // a non-"inherit" value.
296 eRuleFullInherited
// All props have been specified with "inherit"
301 nsPresContext
* mPresContext
; // Our pres context.
303 nsRuleNode
* mParent
; // A pointer to the parent node in the tree.
304 // This enables us to walk backwards from the
305 // most specific rule matched to the least
306 // specific rule (which is the optimal order to
307 // use for lookups of style properties.
308 nsIStyleRule
* mRule
; // [STRONG] A pointer to our specific rule.
310 nsRuleNode
* mNextSibling
; // This value should be used only by the
311 // parent, since the parent may store
312 // children in a hash, which means this
313 // pointer is not meaningful. Order of
314 // siblings is also not meaningful.
319 PRPackedBool mIsImportantRule
;
321 Key(nsIStyleRule
* aRule
, PRUint8 aLevel
, PRPackedBool aIsImportantRule
)
322 : mRule(aRule
), mLevel(aLevel
), mIsImportantRule(aIsImportantRule
)
325 PRBool
operator==(const Key
& aOther
) const
327 return mRule
== aOther
.mRule
&&
328 mLevel
== aOther
.mLevel
&&
329 mIsImportantRule
== aOther
.mIsImportantRule
;
332 PRBool
operator!=(const Key
& aOther
) const
334 return !(*this == aOther
);
339 ChildrenHashHashKey(PLDHashTable
*aTable
, const void *aKey
);
342 ChildrenHashMatchEntry(PLDHashTable
*aTable
,
343 const PLDHashEntryHdr
*aHdr
,
346 static PLDHashTableOps ChildrenHashOps
;
348 static PLDHashOperator
349 EnqueueRuleNodeChildren(PLDHashTable
*table
, PLDHashEntryHdr
*hdr
,
350 PRUint32 number
, void *arg
);
353 return Key(mRule
, GetLevel(), IsImportantRule());
356 // The children of this node are stored in either a hashtable or list
357 // that maps from rules to our nsRuleNode children. When matching
358 // rules, we use this mapping to transition from node to node
359 // (constructing new nodes as needed to flesh out the tree).
364 PLDHashTable
* asHash
;
365 } mChildren
; // Accessed only through the methods below.
373 // Maximum to have in a list before converting to a hashtable.
374 // XXX Need to optimize this.
375 kMaxChildrenInList
= 32
378 PRBool
HaveChildren() const {
379 return mChildren
.asVoid
!= nsnull
;
381 PRBool
ChildrenAreHashed() {
382 return (PRWord(mChildren
.asVoid
) & kTypeMask
) == kHashType
;
384 nsRuleNode
* ChildrenList() {
385 return mChildren
.asList
;
387 nsRuleNode
** ChildrenListPtr() {
388 return &mChildren
.asList
;
390 PLDHashTable
* ChildrenHash() {
391 return (PLDHashTable
*) (PRWord(mChildren
.asHash
) & ~PRWord(kTypeMask
));
393 void SetChildrenList(nsRuleNode
*aList
) {
394 NS_ASSERTION(!(PRWord(aList
) & kTypeMask
),
395 "pointer not 2-byte aligned");
396 mChildren
.asList
= aList
;
398 void SetChildrenHash(PLDHashTable
*aHashtable
) {
399 NS_ASSERTION(!(PRWord(aHashtable
) & kTypeMask
),
400 "pointer not 2-byte aligned");
401 mChildren
.asHash
= (PLDHashTable
*)(PRWord(aHashtable
) | kHashType
);
403 void ConvertChildrenToHash();
405 nsCachedStyleData mStyleData
; // Any data we cached on the rule node.
407 PRUint32 mDependentBits
; // Used to cache the fact that we can look up
408 // cached data under a parent rule.
410 PRUint32 mNoneBits
; // Used to cache the fact that the branch to this
411 // node specifies no non-inherited data for a
412 // given struct type. (This usually implies that
413 // the entire branch specifies no non-inherited
414 // data, although not necessarily, if a
415 // non-inherited value is overridden by an
416 // explicit 'inherit' value.) For example, if an
417 // entire rule branch specifies no color
418 // information, then a bit will be set along every
419 // rule node on that branch, so that you can break
420 // out of the rule tree early and just inherit
421 // from the parent style context. The presence of
422 // this bit means we should just get inherited
423 // data from the parent style context, and it is
424 // never used for reset structs since their
425 // Compute*Data functions don't initialize from
428 // Reference count. This just counts the style contexts that reference this
429 // rulenode. And children the rulenode has had. When this goes to 0 or
430 // stops being 0, we notify the style set.
431 // Note, in particular, that when a child is removed mRefCnt is NOT
432 // decremented. This is on purpose; the notifications to the style set are
433 // only used to determine when it's worth running GC on the ruletree, and
434 // this setup makes it so we only count unused ruletree leaves for purposes
435 // of deciding when to GC. We could more accurately count unused rulenodes
436 // by releasing/addrefing our parent when our refcount transitions to or from
437 // 0, but it doesn't seem worth it to do that.
441 // Overloaded new operator. Initializes the memory to 0 and relies on an arena
442 // (which comes from the presShell) to perform the allocation.
443 void* operator new(size_t sz
, nsPresContext
* aContext
) CPP_THROW_NEW
;
444 void Destroy() { DestroyInternal(nsnull
); }
445 static nsILanguageAtomService
* gLangService
;
447 // Implemented in nsStyleSet.h, since it needs to know about nsStyleSet.
448 inline void AddRef();
450 // Implemented in nsStyleSet.h, since it needs to know about nsStyleSet.
451 inline void Release();
454 void DestroyInternal(nsRuleNode
***aDestroyQueueTail
);
455 void PropagateDependentBit(PRUint32 aBit
, nsRuleNode
* aHighestNode
);
456 void PropagateNoneBit(PRUint32 aBit
, nsRuleNode
* aHighestNode
);
458 const void* SetDefaultOnRoot(const nsStyleStructID aSID
,
459 nsStyleContext
* aContext
);
462 WalkRuleTree(const nsStyleStructID aSID
, nsStyleContext
* aContext
,
463 nsRuleData
* aRuleData
, nsRuleDataStruct
* aSpecificData
);
466 ComputeDisplayData(void* aStartStruct
,
467 const nsRuleDataStruct
& aData
,
468 nsStyleContext
* aContext
, nsRuleNode
* aHighestNode
,
469 RuleDetail aRuleDetail
,
470 const PRBool aCanStoreInRuleTree
);
473 ComputeVisibilityData(void* aStartStruct
,
474 const nsRuleDataStruct
& aData
,
475 nsStyleContext
* aContext
, nsRuleNode
* aHighestNode
,
476 RuleDetail aRuleDetail
,
477 const PRBool aCanStoreInRuleTree
);
480 ComputeFontData(void* aStartStruct
,
481 const nsRuleDataStruct
& aData
,
482 nsStyleContext
* aContext
, nsRuleNode
* aHighestNode
,
483 RuleDetail aRuleDetail
,
484 const PRBool aCanStoreInRuleTree
);
487 ComputeColorData(void* aStartStruct
,
488 const nsRuleDataStruct
& aData
,
489 nsStyleContext
* aContext
, nsRuleNode
* aHighestNode
,
490 RuleDetail aRuleDetail
,
491 const PRBool aCanStoreInRuleTree
);
494 ComputeBackgroundData(void* aStartStruct
,
495 const nsRuleDataStruct
& aData
,
496 nsStyleContext
* aContext
, nsRuleNode
* aHighestNode
,
497 RuleDetail aRuleDetail
,
498 const PRBool aCanStoreInRuleTree
);
501 ComputeMarginData(void* aStartStruct
,
502 const nsRuleDataStruct
& aData
,
503 nsStyleContext
* aContext
, nsRuleNode
* aHighestNode
,
504 RuleDetail aRuleDetail
,
505 const PRBool aCanStoreInRuleTree
);
508 ComputeBorderData(void* aStartStruct
,
509 const nsRuleDataStruct
& aData
,
510 nsStyleContext
* aContext
, nsRuleNode
* aHighestNode
,
511 RuleDetail aRuleDetail
,
512 const PRBool aCanStoreInRuleTree
);
515 ComputePaddingData(void* aStartStruct
,
516 const nsRuleDataStruct
& aData
,
517 nsStyleContext
* aContext
, nsRuleNode
* aHighestNode
,
518 RuleDetail aRuleDetail
,
519 const PRBool aCanStoreInRuleTree
);
522 ComputeOutlineData(void* aStartStruct
,
523 const nsRuleDataStruct
& aData
,
524 nsStyleContext
* aContext
, nsRuleNode
* aHighestNode
,
525 RuleDetail aRuleDetail
,
526 const PRBool aCanStoreInRuleTree
);
529 ComputeListData(void* aStartStruct
,
530 const nsRuleDataStruct
& aData
,
531 nsStyleContext
* aContext
, nsRuleNode
* aHighestNode
,
532 RuleDetail aRuleDetail
,
533 const PRBool aCanStoreInRuleTree
);
536 ComputePositionData(void* aStartStruct
,
537 const nsRuleDataStruct
& aData
,
538 nsStyleContext
* aContext
, nsRuleNode
* aHighestNode
,
539 RuleDetail aRuleDetail
,
540 const PRBool aCanStoreInRuleTree
);
543 ComputeTableData(void* aStartStruct
,
544 const nsRuleDataStruct
& aData
,
545 nsStyleContext
* aContext
, nsRuleNode
* aHighestNode
,
546 RuleDetail aRuleDetail
,
547 const PRBool aCanStoreInRuleTree
);
550 ComputeTableBorderData(void* aStartStruct
,
551 const nsRuleDataStruct
& aData
,
552 nsStyleContext
* aContext
, nsRuleNode
* aHighestNode
,
553 RuleDetail aRuleDetail
,
554 const PRBool aCanStoreInRuleTree
);
557 ComputeContentData(void* aStartStruct
,
558 const nsRuleDataStruct
& aData
,
559 nsStyleContext
* aContext
, nsRuleNode
* aHighestNode
,
560 RuleDetail aRuleDetail
,
561 const PRBool aCanStoreInRuleTree
);
564 ComputeQuotesData(void* aStartStruct
,
565 const nsRuleDataStruct
& aData
,
566 nsStyleContext
* aContext
, nsRuleNode
* aHighestNode
,
567 RuleDetail aRuleDetail
,
568 const PRBool aCanStoreInRuleTree
);
571 ComputeTextData(void* aStartStruct
,
572 const nsRuleDataStruct
& aData
,
573 nsStyleContext
* aContext
, nsRuleNode
* aHighestNode
,
574 RuleDetail aRuleDetail
,
575 const PRBool aCanStoreInRuleTree
);
578 ComputeTextResetData(void* aStartStruct
,
579 const nsRuleDataStruct
& aData
,
580 nsStyleContext
* aContext
, nsRuleNode
* aHighestNode
,
581 RuleDetail aRuleDetail
,
582 const PRBool aCanStoreInRuleTree
);
585 ComputeUserInterfaceData(void* aStartStruct
,
586 const nsRuleDataStruct
& aData
,
587 nsStyleContext
* aContext
,
588 nsRuleNode
* aHighestNode
,
589 RuleDetail aRuleDetail
,
590 const PRBool aCanStoreInRuleTree
);
593 ComputeUIResetData(void* aStartStruct
,
594 const nsRuleDataStruct
& aData
,
595 nsStyleContext
* aContext
, nsRuleNode
* aHighestNode
,
596 RuleDetail aRuleDetail
,
597 const PRBool aCanStoreInRuleTree
);
600 ComputeXULData(void* aStartStruct
,
601 const nsRuleDataStruct
& aData
,
602 nsStyleContext
* aContext
, nsRuleNode
* aHighestNode
,
603 RuleDetail aRuleDetail
,
604 const PRBool aCanStoreInRuleTree
);
607 ComputeColumnData(void* aStartStruct
,
608 const nsRuleDataStruct
& aData
,
609 nsStyleContext
* aContext
, nsRuleNode
* aHighestNode
,
610 RuleDetail aRuleDetail
,
611 const PRBool aCanStoreInRuleTree
);
614 ComputeSVGData(void* aStartStruct
,
615 const nsRuleDataStruct
& aData
,
616 nsStyleContext
* aContext
, nsRuleNode
* aHighestNode
,
617 RuleDetail aRuleDetail
,
618 const PRBool aCanStoreInRuleTree
);
621 ComputeSVGResetData(void* aStartStruct
,
622 const nsRuleDataStruct
& aData
,
623 nsStyleContext
* aContext
, nsRuleNode
* aHighestNode
,
624 RuleDetail aRuleDetail
,
625 const PRBool aCanStoreInRuleTree
);
627 // helpers for |ComputeFontData| that need access to |mNoneBits|:
628 static void SetFontSize(nsPresContext
* aPresContext
,
629 const nsRuleDataFont
& aFontData
,
630 const nsStyleFont
* aFont
,
631 const nsStyleFont
* aParentFont
,
633 const nsFont
& aSystemFont
,
635 nscoord aScriptLevelAdjustedParentSize
,
636 PRBool aUsedStartStruct
,
638 PRBool
& aCanStoreInRuleTree
);
640 static void SetFont(nsPresContext
* aPresContext
,
641 nsStyleContext
* aContext
,
642 nscoord aMinFontSize
,
643 PRUint8 aGenericFontID
,
644 const nsRuleDataFont
& aFontData
,
645 const nsStyleFont
* aParentFont
,
648 PRBool
& aCanStoreInRuleTree
);
650 static void SetGenericFont(nsPresContext
* aPresContext
,
651 nsStyleContext
* aContext
,
652 PRUint8 aGenericFontID
,
653 nscoord aMinFontSize
,
656 void AdjustLogicalBoxProp(nsStyleContext
* aContext
,
657 const nsCSSValue
& aLTRSource
,
658 const nsCSSValue
& aRTLSource
,
659 const nsCSSValue
& aLTRLogicalValue
,
660 const nsCSSValue
& aRTLLogicalValue
,
661 mozilla::css::Side aSide
,
662 nsCSSRect
& aValueRect
,
663 PRBool
& aCanStoreInRuleTree
);
665 inline RuleDetail
CheckSpecifiedProperties(const nsStyleStructID aSID
, const nsRuleDataStruct
& aRuleDataStruct
);
667 const void* GetParentData(const nsStyleStructID aSID
);
668 #define STYLE_STRUCT(name_, checkdata_cb_, ctor_args_) \
669 const nsStyle##name_* GetParent##name_();
670 #include "nsStyleStructList.h"
673 const void* GetDisplayData(nsStyleContext
* aContext
);
674 const void* GetVisibilityData(nsStyleContext
* aContext
);
675 const void* GetFontData(nsStyleContext
* aContext
);
676 const void* GetColorData(nsStyleContext
* aContext
);
677 const void* GetBackgroundData(nsStyleContext
* aContext
);
678 const void* GetMarginData(nsStyleContext
* aContext
);
679 const void* GetBorderData(nsStyleContext
* aContext
);
680 const void* GetPaddingData(nsStyleContext
* aContext
);
681 const void* GetOutlineData(nsStyleContext
* aContext
);
682 const void* GetListData(nsStyleContext
* aContext
);
683 const void* GetPositionData(nsStyleContext
* aContext
);
684 const void* GetTableData(nsStyleContext
* aContext
);
685 const void* GetTableBorderData(nsStyleContext
* aContext
);
687 const void* GetContentData(nsStyleContext
* aContext
);
688 const void* GetQuotesData(nsStyleContext
* aContext
);
689 const void* GetTextData(nsStyleContext
* aContext
);
690 const void* GetTextResetData(nsStyleContext
* aContext
);
691 const void* GetUserInterfaceData(nsStyleContext
* aContext
);
693 const void* GetUIResetData(nsStyleContext
* aContext
);
694 const void* GetXULData(nsStyleContext
* aContext
);
695 const void* GetColumnData(nsStyleContext
* aContext
);
696 const void* GetSVGData(nsStyleContext
* aContext
);
697 const void* GetSVGResetData(nsStyleContext
* aContext
);
699 already_AddRefed
<nsCSSShadowArray
>
700 GetShadowData(const nsCSSValueList
* aList
,
701 nsStyleContext
* aContext
,
706 nsRuleNode(nsPresContext
* aPresContext
, nsRuleNode
* aParent
,
707 nsIStyleRule
* aRule
, PRUint8 aLevel
, PRBool aIsImportant
);
711 static nsRuleNode
* CreateRootNode(nsPresContext
* aPresContext
);
713 // Transition never returns null; on out of memory it'll just return |this|.
714 nsRuleNode
* Transition(nsIStyleRule
* aRule
, PRUint8 aLevel
,
715 PRPackedBool aIsImportantRule
);
716 nsRuleNode
* GetParent() const { return mParent
; }
717 PRBool
IsRoot() const { return mParent
== nsnull
; }
719 // These PRUint8s are really nsStyleSet::sheetType values.
720 PRUint8
GetLevel() const {
721 NS_ASSERTION(!IsRoot(), "can't call on root");
722 return (mDependentBits
& NS_RULE_NODE_LEVEL_MASK
) >>
723 NS_RULE_NODE_LEVEL_SHIFT
;
725 PRBool
IsImportantRule() const {
726 NS_ASSERTION(!IsRoot(), "can't call on root");
727 return (mDependentBits
& NS_RULE_NODE_IS_IMPORTANT
) != 0;
730 // NOTE: Does not |AddRef|.
731 nsIStyleRule
* GetRule() const { return mRule
; }
732 // NOTE: Does not |AddRef|.
733 nsPresContext
* GetPresContext() const { return mPresContext
; }
735 const void* GetStyleData(nsStyleStructID aSID
,
736 nsStyleContext
* aContext
,
737 PRBool aComputeData
);
739 #define STYLE_STRUCT(name_, checkdata_cb_, ctor_args_) \
740 const nsStyle##name_* GetStyle##name_(nsStyleContext* aContext, \
741 PRBool aComputeData);
742 #include "nsStyleStructList.h"
746 * Garbage collection. Mark walks up the tree, marking any unmarked
747 * ancestors until it reaches a marked one. Sweep recursively sweeps
748 * the children, destroys any that are unmarked, and clears marks,
749 * returning true if the node on which it was called was destroyed.
755 HasAuthorSpecifiedRules(nsStyleContext
* aStyleContext
,
756 PRUint32 ruleTypeMask
,
757 PRBool aAuthorColorsAllowed
);
759 // Expose this so media queries can use it
760 static nscoord
CalcLengthWithInitialFont(nsPresContext
* aPresContext
,
761 const nsCSSValue
& aValue
);
762 // Expose this so nsTransformFunctions can use it.
763 static nscoord
CalcLength(const nsCSSValue
& aValue
,
764 nsStyleContext
* aStyleContext
,
765 nsPresContext
* aPresContext
,
766 PRBool
& aCanStoreInRuleTree
);
768 struct ComputedCalc
{
772 ComputedCalc(nscoord aLength
, float aPercent
)
773 : mLength(aLength
), mPercent(aPercent
) {}
776 SpecifiedCalcToComputedCalc(const nsCSSValue
& aValue
,
777 nsStyleContext
* aStyleContext
,
778 nsPresContext
* aPresContext
,
779 PRBool
& aCanStoreInRuleTree
);
781 // Compute the value of an nsStyleCoord that IsCalcUnit().
782 // (Values that don't require aPercentageBasis should be handled
783 // inside nsRuleNode rather than through this API.)
784 static nscoord
ComputeComputedCalc(const nsStyleCoord
& aCoord
,
785 nscoord aPercentageBasis
);
787 // Compute the value of an nsStyleCoord that is either a coord, a
788 // percent, or a calc expression.
789 static nscoord
ComputeCoordPercentCalc(const nsStyleCoord
& aCoord
,
790 nscoord aPercentageBasis
);
792 // Return whether the rule tree for which this node is the root has
793 // cached data such that we need to do dynamic change handling for
794 // changes that change the results of media queries or require
795 // rebuilding all style data.
796 PRBool
TreeHasCachedData() const {
797 NS_ASSERTION(IsRoot(), "should only be called on root of rule tree");
798 return HaveChildren() || mStyleData
.mInheritedData
|| mStyleData
.mResetData
;