Line data Source code
1 : /* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
2 : /* This Source Code Form is subject to the terms of the Mozilla Public
3 : * License, v. 2.0. If a copy of the MPL was not distributed with this
4 : * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
5 :
6 : /* a presentation of a document, part 1 */
7 :
8 : #ifndef nsPresContext_h___
9 : #define nsPresContext_h___
10 :
11 : #include "mozilla/Attributes.h"
12 : #include "mozilla/NotNull.h"
13 : #include "mozilla/UniquePtr.h"
14 : #include "mozilla/WeakPtr.h"
15 : #include "nsColor.h"
16 : #include "nsCoord.h"
17 : #include "nsCOMPtr.h"
18 : #include "nsIPresShell.h"
19 : #include "nsRect.h"
20 : #include "nsFont.h"
21 : #include "gfxFontConstants.h"
22 : #include "nsIAtom.h"
23 : #include "nsIObserver.h"
24 : #include "nsITimer.h"
25 : #include "nsCRT.h"
26 : #include "nsIWidgetListener.h"
27 : #include "nsLanguageAtomService.h"
28 : #include "nsGkAtoms.h"
29 : #include "nsCycleCollectionParticipant.h"
30 : #include "nsChangeHint.h"
31 : #include <algorithm>
32 : #include "gfxTypes.h"
33 : #include "gfxRect.h"
34 : #include "nsTArray.h"
35 : #include "nsAutoPtr.h"
36 : #include "mozilla/MemoryReporting.h"
37 : #include "mozilla/TimeStamp.h"
38 : #include "mozilla/AppUnits.h"
39 : #include "prclist.h"
40 : #include "nsThreadUtils.h"
41 : #include "ScrollbarStyles.h"
42 : #include "nsIMessageManager.h"
43 : #include "mozilla/RestyleLogging.h"
44 : #include "Units.h"
45 : #include "prenv.h"
46 : #include "mozilla/StaticPresData.h"
47 : #include "mozilla/StyleBackendType.h"
48 :
49 : class nsAString;
50 : class nsBidi;
51 : class nsIPrintSettings;
52 : class nsDocShell;
53 : class nsIDocShell;
54 : class nsIDocument;
55 : class nsITheme;
56 : class nsIContent;
57 : class nsIFrame;
58 : class nsFrameManager;
59 : class nsILinkHandler;
60 : class nsIAtom;
61 : class nsIRunnable;
62 : class gfxUserFontEntry;
63 : class gfxUserFontSet;
64 : class gfxTextPerfMetrics;
65 : class nsPluginFrame;
66 : class nsTransitionManager;
67 : class nsAnimationManager;
68 : class nsRefreshDriver;
69 : class nsIWidget;
70 : class nsDeviceContext;
71 : class gfxMissingFontRecorder;
72 :
73 : namespace mozilla {
74 : class EffectCompositor;
75 : class Encoding;
76 : class EventStateManager;
77 : class CounterStyleManager;
78 : class RestyleManager;
79 : namespace layers {
80 : class ContainerLayer;
81 : class LayerManager;
82 : } // namespace layers
83 : namespace dom {
84 : class Element;
85 : } // namespace dom
86 : } // namespace mozilla
87 :
88 : // supported values for cached bool types
89 : enum nsPresContext_CachedBoolPrefType {
90 : kPresContext_UseDocumentFonts = 1,
91 : kPresContext_UnderlineLinks
92 : };
93 :
94 : // supported values for cached integer pref types
95 : enum nsPresContext_CachedIntPrefType {
96 : kPresContext_ScrollbarSide = 1,
97 : kPresContext_BidiDirection
98 : };
99 :
100 : // IDs for the default variable and fixed fonts (not to be changed, see nsFont.h)
101 : // To be used for Get/SetDefaultFont(). The other IDs in nsFont.h are also supported.
102 : const uint8_t kPresContext_DefaultVariableFont_ID = 0x00; // kGenericFont_moz_variable
103 : const uint8_t kPresContext_DefaultFixedFont_ID = 0x01; // kGenericFont_moz_fixed
104 :
105 : #ifdef DEBUG
106 : struct nsAutoLayoutPhase;
107 :
108 : enum nsLayoutPhase {
109 : eLayoutPhase_Paint,
110 : eLayoutPhase_Reflow,
111 : eLayoutPhase_FrameC,
112 : eLayoutPhase_COUNT
113 : };
114 : #endif
115 :
116 : /* Used by nsPresContext::HasAuthorSpecifiedRules */
117 : #define NS_AUTHOR_SPECIFIED_BACKGROUND (1 << 0)
118 : #define NS_AUTHOR_SPECIFIED_BORDER (1 << 1)
119 : #define NS_AUTHOR_SPECIFIED_PADDING (1 << 2)
120 : #define NS_AUTHOR_SPECIFIED_TEXT_SHADOW (1 << 3)
121 :
122 : class nsRootPresContext;
123 :
124 : // An interface for presentation contexts. Presentation contexts are
125 : // objects that provide an outer context for a presentation shell.
126 :
127 : class nsPresContext : public nsIObserver,
128 : public mozilla::SupportsWeakPtr<nsPresContext> {
129 : public:
130 : using Encoding = mozilla::Encoding;
131 : template <typename T> using NotNull = mozilla::NotNull<T>;
132 : typedef mozilla::LangGroupFontPrefs LangGroupFontPrefs;
133 : typedef mozilla::ScrollbarStyles ScrollbarStyles;
134 : typedef mozilla::StaticPresData StaticPresData;
135 :
136 : NS_DECL_CYCLE_COLLECTING_ISUPPORTS
137 : NS_DECL_NSIOBSERVER
138 9187 : NS_DECL_CYCLE_COLLECTION_CLASS(nsPresContext)
139 120 : MOZ_DECLARE_WEAKREFERENCE_TYPENAME(nsPresContext)
140 :
141 : enum nsPresContextType {
142 : eContext_Galley, // unpaginated screen presentation
143 : eContext_PrintPreview, // paginated screen presentation
144 : eContext_Print, // paginated printer presentation
145 : eContext_PageLayout // paginated & editable.
146 : };
147 :
148 : nsPresContext(nsIDocument* aDocument, nsPresContextType aType);
149 :
150 : /**
151 : * Initialize the presentation context from a particular device.
152 : */
153 : nsresult Init(nsDeviceContext* aDeviceContext);
154 :
155 : /**
156 : * Set and detach presentation shell that this context is bound to.
157 : * A presentation context may only be bound to a single shell.
158 : */
159 : void AttachShell(nsIPresShell* aShell, mozilla::StyleBackendType aBackendType);
160 : void DetachShell();
161 :
162 :
163 1795 : nsPresContextType Type() const { return mType; }
164 :
165 : /**
166 : * Get the PresentationShell that this context is bound to.
167 : */
168 36216 : nsIPresShell* PresShell() const
169 : {
170 36216 : NS_ASSERTION(mShell, "Null pres shell");
171 36216 : return mShell;
172 : }
173 :
174 38233 : nsIPresShell* GetPresShell() const { return mShell; }
175 :
176 : /**
177 : * Returns the parent prescontext for this one. Returns null if this is a
178 : * root.
179 : */
180 : nsPresContext* GetParentPresContext();
181 :
182 : /**
183 : * Returns the prescontext of the toplevel content document that contains
184 : * this presentation, or null if there isn't one.
185 : */
186 : nsPresContext* GetToplevelContentDocumentPresContext();
187 :
188 : /**
189 : * Returns the nearest widget for the root frame of this.
190 : *
191 : * @param aOffset If non-null the offset from the origin of the root
192 : * frame's view to the widget's origin (usually positive)
193 : * expressed in appunits of this will be returned in
194 : * aOffset.
195 : */
196 : nsIWidget* GetNearestWidget(nsPoint* aOffset = nullptr);
197 :
198 : /**
199 : * Returns the root widget for this.
200 : * Note that the widget is a mediater with IME.
201 : */
202 : nsIWidget* GetRootWidget();
203 :
204 : /**
205 : * Return the presentation context for the root of the view manager
206 : * hierarchy that contains this presentation context, or nullptr if it can't
207 : * be found (e.g. it's detached).
208 : */
209 : nsRootPresContext* GetRootPresContext();
210 :
211 2 : virtual bool IsRoot() { return false; }
212 :
213 11283 : nsIDocument* Document() const
214 : {
215 11283 : NS_ASSERTION(!mShell || !mShell->GetDocument() ||
216 : mShell->GetDocument() == mDocument,
217 : "nsPresContext doesn't have the same document as nsPresShell!");
218 11283 : return mDocument;
219 : }
220 :
221 : #ifdef MOZILLA_INTERNAL_API
222 17555 : mozilla::StyleSetHandle StyleSet() const { return GetPresShell()->StyleSet(); }
223 :
224 4844 : nsFrameManager* FrameManager()
225 4844 : { return PresShell()->FrameManager(); }
226 :
227 1794 : nsCSSFrameConstructor* FrameConstructor()
228 1794 : { return PresShell()->FrameConstructor(); }
229 :
230 6016 : mozilla::EffectCompositor* EffectCompositor() { return mEffectCompositor; }
231 1553 : nsTransitionManager* TransitionManager() { return mTransitionManager; }
232 2997 : nsAnimationManager* AnimationManager() { return mAnimationManager; }
233 :
234 1037 : nsRefreshDriver* RefreshDriver() { return mRefreshDriver; }
235 :
236 23987 : mozilla::RestyleManager* RestyleManager() {
237 23987 : MOZ_ASSERT(mRestyleManager);
238 23987 : return mRestyleManager;
239 : }
240 :
241 0 : mozilla::CounterStyleManager* CounterStyleManager() const {
242 0 : return mCounterStyleManager;
243 : }
244 : #endif
245 :
246 : /**
247 : * Rebuilds all style data by throwing out the old rule tree and
248 : * building a new one, and additionally applying aExtraHint (which
249 : * must not contain nsChangeHint_ReconstructFrame) to the root frame.
250 : * For aRestyleHint, see RestyleManager::RebuildAllStyleData.
251 : * Also rebuild the user font set and counter style manager.
252 : */
253 : void RebuildAllStyleData(nsChangeHint aExtraHint, nsRestyleHint aRestyleHint);
254 : /**
255 : * Just like RebuildAllStyleData, except (1) asynchronous and (2) it
256 : * doesn't rebuild the user font set.
257 : */
258 : void PostRebuildAllStyleDataEvent(nsChangeHint aExtraHint,
259 : nsRestyleHint aRestyleHint);
260 :
261 : /**
262 : * Handle changes in the values of media features (used in media
263 : * queries).
264 : *
265 : * There are three sensible values to use for aRestyleHint:
266 : * * nsRestyleHint(0) to rebuild style data, with rerunning of
267 : * selector matching, only if media features have changed
268 : * * eRestyle_ForceDescendants to force rebuilding of style data (but
269 : * still only rerun selector matching if media query results have
270 : * changed). (RebuildAllStyleData always adds
271 : * eRestyle_ForceDescendants internally, so here we're only using
272 : * it to distinguish from nsRestyleHint(0) whether we need to call
273 : * RebuildAllStyleData at all.)
274 : * * eRestyle_Subtree to force rebuilding of style data with
275 : * rerunning of selector matching
276 : *
277 : * For aChangeHint, see RestyleManager::RebuildAllStyleData. (Passing
278 : * a nonzero aChangeHint forces rebuilding style data even if
279 : * nsRestyleHint(0) is passed.)
280 : */
281 : void MediaFeatureValuesChanged(nsRestyleHint aRestyleHint,
282 : nsChangeHint aChangeHint = nsChangeHint(0));
283 : /**
284 : * Calls MediaFeatureValuesChanged for this pres context and all descendant
285 : * subdocuments that have a pres context. This should be used for media
286 : * features that must be updated in all subdocuments e.g. display-mode.
287 : */
288 : void MediaFeatureValuesChangedAllDocuments(nsRestyleHint aRestyleHint,
289 : nsChangeHint aChangeHint = nsChangeHint(0));
290 :
291 : void PostMediaFeatureValuesChangedEvent();
292 : void HandleMediaFeatureValuesChangedEvent();
293 122 : void FlushPendingMediaFeatureValuesChanged() {
294 122 : if (mPendingMediaFeatureValuesChanged)
295 20 : MediaFeatureValuesChanged(nsRestyleHint(0));
296 122 : }
297 :
298 : /**
299 : * Updates the size mode on all remote children and recursively notifies this
300 : * document and all subdocuments (including remote children) that a media
301 : * feature value has changed.
302 : */
303 : void SizeModeChanged(nsSizeMode aSizeMode);
304 :
305 : /**
306 : * Access compatibility mode for this context. This is the same as
307 : * our document's compatibility mode.
308 : */
309 : nsCompatibility CompatibilityMode() const;
310 :
311 : /**
312 : * Notify the context that the document's compatibility mode has changed
313 : */
314 : void CompatibilityModeChanged();
315 :
316 : /**
317 : * Access the image animation mode for this context
318 : */
319 41 : uint16_t ImageAnimationMode() const { return mImageAnimationMode; }
320 : virtual void SetImageAnimationModeExternal(uint16_t aMode);
321 : void SetImageAnimationModeInternal(uint16_t aMode);
322 : #ifdef MOZILLA_INTERNAL_API
323 0 : void SetImageAnimationMode(uint16_t aMode)
324 0 : { SetImageAnimationModeInternal(aMode); }
325 : #else
326 : void SetImageAnimationMode(uint16_t aMode)
327 : { SetImageAnimationModeExternal(aMode); }
328 : #endif
329 :
330 : /**
331 : * Get medium of presentation
332 : */
333 331 : nsIAtom* Medium() {
334 331 : if (!mIsEmulatingMedia)
335 331 : return mMedium;
336 0 : return mMediaEmulated;
337 : }
338 :
339 : /*
340 : * Render the document as if being viewed on a device with the specified
341 : * media type.
342 : */
343 : void EmulateMedium(const nsAString& aMediaType);
344 :
345 : /*
346 : * Restore the viewer's natural medium
347 : */
348 : void StopEmulatingMedium();
349 :
350 : /**
351 : * Get the default font for the given language and generic font ID.
352 : * If aLanguage is nullptr, the document's language is used.
353 : *
354 : * See the comment in StaticPresData::GetDefaultFont.
355 : */
356 97 : const nsFont* GetDefaultFont(uint8_t aFontID,
357 : nsIAtom *aLanguage, bool* aNeedsToCache = nullptr) const
358 : {
359 97 : nsIAtom* lang = aLanguage ? aLanguage : mLanguage.get();
360 97 : const LangGroupFontPrefs* prefs = GetFontPrefsForLang(lang, aNeedsToCache);
361 97 : if (aNeedsToCache && *aNeedsToCache) {
362 0 : return nullptr;
363 : }
364 97 : return StaticPresData::Get()->GetDefaultFontHelper(aFontID, lang, prefs);
365 : }
366 :
367 : void ForceCacheLang(nsIAtom *aLanguage);
368 : void CacheAllLangs();
369 :
370 : /** Get a cached boolean pref, by its type */
371 : // * - initially created for bugs 31816, 20760, 22963
372 2 : bool GetCachedBoolPref(nsPresContext_CachedBoolPrefType aPrefType) const
373 : {
374 : // If called with a constant parameter, the compiler should optimize
375 : // this switch statement away.
376 2 : switch (aPrefType) {
377 : case kPresContext_UseDocumentFonts:
378 0 : return mUseDocumentFonts;
379 : case kPresContext_UnderlineLinks:
380 2 : return mUnderlineLinks;
381 : default:
382 0 : NS_ERROR("Invalid arg passed to GetCachedBoolPref");
383 : }
384 :
385 0 : return false;
386 : }
387 :
388 : /** Get a cached integer pref, by its type */
389 : // * - initially created for bugs 30910, 61883, 74186, 84398
390 174 : int32_t GetCachedIntPref(nsPresContext_CachedIntPrefType aPrefType) const
391 : {
392 : // If called with a constant parameter, the compiler should optimize
393 : // this switch statement away.
394 174 : switch (aPrefType) {
395 : case kPresContext_ScrollbarSide:
396 87 : return mPrefScrollbarSide;
397 : case kPresContext_BidiDirection:
398 87 : return mPrefBidiDirection;
399 : default:
400 0 : NS_ERROR("invalid arg passed to GetCachedIntPref");
401 : }
402 :
403 0 : return false;
404 : }
405 :
406 : /**
407 : * Get the default colors
408 : */
409 35 : nscolor DefaultColor() const { return mDefaultColor; }
410 27 : nscolor DefaultBackgroundColor() const { return mBackgroundColor; }
411 2 : nscolor DefaultLinkColor() const { return mLinkColor; }
412 2 : nscolor DefaultActiveLinkColor() const { return mActiveLinkColor; }
413 2 : nscolor DefaultVisitedLinkColor() const { return mVisitedLinkColor; }
414 0 : nscolor FocusBackgroundColor() const { return mFocusBackgroundColor; }
415 0 : nscolor FocusTextColor() const { return mFocusTextColor; }
416 :
417 : /**
418 : * Body text color, for use in quirks mode only.
419 : */
420 0 : nscolor BodyTextColor() const { return mBodyTextColor; }
421 7 : void SetBodyTextColor(nscolor aColor) { mBodyTextColor = aColor; }
422 :
423 2 : bool GetUseFocusColors() const { return mUseFocusColors; }
424 2 : uint8_t FocusRingWidth() const { return mFocusRingWidth; }
425 2 : bool GetFocusRingOnAnything() const { return mFocusRingOnAnything; }
426 2 : uint8_t GetFocusRingStyle() const { return mFocusRingStyle; }
427 :
428 : void SetContainer(nsIDocShell* aContainer);
429 :
430 : virtual nsISupports* GetContainerWeakExternal() const;
431 : nsISupports* GetContainerWeakInternal() const;
432 : #ifdef MOZILLA_INTERNAL_API
433 443 : nsISupports* GetContainerWeak() const
434 443 : { return GetContainerWeakInternal(); }
435 : #else
436 : nsISupports* GetContainerWeak() const
437 : { return GetContainerWeakExternal(); }
438 : #endif
439 :
440 : nsIDocShell* GetDocShell() const;
441 :
442 : // XXX this are going to be replaced with set/get container
443 15 : void SetLinkHandler(nsILinkHandler* aHandler) { mLinkHandler = aHandler; }
444 0 : nsILinkHandler* GetLinkHandler() { return mLinkHandler; }
445 :
446 : /**
447 : * Detach this pres context - i.e. cancel relevant timers,
448 : * SetLinkHandler(null), SetContainer(null) etc.
449 : * Only to be used by the DocumentViewer.
450 : */
451 : virtual void Detach();
452 :
453 : /**
454 : * Get the visible area associated with this presentation context.
455 : * This is the size of the visible area that is used for
456 : * presenting the document. The returned value is in the standard
457 : * nscoord units (as scaled by the device context).
458 : */
459 113 : nsRect GetVisibleArea() const { return mVisibleArea; }
460 :
461 : /**
462 : * Set the currently visible area. The units for r are standard
463 : * nscoord units (as scaled by the device context).
464 : */
465 74 : void SetVisibleArea(const nsRect& r) {
466 74 : if (!r.IsEqualEdges(mVisibleArea)) {
467 27 : mVisibleArea = r;
468 : // Visible area does not affect media queries when paginated.
469 27 : if (!IsPaginated() && HasCachedStyleData()) {
470 20 : mPendingViewportChange = true;
471 20 : PostMediaFeatureValuesChangedEvent();
472 : }
473 : }
474 74 : }
475 :
476 : /**
477 : * Return true if this presentation context is a paginated
478 : * context.
479 : */
480 705 : bool IsPaginated() const { return mPaginated; }
481 :
482 : /**
483 : * Sets whether the presentation context can scroll for a paginated
484 : * context.
485 : */
486 : void SetPaginatedScrolling(bool aResult);
487 :
488 : /**
489 : * Return true if this presentation context can scroll for paginated
490 : * context.
491 : */
492 0 : bool HasPaginatedScrolling() const { return mCanPaginatedScroll; }
493 :
494 : /**
495 : * Get/set the size of a page
496 : */
497 0 : nsSize GetPageSize() { return mPageSize; }
498 0 : void SetPageSize(nsSize aSize) { mPageSize = aSize; }
499 :
500 : /**
501 : * Get/set whether this document should be treated as having real pages
502 : * XXX This raises the obvious question of why a document that isn't a page
503 : * is paginated; there isn't a good reason except history
504 : */
505 89 : bool IsRootPaginatedDocument() { return mIsRootPaginatedDocument; }
506 0 : void SetIsRootPaginatedDocument(bool aIsRootPaginatedDocument)
507 0 : { mIsRootPaginatedDocument = aIsRootPaginatedDocument; }
508 :
509 : /**
510 : * Get/set the print scaling level; used by nsPageFrame to scale up
511 : * pages. Set safe to call before reflow, get guaranteed to be set
512 : * properly after reflow.
513 : */
514 :
515 0 : float GetPageScale() { return mPageScale; }
516 0 : void SetPageScale(float aScale) { mPageScale = aScale; }
517 :
518 : /**
519 : * Get/set the scaling facor to use when rendering the pages for print preview.
520 : * Only safe to get after print preview set up; safe to set anytime.
521 : * This is a scaling factor for the display of the print preview. It
522 : * does not affect layout. It only affects the size of the onscreen pages
523 : * in print preview.
524 : * XXX Temporary: see http://wiki.mozilla.org/Gecko:PrintPreview
525 : */
526 0 : float GetPrintPreviewScale() { return mPPScale; }
527 0 : void SetPrintPreviewScale(float aScale) { mPPScale = aScale; }
528 :
529 1606 : nsDeviceContext* DeviceContext() const { return mDeviceContext; }
530 234 : mozilla::EventStateManager* EventStateManager() { return mEventManager; }
531 73 : nsIAtom* GetLanguageFromCharset() const { return mLanguage; }
532 : already_AddRefed<nsIAtom> GetContentLanguage() const;
533 :
534 : /**
535 : * Get/set a text zoom factor that is applied on top of the normal text zoom
536 : * set by the front-end/user.
537 : */
538 : float GetSystemFontScale() const { return mSystemFontScale; }
539 24 : void SetSystemFontScale(float aFontScale) {
540 24 : MOZ_ASSERT(aFontScale > 0.0f, "invalid font scale");
541 24 : if (aFontScale == mSystemFontScale || IsPrintingOrPrintPreview()) {
542 24 : return;
543 : }
544 :
545 0 : mSystemFontScale = aFontScale;
546 0 : UpdateEffectiveTextZoom();
547 : }
548 :
549 : /**
550 : * Get/set the text zoom factor in use.
551 : * This value should be used if you're interested in the pure text zoom value
552 : * controlled by the front-end, e.g. when transferring zoom levels to a new
553 : * document.
554 : * Code that wants to use this value for layouting and rendering purposes
555 : * should consider using EffectiveTextZoom() instead, so as to take the system
556 : * font scale into account as well.
557 : */
558 12 : float TextZoom() const { return mTextZoom; }
559 28 : void SetTextZoom(float aZoom) {
560 28 : MOZ_ASSERT(aZoom > 0.0f, "invalid zoom factor");
561 28 : if (aZoom == mTextZoom)
562 28 : return;
563 :
564 0 : mTextZoom = aZoom;
565 0 : UpdateEffectiveTextZoom();
566 : }
567 :
568 : protected:
569 : void UpdateEffectiveTextZoom();
570 :
571 : public:
572 : /**
573 : * Corresponds to the product of text zoom and system font scale, limited
574 : * by zoom.maxPercent and minPercent.
575 : * As the system font scale is automatically set by the PresShell, code that
576 : * e.g. wants to transfer zoom levels to a new document should use TextZoom()
577 : * instead, which corresponds to the text zoom level that was actually set by
578 : * the front-end/user.
579 : */
580 79 : float EffectiveTextZoom() const { return mEffectiveTextZoom; }
581 :
582 : /**
583 : * Get the minimum font size for the specified language. If aLanguage
584 : * is nullptr, then the document's language is used. This combines
585 : * the language-specific global preference with the per-presentation
586 : * base minimum font size.
587 : */
588 23 : int32_t MinFontSize(nsIAtom *aLanguage, bool* aNeedsToCache = nullptr) const {
589 23 : const LangGroupFontPrefs *prefs = GetFontPrefsForLang(aLanguage, aNeedsToCache);
590 23 : if (aNeedsToCache && *aNeedsToCache) {
591 0 : return 0;
592 : }
593 23 : return std::max(mBaseMinFontSize, prefs->mMinimumFontSize);
594 : }
595 :
596 : /**
597 : * Get the per-presentation base minimum font size. This size is
598 : * independent of the language-specific global preference.
599 : */
600 4 : int32_t BaseMinFontSize() const {
601 4 : return mBaseMinFontSize;
602 : }
603 :
604 : /**
605 : * Set the per-presentation base minimum font size. This size is
606 : * independent of the language-specific global preference.
607 : */
608 28 : void SetBaseMinFontSize(int32_t aMinFontSize) {
609 28 : if (aMinFontSize == mBaseMinFontSize)
610 28 : return;
611 :
612 0 : mBaseMinFontSize = aMinFontSize;
613 0 : if (HasCachedStyleData()) {
614 : // Media queries could have changed, since we changed the meaning
615 : // of 'em' units in them.
616 0 : MediaFeatureValuesChanged(eRestyle_ForceDescendants,
617 0 : NS_STYLE_HINT_REFLOW);
618 : }
619 : }
620 :
621 69 : float GetFullZoom() { return mFullZoom; }
622 : void SetFullZoom(float aZoom);
623 :
624 212 : float GetOverrideDPPX() { return mOverrideDPPX; }
625 : void SetOverrideDPPX(float aDPPX);
626 :
627 1 : nscoord GetAutoQualityMinFontSize() {
628 1 : return DevPixelsToAppUnits(mAutoQualityMinFontSizePixelsPref);
629 : }
630 :
631 : /**
632 : * Return the device's screen size in inches, for font size
633 : * inflation.
634 : *
635 : * If |aChanged| is non-null, then aChanged is filled in with whether
636 : * the screen size value has changed since either:
637 : * a. the last time the function was called with non-null aChanged, or
638 : * b. the first time the function was called.
639 : */
640 : gfxSize ScreenSizeInchesForFontInflation(bool* aChanged = nullptr);
641 :
642 4806 : static int32_t AppUnitsPerCSSPixel() { return mozilla::AppUnitsPerCSSPixel(); }
643 : int32_t AppUnitsPerDevPixel() const;
644 129 : static int32_t AppUnitsPerCSSInch() { return mozilla::AppUnitsPerCSSInch(); }
645 :
646 1020 : static nscoord CSSPixelsToAppUnits(int32_t aPixels)
647 2040 : { return NSToCoordRoundWithClamp(float(aPixels) *
648 2040 : float(AppUnitsPerCSSPixel())); }
649 :
650 2806 : static nscoord CSSPixelsToAppUnits(float aPixels)
651 2806 : { return NSToCoordRoundWithClamp(aPixels *
652 5612 : float(AppUnitsPerCSSPixel())); }
653 :
654 278 : static int32_t AppUnitsToIntCSSPixels(nscoord aAppUnits)
655 278 : { return NSAppUnitsToIntPixels(aAppUnits,
656 556 : float(AppUnitsPerCSSPixel())); }
657 :
658 295 : static float AppUnitsToFloatCSSPixels(nscoord aAppUnits)
659 295 : { return NSAppUnitsToFloatPixels(aAppUnits,
660 590 : float(AppUnitsPerCSSPixel())); }
661 :
662 0 : static double AppUnitsToDoubleCSSPixels(nscoord aAppUnits)
663 0 : { return NSAppUnitsToDoublePixels(aAppUnits,
664 0 : double(AppUnitsPerCSSPixel())); }
665 :
666 2474 : nscoord DevPixelsToAppUnits(int32_t aPixels) const
667 2474 : { return NSIntPixelsToAppUnits(aPixels, AppUnitsPerDevPixel()); }
668 :
669 162 : int32_t AppUnitsToDevPixels(nscoord aAppUnits) const
670 162 : { return NSAppUnitsToIntPixels(aAppUnits,
671 324 : float(AppUnitsPerDevPixel())); }
672 :
673 18 : float AppUnitsToFloatDevPixels(nscoord aAppUnits)
674 18 : { return aAppUnits / float(AppUnitsPerDevPixel()); }
675 :
676 52 : int32_t CSSPixelsToDevPixels(int32_t aPixels)
677 52 : { return AppUnitsToDevPixels(CSSPixelsToAppUnits(aPixels)); }
678 :
679 0 : float CSSPixelsToDevPixels(float aPixels)
680 : {
681 0 : return NSAppUnitsToFloatPixels(CSSPixelsToAppUnits(aPixels),
682 0 : float(AppUnitsPerDevPixel()));
683 : }
684 :
685 16 : int32_t DevPixelsToIntCSSPixels(int32_t aPixels)
686 16 : { return AppUnitsToIntCSSPixels(DevPixelsToAppUnits(aPixels)); }
687 :
688 : float DevPixelsToFloatCSSPixels(int32_t aPixels)
689 : { return AppUnitsToFloatCSSPixels(DevPixelsToAppUnits(aPixels)); }
690 :
691 28 : mozilla::CSSToLayoutDeviceScale CSSToDevPixelScale() const
692 : {
693 : return mozilla::CSSToLayoutDeviceScale(
694 28 : float(AppUnitsPerCSSPixel()) / float(AppUnitsPerDevPixel()));
695 : }
696 :
697 : // If there is a remainder, it is rounded to nearest app units.
698 : nscoord GfxUnitsToAppUnits(gfxFloat aGfxUnits) const;
699 :
700 : gfxFloat AppUnitsToGfxUnits(nscoord aAppUnits) const;
701 :
702 39 : gfxRect AppUnitsToGfxUnits(const nsRect& aAppRect) const
703 39 : { return gfxRect(AppUnitsToGfxUnits(aAppRect.x),
704 39 : AppUnitsToGfxUnits(aAppRect.y),
705 39 : AppUnitsToGfxUnits(aAppRect.width),
706 156 : AppUnitsToGfxUnits(aAppRect.height)); }
707 :
708 73 : static nscoord CSSTwipsToAppUnits(float aTwips)
709 146 : { return NSToCoordRoundWithClamp(
710 219 : mozilla::AppUnitsPerCSSInch() * NS_TWIPS_TO_INCHES(aTwips)); }
711 :
712 : // Margin-specific version, since they often need TwipsToAppUnits
713 0 : static nsMargin CSSTwipsToAppUnits(const nsIntMargin &marginInTwips)
714 0 : { return nsMargin(CSSTwipsToAppUnits(float(marginInTwips.top)),
715 0 : CSSTwipsToAppUnits(float(marginInTwips.right)),
716 0 : CSSTwipsToAppUnits(float(marginInTwips.bottom)),
717 0 : CSSTwipsToAppUnits(float(marginInTwips.left))); }
718 :
719 0 : static nscoord CSSPointsToAppUnits(float aPoints)
720 0 : { return NSToCoordRound(aPoints * mozilla::AppUnitsPerCSSInch() /
721 0 : POINTS_PER_INCH_FLOAT); }
722 :
723 15 : nscoord RoundAppUnitsToNearestDevPixels(nscoord aAppUnits) const
724 15 : { return DevPixelsToAppUnits(AppUnitsToDevPixels(aAppUnits)); }
725 :
726 : /**
727 : * This checks the root element and the HTML BODY, if any, for an "overflow"
728 : * property that should be applied to the viewport. If one is found then we
729 : * return the element that we took the overflow from (which should then be
730 : * treated as "overflow: visible"), and we store the overflow style here.
731 : * If the document is in fullscreen, and the fullscreen element is not the
732 : * root, the scrollbar of viewport will be suppressed.
733 : * @return if scroll was propagated from some content node, the content node
734 : * it was propagated from.
735 : */
736 : nsIContent* UpdateViewportScrollbarStylesOverride();
737 :
738 : /**
739 : * Returns the cached result from the last call to
740 : * UpdateViewportScrollbarStylesOverride() -- i.e. return the node
741 : * whose scrollbar styles we have propagated to the viewport (or nullptr if
742 : * there is no such node).
743 : */
744 66 : nsIContent* GetViewportScrollbarStylesOverrideNode() const {
745 66 : return mViewportScrollbarOverrideNode;
746 : }
747 :
748 88 : const ScrollbarStyles& GetViewportScrollbarStylesOverride() const
749 : {
750 88 : return mViewportStyleScrollbar;
751 : }
752 :
753 : /**
754 : * Check whether the given element would propagate its scrollbar styles to the
755 : * viewport in non-paginated mode. Must only be called if IsPaginated().
756 : */
757 : bool ElementWouldPropagateScrollbarStyles(mozilla::dom::Element* aElement);
758 :
759 : /**
760 : * Set and get methods for controlling the background drawing
761 : */
762 386 : bool GetBackgroundImageDraw() const { return mDrawImageBackground; }
763 0 : void SetBackgroundImageDraw(bool aCanDraw)
764 : {
765 0 : mDrawImageBackground = aCanDraw;
766 0 : }
767 :
768 431 : bool GetBackgroundColorDraw() const { return mDrawColorBackground; }
769 0 : void SetBackgroundColorDraw(bool aCanDraw)
770 : {
771 0 : mDrawColorBackground = aCanDraw;
772 0 : }
773 :
774 : /**
775 : * Check if bidi enabled (set depending on the presence of RTL
776 : * characters or when default directionality is RTL).
777 : * If enabled, we should apply the Unicode Bidi Algorithm
778 : *
779 : * @lina 07/12/2000
780 : */
781 : #ifdef MOZILLA_INTERNAL_API
782 386 : bool BidiEnabled() const { return BidiEnabledInternal(); }
783 : #else
784 : bool BidiEnabled() const { return BidiEnabledExternal(); }
785 : #endif
786 : virtual bool BidiEnabledExternal() const;
787 : bool BidiEnabledInternal() const;
788 :
789 : /**
790 : * Set bidi enabled. This means we should apply the Unicode Bidi Algorithm
791 : *
792 : * @lina 07/12/2000
793 : */
794 : void SetBidiEnabled() const;
795 :
796 : /**
797 : * Set visual or implicit mode into the pres context.
798 : *
799 : * Visual directionality is a presentation method that displays text
800 : * as if it were a uni-directional, according to the primary display
801 : * direction only.
802 : *
803 : * Implicit directionality is a presentation method in which the
804 : * direction is determined by the Bidi algorithm according to the
805 : * category of the characters and the category of the adjacent
806 : * characters, and according to their primary direction.
807 : *
808 : * @lina 05/02/2000
809 : */
810 30 : void SetVisualMode(bool aIsVisual)
811 : {
812 30 : mIsVisual = aIsVisual;
813 30 : }
814 :
815 : /**
816 : * Check whether the content should be treated as visual.
817 : *
818 : * @lina 05/02/2000
819 : */
820 0 : bool IsVisualMode() const { return mIsVisual; }
821 :
822 : enum class InteractionType : uint32_t {
823 : eClickInteraction,
824 : eKeyInteraction,
825 : eMouseMoveInteraction,
826 : eScrollInteraction
827 : };
828 :
829 : void RecordInteractionTime(InteractionType aType,
830 : const mozilla::TimeStamp& aTimeStamp);
831 :
832 0 : void DisableInteractionTimeRecording()
833 : {
834 0 : mInteractionTimeEnabled = false;
835 0 : }
836 :
837 : //Mohamed
838 :
839 : /**
840 : * Set the Bidi options for the presentation context
841 : */
842 : void SetBidi(uint32_t aBidiOptions,
843 : bool aForceRestyle = false);
844 :
845 : /**
846 : * Get the Bidi options for the presentation context
847 : * Not inline so consumers of nsPresContext are not forced to
848 : * include nsIDocument.
849 : */
850 : uint32_t GetBidi() const;
851 :
852 : /**
853 : * Render only Selection
854 : */
855 0 : void SetIsRenderingOnlySelection(bool aResult)
856 : {
857 0 : mIsRenderingOnlySelection = aResult;
858 0 : }
859 :
860 53 : bool IsRenderingOnlySelection() const { return mIsRenderingOnlySelection; }
861 :
862 : bool IsTopLevelWindowInactive();
863 :
864 : /*
865 : * Obtain a native them for rendering our widgets (both form controls and html)
866 : */
867 : nsITheme* GetTheme();
868 :
869 : /*
870 : * Notify the pres context that the theme has changed. An internal switch
871 : * means it's one of our Mozilla themes that changed (e.g., Modern to Classic).
872 : * Otherwise, the OS is telling us that the native theme for the platform
873 : * has changed.
874 : */
875 : void ThemeChanged();
876 :
877 : /*
878 : * Notify the pres context that the resolution of the user interface has
879 : * changed. This happens if a window is moved between HiDPI and non-HiDPI
880 : * displays, so that the ratio of points to device pixels changes.
881 : * The notification happens asynchronously.
882 : */
883 : void UIResolutionChanged();
884 :
885 : /*
886 : * Like UIResolutionChanged() but invalidates values immediately.
887 : */
888 : void UIResolutionChangedSync();
889 :
890 : /*
891 : * Notify the pres context that a system color has changed
892 : */
893 : void SysColorChanged();
894 :
895 : /** Printing methods below should only be used for Medium() == print **/
896 : void SetPrintSettings(nsIPrintSettings *aPrintSettings);
897 :
898 0 : nsIPrintSettings* GetPrintSettings() { return mPrintSettings; }
899 :
900 : /* Helper function that ensures that this prescontext is shown in its
901 : docshell if it's the most recent prescontext for the docshell. Returns
902 : whether the prescontext is now being shown.
903 : */
904 : bool EnsureVisible();
905 :
906 : #ifdef MOZ_REFLOW_PERF
907 : void CountReflows(const char * aName,
908 : nsIFrame * aFrame);
909 : #endif
910 :
911 666 : void ConstructedFrame() {
912 666 : ++mFramesConstructed;
913 666 : }
914 635 : void ReflowedFrame() {
915 635 : ++mFramesReflowed;
916 635 : }
917 :
918 0 : uint64_t FramesConstructedCount() {
919 0 : return mFramesConstructed;
920 : }
921 0 : uint64_t FramesReflowedCount() {
922 0 : return mFramesReflowed;
923 : }
924 :
925 : /*
926 : * Helper functions for a telemetry scroll probe
927 : * for more information see bug 1340904
928 : */
929 0 : void SetTelemetryScrollY(nscoord aScrollY)
930 : {
931 0 : nscoord delta = abs(aScrollY - mTelemetryScrollLastY);
932 0 : mTelemetryScrollLastY = aScrollY;
933 :
934 0 : mTelemetryScrollTotalY += delta;
935 0 : if (aScrollY > mTelemetryScrollMaxY) {
936 0 : mTelemetryScrollMaxY = aScrollY;
937 : }
938 0 : }
939 1 : nscoord TelemetryScrollMaxY() const
940 : {
941 1 : return mTelemetryScrollMaxY;
942 : }
943 1 : nscoord TelemetryScrollTotalY() const
944 : {
945 1 : return mTelemetryScrollTotalY;
946 : }
947 :
948 760 : static nscoord GetBorderWidthForKeyword(unsigned int aBorderWidthKeyword)
949 : {
950 : // This table maps border-width enums 'thin', 'medium', 'thick'
951 : // to actual nscoord values.
952 : static const nscoord kBorderWidths[] = {
953 2 : CSSPixelsToAppUnits(1),
954 2 : CSSPixelsToAppUnits(3),
955 2 : CSSPixelsToAppUnits(5)
956 766 : };
957 760 : MOZ_ASSERT(size_t(aBorderWidthKeyword) < mozilla::ArrayLength(kBorderWidths));
958 :
959 760 : return kBorderWidths[aBorderWidthKeyword];
960 : }
961 :
962 516 : gfxTextPerfMetrics *GetTextPerfMetrics() { return mTextPerf; }
963 :
964 18223 : bool IsDynamic() { return (mType == eContext_PageLayout || mType == eContext_Galley); }
965 97 : bool IsScreen() { return (mMedium == nsGkAtoms::screen ||
966 97 : mType == eContext_PageLayout ||
967 97 : mType == eContext_PrintPreview); }
968 0 : bool IsPrintingOrPrintPreview() { return (mType == eContext_Print || mType == eContext_PrintPreview); }
969 :
970 : // Is this presentation in a chrome docshell?
971 1345 : bool IsChrome() const { return mIsChrome; }
972 3 : bool IsChromeOriginImage() const { return mIsChromeOriginImage; }
973 : void UpdateIsChrome();
974 :
975 : // Public API for native theme code to get style internals.
976 : bool HasAuthorSpecifiedRules(const nsIFrame *aFrame,
977 : uint32_t ruleTypeMask) const;
978 :
979 : // Is it OK to let the page specify colors and backgrounds?
980 644 : bool UseDocumentColors() const {
981 644 : MOZ_ASSERT(mUseDocumentColors || !(IsChrome() || IsChromeOriginImage()),
982 : "We should never have a chrome doc or image that can't use its colors.");
983 644 : return mUseDocumentColors;
984 : }
985 :
986 : // Explicitly enable and disable paint flashing.
987 0 : void SetPaintFlashing(bool aPaintFlashing) {
988 0 : mPaintFlashing = aPaintFlashing;
989 0 : mPaintFlashingInitialized = true;
990 0 : }
991 :
992 : // This method should be used instead of directly accessing mPaintFlashing,
993 : // as that value may be out of date when mPaintFlashingInitialized is false.
994 : bool GetPaintFlashing() const;
995 :
996 20 : bool SuppressingResizeReflow() const { return mSuppressResizeReflow; }
997 :
998 : gfxUserFontSet* GetUserFontSet(bool aFlushUserFontSet = true);
999 :
1000 : // Should be called whenever the set of fonts available in the user
1001 : // font set changes (e.g., because a new font loads, or because the
1002 : // user font set is changed and fonts become unavailable).
1003 : void UserFontSetUpdated(gfxUserFontEntry* aUpdatedFont = nullptr);
1004 :
1005 21 : gfxMissingFontRecorder *MissingFontRecorder() { return mMissingFonts; }
1006 : void NotifyMissingFonts();
1007 :
1008 : void FlushCounterStyles();
1009 : void RebuildCounterStyles(); // asynchronously
1010 :
1011 : // Ensure that it is safe to hand out CSS rules outside the layout
1012 : // engine by ensuring that all CSS style sheets have unique inners
1013 : // and, if necessary, synchronously rebuilding all style data.
1014 : void EnsureSafeToHandOutCSSRules();
1015 :
1016 : // Mark an area as invalidated, associated with a given transaction id (allocated
1017 : // by nsRefreshDriver::GetTransactionId).
1018 : // Invalidated regions will be dispatched to MozAfterPaint events when
1019 : // NotifyDidPaintForSubtree is called for the transaction id (or any higher id).
1020 : void NotifyInvalidation(uint64_t aTransactionId, const nsRect& aRect);
1021 : // aRect is in device pixels
1022 : void NotifyInvalidation(uint64_t aTransactionId, const nsIntRect& aRect);
1023 : void NotifyDidPaintForSubtree(uint64_t aTransactionId = 0,
1024 : const mozilla::TimeStamp& aTimeStamp = mozilla::TimeStamp());
1025 : void FireDOMPaintEvent(nsTArray<nsRect>* aList, uint64_t aTransactionId,
1026 : mozilla::TimeStamp aTimeStamp = mozilla::TimeStamp());
1027 :
1028 : // Callback for catching invalidations in ContainerLayers
1029 : // Passed to LayerProperties::ComputeDifference
1030 : static void NotifySubDocInvalidation(mozilla::layers::ContainerLayer* aContainer,
1031 : const nsIntRegion& aRegion);
1032 : void SetNotifySubDocInvalidationData(mozilla::layers::ContainerLayer* aContainer);
1033 : static void ClearNotifySubDocInvalidationData(mozilla::layers::ContainerLayer* aContainer);
1034 : bool IsDOMPaintEventPending();
1035 :
1036 : /**
1037 : * Returns the RestyleManager's restyle generation counter.
1038 : */
1039 : uint64_t GetRestyleGeneration() const;
1040 : uint64_t GetUndisplayedRestyleGeneration() const;
1041 :
1042 : /**
1043 : * Returns whether there are any pending restyles or reflows.
1044 : */
1045 : bool HasPendingRestyleOrReflow();
1046 :
1047 : /**
1048 : * Informs the document's FontFaceSet that the refresh driver ticked,
1049 : * flushing style and layout.
1050 : */
1051 : void NotifyFontFaceSetOnRefresh();
1052 :
1053 : /**
1054 : * Notify the prescontext that the presshell is about to reflow a reflow root.
1055 : * The single argument indicates whether this reflow should be interruptible.
1056 : * If aInterruptible is false then CheckForInterrupt and HasPendingInterrupt
1057 : * will always return false. If aInterruptible is true then CheckForInterrupt
1058 : * will return true when a pending event is detected. This is for use by the
1059 : * presshell only. Reflow code wanting to prevent interrupts should use
1060 : * InterruptPreventer.
1061 : */
1062 : void ReflowStarted(bool aInterruptible);
1063 :
1064 : /**
1065 : * A class that can be used to temporarily disable reflow interruption.
1066 : */
1067 : class InterruptPreventer;
1068 : friend class InterruptPreventer;
1069 : class MOZ_STACK_CLASS InterruptPreventer {
1070 : public:
1071 4 : explicit InterruptPreventer(nsPresContext* aCtx) :
1072 : mCtx(aCtx),
1073 : mInterruptsEnabled(aCtx->mInterruptsEnabled),
1074 4 : mHasPendingInterrupt(aCtx->mHasPendingInterrupt)
1075 : {
1076 4 : mCtx->mInterruptsEnabled = false;
1077 4 : mCtx->mHasPendingInterrupt = false;
1078 4 : }
1079 8 : ~InterruptPreventer() {
1080 4 : mCtx->mInterruptsEnabled = mInterruptsEnabled;
1081 4 : mCtx->mHasPendingInterrupt = mHasPendingInterrupt;
1082 4 : }
1083 :
1084 : private:
1085 : nsPresContext* mCtx;
1086 : bool mInterruptsEnabled;
1087 : bool mHasPendingInterrupt;
1088 : };
1089 :
1090 : /**
1091 : * Check for interrupts. This may return true if a pending event is
1092 : * detected. Once it has returned true, it will keep returning true
1093 : * until ReflowStarted is called. In all cases where this returns true,
1094 : * the passed-in frame (which should be the frame whose reflow will be
1095 : * interrupted if true is returned) will be passed to
1096 : * nsIPresShell::FrameNeedsToContinueReflow.
1097 : */
1098 : bool CheckForInterrupt(nsIFrame* aFrame);
1099 : /**
1100 : * Returns true if CheckForInterrupt has returned true since the last
1101 : * ReflowStarted call. Cannot itself trigger an interrupt check.
1102 : */
1103 479 : bool HasPendingInterrupt() { return mHasPendingInterrupt; }
1104 : /**
1105 : * Sets a flag that will trip a reflow interrupt. This only bypasses the
1106 : * interrupt timeout and the pending event check; other checks such as whether
1107 : * interrupts are enabled and the interrupt check skipping still take effect.
1108 : */
1109 0 : void SetPendingInterruptFromTest() { mPendingInterruptFromTest = true; }
1110 :
1111 : /**
1112 : * If we have a presshell, and if the given content's current
1113 : * document is the same as our presshell's document, return the
1114 : * content's primary frame. Otherwise, return null. Only use this
1115 : * if you care about which presshell the primary frame is in.
1116 : */
1117 : nsIFrame* GetPrimaryFrameFor(nsIContent* aContent);
1118 :
1119 : virtual size_t SizeOfExcludingThis(mozilla::MallocSizeOf aMallocSizeOf) const;
1120 21 : virtual size_t SizeOfIncludingThis(mozilla::MallocSizeOf aMallocSizeOf) const {
1121 21 : return aMallocSizeOf(this) + SizeOfExcludingThis(aMallocSizeOf);
1122 : }
1123 :
1124 : bool IsRootContentDocument() const;
1125 :
1126 26 : bool HadNonBlankPaint() const {
1127 26 : return mHadNonBlankPaint;
1128 : }
1129 :
1130 : void NotifyNonBlankPaint();
1131 :
1132 62 : bool IsGlyph() const {
1133 62 : return mIsGlyph;
1134 : }
1135 :
1136 0 : void SetIsGlyph(bool aValue) {
1137 0 : mIsGlyph = aValue;
1138 0 : }
1139 :
1140 109 : bool UsesRootEMUnits() const {
1141 109 : return mUsesRootEMUnits;
1142 : }
1143 :
1144 0 : void SetUsesRootEMUnits(bool aValue) {
1145 0 : mUsesRootEMUnits = aValue;
1146 0 : }
1147 :
1148 0 : bool UsesExChUnits() const {
1149 0 : return mUsesExChUnits;
1150 : }
1151 :
1152 8 : void SetUsesExChUnits(bool aValue) {
1153 8 : mUsesExChUnits = aValue;
1154 8 : }
1155 :
1156 : bool UsesViewportUnits() const {
1157 : return mUsesViewportUnits;
1158 : }
1159 :
1160 0 : void SetUsesViewportUnits(bool aValue) {
1161 0 : mUsesViewportUnits = aValue;
1162 0 : }
1163 :
1164 : // true if there are OMTA transition updates for the current document which
1165 : // have been throttled, and therefore some style information may not be up
1166 : // to date
1167 : bool ExistThrottledUpdates() const {
1168 : return mExistThrottledUpdates;
1169 : }
1170 :
1171 : void SetExistThrottledUpdates(bool aExistThrottledUpdates) {
1172 : mExistThrottledUpdates = aExistThrottledUpdates;
1173 : }
1174 :
1175 : bool IsDeviceSizePageSize();
1176 :
1177 0 : bool HasWarnedAboutPositionedTableParts() const {
1178 0 : return mHasWarnedAboutPositionedTableParts;
1179 : }
1180 :
1181 0 : void SetHasWarnedAboutPositionedTableParts() {
1182 0 : mHasWarnedAboutPositionedTableParts = true;
1183 0 : }
1184 :
1185 0 : bool HasWarnedAboutTooLargeDashedOrDottedRadius() const {
1186 0 : return mHasWarnedAboutTooLargeDashedOrDottedRadius;
1187 : }
1188 :
1189 0 : void SetHasWarnedAboutTooLargeDashedOrDottedRadius() {
1190 0 : mHasWarnedAboutTooLargeDashedOrDottedRadius = true;
1191 0 : }
1192 :
1193 : nsBidi& GetBidiEngine();
1194 :
1195 : protected:
1196 : friend class nsRunnableMethod<nsPresContext>;
1197 : void ThemeChangedInternal();
1198 : void SysColorChangedInternal();
1199 :
1200 : // update device context's resolution from the widget
1201 : void UIResolutionChangedInternal();
1202 :
1203 : // if aScale > 0.0, use it as resolution scale factor to the device context
1204 : // (otherwise get it from the widget)
1205 : void UIResolutionChangedInternalScale(double aScale);
1206 :
1207 : // aData here is a pointer to a double that holds the CSS to device-pixel
1208 : // scale factor from the parent, which will be applied to the subdocument's
1209 : // device context instead of retrieving a scale from the widget.
1210 : static bool
1211 : UIResolutionChangedSubdocumentCallback(nsIDocument* aDocument, void* aData);
1212 :
1213 : void SetImgAnimations(nsIContent *aParent, uint16_t aMode);
1214 : void SetSMILAnimations(nsIDocument *aDoc, uint16_t aNewMode,
1215 : uint16_t aOldMode);
1216 : void GetDocumentColorPreferences();
1217 :
1218 : void PreferenceChanged(const char* aPrefName);
1219 : static void PrefChangedCallback(const char*, void*);
1220 :
1221 : void UpdateAfterPreferencesChanged();
1222 : static void PrefChangedUpdateTimerCallback(nsITimer *aTimer, void *aClosure);
1223 :
1224 : void GetUserPreferences();
1225 :
1226 : /**
1227 : * Fetch the user's font preferences for the given aLanguage's
1228 : * langugage group.
1229 : */
1230 120 : const LangGroupFontPrefs* GetFontPrefsForLang(nsIAtom *aLanguage, bool* aNeedsToCache = nullptr) const
1231 : {
1232 120 : nsIAtom* lang = aLanguage ? aLanguage : mLanguage.get();
1233 120 : return StaticPresData::Get()->GetFontPrefsForLangHelper(lang, &mLangGroupFontPrefs, aNeedsToCache);
1234 : }
1235 :
1236 : void UpdateCharSet(NotNull<const Encoding*> aCharSet);
1237 :
1238 : static bool NotifyDidPaintSubdocumentCallback(nsIDocument* aDocument, void* aData);
1239 :
1240 : public:
1241 : void DoChangeCharSet(NotNull<const Encoding*> aCharSet);
1242 :
1243 : /**
1244 : * Checks for MozAfterPaint listeners on the document
1245 : */
1246 : bool MayHavePaintEventListener();
1247 :
1248 : /**
1249 : * Checks for MozAfterPaint listeners on the document and
1250 : * any subdocuments, except for subdocuments that are non-top-level
1251 : * content documents.
1252 : */
1253 : bool MayHavePaintEventListenerInSubDocument();
1254 :
1255 : #ifdef RESTYLE_LOGGING
1256 : // Controls for whether debug information about restyling in this
1257 : // document should be output.
1258 12245 : bool RestyleLoggingEnabled() const { return mRestyleLoggingEnabled; }
1259 : void StartRestyleLogging() { mRestyleLoggingEnabled = true; }
1260 : void StopRestyleLogging() { mRestyleLoggingEnabled = false; }
1261 : #endif
1262 :
1263 : void InvalidatePaintedLayers();
1264 :
1265 : protected:
1266 : // May be called multiple times (unlink, destructor)
1267 : void Destroy();
1268 :
1269 : void AppUnitsPerDevPixelChanged();
1270 :
1271 0 : void HandleRebuildCounterStyles() {
1272 0 : mPostedFlushCounterStyles = false;
1273 0 : FlushCounterStyles();
1274 0 : }
1275 :
1276 : bool HavePendingInputEvent();
1277 :
1278 : // Can't be inline because we can't include nsStyleSet.h.
1279 : bool HasCachedStyleData();
1280 :
1281 : // Creates a one-shot timer with the given aCallback & aDelay.
1282 : // Returns a refcounted pointer to the timer (or nullptr on failure).
1283 : already_AddRefed<nsITimer> CreateTimer(nsTimerCallbackFunc aCallback,
1284 : const char* aName,
1285 : uint32_t aDelay);
1286 :
1287 : // IMPORTANT: The ownership implicit in the following member variables
1288 : // has been explicitly checked. If you add any members to this class,
1289 : // please make the ownership explicit (pinkerton, scc).
1290 :
1291 : nsPresContextType mType;
1292 : // the nsPresShell owns a strong reference to the nsPresContext, and is responsible
1293 : // for nulling this pointer before it is destroyed
1294 : nsIPresShell* MOZ_NON_OWNING_REF mShell; // [WEAK]
1295 : nsCOMPtr<nsIDocument> mDocument;
1296 : RefPtr<nsDeviceContext> mDeviceContext; // [STRONG] could be weak, but
1297 : // better safe than sorry.
1298 : // Cannot reintroduce cycles
1299 : // since there is no dependency
1300 : // from gfx back to layout.
1301 : RefPtr<mozilla::EventStateManager> mEventManager;
1302 : RefPtr<nsRefreshDriver> mRefreshDriver;
1303 : RefPtr<mozilla::EffectCompositor> mEffectCompositor;
1304 : RefPtr<nsTransitionManager> mTransitionManager;
1305 : RefPtr<nsAnimationManager> mAnimationManager;
1306 : RefPtr<mozilla::RestyleManager> mRestyleManager;
1307 : RefPtr<mozilla::CounterStyleManager> mCounterStyleManager;
1308 : nsIAtom* MOZ_UNSAFE_REF("always a static atom") mMedium; // initialized by subclass ctors
1309 : nsCOMPtr<nsIAtom> mMediaEmulated;
1310 :
1311 : // This pointer is nulled out through SetLinkHandler() in the destructors of
1312 : // the classes which set it. (using SetLinkHandler() again).
1313 : nsILinkHandler* MOZ_NON_OWNING_REF mLinkHandler;
1314 :
1315 : // Formerly mLangGroup; moving from charset-oriented langGroup to
1316 : // maintaining actual language settings everywhere (see bug 524107).
1317 : // This may in fact hold a langGroup such as x-western rather than
1318 : // a specific language, however (e.g, if it is inferred from the
1319 : // charset rather than explicitly specified as a lang attribute).
1320 : nsCOMPtr<nsIAtom> mLanguage;
1321 :
1322 : public:
1323 : // The following are public member variables so that we can use them
1324 : // with mozilla::AutoToggle or mozilla::AutoRestore.
1325 :
1326 : // Should we disable font size inflation because we're inside of
1327 : // shrink-wrapping calculations on an inflation container?
1328 : bool mInflationDisabledForShrinkWrap;
1329 :
1330 : protected:
1331 :
1332 : mozilla::WeakPtr<nsDocShell> mContainer;
1333 :
1334 : // Base minimum font size, independent of the language-specific global preference. Defaults to 0
1335 : int32_t mBaseMinFontSize;
1336 : float mSystemFontScale; // Internal text zoom factor, defaults to 1.0
1337 : float mTextZoom; // Text zoom, defaults to 1.0
1338 : float mEffectiveTextZoom; // Text zoom * system font scale
1339 : float mFullZoom; // Page zoom, defaults to 1.0
1340 : float mOverrideDPPX; // DPPX overrided, defaults to 0.0
1341 : gfxSize mLastFontInflationScreenSize;
1342 :
1343 : int32_t mCurAppUnitsPerDevPixel;
1344 : int32_t mAutoQualityMinFontSizePixelsPref;
1345 :
1346 : nsCOMPtr<nsITheme> mTheme;
1347 : nsLanguageAtomService* mLangService;
1348 : nsCOMPtr<nsIPrintSettings> mPrintSettings;
1349 : nsCOMPtr<nsITimer> mPrefChangedTimer;
1350 :
1351 : mozilla::UniquePtr<nsBidi> mBidiEngine;
1352 :
1353 49 : struct TransactionInvalidations {
1354 : uint64_t mTransactionId;
1355 : nsTArray<nsRect> mInvalidations;
1356 : };
1357 : AutoTArray<TransactionInvalidations, 4> mTransactions;
1358 :
1359 : // text performance metrics
1360 : nsAutoPtr<gfxTextPerfMetrics> mTextPerf;
1361 :
1362 : nsAutoPtr<gfxMissingFontRecorder> mMissingFonts;
1363 :
1364 : nsRect mVisibleArea;
1365 : nsSize mPageSize;
1366 : float mPageScale;
1367 : float mPPScale;
1368 :
1369 : nscolor mDefaultColor;
1370 : nscolor mBackgroundColor;
1371 :
1372 : nscolor mLinkColor;
1373 : nscolor mActiveLinkColor;
1374 : nscolor mVisitedLinkColor;
1375 :
1376 : nscolor mFocusBackgroundColor;
1377 : nscolor mFocusTextColor;
1378 :
1379 : nscolor mBodyTextColor;
1380 :
1381 : // This is a non-owning pointer. May be null. If non-null, it's guaranteed
1382 : // to be pointing to a node that's still alive, because we'll reset it in
1383 : // UpdateViewportScrollbarStylesOverride() as part of the cleanup code
1384 : // when this node is removed from the document. (For <body> and the root node,
1385 : // this call happens in nsCSSFrameConstructor::ContentRemoved(). For
1386 : // fullscreen elements, it happens in the fullscreen-specific cleanup
1387 : // invoked by Element::UnbindFromTree().)
1388 : nsIContent* MOZ_NON_OWNING_REF mViewportScrollbarOverrideNode;
1389 : ScrollbarStyles mViewportStyleScrollbar;
1390 :
1391 : uint8_t mFocusRingWidth;
1392 :
1393 : bool mExistThrottledUpdates;
1394 :
1395 : uint16_t mImageAnimationMode;
1396 : uint16_t mImageAnimationModePref;
1397 :
1398 : // Most documents will only use one (or very few) language groups. Rather
1399 : // than have the overhead of a hash lookup, we simply look along what will
1400 : // typically be a very short (usually of length 1) linked list. There are 31
1401 : // language groups, so in the worst case scenario we'll need to traverse 31
1402 : // link items.
1403 : LangGroupFontPrefs mLangGroupFontPrefs;
1404 :
1405 : bool mFontGroupCacheDirty;
1406 : nsTHashtable<nsRefPtrHashKey<nsIAtom>> mLanguagesUsed;
1407 :
1408 : nscoord mBorderWidthTable[3];
1409 :
1410 : uint32_t mInterruptChecksToSkip;
1411 :
1412 : // Counters for tests and tools that want to detect frame construction
1413 : // or reflow.
1414 : uint64_t mElementsRestyled;
1415 : uint64_t mFramesConstructed;
1416 : uint64_t mFramesReflowed;
1417 :
1418 : mozilla::TimeStamp mReflowStartTime;
1419 :
1420 : // Time of various first interaction types, used to report time from
1421 : // first paint of the top level content pres shell to first interaction.
1422 : mozilla::TimeStamp mFirstNonBlankPaintTime;
1423 : mozilla::TimeStamp mFirstClickTime;
1424 : mozilla::TimeStamp mFirstKeyTime;
1425 : mozilla::TimeStamp mFirstMouseMoveTime;
1426 : mozilla::TimeStamp mFirstScrollTime;
1427 : bool mInteractionTimeEnabled;
1428 :
1429 : // last time we did a full style flush
1430 : mozilla::TimeStamp mLastStyleUpdateForAllAnimations;
1431 :
1432 : nscoord mTelemetryScrollLastY;
1433 : nscoord mTelemetryScrollMaxY;
1434 : nscoord mTelemetryScrollTotalY;
1435 :
1436 : unsigned mHasPendingInterrupt : 1;
1437 : unsigned mPendingInterruptFromTest : 1;
1438 : unsigned mInterruptsEnabled : 1;
1439 : unsigned mUseDocumentFonts : 1;
1440 : unsigned mUseDocumentColors : 1;
1441 : unsigned mUnderlineLinks : 1;
1442 : unsigned mSendAfterPaintToContent : 1;
1443 : unsigned mUseFocusColors : 1;
1444 : unsigned mFocusRingOnAnything : 1;
1445 : unsigned mFocusRingStyle : 1;
1446 : unsigned mDrawImageBackground : 1;
1447 : unsigned mDrawColorBackground : 1;
1448 : unsigned mNeverAnimate : 1;
1449 : unsigned mIsRenderingOnlySelection : 1;
1450 : unsigned mPaginated : 1;
1451 : unsigned mCanPaginatedScroll : 1;
1452 : unsigned mDoScaledTwips : 1;
1453 : unsigned mIsRootPaginatedDocument : 1;
1454 : unsigned mPrefBidiDirection : 1;
1455 : unsigned mPrefScrollbarSide : 2;
1456 : unsigned mPendingSysColorChanged : 1;
1457 : unsigned mPendingThemeChanged : 1;
1458 : unsigned mPendingUIResolutionChanged : 1;
1459 : unsigned mPendingMediaFeatureValuesChanged : 1;
1460 : unsigned mPrefChangePendingNeedsReflow : 1;
1461 : unsigned mIsEmulatingMedia : 1;
1462 :
1463 : // Are we currently drawing an SVG glyph?
1464 : unsigned mIsGlyph : 1;
1465 :
1466 : // Does the associated document use root-em (rem) units?
1467 : unsigned mUsesRootEMUnits : 1;
1468 : // Does the associated document use ex or ch units?
1469 : unsigned mUsesExChUnits : 1;
1470 : // Does the associated document use viewport units (vw/vh/vmin/vmax)?
1471 : unsigned mUsesViewportUnits : 1;
1472 :
1473 : // Has there been a change to the viewport's dimensions?
1474 : unsigned mPendingViewportChange : 1;
1475 :
1476 : // Is the current mCounterStyleManager valid?
1477 : unsigned mCounterStylesDirty : 1;
1478 : // Do we currently have an event posted to call FlushCounterStyles?
1479 : unsigned mPostedFlushCounterStyles: 1;
1480 :
1481 : // resize reflow is suppressed when the only change has been to zoom
1482 : // the document rather than to change the document's dimensions
1483 : unsigned mSuppressResizeReflow : 1;
1484 :
1485 : unsigned mIsVisual : 1;
1486 :
1487 : unsigned mFireAfterPaintEvents : 1;
1488 :
1489 : unsigned mIsChrome : 1;
1490 : unsigned mIsChromeOriginImage : 1;
1491 :
1492 : // Should we paint flash in this context? Do not use this variable directly.
1493 : // Use GetPaintFlashing() method instead.
1494 : mutable unsigned mPaintFlashing : 1;
1495 : mutable unsigned mPaintFlashingInitialized : 1;
1496 :
1497 : unsigned mHasWarnedAboutPositionedTableParts : 1;
1498 :
1499 : unsigned mHasWarnedAboutTooLargeDashedOrDottedRadius : 1;
1500 :
1501 : // Have we added quirk.css to the style set?
1502 : unsigned mQuirkSheetAdded : 1;
1503 :
1504 : // Is there a pref update to process once we have a container?
1505 : unsigned mNeedsPrefUpdate : 1;
1506 :
1507 : // Has NotifyNonBlankPaint been called on this PresContext?
1508 : unsigned mHadNonBlankPaint : 1;
1509 :
1510 : #ifdef RESTYLE_LOGGING
1511 : // Should we output debug information about restyling for this document?
1512 : unsigned mRestyleLoggingEnabled : 1;
1513 : #endif
1514 :
1515 : #ifdef DEBUG
1516 : unsigned mInitialized : 1;
1517 : #endif
1518 :
1519 :
1520 : protected:
1521 :
1522 : virtual ~nsPresContext();
1523 :
1524 : nscolor MakeColorPref(const nsString& aColor);
1525 :
1526 : void LastRelease();
1527 :
1528 : #ifdef DEBUG
1529 : private:
1530 : friend struct nsAutoLayoutPhase;
1531 : uint32_t mLayoutPhaseCount[eLayoutPhase_COUNT];
1532 : public:
1533 : uint32_t LayoutPhaseCount(nsLayoutPhase aPhase) {
1534 : return mLayoutPhaseCount[aPhase];
1535 : }
1536 : #endif
1537 :
1538 : };
1539 :
1540 : class nsRootPresContext final : public nsPresContext {
1541 : public:
1542 : nsRootPresContext(nsIDocument* aDocument, nsPresContextType aType);
1543 : virtual ~nsRootPresContext();
1544 : virtual void Detach() override;
1545 :
1546 : /**
1547 : * Ensure that NotifyDidPaintForSubtree is eventually called on this
1548 : * object after a timeout.
1549 : */
1550 : void EnsureEventualDidPaintEvent(uint64_t aTransactionId);
1551 :
1552 : /**
1553 : * Cancels any pending eventual did paint timer for transaction
1554 : * ids up to and including aTransactionId.
1555 : */
1556 : void CancelDidPaintTimers(uint64_t aTransactionId);
1557 :
1558 : /**
1559 : * Cancel all pending eventual did paint timers.
1560 : */
1561 : void CancelAllDidPaintTimers();
1562 :
1563 : /**
1564 : * Registers a plugin to receive geometry updates (position and clip
1565 : * region) so it can update its widget.
1566 : * Callers must call UnregisterPluginForGeometryUpdates before
1567 : * the aPlugin frame is destroyed.
1568 : */
1569 : void RegisterPluginForGeometryUpdates(nsIContent* aPlugin);
1570 : /**
1571 : * Stops a plugin receiving geometry updates (position and clip
1572 : * region). If the plugin was not already registered, this does
1573 : * nothing.
1574 : */
1575 : void UnregisterPluginForGeometryUpdates(nsIContent* aPlugin);
1576 :
1577 26 : bool NeedToComputePluginGeometryUpdates()
1578 : {
1579 26 : return mRegisteredPlugins.Count() > 0;
1580 : }
1581 : /**
1582 : * Compute geometry updates for each plugin given that aList is the display
1583 : * list for aFrame. The updates are not yet applied;
1584 : * ApplyPluginGeometryUpdates is responsible for that. In the meantime they
1585 : * are stored on each nsPluginFrame.
1586 : * This needs to be called even when aFrame is a popup, since although
1587 : * windowed plugins aren't allowed in popups, windowless plugins are
1588 : * and ComputePluginGeometryUpdates needs to be called for them.
1589 : * aBuilder and aList can be null. This indicates that all plugins are
1590 : * hidden because we're in a background tab.
1591 : */
1592 : void ComputePluginGeometryUpdates(nsIFrame* aFrame,
1593 : nsDisplayListBuilder* aBuilder,
1594 : nsDisplayList* aList);
1595 :
1596 : /**
1597 : * Apply the stored plugin geometry updates. This should normally be called
1598 : * in DidPaint so the plugins are moved/clipped immediately after we've
1599 : * updated our window, so they look in sync with our window.
1600 : */
1601 : void ApplyPluginGeometryUpdates();
1602 :
1603 : /**
1604 : * Transfer stored plugin geometry updates to the compositor. Called during
1605 : * reflow, data is shipped over with layer updates. e10s specific.
1606 : */
1607 : void CollectPluginGeometryUpdates(mozilla::layers::LayerManager* aLayerManager);
1608 :
1609 16636 : virtual bool IsRoot() override { return true; }
1610 :
1611 : /**
1612 : * Increment DOM-modification generation counter to indicate that
1613 : * the DOM has changed in a way that might lead to style changes/
1614 : * reflows/frame creation and destruction.
1615 : */
1616 835 : void IncrementDOMGeneration() { mDOMGeneration++; }
1617 :
1618 : /**
1619 : * Get the current DOM generation counter.
1620 : */
1621 610 : uint32_t GetDOMGeneration() { return mDOMGeneration; }
1622 :
1623 : /**
1624 : * Add a runnable that will get called before the next paint. They will get
1625 : * run eventually even if painting doesn't happen. They might run well before
1626 : * painting happens.
1627 : */
1628 : void AddWillPaintObserver(nsIRunnable* aRunnable);
1629 :
1630 : /**
1631 : * Run all runnables that need to get called before the next paint.
1632 : */
1633 : void FlushWillPaintObservers();
1634 :
1635 : virtual size_t SizeOfExcludingThis(mozilla::MallocSizeOf aMallocSizeOf) const override;
1636 :
1637 : protected:
1638 : /**
1639 : * Start a timer to ensure we eventually run ApplyPluginGeometryUpdates.
1640 : */
1641 : void InitApplyPluginGeometryTimer();
1642 : /**
1643 : * Cancel the timer that ensures we eventually run ApplyPluginGeometryUpdates.
1644 : */
1645 : void CancelApplyPluginGeometryTimer();
1646 :
1647 9 : class RunWillPaintObservers : public mozilla::Runnable {
1648 : public:
1649 3 : explicit RunWillPaintObservers(nsRootPresContext* aPresContext)
1650 3 : : Runnable("nsPresContextType::RunWillPaintObservers")
1651 3 : , mPresContext(aPresContext) {}
1652 3 : void Revoke() { mPresContext = nullptr; }
1653 3 : NS_IMETHOD Run() override
1654 : {
1655 3 : if (mPresContext) {
1656 1 : mPresContext->FlushWillPaintObservers();
1657 : }
1658 3 : return NS_OK;
1659 : }
1660 : // The lifetime of this reference is handled by an nsRevocableEventPtr
1661 : nsRootPresContext* MOZ_NON_OWNING_REF mPresContext;
1662 : };
1663 :
1664 : friend class nsPresContext;
1665 :
1666 9 : struct NotifyDidPaintTimer {
1667 : uint64_t mTransactionId;
1668 : nsCOMPtr<nsITimer> mTimer;
1669 : };
1670 : AutoTArray<NotifyDidPaintTimer, 4> mNotifyDidPaintTimers;
1671 :
1672 : nsCOMPtr<nsITimer> mApplyPluginGeometryTimer;
1673 : nsTHashtable<nsRefPtrHashKey<nsIContent> > mRegisteredPlugins;
1674 : nsTArray<nsCOMPtr<nsIRunnable> > mWillPaintObservers;
1675 : nsRevocableEventPtr<RunWillPaintObservers> mWillPaintFallbackEvent;
1676 : uint32_t mDOMGeneration;
1677 : };
1678 :
1679 : #ifdef MOZ_REFLOW_PERF
1680 :
1681 : #define DO_GLOBAL_REFLOW_COUNT(_name) \
1682 : aPresContext->CountReflows((_name), (nsIFrame*)this);
1683 : #else
1684 : #define DO_GLOBAL_REFLOW_COUNT(_name)
1685 : #endif // MOZ_REFLOW_PERF
1686 :
1687 : #endif /* nsPresContext_h___ */
|