1 /* 2 * Copyright (C) 2009 Apple Inc. All rights reserved. 3 * 4 * Redistribution and use in source and binary forms, with or without 5 * modification, are permitted provided that the following conditions 6 * are met: 7 * 1. Redistributions of source code must retain the above copyright 8 * notice, this list of conditions and the following disclaimer. 9 * 2. Redistributions in binary form must reproduce the above copyright 10 * notice, this list of conditions and the following disclaimer in the 11 * documentation and/or other materials provided with the distribution. 12 * 13 * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY 14 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 15 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 16 * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE COMPUTER, INC. OR 17 * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, 18 * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, 19 * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR 20 * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY 21 * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 22 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 23 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 24 */ 25 26 #ifndef RenderLayerCompositor_h 27 #define RenderLayerCompositor_h 28 29 #include "core/page/ChromeClient.h" 30 #include "core/rendering/RenderLayer.h" 31 #include "core/rendering/compositing/CompositingReasonFinder.h" 32 #include "platform/graphics/GraphicsLayerClient.h" 33 #include "wtf/HashMap.h" 34 35 namespace WebCore { 36 37 class GraphicsLayer; 38 class RenderPart; 39 class ScrollingCoordinator; 40 41 enum CompositingUpdateType { 42 CompositingUpdateNone, 43 CompositingUpdateAfterGeometryChange, 44 CompositingUpdateAfterCompositingInputChange, 45 CompositingUpdateRebuildTree, 46 }; 47 48 enum CompositingStateTransitionType { 49 NoCompositingStateChange, 50 AllocateOwnCompositedLayerMapping, 51 RemoveOwnCompositedLayerMapping, 52 PutInSquashingLayer, 53 RemoveFromSquashingLayer 54 }; 55 56 // RenderLayerCompositor manages the hierarchy of 57 // composited RenderLayers. It determines which RenderLayers 58 // become compositing, and creates and maintains a hierarchy of 59 // GraphicsLayers based on the RenderLayer painting order. 60 // 61 // There is one RenderLayerCompositor per RenderView. 62 63 class RenderLayerCompositor FINAL : public GraphicsLayerClient { 64 WTF_MAKE_FAST_ALLOCATED; 65 public: 66 explicit RenderLayerCompositor(RenderView&); 67 virtual ~RenderLayerCompositor(); 68 69 void updateIfNeededRecursive(); 70 71 // Return true if this RenderView is in "compositing mode" (i.e. has one or more 72 // composited RenderLayers) 73 bool inCompositingMode() const; 74 // FIXME: Replace all callers with inCompositingMdoe and remove this function. 75 bool staleInCompositingMode() const; 76 // This will make a compositing layer at the root automatically, and hook up to 77 // the native view/window system. 78 void setCompositingModeEnabled(bool); 79 80 // Returns true if the accelerated compositing is enabled hasAcceleratedCompositing()81 bool hasAcceleratedCompositing() const { return m_hasAcceleratedCompositing; } 82 bool layerSquashingEnabled() const; 83 84 bool acceleratedCompositingForOverflowScrollEnabled() const; 85 86 bool rootShouldAlwaysComposite() const; 87 88 // Copy the accelerated compositing related flags from Settings 89 void updateAcceleratedCompositingSettings(); 90 91 // Used to indicate that a compositing update will be needed for the next frame that gets drawn. 92 void setNeedsCompositingUpdate(CompositingUpdateType); 93 94 void didLayout(); 95 96 enum UpdateLayerCompositingStateOptions { 97 Normal, 98 UseChickenEggHacks, // Use this to trigger temporary chicken-egg hacks. See crbug.com/339892. 99 }; 100 101 // Update the compositing dirty bits, based on the compositing-impacting properties of the layer. 102 void updateLayerCompositingState(RenderLayer*, UpdateLayerCompositingStateOptions = Normal); 103 104 // Returns whether this layer is clipped by another layer that is not an ancestor of the given layer in the stacking context hierarchy. 105 bool clippedByNonAncestorInStackingTree(const RenderLayer*) const; 106 // Whether layer's compositedLayerMapping needs a GraphicsLayer to clip z-order children of the given RenderLayer. 107 bool clipsCompositingDescendants(const RenderLayer*) const; 108 109 // Whether the given layer needs an extra 'contents' layer. 110 bool needsContentsCompositingLayer(const RenderLayer*) const; 111 112 bool supportsFixedRootBackgroundCompositing() const; 113 bool needsFixedRootBackgroundLayer(const RenderLayer*) const; 114 GraphicsLayer* fixedRootBackgroundLayer() const; setNeedsUpdateFixedBackground()115 void setNeedsUpdateFixedBackground() { m_needsUpdateFixedBackground = true; } 116 117 // Repaint the appropriate layers when the given RenderLayer starts or stops being composited. 118 void repaintOnCompositingChange(RenderLayer*); 119 120 void repaintInCompositedAncestor(RenderLayer*, const LayoutRect&); 121 void repaintCompositedLayers(); 122 123 RenderLayer* rootRenderLayer() const; 124 GraphicsLayer* rootGraphicsLayer() const; 125 GraphicsLayer* scrollLayer() const; 126 GraphicsLayer* containerLayer() const; 127 128 // We don't always have a root transform layer. This function lazily allocates one 129 // and returns it as required. 130 GraphicsLayer* ensureRootTransformLayer(); 131 132 enum RootLayerAttachment { 133 RootLayerUnattached, 134 RootLayerAttachedViaChromeClient, 135 RootLayerAttachedViaEnclosingFrame 136 }; 137 rootLayerAttachment()138 RootLayerAttachment rootLayerAttachment() const { return m_rootLayerAttachment; } 139 void updateRootLayerAttachment(); 140 void updateRootLayerPosition(); 141 142 void setIsInWindow(bool); 143 144 static RenderLayerCompositor* frameContentsCompositor(RenderPart*); 145 // Return true if the layers changed. 146 static bool parentFrameContentLayers(RenderPart*); 147 148 // Update the geometry of the layers used for clipping and scrolling in frames. 149 void frameViewDidChangeLocation(const IntPoint& contentsOffset); 150 void frameViewDidChangeSize(); 151 void frameViewDidScroll(); 152 void frameViewScrollbarsExistenceDidChange(); 153 void rootFixedBackgroundsChanged(); 154 155 bool scrollingLayerDidChange(RenderLayer*); 156 157 String layerTreeAsText(LayerTreeFlags); 158 layerForHorizontalScrollbar()159 GraphicsLayer* layerForHorizontalScrollbar() const { return m_layerForHorizontalScrollbar.get(); } layerForVerticalScrollbar()160 GraphicsLayer* layerForVerticalScrollbar() const { return m_layerForVerticalScrollbar.get(); } layerForScrollCorner()161 GraphicsLayer* layerForScrollCorner() const { return m_layerForScrollCorner.get(); } 162 163 void resetTrackedRepaintRects(); 164 void setTracksRepaints(bool); 165 166 virtual String debugName(const GraphicsLayer*) OVERRIDE; 167 168 void updateStyleDeterminedCompositingReasons(RenderLayer*); 169 170 // Whether the layer could ever be composited. 171 bool canBeComposited(const RenderLayer*) const; 172 173 // FIXME: Move allocateOrClearCompositedLayerMapping to CompositingLayerAssigner once we've fixed 174 // the compositing chicken/egg issues. 175 bool allocateOrClearCompositedLayerMapping(RenderLayer*, CompositingStateTransitionType compositedLayerUpdate); 176 177 void updateDirectCompositingReasons(RenderLayer*); 178 179 void setOverlayLayer(GraphicsLayer*); 180 inOverlayFullscreenVideo()181 bool inOverlayFullscreenVideo() const { return m_inOverlayFullscreenVideo; } 182 183 private: 184 class OverlapMap; 185 186 #if ASSERT_ENABLED 187 void assertNoUnresolvedDirtyBits(); 188 #endif 189 190 // Make updates to the layer based on viewport-constrained properties such as position:fixed. This can in turn affect 191 // compositing. 192 bool updateLayerIfViewportConstrained(RenderLayer*); 193 194 // GraphicsLayerClient implementation notifyAnimationStarted(const GraphicsLayer *,double)195 virtual void notifyAnimationStarted(const GraphicsLayer*, double) OVERRIDE { } 196 virtual void paintContents(const GraphicsLayer*, GraphicsContext&, GraphicsLayerPaintingPhase, const IntRect&) OVERRIDE; 197 198 virtual bool isTrackingRepaints() const OVERRIDE; 199 200 // Whether the given RL needs to paint into its own separate backing (and hence would need its own CompositedLayerMapping). 201 bool needsOwnBacking(const RenderLayer*) const; 202 203 void updateIfNeeded(); 204 205 void recursiveRepaintLayer(RenderLayer*); 206 207 void computeCompositingRequirements(RenderLayer* ancestorLayer, RenderLayer*, OverlapMap&, struct CompositingRecursionData&, bool& descendantHas3DTransform, Vector<RenderLayer*>& unclippedDescendants, IntRect& absoluteDecendantBoundingBox); 208 209 bool hasAnyAdditionalCompositedLayers(const RenderLayer* rootLayer) const; 210 211 void ensureRootLayer(); 212 void destroyRootLayer(); 213 214 void attachRootLayer(RootLayerAttachment); 215 void detachRootLayer(); 216 217 void updateOverflowControlsLayers(); 218 219 Page* page() const; 220 221 GraphicsLayerFactory* graphicsLayerFactory() const; 222 ScrollingCoordinator* scrollingCoordinator() const; 223 224 void enableCompositingModeIfNeeded(); 225 226 bool requiresHorizontalScrollbarLayer() const; 227 bool requiresVerticalScrollbarLayer() const; 228 bool requiresScrollCornerLayer() const; 229 230 void applyUpdateLayerCompositingStateChickenEggHacks(RenderLayer*, CompositingStateTransitionType compositedLayerUpdate); 231 232 DocumentLifecycle& lifecycle() const; 233 234 void applyOverlayFullscreenVideoAdjustment(); 235 236 RenderView& m_renderView; 237 OwnPtr<GraphicsLayer> m_rootContentLayer; 238 OwnPtr<GraphicsLayer> m_rootTransformLayer; 239 240 CompositingReasonFinder m_compositingReasonFinder; 241 242 CompositingUpdateType m_pendingUpdateType; 243 244 bool m_hasAcceleratedCompositing; 245 bool m_compositing; 246 247 // The root layer doesn't composite if it's a non-scrollable frame. 248 // So, after a layout we set this dirty bit to know that we need 249 // to recompute whether the root layer should composite even if 250 // none of its descendants composite. 251 // FIXME: Get rid of all the callers of setCompositingModeEnabled 252 // except the one in updateIfNeeded, then rename this to 253 // m_compositingDirty. 254 bool m_rootShouldAlwaysCompositeDirty; 255 bool m_needsUpdateFixedBackground; 256 bool m_isTrackingRepaints; // Used for testing. 257 258 RootLayerAttachment m_rootLayerAttachment; 259 260 // Enclosing container layer, which clips for iframe content 261 OwnPtr<GraphicsLayer> m_containerLayer; 262 OwnPtr<GraphicsLayer> m_scrollLayer; 263 264 // Enclosing layer for overflow controls and the clipping layer 265 OwnPtr<GraphicsLayer> m_overflowControlsHostLayer; 266 267 // Layers for overflow controls 268 OwnPtr<GraphicsLayer> m_layerForHorizontalScrollbar; 269 OwnPtr<GraphicsLayer> m_layerForVerticalScrollbar; 270 OwnPtr<GraphicsLayer> m_layerForScrollCorner; 271 #if USE(RUBBER_BANDING) 272 OwnPtr<GraphicsLayer> m_layerForOverhangShadow; 273 #endif 274 275 bool m_inOverlayFullscreenVideo; 276 }; 277 278 } // namespace WebCore 279 280 #endif // RenderLayerCompositor_h 281