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 WKCACFLayer_h 27 #define WKCACFLayer_h 28 29 #if USE(ACCELERATED_COMPOSITING) 30 31 #include "StringHash.h" 32 33 #include <wtf/RefCounted.h> 34 35 #include <QuartzCore/CACFLayer.h> 36 #include <QuartzCore/CACFVector.h> 37 #include <wtf/PassRefPtr.h> 38 #include <wtf/RetainPtr.h> 39 #include <wtf/Vector.h> 40 41 #include "GraphicsContext.h" 42 #include "GraphicsLayerCACF.h" 43 #include "PlatformString.h" 44 #include "TransformationMatrix.h" 45 46 namespace WebCore { 47 48 class WKCACFAnimation; 49 class WKCACFTimingFunction; 50 51 class WKCACFLayer : public RefCounted<WKCACFLayer> { 52 public: 53 enum LayerType { Layer, TransformLayer }; 54 enum FilterType { Linear, Nearest, Trilinear, Lanczos }; 55 enum ContentsGravityType { Center, Top, Bottom, Left, Right, TopLeft, TopRight, 56 BottomLeft, BottomRight, Resize, ResizeAspect, ResizeAspectFill }; 57 58 static PassRefPtr<WKCACFLayer> create(LayerType, GraphicsLayerCACF* owner = 0); 59 static WKCACFLayer* layer(CACFLayerRef layer) { return static_cast<WKCACFLayer*>(CACFLayerGetUserData(layer)); } 60 61 ~WKCACFLayer(); 62 63 // Makes this layer the root when the passed context is rendered 64 void becomeRootLayerForContext(CACFContextRef); 65 66 static RetainPtr<CFTypeRef> cfValue(float value) { return RetainPtr<CFTypeRef>(AdoptCF, CFNumberCreate(0, kCFNumberFloat32Type, &value)); } 67 static RetainPtr<CFTypeRef> cfValue(const TransformationMatrix& value) 68 { 69 CATransform3D t; 70 t.m11 = value.m11(); 71 t.m12 = value.m12(); 72 t.m13 = value.m13(); 73 t.m14 = value.m14(); 74 t.m21 = value.m21(); 75 t.m22 = value.m22(); 76 t.m23 = value.m23(); 77 t.m24 = value.m24(); 78 t.m31 = value.m31(); 79 t.m32 = value.m32(); 80 t.m33 = value.m33(); 81 t.m34 = value.m34(); 82 t.m41 = value.m41(); 83 t.m42 = value.m42(); 84 t.m43 = value.m43(); 85 t.m44 = value.m44(); 86 return RetainPtr<CFTypeRef>(AdoptCF, CACFVectorCreateTransform(t)); 87 } 88 static RetainPtr<CFTypeRef> cfValue(const FloatPoint& value) 89 { 90 CGPoint p; 91 p.x = value.x(); p.y = value.y(); 92 return RetainPtr<CFTypeRef>(AdoptCF, CACFVectorCreatePoint(p)); 93 } 94 static RetainPtr<CFTypeRef> cfValue(const FloatRect& rect) 95 { 96 CGRect r; 97 r.origin.x = rect.x(); 98 r.origin.y = rect.y(); 99 r.size.width = rect.width(); 100 r.size.height = rect.height(); 101 CGFloat v[4] = { CGRectGetMinX(r), CGRectGetMinY(r), CGRectGetMaxX(r), CGRectGetMaxY(r) }; 102 return RetainPtr<CFTypeRef>(AdoptCF, CACFVectorCreate(4, v)); 103 } 104 static RetainPtr<CFTypeRef> cfValue(const Color& color) 105 { 106 return RetainPtr<CFTypeRef>(AdoptCF, CGColorCreateGenericRGB(color.red(), color.green(), color.blue(), color.alpha())); 107 } 108 109 void display(PlatformGraphicsContext*); 110 111 bool isTransformLayer() const; 112 113 void addSublayer(PassRefPtr<WKCACFLayer> sublayer); 114 void insertSublayer(PassRefPtr<WKCACFLayer>, size_t index); 115 void insertSublayerAboveLayer(PassRefPtr<WKCACFLayer>, const WKCACFLayer* reference); 116 void insertSublayerBelowLayer(PassRefPtr<WKCACFLayer>, const WKCACFLayer* reference); 117 void replaceSublayer(WKCACFLayer* reference, PassRefPtr<WKCACFLayer>); 118 void removeFromSuperlayer(); 119 static void moveSublayers(WKCACFLayer* fromLayer, WKCACFLayer* toLayer); 120 121 WKCACFLayer* ancestorOrSelfWithSuperlayer(WKCACFLayer*) const; 122 123 void setAnchorPoint(const CGPoint& p) { CACFLayerSetAnchorPoint(layer(), p); setNeedsCommit(); } 124 CGPoint anchorPoint() const { return CACFLayerGetAnchorPoint(layer()); } 125 126 void setAnchorPointZ(CGFloat z) { CACFLayerSetAnchorPointZ(layer(), z); setNeedsCommit(); } 127 CGFloat anchorPointZ() const { return CACFLayerGetAnchorPointZ(layer()); } 128 129 void setBackgroundColor(CGColorRef color) { CACFLayerSetBackgroundColor(layer(), color); setNeedsCommit(); } 130 CGColorRef backgroundColor() const { return CACFLayerGetBackgroundColor(layer()); } 131 132 void setBorderColor(CGColorRef color) { CACFLayerSetBorderColor(layer(), color); setNeedsCommit(); } 133 CGColorRef borderColor() const { return CACFLayerGetBorderColor(layer()); } 134 135 void setBorderWidth(CGFloat width) { CACFLayerSetBorderWidth(layer(), width); setNeedsCommit(); } 136 CGFloat borderWidth() const { return CACFLayerGetBorderWidth(layer()); } 137 138 void setBounds(const CGRect&); 139 CGRect bounds() const { return CACFLayerGetBounds(layer()); } 140 141 void setClearsContext(bool clears) { CACFLayerSetClearsContext(layer(), clears); setNeedsCommit(); } 142 bool clearsContext() const { return CACFLayerGetClearsContext(layer()); } 143 144 void setContents(CGImageRef contents) { CACFLayerSetContents(layer(), contents); setNeedsCommit(); } 145 CGImageRef contents() const { return static_cast<CGImageRef>(const_cast<void*>(CACFLayerGetContents(layer()))); } 146 147 void setContentsRect(const CGRect& contentsRect) { CACFLayerSetContentsRect(layer(), contentsRect); setNeedsCommit(); } 148 CGRect contentsRect() const { return CACFLayerGetContentsRect(layer()); } 149 150 void setContentsGravity(ContentsGravityType); 151 ContentsGravityType contentsGravity() const; 152 153 void setDoubleSided(bool b) { CACFLayerSetDoubleSided(layer(), b); setNeedsCommit(); } 154 bool doubleSided() const { return CACFLayerIsDoubleSided(layer()); } 155 156 void setEdgeAntialiasingMask(uint32_t mask) { CACFLayerSetEdgeAntialiasingMask(layer(), mask); setNeedsCommit(); } 157 uint32_t edgeAntialiasingMask() const { return CACFLayerGetEdgeAntialiasingMask(layer()); } 158 159 void setFilters(CFArrayRef filters) { CACFLayerSetFilters(layer(), filters); setNeedsCommit(); } 160 CFArrayRef filters() const { return CACFLayerGetFilters(layer()); } 161 162 void setFrame(const CGRect&); 163 CGRect frame() const { return CACFLayerGetFrame(layer()); } 164 165 void setHidden(bool hidden) { CACFLayerSetHidden(layer(), hidden); setNeedsCommit(); } 166 bool isHidden() const { return CACFLayerIsHidden(layer()); } 167 168 void setMasksToBounds(bool b) { CACFLayerSetMasksToBounds(layer(), b); } 169 bool masksToBounds() const { return CACFLayerGetMasksToBounds(layer()); } 170 171 void setMagnificationFilter(FilterType); 172 FilterType magnificationFilter() const; 173 174 void setMinificationFilter(FilterType); 175 FilterType minificationFilter() const; 176 177 void setMinificationFilterBias(float bias) { CACFLayerSetMinificationFilterBias(layer(), bias); } 178 float minificationFilterBias() const { return CACFLayerGetMinificationFilterBias(layer()); } 179 180 void setName(const String& name) { CACFLayerSetName(layer(), RetainPtr<CFStringRef>(AdoptCF, name.createCFString()).get()); } 181 String name() const { return CACFLayerGetName(layer()); } 182 183 void setNeedsDisplay(const CGRect& dirtyRect); 184 void setNeedsDisplay(); 185 186 void setNeedsDisplayOnBoundsChange(bool needsDisplay) { m_needsDisplayOnBoundsChange = needsDisplay; } 187 188 void setOpacity(float opacity) { CACFLayerSetOpacity(layer(), opacity); setNeedsCommit(); } 189 float opacity() const { return CACFLayerGetOpacity(layer()); } 190 191 void setOpaque(bool b) { CACFLayerSetOpaque(layer(), b); setNeedsCommit(); } 192 bool opaque() const { return CACFLayerIsOpaque(layer()); } 193 194 void setPosition(const CGPoint& position) { CACFLayerSetPosition(layer(), position); setNeedsCommit(); } 195 CGPoint position() const { return CACFLayerGetPosition(layer()); } 196 197 void setZPosition(CGFloat position) { CACFLayerSetZPosition(layer(), position); setNeedsCommit(); } 198 CGFloat zPosition() const { return CACFLayerGetZPosition(layer()); } 199 200 void setSpeed(float speed) { CACFLayerSetSpeed(layer(), speed); } 201 CFTimeInterval speed() const { CACFLayerGetSpeed(layer()); } 202 203 void setTimeOffset(CFTimeInterval t) { CACFLayerSetTimeOffset(layer(), t); } 204 CFTimeInterval timeOffset() const { CACFLayerGetTimeOffset(layer()); } 205 206 WKCACFLayer* rootLayer() const; 207 208 void setSortsSublayers(bool sorts) { CACFLayerSetSortsSublayers(layer(), sorts); setNeedsCommit(); } 209 bool sortsSublayers() const { return CACFLayerGetSortsSublayers(layer()); } 210 211 void removeAllSublayers(); 212 213 void setSublayers(const Vector<RefPtr<WKCACFLayer> >&); 214 215 void setSublayerTransform(const CATransform3D& transform) { CACFLayerSetSublayerTransform(layer(), transform); setNeedsCommit(); } 216 CATransform3D sublayerTransform() const { return CACFLayerGetSublayerTransform(layer()); } 217 218 WKCACFLayer* superlayer() const; 219 220 void setTransform(const CATransform3D& transform) { CACFLayerSetTransform(layer(), transform); setNeedsCommit(); } 221 CATransform3D transform() const { return CACFLayerGetTransform(layer()); } 222 223 void setGeometryFlipped(bool flipped) { CACFLayerSetGeometryFlipped(layer(), flipped); setNeedsCommit(); } 224 bool geometryFlipped() const { return CACFLayerIsGeometryFlipped(layer()); } 225 226 #ifndef NDEBUG 227 // Print the tree from the root. Also does consistency checks 228 void printTree() const; 229 #endif 230 231 private: 232 WKCACFLayer(LayerType, GraphicsLayerCACF* owner); 233 234 void setNeedsCommit(); 235 CACFLayerRef layer() const { return m_layer.get(); } 236 size_t numSublayers() const 237 { 238 CFArrayRef sublayers = CACFLayerGetSublayers(layer()); 239 return sublayers ? CFArrayGetCount(sublayers) : 0; 240 } 241 242 const WKCACFLayer* sublayerAtIndex(int) const; 243 244 // Returns the index of the passed layer in this layer's sublayers list 245 // or -1 if not found 246 int indexOfSublayer(const WKCACFLayer*); 247 248 // This should only be called from removeFromSuperlayer. 249 void removeSublayer(const WKCACFLayer*); 250 251 #ifndef NDEBUG 252 // Print this layer and its children to the console 253 void printLayer(int indent) const; 254 #endif 255 256 RetainPtr<CACFLayerRef> m_layer; 257 bool m_needsDisplayOnBoundsChange; 258 GraphicsLayerCACF* m_owner; 259 }; 260 261 } 262 263 #endif // USE(ACCELERATED_COMPOSITING) 264 265 #endif // WKCACFLayer_h 266