Skip to content

Commit

Permalink
ios: unified texture from iosurface using ios11/undocmented api
Browse files Browse the repository at this point in the history
it works, but not enabled. now creating texture for macOS and iOS are
unified. iOS11 adds a new api  'texImageIOSurface' which is implemented
by existing 'texImageIOSurface' with additional invert parameter.
  • Loading branch information
wang-bin committed Oct 22, 2017
1 parent 1416eed commit 73b374f
Show file tree
Hide file tree
Showing 2 changed files with 49 additions and 7 deletions.
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
/******************************************************************************
QtAV: Multimedia framework based on Qt and FFmpeg
Copyright (C) 2012-2016 Wang Bin <[email protected]>
Copyright (C) 2012-2017 Wang Bin <[email protected]>
* This file is part of QtAV (from 2016)
Expand All @@ -20,6 +20,20 @@
******************************************************************************/

#include "SurfaceInteropCV.h"
#ifdef Q_OS_IOS
#import <OpenGLES/EAGL.h>
#include <CoreVideo/CVOpenGLESTextureCache.h>
# ifdef __IPHONE_11_0 // always defined in new sdk
# import <OpenGLES/EAGLIOSurface.h>
# endif //__IPHONE_11_0
# if COREVIDEO_SUPPORTS_IOSURFACE
// declare the private API if IOSurface is supported in SDK. Thus we can use IOSurface on any iOS version even with old SDK and compiler
@interface EAGLContext()
- (BOOL)texImageIOSurface:(IOSurfaceRef)ioSurface target:(NSUInteger)target internalFormat:(NSUInteger)internalFormat width:(uint32_t)width height:(uint32_t)height format:(NSUInteger)format type:(NSUInteger)type plane:(uint32_t)plane invert:(BOOL)invert NS_AVAILABLE_IOS(4_0); // confirmed in iOS5.1
@end
# endif //COREVIDEO_SUPPORTS_IOSURFACE
#endif //Q_OS_IOS

#include <IOSurface/IOSurface.h>
#include "QtAV/VideoFrame.h"
#include "opengl/OpenGLHelper.h"
Expand Down Expand Up @@ -76,24 +90,35 @@ bool InteropResourceIOSurface::map(CVPixelBufferRef buf, GLuint *tex, int w, int
{
Q_UNUSED(w);
Q_UNUSED(h);
#if COREVIDEO_SUPPORTS_IOSURFACE // IOSurface header is not included otherwise
const OSType pixfmt = CVPixelBufferGetPixelFormatType(buf);
GLint iformat;
GLenum format, dtype;
getParametersGL(pixfmt, &iformat, &format, &dtype, plane);
switch (pixfmt) {
case '2vuy':
case 'yuvs':
iformat = GL_RGB8; // ES2 requires internal format and format are the same. OSX can use internal format GL_RGB or sized GL_RGB8
// ES2 requires internal format and format are the same. desktop can use internal format GL_RGB or sized GL_RGB8
#ifdef Q_OS_IOS
iformat = GL_RGB_422_APPLE;
#else
iformat = GL_RGB8;
#endif
format = GL_RGB_422_APPLE;
dtype = pixfmt == '2vuy' ? GL_UNSIGNED_SHORT_8_8_APPLE : GL_UNSIGNED_SHORT_8_8_REV_APPLE;
break;
// macOS: GL_RGBA8, GL_BGRA, GL_UNSIGNED_INT_8_8_8_8_REV
// GL_YCBCR_422_APPLE: convert to rgb texture internally (bt601). only supports OSX
// GL_RGB_422_APPLE: raw yuv422 texture
case 'BGRA':
#ifdef Q_OS_IOS
iformat = GL_RGBA;
format = GL_RGBA;
#else
iformat = GL_RGBA8;
format = GL_BGRA;
dtype = GL_UNSIGNED_INT_8_8_8_8_REV;
#endif
break;
default:
break;
Expand All @@ -104,12 +129,30 @@ bool InteropResourceIOSurface::map(CVPixelBufferRef buf, GLuint *tex, int w, int
const int planeH = CVPixelBufferGetHeightOfPlane(buf, plane);
//qDebug("map plane%d. %dx%d, gl %d %d %d", plane, planeW, planeH, iformat, format, dtype);

const IOSurfaceRef surface = CVPixelBufferGetIOSurface(buf);
const IOSurfaceRef surface = CVPixelBufferGetIOSurface(buf); // available in ios11 sdk, ios4 runtime
#ifdef Q_OS_IOS
BOOL ok = false;
# ifdef __IPHONE_11_0
# if __has_builtin(__builtin_available) // xcode9: runtime check @available is required, or -Wno-unguarded-availability-new
if (@available(iOS 11, *)) //symbol is available in iOS5+, but crashes at runtime
# else
if (false)
# endif // __has_builtin(__builtin_available)
ok = [[EAGLContext currentContext] texImageIOSurface:surface target:target internalFormat:iformat width:planeW height:planeH format:format type:dtype plane:plane];
else // fallback to old private api if runtime version < 11
# endif //__IPHONE_11_0
ok = [[EAGLContext currentContext] texImageIOSurface:surface target:target internalFormat:iformat width:planeW height:planeH format:format type:dtype plane:plane invert:NO];
if (!ok) {
qWarning("error creating IOSurface texture at plane %d", i);
}
#else
CGLError err = CGLTexImageIOSurface2D(CGLGetCurrentContext(), target, iformat, planeW, planeH, format, dtype, surface, plane);
if (err != kCGLNoError) {
qWarning("error creating IOSurface texture at plane %d: %s", plane, CGLErrorString(err));
}
#endif // Q_OS_IOS
DYGL(glBindTexture(target, 0));
#endif //COREVIDEO_SUPPORTS_IOSURFACE
return true;
}
} // namespace cv
Expand Down
7 changes: 3 additions & 4 deletions src/libQtAV.pro
Original file line number Diff line number Diff line change
Expand Up @@ -329,14 +329,13 @@ config_libcedarv {
}
mac {
HEADERS *= codec/video/SurfaceInteropCV.h
SOURCES *= codec/video/SurfaceInteropCV.cpp
SOURCES *= codec/video/SurfaceInteropCV.cpp \
codec/video/SurfaceInteropIOSurface.mm
ios {
OBJECTIVE_SOURCES *= codec/video/SurfaceInteropCVOpenGLES.mm
} else {
CONFIG += config_vda
SOURCES *= codec/video/SurfaceInteropIOSurface.cpp
#CONFIG += config_vda
#SOURCES *= codec/video/SurfaceInteropCVOpenGL.cpp
LIBS += -framework IOSurface
}
LIBS += -framework CoreVideo -framework CoreFoundation
}
Expand Down

0 comments on commit 73b374f

Please sign in to comment.