diff options
author | Qt Forward Merge Bot <qt_forward_merge_bot@qt-project.org> | 2020-03-18 11:54:53 +0100 |
---|---|---|
committer | Qt Forward Merge Bot <qt_forward_merge_bot@qt-project.org> | 2020-03-18 11:54:53 +0100 |
commit | 432e929e644097b25060f85b1e089f2943577bc9 (patch) | |
tree | 9a0cf5abcc77b85ee7aa88f875cb5dc097ab667c /src/plugins | |
parent | 4ad0484b825524bcbb74145ac4e63bdd6274ce6a (diff) | |
parent | 69837e6e04ae125186a8deaac59d82607fcd6d1a (diff) |
Merge remote-tracking branch 'origin/5.15' into dev
Change-Id: I21c230900111b4881b40c451bffc3d5c2101111b
Diffstat (limited to 'src/plugins')
14 files changed, 187 insertions, 66 deletions
diff --git a/src/plugins/alsa/qalsaaudiooutput.cpp b/src/plugins/alsa/qalsaaudiooutput.cpp index 5c8ae171c..ee5aee989 100644 --- a/src/plugins/alsa/qalsaaudiooutput.cpp +++ b/src/plugins/alsa/qalsaaudiooutput.cpp @@ -707,7 +707,7 @@ bool QAlsaAudioOutput::deviceReady() if(l > 0) { // Got some data to output - if(deviceState != QAudio::ActiveState) + if (deviceState != QAudio::ActiveState && deviceState != QAudio::IdleState) return true; qint64 bytesWritten = write(audioBuffer,l); if (bytesWritten != l) diff --git a/src/plugins/android/src/mediaplayer/qandroidmetadatareadercontrol.cpp b/src/plugins/android/src/mediaplayer/qandroidmetadatareadercontrol.cpp index ef86af896..66eafc765 100644 --- a/src/plugins/android/src/mediaplayer/qandroidmetadatareadercontrol.cpp +++ b/src/plugins/android/src/mediaplayer/qandroidmetadatareadercontrol.cpp @@ -176,12 +176,12 @@ void QAndroidMetaDataReaderControl::extractMetadata(QAndroidMetaDataReaderContro if (!string.isNull()) { metadata.insert(isVideo ? QMediaMetaData::LeadPerformer : QMediaMetaData::ContributingArtist, - string.split('/', QString::SkipEmptyParts)); + string.split('/', Qt::SkipEmptyParts)); } string = retriever.extractMetadata(AndroidMediaMetadataRetriever::Author); if (!string.isNull()) - metadata.insert(QMediaMetaData::Author, string.split('/', QString::SkipEmptyParts)); + metadata.insert(QMediaMetaData::Author, string.split('/', Qt::SkipEmptyParts)); string = retriever.extractMetadata(AndroidMediaMetadataRetriever::Bitrate); if (!string.isNull()) { @@ -196,7 +196,7 @@ void QAndroidMetaDataReaderControl::extractMetadata(QAndroidMetaDataReaderContro string = retriever.extractMetadata(AndroidMediaMetadataRetriever::Composer); if (!string.isNull()) - metadata.insert(QMediaMetaData::Composer, string.split('/', QString::SkipEmptyParts)); + metadata.insert(QMediaMetaData::Composer, string.split('/', Qt::SkipEmptyParts)); string = retriever.extractMetadata(AndroidMediaMetadataRetriever::Date); if (!string.isNull()) @@ -231,7 +231,7 @@ void QAndroidMetaDataReaderControl::extractMetadata(QAndroidMetaDataReaderContro string = retriever.extractMetadata(AndroidMediaMetadataRetriever::Writer); if (!string.isNull()) - metadata.insert(QMediaMetaData::Writer, string.split('/', QString::SkipEmptyParts)); + metadata.insert(QMediaMetaData::Writer, string.split('/', Qt::SkipEmptyParts)); string = retriever.extractMetadata(AndroidMediaMetadataRetriever::Year); if (!string.isNull()) diff --git a/src/plugins/android/src/wrappers/jni/androidmediaplayer.cpp b/src/plugins/android/src/wrappers/jni/androidmediaplayer.cpp index f899481f0..de8422b86 100644 --- a/src/plugins/android/src/wrappers/jni/androidmediaplayer.cpp +++ b/src/plugins/android/src/wrappers/jni/androidmediaplayer.cpp @@ -271,7 +271,7 @@ void AndroidMediaPlayer::setAudioRole(QAudio::Role role) void AndroidMediaPlayer::setCustomAudioRole(const QString &role) { - QStringList roles = role.split(",", QString::SkipEmptyParts); + QStringList roles = role.split(",", Qt::SkipEmptyParts); int type = 0; // CONTENT_TYPE_UNKNOWN int usage = 0; // USAGE_UNKNOWN diff --git a/src/plugins/avfoundation/camera/avfcamerarenderercontrol.mm b/src/plugins/avfoundation/camera/avfcamerarenderercontrol.mm index 0359f5d0a..9e1bf3f84 100644 --- a/src/plugins/avfoundation/camera/avfcamerarenderercontrol.mm +++ b/src/plugins/avfoundation/camera/avfcamerarenderercontrol.mm @@ -297,11 +297,9 @@ void AVFCameraRendererControl::setSurface(QAbstractVideoSurface *surface) { if (m_surface != surface) { m_surface = surface; -#ifdef Q_OS_IOS m_supportsTextures = m_surface - ? m_surface->supportedPixelFormats(QAbstractVideoBuffer::GLTextureHandle).contains(QVideoFrame::Format_BGRA32) + ? !m_surface->supportedPixelFormats(QAbstractVideoBuffer::GLTextureHandle).isEmpty() : false; -#endif Q_EMIT surfaceChanged(surface); } } diff --git a/src/plugins/avfoundation/camera/avfcamerasession.mm b/src/plugins/avfoundation/camera/avfcamerasession.mm index a3263badc..3c5f8f09a 100644 --- a/src/plugins/avfoundation/camera/avfcamerasession.mm +++ b/src/plugins/avfoundation/camera/avfcamerasession.mm @@ -408,7 +408,8 @@ bool AVFCameraSession::applyViewfinderSettings() vfSettings.setResolution(imageResolution); } - return vfControl->applySettings(vfSettings); + vfControl->applySettings(vfSettings); + return !vfSettings.isNull(); } return false; diff --git a/src/plugins/avfoundation/camera/avfcamerautility.h b/src/plugins/avfoundation/camera/avfcamerautility.h index 370302b1c..33956fc8a 100644 --- a/src/plugins/avfoundation/camera/avfcamerautility.h +++ b/src/plugins/avfoundation/camera/avfcamerautility.h @@ -161,7 +161,7 @@ QSize qt_device_format_high_resolution(AVCaptureDeviceFormat *format); QSize qt_device_format_pixel_aspect_ratio(AVCaptureDeviceFormat *format); QVector<AVFPSRange> qt_device_format_framerates(AVCaptureDeviceFormat *format); AVCaptureDeviceFormat *qt_find_best_resolution_match(AVCaptureDevice *captureDevice, const QSize &res, - FourCharCode preferredFormat); + FourCharCode preferredFormat, bool stillImage = true); AVCaptureDeviceFormat *qt_find_best_framerate_match(AVCaptureDevice *captureDevice, FourCharCode preferredFormat, Float64 fps); diff --git a/src/plugins/avfoundation/camera/avfcamerautility.mm b/src/plugins/avfoundation/camera/avfcamerautility.mm index 8c743dcbc..25ccc4b01 100644 --- a/src/plugins/avfoundation/camera/avfcamerautility.mm +++ b/src/plugins/avfoundation/camera/avfcamerautility.mm @@ -239,7 +239,8 @@ QSize qt_device_format_pixel_aspect_ratio(AVCaptureDeviceFormat *format) AVCaptureDeviceFormat *qt_find_best_resolution_match(AVCaptureDevice *captureDevice, const QSize &request, - FourCharCode filter) + FourCharCode filter, + bool stillImage) { Q_ASSERT(captureDevice); Q_ASSERT(!request.isNull() && request.isValid()); @@ -254,7 +255,7 @@ AVCaptureDeviceFormat *qt_find_best_resolution_match(AVCaptureDevice *captureDev if (qt_device_format_resolution(format) == request) return format; // iOS only (still images). - if (qt_device_format_high_resolution(format) == request) + if (stillImage && qt_device_format_high_resolution(format) == request) return format; } @@ -272,7 +273,7 @@ AVCaptureDeviceFormat *qt_find_best_resolution_match(AVCaptureDevice *captureDev if (!res.isNull() && res.isValid() && qt_area_sane(res)) pairs << FormatPair(res, format); const QSize highRes(qt_device_format_high_resolution(format)); - if (!highRes.isNull() && highRes.isValid() && qt_area_sane(highRes)) + if (stillImage && !highRes.isNull() && highRes.isValid() && qt_area_sane(highRes)) pairs << FormatPair(highRes, format); } diff --git a/src/plugins/avfoundation/camera/avfcameraviewfindersettingscontrol.mm b/src/plugins/avfoundation/camera/avfcameraviewfindersettingscontrol.mm index 91f3cb7dc..dd0393f96 100644 --- a/src/plugins/avfoundation/camera/avfcameraviewfindersettingscontrol.mm +++ b/src/plugins/avfoundation/camera/avfcameraviewfindersettingscontrol.mm @@ -185,6 +185,16 @@ void AVFCameraViewfinderSettingsControl2::setViewfinderSettings(const QCameraVie return; m_settings = settings; +#if defined(Q_OS_IOS) + bool active = m_service->session()->state() == QCamera::ActiveState; + if (active) + [m_service->session()->captureSession() beginConfiguration]; + applySettings(m_settings); + if (active) + [m_service->session()->captureSession() commitConfiguration]; +#else + applySettings(m_settings); +#endif } QVideoFrame::PixelFormat AVFCameraViewfinderSettingsControl2::QtPixelFormatFromCVFormat(unsigned avPixelFormat) @@ -263,7 +273,7 @@ AVCaptureDeviceFormat *AVFCameraViewfinderSettingsControl2::findBestFormatMatch( // Either the exact match (including high resolution for images on iOS) // or a format with a resolution close to the requested one. return qt_find_best_resolution_match(captureDevice, resolution, - m_service->session()->defaultCodec()); + m_service->session()->defaultCodec(), false); } // No resolution requested, what about framerates? @@ -331,7 +341,10 @@ bool AVFCameraViewfinderSettingsControl2::convertPixelFormatIfSupported(QVideoFr if (m_service->videoOutput()->surface()) { const QAbstractVideoSurface *surface = m_service->videoOutput()->surface(); - if (!surface->supportedPixelFormats().contains(qtFormat)) + QAbstractVideoBuffer::HandleType h = m_service->videoOutput()->supportsTextures() + ? QAbstractVideoBuffer::GLTextureHandle + : QAbstractVideoBuffer::NoHandle; + if (!surface->supportedPixelFormats(h).contains(qtFormat)) return false; } @@ -379,21 +392,19 @@ bool AVFCameraViewfinderSettingsControl2::applySettings(const QCameraViewfinderS // format, or if no surface is set, the preferred capture device format const QVector<QVideoFrame::PixelFormat> deviceFormats = viewfinderPixelFormats(); - QVideoFrame::PixelFormat pickedFormat = deviceFormats.first(); - QAbstractVideoSurface *surface = m_service->videoOutput()->surface(); + QVideoFrame::PixelFormat pickedFormat = deviceFormats.first(); if (surface) { - if (m_service->videoOutput()->supportsTextures()) { - pickedFormat = QVideoFrame::Format_ARGB32; - } else { - QList<QVideoFrame::PixelFormat> surfaceFormats = surface->supportedPixelFormats(); - - for (int i = 0; i < surfaceFormats.count(); ++i) { - const QVideoFrame::PixelFormat surfaceFormat = surfaceFormats.at(i); - if (deviceFormats.contains(surfaceFormat)) { - pickedFormat = surfaceFormat; - break; - } + pickedFormat = QVideoFrame::Format_Invalid; + QAbstractVideoBuffer::HandleType h = m_service->videoOutput()->supportsTextures() + ? QAbstractVideoBuffer::GLTextureHandle + : QAbstractVideoBuffer::NoHandle; + QList<QVideoFrame::PixelFormat> surfaceFormats = surface->supportedPixelFormats(h); + for (int i = 0; i < surfaceFormats.count(); ++i) { + const QVideoFrame::PixelFormat surfaceFormat = surfaceFormats.at(i); + if (deviceFormats.contains(surfaceFormat)) { + pickedFormat = surfaceFormat; + break; } } } @@ -401,13 +412,15 @@ bool AVFCameraViewfinderSettingsControl2::applySettings(const QCameraViewfinderS CVPixelFormatFromQtFormat(pickedFormat, avfPixelFormat); } - if (avfPixelFormat != 0) { - NSMutableDictionary *videoSettings = [NSMutableDictionary dictionaryWithCapacity:1]; - [videoSettings setObject:[NSNumber numberWithUnsignedInt:avfPixelFormat] - forKey:(id)kCVPixelBufferPixelFormatTypeKey]; + NSMutableDictionary *videoSettings = [NSMutableDictionary dictionaryWithCapacity:1]; + [videoSettings setObject:[NSNumber numberWithUnsignedInt:avfPixelFormat] + forKey:(id)kCVPixelBufferPixelFormatTypeKey]; - videoOutput.videoSettings = videoSettings; - } + const AVFConfigurationLock lock(captureDevice); + if (!lock) + qWarning("Failed to set active format (lock failed)"); + + videoOutput.videoSettings = videoSettings; } qt_set_framerate_limits(captureDevice, videoConnection(), settings.minimumFrameRate(), settings.maximumFrameRate()); diff --git a/src/plugins/avfoundation/mediaplayer/avfmediaplayersession.h b/src/plugins/avfoundation/mediaplayer/avfmediaplayersession.h index 7a268a3d9..db29e88aa 100644 --- a/src/plugins/avfoundation/mediaplayer/avfmediaplayersession.h +++ b/src/plugins/avfoundation/mediaplayer/avfmediaplayersession.h @@ -67,7 +67,7 @@ public: QMediaPlayer::MediaStatus mediaStatus() const; QMediaContent media() const; - const QIODevice *mediaStream() const; + QIODevice *mediaStream() const; void setMedia(const QMediaContent &content, QIODevice *stream); qint64 position() const; @@ -110,6 +110,9 @@ public Q_SLOTS: void processDurationChange(qint64 duration); + void streamReady(); + void streamDestroyed(); + Q_SIGNALS: void positionChanged(qint64 position); void durationChanged(qint64 duration); @@ -128,6 +131,7 @@ private: void setAudioAvailable(bool available); void setVideoAvailable(bool available); void setSeekable(bool seekable); + void resetStream(QIODevice *stream = nullptr); AVFMediaPlayerService *m_service; AVFVideoOutput *m_videoOutput; diff --git a/src/plugins/avfoundation/mediaplayer/avfmediaplayersession.mm b/src/plugins/avfoundation/mediaplayer/avfmediaplayersession.mm index 3e3736183..424f30008 100644 --- a/src/plugins/avfoundation/mediaplayer/avfmediaplayersession.mm +++ b/src/plugins/avfoundation/mediaplayer/avfmediaplayersession.mm @@ -42,6 +42,7 @@ #include "avfvideooutput.h" #include <qpointer.h> +#include <QFileInfo> #import <AVFoundation/AVFoundation.h> @@ -66,7 +67,7 @@ static void *AVFMediaPlayerSessionObserverBufferLikelyToKeepUpContext = &AVFMedi static void *AVFMediaPlayerSessionObserverCurrentItemObservationContext = &AVFMediaPlayerSessionObserverCurrentItemObservationContext; static void *AVFMediaPlayerSessionObserverCurrentItemDurationObservationContext = &AVFMediaPlayerSessionObserverCurrentItemDurationObservationContext; -@interface AVFMediaPlayerSessionObserver : NSObject +@interface AVFMediaPlayerSessionObserver : NSObject<AVAssetResourceLoaderDelegate> @property (readonly, getter=player) AVPlayer* m_player; @property (readonly, getter=playerItem) AVPlayerItem* m_playerItem; @@ -74,7 +75,7 @@ static void *AVFMediaPlayerSessionObserverCurrentItemDurationObservationContext @property (readonly, getter=session) AVFMediaPlayerSession* m_session; - (AVFMediaPlayerSessionObserver *) initWithMediaPlayerSession:(AVFMediaPlayerSession *)session; -- (void) setURL:(NSURL *)url; +- (void) setURL:(NSURL *)url mimeType:(NSString *)mimeType; - (void) unloadMedia; - (void) prepareToPlayAsset:(AVURLAsset *)asset withKeys:(NSArray *)requestedKeys; - (void) assetFailedToPrepareForPlayback:(NSError *)error; @@ -84,6 +85,7 @@ static void *AVFMediaPlayerSessionObserverCurrentItemDurationObservationContext change:(NSDictionary *)change context:(void *)context; - (void) detatchSession; - (void) dealloc; +- (BOOL) resourceLoader:(AVAssetResourceLoader *)resourceLoader shouldWaitForLoadingOfRequestedResource:(AVAssetResourceLoadingRequest *)loadingRequest; @end @implementation AVFMediaPlayerSessionObserver @@ -95,6 +97,8 @@ static void *AVFMediaPlayerSessionObserverCurrentItemDurationObservationContext AVPlayerLayer *m_playerLayer; NSURL *m_URL; BOOL m_bufferIsLikelyToKeepUp; + NSData *m_data; + NSString *m_mimeType; } @synthesize m_player, m_playerItem, m_playerLayer, m_session; @@ -109,8 +113,11 @@ static void *AVFMediaPlayerSessionObserverCurrentItemDurationObservationContext return self; } -- (void) setURL:(NSURL *)url +- (void) setURL:(NSURL *)url mimeType:(NSString *)mimeType { + [m_mimeType release]; + m_mimeType = [mimeType retain]; + if (m_URL != url) { [m_URL release]; @@ -122,6 +129,8 @@ static void *AVFMediaPlayerSessionObserverCurrentItemDurationObservationContext // use __block to avoid maintaining strong references on variables captured by the // following block callback __block AVURLAsset *asset = [[AVURLAsset URLAssetWithURL:m_URL options:nil] retain]; + [asset.resourceLoader setDelegate:self queue:dispatch_get_main_queue()]; + __block NSArray *requestedKeys = [[NSArray arrayWithObjects:AVF_TRACKS_KEY, AVF_PLAYABLE_KEY, nil] retain]; __block AVFMediaPlayerSessionObserver *blockSelf = self; @@ -403,9 +412,48 @@ static void *AVFMediaPlayerSessionObserverCurrentItemDurationObservationContext [m_URL release]; } + [m_mimeType release]; [super dealloc]; } +- (BOOL) resourceLoader:(AVAssetResourceLoader *)resourceLoader shouldWaitForLoadingOfRequestedResource:(AVAssetResourceLoadingRequest *)loadingRequest +{ + Q_UNUSED(resourceLoader); + + if (![loadingRequest.request.URL.scheme isEqualToString:@"iodevice"]) + return NO; + + QIODevice *device = m_session->mediaStream(); + if (!device) + return NO; + + device->seek(loadingRequest.dataRequest.requestedOffset); + if (loadingRequest.contentInformationRequest) { + loadingRequest.contentInformationRequest.contentType = m_mimeType; + loadingRequest.contentInformationRequest.contentLength = device->size(); + loadingRequest.contentInformationRequest.byteRangeAccessSupported = YES; + } + + if (loadingRequest.dataRequest) { + NSInteger requestedLength = loadingRequest.dataRequest.requestedLength; + int maxBytes = qMin(32 * 1064, int(requestedLength)); + char buffer[maxBytes]; + NSInteger submitted = 0; + while (submitted < requestedLength) { + qint64 len = device->read(buffer, maxBytes); + if (len < 1) + break; + + [loadingRequest.dataRequest respondWithData:[NSData dataWithBytes:buffer length:len]]; + submitted += len; + } + + // Finish loading even if not all bytes submitted. + [loadingRequest finishLoading]; + } + + return YES; +} @end AVFMediaPlayerSession::AVFMediaPlayerSession(AVFMediaPlayerService *service, QObject *parent) @@ -483,11 +531,23 @@ QMediaContent AVFMediaPlayerSession::media() const return m_resources; } -const QIODevice *AVFMediaPlayerSession::mediaStream() const +QIODevice *AVFMediaPlayerSession::mediaStream() const { return m_mediaStream; } +static void setURL(void *observer, const QString &url, const QString &mimeType = QString()) +{ + NSString *urlString = [NSString stringWithUTF8String:url.toUtf8().constData()]; + NSURL *nsurl = [NSURL URLWithString:urlString]; + [static_cast<AVFMediaPlayerSessionObserver*>(observer) setURL:nsurl mimeType:[NSString stringWithUTF8String:mimeType.toLatin1().constData()]]; +} + +static void setStreamURL(void *observer, const QString &url) +{ + setURL(observer, QLatin1String("iodevice://") + url, QFileInfo(url).suffix()); +} + void AVFMediaPlayerSession::setMedia(const QMediaContent &content, QIODevice *stream) { #ifdef QT_DEBUG_AVF @@ -497,7 +557,7 @@ void AVFMediaPlayerSession::setMedia(const QMediaContent &content, QIODevice *st [static_cast<AVFMediaPlayerSessionObserver*>(m_observer) unloadMedia]; m_resources = content; - m_mediaStream = stream; + resetStream(stream); setAudioAvailable(false); setVideoAvailable(false); @@ -508,7 +568,7 @@ void AVFMediaPlayerSession::setMedia(const QMediaContent &content, QIODevice *st const QMediaPlayer::MediaStatus oldMediaStatus = m_mediaStatus; const QMediaPlayer::State oldState = m_state; - if (content.isNull() || content.request().url().isEmpty()) { + if (!m_mediaStream && (content.isNull() || content.request().url().isEmpty())) { m_mediaStatus = QMediaPlayer::NoMedia; if (m_mediaStatus != oldMediaStatus) Q_EMIT mediaStatusChanged(m_mediaStatus); @@ -524,11 +584,16 @@ void AVFMediaPlayerSession::setMedia(const QMediaContent &content, QIODevice *st if (m_mediaStatus != oldMediaStatus) Q_EMIT mediaStatusChanged(m_mediaStatus); - //Load AVURLAsset - //initialize asset using content's URL - NSString *urlString = [NSString stringWithUTF8String:content.request().url().toEncoded().constData()]; - NSURL *url = [NSURL URLWithString:urlString]; - [static_cast<AVFMediaPlayerSessionObserver*>(m_observer) setURL:url]; + if (m_mediaStream) { + // If there is a data, try to load it, + // otherwise wait for readyRead. + if (m_mediaStream->size()) + setStreamURL(m_observer, m_resources.request().url().toString()); + } else { + //Load AVURLAsset + //initialize asset using content's URL + setURL(m_observer, m_resources.request().url().toString()); + } m_state = QMediaPlayer::StoppedState; if (m_state != oldState) @@ -686,7 +751,7 @@ void AVFMediaPlayerSession::setPosition(qint64 pos) CMTime newTime = [playerItem currentTime]; newTime.value = (pos / 1000.0f) * newTime.timescale; - [playerItem seekToTime:newTime]; + [playerItem seekToTime:newTime toleranceBefore:kCMTimeZero toleranceAfter:kCMTimeZero completionHandler:nil]; Q_EMIT positionChanged(pos); @@ -875,9 +940,11 @@ void AVFMediaPlayerSession::processLoadStateChange(QMediaPlayer::State newState) // Get the native size of the video, and reset the bounds of the player layer AVPlayerLayer *playerLayer = [static_cast<AVFMediaPlayerSessionObserver*>(m_observer) playerLayer]; if (videoTrack && playerLayer) { - playerLayer.bounds = CGRectMake(0.0f, 0.0f, - videoTrack.naturalSize.width, - videoTrack.naturalSize.height); + if (!playerLayer.bounds.size.width || !playerLayer.bounds.size.height) { + playerLayer.bounds = CGRectMake(0.0f, 0.0f, + videoTrack.naturalSize.width, + videoTrack.naturalSize.height); + } if (m_videoOutput && newState != QMediaPlayer::StoppedState) { m_videoOutput->setLayer(playerLayer); @@ -928,7 +995,8 @@ void AVFMediaPlayerSession::processBufferStateChange(int bufferStatus) } else if (status == QMediaPlayer::StalledMedia) { status = QMediaPlayer::BufferedMedia; // Resume playback. - [[static_cast<AVFMediaPlayerSessionObserver*>(m_observer) player] setRate:m_rate]; + if (m_state == QMediaPlayer::PlayingState) + [[static_cast<AVFMediaPlayerSessionObserver*>(m_observer) player] setRate:m_rate]; } if (m_mediaStatus != status) @@ -966,3 +1034,28 @@ void AVFMediaPlayerSession::processMediaLoadError() Q_EMIT error(QMediaPlayer::FormatError, tr("Failed to load media")); } + +void AVFMediaPlayerSession::streamReady() +{ + setStreamURL(m_observer, m_resources.request().url().toString()); +} + +void AVFMediaPlayerSession::streamDestroyed() +{ + resetStream(nullptr); +} + +void AVFMediaPlayerSession::resetStream(QIODevice *stream) +{ + if (m_mediaStream) { + disconnect(m_mediaStream, &QIODevice::readyRead, this, &AVFMediaPlayerSession::streamReady); + disconnect(m_mediaStream, &QIODevice::destroyed, this, &AVFMediaPlayerSession::streamDestroyed); + } + + m_mediaStream = stream; + + if (m_mediaStream) { + connect(m_mediaStream, &QIODevice::readyRead, this, &AVFMediaPlayerSession::streamReady); + connect(m_mediaStream, &QIODevice::destroyed, this, &AVFMediaPlayerSession::streamDestroyed); + } +} diff --git a/src/plugins/avfoundation/mediaplayer/avfvideowidget.mm b/src/plugins/avfoundation/mediaplayer/avfvideowidget.mm index be349710c..0987342b4 100644 --- a/src/plugins/avfoundation/mediaplayer/avfvideowidget.mm +++ b/src/plugins/avfoundation/mediaplayer/avfvideowidget.mm @@ -38,12 +38,9 @@ ****************************************************************************/ #include "avfvideowidget.h" -#include <QtCore/QDebug> -#include <AVFoundation/AVFoundation.h> -#include <QtGui/QResizeEvent> -#include <QtGui/QPaintEvent> -#include <QtGui/QPainter> +#import <AVFoundation/AVFoundation.h> +#import <QuartzCore/CATransaction.h> #if defined(Q_OS_MACOS) #import <AppKit/AppKit.h> @@ -51,6 +48,11 @@ #import <UIKit/UIKit.h> #endif +#include <QtCore/QDebug> +#include <QtGui/QResizeEvent> +#include <QtGui/QPaintEvent> +#include <QtGui/QPainter> + QT_USE_NAMESPACE AVFVideoWidget::AVFVideoWidget(QWidget *parent) @@ -178,5 +180,8 @@ void AVFVideoWidget::updateAspectRatio() void AVFVideoWidget::updatePlayerLayerBounds(const QSize &size) { - m_playerLayer.bounds = CGRectMake(0.0f, 0.0f, (float)size.width(), (float)size.height()); + [CATransaction begin]; + [CATransaction setDisableActions: YES]; // disable animation/flicks + m_playerLayer.bounds = QRect(QPoint(0, 0), size).toCGRect(); + [CATransaction commit]; } diff --git a/src/plugins/avfoundation/mediaplayer/avfvideowindowcontrol.mm b/src/plugins/avfoundation/mediaplayer/avfvideowindowcontrol.mm index 7fa41fdc2..d61129ec9 100644 --- a/src/plugins/avfoundation/mediaplayer/avfvideowindowcontrol.mm +++ b/src/plugins/avfoundation/mediaplayer/avfvideowindowcontrol.mm @@ -40,6 +40,7 @@ #include "avfvideowindowcontrol.h" #include <AVFoundation/AVFoundation.h> +#import <QuartzCore/CATransaction.h> #if QT_HAS_INCLUDE(<AppKit/AppKit.h>) #include <AppKit/AppKit.h> @@ -244,10 +245,10 @@ void AVFVideoWindowControl::updateAspectRatio() void AVFVideoWindowControl::updatePlayerLayerBounds() { if (m_playerLayer) { - CGRect newBounds = CGRectMake(0, 0, - m_displayRect.width(), m_displayRect.height()); - m_playerLayer.bounds = newBounds; - m_playerLayer.position = CGPointMake(m_displayRect.x(), m_displayRect.y()); + [CATransaction begin]; + [CATransaction setDisableActions: YES]; // disable animation/flicks + m_playerLayer.frame = m_displayRect.toCGRect(); + [CATransaction commit]; } } diff --git a/src/plugins/gstreamer/camerabin/camerabinsession.cpp b/src/plugins/gstreamer/camerabin/camerabinsession.cpp index 3e505a413..9445bd9d0 100644 --- a/src/plugins/gstreamer/camerabin/camerabinsession.cpp +++ b/src/plugins/gstreamer/camerabin/camerabinsession.cpp @@ -347,10 +347,12 @@ void CameraBinSession::setupCaptureResolution() // If capture resolution is specified, use it also for the viewfinder to avoid caps negotiation // to fail. if (m_usingWrapperCameraBinSrc) { - if (m_captureMode == QCamera::CaptureStillImage && !imageResolution.isEmpty()) - viewfinderResolution = imageResolution; - else if (m_captureMode == QCamera::CaptureVideo && !videoResolution.isEmpty()) - viewfinderResolution = videoResolution; + if (viewfinderResolution.isEmpty()) { + if (m_captureMode == QCamera::CaptureStillImage && !imageResolution.isEmpty()) + viewfinderResolution = imageResolution; + else if (m_captureMode == QCamera::CaptureVideo && !videoResolution.isEmpty()) + viewfinderResolution = videoResolution; + } // Make sure we don't use incompatible frame rate and pixel format with the new resolution if (viewfinderResolution != m_viewfinderSettings.resolution() && diff --git a/src/plugins/wmf/player/mfplayersession.cpp b/src/plugins/wmf/player/mfplayersession.cpp index 10ba25998..24bfda833 100644 --- a/src/plugins/wmf/player/mfplayersession.cpp +++ b/src/plugins/wmf/player/mfplayersession.cpp @@ -288,6 +288,9 @@ MFPlayerSession::MediaType MFPlayerSession::getStreamType(IMFStreamDescriptor *s } } + if (typeHandler) + typeHandler->Release(); + return Unknown; } |