1/****************************************************************************
2**
3** Copyright (C) 2016 The Qt Company Ltd.
4** Contact: https://www.qt.io/licensing/
5**
6** This file is part of the test suite of the Qt Toolkit.
7**
8** $QT_BEGIN_LICENSE:GPL-EXCEPT$
9** Commercial License Usage
10** Licensees holding valid commercial Qt licenses may use this file in
11** accordance with the commercial license agreement provided with the
12** Software or, alternatively, in accordance with the terms contained in
13** a written agreement between you and The Qt Company. For licensing terms
14** and conditions see https://www.qt.io/terms-conditions. For further
15** information use the contact form at https://www.qt.io/contact-us.
16**
17** GNU General Public License Usage
18** Alternatively, this file may be used under the terms of the GNU
19** General Public License version 3 as published by the Free Software
20** Foundation with exceptions as appearing in the file LICENSE.GPL3-EXCEPT
21** included in the packaging of this file. Please review the following
22** information to ensure the GNU General Public License requirements will
23** be met: https://www.gnu.org/licenses/gpl-3.0.html.
24**
25** $QT_END_LICENSE$
26**
27****************************************************************************/
28
29//TESTED_COMPONENT=src/multimedia
30
31#include <QtTest/QtTest>
32
33#include <QtCore/qdebug.h>
34#include <QtCore/qbuffer.h>
35#include <QtNetwork/qnetworkconfiguration.h>
36#include <QtNetwork/qnetworkconfigmanager.h>
37
38#include <qabstractvideosurface.h>
39#include <qmediaplayer.h>
40#include <qmediaplayercontrol.h>
41#include <qmediaplaylist.h>
42#include <qmediaservice.h>
43#include <qmediastreamscontrol.h>
44#include <qmedianetworkaccesscontrol.h>
45#include <qvideorenderercontrol.h>
46
47#include "mockmediaserviceprovider.h"
48#include "mockmediaplayerservice.h"
49#include "mockvideosurface.h"
50
51QT_USE_NAMESPACE
52
53class AutoConnection
54{
55public:
56 AutoConnection(QObject *sender, const char *signal, QObject *receiver, const char *method)
57 : sender(sender), signal(signal), receiver(receiver), method(method)
58 {
59 QObject::connect(sender, signal, receiver, member: method);
60 }
61
62 ~AutoConnection()
63 {
64 QObject::disconnect(sender, signal, receiver, member: method);
65 }
66
67private:
68 QObject *sender;
69 const char *signal;
70 QObject *receiver;
71 const char *method;
72};
73
74class tst_QMediaPlayer: public QObject
75{
76 Q_OBJECT
77
78public slots:
79 void initTestCase();
80 void cleanupTestCase();
81 void init();
82 void cleanup();
83
84private slots:
85 void testNullService_data();
86 void testNullService();
87 void testValid();
88 void testMedia_data();
89 void testMedia();
90 void testDuration_data();
91 void testDuration();
92 void testPosition_data();
93 void testPosition();
94 void testVolume_data();
95 void testVolume();
96 void testMuted_data();
97 void testMuted();
98 void testIsAvailable();
99 void testVideoAvailable_data();
100 void testVideoAvailable();
101 void testBufferStatus_data();
102 void testBufferStatus();
103 void testSeekable_data();
104 void testSeekable();
105 void testPlaybackRate_data();
106 void testPlaybackRate();
107 void testError_data();
108 void testError();
109 void testErrorString_data();
110 void testErrorString();
111 void testService();
112 void testPlay_data();
113 void testPlay();
114 void testPause_data();
115 void testPause();
116 void testStop_data();
117 void testStop();
118 void testMediaStatus_data();
119 void testMediaStatus();
120 void testPlaylist();
121#ifndef QT_NO_BEARERMANAGEMENT
122 void testNetworkAccess();
123#endif
124 void testSetVideoOutput();
125 void testSetVideoOutputNoService();
126 void testSetVideoOutputNoControl();
127 void testSetVideoOutputDestruction();
128 void testPositionPropertyWatch();
129 void debugEnums();
130 void testPlayerFlags();
131 void testDestructor();
132 void testSupportedMimeTypes();
133 void testQrc_data();
134 void testQrc();
135 void testAudioRole();
136 void testCustomAudioRole();
137
138private:
139 void setupCommonTestData();
140
141 MockMediaServiceProvider *mockProvider;
142 MockMediaPlayerService *mockService;
143 QMediaPlayer *player;
144};
145
146void tst_QMediaPlayer::setupCommonTestData()
147{
148 QTest::addColumn<bool>(name: "valid");
149 QTest::addColumn<QMediaPlayer::State>(name: "state");
150 QTest::addColumn<QMediaPlayer::MediaStatus>(name: "status");
151 QTest::addColumn<QMediaContent>(name: "mediaContent");
152 QTest::addColumn<qint64>(name: "duration");
153 QTest::addColumn<qint64>(name: "position");
154 QTest::addColumn<bool>(name: "seekable");
155 QTest::addColumn<int>(name: "volume");
156 QTest::addColumn<bool>(name: "muted");
157 QTest::addColumn<bool>(name: "videoAvailable");
158 QTest::addColumn<int>(name: "bufferStatus");
159 QTest::addColumn<qreal>(name: "playbackRate");
160 QTest::addColumn<QMediaPlayer::Error>(name: "error");
161 QTest::addColumn<QString>(name: "errorString");
162
163 QTest::newRow(dataTag: "invalid") << false << QMediaPlayer::StoppedState << QMediaPlayer::UnknownMediaStatus <<
164 QMediaContent() << qint64(0) << qint64(0) << false << 0 << false << false << 0 <<
165 qreal(0) << QMediaPlayer::NoError << QString();
166 QTest::newRow(dataTag: "valid+null") << true << QMediaPlayer::StoppedState << QMediaPlayer::UnknownMediaStatus <<
167 QMediaContent() << qint64(0) << qint64(0) << false << 0 << false << false << 50 <<
168 qreal(0) << QMediaPlayer::NoError << QString();
169 QTest::newRow(dataTag: "valid+content+stopped") << true << QMediaPlayer::StoppedState << QMediaPlayer::UnknownMediaStatus <<
170 QMediaContent(QUrl("file:///some.mp3")) << qint64(0) << qint64(0) << false << 50 << false << false << 0 <<
171 qreal(1) << QMediaPlayer::NoError << QString();
172 QTest::newRow(dataTag: "valid+content+playing") << true << QMediaPlayer::PlayingState << QMediaPlayer::LoadedMedia <<
173 QMediaContent(QUrl("file:///some.mp3")) << qint64(10000) << qint64(10) << true << 50 << true << false << 0 <<
174 qreal(1) << QMediaPlayer::NoError << QString();
175 QTest::newRow(dataTag: "valid+content+paused") << true << QMediaPlayer::PausedState << QMediaPlayer::LoadedMedia <<
176 QMediaContent(QUrl("file:///some.mp3")) << qint64(10000) << qint64(10) << true << 50 << true << false << 0 <<
177 qreal(1) << QMediaPlayer::NoError << QString();
178 QTest::newRow(dataTag: "valud+streaming") << true << QMediaPlayer::PlayingState << QMediaPlayer::LoadedMedia <<
179 QMediaContent(QUrl("http://example.com/stream")) << qint64(10000) << qint64(10000) << false << 50 << false << true << 0 <<
180 qreal(1) << QMediaPlayer::NoError << QString();
181 QTest::newRow(dataTag: "valid+error") << true << QMediaPlayer::StoppedState << QMediaPlayer::UnknownMediaStatus <<
182 QMediaContent(QUrl("http://example.com/stream")) << qint64(0) << qint64(0) << false << 50 << false << false << 0 <<
183 qreal(0) << QMediaPlayer::ResourceError << QString("Resource unavailable");
184}
185
186void tst_QMediaPlayer::initTestCase()
187{
188 qRegisterMetaType<QMediaPlayer::State>(typeName: "QMediaPlayer::State");
189 qRegisterMetaType<QMediaPlayer::Error>(typeName: "QMediaPlayer::Error");
190 qRegisterMetaType<QMediaPlayer::MediaStatus>(typeName: "QMediaPlayer::MediaStatus");
191 qRegisterMetaType<QMediaContent>(typeName: "QMediaContent");
192}
193
194void tst_QMediaPlayer::cleanupTestCase()
195{
196}
197
198void tst_QMediaPlayer::init()
199{
200 mockService = new MockMediaPlayerService;
201 mockProvider = new MockMediaServiceProvider(mockService);
202 QMediaServiceProvider::setDefaultServiceProvider(mockProvider);
203
204 player = new QMediaPlayer;
205}
206
207void tst_QMediaPlayer::cleanup()
208{
209 delete player;
210 delete mockProvider;
211 delete mockService;
212}
213
214void tst_QMediaPlayer::testNullService_data()
215{
216 setupCommonTestData();
217}
218
219void tst_QMediaPlayer::testNullService()
220{
221 mockProvider->service = 0;
222 QMediaPlayer player;
223
224 const QIODevice *nullDevice = 0;
225
226 QCOMPARE(player.media(), QMediaContent());
227 QCOMPARE(player.mediaStream(), nullDevice);
228 QCOMPARE(player.state(), QMediaPlayer::StoppedState);
229 QCOMPARE(player.mediaStatus(), QMediaPlayer::UnknownMediaStatus);
230 QCOMPARE(player.duration(), qint64(-1));
231 QCOMPARE(player.position(), qint64(0));
232 QCOMPARE(player.volume(), 0);
233 QCOMPARE(player.isMuted(), false);
234 QCOMPARE(player.isVideoAvailable(), false);
235 QCOMPARE(player.bufferStatus(), 0);
236 QCOMPARE(player.isSeekable(), false);
237 QCOMPARE(player.playbackRate(), qreal(0));
238 QCOMPARE(player.error(), QMediaPlayer::ServiceMissingError);
239 QCOMPARE(player.isAvailable(), false);
240 QCOMPARE(player.availability(), QMultimedia::ServiceMissing);
241
242 {
243 QFETCH(QMediaContent, mediaContent);
244
245 QSignalSpy spy(&player, SIGNAL(currentMediaChanged(QMediaContent)));
246 QFile file;
247
248 player.setMedia(media: mediaContent, stream: &file);
249 QCOMPARE(player.currentMedia(), QMediaContent());
250 QCOMPARE(player.media(), mediaContent);
251 QCOMPARE(player.mediaStream(), nullDevice);
252 QCOMPARE(spy.count(), 0);
253 } {
254 QSignalSpy stateSpy(&player, SIGNAL(stateChanged(QMediaPlayer::State)));
255 QSignalSpy statusSpy(&player, SIGNAL(mediaStatusChanged(QMediaPlayer::MediaStatus)));
256
257 player.play();
258 QCOMPARE(player.state(), QMediaPlayer::StoppedState);
259 QCOMPARE(player.mediaStatus(), QMediaPlayer::UnknownMediaStatus);
260 QCOMPARE(stateSpy.count(), 0);
261 QCOMPARE(statusSpy.count(), 0);
262
263 player.pause();
264 QCOMPARE(player.state(), QMediaPlayer::StoppedState);
265 QCOMPARE(player.mediaStatus(), QMediaPlayer::UnknownMediaStatus);
266 QCOMPARE(stateSpy.count(), 0);
267 QCOMPARE(statusSpy.count(), 0);
268
269 player.stop();
270 QCOMPARE(player.state(), QMediaPlayer::StoppedState);
271 QCOMPARE(player.mediaStatus(), QMediaPlayer::UnknownMediaStatus);
272 QCOMPARE(stateSpy.count(), 0);
273 QCOMPARE(statusSpy.count(), 0);
274 } {
275 QFETCH(int, volume);
276 QFETCH(bool, muted);
277
278 QSignalSpy volumeSpy(&player, SIGNAL(volumeChanged(int)));
279 QSignalSpy mutingSpy(&player, SIGNAL(mutedChanged(bool)));
280
281 player.setVolume(volume);
282 QCOMPARE(player.volume(), 0);
283 QCOMPARE(volumeSpy.count(), 0);
284
285 player.setMuted(muted);
286 QCOMPARE(player.isMuted(), false);
287 QCOMPARE(mutingSpy.count(), 0);
288 } {
289 QFETCH(qint64, position);
290
291 QSignalSpy spy(&player, SIGNAL(positionChanged(qint64)));
292
293 player.setPosition(position);
294 QCOMPARE(player.position(), qint64(0));
295 QCOMPARE(spy.count(), 0);
296 } {
297 QFETCH(qreal, playbackRate);
298
299 QSignalSpy spy(&player, SIGNAL(playbackRateChanged(qreal)));
300
301 player.setPlaybackRate(playbackRate);
302 QCOMPARE(player.playbackRate(), qreal(0));
303 QCOMPARE(spy.count(), 0);
304 } {
305 QMediaPlaylist playlist;
306 player.setPlaylist(&playlist);
307
308 QSignalSpy mediaSpy(&player, SIGNAL(mediaChanged(QMediaContent)));
309 QSignalSpy statusSpy(&player, SIGNAL(mediaStatusChanged(QMediaPlayer::MediaStatus)));
310
311 playlist.addMedia(content: QUrl("http://example.com/stream"));
312 playlist.addMedia(content: QUrl("file:///some.mp3"));
313
314 playlist.setCurrentIndex(0);
315 QCOMPARE(playlist.currentIndex(), 0);
316 QCOMPARE(player.currentMedia(), QMediaContent());
317 QCOMPARE(player.media().playlist(), &playlist);
318 QCOMPARE(mediaSpy.count(), 0);
319 QCOMPARE(statusSpy.count(), 0);
320
321 playlist.next();
322 QCOMPARE(playlist.currentIndex(), 1);
323 QCOMPARE(player.currentMedia(), QMediaContent());
324 QCOMPARE(player.media().playlist(), &playlist);
325 QCOMPARE(mediaSpy.count(), 0);
326 QCOMPARE(statusSpy.count(), 0);
327 }
328}
329
330void tst_QMediaPlayer::testValid()
331{
332 /*
333 QFETCH(bool, valid);
334
335 mockService->setIsValid(valid);
336 QCOMPARE(player->isValid(), valid);
337 */
338}
339
340void tst_QMediaPlayer::testMedia_data()
341{
342 setupCommonTestData();
343}
344
345void tst_QMediaPlayer::testMedia()
346{
347 QFETCH(QMediaContent, mediaContent);
348
349 mockService->setMedia(mediaContent);
350 QCOMPARE(player->currentMedia(), mediaContent);
351
352 QBuffer stream;
353 player->setMedia(media: mediaContent, stream: &stream);
354 QCOMPARE(player->currentMedia(), mediaContent);
355 QCOMPARE((QBuffer*)player->mediaStream(), &stream);
356}
357
358void tst_QMediaPlayer::testDuration_data()
359{
360 setupCommonTestData();
361}
362
363void tst_QMediaPlayer::testDuration()
364{
365 QFETCH(qint64, duration);
366
367 mockService->setDuration(duration);
368 QVERIFY(player->duration() == duration);
369}
370
371void tst_QMediaPlayer::testPosition_data()
372{
373 setupCommonTestData();
374}
375
376void tst_QMediaPlayer::testPosition()
377{
378 QFETCH(bool, valid);
379 QFETCH(bool, seekable);
380 QFETCH(qint64, position);
381 QFETCH(qint64, duration);
382
383 mockService->setIsValid(valid);
384 mockService->setSeekable(seekable);
385 mockService->setPosition(position);
386 mockService->setDuration(duration);
387 QVERIFY(player->isSeekable() == seekable);
388 QVERIFY(player->position() == position);
389 QVERIFY(player->duration() == duration);
390
391 if (seekable) {
392 { QSignalSpy spy(player, SIGNAL(positionChanged(qint64)));
393 player->setPosition(position);
394 QCOMPARE(player->position(), position);
395 QCOMPARE(spy.count(), 0); }
396
397 mockService->setPosition(position);
398 { QSignalSpy spy(player, SIGNAL(positionChanged(qint64)));
399 player->setPosition(0);
400 QCOMPARE(player->position(), qint64(0));
401 QCOMPARE(spy.count(), position == 0 ? 0 : 1); }
402
403 mockService->setPosition(position);
404 { QSignalSpy spy(player, SIGNAL(positionChanged(qint64)));
405 player->setPosition(duration);
406 QCOMPARE(player->position(), duration);
407 QCOMPARE(spy.count(), position == duration ? 0 : 1); }
408
409 mockService->setPosition(position);
410 { QSignalSpy spy(player, SIGNAL(positionChanged(qint64)));
411 player->setPosition(-1);
412 QCOMPARE(player->position(), qint64(0));
413 QCOMPARE(spy.count(), position == 0 ? 0 : 1); }
414
415 }
416 else {
417 QSignalSpy spy(player, SIGNAL(positionChanged(qint64)));
418 player->setPosition(position);
419
420 QCOMPARE(player->position(), position);
421 QCOMPARE(spy.count(), 0);
422 }
423}
424
425void tst_QMediaPlayer::testVolume_data()
426{
427 setupCommonTestData();
428}
429
430void tst_QMediaPlayer::testVolume()
431{
432 QFETCH(bool, valid);
433 QFETCH(int, volume);
434
435 mockService->setVolume(volume);
436 QVERIFY(player->volume() == volume);
437
438 if (valid) {
439 { QSignalSpy spy(player, SIGNAL(volumeChanged(int)));
440 player->setVolume(10);
441 QCOMPARE(player->volume(), 10);
442 QCOMPARE(spy.count(), 1); }
443
444 { QSignalSpy spy(player, SIGNAL(volumeChanged(int)));
445 player->setVolume(-1000);
446 QCOMPARE(player->volume(), 0);
447 QCOMPARE(spy.count(), 1); }
448
449 { QSignalSpy spy(player, SIGNAL(volumeChanged(int)));
450 player->setVolume(100);
451 QCOMPARE(player->volume(), 100);
452 QCOMPARE(spy.count(), 1); }
453
454 { QSignalSpy spy(player, SIGNAL(volumeChanged(int)));
455 player->setVolume(1000);
456 QCOMPARE(player->volume(), 100);
457 QCOMPARE(spy.count(), 0); }
458 }
459}
460
461void tst_QMediaPlayer::testMuted_data()
462{
463 setupCommonTestData();
464}
465
466void tst_QMediaPlayer::testMuted()
467{
468 QFETCH(bool, valid);
469 QFETCH(bool, muted);
470 QFETCH(int, volume);
471
472 if (valid) {
473 mockService->setMuted(muted);
474 mockService->setVolume(volume);
475 QVERIFY(player->isMuted() == muted);
476
477 QSignalSpy spy(player, SIGNAL(mutedChanged(bool)));
478 player->setMuted(!muted);
479 QCOMPARE(player->isMuted(), !muted);
480 QCOMPARE(player->volume(), volume);
481 QCOMPARE(spy.count(), 1);
482 }
483}
484
485void tst_QMediaPlayer::testVideoAvailable_data()
486{
487 setupCommonTestData();
488}
489
490void tst_QMediaPlayer::testVideoAvailable()
491{
492 QFETCH(bool, videoAvailable);
493
494 mockService->setVideoAvailable(videoAvailable);
495 QVERIFY(player->isVideoAvailable() == videoAvailable);
496}
497
498void tst_QMediaPlayer::testBufferStatus_data()
499{
500 setupCommonTestData();
501}
502
503void tst_QMediaPlayer::testBufferStatus()
504{
505 QFETCH(int, bufferStatus);
506
507 mockService->setBufferStatus(bufferStatus);
508 QVERIFY(player->bufferStatus() == bufferStatus);
509}
510
511void tst_QMediaPlayer::testSeekable_data()
512{
513 setupCommonTestData();
514}
515
516void tst_QMediaPlayer::testSeekable()
517{
518 QFETCH(bool, seekable);
519
520 mockService->setSeekable(seekable);
521 QVERIFY(player->isSeekable() == seekable);
522}
523
524void tst_QMediaPlayer::testPlaybackRate_data()
525{
526 setupCommonTestData();
527}
528
529void tst_QMediaPlayer::testPlaybackRate()
530{
531 QFETCH(bool, valid);
532 QFETCH(qreal, playbackRate);
533
534 if (valid) {
535 mockService->setPlaybackRate(playbackRate);
536 QVERIFY(player->playbackRate() == playbackRate);
537
538 QSignalSpy spy(player, SIGNAL(playbackRateChanged(qreal)));
539 player->setPlaybackRate(playbackRate + 0.5f);
540 QCOMPARE(player->playbackRate(), playbackRate + 0.5f);
541 QCOMPARE(spy.count(), 1);
542 }
543}
544
545void tst_QMediaPlayer::testError_data()
546{
547 setupCommonTestData();
548}
549
550void tst_QMediaPlayer::testError()
551{
552 QFETCH(QMediaPlayer::Error, error);
553
554 mockService->setError(error);
555 QVERIFY(player->error() == error);
556}
557
558void tst_QMediaPlayer::testErrorString_data()
559{
560 setupCommonTestData();
561}
562
563void tst_QMediaPlayer::testErrorString()
564{
565 QFETCH(QString, errorString);
566
567 mockService->setErrorString(errorString);
568 QVERIFY(player->errorString() == errorString);
569}
570
571void tst_QMediaPlayer::testIsAvailable()
572{
573 QCOMPARE(player->isAvailable(), true);
574 QCOMPARE(player->availability(), QMultimedia::Available);
575}
576
577void tst_QMediaPlayer::testService()
578{
579 /*
580 QFETCH(bool, valid);
581
582 mockService->setIsValid(valid);
583
584 if (valid)
585 QVERIFY(player->service() != 0);
586 else
587 QVERIFY(player->service() == 0);
588 */
589}
590
591void tst_QMediaPlayer::testPlay_data()
592{
593 setupCommonTestData();
594}
595
596void tst_QMediaPlayer::testPlay()
597{
598 QFETCH(bool, valid);
599 QFETCH(QMediaContent, mediaContent);
600 QFETCH(QMediaPlayer::State, state);
601
602 mockService->setIsValid(valid);
603 mockService->setState(state);
604 mockService->setMedia(mediaContent);
605 QVERIFY(player->state() == state);
606 QVERIFY(player->currentMedia() == mediaContent);
607
608 QSignalSpy spy(player, SIGNAL(stateChanged(QMediaPlayer::State)));
609
610 player->play();
611
612 if (!valid || mediaContent.isNull()) {
613 QCOMPARE(player->state(), QMediaPlayer::StoppedState);
614 QCOMPARE(spy.count(), 0);
615 }
616 else {
617 QCOMPARE(player->state(), QMediaPlayer::PlayingState);
618 QCOMPARE(spy.count(), state == QMediaPlayer::PlayingState ? 0 : 1);
619 }
620}
621
622void tst_QMediaPlayer::testPause_data()
623{
624 setupCommonTestData();
625}
626
627void tst_QMediaPlayer::testPause()
628{
629 QFETCH(bool, valid);
630 QFETCH(QMediaContent, mediaContent);
631 QFETCH(QMediaPlayer::State, state);
632
633 mockService->setIsValid(valid);
634 mockService->setState(state);
635 mockService->setMedia(mediaContent);
636 QVERIFY(player->state() == state);
637 QVERIFY(player->currentMedia() == mediaContent);
638
639 QSignalSpy spy(player, SIGNAL(stateChanged(QMediaPlayer::State)));
640
641 player->pause();
642
643 if (!valid || mediaContent.isNull()) {
644 QCOMPARE(player->state(), QMediaPlayer::StoppedState);
645 QCOMPARE(spy.count(), 0);
646 }
647 else {
648 QCOMPARE(player->state(), QMediaPlayer::PausedState);
649 QCOMPARE(spy.count(), state == QMediaPlayer::PausedState ? 0 : 1);
650 }
651}
652
653void tst_QMediaPlayer::testStop_data()
654{
655 setupCommonTestData();
656}
657
658void tst_QMediaPlayer::testStop()
659{
660 QFETCH(QMediaContent, mediaContent);
661 QFETCH(QMediaPlayer::State, state);
662
663 mockService->setState(state);
664 mockService->setMedia(mediaContent);
665 QVERIFY(player->state() == state);
666 QVERIFY(player->currentMedia() == mediaContent);
667
668 QSignalSpy spy(player, SIGNAL(stateChanged(QMediaPlayer::State)));
669
670 player->stop();
671
672 if (mediaContent.isNull() || state == QMediaPlayer::StoppedState) {
673 QCOMPARE(player->state(), QMediaPlayer::StoppedState);
674 QCOMPARE(spy.count(), 0);
675 }
676 else {
677 QCOMPARE(player->state(), QMediaPlayer::StoppedState);
678 QCOMPARE(spy.count(), 1);
679 }
680}
681
682void tst_QMediaPlayer::testMediaStatus_data()
683{
684 setupCommonTestData();
685}
686
687void tst_QMediaPlayer::testMediaStatus()
688{
689 QFETCH(int, bufferStatus);
690 int bufferSignals = 0;
691
692 player->setNotifyInterval(10);
693
694 mockService->setMediaStatus(QMediaPlayer::NoMedia);
695 mockService->setBufferStatus(bufferStatus);
696
697 AutoConnection connection(
698 player, SIGNAL(bufferStatusChanged(int)),
699 &QTestEventLoop::instance(), SLOT(exitLoop()));
700
701 QSignalSpy statusSpy(player, SIGNAL(mediaStatusChanged(QMediaPlayer::MediaStatus)));
702 QSignalSpy bufferSpy(player, SIGNAL(bufferStatusChanged(int)));
703
704 QCOMPARE(player->mediaStatus(), QMediaPlayer::NoMedia);
705
706 mockService->setMediaStatus(QMediaPlayer::LoadingMedia);
707 QCOMPARE(player->mediaStatus(), QMediaPlayer::LoadingMedia);
708 QCOMPARE(statusSpy.count(), 1);
709
710 QCOMPARE(qvariant_cast<QMediaPlayer::MediaStatus>(statusSpy.last().value(0)),
711 QMediaPlayer::LoadingMedia);
712
713 mockService->setMediaStatus(QMediaPlayer::LoadedMedia);
714 QCOMPARE(player->mediaStatus(), QMediaPlayer::LoadedMedia);
715 QCOMPARE(statusSpy.count(), 2);
716
717 QCOMPARE(qvariant_cast<QMediaPlayer::MediaStatus>(statusSpy.last().value(0)),
718 QMediaPlayer::LoadedMedia);
719
720 // Verify the bufferStatusChanged() signal isn't being emitted.
721 QTestEventLoop::instance().enterLoop(secs: 1);
722 QCOMPARE(bufferSpy.count(), 0);
723
724 mockService->setMediaStatus(QMediaPlayer::StalledMedia);
725 QCOMPARE(player->mediaStatus(), QMediaPlayer::StalledMedia);
726 QCOMPARE(statusSpy.count(), 3);
727
728 QCOMPARE(qvariant_cast<QMediaPlayer::MediaStatus>(statusSpy.last().value(0)),
729 QMediaPlayer::StalledMedia);
730
731 // Verify the bufferStatusChanged() signal is being emitted.
732 QTestEventLoop::instance().enterLoop(secs: 1);
733 QVERIFY(bufferSpy.count() > bufferSignals);
734 QCOMPARE(bufferSpy.last().value(0).toInt(), bufferStatus);
735 bufferSignals = bufferSpy.count();
736
737 mockService->setMediaStatus(QMediaPlayer::BufferingMedia);
738 QCOMPARE(player->mediaStatus(), QMediaPlayer::BufferingMedia);
739 QCOMPARE(statusSpy.count(), 4);
740
741 QCOMPARE(qvariant_cast<QMediaPlayer::MediaStatus>(statusSpy.last().value(0)),
742 QMediaPlayer::BufferingMedia);
743
744 // Verify the bufferStatusChanged() signal is being emitted.
745 QTestEventLoop::instance().enterLoop(secs: 1);
746 QVERIFY(bufferSpy.count() > bufferSignals);
747 QCOMPARE(bufferSpy.last().value(0).toInt(), bufferStatus);
748 bufferSignals = bufferSpy.count();
749
750 mockService->setMediaStatus(QMediaPlayer::BufferedMedia);
751 QCOMPARE(player->mediaStatus(), QMediaPlayer::BufferedMedia);
752 QCOMPARE(statusSpy.count(), 5);
753
754 QCOMPARE(qvariant_cast<QMediaPlayer::MediaStatus>(statusSpy.last().value(0)),
755 QMediaPlayer::BufferedMedia);
756
757 // Verify the bufferStatusChanged() signal isn't being emitted.
758 QTestEventLoop::instance().enterLoop(secs: 1);
759 QCOMPARE(bufferSpy.count(), bufferSignals);
760
761 mockService->setMediaStatus(QMediaPlayer::EndOfMedia);
762 QCOMPARE(player->mediaStatus(), QMediaPlayer::EndOfMedia);
763 QCOMPARE(statusSpy.count(), 6);
764
765 QCOMPARE(qvariant_cast<QMediaPlayer::MediaStatus>(statusSpy.last().value(0)),
766 QMediaPlayer::EndOfMedia);
767}
768
769void tst_QMediaPlayer::testPlaylist()
770{
771 QMediaContent content0(QUrl(QLatin1String("test://audio/song1.mp3")));
772 QMediaContent content1(QUrl(QLatin1String("test://audio/song2.mp3")));
773 QMediaContent content2(QUrl(QLatin1String("test://video/movie1.mp4")));
774 QMediaContent content3(QUrl(QLatin1String("test://video/movie2.mp4")));
775 QMediaContent content4(QUrl(QLatin1String("test://image/photo.jpg")));
776
777 mockService->setIsValid(true);
778 mockService->setState(state: QMediaPlayer::StoppedState, status: QMediaPlayer::NoMedia);
779
780 QMediaPlaylist *playlist = new QMediaPlaylist;
781 player->setPlaylist(playlist);
782 QCOMPARE(player->media().playlist(), playlist);
783
784 QSignalSpy stateSpy(player, SIGNAL(stateChanged(QMediaPlayer::State)));
785 QSignalSpy mediaSpy(player, SIGNAL(currentMediaChanged(QMediaContent)));
786
787 // Test the player does nothing with an empty playlist attached.
788 player->play();
789 QCOMPARE(player->state(), QMediaPlayer::StoppedState);
790 QCOMPARE(player->currentMedia(), QMediaContent());
791 QCOMPARE(stateSpy.count(), 0);
792 QCOMPARE(mediaSpy.count(), 0);
793
794 playlist->addMedia(content: content0);
795 playlist->addMedia(content: content1);
796 playlist->addMedia(content: content2);
797 playlist->addMedia(content: content3);
798
799 // Test changing the playlist position, changes the current media, but not the playing state.
800 playlist->setCurrentIndex(1);
801 QCOMPARE(player->currentMedia(), content1);
802 QCOMPARE(player->state(), QMediaPlayer::StoppedState);
803 QCOMPARE(stateSpy.count(), 0);
804 QCOMPARE(mediaSpy.count(), 1);
805
806 // Test playing starts with the current media.
807 player->play();
808 QCOMPARE(player->currentMedia(), content1);
809 QCOMPARE(player->state(), QMediaPlayer::PlayingState);
810 QCOMPARE(stateSpy.count(), 1);
811 QCOMPARE(mediaSpy.count(), 1);
812
813 // Test pausing doesn't change the current media.
814 player->pause();
815 QCOMPARE(player->currentMedia(), content1);
816 QCOMPARE(player->state(), QMediaPlayer::PausedState);
817 QCOMPARE(stateSpy.count(), 2);
818 QCOMPARE(mediaSpy.count(), 1);
819
820 // Test stopping doesn't change the current media.
821 player->stop();
822 QCOMPARE(player->currentMedia(), content1);
823 QCOMPARE(player->state(), QMediaPlayer::StoppedState);
824 QCOMPARE(stateSpy.count(), 3);
825 QCOMPARE(mediaSpy.count(), 1);
826
827 // Test when the player service reaches the end of the current media, the player moves onto
828 // the next item without stopping.
829 player->play();
830 QCOMPARE(player->currentMedia(), content1);
831 QCOMPARE(player->state(), QMediaPlayer::PlayingState);
832 QCOMPARE(stateSpy.count(), 4);
833 QCOMPARE(mediaSpy.count(), 1);
834
835 mockService->setState(state: QMediaPlayer::StoppedState, status: QMediaPlayer::EndOfMedia);
836 QCOMPARE(player->currentMedia(), content2);
837 QCOMPARE(player->state(), QMediaPlayer::PlayingState);
838 QCOMPARE(stateSpy.count(), 4);
839 QCOMPARE(mediaSpy.count(), 2);
840
841 // Test skipping the current media doesn't change the state.
842 playlist->next();
843 QCOMPARE(player->currentMedia(), content3);
844 QCOMPARE(player->state(), QMediaPlayer::PlayingState);
845 QCOMPARE(stateSpy.count(), 4);
846 QCOMPARE(mediaSpy.count(), 3);
847
848 // Test changing the current media while paused doesn't change the state.
849 player->pause();
850 mockService->setMediaStatus(QMediaPlayer::BufferedMedia);
851 QCOMPARE(player->currentMedia(), content3);
852 QCOMPARE(player->state(), QMediaPlayer::PausedState);
853 QCOMPARE(stateSpy.count(), 5);
854 QCOMPARE(mediaSpy.count(), 3);
855
856 playlist->previous();
857 QCOMPARE(player->currentMedia(), content2);
858 QCOMPARE(player->state(), QMediaPlayer::PausedState);
859 QCOMPARE(stateSpy.count(), 5);
860 QCOMPARE(mediaSpy.count(), 4);
861
862 // Test changing the current media while stopped doesn't change the state.
863 player->stop();
864 mockService->setMediaStatus(QMediaPlayer::LoadedMedia);
865 QCOMPARE(player->currentMedia(), content2);
866 QCOMPARE(player->state(), QMediaPlayer::StoppedState);
867 QCOMPARE(stateSpy.count(), 6);
868 QCOMPARE(mediaSpy.count(), 4);
869
870 playlist->next();
871 QCOMPARE(player->currentMedia(), content3);
872 QCOMPARE(player->state(), QMediaPlayer::StoppedState);
873 QCOMPARE(stateSpy.count(), 6);
874 QCOMPARE(mediaSpy.count(), 5);
875
876 // Test the player is stopped and the current media cleared when it reaches the end of the last
877 // item in the playlist.
878 player->play();
879 QCOMPARE(player->currentMedia(), content3);
880 QCOMPARE(player->state(), QMediaPlayer::PlayingState);
881 QCOMPARE(stateSpy.count(), 7);
882 QCOMPARE(mediaSpy.count(), 5);
883
884 // Double up the signals to ensure some noise doesn't destabalize things.
885 mockService->setState(state: QMediaPlayer::StoppedState, status: QMediaPlayer::EndOfMedia);
886 mockService->setState(state: QMediaPlayer::StoppedState, status: QMediaPlayer::EndOfMedia);
887 QCOMPARE(player->currentMedia(), QMediaContent());
888 QCOMPARE(player->state(), QMediaPlayer::StoppedState);
889 QCOMPARE(stateSpy.count(), 8);
890 QCOMPARE(mediaSpy.count(), 6);
891
892 // Test starts playing from the start of the playlist if there is no current media selected.
893 player->play();
894 QCOMPARE(player->currentMedia(), content0);
895 QCOMPARE(player->state(), QMediaPlayer::PlayingState);
896 QCOMPARE(stateSpy.count(), 9);
897 // one notification is for playlist and another is for the first media in the playlist
898 QCOMPARE(mediaSpy.count(), 8);
899
900 // Test deleting the playlist stops the player and clears the media it set.
901 delete playlist;
902 QCOMPARE(player->currentMedia(), QMediaContent());
903 QCOMPARE(player->state(), QMediaPlayer::StoppedState);
904 QCOMPARE(stateSpy.count(), 10);
905 QCOMPARE(mediaSpy.count(), 9);
906
907 // Test the player works as normal with the playlist removed.
908 player->play();
909 QCOMPARE(player->currentMedia(), QMediaContent());
910 QCOMPARE(player->state(), QMediaPlayer::StoppedState);
911 QCOMPARE(stateSpy.count(), 10);
912 QCOMPARE(mediaSpy.count(), 9);
913
914 player->setMedia(media: content1);
915 player->play();
916
917 QCOMPARE(player->currentMedia(), content1);
918 QCOMPARE(player->state(), QMediaPlayer::PlayingState);
919 QCOMPARE(stateSpy.count(), 11);
920 QCOMPARE(mediaSpy.count(), 10);
921
922 // Test the player can bind to playlist again
923 playlist = new QMediaPlaylist;
924 player->setPlaylist(playlist);
925
926 QCOMPARE(player->currentMedia(), QMediaContent());
927 QCOMPARE(player->state(), QMediaPlayer::StoppedState);
928
929 playlist->addMedia(content: content0);
930 playlist->addMedia(content: content1);
931 playlist->addMedia(content: content2);
932 playlist->addMedia(content: content3);
933
934 playlist->setCurrentIndex(1);
935 QCOMPARE(player->currentMedia(), content1);
936 QCOMPARE(player->state(), QMediaPlayer::StoppedState);
937
938 // Test attaching the new playlist,
939 // player should detach the current one
940 QMediaPlaylist *playlist2 = new QMediaPlaylist;
941 playlist2->addMedia(content: content1);
942 playlist2->addMedia(content: content2);
943 playlist2->addMedia(content: content3);
944 playlist2->setCurrentIndex(2);
945
946 player->play();
947 player->setPlaylist(playlist2);
948 QCOMPARE(player->currentMedia(), playlist2->currentMedia());
949 QCOMPARE(player->state(), QMediaPlayer::StoppedState);
950
951 playlist2->setCurrentIndex(1);
952 QCOMPARE(player->currentMedia(), playlist2->currentMedia());
953
954 {
955 QMediaPlaylist playlist;
956 playlist.addMedia(content: content1);
957 playlist.addMedia(content: content2);
958 playlist.addMedia(content: content3);
959 playlist.setCurrentIndex(1);
960
961 // playlist resets to the first item
962 player->setPlaylist(&playlist);
963 QCOMPARE(player->playlist(), &playlist);
964 QCOMPARE(player->currentMedia(), content1);
965 } //playlist should be detached now
966
967 QVERIFY(player->playlist() == 0);
968 QCOMPARE(player->currentMedia(), QMediaContent());
969
970 // Test when the player service encounters an invalid media, the player moves onto
971 // the next item without stopping
972 {
973 QSignalSpy ss(player, SIGNAL(stateChanged(QMediaPlayer::State)));
974 QSignalSpy ms(player, SIGNAL(mediaStatusChanged(QMediaPlayer::MediaStatus)));
975
976 // playlist index is set to 0 when it is loaded into media player
977 player->setPlaylist(playlist);
978 player->play();
979 QCOMPARE(ss.count(), 1);
980 QCOMPARE(ms.count(), 1);
981 QCOMPARE(qvariant_cast<QMediaPlayer::MediaStatus>(ms.last().value(0)), QMediaPlayer::LoadingMedia);
982 ms.clear();
983
984 mockService->setState(state: QMediaPlayer::StoppedState, status: QMediaPlayer::InvalidMedia);
985 QCOMPARE(player->state(), QMediaPlayer::PlayingState);
986 QCOMPARE(player->mediaStatus(), QMediaPlayer::LoadingMedia);
987 QCOMPARE(ss.count(), 1);
988 QCOMPARE(ms.count(), 2);
989 QCOMPARE(qvariant_cast<QMediaPlayer::MediaStatus>(ms.at(0).value(0)), QMediaPlayer::InvalidMedia);
990 QCOMPARE(qvariant_cast<QMediaPlayer::MediaStatus>(ms.at(1).value(0)), QMediaPlayer::LoadingMedia);
991
992 // NOTE: status should begin transitioning through to BufferedMedia.
993 QCOMPARE(player->currentMedia(), content1);
994 }
995
996 delete playlist;
997 delete playlist2;
998}
999
1000void tst_QMediaPlayer::testPlayerFlags()
1001{
1002 MockMediaServiceProvider provider(0, true);
1003 QMediaPlayer::Flag flags = QMediaPlayer::LowLatency;
1004
1005 QMediaServiceProviderHint::Feature feature;
1006
1007 if (flags & QMediaPlayer::LowLatency)
1008 {
1009 /* if the flag is low latency set the low latency play back for the service provider */
1010 feature = QMediaServiceProviderHint::LowLatencyPlayback;
1011 const QByteArray service(Q_MEDIASERVICE_MEDIAPLAYER);
1012 const QMediaServiceProviderHint providerHint(feature);
1013 /* request service for the service provider */
1014 provider.requestService(service,providerHint);
1015
1016 /* Constructs a SupportedFeatures media service provider hint. */
1017 QMediaServiceProviderHint servicepro(feature);
1018
1019 /* compare the flag value */
1020 QVERIFY(servicepro.features() == QMediaServiceProviderHint::LowLatencyPlayback);
1021 }
1022
1023 /* The player is expected to play QIODevice based streams.
1024 If passed to QMediaPlayer constructor,
1025 the service supporting streams playback will be chosen. */
1026 flags = QMediaPlayer::StreamPlayback;
1027 /* Construct a QMediaPlayer that uses the playback service from provider,
1028 parented to parent and with flags.*/
1029
1030 if (flags & QMediaPlayer::StreamPlayback)
1031 {
1032 /* if the flag is stream play back set the stream play back for the service provider */
1033 feature = QMediaServiceProviderHint::StreamPlayback;
1034 const QByteArray service(Q_MEDIASERVICE_MEDIAPLAYER);
1035 const QMediaServiceProviderHint providerHint(feature);
1036
1037 /* request service for the service provider */
1038 provider.requestService(service,providerHint);
1039
1040 /* Constructs a SupportedFeatures media service provider hint. */
1041 QMediaServiceProviderHint servicepro(feature);
1042
1043 /* compare the flag value */
1044 QVERIFY(servicepro.features() == QMediaServiceProviderHint::StreamPlayback);
1045 }
1046}
1047
1048void tst_QMediaPlayer::testDestructor()
1049{
1050 //don't use the same service as tst_QMediaPlayer::player
1051 mockProvider->service = new MockMediaPlayerService;
1052 mockProvider->deleteServiceOnRelease = true;
1053
1054 /* create an object for player */
1055 QMediaPlayer *victim = new QMediaPlayer;
1056
1057 /* check whether the object is created */
1058 QVERIFY(victim);
1059
1060 /* delete the instance (a crash is a failure :) */
1061 delete victim;
1062
1063 //service is released
1064 QVERIFY(mockProvider->service == 0);
1065
1066 mockProvider->deleteServiceOnRelease = false;
1067}
1068
1069#ifndef QT_NO_BEARERMANAGEMENT
1070void tst_QMediaPlayer::testNetworkAccess()
1071{
1072 QNetworkConfigurationManager manager;
1073 QList<QNetworkConfiguration> configs = manager.allConfigurations();
1074
1075 if (configs.count() >= 1) {
1076 QSignalSpy spy(player, SIGNAL(networkConfigurationChanged(QNetworkConfiguration)));
1077 int index = qFloor(v: (configs.count())/2);
1078 player->setNetworkConfigurations(configs);
1079 mockService->selectCurrentConfiguration(config: configs.at(i: index));
1080
1081 QVERIFY(spy.count() == 1);
1082 QList<QVariant> args = spy.takeFirst();
1083 QNetworkConfiguration config = args.at(i: 0).value<QNetworkConfiguration>();
1084 QCOMPARE(config.identifier() , configs.at(index).identifier());
1085 QCOMPARE(player->currentNetworkConfiguration().identifier() , config.identifier());
1086 }
1087
1088 // invalidate current network configuration
1089 QSignalSpy spy(player, SIGNAL(networkConfigurationChanged(QNetworkConfiguration)));
1090 mockService->selectCurrentConfiguration(config: QNetworkConfiguration());
1091 QVERIFY(spy.count() == 1);
1092 QList<QVariant> args = spy.takeFirst();
1093 QNetworkConfiguration config = args.at(i: 0).value<QNetworkConfiguration>();
1094 QVERIFY(config.isValid() == false);
1095 QVERIFY(player->currentNetworkConfiguration().isValid() == false);
1096}
1097#endif
1098
1099void tst_QMediaPlayer::testSetVideoOutput()
1100{
1101 MockVideoSurface surface;
1102
1103 player->setVideoOutput(reinterpret_cast<QVideoWidget *>(0));
1104 player->setVideoOutput(reinterpret_cast<QGraphicsVideoItem *>(0));
1105
1106 QCOMPARE(mockService->rendererRef, 0);
1107
1108 player->setVideoOutput(&surface);
1109 QVERIFY(mockService->rendererControl->surface() == &surface);
1110 QCOMPARE(mockService->rendererRef, 1);
1111
1112 player->setVideoOutput(reinterpret_cast<QAbstractVideoSurface *>(0));
1113 QVERIFY(mockService->rendererControl->surface() == 0);
1114
1115 //rendererControl is released
1116 QCOMPARE(mockService->rendererRef, 0);
1117
1118 player->setVideoOutput(&surface);
1119 QVERIFY(mockService->rendererControl->surface() == &surface);
1120 QCOMPARE(mockService->rendererRef, 1);
1121
1122 player->setVideoOutput(reinterpret_cast<QVideoWidget *>(0));
1123 QVERIFY(mockService->rendererControl->surface() == 0);
1124 //rendererControl is released
1125 QCOMPARE(mockService->rendererRef, 0);
1126
1127 player->setVideoOutput(&surface);
1128 QVERIFY(mockService->rendererControl->surface() == &surface);
1129 QCOMPARE(mockService->rendererRef, 1);
1130}
1131
1132
1133void tst_QMediaPlayer::testSetVideoOutputNoService()
1134{
1135 MockVideoSurface surface;
1136
1137 MockMediaServiceProvider provider(0, true);
1138 QMediaServiceProvider::setDefaultServiceProvider(&provider);
1139 QMediaPlayer player;
1140
1141 player.setVideoOutput(&surface);
1142 // Nothing we can verify here other than it doesn't assert.
1143}
1144
1145void tst_QMediaPlayer::testSetVideoOutputNoControl()
1146{
1147 MockVideoSurface surface;
1148
1149 MockMediaPlayerService service;
1150 service.rendererRef = 1;
1151
1152 MockMediaServiceProvider provider(&service);
1153 QMediaServiceProvider::setDefaultServiceProvider(&provider);
1154 QMediaPlayer player;
1155
1156 player.setVideoOutput(&surface);
1157 QVERIFY(service.rendererControl->surface() == 0);
1158}
1159
1160void tst_QMediaPlayer::testSetVideoOutputDestruction()
1161{
1162 MockVideoSurface surface;
1163 {
1164 QMediaPlayer player;
1165 player.setVideoOutput(&surface);
1166 QVERIFY(mockService->rendererControl->surface() == &surface);
1167 QCOMPARE(mockService->rendererRef, 1);
1168 }
1169 QVERIFY(mockService->rendererControl->surface() == 0);
1170 QCOMPARE(mockService->rendererRef, 0);
1171}
1172
1173void tst_QMediaPlayer::testPositionPropertyWatch()
1174{
1175 QMediaContent content0(QUrl(QLatin1String("test://audio/song1.mp3")));
1176 QMediaContent content1(QUrl(QLatin1String("test://audio/song2.mp3")));
1177
1178 mockService->setIsValid(true);
1179 mockService->setState(state: QMediaPlayer::StoppedState, status: QMediaPlayer::NoMedia);
1180
1181 QMediaPlaylist *playlist = new QMediaPlaylist;
1182
1183 playlist->addMedia(content: content0);
1184 playlist->addMedia(content: content1);
1185
1186 player->setPlaylist(playlist);
1187 player->setNotifyInterval(5);
1188
1189 player->play();
1190 QSignalSpy positionSpy(player, SIGNAL(positionChanged(qint64)));
1191 playlist->next();
1192 QCOMPARE(player->state(), QMediaPlayer::PlayingState);
1193 QTRY_VERIFY(positionSpy.count() > 0);
1194
1195 playlist->next();
1196 QCOMPARE(player->state(), QMediaPlayer::StoppedState);
1197
1198 positionSpy.clear();
1199 QTRY_COMPARE(positionSpy.count(), 0);
1200
1201 delete playlist;
1202}
1203
1204void tst_QMediaPlayer::debugEnums()
1205{
1206 QTest::ignoreMessage(type: QtDebugMsg, message: "QMediaPlayer::PlayingState");
1207 qDebug() << QMediaPlayer::PlayingState;
1208 QTest::ignoreMessage(type: QtDebugMsg, message: "QMediaPlayer::NoMedia");
1209 qDebug() << QMediaPlayer::NoMedia;
1210 QTest::ignoreMessage(type: QtDebugMsg, message: "QMediaPlayer::NetworkError");
1211 qDebug() << QMediaPlayer::NetworkError;
1212}
1213
1214void tst_QMediaPlayer::testSupportedMimeTypes()
1215{
1216 QStringList mimeList = QMediaPlayer::supportedMimeTypes(flags: QMediaPlayer::LowLatency);
1217
1218 // This is empty on some platforms, and not on others, so can't test something here at the moment.
1219}
1220
1221void tst_QMediaPlayer::testQrc_data()
1222{
1223 QTest::addColumn<QMediaContent>(name: "mediaContent");
1224 QTest::addColumn<QMediaPlayer::MediaStatus>(name: "status");
1225 QTest::addColumn<QMediaPlayer::Error>(name: "error");
1226 QTest::addColumn<int>(name: "errorCount");
1227 QTest::addColumn<bool>(name: "hasStreamFeature");
1228 QTest::addColumn<QString>(name: "backendMediaContentScheme");
1229 QTest::addColumn<bool>(name: "backendHasStream");
1230
1231 QTest::newRow(dataTag: "invalid") << QMediaContent(QUrl(QLatin1String("qrc:/invalid.mp3")))
1232 << QMediaPlayer::InvalidMedia
1233 << QMediaPlayer::ResourceError
1234 << 1 // error count
1235 << false // No StreamPlayback support
1236 << QString() // backend should not have got any media (empty URL scheme)
1237 << false; // backend should not have got any stream
1238
1239 QTest::newRow(dataTag: "valid+nostream") << QMediaContent(QUrl(QLatin1String("qrc:/testdata/nokia-tune.mp3")))
1240 << QMediaPlayer::LoadingMedia
1241 << QMediaPlayer::NoError
1242 << 0 // error count
1243 << false // No StreamPlayback support
1244 << QStringLiteral("file") // backend should have a got a temporary file
1245 << false; // backend should not have got any stream
1246
1247 QTest::newRow(dataTag: "valid+stream") << QMediaContent(QUrl(QLatin1String("qrc:/testdata/nokia-tune.mp3")))
1248 << QMediaPlayer::LoadingMedia
1249 << QMediaPlayer::NoError
1250 << 0 // error count
1251 << true // StreamPlayback support
1252 << QStringLiteral("qrc")
1253 << true; // backend should have got a stream (QFile opened from the resource)
1254}
1255
1256void tst_QMediaPlayer::testQrc()
1257{
1258 QFETCH(QMediaContent, mediaContent);
1259 QFETCH(QMediaPlayer::MediaStatus, status);
1260 QFETCH(QMediaPlayer::Error, error);
1261 QFETCH(int, errorCount);
1262 QFETCH(bool, hasStreamFeature);
1263 QFETCH(QString, backendMediaContentScheme);
1264 QFETCH(bool, backendHasStream);
1265
1266 if (hasStreamFeature)
1267 mockProvider->setSupportedFeatures(QMediaServiceProviderHint::StreamPlayback);
1268
1269 QMediaPlayer player;
1270
1271 mockService->setState(state: QMediaPlayer::PlayingState, status: QMediaPlayer::NoMedia);
1272
1273 QSignalSpy mediaSpy(&player, SIGNAL(currentMediaChanged(QMediaContent)));
1274 QSignalSpy statusSpy(&player, SIGNAL(mediaStatusChanged(QMediaPlayer::MediaStatus)));
1275 QSignalSpy errorSpy(&player, SIGNAL(error(QMediaPlayer::Error)));
1276
1277 player.setMedia(media: mediaContent);
1278
1279 QTRY_COMPARE(player.mediaStatus(), status);
1280 QCOMPARE(statusSpy.count(), 1);
1281 QCOMPARE(qvariant_cast<QMediaPlayer::MediaStatus>(statusSpy.last().value(0)), status);
1282
1283 QCOMPARE(player.media(), mediaContent);
1284 QCOMPARE(player.currentMedia(), mediaContent);
1285 QCOMPARE(mediaSpy.count(), 1);
1286 QCOMPARE(qvariant_cast<QMediaContent>(mediaSpy.last().value(0)), mediaContent);
1287
1288 QCOMPARE(player.error(), error);
1289 QCOMPARE(errorSpy.count(), errorCount);
1290 if (errorCount > 0) {
1291 QCOMPARE(qvariant_cast<QMediaPlayer::Error>(errorSpy.last().value(0)), error);
1292 QVERIFY(!player.errorString().isEmpty());
1293 }
1294
1295 // Check the media actually passed to the backend
1296 QCOMPARE(mockService->mockControl->media().request().url().scheme(), backendMediaContentScheme);
1297 QCOMPARE(bool(mockService->mockControl->mediaStream()), backendHasStream);
1298}
1299
1300void tst_QMediaPlayer::testAudioRole()
1301{
1302 {
1303 mockService->setHasAudioRole(false);
1304 QMediaPlayer player;
1305
1306 QCOMPARE(player.audioRole(), QAudio::UnknownRole);
1307 QVERIFY(player.supportedAudioRoles().isEmpty());
1308
1309 QSignalSpy spy(&player, SIGNAL(audioRoleChanged(QAudio::Role)));
1310 player.setAudioRole(QAudio::MusicRole);
1311 QCOMPARE(player.audioRole(), QAudio::UnknownRole);
1312 QCOMPARE(spy.count(), 0);
1313 }
1314
1315 {
1316 mockService->reset();
1317 mockService->setHasAudioRole(true);
1318 QMediaPlayer player;
1319 QSignalSpy spy(&player, SIGNAL(audioRoleChanged(QAudio::Role)));
1320
1321 QCOMPARE(player.audioRole(), QAudio::UnknownRole);
1322 QVERIFY(!player.supportedAudioRoles().isEmpty());
1323
1324 player.setAudioRole(QAudio::MusicRole);
1325 QCOMPARE(player.audioRole(), QAudio::MusicRole);
1326 QCOMPARE(mockService->mockAudioRoleControl->audioRole(), QAudio::MusicRole);
1327 QCOMPARE(spy.count(), 1);
1328 QCOMPARE(qvariant_cast<QAudio::Role>(spy.last().value(0)), QAudio::MusicRole);
1329
1330 spy.clear();
1331
1332 player.setProperty(name: "audioRole", value: QVariant::fromValue(value: QAudio::AlarmRole));
1333 QCOMPARE(qvariant_cast<QAudio::Role>(player.property("audioRole")), QAudio::AlarmRole);
1334 QCOMPARE(mockService->mockAudioRoleControl->audioRole(), QAudio::AlarmRole);
1335 QCOMPARE(spy.count(), 1);
1336 QCOMPARE(qvariant_cast<QAudio::Role>(spy.last().value(0)), QAudio::AlarmRole);
1337 }
1338}
1339
1340void tst_QMediaPlayer::testCustomAudioRole()
1341{
1342 {
1343 mockService->setHasCustomAudioRole(false);
1344 QMediaPlayer player;
1345
1346 QVERIFY(player.customAudioRole().isEmpty());
1347 QVERIFY(player.supportedCustomAudioRoles().isEmpty());
1348
1349 QSignalSpy spyRole(&player, SIGNAL(audioRoleChanged(QAudio::Role)));
1350 QSignalSpy spyCustomRole(&player, SIGNAL(customAudioRoleChanged(const QString &)));
1351 player.setCustomAudioRole(QStringLiteral("customRole"));
1352 QCOMPARE(player.audioRole(), QAudio::UnknownRole);
1353 QVERIFY(player.customAudioRole().isEmpty());
1354 QCOMPARE(spyRole.count(), 0);
1355 QCOMPARE(spyCustomRole.count(), 0);
1356 }
1357
1358 {
1359 mockService->reset();
1360 mockService->setHasAudioRole(false);
1361 QMediaPlayer player;
1362
1363 QVERIFY(player.customAudioRole().isEmpty());
1364 QVERIFY(player.supportedCustomAudioRoles().isEmpty());
1365
1366 QSignalSpy spyRole(&player, SIGNAL(audioRoleChanged(QAudio::Role)));
1367 QSignalSpy spyCustomRole(&player, SIGNAL(customAudioRoleChanged(const QString &)));
1368 player.setCustomAudioRole(QStringLiteral("customRole"));
1369 QCOMPARE(player.audioRole(), QAudio::UnknownRole);
1370 QVERIFY(player.customAudioRole().isEmpty());
1371 QCOMPARE(spyRole.count(), 0);
1372 QCOMPARE(spyCustomRole.count(), 0);
1373 }
1374
1375 {
1376 mockService->reset();
1377 QMediaPlayer player;
1378 QSignalSpy spyRole(&player, SIGNAL(audioRoleChanged(QAudio::Role)));
1379 QSignalSpy spyCustomRole(&player, SIGNAL(customAudioRoleChanged(const QString &)));
1380
1381 QCOMPARE(player.audioRole(), QAudio::UnknownRole);
1382 QVERIFY(player.customAudioRole().isEmpty());
1383 QVERIFY(!player.supportedCustomAudioRoles().isEmpty());
1384
1385 QString customRole(QStringLiteral("customRole"));
1386 player.setCustomAudioRole(customRole);
1387 QCOMPARE(player.audioRole(), QAudio::CustomRole);
1388 QCOMPARE(player.customAudioRole(), customRole);
1389 QCOMPARE(mockService->mockAudioRoleControl->audioRole(), QAudio::CustomRole);
1390 QCOMPARE(mockService->mockCustomAudioRoleControl->customAudioRole(), customRole);
1391 QCOMPARE(spyRole.count(), 1);
1392 QCOMPARE(qvariant_cast<QAudio::Role>(spyRole.last().value(0)), QAudio::CustomRole);
1393 QCOMPARE(spyCustomRole.count(), 1);
1394 QCOMPARE(qvariant_cast<QString>(spyCustomRole.last().value(0)), customRole);
1395
1396 spyRole.clear();
1397 spyCustomRole.clear();
1398
1399 QString customRole2(QStringLiteral("customRole2"));
1400 player.setProperty(name: "customAudioRole", value: QVariant::fromValue(value: customRole2));
1401 QCOMPARE(qvariant_cast<QString>(player.property("customAudioRole")), customRole2);
1402 QCOMPARE(mockService->mockCustomAudioRoleControl->customAudioRole(), customRole2);
1403 QCOMPARE(spyRole.count(), 0);
1404 QCOMPARE(spyCustomRole.count(), 1);
1405 QCOMPARE(qvariant_cast<QString>(spyCustomRole.last().value(0)), customRole2);
1406
1407 spyRole.clear();
1408 spyCustomRole.clear();
1409
1410 player.setAudioRole(QAudio::MusicRole);
1411 QCOMPARE(player.audioRole(), QAudio::MusicRole);
1412 QVERIFY(player.customAudioRole().isEmpty());
1413 QCOMPARE(mockService->mockAudioRoleControl->audioRole(), QAudio::MusicRole);
1414 QVERIFY(mockService->mockCustomAudioRoleControl->customAudioRole().isEmpty());
1415 QCOMPARE(spyRole.count(), 1);
1416 QCOMPARE(qvariant_cast<QAudio::Role>(spyRole.last().value(0)), QAudio::MusicRole);
1417 QCOMPARE(spyCustomRole.count(), 1);
1418 QVERIFY(qvariant_cast<QString>(spyCustomRole.last().value(0)).isEmpty());
1419
1420 spyRole.clear();
1421 spyCustomRole.clear();
1422
1423 player.setAudioRole(QAudio::CustomRole);
1424 QCOMPARE(player.audioRole(), QAudio::CustomRole);
1425 QVERIFY(player.customAudioRole().isEmpty());
1426 QCOMPARE(mockService->mockAudioRoleControl->audioRole(), QAudio::CustomRole);
1427 QVERIFY(mockService->mockCustomAudioRoleControl->customAudioRole().isEmpty());
1428 QCOMPARE(spyRole.count(), 1);
1429 QCOMPARE(qvariant_cast<QAudio::Role>(spyRole.last().value(0)), QAudio::CustomRole);
1430 QCOMPARE(spyCustomRole.count(), 0);
1431 }
1432}
1433
1434QTEST_GUILESS_MAIN(tst_QMediaPlayer)
1435#include "tst_qmediaplayer.moc"
1436

source code of qtmultimedia/tests/auto/unit/qmediaplayer/tst_qmediaplayer.cpp