1 /* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */ 2 /* vim: set ts=8 sts=2 et sw=2 tw=80: */ 3 /* This Source Code Form is subject to the terms of the Mozilla Public 4 * License, v. 2.0. If a copy of the MPL was not distributed with this 5 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */ 6 7 #ifndef GFX_LAYERS_H 8 #define GFX_LAYERS_H 9 10 #include <map> 11 #include <stdint.h> // for uint32_t, uint64_t, uint8_t 12 #include <stdio.h> // for FILE 13 #include <sys/types.h> // for int32_t 14 #include "FrameMetrics.h" // for FrameMetrics 15 #include "Units.h" // for LayerMargin, LayerPoint, ParentLayerIntRect 16 #include "gfxContext.h" 17 #include "gfxTypes.h" 18 #include "gfxPoint.h" // for gfxPoint 19 #include "gfxRect.h" // for gfxRect 20 #include "gfx2DGlue.h" 21 #include "mozilla/Assertions.h" // for MOZ_ASSERT_HELPER2, etc 22 #include "mozilla/Array.h" 23 #include "mozilla/DebugOnly.h" // for DebugOnly 24 #include "mozilla/EventForwards.h" // for nsPaintEvent 25 #include "mozilla/Maybe.h" // for Maybe 26 #include "mozilla/Poison.h" 27 #include "mozilla/RefPtr.h" // for already_AddRefed 28 #include "mozilla/StyleAnimationValue.h" // for StyleAnimationValue, etc 29 #include "mozilla/TimeStamp.h" // for TimeStamp, TimeDuration 30 #include "mozilla/UniquePtr.h" // for UniquePtr 31 #include "mozilla/gfx/BaseMargin.h" // for BaseMargin 32 #include "mozilla/gfx/BasePoint.h" // for BasePoint 33 #include "mozilla/gfx/Point.h" // for IntSize 34 #include "mozilla/gfx/TiledRegion.h" // for TiledIntRegion 35 #include "mozilla/gfx/Types.h" // for SurfaceFormat 36 #include "mozilla/gfx/UserData.h" // for UserData, etc 37 #include "mozilla/layers/AnimationInfo.h" // for AnimationInfo 38 #include "mozilla/layers/BSPTree.h" // for LayerPolygon 39 #include "mozilla/layers/CanvasRenderer.h" 40 #include "mozilla/layers/LayerAttributes.h" 41 #include "mozilla/layers/LayersTypes.h" 42 #include "mozilla/mozalloc.h" // for operator delete, etc 43 #include "nsAutoPtr.h" // for nsAutoPtr, nsRefPtr, etc 44 #include "nsCOMPtr.h" // for already_AddRefed 45 #include "nsCSSPropertyID.h" // for nsCSSPropertyID 46 #include "nsDebug.h" // for NS_ASSERTION 47 #include "nsISupportsImpl.h" // for Layer::Release, etc 48 #include "nsRect.h" // for mozilla::gfx::IntRect 49 #include "nsRegion.h" // for nsIntRegion 50 #include "nsString.h" // for nsCString 51 #include "nsTArray.h" // for nsTArray 52 #include "nsTArrayForwardDeclare.h" // for InfallibleTArray 53 #include "nscore.h" // for nsACString, nsAString 54 #include "mozilla/Logging.h" // for PRLogModuleInfo 55 #include "nsIWidget.h" // For plugin window configuration information structs 56 #include "ImageContainer.h" 57 58 class gfxContext; 59 class nsDisplayListBuilder; 60 class nsDisplayItem; 61 62 extern uint8_t gLayerManagerLayerBuilder; 63 64 namespace mozilla { 65 66 class ComputedTimingFunction; 67 class FrameLayerBuilder; 68 class StyleAnimationValue; 69 70 namespace gl { 71 class GLContext; 72 } // namespace gl 73 74 namespace gfx { 75 class DrawTarget; 76 } // namespace gfx 77 78 namespace layers { 79 80 class Animation; 81 class AsyncCanvasRenderer; 82 class AsyncPanZoomController; 83 class BasicLayerManager; 84 class ClientLayerManager; 85 class HostLayerManager; 86 class Layer; 87 class LayerMetricsWrapper; 88 class PaintedLayer; 89 class ContainerLayer; 90 class ImageLayer; 91 class DisplayItemLayer; 92 class ColorLayer; 93 class CompositorAnimations; 94 class CompositorBridgeChild; 95 class CanvasLayer; 96 class BorderLayer; 97 class ReadbackLayer; 98 class ReadbackProcessor; 99 class RefLayer; 100 class HostLayer; 101 class FocusTarget; 102 class KnowsCompositor; 103 class ShadowableLayer; 104 class ShadowLayerForwarder; 105 class LayerManagerComposite; 106 class SpecificLayerAttributes; 107 class TransactionIdAllocator; 108 class Compositor; 109 class FrameUniformityData; 110 class PersistentBufferProvider; 111 class GlyphArray; 112 class WebRenderLayerManager; 113 struct AnimData; 114 115 namespace layerscope { 116 class LayersPacket; 117 } // namespace layerscope 118 119 #define MOZ_LAYER_DECL_NAME(n, e) \ 120 virtual const char* Name() const override { return n; } \ 121 virtual LayerType GetType() const override { return e; } \ 122 static LayerType Type() { return e; } 123 124 // Defined in LayerUserData.h; please include that file instead. 125 class LayerUserData; 126 127 class DidCompositeObserver { 128 public: 129 virtual void DidComposite() = 0; 130 }; 131 132 /* 133 * Motivation: For truly smooth animation and video playback, we need to 134 * be able to compose frames and render them on a dedicated thread (i.e. 135 * off the main thread where DOM manipulation, script execution and layout 136 * induce difficult-to-bound latency). This requires Gecko to construct 137 * some kind of persistent scene structure (graph or tree) that can be 138 * safely transmitted across threads. We have other scenarios (e.g. mobile 139 * browsing) where retaining some rendered data between paints is desired 140 * for performance, so again we need a retained scene structure. 141 * 142 * Our retained scene structure is a layer tree. Each layer represents 143 * content which can be composited onto a destination surface; the root 144 * layer is usually composited into a window, and non-root layers are 145 * composited into their parent layers. Layers have attributes (e.g. 146 * opacity and clipping) that influence their compositing. 147 * 148 * We want to support a variety of layer implementations, including 149 * a simple "immediate mode" implementation that doesn't retain any 150 * rendered data between paints (i.e. uses cairo in just the way that 151 * Gecko used it before layers were introduced). But we also don't want 152 * to have bifurcated "layers"/"non-layers" rendering paths in Gecko. 153 * Therefore the layers API is carefully designed to permit maximally 154 * efficient implementation in an "immediate mode" style. See the 155 * BasicLayerManager for such an implementation. 156 */ 157 158 /** 159 * A LayerManager controls a tree of layers. All layers in the tree 160 * must use the same LayerManager. 161 * 162 * All modifications to a layer tree must happen inside a transaction. 163 * Only the state of the layer tree at the end of a transaction is 164 * rendered. Transactions cannot be nested 165 * 166 * Each transaction has two phases: 167 * 1) Construction: layers are created, inserted, removed and have 168 * properties set on them in this phase. 169 * BeginTransaction and BeginTransactionWithTarget start a transaction in 170 * the Construction phase. 171 * 2) Drawing: PaintedLayers are rendered into in this phase, in tree 172 * order. When the client has finished drawing into the PaintedLayers, it should 173 * call EndTransaction to complete the transaction. 174 * 175 * All layer API calls happen on the main thread. 176 * 177 * Layers are refcounted. The layer manager holds a reference to the 178 * root layer, and each container layer holds a reference to its children. 179 */ 180 class LayerManager { 181 NS_INLINE_DECL_REFCOUNTING(LayerManager) 182 183 protected: 184 typedef mozilla::gfx::DrawTarget DrawTarget; 185 typedef mozilla::gfx::IntSize IntSize; 186 typedef mozilla::gfx::SurfaceFormat SurfaceFormat; 187 188 public: LayerManager()189 LayerManager() 190 : mDestroyed(false), 191 mSnapEffectiveTransforms(true), 192 mId(0), 193 mInTransaction(false), 194 mPaintedPixelCount(0) {} 195 196 /** 197 * Release layers and resources held by this layer manager, and mark 198 * it as destroyed. Should do any cleanup necessary in preparation 199 * for its widget going away. After this call, only user data calls 200 * are valid on the layer manager. 201 */ Destroy()202 virtual void Destroy() { 203 mDestroyed = true; 204 mUserData.Destroy(); 205 mRoot = nullptr; 206 } IsDestroyed()207 bool IsDestroyed() { return mDestroyed; } 208 AsShadowForwarder()209 virtual ShadowLayerForwarder* AsShadowForwarder() { return nullptr; } 210 AsKnowsCompositor()211 virtual KnowsCompositor* AsKnowsCompositor() { return nullptr; } 212 AsLayerManagerComposite()213 virtual LayerManagerComposite* AsLayerManagerComposite() { return nullptr; } 214 AsClientLayerManager()215 virtual ClientLayerManager* AsClientLayerManager() { return nullptr; } 216 AsBasicLayerManager()217 virtual BasicLayerManager* AsBasicLayerManager() { return nullptr; } AsHostLayerManager()218 virtual HostLayerManager* AsHostLayerManager() { return nullptr; } 219 AsWebRenderLayerManager()220 virtual WebRenderLayerManager* AsWebRenderLayerManager() { return nullptr; } 221 222 /** 223 * Returns true if this LayerManager is owned by an nsIWidget, 224 * and is used for drawing into the widget. 225 */ IsWidgetLayerManager()226 virtual bool IsWidgetLayerManager() { return true; } IsInactiveLayerManager()227 virtual bool IsInactiveLayerManager() { return false; } 228 229 /** 230 * Start a new transaction. Nested transactions are not allowed so 231 * there must be no transaction currently in progress. 232 * This transaction will update the state of the window from which 233 * this LayerManager was obtained. 234 */ 235 virtual bool BeginTransaction() = 0; 236 /** 237 * Start a new transaction. Nested transactions are not allowed so 238 * there must be no transaction currently in progress. 239 * This transaction will render the contents of the layer tree to 240 * the given target context. The rendering will be complete when 241 * EndTransaction returns. 242 */ 243 virtual bool BeginTransactionWithTarget(gfxContext* aTarget) = 0; 244 245 enum EndTransactionFlags { 246 END_DEFAULT = 0, 247 END_NO_IMMEDIATE_REDRAW = 1 << 0, // Do not perform the drawing phase 248 END_NO_COMPOSITE = 249 1 << 1, // Do not composite after drawing painted layer contents. 250 END_NO_REMOTE_COMPOSITE = 1 << 2 // Do not schedule a composition with a 251 // remote Compositor, if one exists. 252 }; 253 GetLayerBuilder()254 FrameLayerBuilder* GetLayerBuilder() { 255 return reinterpret_cast<FrameLayerBuilder*>( 256 GetUserData(&gLayerManagerLayerBuilder)); 257 } 258 259 /** 260 * Attempts to end an "empty transaction". There must have been no 261 * changes to the layer tree since the BeginTransaction(). 262 * It's possible for this to fail; PaintedLayers may need to be updated 263 * due to VRAM data being lost, for example. In such cases this method 264 * returns false, and the caller must proceed with a normal layer tree 265 * update and EndTransaction. 266 */ 267 virtual bool EndEmptyTransaction( 268 EndTransactionFlags aFlags = END_DEFAULT) = 0; 269 270 /** 271 * Function called to draw the contents of each PaintedLayer. 272 * aRegionToDraw contains the region that needs to be drawn. 273 * This would normally be a subregion of the visible region. 274 * The callee must draw all of aRegionToDraw. Drawing outside 275 * aRegionToDraw will be clipped out or ignored. 276 * The callee must draw all of aRegionToDraw. 277 * This region is relative to 0,0 in the PaintedLayer. 278 * 279 * aDirtyRegion should contain the total region that is be due to be painted 280 * during the transaction, even though only aRegionToDraw should be drawn 281 * during this call. aRegionToDraw must be entirely contained within 282 * aDirtyRegion. If the total dirty region is unknown it is okay to pass a 283 * subregion of the total dirty region, e.g. just aRegionToDraw, though it 284 * may not be as efficient. 285 * 286 * aRegionToInvalidate contains a region whose contents have been 287 * changed by the layer manager and which must therefore be invalidated. 288 * For example, this could be non-empty if a retained layer internally 289 * switches from RGBA to RGB or back ... we might want to repaint it to 290 * consistently use subpixel-AA or not. 291 * This region is relative to 0,0 in the PaintedLayer. 292 * aRegionToInvalidate may contain areas that are outside 293 * aRegionToDraw; the callee must ensure that these areas are repainted 294 * in the current layer manager transaction or in a later layer 295 * manager transaction. 296 * 297 * aContext must not be used after the call has returned. 298 * We guarantee that buffered contents in the visible 299 * region are valid once drawing is complete. 300 * 301 * The origin of aContext is 0,0 in the PaintedLayer. 302 */ 303 typedef void (*DrawPaintedLayerCallback)( 304 PaintedLayer* aLayer, gfxContext* aContext, 305 const nsIntRegion& aRegionToDraw, const nsIntRegion& aDirtyRegion, 306 DrawRegionClip aClip, const nsIntRegion& aRegionToInvalidate, 307 void* aCallbackData); 308 309 /** 310 * Finish the construction phase of the transaction, perform the 311 * drawing phase, and end the transaction. 312 * During the drawing phase, all PaintedLayers in the tree are 313 * drawn in tree order, exactly once each, except for those layers 314 * where it is known that the visible region is empty. 315 */ 316 virtual void EndTransaction(DrawPaintedLayerCallback aCallback, 317 void* aCallbackData, 318 EndTransactionFlags aFlags = END_DEFAULT) = 0; 319 320 /** 321 * Schedule a composition with the remote Compositor, if one exists 322 * for this LayerManager. Useful in conjunction with the 323 * END_NO_REMOTE_COMPOSITE flag to EndTransaction. 324 */ ScheduleComposite()325 virtual void ScheduleComposite() {} 326 SetNeedsComposite(bool aNeedsComposite)327 virtual void SetNeedsComposite(bool aNeedsComposite) {} NeedsComposite()328 virtual bool NeedsComposite() const { return false; } 329 HasShadowManagerInternal()330 virtual bool HasShadowManagerInternal() const { return false; } HasShadowManager()331 bool HasShadowManager() const { return HasShadowManagerInternal(); } StorePluginWidgetConfigurations(const nsTArray<nsIWidget::Configuration> & aConfigurations)332 virtual void StorePluginWidgetConfigurations( 333 const nsTArray<nsIWidget::Configuration>& aConfigurations) {} IsSnappingEffectiveTransforms()334 bool IsSnappingEffectiveTransforms() { return mSnapEffectiveTransforms; } 335 336 /** 337 * Returns true if this LayerManager can properly support layers with 338 * SurfaceMode::SURFACE_COMPONENT_ALPHA. LayerManagers that can't will use 339 * transparent surfaces (and lose subpixel-AA for text). 340 */ 341 virtual bool AreComponentAlphaLayersEnabled(); 342 343 /** 344 * Returns true if this LayerManager always requires an intermediate surface 345 * to render blend operations. 346 */ BlendingRequiresIntermediateSurface()347 virtual bool BlendingRequiresIntermediateSurface() { return false; } 348 349 /** 350 * CONSTRUCTION PHASE ONLY 351 * Set the root layer. The root layer is initially null. If there is 352 * no root layer, EndTransaction won't draw anything. 353 */ 354 virtual void SetRoot(Layer* aLayer) = 0; 355 /** 356 * Can be called anytime 357 */ GetRoot()358 Layer* GetRoot() { return mRoot; } 359 360 /** 361 * Does a breadth-first search from the root layer to find the first 362 * scrollable layer, and returns its ViewID. Note that there may be 363 * other layers in the tree which share the same ViewID. 364 * Can be called any time. 365 */ 366 FrameMetrics::ViewID GetRootScrollableLayerId(); 367 368 /** 369 * Returns a LayerMetricsWrapper containing the Root 370 * Content Documents layer. 371 */ 372 LayerMetricsWrapper GetRootContentLayer(); 373 374 /** 375 * CONSTRUCTION PHASE ONLY 376 * Called when a managee has mutated. 377 * Subclasses overriding this method must first call their 378 * superclass's impl 379 */ Mutated(Layer * aLayer)380 virtual void Mutated(Layer* aLayer) {} MutatedSimple(Layer * aLayer)381 virtual void MutatedSimple(Layer* aLayer) {} 382 383 /** 384 * Hints that can be used during PaintedLayer creation to influence the type 385 * or properties of the layer created. 386 * 387 * NONE: No hint. 388 * SCROLLABLE: This layer may represent scrollable content. 389 */ 390 enum PaintedLayerCreationHint { NONE, SCROLLABLE }; 391 392 /** 393 * CONSTRUCTION PHASE ONLY 394 * Create a PaintedLayer for this manager's layer tree. 395 */ 396 virtual already_AddRefed<PaintedLayer> CreatePaintedLayer() = 0; 397 /** 398 * CONSTRUCTION PHASE ONLY 399 * Create a PaintedLayer for this manager's layer tree, with a creation hint 400 * parameter to help optimise the type of layer created. 401 */ CreatePaintedLayerWithHint(PaintedLayerCreationHint)402 virtual already_AddRefed<PaintedLayer> CreatePaintedLayerWithHint( 403 PaintedLayerCreationHint) { 404 return CreatePaintedLayer(); 405 } 406 /** 407 * CONSTRUCTION PHASE ONLY 408 * Create a ContainerLayer for this manager's layer tree. 409 */ 410 virtual already_AddRefed<ContainerLayer> CreateContainerLayer() = 0; 411 /** 412 * CONSTRUCTION PHASE ONLY 413 * Create an ImageLayer for this manager's layer tree. 414 */ 415 virtual already_AddRefed<ImageLayer> CreateImageLayer() = 0; 416 /** 417 * CONSTRUCTION PHASE ONLY 418 * Create a ColorLayer for this manager's layer tree. 419 */ 420 virtual already_AddRefed<ColorLayer> CreateColorLayer() = 0; 421 /** 422 * CONSTRUCTION PHASE ONLY 423 * Create a BorderLayer for this manager's layer tree. 424 */ 425 virtual already_AddRefed<BorderLayer> CreateBorderLayer() = 0; 426 /** 427 * CONSTRUCTION PHASE ONLY 428 * Create a CanvasLayer for this manager's layer tree. 429 */ 430 virtual already_AddRefed<CanvasLayer> CreateCanvasLayer() = 0; 431 /** 432 * CONSTRUCTION PHASE ONLY 433 * Create a ReadbackLayer for this manager's layer tree. 434 */ CreateReadbackLayer()435 virtual already_AddRefed<ReadbackLayer> CreateReadbackLayer() { 436 return nullptr; 437 } 438 /** 439 * CONSTRUCTION PHASE ONLY 440 * Create a RefLayer for this manager's layer tree. 441 */ CreateRefLayer()442 virtual already_AddRefed<RefLayer> CreateRefLayer() { return nullptr; } 443 /** 444 * CONSTRUCTION PHASE ONLY 445 * Create a DisplayItemLayer for this manager's layer tree. 446 */ CreateDisplayItemLayer()447 virtual already_AddRefed<DisplayItemLayer> CreateDisplayItemLayer() { 448 return nullptr; 449 } 450 /** 451 * Can be called anytime, from any thread. 452 * 453 * Creates an Image container which forwards its images to the compositor 454 * within layer transactions on the main thread or asynchronously using the 455 * ImageBridge IPDL protocol. In the case of asynchronous, If the protocol is 456 * not available, the returned ImageContainer will forward images within layer 457 * transactions. 458 */ 459 static already_AddRefed<ImageContainer> CreateImageContainer( 460 ImageContainer::Mode flag = ImageContainer::SYNCHRONOUS); 461 462 /** 463 * Since the lifetimes of display items and display item layers are different, 464 * calling this tells the layer manager that the display item layer is valid 465 * for only one transaction. Users should call ClearDisplayItemLayers() to 466 * remove references to the dead display item at the end of a transaction. 467 */ 468 virtual void TrackDisplayItemLayer(RefPtr<DisplayItemLayer> aLayer); 469 virtual void ClearDisplayItemLayers(); 470 471 /** 472 * Type of layer manager his is. This is to be used sparsely in order to 473 * avoid a lot of Layers backend specific code. It should be used only when 474 * Layers backend specific functionality is necessary. 475 */ 476 virtual LayersBackend GetBackendType() = 0; 477 478 /** 479 * Type of layers backend that will be used to composite this layer tree. 480 * When compositing is done remotely, then this returns the layers type 481 * of the compositor. 482 */ GetCompositorBackendType()483 virtual LayersBackend GetCompositorBackendType() { return GetBackendType(); } 484 485 /** 486 * Creates a DrawTarget which is optimized for inter-operating with this 487 * layer manager. 488 */ 489 virtual already_AddRefed<DrawTarget> CreateOptimalDrawTarget( 490 const IntSize& aSize, SurfaceFormat imageFormat); 491 492 /** 493 * Creates a DrawTarget for alpha masks which is optimized for inter- 494 * operating with this layer manager. In contrast to CreateOptimalDrawTarget, 495 * this surface is optimised for drawing alpha only and we assume that 496 * drawing the mask is fairly simple. 497 */ 498 virtual already_AddRefed<DrawTarget> CreateOptimalMaskDrawTarget( 499 const IntSize& aSize); 500 501 /** 502 * Creates a DrawTarget for use with canvas which is optimized for 503 * inter-operating with this layermanager. 504 */ 505 virtual already_AddRefed<mozilla::gfx::DrawTarget> CreateDrawTarget( 506 const mozilla::gfx::IntSize& aSize, mozilla::gfx::SurfaceFormat aFormat); 507 508 /** 509 * Creates a PersistentBufferProvider for use with canvas which is optimized 510 * for inter-operating with this layermanager. 511 */ 512 virtual already_AddRefed<PersistentBufferProvider> 513 CreatePersistentBufferProvider(const mozilla::gfx::IntSize& aSize, 514 mozilla::gfx::SurfaceFormat aFormat); 515 CanUseCanvasLayerForSize(const gfx::IntSize & aSize)516 virtual bool CanUseCanvasLayerForSize(const gfx::IntSize& aSize) { 517 return true; 518 } 519 520 /** 521 * returns the maximum texture size on this layer backend, or INT32_MAX 522 * if there is no maximum 523 */ 524 virtual int32_t GetMaxTextureSize() const = 0; 525 526 /** 527 * Return the name of the layer manager's backend. 528 */ 529 virtual void GetBackendName(nsAString& aName) = 0; 530 531 /** 532 * This setter can be used anytime. The user data for all keys is 533 * initially null. Ownership pases to the layer manager. 534 */ SetUserData(void * aKey,LayerUserData * aData)535 void SetUserData(void* aKey, LayerUserData* aData) { 536 mUserData.Add(static_cast<gfx::UserDataKey*>(aKey), aData, 537 LayerUserDataDestroy); 538 } 539 /** 540 * This can be used anytime. Ownership passes to the caller! 541 */ 542 UniquePtr<LayerUserData> RemoveUserData(void* aKey); 543 544 /** 545 * This getter can be used anytime. 546 */ HasUserData(void * aKey)547 bool HasUserData(void* aKey) { 548 return mUserData.Has(static_cast<gfx::UserDataKey*>(aKey)); 549 } 550 /** 551 * This getter can be used anytime. Ownership is retained by the layer 552 * manager. 553 */ GetUserData(void * aKey)554 LayerUserData* GetUserData(void* aKey) const { 555 return static_cast<LayerUserData*>( 556 mUserData.Get(static_cast<gfx::UserDataKey*>(aKey))); 557 } 558 559 /** 560 * Must be called outside of a layers transaction. 561 * 562 * For the subtree rooted at |aSubtree|, this attempts to free up 563 * any free-able resources like retained buffers, but may do nothing 564 * at all. After this call, the layer tree is left in an undefined 565 * state; the layers in |aSubtree|'s subtree may no longer have 566 * buffers with valid content and may no longer be able to draw 567 * their visible and valid regions. 568 * 569 * In general, a painting or forwarding transaction on |this| must 570 * complete on the tree before it returns to a valid state. 571 * 572 * Resource freeing begins from |aSubtree| or |mRoot| if |aSubtree| 573 * is null. |aSubtree|'s manager must be this. 574 */ 575 virtual void ClearCachedResources(Layer* aSubtree = nullptr) {} 576 577 /** 578 * Flag the next paint as the first for a document. 579 */ SetIsFirstPaint()580 virtual void SetIsFirstPaint() {} 581 582 /** 583 * Set the current focus target to be sent with the next paint. 584 */ SetFocusTarget(const FocusTarget & aFocusTarget)585 virtual void SetFocusTarget(const FocusTarget& aFocusTarget) {} 586 587 /** 588 * Make sure that the previous transaction has been entirely 589 * completed. 590 * 591 * Note: This may sychronously wait on a remote compositor 592 * to complete rendering. 593 */ FlushRendering()594 virtual void FlushRendering() {} 595 596 /** 597 * Make sure that the previous transaction has been 598 * received. This will synchronsly wait on a remote compositor. */ WaitOnTransactionProcessed()599 virtual void WaitOnTransactionProcessed() {} 600 SendInvalidRegion(const nsIntRegion & aRegion)601 virtual void SendInvalidRegion(const nsIntRegion& aRegion) {} 602 603 /** 604 * Checks if we need to invalidate the OS widget to trigger 605 * painting when updating this layer manager. 606 */ NeedsWidgetInvalidation()607 virtual bool NeedsWidgetInvalidation() { return true; } 608 Name()609 virtual const char* Name() const { return "???"; } 610 611 /** 612 * Dump information about this layer manager and its managed tree to 613 * aStream. 614 */ 615 void Dump(std::stringstream& aStream, const char* aPrefix = "", 616 bool aDumpHtml = false, bool aSorted = false); 617 /** 618 * Dump information about just this layer manager itself to aStream 619 */ 620 void DumpSelf(std::stringstream& aStream, const char* aPrefix = "", 621 bool aSorted = false); 622 void Dump(bool aSorted = false); 623 624 /** 625 * Dump information about this layer manager and its managed tree to 626 * layerscope packet. 627 */ 628 void Dump(layerscope::LayersPacket* aPacket); 629 630 /** 631 * Log information about this layer manager and its managed tree to 632 * the NSPR log (if enabled for "Layers"). 633 */ 634 void Log(const char* aPrefix = ""); 635 /** 636 * Log information about just this layer manager itself to the NSPR 637 * log (if enabled for "Layers"). 638 */ 639 void LogSelf(const char* aPrefix = ""); 640 641 /** 642 * Record (and return) frame-intervals and paint-times for frames which were 643 * presented between calling StartFrameTimeRecording and 644 * StopFrameTimeRecording. 645 * 646 * - Uses a cyclic buffer and serves concurrent consumers, so if Stop is 647 * called too late (elements were overwritten since Start), result is 648 * considered invalid and hence empty. 649 * - Buffer is capable of holding 10 seconds @ 60fps (or more if frames were 650 * less frequent). Can be changed (up to 1 hour) via pref: 651 * toolkit.framesRecording.bufferSize. 652 * - Note: the first frame-interval may be longer than expected because last 653 * frame might have been presented some time before calling 654 * StartFrameTimeRecording. 655 */ 656 657 /** 658 * Returns a handle which represents current recording start position. 659 */ 660 virtual uint32_t StartFrameTimeRecording(int32_t aBufferSize); 661 662 /** 663 * Clears, then populates aFrameIntervals with the recorded frame timing 664 * data. The array will be empty if data was overwritten since 665 * aStartIndex was obtained. 666 */ 667 virtual void StopFrameTimeRecording(uint32_t aStartIndex, 668 nsTArray<float>& aFrameIntervals); 669 670 void RecordFrame(); 671 672 static bool IsLogEnabled(); 673 static mozilla::LogModule* GetLog(); 674 IsCompositingCheap(LayersBackend aBackend)675 bool IsCompositingCheap(LayersBackend aBackend) { 676 // LayersBackend::LAYERS_NONE is an error state, but in that case we should 677 // try to avoid loading the compositor! 678 return LayersBackend::LAYERS_BASIC != aBackend && 679 LayersBackend::LAYERS_NONE != aBackend; 680 } 681 IsCompositingCheap()682 virtual bool IsCompositingCheap() { return true; } 683 IsInTransaction()684 bool IsInTransaction() const { return mInTransaction; } GetFrameUniformity(FrameUniformityData * aOutData)685 virtual void GetFrameUniformity(FrameUniformityData* aOutData) {} 686 SetRegionToClear(const nsIntRegion & aRegion)687 virtual void SetRegionToClear(const nsIntRegion& aRegion) { 688 mRegionToClear = aRegion; 689 } 690 RequestProperty(const nsAString & property)691 virtual float RequestProperty(const nsAString& property) { return -1; } 692 GetAnimationReadyTime()693 const TimeStamp& GetAnimationReadyTime() const { return mAnimationReadyTime; } 694 AsyncPanZoomEnabled()695 virtual bool AsyncPanZoomEnabled() const { return false; } 696 697 static void LayerUserDataDestroy(void* data); 698 AddPaintedPixelCount(int32_t aCount)699 void AddPaintedPixelCount(int32_t aCount) { mPaintedPixelCount += aCount; } 700 GetAndClearPaintedPixelCount()701 uint32_t GetAndClearPaintedPixelCount() { 702 uint32_t count = mPaintedPixelCount; 703 mPaintedPixelCount = 0; 704 return count; 705 } 706 SetLayerObserverEpoch(uint64_t aLayerObserverEpoch)707 virtual void SetLayerObserverEpoch(uint64_t aLayerObserverEpoch) {} 708 DidComposite(uint64_t aTransactionId,const mozilla::TimeStamp & aCompositeStart,const mozilla::TimeStamp & aCompositeEnd)709 virtual void DidComposite(uint64_t aTransactionId, 710 const mozilla::TimeStamp& aCompositeStart, 711 const mozilla::TimeStamp& aCompositeEnd) {} 712 AddDidCompositeObserver(DidCompositeObserver * aObserver)713 virtual void AddDidCompositeObserver(DidCompositeObserver* aObserver) { 714 MOZ_CRASH("GFX: LayerManager"); 715 } RemoveDidCompositeObserver(DidCompositeObserver * aObserver)716 virtual void RemoveDidCompositeObserver(DidCompositeObserver* aObserver) { 717 MOZ_CRASH("GFX: LayerManager"); 718 } 719 UpdateTextureFactoryIdentifier(const TextureFactoryIdentifier & aNewIdentifier)720 virtual void UpdateTextureFactoryIdentifier( 721 const TextureFactoryIdentifier& aNewIdentifier) {} 722 GetTextureFactoryIdentifier()723 virtual TextureFactoryIdentifier GetTextureFactoryIdentifier() { 724 return TextureFactoryIdentifier(); 725 } 726 SetTransactionIdAllocator(TransactionIdAllocator * aAllocator)727 virtual void SetTransactionIdAllocator(TransactionIdAllocator* aAllocator) {} 728 GetLastTransactionId()729 virtual uint64_t GetLastTransactionId() { return 0; } 730 GetCompositorBridgeChild()731 virtual CompositorBridgeChild* GetCompositorBridgeChild() { return nullptr; } 732 733 protected: 734 RefPtr<Layer> mRoot; 735 gfx::UserData mUserData; 736 bool mDestroyed; 737 bool mSnapEffectiveTransforms; 738 739 nsIntRegion mRegionToClear; 740 741 // Protected destructor, to discourage deletion outside of Release(): ~LayerManager()742 virtual ~LayerManager() {} 743 744 // Print interesting information about this into aStreamo. Internally 745 // used to implement Dump*() and Log*(). 746 virtual void PrintInfo(std::stringstream& aStream, const char* aPrefix); 747 748 // Print interesting information about this into layerscope packet. 749 // Internally used to implement Dump(). 750 virtual void DumpPacket(layerscope::LayersPacket* aPacket); 751 752 uint64_t mId; 753 bool mInTransaction; 754 // The time when painting most recently finished. This is recorded so that 755 // we can time any play-pending animations from this point. 756 TimeStamp mAnimationReadyTime; 757 // The count of pixels that were painted in the current transaction. 758 uint32_t mPaintedPixelCount; 759 760 private: 761 struct FramesTimingRecording { 762 // Stores state and data for frame intervals and paint times recording. 763 // see LayerManager::StartFrameTimeRecording() at Layers.cpp for more 764 // details. FramesTimingRecordingFramesTimingRecording765 FramesTimingRecording() 766 : mNextIndex(0), 767 mLatestStartIndex(0), 768 mCurrentRunStartIndex(0), 769 mIsPaused(true) {} 770 nsTArray<float> mIntervals; 771 TimeStamp mLastFrameTime; 772 uint32_t mNextIndex; 773 uint32_t mLatestStartIndex; 774 uint32_t mCurrentRunStartIndex; 775 bool mIsPaused; 776 }; 777 FramesTimingRecording mRecording; 778 779 public: 780 /* 781 * Methods to store/get/clear a "pending scroll info update" object on a 782 * per-scrollid basis. This is used for empty transactions that push over 783 * scroll position updates to the APZ code. 784 */ 785 virtual bool SetPendingScrollUpdateForNextTransaction( 786 FrameMetrics::ViewID aScrollId, const ScrollUpdateInfo& aUpdateInfo); 787 Maybe<ScrollUpdateInfo> GetPendingScrollInfoUpdate( 788 FrameMetrics::ViewID aScrollId); 789 void ClearPendingScrollInfoUpdate(); 790 791 private: 792 std::map<FrameMetrics::ViewID, ScrollUpdateInfo> mPendingScrollUpdates; 793 794 // Display items are only valid during this transaction. 795 // At the end of the transaction, we have to go and clear out 796 // DisplayItemLayer's and null their display item. See comment 797 // above DisplayItemLayer declaration. 798 // Since layers are ref counted, we also have to stop holding 799 // a reference to the display item layer as well. 800 nsTArray<RefPtr<DisplayItemLayer>> mDisplayItemLayers; 801 }; 802 803 /** 804 * A Layer represents anything that can be rendered onto a destination 805 * surface. 806 */ 807 class Layer { 808 NS_INLINE_DECL_REFCOUNTING(Layer) 809 810 typedef InfallibleTArray<Animation> AnimationArray; 811 812 public: 813 // Keep these in alphabetical order 814 enum LayerType { 815 TYPE_CANVAS, 816 TYPE_COLOR, 817 TYPE_CONTAINER, 818 TYPE_DISPLAYITEM, 819 TYPE_IMAGE, 820 TYPE_BORDER, 821 TYPE_READBACK, 822 TYPE_REF, 823 TYPE_SHADOW, 824 TYPE_PAINTED 825 }; 826 827 /** 828 * Returns the LayerManager this Layer belongs to. Note that the layer 829 * manager might be in a destroyed state, at which point it's only 830 * valid to set/get user data from it. 831 */ Manager()832 LayerManager* Manager() { return mManager; } 833 834 /** 835 * This should only be called when changing layer managers from HostLayers. 836 */ 837 void SetManager(LayerManager* aManager, HostLayer* aSelf); 838 839 enum { 840 /** 841 * If this is set, the caller is promising that by the end of this 842 * transaction the entire visible region (as specified by 843 * SetVisibleRegion) will be filled with opaque content. 844 */ 845 CONTENT_OPAQUE = 0x01, 846 /** 847 * If this is set, the caller is notifying that the contents of this layer 848 * require per-component alpha for optimal fidelity. However, there is no 849 * guarantee that component alpha will be supported for this layer at 850 * paint time. 851 * This should never be set at the same time as CONTENT_OPAQUE. 852 */ 853 CONTENT_COMPONENT_ALPHA = 0x02, 854 855 /** 856 * If this is set then one of the descendant layers of this one has 857 * CONTENT_COMPONENT_ALPHA set. 858 */ 859 CONTENT_COMPONENT_ALPHA_DESCENDANT = 0x04, 860 861 /** 862 * If this is set then this layer is part of a preserve-3d group, and should 863 * be sorted with sibling layers that are also part of the same group. 864 */ 865 CONTENT_EXTEND_3D_CONTEXT = 0x08, 866 /** 867 * This indicates that the transform may be changed on during an empty 868 * transaction where there is no possibility of redrawing the content, so 869 * the implementation should be ready for that. 870 */ 871 CONTENT_MAY_CHANGE_TRANSFORM = 0x10, 872 873 /** 874 * Disable subpixel AA for this layer. This is used if the display isn't 875 * suited for subpixel AA like hidpi or rotated content. 876 */ 877 CONTENT_DISABLE_SUBPIXEL_AA = 0x20, 878 879 /** 880 * If this is set then the layer contains content that may look 881 * objectionable if not handled as an active layer (such as text with an 882 * animated transform). This is for internal layout/FrameLayerBuilder usage 883 * only until flattening code is obsoleted. See bug 633097 884 */ 885 CONTENT_DISABLE_FLATTENING = 0x40, 886 887 /** 888 * This layer is hidden if the backface of the layer is visible 889 * to user. 890 */ 891 CONTENT_BACKFACE_HIDDEN = 0x80 892 }; 893 /** 894 * CONSTRUCTION PHASE ONLY 895 * This lets layout make some promises about what will be drawn into the 896 * visible region of the PaintedLayer. This enables internal quality 897 * and performance optimizations. 898 */ SetContentFlags(uint32_t aFlags)899 void SetContentFlags(uint32_t aFlags) { 900 NS_ASSERTION((aFlags & (CONTENT_OPAQUE | CONTENT_COMPONENT_ALPHA)) != 901 (CONTENT_OPAQUE | CONTENT_COMPONENT_ALPHA), 902 "Can't be opaque and require component alpha"); 903 if (mSimpleAttrs.SetContentFlags(aFlags)) { 904 MOZ_LAYERS_LOG_IF_SHADOWABLE(this, 905 ("Layer::Mutated(%p) ContentFlags", this)); 906 MutatedSimple(); 907 } 908 } 909 910 /** 911 * CONSTRUCTION PHASE ONLY 912 * Tell this layer which region will be visible. The visible region 913 * is a region which contains all the contents of the layer that can 914 * actually affect the rendering of the window. It can exclude areas 915 * that are covered by opaque contents of other layers, and it can 916 * exclude areas where this layer simply contains no content at all. 917 * (This can be an overapproximation to the "true" visible region.) 918 * 919 * There is no general guarantee that drawing outside the bounds of the 920 * visible region will be ignored. So if a layer draws outside the bounds 921 * of its visible region, it needs to ensure that what it draws is valid. 922 */ SetVisibleRegion(const LayerIntRegion & aRegion)923 virtual void SetVisibleRegion(const LayerIntRegion& aRegion) { 924 // IsEmpty is required otherwise we get invalidation glitches. 925 // See bug 1288464 for investigating why. 926 if (!mVisibleRegion.IsEqual(aRegion) || aRegion.IsEmpty()) { 927 MOZ_LAYERS_LOG_IF_SHADOWABLE( 928 this, ("Layer::Mutated(%p) VisibleRegion was %s is %s", this, 929 mVisibleRegion.ToString().get(), aRegion.ToString().get())); 930 mVisibleRegion = aRegion; 931 Mutated(); 932 } 933 } 934 935 /** 936 * CONSTRUCTION PHASE ONLY 937 * Set the (sub)document metrics used to render the Layer subtree 938 * rooted at this. Note that a layer may have multiple FrameMetrics 939 * objects; calling this function will remove all of them and replace 940 * them with the provided FrameMetrics. See the documentation for 941 * SetFrameMetrics(const nsTArray<FrameMetrics>&) for more details. 942 */ SetScrollMetadata(const ScrollMetadata & aScrollMetadata)943 void SetScrollMetadata(const ScrollMetadata& aScrollMetadata) { 944 Manager()->ClearPendingScrollInfoUpdate(); 945 if (mScrollMetadata.Length() != 1 || 946 mScrollMetadata[0] != aScrollMetadata) { 947 MOZ_LAYERS_LOG_IF_SHADOWABLE(this, 948 ("Layer::Mutated(%p) FrameMetrics", this)); 949 mScrollMetadata.ReplaceElementsAt(0, mScrollMetadata.Length(), 950 aScrollMetadata); 951 ScrollMetadataChanged(); 952 Mutated(); 953 } 954 } 955 956 /** 957 * CONSTRUCTION PHASE ONLY 958 * Set the (sub)document metrics used to render the Layer subtree 959 * rooted at this. There might be multiple metrics on this layer 960 * because the layer may, for example, be contained inside multiple 961 * nested scrolling subdocuments. In general a Layer having multiple 962 * ScrollMetadata objects is conceptually equivalent to having a stack 963 * of ContainerLayers that have been flattened into this Layer. 964 * See the documentation in LayerMetricsWrapper.h for a more detailed 965 * explanation of this conceptual equivalence. 966 * 967 * Note also that there is actually a many-to-many relationship between 968 * Layers and ScrollMetadata, because multiple Layers may have identical 969 * ScrollMetadata objects. This happens when those layers belong to the 970 * same scrolling subdocument and therefore end up with the same async 971 * transform when they are scrolled by the APZ code. 972 */ SetScrollMetadata(const nsTArray<ScrollMetadata> & aMetadataArray)973 void SetScrollMetadata(const nsTArray<ScrollMetadata>& aMetadataArray) { 974 Manager()->ClearPendingScrollInfoUpdate(); 975 if (mScrollMetadata != aMetadataArray) { 976 MOZ_LAYERS_LOG_IF_SHADOWABLE(this, 977 ("Layer::Mutated(%p) FrameMetrics", this)); 978 mScrollMetadata = aMetadataArray; 979 ScrollMetadataChanged(); 980 Mutated(); 981 } 982 } 983 984 /* 985 * Compositor event handling 986 * ========================= 987 * When a touch-start event (or similar) is sent to the 988 * AsyncPanZoomController, it needs to decide whether the event should be sent 989 * to the main thread. Each layer has a list of event handling regions. When 990 * the compositor needs to determine how to handle a touch event, it scans the 991 * layer tree from top to bottom in z-order (traversing children before their 992 * parents). Points outside the clip region for a layer cause that layer (and 993 * its subtree) to be ignored. If a layer has a mask layer, and that mask 994 * layer's alpha value is zero at the event point, then the layer and its 995 * subtree should be ignored. For each layer, if the point is outside its hit 996 * region, we ignore the layer and move onto the next. If the point is inside 997 * its hit region but outside the dispatch-to-content region, we can initiate 998 * a gesture without consulting the content thread. Otherwise we must dispatch 999 * the event to content. Note that if a layer or any ancestor layer has a 1000 * ForceEmptyHitRegion override in GetEventRegionsOverride() then the 1001 * hit-region must be treated as empty. Similarly, if there is a 1002 * ForceDispatchToContent override then the dispatch-to-content region must be 1003 * treated as encompassing the entire hit region, and therefore we must 1004 * consult the content thread before initiating a gesture. (If both flags are 1005 * set, ForceEmptyHitRegion takes priority.) 1006 */ 1007 /** 1008 * CONSTRUCTION PHASE ONLY 1009 * Set the event handling region. 1010 */ SetEventRegions(const EventRegions & aRegions)1011 void SetEventRegions(const EventRegions& aRegions) { 1012 if (mEventRegions != aRegions) { 1013 MOZ_LAYERS_LOG_IF_SHADOWABLE( 1014 this, ("Layer::Mutated(%p) eventregions were %s, now %s", this, 1015 mEventRegions.ToString().get(), aRegions.ToString().get())); 1016 mEventRegions = aRegions; 1017 Mutated(); 1018 } 1019 } 1020 1021 /** 1022 * CONSTRUCTION PHASE ONLY 1023 * Set the opacity which will be applied to this layer as it 1024 * is composited to the destination. 1025 */ SetOpacity(float aOpacity)1026 void SetOpacity(float aOpacity) { 1027 if (mSimpleAttrs.SetOpacity(aOpacity)) { 1028 MOZ_LAYERS_LOG_IF_SHADOWABLE(this, ("Layer::Mutated(%p) Opacity", this)); 1029 MutatedSimple(); 1030 } 1031 } 1032 SetMixBlendMode(gfx::CompositionOp aMixBlendMode)1033 void SetMixBlendMode(gfx::CompositionOp aMixBlendMode) { 1034 if (mSimpleAttrs.SetMixBlendMode(aMixBlendMode)) { 1035 MOZ_LAYERS_LOG_IF_SHADOWABLE(this, 1036 ("Layer::Mutated(%p) MixBlendMode", this)); 1037 MutatedSimple(); 1038 } 1039 } 1040 SetForceIsolatedGroup(bool aForceIsolatedGroup)1041 void SetForceIsolatedGroup(bool aForceIsolatedGroup) { 1042 if (mSimpleAttrs.SetForceIsolatedGroup(aForceIsolatedGroup)) { 1043 MOZ_LAYERS_LOG_IF_SHADOWABLE( 1044 this, ("Layer::Mutated(%p) ForceIsolatedGroup", this)); 1045 MutatedSimple(); 1046 } 1047 } 1048 GetForceIsolatedGroup()1049 bool GetForceIsolatedGroup() const { 1050 return mSimpleAttrs.ForceIsolatedGroup(); 1051 } 1052 1053 /** 1054 * CONSTRUCTION PHASE ONLY 1055 * Set a clip rect which will be applied to this layer as it is 1056 * composited to the destination. The coordinates are relative to 1057 * the parent layer (i.e. the contents of this layer 1058 * are transformed before this clip rect is applied). 1059 * For the root layer, the coordinates are relative to the widget, 1060 * in device pixels. 1061 * If aRect is null no clipping will be performed. 1062 */ SetClipRect(const Maybe<ParentLayerIntRect> & aRect)1063 void SetClipRect(const Maybe<ParentLayerIntRect>& aRect) { 1064 if (mClipRect) { 1065 if (!aRect) { 1066 MOZ_LAYERS_LOG_IF_SHADOWABLE( 1067 this, ("Layer::Mutated(%p) ClipRect was %d,%d,%d,%d is <none>", 1068 this, mClipRect->X(), mClipRect->Y(), mClipRect->Width(), 1069 mClipRect->Height())); 1070 mClipRect.reset(); 1071 Mutated(); 1072 } else { 1073 if (!aRect->IsEqualEdges(*mClipRect)) { 1074 MOZ_LAYERS_LOG_IF_SHADOWABLE( 1075 this, 1076 ("Layer::Mutated(%p) ClipRect was %d,%d,%d,%d is %d,%d,%d,%d", 1077 this, mClipRect->X(), mClipRect->Y(), mClipRect->Width(), 1078 mClipRect->Height(), aRect->X(), aRect->Y(), aRect->Width(), 1079 aRect->Height())); 1080 mClipRect = aRect; 1081 Mutated(); 1082 } 1083 } 1084 } else { 1085 if (aRect) { 1086 MOZ_LAYERS_LOG_IF_SHADOWABLE( 1087 this, 1088 ("Layer::Mutated(%p) ClipRect was <none> is %d,%d,%d,%d", this, 1089 aRect->X(), aRect->Y(), aRect->Width(), aRect->Height())); 1090 mClipRect = aRect; 1091 Mutated(); 1092 } 1093 } 1094 } 1095 1096 /** 1097 * CONSTRUCTION PHASE ONLY 1098 * Set an optional scrolled clip on the layer. 1099 * The scrolled clip, if present, consists of a clip rect and an optional 1100 * mask. This scrolled clip is always scrolled by all scroll frames associated 1101 * with this layer. (By contrast, the scroll clips stored in ScrollMetadata 1102 * are only scrolled by scroll frames above that ScrollMetadata, and the 1103 * layer's mClipRect is always fixed to the layer contents (which may or may 1104 * not be scrolled by some of the scroll frames associated with the layer, 1105 * depending on whether the layer is fixed).) 1106 */ SetScrolledClip(const Maybe<LayerClip> & aScrolledClip)1107 void SetScrolledClip(const Maybe<LayerClip>& aScrolledClip) { 1108 if (mSimpleAttrs.SetScrolledClip(aScrolledClip)) { 1109 MOZ_LAYERS_LOG_IF_SHADOWABLE(this, 1110 ("Layer::Mutated(%p) ScrolledClip", this)); 1111 MutatedSimple(); 1112 } 1113 } 1114 1115 /** 1116 * CONSTRUCTION PHASE ONLY 1117 * Set a layer to mask this layer. 1118 * 1119 * The mask layer should be applied using its effective transform (after it 1120 * is calculated by ComputeEffectiveTransformForMaskLayer), this should use 1121 * this layer's parent's transform and the mask layer's transform, but not 1122 * this layer's. That is, the mask layer is specified relative to this layer's 1123 * position in it's parent layer's coord space. 1124 * Currently, only 2D translations are supported for the mask layer transform. 1125 * 1126 * Ownership of aMaskLayer passes to this. 1127 * Typical use would be an ImageLayer with an alpha image used for masking. 1128 * See also ContainerState::BuildMaskLayer in FrameLayerBuilder.cpp. 1129 */ SetMaskLayer(Layer * aMaskLayer)1130 void SetMaskLayer(Layer* aMaskLayer) { 1131 #ifdef DEBUG 1132 if (aMaskLayer) { 1133 bool maskIs2D = aMaskLayer->GetTransform().CanDraw2D(); 1134 NS_ASSERTION(maskIs2D, "Mask layer has invalid transform."); 1135 } 1136 #endif 1137 1138 if (mMaskLayer != aMaskLayer) { 1139 MOZ_LAYERS_LOG_IF_SHADOWABLE(this, 1140 ("Layer::Mutated(%p) MaskLayer", this)); 1141 mMaskLayer = aMaskLayer; 1142 Mutated(); 1143 } 1144 } 1145 1146 /** 1147 * CONSTRUCTION PHASE ONLY 1148 * Add mask layers associated with LayerClips. 1149 */ SetAncestorMaskLayers(const nsTArray<RefPtr<Layer>> & aLayers)1150 void SetAncestorMaskLayers(const nsTArray<RefPtr<Layer>>& aLayers) { 1151 if (aLayers != mAncestorMaskLayers) { 1152 MOZ_LAYERS_LOG_IF_SHADOWABLE( 1153 this, ("Layer::Mutated(%p) AncestorMaskLayers", this)); 1154 mAncestorMaskLayers = aLayers; 1155 Mutated(); 1156 } 1157 } 1158 1159 /** 1160 * CONSTRUCTION PHASE ONLY 1161 * Add a mask layer associated with a LayerClip. 1162 */ AddAncestorMaskLayer(const RefPtr<Layer> & aLayer)1163 void AddAncestorMaskLayer(const RefPtr<Layer>& aLayer) { 1164 mAncestorMaskLayers.AppendElement(aLayer); 1165 Mutated(); 1166 } 1167 1168 /** 1169 * CONSTRUCTION PHASE ONLY 1170 * Tell this layer what its transform should be. The transformation 1171 * is applied when compositing the layer into its parent container. 1172 */ SetBaseTransform(const gfx::Matrix4x4 & aMatrix)1173 void SetBaseTransform(const gfx::Matrix4x4& aMatrix) { 1174 NS_ASSERTION(!aMatrix.IsSingular(), 1175 "Shouldn't be trying to draw with a singular matrix!"); 1176 mPendingTransform = nullptr; 1177 if (!mSimpleAttrs.SetTransform(aMatrix)) { 1178 return; 1179 } 1180 MOZ_LAYERS_LOG_IF_SHADOWABLE(this, 1181 ("Layer::Mutated(%p) BaseTransform", this)); 1182 MutatedSimple(); 1183 } 1184 1185 /** 1186 * Can be called at any time. 1187 * 1188 * Like SetBaseTransform(), but can be called before the next 1189 * transform (i.e. outside an open transaction). Semantically, this 1190 * method enqueues a new transform value to be set immediately after 1191 * the next transaction is opened. 1192 */ SetBaseTransformForNextTransaction(const gfx::Matrix4x4 & aMatrix)1193 void SetBaseTransformForNextTransaction(const gfx::Matrix4x4& aMatrix) { 1194 mPendingTransform = new gfx::Matrix4x4(aMatrix); 1195 } 1196 SetPostScale(float aXScale,float aYScale)1197 void SetPostScale(float aXScale, float aYScale) { 1198 if (!mSimpleAttrs.SetPostScale(aXScale, aYScale)) { 1199 return; 1200 } 1201 MOZ_LAYERS_LOG_IF_SHADOWABLE(this, ("Layer::Mutated(%p) PostScale", this)); 1202 MutatedSimple(); 1203 } 1204 1205 /** 1206 * CONSTRUCTION PHASE ONLY 1207 * A layer is "fixed position" when it draws content from a content 1208 * (not chrome) document, the topmost content document has a root scrollframe 1209 * with a displayport, but the layer does not move when that displayport 1210 * scrolls. 1211 */ SetIsFixedPosition(bool aFixedPosition)1212 void SetIsFixedPosition(bool aFixedPosition) { 1213 if (mSimpleAttrs.SetIsFixedPosition(aFixedPosition)) { 1214 MOZ_LAYERS_LOG_IF_SHADOWABLE( 1215 this, ("Layer::Mutated(%p) IsFixedPosition", this)); 1216 MutatedSimple(); 1217 } 1218 } 1219 1220 /** 1221 * CONSTRUCTION PHASE ONLY 1222 * This flag is true when the transform on the layer is a perspective 1223 * transform. The compositor treats perspective transforms specially 1224 * for async scrolling purposes. 1225 */ SetTransformIsPerspective(bool aTransformIsPerspective)1226 void SetTransformIsPerspective(bool aTransformIsPerspective) { 1227 if (mSimpleAttrs.SetTransformIsPerspective(aTransformIsPerspective)) { 1228 MOZ_LAYERS_LOG_IF_SHADOWABLE( 1229 this, ("Layer::Mutated(%p) TransformIsPerspective", this)); 1230 MutatedSimple(); 1231 } 1232 } 1233 // This is only called when the layer tree is updated. Do not call this from 1234 // layout code. To add an animation to this layer, use AddAnimation. 1235 void SetCompositorAnimations( 1236 const CompositorAnimations& aCompositorAnimations); 1237 // Go through all animations in this layer and its children and, for 1238 // any animations with a null start time, update their start time such 1239 // that at |aReadyTime| the animation's current time corresponds to its 1240 // 'initial current time' value. 1241 void StartPendingAnimations(const TimeStamp& aReadyTime); 1242 1243 /** 1244 * CONSTRUCTION PHASE ONLY 1245 * If a layer represents a fixed position element, this data is stored on the 1246 * layer for use by the compositor. 1247 * 1248 * - |aScrollId| identifies the scroll frame that this element is fixed 1249 * with respect to. 1250 * 1251 * - |aAnchor| is the point on the layer that is considered the "anchor" 1252 * point, that is, the point which remains in the same position when 1253 * compositing the layer tree with a transformation (such as when 1254 * asynchronously scrolling and zooming). 1255 * 1256 * - |aSides| is the set of sides to which the element is fixed relative to. 1257 * This is used if the viewport size is changed in the compositor and 1258 * fixed position items need to shift accordingly. This value is made up 1259 * combining appropriate values from mozilla::SideBits. 1260 */ SetFixedPositionData(FrameMetrics::ViewID aScrollId,const LayerPoint & aAnchor,int32_t aSides)1261 void SetFixedPositionData(FrameMetrics::ViewID aScrollId, 1262 const LayerPoint& aAnchor, int32_t aSides) { 1263 if (mSimpleAttrs.SetFixedPositionData(aScrollId, aAnchor, aSides)) { 1264 MOZ_LAYERS_LOG_IF_SHADOWABLE( 1265 this, ("Layer::Mutated(%p) FixedPositionData", this)); 1266 MutatedSimple(); 1267 } 1268 } 1269 1270 /** 1271 * CONSTRUCTION PHASE ONLY 1272 * If a layer is "sticky position", |aScrollId| holds the scroll identifier 1273 * of the scrollable content that contains it. The difference between the two 1274 * rectangles |aOuter| and |aInner| is treated as two intervals in each 1275 * dimension, with the current scroll position at the origin. For each 1276 * dimension, while that component of the scroll position lies within either 1277 * interval, the layer should not move relative to its scrolling container. 1278 */ SetStickyPositionData(FrameMetrics::ViewID aScrollId,LayerRectAbsolute aOuter,LayerRectAbsolute aInner)1279 void SetStickyPositionData(FrameMetrics::ViewID aScrollId, 1280 LayerRectAbsolute aOuter, 1281 LayerRectAbsolute aInner) { 1282 if (mSimpleAttrs.SetStickyPositionData(aScrollId, aOuter, aInner)) { 1283 MOZ_LAYERS_LOG_IF_SHADOWABLE( 1284 this, ("Layer::Mutated(%p) StickyPositionData", this)); 1285 MutatedSimple(); 1286 } 1287 } 1288 1289 /** 1290 * CONSTRUCTION PHASE ONLY 1291 * If a layer is a scroll thumb container layer, set the scroll identifier 1292 * of the scroll frame scrolled by the thumb, and other data related to the 1293 * thumb. 1294 */ SetScrollThumbData(FrameMetrics::ViewID aScrollId,const ScrollThumbData & aThumbData)1295 void SetScrollThumbData(FrameMetrics::ViewID aScrollId, 1296 const ScrollThumbData& aThumbData) { 1297 if (mSimpleAttrs.SetScrollThumbData(aScrollId, aThumbData)) { 1298 MOZ_LAYERS_LOG_IF_SHADOWABLE(this, 1299 ("Layer::Mutated(%p) ScrollbarData", this)); 1300 MutatedSimple(); 1301 } 1302 } 1303 1304 // Set during construction for the container layer of scrollbar components. 1305 // |aScrollId| holds the scroll identifier of the scrollable content that 1306 // the scrollbar is for. SetScrollbarContainer(FrameMetrics::ViewID aScrollId,ScrollDirection aDirection)1307 void SetScrollbarContainer(FrameMetrics::ViewID aScrollId, 1308 ScrollDirection aDirection) { 1309 if (mSimpleAttrs.SetScrollbarContainer(aScrollId, aDirection)) { 1310 MutatedSimple(); 1311 } 1312 } 1313 1314 // Used when forwarding transactions. Do not use at any other time. SetSimpleAttributes(const SimpleLayerAttributes & aAttrs)1315 void SetSimpleAttributes(const SimpleLayerAttributes& aAttrs) { 1316 mSimpleAttrs = aAttrs; 1317 } GetSimpleAttributes()1318 const SimpleLayerAttributes& GetSimpleAttributes() const { 1319 return mSimpleAttrs; 1320 } 1321 1322 // These getters can be used anytime. GetOpacity()1323 float GetOpacity() { return mSimpleAttrs.Opacity(); } GetMixBlendMode()1324 gfx::CompositionOp GetMixBlendMode() const { 1325 return mSimpleAttrs.MixBlendMode(); 1326 } GetClipRect()1327 const Maybe<ParentLayerIntRect>& GetClipRect() const { return mClipRect; } GetScrolledClip()1328 const Maybe<LayerClip>& GetScrolledClip() const { 1329 return mSimpleAttrs.ScrolledClip(); 1330 } 1331 Maybe<ParentLayerIntRect> GetScrolledClipRect() const; GetContentFlags()1332 uint32_t GetContentFlags() { return mSimpleAttrs.ContentFlags(); } GetVisibleRegion()1333 const LayerIntRegion& GetVisibleRegion() const { return mVisibleRegion; } 1334 const ScrollMetadata& GetScrollMetadata(uint32_t aIndex) const; 1335 const FrameMetrics& GetFrameMetrics(uint32_t aIndex) const; GetScrollMetadataCount()1336 uint32_t GetScrollMetadataCount() const { return mScrollMetadata.Length(); } GetAllScrollMetadata()1337 const nsTArray<ScrollMetadata>& GetAllScrollMetadata() { 1338 return mScrollMetadata; 1339 } 1340 bool HasScrollableFrameMetrics() const; 1341 bool IsScrollableWithoutContent() const; GetEventRegions()1342 const EventRegions& GetEventRegions() const { return mEventRegions; } GetParent()1343 ContainerLayer* GetParent() { return mParent; } GetNextSibling()1344 Layer* GetNextSibling() { 1345 if (mNextSibling) { 1346 mNextSibling->CheckCanary(); 1347 } 1348 return mNextSibling; 1349 } GetNextSibling()1350 const Layer* GetNextSibling() const { 1351 if (mNextSibling) { 1352 mNextSibling->CheckCanary(); 1353 } 1354 return mNextSibling; 1355 } GetPrevSibling()1356 Layer* GetPrevSibling() { return mPrevSibling; } GetPrevSibling()1357 const Layer* GetPrevSibling() const { return mPrevSibling; } GetFirstChild()1358 virtual Layer* GetFirstChild() const { return nullptr; } GetLastChild()1359 virtual Layer* GetLastChild() const { return nullptr; } 1360 gfx::Matrix4x4 GetTransform() const; 1361 // Same as GetTransform(), but returns the transform as a strongly-typed 1362 // matrix. Eventually this will replace GetTransform(). 1363 const CSSTransformMatrix GetTransformTyped() const; GetBaseTransform()1364 const gfx::Matrix4x4& GetBaseTransform() const { 1365 return mSimpleAttrs.Transform(); 1366 } 1367 // Note: these are virtual because ContainerLayerComposite overrides them. GetPostXScale()1368 virtual float GetPostXScale() const { return mSimpleAttrs.PostXScale(); } GetPostYScale()1369 virtual float GetPostYScale() const { return mSimpleAttrs.PostYScale(); } GetIsFixedPosition()1370 bool GetIsFixedPosition() { return mSimpleAttrs.IsFixedPosition(); } GetTransformIsPerspective()1371 bool GetTransformIsPerspective() const { 1372 return mSimpleAttrs.TransformIsPerspective(); 1373 } GetIsStickyPosition()1374 bool GetIsStickyPosition() { return mSimpleAttrs.IsStickyPosition(); } GetFixedPositionScrollContainerId()1375 FrameMetrics::ViewID GetFixedPositionScrollContainerId() { 1376 return mSimpleAttrs.FixedPositionScrollContainerId(); 1377 } GetFixedPositionAnchor()1378 LayerPoint GetFixedPositionAnchor() { 1379 return mSimpleAttrs.FixedPositionAnchor(); 1380 } GetFixedPositionSides()1381 int32_t GetFixedPositionSides() { return mSimpleAttrs.FixedPositionSides(); } GetStickyScrollContainerId()1382 FrameMetrics::ViewID GetStickyScrollContainerId() { 1383 return mSimpleAttrs.StickyScrollContainerId(); 1384 } GetStickyScrollRangeOuter()1385 const LayerRectAbsolute& GetStickyScrollRangeOuter() { 1386 return mSimpleAttrs.StickyScrollRangeOuter(); 1387 } GetStickyScrollRangeInner()1388 const LayerRectAbsolute& GetStickyScrollRangeInner() { 1389 return mSimpleAttrs.StickyScrollRangeInner(); 1390 } GetScrollbarTargetContainerId()1391 FrameMetrics::ViewID GetScrollbarTargetContainerId() { 1392 return mSimpleAttrs.ScrollbarTargetContainerId(); 1393 } GetScrollThumbData()1394 const ScrollThumbData& GetScrollThumbData() const { 1395 return mSimpleAttrs.ThumbData(); 1396 } IsScrollbarContainer()1397 bool IsScrollbarContainer() { 1398 return mSimpleAttrs.GetScrollbarContainerDirection().isSome(); 1399 } GetScrollbarContainerDirection()1400 Maybe<ScrollDirection> GetScrollbarContainerDirection() { 1401 return mSimpleAttrs.GetScrollbarContainerDirection(); 1402 } GetMaskLayer()1403 Layer* GetMaskLayer() const { return mMaskLayer; } HasPendingTransform()1404 bool HasPendingTransform() const { return mPendingTransform; } 1405 CheckCanary()1406 void CheckCanary() const { mCanary.Check(); } 1407 1408 // Ancestor mask layers are associated with FrameMetrics, but for simplicity 1409 // in maintaining the layer tree structure we attach them to the layer. GetAncestorMaskLayerCount()1410 size_t GetAncestorMaskLayerCount() const { 1411 return mAncestorMaskLayers.Length(); 1412 } GetAncestorMaskLayerAt(size_t aIndex)1413 Layer* GetAncestorMaskLayerAt(size_t aIndex) const { 1414 return mAncestorMaskLayers.ElementAt(aIndex); 1415 } GetAllAncestorMaskLayers()1416 const nsTArray<RefPtr<Layer>>& GetAllAncestorMaskLayers() const { 1417 return mAncestorMaskLayers; 1418 } 1419 HasMaskLayers()1420 bool HasMaskLayers() const { 1421 return GetMaskLayer() || mAncestorMaskLayers.Length() > 0; 1422 } 1423 1424 /* 1425 * Get the combined clip rect of the Layer clip and all clips on FrameMetrics. 1426 * This is intended for use in Layout. The compositor needs to apply async 1427 * transforms to find the combined clip. 1428 */ 1429 Maybe<ParentLayerIntRect> GetCombinedClipRect() const; 1430 1431 /** 1432 * Retrieve the root level visible region for |this| taking into account 1433 * clipping applied to parent layers of |this| as well as subtracting 1434 * visible regions of higher siblings of this layer and each ancestor. 1435 * 1436 * Note translation values for offsets of visible regions and accumulated 1437 * aLayerOffset are integer rounded using IntPoint::Round. 1438 * 1439 * @param aResult - the resulting visible region of this layer. 1440 * @param aLayerOffset - this layer's total offset from the root layer. 1441 * @return - false if during layer tree traversal a parent or sibling 1442 * transform is found to be non-translational. This method returns early 1443 * in this case, results will not be valid. Returns true on successful 1444 * traversal. 1445 */ 1446 bool GetVisibleRegionRelativeToRootLayer(nsIntRegion& aResult, 1447 nsIntPoint* aLayerOffset); 1448 1449 // Note that all lengths in animation data are either in CSS pixels or app 1450 // units and must be converted to device pixels by the compositor. GetAnimations()1451 AnimationArray& GetAnimations() { return mAnimationInfo.GetAnimations(); } GetCompositorAnimationsId()1452 uint64_t GetCompositorAnimationsId() { 1453 return mAnimationInfo.GetCompositorAnimationsId(); 1454 } 1455 InfallibleTArray<AnimData>& GetAnimationData(); 1456 GetAnimationGeneration()1457 uint64_t GetAnimationGeneration() { 1458 return mAnimationInfo.GetAnimationGeneration(); 1459 } 1460 1461 bool HasTransformAnimation() const; 1462 bool HasOpacityAnimation() const; 1463 GetBaseAnimationStyle()1464 AnimationValue GetBaseAnimationStyle() const { 1465 return mAnimationInfo.GetBaseAnimationStyle(); 1466 } 1467 1468 /** 1469 * Returns the local transform for this layer: either mTransform or, 1470 * for shadow layers, GetShadowBaseTransform(), in either case with the 1471 * pre- and post-scales applied. 1472 */ 1473 gfx::Matrix4x4 GetLocalTransform(); 1474 1475 /** 1476 * Same as GetLocalTransform(), but returns a strongly-typed matrix. 1477 * Eventually, this will replace GetLocalTransform(). 1478 */ 1479 const LayerToParentLayerMatrix4x4 GetLocalTransformTyped(); 1480 1481 /** 1482 * Returns the local opacity for this layer: either mOpacity or, 1483 * for shadow layers, GetShadowOpacity() 1484 */ 1485 float GetLocalOpacity(); 1486 1487 /** 1488 * DRAWING PHASE ONLY 1489 * 1490 * Apply pending changes to layers before drawing them, if those 1491 * pending changes haven't been overridden by later changes. 1492 */ 1493 void ApplyPendingUpdatesToSubtree(); 1494 1495 /** 1496 * DRAWING PHASE ONLY 1497 * 1498 * Write layer-subtype-specific attributes into aAttrs. Used to 1499 * synchronize layer attributes to their shadows'. 1500 */ FillSpecificAttributes(SpecificLayerAttributes & aAttrs)1501 virtual void FillSpecificAttributes(SpecificLayerAttributes& aAttrs) {} 1502 1503 // Returns true if it's OK to save the contents of aLayer in an 1504 // opaque surface (a surface without an alpha channel). 1505 // If we can use a surface without an alpha channel, we should, because 1506 // it will often make painting of antialiased text faster and higher 1507 // quality. 1508 bool CanUseOpaqueSurface(); 1509 GetSurfaceMode()1510 SurfaceMode GetSurfaceMode() { 1511 if (CanUseOpaqueSurface()) return SurfaceMode::SURFACE_OPAQUE; 1512 if (GetContentFlags() & CONTENT_COMPONENT_ALPHA) 1513 return SurfaceMode::SURFACE_COMPONENT_ALPHA; 1514 return SurfaceMode::SURFACE_SINGLE_CHANNEL_ALPHA; 1515 } 1516 1517 // Returns true if this layer can be treated as opaque for visibility 1518 // computation. A layer may be non-opaque for visibility even if it 1519 // is not transparent, for example, if it has a mix-blend-mode. 1520 bool IsOpaqueForVisibility(); 1521 1522 /** 1523 * This setter can be used anytime. The user data for all keys is 1524 * initially null. Ownership pases to the layer manager. 1525 */ 1526 void SetUserData( 1527 void* aKey, LayerUserData* aData, 1528 void (*aDestroy)(void*) = LayerManager::LayerUserDataDestroy) { 1529 mUserData.Add(static_cast<gfx::UserDataKey*>(aKey), aData, aDestroy); 1530 } 1531 /** 1532 * This can be used anytime. Ownership passes to the caller! 1533 */ 1534 UniquePtr<LayerUserData> RemoveUserData(void* aKey); 1535 /** 1536 * This getter can be used anytime. 1537 */ HasUserData(void * aKey)1538 bool HasUserData(void* aKey) { 1539 return mUserData.Has(static_cast<gfx::UserDataKey*>(aKey)); 1540 } 1541 /** 1542 * This getter can be used anytime. Ownership is retained by the layer 1543 * manager. 1544 */ GetUserData(void * aKey)1545 LayerUserData* GetUserData(void* aKey) const { 1546 return static_cast<LayerUserData*>( 1547 mUserData.Get(static_cast<gfx::UserDataKey*>(aKey))); 1548 } 1549 1550 /** 1551 * |Disconnect()| is used by layers hooked up over IPC. It may be 1552 * called at any time, and may not be called at all. Using an 1553 * IPC-enabled layer after Destroy() (drawing etc.) results in a 1554 * safe no-op; no crashy or uaf etc. 1555 * 1556 * XXX: this interface is essentially LayerManager::Destroy, but at 1557 * Layer granularity. It might be beneficial to unify them. 1558 */ Disconnect()1559 virtual void Disconnect() {} 1560 1561 /** 1562 * Dynamic downcast to a PaintedLayer. Returns null if this is not 1563 * a PaintedLayer. 1564 */ AsPaintedLayer()1565 virtual PaintedLayer* AsPaintedLayer() { return nullptr; } 1566 1567 /** 1568 * Dynamic cast to a ContainerLayer. Returns null if this is not 1569 * a ContainerLayer. 1570 */ AsContainerLayer()1571 virtual ContainerLayer* AsContainerLayer() { return nullptr; } AsContainerLayer()1572 virtual const ContainerLayer* AsContainerLayer() const { return nullptr; } 1573 1574 /** 1575 * Dynamic cast to a RefLayer. Returns null if this is not a 1576 * RefLayer. 1577 */ AsRefLayer()1578 virtual RefLayer* AsRefLayer() { return nullptr; } 1579 1580 /** 1581 * Dynamic cast to a Color. Returns null if this is not a 1582 * ColorLayer. 1583 */ AsColorLayer()1584 virtual ColorLayer* AsColorLayer() { return nullptr; } 1585 1586 /** 1587 * Dynamic cast to a Border. Returns null if this is not a 1588 * ColorLayer. 1589 */ AsBorderLayer()1590 virtual BorderLayer* AsBorderLayer() { return nullptr; } 1591 1592 /** 1593 * Dynamic cast to a Canvas. Returns null if this is not a 1594 * ColorLayer. 1595 */ AsCanvasLayer()1596 virtual CanvasLayer* AsCanvasLayer() { return nullptr; } 1597 1598 /** 1599 * Dynamic cast to an Image. Returns null if this is not a 1600 * ColorLayer. 1601 */ AsImageLayer()1602 virtual ImageLayer* AsImageLayer() { return nullptr; } 1603 1604 /** 1605 * Dynamic cast to a LayerComposite. Return null if this is not a 1606 * LayerComposite. Can be used anytime. 1607 */ AsHostLayer()1608 virtual HostLayer* AsHostLayer() { return nullptr; } 1609 1610 /** 1611 * Dynamic cast to a ShadowableLayer. Return null if this is not a 1612 * ShadowableLayer. Can be used anytime. 1613 */ AsShadowableLayer()1614 virtual ShadowableLayer* AsShadowableLayer() { return nullptr; } 1615 1616 /** 1617 * Dynamic cast as a DisplayItemLayer. Return null if not a 1618 * DisplayItemLayer. Can be used anytime. 1619 */ AsDisplayItemLayer()1620 virtual DisplayItemLayer* AsDisplayItemLayer() { return nullptr; } 1621 1622 // These getters can be used anytime. They return the effective 1623 // values that should be used when drawing this layer to screen, 1624 // accounting for this layer possibly being a shadow. 1625 const Maybe<ParentLayerIntRect>& GetLocalClipRect(); 1626 const LayerIntRegion& GetLocalVisibleRegion(); 1627 Extend3DContext()1628 bool Extend3DContext() { 1629 return GetContentFlags() & CONTENT_EXTEND_3D_CONTEXT; 1630 } Combines3DTransformWithAncestors()1631 bool Combines3DTransformWithAncestors() { 1632 return GetParent() && 1633 reinterpret_cast<Layer*>(GetParent())->Extend3DContext(); 1634 } Is3DContextLeaf()1635 bool Is3DContextLeaf() { 1636 return !Extend3DContext() && Combines3DTransformWithAncestors(); 1637 } 1638 /** 1639 * It is true if the user can see the back of the layer and the 1640 * backface is hidden. The compositor should skip the layer if the 1641 * result is true. 1642 */ 1643 bool IsBackfaceHidden(); IsVisible()1644 bool IsVisible() { 1645 // For containers extending 3D context, visible region 1646 // is meaningless, since they are just intermediate result of 1647 // content. 1648 return !GetLocalVisibleRegion().IsEmpty() || Extend3DContext(); 1649 } 1650 1651 /** 1652 * Return true if current layer content is opaque. 1653 * It does not guarantee that layer content is always opaque. 1654 */ IsOpaque()1655 virtual bool IsOpaque() { return GetContentFlags() & CONTENT_OPAQUE; } 1656 1657 /** 1658 * Returns the product of the opacities of this layer and all ancestors up 1659 * to and excluding the nearest ancestor that has UseIntermediateSurface() 1660 * set. 1661 */ 1662 float GetEffectiveOpacity(); 1663 1664 /** 1665 * Returns the blendmode of this layer. 1666 */ 1667 gfx::CompositionOp GetEffectiveMixBlendMode(); 1668 1669 /** 1670 * This returns the effective transform computed by 1671 * ComputeEffectiveTransforms. Typically this is a transform that transforms 1672 * this layer all the way to some intermediate surface or destination 1673 * surface. For non-BasicLayers this will be a transform to the nearest 1674 * ancestor with UseIntermediateSurface() (or to the root, if there is no 1675 * such ancestor), but for BasicLayers it's different. 1676 */ GetEffectiveTransform()1677 const gfx::Matrix4x4& GetEffectiveTransform() const { 1678 return mEffectiveTransform; 1679 } 1680 1681 /** 1682 * This returns the effective transform for Layer's buffer computed by 1683 * ComputeEffectiveTransforms. Typically this is a transform that transforms 1684 * this layer's buffer all the way to some intermediate surface or destination 1685 * surface. For non-BasicLayers this will be a transform to the nearest 1686 * ancestor with UseIntermediateSurface() (or to the root, if there is no 1687 * such ancestor), but for BasicLayers it's different. 1688 * 1689 * By default, its value is same to GetEffectiveTransform(). 1690 * When ImageLayer is rendered with ScaleMode::STRETCH, 1691 * it becomes different from GetEffectiveTransform(). 1692 */ GetEffectiveTransformForBuffer()1693 virtual const gfx::Matrix4x4& GetEffectiveTransformForBuffer() const { 1694 return mEffectiveTransform; 1695 } 1696 1697 /** 1698 * If the current layers participates in a preserve-3d 1699 * context (returns true for Combines3DTransformWithAncestors), 1700 * returns the combined transform up to the preserve-3d (nearest 1701 * ancestor that doesn't Extend3DContext()). Otherwise returns 1702 * the local transform. 1703 */ 1704 gfx::Matrix4x4 ComputeTransformToPreserve3DRoot(); 1705 1706 /** 1707 * @param aTransformToSurface the composition of the transforms 1708 * from the parent layer (if any) to the destination pixel grid. 1709 * 1710 * Computes mEffectiveTransform for this layer and all its descendants. 1711 * mEffectiveTransform transforms this layer up to the destination 1712 * pixel grid (whatever aTransformToSurface is relative to). 1713 * 1714 * We promise that when this is called on a layer, all ancestor layers 1715 * have already had ComputeEffectiveTransforms called. 1716 */ 1717 virtual void ComputeEffectiveTransforms( 1718 const gfx::Matrix4x4& aTransformToSurface) = 0; 1719 1720 /** 1721 * Computes the effective transform for mask layers, if this layer has any. 1722 */ 1723 void ComputeEffectiveTransformForMaskLayers( 1724 const gfx::Matrix4x4& aTransformToSurface); 1725 static void ComputeEffectiveTransformForMaskLayer( 1726 Layer* aMaskLayer, const gfx::Matrix4x4& aTransformToSurface); 1727 1728 /** 1729 * Calculate the scissor rect required when rendering this layer. 1730 * Returns a rectangle relative to the intermediate surface belonging to the 1731 * nearest ancestor that has an intermediate surface, or relative to the root 1732 * viewport if no ancestor has an intermediate surface, corresponding to the 1733 * clip rect for this layer intersected with aCurrentScissorRect. 1734 */ 1735 RenderTargetIntRect CalculateScissorRect( 1736 const RenderTargetIntRect& aCurrentScissorRect); 1737 1738 virtual const char* Name() const = 0; 1739 virtual LayerType GetType() const = 0; 1740 1741 /** 1742 * Only the implementation should call this. This is per-implementation 1743 * private data. Normally, all layers with a given layer manager 1744 * use the same type of ImplData. 1745 */ ImplData()1746 void* ImplData() { return mImplData; } 1747 1748 /** 1749 * Only the implementation should use these methods. 1750 */ SetParent(ContainerLayer * aParent)1751 void SetParent(ContainerLayer* aParent) { mParent = aParent; } SetNextSibling(Layer * aSibling)1752 void SetNextSibling(Layer* aSibling) { mNextSibling = aSibling; } SetPrevSibling(Layer * aSibling)1753 void SetPrevSibling(Layer* aSibling) { mPrevSibling = aSibling; } 1754 1755 /** 1756 * Dump information about this layer manager and its managed tree to 1757 * aStream. 1758 */ 1759 void Dump(std::stringstream& aStream, const char* aPrefix = "", 1760 bool aDumpHtml = false, bool aSorted = false, 1761 const Maybe<gfx::Polygon>& aGeometry = Nothing()); 1762 /** 1763 * Dump information about just this layer manager itself to aStream. 1764 */ 1765 void DumpSelf(std::stringstream& aStream, const char* aPrefix = "", 1766 const Maybe<gfx::Polygon>& aGeometry = Nothing()); 1767 1768 /** 1769 * Dump information about this layer and its child & sibling layers to 1770 * layerscope packet. 1771 */ 1772 void Dump(layerscope::LayersPacket* aPacket, const void* aParent); 1773 1774 /** 1775 * Log information about this layer manager and its managed tree to 1776 * the NSPR log (if enabled for "Layers"). 1777 */ 1778 void Log(const char* aPrefix = ""); 1779 /** 1780 * Log information about just this layer manager itself to the NSPR 1781 * log (if enabled for "Layers"). 1782 */ 1783 void LogSelf(const char* aPrefix = ""); 1784 1785 // Print interesting information about this into aStream. Internally 1786 // used to implement Dump*() and Log*(). If subclasses have 1787 // additional interesting properties, they should override this with 1788 // an implementation that first calls the base implementation then 1789 // appends additional info to aTo. 1790 virtual void PrintInfo(std::stringstream& aStream, const char* aPrefix); 1791 1792 // Just like PrintInfo, but this function dump information into layerscope 1793 // packet, instead of a StringStream. It is also internally used to implement 1794 // Dump(); 1795 virtual void DumpPacket(layerscope::LayersPacket* aPacket, 1796 const void* aParent); 1797 1798 /** 1799 * Store display list log. 1800 */ 1801 void SetDisplayListLog(const char* log); 1802 1803 /** 1804 * Return display list log. 1805 */ 1806 void GetDisplayListLog(nsCString& log); 1807 IsLogEnabled()1808 static bool IsLogEnabled() { return LayerManager::IsLogEnabled(); } 1809 1810 /** 1811 * Returns the current area of the layer (in layer-space coordinates) 1812 * marked as needed to be recomposited. 1813 */ GetInvalidRegion()1814 const virtual gfx::TiledIntRegion& GetInvalidRegion() { 1815 return mInvalidRegion; 1816 } AddInvalidRegion(const nsIntRegion & aRegion)1817 void AddInvalidRegion(const nsIntRegion& aRegion) { 1818 mInvalidRegion.Add(aRegion); 1819 } 1820 1821 /** 1822 * Mark the entirety of the layer's visible region as being invalid. 1823 */ SetInvalidRectToVisibleRegion()1824 void SetInvalidRectToVisibleRegion() { 1825 mInvalidRegion.SetEmpty(); 1826 mInvalidRegion.Add(GetVisibleRegion().ToUnknownRegion()); 1827 } 1828 1829 /** 1830 * Adds to the current invalid rect. 1831 */ AddInvalidRect(const gfx::IntRect & aRect)1832 void AddInvalidRect(const gfx::IntRect& aRect) { mInvalidRegion.Add(aRect); } 1833 1834 /** 1835 * Clear the invalid rect, marking the layer as being identical to what is 1836 * currently composited. 1837 */ ClearInvalidRegion()1838 virtual void ClearInvalidRegion() { mInvalidRegion.SetEmpty(); } 1839 1840 // These functions allow attaching an AsyncPanZoomController to this layer, 1841 // and can be used anytime. 1842 // A layer has an APZC at index aIndex only-if 1843 // GetFrameMetrics(aIndex).IsScrollable(); attempting to get an APZC for a 1844 // non-scrollable metrics will return null. The aIndex for these functions 1845 // must be less than GetScrollMetadataCount(). 1846 void SetAsyncPanZoomController(uint32_t aIndex, 1847 AsyncPanZoomController* controller); 1848 AsyncPanZoomController* GetAsyncPanZoomController(uint32_t aIndex) const; 1849 // The ScrollMetadataChanged function is used internally to ensure the APZC 1850 // array length matches the frame metrics array length. 1851 ClearCachedResources()1852 virtual void ClearCachedResources() {} 1853 SupportsAsyncUpdate()1854 virtual bool SupportsAsyncUpdate() { return false; } 1855 1856 private: 1857 void ScrollMetadataChanged(); 1858 1859 public: 1860 void ApplyPendingUpdatesForThisTransaction(); 1861 1862 #ifdef DEBUG SetDebugColorIndex(uint32_t aIndex)1863 void SetDebugColorIndex(uint32_t aIndex) { mDebugColorIndex = aIndex; } GetDebugColorIndex()1864 uint32_t GetDebugColorIndex() { return mDebugColorIndex; } 1865 #endif 1866 Mutated()1867 void Mutated() { mManager->Mutated(this); } MutatedSimple()1868 void MutatedSimple() { mManager->MutatedSimple(this); } 1869 GetMaxLayerSize()1870 virtual int32_t GetMaxLayerSize() { return Manager()->GetMaxTextureSize(); } 1871 1872 /** 1873 * Returns true if this layer's effective transform is not just 1874 * a translation by integers, or if this layer or some ancestor layer 1875 * is marked as having a transform that may change without a full layer 1876 * transaction. 1877 * 1878 * Note: This function ignores ancestor layers across layer tree boundaries 1879 * so that it returns a consistent value when compositing and when painting. 1880 */ 1881 bool MayResample(); 1882 1883 RenderTargetRect TransformRectToRenderTarget(const LayerIntRect& aRect); 1884 1885 /** 1886 * Add debugging information to the layer dump. 1887 */ AddExtraDumpInfo(const nsACString & aStr)1888 void AddExtraDumpInfo(const nsACString& aStr) { 1889 #ifdef MOZ_DUMP_PAINTING 1890 mExtraDumpInfo.AppendElement(aStr); 1891 #endif 1892 } 1893 1894 /** 1895 * Clear debugging information. Useful for recycling. 1896 */ ClearExtraDumpInfo()1897 void ClearExtraDumpInfo() { 1898 #ifdef MOZ_DUMP_PAINTING 1899 mExtraDumpInfo.Clear(); 1900 #endif 1901 } 1902 GetAnimationInfo()1903 AnimationInfo& GetAnimationInfo() { return mAnimationInfo; } 1904 1905 protected: 1906 Layer(LayerManager* aManager, void* aImplData); 1907 1908 // Protected destructor, to discourage deletion outside of Release(): 1909 virtual ~Layer(); 1910 1911 /** 1912 * We can snap layer transforms for two reasons: 1913 * 1) To avoid unnecessary resampling when a transform is a translation 1914 * by a non-integer number of pixels. 1915 * Snapping the translation to an integer number of pixels avoids 1916 * blurring the layer and can be faster to composite. 1917 * 2) When a layer is used to render a rectangular object, we need to 1918 * emulate the rendering of rectangular inactive content and snap the 1919 * edges of the rectangle to pixel boundaries. This is both to ensure 1920 * layer rendering is consistent with inactive content rendering, and to 1921 * avoid seams. 1922 * This function implements type 1 snapping. If aTransform is a 2D 1923 * translation, and this layer's layer manager has enabled snapping 1924 * (which is the default), return aTransform with the translation snapped 1925 * to nearest pixels. Otherwise just return aTransform. Call this when the 1926 * layer does not correspond to a single rectangular content object. 1927 * This function does not try to snap if aTransform has a scale, because in 1928 * that case resampling is inevitable and there's no point in trying to 1929 * avoid it. In fact snapping can cause problems because pixel edges in the 1930 * layer's content can be rendered unpredictably (jiggling) as the scale 1931 * interacts with the snapping of the translation, especially with animated 1932 * transforms. 1933 * @param aResidualTransform a transform to apply before the result transform 1934 * in order to get the results to completely match aTransform. 1935 */ 1936 gfx::Matrix4x4 SnapTransformTranslation(const gfx::Matrix4x4& aTransform, 1937 gfx::Matrix* aResidualTransform); 1938 gfx::Matrix4x4 SnapTransformTranslation3D(const gfx::Matrix4x4& aTransform, 1939 gfx::Matrix* aResidualTransform); 1940 /** 1941 * See comment for SnapTransformTranslation. 1942 * This function implements type 2 snapping. If aTransform is a translation 1943 * and/or scale, transform aSnapRect by aTransform, snap to pixel boundaries, 1944 * and return the transform that maps aSnapRect to that rect. Otherwise 1945 * just return aTransform. 1946 * @param aSnapRect a rectangle whose edges should be snapped to pixel 1947 * boundaries in the destination surface. 1948 * @param aResidualTransform a transform to apply before the result transform 1949 * in order to get the results to completely match aTransform. 1950 */ 1951 gfx::Matrix4x4 SnapTransform(const gfx::Matrix4x4& aTransform, 1952 const gfxRect& aSnapRect, 1953 gfx::Matrix* aResidualTransform); 1954 1955 LayerManager* mManager; 1956 ContainerLayer* mParent; 1957 Layer* mNextSibling; 1958 Layer* mPrevSibling; 1959 void* mImplData; 1960 RefPtr<Layer> mMaskLayer; 1961 nsTArray<RefPtr<Layer>> mAncestorMaskLayers; 1962 // Look for out-of-bound in the middle of the structure 1963 mozilla::CorruptionCanary mCanary; 1964 gfx::UserData mUserData; 1965 SimpleLayerAttributes mSimpleAttrs; 1966 LayerIntRegion mVisibleRegion; 1967 nsTArray<ScrollMetadata> mScrollMetadata; 1968 EventRegions mEventRegions; 1969 // A mutation of |mTransform| that we've queued to be applied at the 1970 // end of the next transaction (if nothing else overrides it in the 1971 // meantime). 1972 nsAutoPtr<gfx::Matrix4x4> mPendingTransform; 1973 gfx::Matrix4x4 mEffectiveTransform; 1974 AnimationInfo mAnimationInfo; 1975 Maybe<ParentLayerIntRect> mClipRect; 1976 gfx::IntRect mTileSourceRect; 1977 gfx::TiledIntRegion mInvalidRegion; 1978 nsTArray<RefPtr<AsyncPanZoomController>> mApzcs; 1979 bool mUseTileSourceRect; 1980 #ifdef DEBUG 1981 uint32_t mDebugColorIndex; 1982 #endif 1983 #ifdef MOZ_DUMP_PAINTING 1984 nsTArray<nsCString> mExtraDumpInfo; 1985 #endif 1986 // Store display list log. 1987 nsCString mDisplayListLog; 1988 }; 1989 1990 /** 1991 * A Layer which we can paint into. It is a conceptually 1992 * infinite surface, but each PaintedLayer has an associated "valid region" 1993 * of contents that it is currently storing, which is finite. PaintedLayer 1994 * implementations can store content between paints. 1995 * 1996 * PaintedLayers are rendered into during the drawing phase of a transaction. 1997 * 1998 * Currently the contents of a PaintedLayer are in the device output color 1999 * space. 2000 */ 2001 class PaintedLayer : public Layer { 2002 public: 2003 /** 2004 * CONSTRUCTION PHASE ONLY 2005 * Tell this layer that the content in some region has changed and 2006 * will need to be repainted. This area is removed from the valid 2007 * region. 2008 */ 2009 virtual void InvalidateRegion(const nsIntRegion& aRegion) = 0; 2010 /** 2011 * CONSTRUCTION PHASE ONLY 2012 * Set whether ComputeEffectiveTransforms should compute the 2013 * "residual translation" --- the translation that should be applied *before* 2014 * mEffectiveTransform to get the ideal transform for this PaintedLayer. 2015 * When this is true, ComputeEffectiveTransforms will compute the residual 2016 * and ensure that the layer is invalidated whenever the residual changes. 2017 * When it's false, a change in the residual will not trigger invalidation 2018 * and GetResidualTranslation will return 0,0. 2019 * So when the residual is to be ignored, set this to false for better 2020 * performance. 2021 */ SetAllowResidualTranslation(bool aAllow)2022 void SetAllowResidualTranslation(bool aAllow) { 2023 mAllowResidualTranslation = aAllow; 2024 } 2025 SetValidRegion(const nsIntRegion & aRegion)2026 void SetValidRegion(const nsIntRegion& aRegion) { 2027 MOZ_LAYERS_LOG_IF_SHADOWABLE(this, 2028 ("Layer::Mutated(%p) ValidRegion", this)); 2029 mValidRegion = aRegion; 2030 mValidRegionIsCurrent = true; 2031 Mutated(); 2032 } 2033 2034 /** 2035 * Can be used anytime 2036 */ GetValidRegion()2037 const nsIntRegion& GetValidRegion() const { 2038 EnsureValidRegionIsCurrent(); 2039 return mValidRegion; 2040 } 2041 InvalidateWholeLayer()2042 void InvalidateWholeLayer() { 2043 mInvalidRegion.Add(GetValidRegion().GetBounds()); 2044 ClearValidRegion(); 2045 } 2046 ClearValidRegion()2047 void ClearValidRegion() { 2048 mValidRegion.SetEmpty(); 2049 mValidRegionIsCurrent = true; 2050 } AddToValidRegion(const nsIntRegion & aRegion)2051 void AddToValidRegion(const nsIntRegion& aRegion) { 2052 EnsureValidRegionIsCurrent(); 2053 mValidRegion.OrWith(aRegion); 2054 } SubtractFromValidRegion(const nsIntRegion & aRegion)2055 void SubtractFromValidRegion(const nsIntRegion& aRegion) { 2056 EnsureValidRegionIsCurrent(); 2057 mValidRegion.SubOut(aRegion); 2058 } UpdateValidRegionAfterInvalidRegionChanged()2059 void UpdateValidRegionAfterInvalidRegionChanged() { 2060 // Changes to mInvalidRegion will be applied to mValidRegion on the next 2061 // call to EnsureValidRegionIsCurrent(). 2062 mValidRegionIsCurrent = false; 2063 } 2064 ClearInvalidRegion()2065 void ClearInvalidRegion() override { 2066 // mInvalidRegion is about to be reset. This is the last chance to apply 2067 // any pending changes from it to mValidRegion. Do that by calling 2068 // EnsureValidRegionIsCurrent(). 2069 EnsureValidRegionIsCurrent(); 2070 mInvalidRegion.SetEmpty(); 2071 } 2072 AsPaintedLayer()2073 virtual PaintedLayer* AsPaintedLayer() override { return this; } 2074 2075 MOZ_LAYER_DECL_NAME("PaintedLayer", TYPE_PAINTED) 2076 ComputeEffectiveTransforms(const gfx::Matrix4x4 & aTransformToSurface)2077 virtual void ComputeEffectiveTransforms( 2078 const gfx::Matrix4x4& aTransformToSurface) override { 2079 gfx::Matrix4x4 idealTransform = GetLocalTransform() * aTransformToSurface; 2080 gfx::Matrix residual; 2081 mEffectiveTransform = SnapTransformTranslation( 2082 idealTransform, mAllowResidualTranslation ? &residual : nullptr); 2083 // The residual can only be a translation because SnapTransformTranslation 2084 // only changes the transform if it's a translation 2085 NS_ASSERTION(residual.IsTranslation(), 2086 "Residual transform can only be a translation"); 2087 if (!gfx::ThebesPoint(residual.GetTranslation()) 2088 .WithinEpsilonOf(mResidualTranslation, 1e-3f)) { 2089 mResidualTranslation = gfx::ThebesPoint(residual.GetTranslation()); 2090 DebugOnly<mozilla::gfx::Point> transformedOrig = 2091 idealTransform.TransformPoint(mozilla::gfx::Point()); 2092 #ifdef DEBUG 2093 DebugOnly<mozilla::gfx::Point> transformed = 2094 idealTransform.TransformPoint(mozilla::gfx::Point( 2095 mResidualTranslation.x, mResidualTranslation.y)) - 2096 *&transformedOrig; 2097 #endif 2098 NS_ASSERTION(-0.5 <= (&transformed)->x && (&transformed)->x < 0.5 && 2099 -0.5 <= (&transformed)->y && (&transformed)->y < 0.5, 2100 "Residual translation out of range"); 2101 ClearValidRegion(); 2102 } 2103 ComputeEffectiveTransformForMaskLayers(aTransformToSurface); 2104 } 2105 GetCreationHint()2106 LayerManager::PaintedLayerCreationHint GetCreationHint() const { 2107 return mCreationHint; 2108 } 2109 UsedForReadback()2110 bool UsedForReadback() { return mUsedForReadback; } SetUsedForReadback(bool aUsed)2111 void SetUsedForReadback(bool aUsed) { mUsedForReadback = aUsed; } 2112 2113 /** 2114 * Returns true if aLayer is optimized for the given PaintedLayerCreationHint. 2115 */ IsOptimizedFor(LayerManager::PaintedLayerCreationHint aCreationHint)2116 virtual bool IsOptimizedFor( 2117 LayerManager::PaintedLayerCreationHint aCreationHint) { 2118 return true; 2119 } 2120 2121 /** 2122 * Returns the residual translation. Apply this translation when drawing 2123 * into the PaintedLayer so that when mEffectiveTransform is applied 2124 * afterwards by layer compositing, the results exactly match the "ideal 2125 * transform" (the product of the transform of this layer and its ancestors). 2126 * Returns 0,0 unless SetAllowResidualTranslation(true) has been called. 2127 * The residual translation components are always in the range [-0.5, 0.5). 2128 */ GetResidualTranslation()2129 gfxPoint GetResidualTranslation() const { return mResidualTranslation; } 2130 2131 protected: 2132 PaintedLayer( 2133 LayerManager* aManager, void* aImplData, 2134 LayerManager::PaintedLayerCreationHint aCreationHint = LayerManager::NONE) Layer(aManager,aImplData)2135 : Layer(aManager, aImplData), 2136 mValidRegion(), 2137 mValidRegionIsCurrent(true), 2138 mCreationHint(aCreationHint), 2139 mUsedForReadback(false), 2140 mAllowResidualTranslation(false) {} 2141 2142 virtual void PrintInfo(std::stringstream& aStream, 2143 const char* aPrefix) override; 2144 2145 virtual void DumpPacket(layerscope::LayersPacket* aPacket, 2146 const void* aParent) override; 2147 2148 /** 2149 * ComputeEffectiveTransforms snaps the ideal transform to get 2150 * mEffectiveTransform. mResidualTranslation is the translation that should be 2151 * applied *before* mEffectiveTransform to get the ideal transform. 2152 */ 2153 gfxPoint mResidualTranslation; 2154 2155 private: 2156 /** 2157 * Needs to be called prior to accessing mValidRegion, unless mValidRegion is 2158 * being completely overwritten. 2159 */ EnsureValidRegionIsCurrent()2160 void EnsureValidRegionIsCurrent() const { 2161 if (!mValidRegionIsCurrent) { 2162 // Apply any pending mInvalidRegion changes to mValidRegion. 2163 if (!mValidRegion.IsEmpty()) { 2164 // Calling mInvalidRegion.GetRegion() is expensive. 2165 // That's why we delay the adjustment of mValidRegion for as long as 2166 // possible, so that multiple modifications to mInvalidRegion can be 2167 // applied to mValidRegion in one go. 2168 mValidRegion.SubOut(mInvalidRegion.GetRegion()); 2169 } 2170 mValidRegionIsCurrent = true; 2171 } 2172 } 2173 2174 /** 2175 * The layer's valid region. If mValidRegionIsCurrent is false, then 2176 * mValidRegion has not yet been updated for recent changes to 2177 * mInvalidRegion. Those pending changes can be applied by calling 2178 * EnsureValidRegionIsCurrent(). 2179 */ 2180 mutable nsIntRegion mValidRegion; 2181 2182 mutable bool mValidRegionIsCurrent; 2183 2184 protected: 2185 /** 2186 * The creation hint that was used when constructing this layer. 2187 */ 2188 const LayerManager::PaintedLayerCreationHint mCreationHint; 2189 /** 2190 * Set when this PaintedLayer is participating in readback, i.e. some 2191 * ReadbackLayer (may) be getting its background from this layer. 2192 */ 2193 bool mUsedForReadback; 2194 /** 2195 * True when 2196 */ 2197 bool mAllowResidualTranslation; 2198 }; 2199 2200 /** 2201 * A Layer which other layers render into. It holds references to its 2202 * children. 2203 */ 2204 class ContainerLayer : public Layer { 2205 public: 2206 ~ContainerLayer(); 2207 2208 /** 2209 * CONSTRUCTION PHASE ONLY 2210 * Insert aChild into the child list of this container. aChild must 2211 * not be currently in any child list or the root for the layer manager. 2212 * If aAfter is non-null, it must be a child of this container and 2213 * we insert after that layer. If it's null we insert at the start. 2214 */ 2215 virtual bool InsertAfter(Layer* aChild, Layer* aAfter); 2216 /** 2217 * CONSTRUCTION PHASE ONLY 2218 * Remove aChild from the child list of this container. aChild must 2219 * be a child of this container. 2220 */ 2221 virtual bool RemoveChild(Layer* aChild); 2222 /** 2223 * CONSTRUCTION PHASE ONLY 2224 * Reposition aChild from the child list of this container. aChild must 2225 * be a child of this container. 2226 * If aAfter is non-null, it must be a child of this container and we 2227 * reposition after that layer. If it's null, we reposition at the start. 2228 */ 2229 virtual bool RepositionChild(Layer* aChild, Layer* aAfter); 2230 SetPreScale(float aXScale,float aYScale)2231 void SetPreScale(float aXScale, float aYScale) { 2232 if (mPreXScale == aXScale && mPreYScale == aYScale) { 2233 return; 2234 } 2235 2236 MOZ_LAYERS_LOG_IF_SHADOWABLE(this, ("Layer::Mutated(%p) PreScale", this)); 2237 mPreXScale = aXScale; 2238 mPreYScale = aYScale; 2239 Mutated(); 2240 } 2241 SetInheritedScale(float aXScale,float aYScale)2242 void SetInheritedScale(float aXScale, float aYScale) { 2243 if (mInheritedXScale == aXScale && mInheritedYScale == aYScale) { 2244 return; 2245 } 2246 2247 MOZ_LAYERS_LOG_IF_SHADOWABLE(this, 2248 ("Layer::Mutated(%p) InheritedScale", this)); 2249 mInheritedXScale = aXScale; 2250 mInheritedYScale = aYScale; 2251 Mutated(); 2252 } 2253 SetScaleToResolution(bool aScaleToResolution,float aResolution)2254 void SetScaleToResolution(bool aScaleToResolution, float aResolution) { 2255 if (mScaleToResolution == aScaleToResolution && 2256 mPresShellResolution == aResolution) { 2257 return; 2258 } 2259 2260 MOZ_LAYERS_LOG_IF_SHADOWABLE( 2261 this, ("Layer::Mutated(%p) ScaleToResolution", this)); 2262 mScaleToResolution = aScaleToResolution; 2263 mPresShellResolution = aResolution; 2264 Mutated(); 2265 } 2266 2267 virtual void FillSpecificAttributes(SpecificLayerAttributes& aAttrs) override; 2268 2269 enum class SortMode { 2270 WITH_GEOMETRY, 2271 WITHOUT_GEOMETRY, 2272 }; 2273 2274 nsTArray<LayerPolygon> SortChildrenBy3DZOrder(SortMode aSortMode); 2275 AsContainerLayer()2276 virtual ContainerLayer* AsContainerLayer() override { return this; } AsContainerLayer()2277 virtual const ContainerLayer* AsContainerLayer() const override { 2278 return this; 2279 } 2280 2281 // These getters can be used anytime. GetFirstChild()2282 virtual Layer* GetFirstChild() const override { return mFirstChild; } GetLastChild()2283 virtual Layer* GetLastChild() const override { return mLastChild; } GetPreXScale()2284 float GetPreXScale() const { return mPreXScale; } GetPreYScale()2285 float GetPreYScale() const { return mPreYScale; } GetInheritedXScale()2286 float GetInheritedXScale() const { return mInheritedXScale; } GetInheritedYScale()2287 float GetInheritedYScale() const { return mInheritedYScale; } GetPresShellResolution()2288 float GetPresShellResolution() const { return mPresShellResolution; } ScaleToResolution()2289 bool ScaleToResolution() const { return mScaleToResolution; } 2290 2291 MOZ_LAYER_DECL_NAME("ContainerLayer", TYPE_CONTAINER) 2292 2293 /** 2294 * ContainerLayer backends need to override ComputeEffectiveTransforms 2295 * since the decision about whether to use a temporary surface for the 2296 * container is backend-specific. ComputeEffectiveTransforms must also set 2297 * mUseIntermediateSurface. 2298 */ 2299 virtual void ComputeEffectiveTransforms( 2300 const gfx::Matrix4x4& aTransformToSurface) override = 0; 2301 2302 /** 2303 * Call this only after ComputeEffectiveTransforms has been invoked 2304 * on this layer. 2305 * Returns true if this will use an intermediate surface. This is largely 2306 * backend-dependent, but it affects the operation of GetEffectiveOpacity(). 2307 */ UseIntermediateSurface()2308 bool UseIntermediateSurface() { return mUseIntermediateSurface; } 2309 2310 /** 2311 * Returns the rectangle covered by the intermediate surface, 2312 * in this layer's coordinate system. 2313 * 2314 * NOTE: Since this layer has an intermediate surface it follows 2315 * that LayerPixel == RenderTargetPixel 2316 */ GetIntermediateSurfaceRect()2317 RenderTargetIntRect GetIntermediateSurfaceRect() { 2318 NS_ASSERTION(mUseIntermediateSurface, "Must have intermediate surface"); 2319 return RenderTargetIntRect::FromUnknownRect( 2320 GetLocalVisibleRegion().ToUnknownRegion().GetBounds()); 2321 } 2322 2323 /** 2324 * Returns true if this container has more than one non-empty child 2325 */ 2326 bool HasMultipleChildren(); 2327 2328 /** 2329 * Returns true if this container supports children with component alpha. 2330 * Should only be called while painting a child of this layer. 2331 */ SupportsComponentAlphaChildren()2332 bool SupportsComponentAlphaChildren() { 2333 return mSupportsComponentAlphaChildren; 2334 } 2335 2336 /** 2337 * Returns true if aLayer or any layer in its parent chain has the opaque 2338 * content flag set. 2339 */ 2340 static bool HasOpaqueAncestorLayer(Layer* aLayer); 2341 SetChildrenChanged(bool aVal)2342 void SetChildrenChanged(bool aVal) { mChildrenChanged = aVal; } 2343 2344 // If |aRect| is null, the entire layer should be considered invalid for 2345 // compositing. SetInvalidCompositeRect(const gfx::IntRect * aRect)2346 virtual void SetInvalidCompositeRect(const gfx::IntRect* aRect) {} 2347 2348 protected: 2349 friend class ReadbackProcessor; 2350 2351 // Note that this is not virtual, and is based on the implementation of 2352 // ContainerLayer::RemoveChild, so it should only be called where you would 2353 // want to explicitly call the base class implementation of RemoveChild; 2354 // e.g., while (mFirstChild) ContainerLayer::RemoveChild(mFirstChild); 2355 void RemoveAllChildren(); 2356 2357 void DidInsertChild(Layer* aLayer); 2358 void DidRemoveChild(Layer* aLayer); 2359 2360 bool AnyAncestorOrThisIs3DContextLeaf(); 2361 2362 void Collect3DContextLeaves(nsTArray<Layer*>& aToSort); 2363 2364 // Collects child layers that do not extend 3D context. For ContainerLayers 2365 // that do extend 3D context, the 3D context leaves are collected. CollectChildren()2366 nsTArray<Layer*> CollectChildren() { 2367 nsTArray<Layer*> children; 2368 2369 for (Layer* layer = GetFirstChild(); layer; 2370 layer = layer->GetNextSibling()) { 2371 ContainerLayer* container = layer->AsContainerLayer(); 2372 2373 if (container && container->Extend3DContext() && 2374 !container->UseIntermediateSurface()) { 2375 container->Collect3DContextLeaves(children); 2376 } else { 2377 children.AppendElement(layer); 2378 } 2379 } 2380 2381 return children; 2382 } 2383 2384 ContainerLayer(LayerManager* aManager, void* aImplData); 2385 2386 /** 2387 * A default implementation of ComputeEffectiveTransforms for use by OpenGL 2388 * and D3D. 2389 */ 2390 void DefaultComputeEffectiveTransforms( 2391 const gfx::Matrix4x4& aTransformToSurface); 2392 2393 /** 2394 * A default implementation to compute and set the value for 2395 * SupportsComponentAlphaChildren(). 2396 * 2397 * If aNeedsSurfaceCopy is provided, then it is set to true if the caller 2398 * needs to copy the background up into the intermediate surface created, 2399 * false otherwise. 2400 */ 2401 void DefaultComputeSupportsComponentAlphaChildren( 2402 bool* aNeedsSurfaceCopy = nullptr); 2403 2404 /** 2405 * Loops over the children calling ComputeEffectiveTransforms on them. 2406 */ 2407 void ComputeEffectiveTransformsForChildren( 2408 const gfx::Matrix4x4& aTransformToSurface); 2409 2410 virtual void PrintInfo(std::stringstream& aStream, 2411 const char* aPrefix) override; 2412 2413 virtual void DumpPacket(layerscope::LayersPacket* aPacket, 2414 const void* aParent) override; 2415 2416 /** 2417 * True for if the container start a new 3D context extended by one 2418 * or more children. 2419 */ 2420 bool Creates3DContextWithExtendingChildren(); 2421 2422 Layer* mFirstChild; 2423 Layer* mLastChild; 2424 float mPreXScale; 2425 float mPreYScale; 2426 // The resolution scale inherited from the parent layer. This will already 2427 // be part of mTransform. 2428 float mInheritedXScale; 2429 float mInheritedYScale; 2430 // For layers corresponding to an nsDisplayResolution, the resolution of the 2431 // associated pres shell; for other layers, 1.0. 2432 float mPresShellResolution; 2433 // Whether the compositor should scale to mPresShellResolution. 2434 bool mScaleToResolution; 2435 bool mUseIntermediateSurface; 2436 bool mSupportsComponentAlphaChildren; 2437 bool mMayHaveReadbackChild; 2438 // This is updated by ComputeDifferences. This will be true if we need to 2439 // invalidate the intermediate surface. 2440 bool mChildrenChanged; 2441 }; 2442 2443 /** 2444 * A generic layer that references back to its display item. 2445 * 2446 * In order to not throw away information early in the pipeline from layout -> 2447 * webrender, we'd like a generic layer type that can represent all the 2448 * nsDisplayItems instead of creating a new layer type for each nsDisplayItem 2449 * for Webrender. Another option is to break down nsDisplayItems into smaller 2450 * nsDisplayItems early in the pipeline. The problem with this is that the whole 2451 * pipeline would have to deal with more display items, which is slower. 2452 * 2453 * An alternative is to create a DisplayItemLayer, but the wrinkle with this is 2454 * that it has a pointer to its nsDisplayItem. Managing the lifetime is key as 2455 * display items only live as long as their display list builder, which goes 2456 * away at the end of a paint. Layers however, are retained between paints. It's 2457 * ok to recycle a DisplayItemLayer for a different display item since its just 2458 * a pointer. Instead, when a layer transaction is completed, it is up to the 2459 * layer manager to tell DisplayItemLayers that the display item pointer is no 2460 * longer valid. 2461 */ 2462 class DisplayItemLayer : public Layer { 2463 public: AsDisplayItemLayer()2464 virtual DisplayItemLayer* AsDisplayItemLayer() override { return this; } 2465 void EndTransaction(); 2466 2467 MOZ_LAYER_DECL_NAME("DisplayItemLayer", TYPE_DISPLAYITEM) 2468 SetDisplayItem(nsDisplayItem * aItem,nsDisplayListBuilder * aBuilder)2469 void SetDisplayItem(nsDisplayItem* aItem, nsDisplayListBuilder* aBuilder) { 2470 mItem = aItem; 2471 mBuilder = aBuilder; 2472 } 2473 GetDisplayItem()2474 nsDisplayItem* GetDisplayItem() { return mItem; } GetDisplayListBuilder()2475 nsDisplayListBuilder* GetDisplayListBuilder() { return mBuilder; } 2476 ComputeEffectiveTransforms(const gfx::Matrix4x4 & aTransformToSurface)2477 virtual void ComputeEffectiveTransforms( 2478 const gfx::Matrix4x4& aTransformToSurface) override { 2479 gfx::Matrix4x4 idealTransform = GetLocalTransform() * aTransformToSurface; 2480 mEffectiveTransform = SnapTransformTranslation(idealTransform, nullptr); 2481 ComputeEffectiveTransformForMaskLayers(aTransformToSurface); 2482 } 2483 2484 protected: DisplayItemLayer(LayerManager * aManager,void * aImplData)2485 DisplayItemLayer(LayerManager* aManager, void* aImplData) 2486 : Layer(aManager, aImplData), mItem(nullptr) {} 2487 2488 virtual void PrintInfo(std::stringstream& aStream, 2489 const char* aPrefix) override; 2490 2491 virtual void DumpPacket(layerscope::LayersPacket* aPacket, 2492 const void* aParent) override; 2493 2494 // READ COMMENT ABOVE TO ENSURE WE DON'T HAVE A DANGLING POINTER 2495 nsDisplayItem* mItem; 2496 nsDisplayListBuilder* mBuilder; 2497 }; 2498 2499 /** 2500 * A Layer which just renders a solid color in its visible region. It actually 2501 * can fill any area that contains the visible region, so if you need to 2502 * restrict the area filled, set a clip region on this layer. 2503 */ 2504 class ColorLayer : public Layer { 2505 public: AsColorLayer()2506 virtual ColorLayer* AsColorLayer() override { return this; } 2507 2508 /** 2509 * CONSTRUCTION PHASE ONLY 2510 * Set the color of the layer. 2511 */ SetColor(const gfx::Color & aColor)2512 virtual void SetColor(const gfx::Color& aColor) { 2513 if (mColor != aColor) { 2514 MOZ_LAYERS_LOG_IF_SHADOWABLE(this, ("Layer::Mutated(%p) Color", this)); 2515 mColor = aColor; 2516 Mutated(); 2517 } 2518 } 2519 SetBounds(const gfx::IntRect & aBounds)2520 void SetBounds(const gfx::IntRect& aBounds) { 2521 if (!mBounds.IsEqualEdges(aBounds)) { 2522 mBounds = aBounds; 2523 Mutated(); 2524 } 2525 } 2526 GetBounds()2527 const gfx::IntRect& GetBounds() { return mBounds; } 2528 2529 // This getter can be used anytime. GetColor()2530 virtual const gfx::Color& GetColor() { return mColor; } 2531 2532 MOZ_LAYER_DECL_NAME("ColorLayer", TYPE_COLOR) 2533 ComputeEffectiveTransforms(const gfx::Matrix4x4 & aTransformToSurface)2534 virtual void ComputeEffectiveTransforms( 2535 const gfx::Matrix4x4& aTransformToSurface) override { 2536 gfx::Matrix4x4 idealTransform = GetLocalTransform() * aTransformToSurface; 2537 mEffectiveTransform = SnapTransformTranslation(idealTransform, nullptr); 2538 ComputeEffectiveTransformForMaskLayers(aTransformToSurface); 2539 } 2540 2541 protected: ColorLayer(LayerManager * aManager,void * aImplData)2542 ColorLayer(LayerManager* aManager, void* aImplData) 2543 : Layer(aManager, aImplData), mColor() {} 2544 2545 virtual void PrintInfo(std::stringstream& aStream, 2546 const char* aPrefix) override; 2547 2548 virtual void DumpPacket(layerscope::LayersPacket* aPacket, 2549 const void* aParent) override; 2550 2551 gfx::IntRect mBounds; 2552 gfx::Color mColor; 2553 }; 2554 2555 /** 2556 * A Layer which renders a rounded rect. 2557 */ 2558 class BorderLayer : public Layer { 2559 public: AsBorderLayer()2560 virtual BorderLayer* AsBorderLayer() override { return this; } 2561 2562 /** 2563 * CONSTRUCTION PHASE ONLY 2564 * Set the color of the layer. 2565 */ 2566 2567 // Colors of each side as in css::Side SetColors(const BorderColors & aColors)2568 virtual void SetColors(const BorderColors& aColors) { 2569 MOZ_LAYERS_LOG_IF_SHADOWABLE(this, ("Layer::Mutated(%p) Colors", this)); 2570 PodCopy(&mColors[0], &aColors[0], 4); 2571 Mutated(); 2572 } 2573 SetRect(const LayerRect & aRect)2574 virtual void SetRect(const LayerRect& aRect) { 2575 MOZ_LAYERS_LOG_IF_SHADOWABLE(this, ("Layer::Mutated(%p) Rect", this)); 2576 mRect = aRect; 2577 Mutated(); 2578 } 2579 2580 // Size of each rounded corner as in css::Corner, 0.0 means a 2581 // rectangular corner. SetCornerRadii(const BorderCorners & aCorners)2582 virtual void SetCornerRadii(const BorderCorners& aCorners) { 2583 MOZ_LAYERS_LOG_IF_SHADOWABLE(this, ("Layer::Mutated(%p) Corners", this)); 2584 PodCopy(&mCorners[0], &aCorners[0], 4); 2585 Mutated(); 2586 } 2587 SetWidths(const BorderWidths & aWidths)2588 virtual void SetWidths(const BorderWidths& aWidths) { 2589 MOZ_LAYERS_LOG_IF_SHADOWABLE(this, ("Layer::Mutated(%p) Widths", this)); 2590 PodCopy(&mWidths[0], &aWidths[0], 4); 2591 Mutated(); 2592 } 2593 SetStyles(const BorderStyles & aBorderStyles)2594 virtual void SetStyles(const BorderStyles& aBorderStyles) { 2595 MOZ_LAYERS_LOG_IF_SHADOWABLE(this, ("Layer::Mutated(%p) Widths", this)); 2596 PodCopy(&mBorderStyles[0], &aBorderStyles[0], 4); 2597 Mutated(); 2598 } 2599 2600 MOZ_LAYER_DECL_NAME("BorderLayer", TYPE_BORDER) 2601 ComputeEffectiveTransforms(const gfx::Matrix4x4 & aTransformToSurface)2602 virtual void ComputeEffectiveTransforms( 2603 const gfx::Matrix4x4& aTransformToSurface) override { 2604 gfx::Matrix4x4 idealTransform = GetLocalTransform() * aTransformToSurface; 2605 mEffectiveTransform = SnapTransformTranslation(idealTransform, nullptr); 2606 ComputeEffectiveTransformForMaskLayers(aTransformToSurface); 2607 } 2608 GetColors()2609 const BorderColors& GetColors() { return mColors; } GetRect()2610 const LayerRect& GetRect() { return mRect; } GetCorners()2611 const BorderCorners& GetCorners() { return mCorners; } GetWidths()2612 const BorderWidths& GetWidths() { return mWidths; } 2613 2614 protected: BorderLayer(LayerManager * aManager,void * aImplData)2615 BorderLayer(LayerManager* aManager, void* aImplData) 2616 : Layer(aManager, aImplData) {} 2617 2618 virtual void PrintInfo(std::stringstream& aStream, 2619 const char* aPrefix) override; 2620 2621 virtual void DumpPacket(layerscope::LayersPacket* aPacket, 2622 const void* aParent) override; 2623 2624 BorderColors mColors; 2625 LayerRect mRect; 2626 BorderCorners mCorners; 2627 BorderWidths mWidths; 2628 BorderStyles mBorderStyles; 2629 }; 2630 2631 /** 2632 * A Layer for HTML Canvas elements. It's backed by either a 2633 * gfxASurface or a GLContext (for WebGL layers), and has some control 2634 * for intelligent updating from the source if necessary (for example, 2635 * if hardware compositing is not available, for reading from the GL 2636 * buffer into an image surface that we can layer composite.) 2637 * 2638 * After Initialize is called, the underlying canvas Surface/GLContext 2639 * must not be modified during a layer transaction. 2640 */ 2641 class CanvasLayer : public Layer { 2642 public: SetBounds(gfx::IntRect aBounds)2643 void SetBounds(gfx::IntRect aBounds) { mBounds = aBounds; } 2644 AsCanvasLayer()2645 virtual CanvasLayer* AsCanvasLayer() override { return this; } 2646 2647 /** 2648 * Notify this CanvasLayer that the canvas surface contents have 2649 * changed (or will change) before the next transaction. 2650 */ Updated()2651 void Updated() { 2652 mCanvasRenderer->SetDirty(); 2653 SetInvalidRectToVisibleRegion(); 2654 } 2655 2656 /** 2657 * Notify this CanvasLayer that the canvas surface contents have 2658 * been painted since the last change. 2659 */ Painted()2660 void Painted() { mCanvasRenderer->ResetDirty(); } 2661 2662 /** 2663 * Returns true if the canvas surface contents have changed since the 2664 * last paint. 2665 */ IsDirty()2666 bool IsDirty() { 2667 // We can only tell if we are dirty if we're part of the 2668 // widget's retained layer tree. 2669 if (!mManager || !mManager->IsWidgetLayerManager()) { 2670 return true; 2671 } 2672 return mCanvasRenderer->IsDirty(); 2673 } 2674 GetBounds()2675 const nsIntRect& GetBounds() const { return mBounds; } 2676 2677 CanvasRenderer* CreateOrGetCanvasRenderer(); 2678 2679 public: 2680 /** 2681 * CONSTRUCTION PHASE ONLY 2682 * Set the filter used to resample this image (if necessary). 2683 */ SetSamplingFilter(gfx::SamplingFilter aSamplingFilter)2684 void SetSamplingFilter(gfx::SamplingFilter aSamplingFilter) { 2685 if (mSamplingFilter != aSamplingFilter) { 2686 MOZ_LAYERS_LOG_IF_SHADOWABLE(this, ("Layer::Mutated(%p) Filter", this)); 2687 mSamplingFilter = aSamplingFilter; 2688 Mutated(); 2689 } 2690 } GetSamplingFilter()2691 gfx::SamplingFilter GetSamplingFilter() const { return mSamplingFilter; } 2692 2693 MOZ_LAYER_DECL_NAME("CanvasLayer", TYPE_CANVAS) 2694 ComputeEffectiveTransforms(const gfx::Matrix4x4 & aTransformToSurface)2695 virtual void ComputeEffectiveTransforms( 2696 const gfx::Matrix4x4& aTransformToSurface) override { 2697 // Snap our local transform first, and snap the inherited transform as well. 2698 // This makes our snapping equivalent to what would happen if our content 2699 // was drawn into a PaintedLayer (gfxContext would snap using the local 2700 // transform, then we'd snap again when compositing the PaintedLayer). 2701 mEffectiveTransform = 2702 SnapTransform(GetLocalTransform(), 2703 gfxRect(0, 0, mBounds.Width(), mBounds.Height()), 2704 nullptr) * 2705 SnapTransformTranslation(aTransformToSurface, nullptr); 2706 ComputeEffectiveTransformForMaskLayers(aTransformToSurface); 2707 } 2708 2709 protected: 2710 CanvasLayer(LayerManager* aManager, void* aImplData); 2711 virtual ~CanvasLayer(); 2712 2713 virtual void PrintInfo(std::stringstream& aStream, 2714 const char* aPrefix) override; 2715 2716 virtual void DumpPacket(layerscope::LayersPacket* aPacket, 2717 const void* aParent) override; 2718 2719 virtual CanvasRenderer* CreateCanvasRendererInternal() = 0; 2720 2721 UniquePtr<CanvasRenderer> mCanvasRenderer; 2722 gfx::SamplingFilter mSamplingFilter; 2723 2724 /** 2725 * 0, 0, canvaswidth, canvasheight 2726 */ 2727 gfx::IntRect mBounds; 2728 }; 2729 2730 /** 2731 * ContainerLayer that refers to a "foreign" layer tree, through an 2732 * ID. Usage of RefLayer looks like 2733 * 2734 * Construction phase: 2735 * allocate ID for layer subtree 2736 * create RefLayer, SetReferentId(ID) 2737 * 2738 * Composition: 2739 * look up subtree for GetReferentId() 2740 * ConnectReferentLayer(subtree) 2741 * compose 2742 * ClearReferentLayer() 2743 * 2744 * Clients will usually want to Connect/Clear() on each transaction to 2745 * avoid difficulties managing memory across multiple layer subtrees. 2746 */ 2747 class RefLayer : public ContainerLayer { 2748 friend class LayerManager; 2749 2750 private: InsertAfter(Layer * aChild,Layer * aAfter)2751 virtual bool InsertAfter(Layer* aChild, Layer* aAfter) override { 2752 MOZ_CRASH("GFX: RefLayer"); 2753 return false; 2754 } 2755 RemoveChild(Layer * aChild)2756 virtual bool RemoveChild(Layer* aChild) override { 2757 MOZ_CRASH("GFX: RefLayer"); 2758 return false; 2759 } 2760 RepositionChild(Layer * aChild,Layer * aAfter)2761 virtual bool RepositionChild(Layer* aChild, Layer* aAfter) override { 2762 MOZ_CRASH("GFX: RefLayer"); 2763 return false; 2764 } 2765 2766 public: 2767 /** 2768 * CONSTRUCTION PHASE ONLY 2769 * Set the ID of the layer's referent. 2770 */ SetReferentId(uint64_t aId)2771 void SetReferentId(uint64_t aId) { 2772 MOZ_ASSERT(aId != 0); 2773 if (mId != aId) { 2774 MOZ_LAYERS_LOG_IF_SHADOWABLE(this, 2775 ("Layer::Mutated(%p) ReferentId", this)); 2776 mId = aId; 2777 Mutated(); 2778 } 2779 } 2780 /** 2781 * CONSTRUCTION PHASE ONLY 2782 * Connect this ref layer to its referent, temporarily. 2783 * ClearReferentLayer() must be called after composition. 2784 */ ConnectReferentLayer(Layer * aLayer)2785 void ConnectReferentLayer(Layer* aLayer) { 2786 MOZ_ASSERT(!mFirstChild && !mLastChild); 2787 MOZ_ASSERT(!aLayer->GetParent()); 2788 if (aLayer->Manager() != Manager()) { 2789 // This can happen when e.g. rendering while dragging tabs 2790 // between windows - aLayer's manager may be the manager for the 2791 // old window's tab. In that case, it will be changed before the 2792 // next render (see SetLayerManager). It is simply easier to 2793 // ignore the rendering here than it is to pause it. 2794 NS_WARNING("ConnectReferentLayer failed - Incorrect LayerManager"); 2795 return; 2796 } 2797 2798 mFirstChild = mLastChild = aLayer; 2799 aLayer->SetParent(this); 2800 } 2801 2802 /** 2803 * CONSTRUCTION PHASE ONLY 2804 * Set flags that indicate how event regions in the child layer tree need 2805 * to be overridden because of properties of the parent layer tree. 2806 */ SetEventRegionsOverride(EventRegionsOverride aVal)2807 void SetEventRegionsOverride(EventRegionsOverride aVal) { 2808 if (mEventRegionsOverride == aVal) { 2809 return; 2810 } 2811 2812 MOZ_LAYERS_LOG_IF_SHADOWABLE( 2813 this, ("Layer::Mutated(%p) EventRegionsOverride", this)); 2814 mEventRegionsOverride = aVal; 2815 Mutated(); 2816 } 2817 GetEventRegionsOverride()2818 EventRegionsOverride GetEventRegionsOverride() const { 2819 return mEventRegionsOverride; 2820 } 2821 2822 /** 2823 * DRAWING PHASE ONLY 2824 * |aLayer| is the same as the argument to ConnectReferentLayer(). 2825 */ DetachReferentLayer(Layer * aLayer)2826 void DetachReferentLayer(Layer* aLayer) { 2827 mFirstChild = mLastChild = nullptr; 2828 aLayer->SetParent(nullptr); 2829 } 2830 2831 // These getters can be used anytime. AsRefLayer()2832 virtual RefLayer* AsRefLayer() override { return this; } 2833 GetReferentId()2834 virtual uint64_t GetReferentId() { return mId; } 2835 2836 /** 2837 * DRAWING PHASE ONLY 2838 */ 2839 virtual void FillSpecificAttributes(SpecificLayerAttributes& aAttrs) override; 2840 2841 MOZ_LAYER_DECL_NAME("RefLayer", TYPE_REF) 2842 2843 protected: RefLayer(LayerManager * aManager,void * aImplData)2844 RefLayer(LayerManager* aManager, void* aImplData) 2845 : ContainerLayer(aManager, aImplData), 2846 mId(0), 2847 mEventRegionsOverride(EventRegionsOverride::NoOverride) {} 2848 2849 virtual void PrintInfo(std::stringstream& aStream, 2850 const char* aPrefix) override; 2851 2852 virtual void DumpPacket(layerscope::LayersPacket* aPacket, 2853 const void* aParent) override; 2854 2855 // 0 is a special value that means "no ID". 2856 uint64_t mId; 2857 EventRegionsOverride mEventRegionsOverride; 2858 }; 2859 2860 void SetAntialiasingFlags(Layer* aLayer, gfx::DrawTarget* aTarget); 2861 2862 #ifdef MOZ_DUMP_PAINTING 2863 void WriteSnapshotToDumpFile(Layer* aLayer, gfx::DataSourceSurface* aSurf); 2864 void WriteSnapshotToDumpFile(LayerManager* aManager, 2865 gfx::DataSourceSurface* aSurf); 2866 void WriteSnapshotToDumpFile(Compositor* aCompositor, gfx::DrawTarget* aTarget); 2867 #endif 2868 2869 // A utility function used by different LayerManager implementations. 2870 gfx::IntRect ToOutsideIntRect(const gfxRect& aRect); 2871 2872 } // namespace layers 2873 } // namespace mozilla 2874 2875 #endif /* GFX_LAYERS_H */ 2876