MacIOSurface.h (6910B)
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 MacIOSurface_h__ 8 #define MacIOSurface_h__ 9 #ifdef XP_DARWIN 10 # include <CoreVideo/CoreVideo.h> 11 # include <IOSurface/IOSurfaceRef.h> 12 # include <QuartzCore/QuartzCore.h> 13 # include <dlfcn.h> 14 15 # include "mozilla/gfx/Types.h" 16 # include "mozilla/Maybe.h" 17 # include "CFTypeRefPtr.h" 18 19 namespace mozilla { 20 namespace gl { 21 class GLContext; 22 } 23 } // namespace mozilla 24 25 # ifdef XP_MACOSX 26 struct _CGLContextObject; 27 28 typedef _CGLContextObject* CGLContextObj; 29 # endif 30 typedef uint32_t IOSurfaceID; 31 32 # ifdef XP_MACOSX 33 # import <OpenGL/OpenGL.h> 34 # else 35 # include "GLTypes.h" 36 typedef realGLboolean GLboolean; 37 # include <OpenGLES/ES2/gl.h> 38 # endif 39 40 # include "2D.h" 41 # include "mozilla/RefCounted.h" 42 43 class MacIOSurface final 44 : public mozilla::external::AtomicRefCounted<MacIOSurface> { 45 public: 46 MOZ_DECLARE_REFCOUNTED_VIRTUAL_TYPENAME(MacIOSurface) 47 typedef mozilla::gfx::SourceSurface SourceSurface; 48 typedef mozilla::gfx::DrawTarget DrawTarget; 49 typedef mozilla::gfx::BackendType BackendType; 50 typedef mozilla::gfx::IntSize IntSize; 51 typedef mozilla::gfx::ChromaSubsampling ChromaSubsampling; 52 typedef mozilla::gfx::YUVColorSpace YUVColorSpace; 53 typedef mozilla::gfx::ColorSpace2 ColorSpace2; 54 typedef mozilla::gfx::TransferFunction TransferFunction; 55 typedef mozilla::gfx::ColorRange ColorRange; 56 typedef mozilla::gfx::ColorDepth ColorDepth; 57 58 // The usage count of the IOSurface is increased by 1 during the lifetime 59 // of the MacIOSurface instance. 60 // MacIOSurface holds a reference to the corresponding IOSurface. 61 62 static already_AddRefed<MacIOSurface> CreateIOSurface(int aWidth, int aHeight, 63 bool aHasAlpha = true); 64 static already_AddRefed<MacIOSurface> CreateBiPlanarSurface( 65 const IntSize& aYSize, const IntSize& aCbCrSize, 66 ChromaSubsampling aChromaSubsampling, YUVColorSpace aColorSpace, 67 TransferFunction aTransferFunction, ColorRange aColorRange, 68 ColorDepth aColorDepth); 69 static already_AddRefed<MacIOSurface> CreateSinglePlanarSurface( 70 const IntSize& aSize, YUVColorSpace aColorSpace, 71 TransferFunction aTransferFunction, ColorRange aColorRange); 72 static void ReleaseIOSurface(MacIOSurface* aIOSurface); 73 static already_AddRefed<MacIOSurface> LookupSurface( 74 IOSurfaceID aSurfaceID, bool aHasAlpha = true, 75 mozilla::gfx::YUVColorSpace aColorSpace = 76 mozilla::gfx::YUVColorSpace::Identity); 77 static mozilla::gfx::SurfaceFormat SurfaceFormatForPixelFormat( 78 OSType aPixelFormat, bool aHasAlpha); 79 80 explicit MacIOSurface(CFTypeRefPtr<IOSurfaceRef> aIOSurfaceRef, 81 bool aHasAlpha = true, 82 mozilla::gfx::YUVColorSpace aColorSpace = 83 mozilla::gfx::YUVColorSpace::Identity); 84 85 ~MacIOSurface(); 86 IOSurfaceID GetIOSurfaceID() const; 87 void* GetBaseAddress() const; 88 void* GetBaseAddressOfPlane(size_t planeIndex) const; 89 size_t GetPlaneCount() const; 90 OSType GetPixelFormat() const; 91 // GetWidth() and GetHeight() return values in "display pixels". A 92 // "display pixel" is the smallest fully addressable part of a display. 93 // But in HiDPI modes each "display pixel" corresponds to more than one 94 // device pixel. Use GetDevicePixel**() to get device pixels. 95 size_t GetWidth(size_t plane = 0) const; 96 size_t GetHeight(size_t plane = 0) const; 97 IntSize GetSize(size_t plane = 0) const { 98 return IntSize(GetWidth(plane), GetHeight(plane)); 99 } 100 size_t GetDevicePixelWidth(size_t plane = 0) const; 101 size_t GetDevicePixelHeight(size_t plane = 0) const; 102 size_t GetBytesPerRow(size_t plane = 0) const; 103 size_t GetAllocSize() const; 104 bool Lock(bool aReadOnly = true); 105 void Unlock(bool aReadOnly = true); 106 bool IsLocked() const { return mIsLocked; } 107 void IncrementUseCount(); 108 void DecrementUseCount(); 109 bool HasAlpha() const { return mHasAlpha; } 110 mozilla::gfx::SurfaceFormat GetFormat() const; 111 mozilla::gfx::SurfaceFormat GetReadFormat() const; 112 mozilla::gfx::ColorDepth GetColorDepth() const; 113 // This would be better suited on MacIOSurfaceImage type, however due to the 114 // current data structure, this is not possible as only the IOSurfaceRef is 115 // being used across. 116 void SetYUVColorSpace(YUVColorSpace aColorSpace) { 117 mColorSpace = aColorSpace; 118 } 119 YUVColorSpace GetYUVColorSpace() const { return mColorSpace; } 120 bool IsFullRange() const { 121 OSType format = GetPixelFormat(); 122 return (format == kCVPixelFormatType_420YpCbCr8BiPlanarFullRange || 123 format == kCVPixelFormatType_420YpCbCr10BiPlanarFullRange || 124 format == kCVPixelFormatType_422YpCbCr10BiPlanarFullRange || 125 format == kCVPixelFormatType_422YpCbCr8FullRange); 126 } 127 mozilla::gfx::ColorRange GetColorRange() const { 128 if (IsFullRange()) return mozilla::gfx::ColorRange::FULL; 129 return mozilla::gfx::ColorRange::LIMITED; 130 } 131 132 // Bind this IOSurface to a texture using the most efficient mechanism 133 // available on the current platform. 134 // 135 // Note that on iOS simulator, due to incomplete support for 136 // texImageIOSurface, this will only use texImage2D to upload, and cannot be 137 // used to read-back the GL texture to an IOSurface. 138 bool BindTexImage(mozilla::gl::GLContext* aGL, size_t aPlane, 139 mozilla::gfx::SurfaceFormat* aOutReadFormat = nullptr); 140 141 already_AddRefed<SourceSurface> GetAsSurface(); 142 143 // Creates a DrawTarget that wraps the data in the IOSurface. Rendering to 144 // this DrawTarget directly manipulates the contents of the IOSurface. 145 // Only call when the surface is already locked for writing! 146 // The returned DrawTarget must only be used while the surface is still 147 // locked. 148 // Also, only call this if you're reasonably sure that the DrawTarget of the 149 // selected backend supports the IOSurface's SurfaceFormat. 150 already_AddRefed<DrawTarget> GetAsDrawTargetLocked(BackendType aBackendType); 151 152 static size_t GetMaxWidth(); 153 static size_t GetMaxHeight(); 154 155 # ifdef DEBUG 156 static mozilla::Maybe<OSType> ChoosePixelFormat( 157 mozilla::gfx::ChromaSubsampling aChromaSubsampling, 158 mozilla::gfx::ColorRange aColorRange, 159 mozilla::gfx::ColorDepth aColorDepth); 160 # endif 161 162 CFTypeRefPtr<IOSurfaceRef> GetIOSurfaceRef() { return mIOSurfaceRef; } 163 164 void SetColorSpace(mozilla::gfx::ColorSpace2) const; 165 166 ColorSpace2 mColorPrimaries = ColorSpace2::UNKNOWN; 167 168 private: 169 CFTypeRefPtr<IOSurfaceRef> mIOSurfaceRef; 170 const bool mHasAlpha; 171 YUVColorSpace mColorSpace = YUVColorSpace::Identity; 172 bool mIsLocked = false; 173 }; 174 175 #endif 176 #endif