Backport AVKit-based wxMediaCtrl to fix build under OS X 10.12

Allow building wxOSX using 10.12 SDK which doesn't include QTKit support any longer.

See https://github.com/wxWidgets/wxWidgets/pull/341
This commit is contained in:
VZ
2016-11-19 18:30:17 +01:00
committed by GitHub
5 changed files with 830 additions and 24 deletions

194
configure vendored
View File

@@ -1238,6 +1238,7 @@ enable_svg
enable_webkit
enable_webview
enable_graphics_ctx
enable_qtkit
enable_clipboard
enable_dnd
enable_controls
@@ -2169,6 +2170,7 @@ Optional Features:
--enable-webkit use wxWebKitCtrl (Mac-only, use wxWebView instead)
--enable-webview use wxWebView library
--enable-graphics_ctx use graphics context 2D drawing API
--disable-qtkit force AVFoundation instead of QTKit (requires OS X 10.7+)
--enable-clipboard use wxClipboard class
--enable-dnd use Drag'n'Drop classes
--disable-controls disable compilation of all standard controls
@@ -3339,6 +3341,97 @@ fi
as_fn_set_status $ac_retval
} # ac_fn_cxx_try_run
# ac_fn_c_check_header_mongrel LINENO HEADER VAR INCLUDES
# -------------------------------------------------------
# Tests whether HEADER exists, giving a warning if it cannot be compiled using
# the include files in INCLUDES and setting the cache variable VAR
# accordingly.
ac_fn_c_check_header_mongrel ()
{
as_lineno=${as_lineno-"$1"} as_lineno_stack=as_lineno_stack=$as_lineno_stack
if eval \${$3+:} false; then :
{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $2" >&5
$as_echo_n "checking for $2... " >&6; }
if eval \${$3+:} false; then :
$as_echo_n "(cached) " >&6
fi
eval ac_res=\$$3
{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_res" >&5
$as_echo "$ac_res" >&6; }
else
# Is the header compilable?
{ $as_echo "$as_me:${as_lineno-$LINENO}: checking $2 usability" >&5
$as_echo_n "checking $2 usability... " >&6; }
cat confdefs.h - <<_ACEOF >conftest.$ac_ext
/* end confdefs.h. */
$4
#include <$2>
_ACEOF
if ac_fn_c_try_compile "$LINENO"; then :
ac_header_compiler=yes
else
ac_header_compiler=no
fi
rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_header_compiler" >&5
$as_echo "$ac_header_compiler" >&6; }
# Is the header present?
{ $as_echo "$as_me:${as_lineno-$LINENO}: checking $2 presence" >&5
$as_echo_n "checking $2 presence... " >&6; }
cat confdefs.h - <<_ACEOF >conftest.$ac_ext
/* end confdefs.h. */
#include <$2>
_ACEOF
if ac_fn_c_try_cpp "$LINENO"; then :
ac_header_preproc=yes
else
ac_header_preproc=no
fi
rm -f conftest.err conftest.i conftest.$ac_ext
{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_header_preproc" >&5
$as_echo "$ac_header_preproc" >&6; }
# So? What about this header?
case $ac_header_compiler:$ac_header_preproc:$ac_c_preproc_warn_flag in #((
yes:no: )
{ $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: $2: accepted by the compiler, rejected by the preprocessor!" >&5
$as_echo "$as_me: WARNING: $2: accepted by the compiler, rejected by the preprocessor!" >&2;}
{ $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: $2: proceeding with the compiler's result" >&5
$as_echo "$as_me: WARNING: $2: proceeding with the compiler's result" >&2;}
;;
no:yes:* )
{ $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: $2: present but cannot be compiled" >&5
$as_echo "$as_me: WARNING: $2: present but cannot be compiled" >&2;}
{ $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: $2: check for missing prerequisite headers?" >&5
$as_echo "$as_me: WARNING: $2: check for missing prerequisite headers?" >&2;}
{ $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: $2: see the Autoconf documentation" >&5
$as_echo "$as_me: WARNING: $2: see the Autoconf documentation" >&2;}
{ $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: $2: section \"Present But Cannot Be Compiled\"" >&5
$as_echo "$as_me: WARNING: $2: section \"Present But Cannot Be Compiled\"" >&2;}
{ $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: $2: proceeding with the compiler's result" >&5
$as_echo "$as_me: WARNING: $2: proceeding with the compiler's result" >&2;}
( $as_echo "## ----------------------------------------- ##
## Report this to wx-dev@lists.wxwidgets.org ##
## ----------------------------------------- ##"
) | sed "s/^/$as_me: WARNING: /" >&2
;;
esac
{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for $2" >&5
$as_echo_n "checking for $2... " >&6; }
if eval \${$3+:} false; then :
$as_echo_n "(cached) " >&6
else
eval "$3=\$ac_header_compiler"
fi
eval ac_res=\$$3
{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $ac_res" >&5
$as_echo "$ac_res" >&6; }
fi
eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno
} # ac_fn_c_check_header_mongrel
cat >config.log <<_ACEOF
This file contains any messages produced by compilers while
running configure, to aid debugging if configure makes a mistake.
@@ -10923,6 +11016,51 @@ fi
{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $result" >&5
$as_echo "$result" >&6; }
else
enablestring=disable
defaultval=
if test -z "$defaultval"; then
if test x"$enablestring" = xdisable; then
defaultval=yes
else
defaultval=no
fi
fi
{ $as_echo "$as_me:${as_lineno-$LINENO}: checking for --${enablestring:-enable}-qtkit" >&5
$as_echo_n "checking for --${enablestring:-enable}-qtkit... " >&6; }
# Check whether --enable-qtkit was given.
if test "${enable_qtkit+set}" = set; then :
enableval=$enable_qtkit;
if test "$enableval" = yes; then
wx_cv_use_qtkit='wxOSX_USE_QTKIT=yes'
else
wx_cv_use_qtkit='wxOSX_USE_QTKIT=no'
fi
else
wx_cv_use_qtkit='wxOSX_USE_QTKIT=${'DEFAULT_wxOSX_USE_QTKIT":-$defaultval}"
fi
eval "$wx_cv_use_qtkit"
if test x"$enablestring" = xdisable; then
if test $wxOSX_USE_QTKIT = no; then
result=yes
else
result=no
fi
else
result=$wxOSX_USE_QTKIT
fi
{ $as_echo "$as_me:${as_lineno-$LINENO}: result: $result" >&5
$as_echo "$result" >&6; }
fi
@@ -37365,7 +37503,61 @@ fi
fi
elif test "$wxUSE_MAC" = 1; then
GST_LIBS="-framework QTKit"
if test "$wxUSE_OSX_IPHONE" = 1; then
GST_LIBS="-framework AVFoundation -framework CoreMedia"
else
old_CPPFLAGS="$CPPFLAGS"
CPPFLAGS="-x objective-c++ $CPPFLAGS"
if test "$wxOSX_USE_QTKIT" = "no"; then
$as_echo "#define wxOSX_USE_QTKIT 0" >>confdefs.h
GST_LIBS="-framework AVFoundation -framework CoreMedia"
else
ac_fn_c_check_header_mongrel "$LINENO" "QTKit/QTKit.h" "ac_cv_header_QTKit_QTKit_h" "$ac_includes_default"
if test "x$ac_cv_header_QTKit_QTKit_h" = xyes; then :
GST_LIBS="-framework QTKit"
else
$as_echo "#define wxOSX_USE_QTKIT 0" >>confdefs.h
wxOSX_USE_QTKIT=no
GST_LIBS="-framework AVFoundation -framework CoreMedia"
fi
fi
if test "$wxOSX_USE_QTKIT" = "no"; then
{ $as_echo "$as_me:${as_lineno-$LINENO}: checking if AVKit is availble" >&5
$as_echo_n "checking if AVKit is availble... " >&6; }
cat confdefs.h - <<_ACEOF >conftest.$ac_ext
/* end confdefs.h. */
#include "AvailabilityMacros.h"
int
main ()
{
#if MAC_OS_X_VERSION_MIN_REQUIRED >= MAC_OS_X_VERSION_10_9
// AVKit available
#else
choke me
#endif
;
return 0;
}
_ACEOF
if ac_fn_c_try_compile "$LINENO"; then :
GST_LIBS="$GST_LIBS -framework AVKit"
fi
rm -f core conftest.err conftest.$ac_objext conftest.$ac_ext
fi
CPPFLAGS="$old_CPPFLAGS"
fi
fi
if test $USE_MEDIA = 1; then

View File

@@ -838,6 +838,8 @@ dnl wxDC is implemented in terms of wxGraphicsContext in wxOSX so the latter
dnl can't be disabled, don't even provide an option to do it
if test "$wxUSE_MAC" != 1; then
WX_ARG_FEATURE(graphics_ctx,[ --enable-graphics_ctx use graphics context 2D drawing API], wxUSE_GRAPHICS_CONTEXT)
else
WX_ARG_DISABLE(qtkit, [ --disable-qtkit force AVFoundation instead of QTKit (requires OS X 10.7+)], wxOSX_USE_QTKIT)
fi
dnl ---------------------------------------------------------------------------
@@ -7590,10 +7592,50 @@ if test "$wxUSE_MEDIACTRL" = "yes" -o "$wxUSE_MEDIACTRL" = "auto"; then
USE_MEDIA=0
fi
elif test "$wxUSE_MAC" = 1; then
dnl We always have the necessary libraries under Mac
dnl but we need to link with it explicitly.
GST_LIBS="-framework QTKit"
elif test "$wxUSE_MAC" = 1; then
if test "$wxUSE_OSX_IPHONE" = 1; then
dnl this will also be used for cocoa in the future
GST_LIBS="-framework AVFoundation -framework CoreMedia"
else
dnl We always have the necessary libraries under Mac
dnl but we need to link with it explicitly.
dnl QTKit is no longer available as of 10.12 SDK
old_CPPFLAGS="$CPPFLAGS"
CPPFLAGS="-x objective-c++ $CPPFLAGS"
if test "$wxOSX_USE_QTKIT" = "no"; then
dnl Do not test for QTKit if has been disabled from the command line
AC_DEFINE(wxOSX_USE_QTKIT,0)
GST_LIBS="-framework AVFoundation -framework CoreMedia"
else
dnl check if QTKit is available, otherwise force AVFoundation usage
AC_CHECK_HEADER([QTKit/QTKit.h],
[
GST_LIBS="-framework QTKit"
],
[
AC_DEFINE(wxOSX_USE_QTKIT,0)
wxOSX_USE_QTKIT=no
GST_LIBS="-framework AVFoundation -framework CoreMedia"
])
fi
if test "$wxOSX_USE_QTKIT" = "no"; then
dnl AVKit is only available since OS X 10.9
AC_MSG_CHECKING([if AVKit is availble])
AC_TRY_COMPILE(
[#include "AvailabilityMacros.h"],
[
#if MAC_OS_X_VERSION_MIN_REQUIRED >= MAC_OS_X_VERSION_10_9
// AVKit available
#else
choke me
#endif
],
GST_LIBS="$GST_LIBS -framework AVKit"
)
fi
CPPFLAGS="$old_CPPFLAGS"
fi
fi
if test $USE_MEDIA = 1; then

View File

@@ -656,6 +656,8 @@ wxOSX:
- Fix conversion of wxBitmap to wxImage in 64 bit builds.
- Fix length of text in wxTextDataObject.
- Fix using wxHTTP and wxFTP from worker thread.
- Compilation fix for wxMediaCtrl under 10.12 (Tobias Taschner)
- Added --disable-qtkit to force usage of AVFoundation under 10.7-10.11 (Tobias Taschner)
- Fix wxFileDialog::GetFilterIndex() for file open dialogs (phsilva).
- Fix wxSearchCtrl appearance under 10.10 (John Roberts).
- Fix handling of "Cancel" button in wxSearchCtrl (John Roberts).

View File

@@ -871,6 +871,11 @@
*/
#define wxUSE_WEBKIT 0
/*
* wxMediaCtrl on OS X
*/
#undef wxOSX_USE_QTKIT
/*
* Objective-C class name uniquifying
*/

View File

@@ -1,10 +1,10 @@
/////////////////////////////////////////////////////////////////////////////
// Name: src/cocoa/mediactrl.cpp
// Name: src/osx/cocoa/mediactrl.mm
// Purpose: Built-in Media Backends for Cocoa
// Author: Ryan Norton <wxprojects@comcast.net>
// Author: Ryan Norton <wxprojects@comcast.net>, Stefan Csomor
// Modified by:
// Created: 02/03/05
// Copyright: (c) 2004-2005 Ryan Norton, (c) 2005 David Elliot
// Copyright: (c) 2004-2005 Ryan Norton, (c) 2005 David Elliot, (c) Stefan Csomor
// Licence: wxWindows licence
/////////////////////////////////////////////////////////////////////////////
@@ -36,10 +36,34 @@
#include "wx/osx/private.h"
#ifndef wxOSX_USE_QTKIT
#if wxOSX_USE_IPHONE
#define wxOSX_USE_QTKIT 0
#define wxOSX_USE_AVFOUNDATION 1
#else
#define wxOSX_USE_QTKIT 1
#define wxOSX_USE_AVFOUNDATION 0
#endif
#else
#if wxOSX_USE_QTKIT
#define wxOSX_USE_AVFOUNDATION 0
#else
#define wxOSX_USE_AVFOUNDATION 1
#endif
#endif
#if wxOSX_USE_AVFOUNDATION && wxOSX_USE_COCOA && MAC_OS_X_VERSION_MIN_REQUIRED >= MAC_OS_X_VERSION_10_9
#define wxOSX_USE_AVKIT 1
#else
#define wxOSX_USE_AVKIT 0
#endif
//===========================================================================
// BACKEND DECLARATIONS
//===========================================================================
#if wxOSX_USE_QTKIT
//---------------------------------------------------------------------------
//
// wxQTMediaBackend
@@ -147,9 +171,9 @@ private:
-(void)dealloc
{
NSNotificationCenter *nc = [NSNotificationCenter defaultCenter];
[nc removeObserver:self];
[nc removeObserver:self];
[super dealloc];
[super dealloc];
}
-(wxQTMediaBackend*) backend
@@ -173,17 +197,17 @@ private:
- (void)movieRateChanged:(NSNotification *)notification
{
NSDictionary *userInfo = [notification userInfo];
NSNumber *newRate = [userInfo objectForKey:QTMovieRateDidChangeNotificationParameter];
NSDictionary *userInfo = [notification userInfo];
if ([newRate intValue] == 0)
{
m_backend->QueuePauseEvent();
}
NSNumber *newRate = [userInfo objectForKey:QTMovieRateDidChangeNotificationParameter];
if ([newRate intValue] == 0)
{
m_backend->QueuePauseEvent();
}
else if ( [self isPlaying] == NO )
{
m_backend->QueuePlayEvent();
m_backend->QueuePlayEvent();
}
}
@@ -207,12 +231,12 @@ private:
-(BOOL)isPlaying
{
if ([self rate] == 0)
{
return NO;
}
return YES;
if ([self rate] == 0)
{
return NO;
}
return YES;
}
@end
@@ -433,6 +457,547 @@ void wxQTMediaBackend::DoShowPlayerControls(wxMediaCtrlPlayerControls flags)
}
}
#endif
#if wxOSX_USE_AVFOUNDATION
//---------------------------------------------------------------------------
//
// wxAVMediaBackend
//
//---------------------------------------------------------------------------
#import <AVFoundation/AVFoundation.h>
#if wxOSX_USE_AVKIT
#import <AVKit/AVKit.h>
#endif
class WXDLLIMPEXP_FWD_MEDIA wxAVMediaBackend;
static void *AVSPPlayerItemStatusContext = &AVSPPlayerItemStatusContext;
static void *AVSPPlayerRateContext = &AVSPPlayerRateContext;
@interface wxAVPlayer : AVPlayer {
AVPlayerLayer *playerLayer;
wxAVMediaBackend* m_backend;
}
-(BOOL)isPlaying;
@property (retain) AVPlayerLayer *playerLayer;
@end
class WXDLLIMPEXP_MEDIA wxAVMediaBackend : public wxMediaBackendCommonBase
{
public:
wxAVMediaBackend();
~wxAVMediaBackend();
virtual bool CreateControl(wxControl* ctrl, wxWindow* parent,
wxWindowID id,
const wxPoint& pos,
const wxSize& size,
long style,
const wxValidator& validator,
const wxString& name);
virtual bool Play();
virtual bool Pause();
virtual bool Stop();
virtual bool Load(const wxString& fileName);
virtual bool Load(const wxURI& location);
virtual wxMediaState GetState();
virtual bool SetPosition(wxLongLong where);
virtual wxLongLong GetPosition();
virtual wxLongLong GetDuration();
virtual void Move(int x, int y, int w, int h);
wxSize GetVideoSize() const;
virtual double GetPlaybackRate();
virtual bool SetPlaybackRate(double dRate);
virtual double GetVolume();
virtual bool SetVolume(double dVolume);
void Cleanup();
void FinishLoad();
virtual bool ShowPlayerControls(wxMediaCtrlPlayerControls flags);
private:
void DoShowPlayerControls(wxMediaCtrlPlayerControls flags);
wxSize m_bestSize; //Original movie size
wxAVPlayer* m_player; //AVPlayer handle/instance
wxMediaCtrlPlayerControls m_interfaceflags; // Saved interface flags
wxDECLARE_DYNAMIC_CLASS(wxAVMediaBackend);
};
// --------------------------------------------------------------------------
// wxAVMediaBackend
// --------------------------------------------------------------------------
@implementation wxAVPlayer
@synthesize playerLayer;
- (id) init
{
self = [super init];
[self addObserver:self forKeyPath:@"currentItem.status"
options:NSKeyValueObservingOptionNew context:AVSPPlayerItemStatusContext];
[self addObserver:self forKeyPath:@"rate"
options:NSKeyValueObservingOptionNew context:AVSPPlayerRateContext];
return self;
}
- (void)dealloc
{
[playerLayer release];
[[NSNotificationCenter defaultCenter] removeObserver:self];
[self removeObserver:self forKeyPath:@"rate" context:AVSPPlayerRateContext];
[self removeObserver:self forKeyPath:@"currentItem.status" context:AVSPPlayerItemStatusContext];
[super dealloc];
}
- (void)observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object change:(NSDictionary *)change context:(void *)context
{
if (context == AVSPPlayerItemStatusContext)
{
id val = [change objectForKey:NSKeyValueChangeNewKey];
if ( val != [NSNull null ] )
{
AVPlayerStatus status = (AVPlayerStatus) [ val integerValue];
switch (status)
{
case AVPlayerItemStatusUnknown:
break;
case AVPlayerItemStatusReadyToPlay:
[[NSNotificationCenter defaultCenter]
addObserver:self selector:@selector(playerItemDidReachEnd:)
name:AVPlayerItemDidPlayToEndTimeNotification object:self.currentItem];
m_backend->FinishLoad();
break;
case AVPlayerItemStatusFailed:
break;
default:
break;
}
}
}
else if (context == AVSPPlayerRateContext)
{
NSNumber* newRate = [change objectForKey:NSKeyValueChangeNewKey];
if ([newRate intValue] == 0)
{
m_backend->QueuePauseEvent();
}
else if ( [self isPlaying] == NO )
{
m_backend->QueuePlayEvent();
}
}
else
{
[super observeValueForKeyPath:keyPath ofObject:object change:change context:context];
}
}
-(wxAVMediaBackend*) backend
{
return m_backend;
}
-(void) setBackend:(wxAVMediaBackend*) backend
{
m_backend = backend;
}
- (void)playerItemDidReachEnd:(NSNotification *)notification
{
if ( m_backend )
{
if ( m_backend->SendStopEvent() )
m_backend->QueueFinishEvent();
}
}
-(BOOL)isPlaying
{
if ([self rate] == 0)
{
return NO;
}
return YES;
}
@end
#if wxOSX_USE_IPHONE
@interface wxAVView : UIView
{
}
@end
@implementation wxAVView
+ (void)initialize
{
static BOOL initialized = NO;
if (!initialized)
{
initialized = YES;
wxOSXIPhoneClassAddWXMethods( self );
}
}
+ (Class)layerClass
{
return [AVPlayerLayer class];
}
- (id) initWithFrame:(CGRect)rect player:(wxAVPlayer*) player
{
if ( !(self=[super initWithFrame:rect]) )
return nil;
AVPlayerLayer* playerLayer = (AVPlayerLayer*) [self layer];
[playerLayer setPlayer: player];
[player setPlayerLayer:playerLayer];
return self;
}
- (AVPlayerLayer*) playerLayer
{
return (AVPlayerLayer*) [self layer];
}
@end
#else
#if wxOSX_USE_AVKIT
@interface wxAVPlayerView : AVPlayerView
{
}
@end
@implementation wxAVPlayerView
+ (void)initialize
{
static BOOL initialized = NO;
if (!initialized)
{
initialized = YES;
wxOSXCocoaClassAddWXMethods( self );
}
}
- (id) initWithFrame:(NSRect)rect player:(wxAVPlayer*) player
{
if ( !(self=[super initWithFrame:rect]) )
return nil;
self.player = player;
return self;
}
- (AVPlayerLayer*) playerLayer
{
return (AVPlayerLayer*) [[[self layer] sublayers] firstObject];
}
@end
#endif // wxOSX_USE_AVKIT
@interface wxAVView : NSView
{
}
@end
@implementation wxAVView
+ (void)initialize
{
static BOOL initialized = NO;
if (!initialized)
{
initialized = YES;
wxOSXCocoaClassAddWXMethods( self );
}
}
- (id) initWithFrame:(NSRect)rect player:(AVPlayer*) player
{
if ( !(self=[super initWithFrame:rect]) )
return nil;
[self setWantsLayer:YES];
AVPlayerLayer* playerlayer = [[AVPlayerLayer playerLayerWithPlayer: player] retain];
[player setPlayerLayer:playerlayer];
[playerlayer setFrame:[[self layer] bounds]];
[playerlayer setAutoresizingMask:kCALayerWidthSizable | kCALayerHeightSizable];
[[self layer] addSublayer:playerlayer];
return self;
}
- (AVPlayerLayer*) playerLayer
{
return (AVPlayerLayer*) [[[self layer] sublayers] firstObject];
}
@end
#endif
IMPLEMENT_DYNAMIC_CLASS(wxAVMediaBackend, wxMediaBackend);
wxAVMediaBackend::wxAVMediaBackend() :
m_player(nil),
m_interfaceflags(wxMEDIACTRLPLAYERCONTROLS_NONE)
{
}
wxAVMediaBackend::~wxAVMediaBackend()
{
Cleanup();
}
bool wxAVMediaBackend::CreateControl(wxControl* inctrl, wxWindow* parent,
wxWindowID wid,
const wxPoint& pos,
const wxSize& size,
long style,
const wxValidator& validator,
const wxString& name)
{
wxMediaCtrl* mediactrl = (wxMediaCtrl*) inctrl;
mediactrl->DontCreatePeer();
if ( !mediactrl->wxControl::Create(
parent, wid, pos, size,
wxWindow::MacRemoveBordersFromStyle(style),
validator, name))
{
return false;
}
m_player = [[wxAVPlayer alloc] init];
[m_player setBackend:this];
NSRect r = wxOSXGetFrameForControl( mediactrl, pos , size ) ;
WXWidget view = NULL;
#if wxOSX_USE_AVKIT
if ( NSClassFromString(@"AVPlayerView") )
{
view = [[wxAVPlayerView alloc] initWithFrame: r player:m_player];
[(wxAVPlayerView*) view setControlsStyle:AVPlayerViewControlsStyleNone];
}
#endif
if ( view == NULL )
{
view = [[wxAVView alloc] initWithFrame: r player:m_player];
}
#if wxOSX_USE_IPHONE
wxWidgetIPhoneImpl* impl = new wxWidgetIPhoneImpl(mediactrl,view);
#else
wxWidgetCocoaImpl* impl = new wxWidgetCocoaImpl(mediactrl,view);
#endif
mediactrl->SetPeer(impl);
m_ctrl = mediactrl;
return true;
}
bool wxAVMediaBackend::Load(const wxString& fileName)
{
return Load(
wxURI(
wxString( wxT("file://") ) + fileName
)
);
}
bool wxAVMediaBackend::Load(const wxURI& location)
{
wxCFStringRef uri(location.BuildURI());
NSURL *url = [NSURL URLWithString: uri.AsNSString()];
AVAsset* asset = [AVAsset assetWithURL:url];
if (! asset )
return false;
if ( [asset isPlayable] )
{
AVPlayerItem *playerItem = [AVPlayerItem playerItemWithAsset:asset];
[m_player replaceCurrentItemWithPlayerItem:playerItem];
return playerItem != nil;
}
return false;
}
void wxAVMediaBackend::FinishLoad()
{
DoShowPlayerControls(m_interfaceflags);
AVPlayerItem *playerItem = [m_player currentItem];
CGSize s = [playerItem presentationSize];
m_bestSize = wxSize(s.width, s.height);
NotifyMovieLoaded();
}
bool wxAVMediaBackend::Play()
{
[m_player play];
return true;
}
bool wxAVMediaBackend::Pause()
{
[m_player pause];
return true;
}
bool wxAVMediaBackend::Stop()
{
[m_player pause];
[m_player seekToTime:kCMTimeZero];
return true;
}
double wxAVMediaBackend::GetVolume()
{
return [m_player volume];
}
bool wxAVMediaBackend::SetVolume(double dVolume)
{
[m_player setVolume:dVolume];
return true;
}
double wxAVMediaBackend::GetPlaybackRate()
{
return [m_player rate];
}
bool wxAVMediaBackend::SetPlaybackRate(double dRate)
{
[m_player setRate:dRate];
return true;
}
bool wxAVMediaBackend::SetPosition(wxLongLong where)
{
[m_player seekToTime:CMTimeMakeWithSeconds(where.GetValue() / 1000.0, 1)
toleranceBefore:kCMTimeZero toleranceAfter:kCMTimeZero];
return true;
}
wxLongLong wxAVMediaBackend::GetPosition()
{
return CMTimeGetSeconds([m_player currentTime])*1000.0;
}
wxLongLong wxAVMediaBackend::GetDuration()
{
AVPlayerItem *playerItem = [m_player currentItem];
if ([playerItem status] == AVPlayerItemStatusReadyToPlay)
return CMTimeGetSeconds([[playerItem asset] duration])*1000.0;
else
return 0.f;
}
wxMediaState wxAVMediaBackend::GetState()
{
if ( [m_player isPlaying] )
return wxMEDIASTATE_PLAYING;
else
{
if ( GetPosition() == 0 )
return wxMEDIASTATE_STOPPED;
else
return wxMEDIASTATE_PAUSED;
}
}
void wxAVMediaBackend::Cleanup()
{
[m_player pause];
[m_player release];
m_player = nil;
}
wxSize wxAVMediaBackend::GetVideoSize() const
{
return m_bestSize;
}
void wxAVMediaBackend::Move(int x, int y, int w, int h)
{
// as we have a native player, no need to move the video area
}
bool wxAVMediaBackend::ShowPlayerControls(wxMediaCtrlPlayerControls flags)
{
if ( m_interfaceflags != flags )
DoShowPlayerControls(flags);
m_interfaceflags = flags;
return true;
}
void wxAVMediaBackend::DoShowPlayerControls(wxMediaCtrlPlayerControls flags)
{
#if wxOSX_USE_AVKIT
NSView* view = m_ctrl->GetHandle();
if ( [view isKindOfClass:[wxAVPlayerView class]] )
{
wxAVPlayerView* playerView = (wxAVPlayerView*) view;
if (flags == wxMEDIACTRLPLAYERCONTROLS_NONE )
playerView.controlsStyle = AVPlayerViewControlsStyleNone;
else
playerView.controlsStyle = AVPlayerViewControlsStyleDefault;
}
#endif
}
#endif
//in source file that contains stuff you don't directly use
#include "wx/html/forcelnk.h"
FORCE_LINK_ME(basewxmediabackends);