summaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/3rdparty/webkit/WebCore/WebCore.pro3
-rw-r--r--src/3rdparty/webkit/WebKit/qt/Api/qwebkitversion.h2
-rw-r--r--src/corelib/codecs/qiconvcodec.cpp22
-rw-r--r--src/corelib/global/qglobal.cpp28
-rw-r--r--src/corelib/io/qiodevice.cpp13
-rw-r--r--src/corelib/kernel/qeventdispatcher_symbian.cpp127
-rw-r--r--src/corelib/kernel/qeventdispatcher_symbian_p.h5
-rw-r--r--src/corelib/tools/qbytearray.cpp39
-rw-r--r--src/corelib/tools/qbytearray.h3
-rw-r--r--src/corelib/tools/qbytedata_p.h2
-rw-r--r--src/corelib/tools/qlist.cpp8
-rw-r--r--src/corelib/tools/qstring.cpp40
-rw-r--r--src/corelib/tools/qstring.h1
-rw-r--r--src/corelib/xml/qxmlstream.g2
-rw-r--r--src/corelib/xml/qxmlstream_p.h4
-rw-r--r--src/declarative/graphicsitems/qdeclarativeitem.cpp5
-rw-r--r--src/gui/egl/qegl_p.h6
-rw-r--r--src/gui/egl/qegl_stub.cpp8
-rw-r--r--src/gui/graphicsview/qgraphicsitem_p.h7
-rw-r--r--src/gui/graphicsview/qgraphicsproxywidget.cpp2
-rw-r--r--src/gui/graphicsview/qgraphicsview_p.h8
-rw-r--r--src/gui/graphicsview/qgraphicswidget.cpp10
-rw-r--r--src/gui/kernel/qapplication_s60.cpp18
-rw-r--r--src/gui/kernel/qcocoasharedwindowmethods_mac_p.h54
-rw-r--r--src/gui/kernel/qcocoaview_mac.mm3
-rw-r--r--src/gui/kernel/qsoftkeymanager_s60.cpp2
-rw-r--r--src/gui/kernel/qt_cocoa_helpers_mac.mm131
-rw-r--r--src/gui/kernel/qt_cocoa_helpers_mac_p.h5
-rw-r--r--src/gui/kernel/qt_mac_p.h1
-rw-r--r--src/gui/kernel/qt_s60_p.h3
-rw-r--r--src/gui/kernel/qwidget.cpp27
-rw-r--r--src/gui/kernel/qwidget_mac.mm6
-rw-r--r--src/gui/kernel/qwidget_p.h7
-rw-r--r--src/gui/kernel/qwidget_s60.cpp91
-rw-r--r--src/gui/painting/qprintengine_ps.cpp25
-rw-r--r--src/gui/painting/qprintengine_win.cpp7
-rw-r--r--src/gui/s60framework/qs60mainappui.cpp12
-rw-r--r--src/gui/styles/qs60style.cpp43
-rw-r--r--src/gui/styles/qs60style_s60.cpp8
-rw-r--r--src/gui/styles/qstylesheetstyle.cpp9
-rw-r--r--src/gui/styles/qstylesheetstyle_p.h1
-rw-r--r--src/gui/text/qfont.cpp5
-rw-r--r--src/gui/text/qfontdatabase.cpp14
-rw-r--r--src/gui/text/qfontdatabase_s60.cpp46
-rw-r--r--src/gui/text/qfontengine_s60.cpp32
-rw-r--r--src/gui/text/qfontengine_s60_p.h8
-rw-r--r--src/gui/widgets/qlineedit.cpp10
-rw-r--r--src/gui/widgets/qmenu.cpp4
-rw-r--r--src/gui/widgets/qmenu_mac.mm3
-rw-r--r--src/gui/widgets/qtabbar.cpp19
-rw-r--r--src/gui/widgets/qtabwidget.cpp2
-rw-r--r--src/imports/multimedia/qdeclarativeaudio.cpp16
-rw-r--r--src/imports/multimedia/qdeclarativevideo.cpp19
-rw-r--r--src/multimedia/mediaservices/effects/qsoundeffect.cpp12
-rw-r--r--src/multimedia/multimedia/audio/qaudioinput.cpp4
-rw-r--r--src/multimedia/multimedia/audio/qaudioinput_alsa_p.cpp9
-rw-r--r--src/multimedia/multimedia/audio/qaudioinput_win32_p.cpp67
-rw-r--r--src/multimedia/multimedia/audio/qaudioinput_win32_p.h3
-rw-r--r--src/multimedia/multimedia/audio/qaudiooutput_alsa_p.cpp16
-rw-r--r--src/multimedia/multimedia/audio/qaudiooutput_win32_p.cpp70
-rw-r--r--src/multimedia/multimedia/audio/qaudiooutput_win32_p.h3
-rw-r--r--src/network/access/qftp.cpp2
-rw-r--r--src/network/access/qhttpnetworkconnection.cpp6
-rw-r--r--src/network/access/qhttpnetworkconnectionchannel.cpp9
-rw-r--r--src/network/access/qnetworkaccesshttpbackend.cpp3
-rw-r--r--src/network/access/qnetworkaccessmanager.h12
-rw-r--r--src/network/access/qnetworkcookiejar.cpp3
-rw-r--r--src/network/access/qnetworkreplyimpl.cpp80
-rw-r--r--src/network/access/qnetworkreplyimpl_p.h5
-rw-r--r--src/opengl/qgl.cpp12
-rw-r--r--src/openvg/qpaintengine_vg.cpp56
-rw-r--r--src/openvg/qpaintengine_vg_p.h4
-rw-r--r--src/plugins/accessible/widgets/simplewidgets.cpp4
-rw-r--r--src/plugins/mediaservices/directshow/mediaplayer/directshowsamplescheduler.cpp23
-rw-r--r--src/plugins/mediaservices/directshow/mediaplayer/directshowsamplescheduler.h5
-rw-r--r--src/plugins/mediaservices/gstreamer/gstreamer.pro35
-rw-r--r--src/plugins/mediaservices/gstreamer/mediaplayer/qgstreamerplayerservice.cpp22
-rw-r--r--src/plugins/mediaservices/gstreamer/qvideosurfacegstsink.cpp18
-rw-r--r--src/plugins/mediaservices/gstreamer/qvideosurfacegstsink.h6
-rw-r--r--src/plugins/mediaservices/mediaservices.pro4
-rw-r--r--src/plugins/mediaservices/symbian/mediaplayer/mediaplayer.pri63
-rw-r--r--src/plugins/mediaservices/symbian/mediaplayer/ms60mediaplayerresolver.h58
-rw-r--r--src/plugins/mediaservices/symbian/mediaplayer/s60audioplayersession.cpp268
-rw-r--r--src/plugins/mediaservices/symbian/mediaplayer/s60audioplayersession.h116
-rw-r--r--src/plugins/mediaservices/symbian/mediaplayer/s60mediametadataprovider.cpp185
-rw-r--r--src/plugins/mediaservices/symbian/mediaplayer/s60mediametadataprovider.h81
-rw-r--r--src/plugins/mediaservices/symbian/mediaplayer/s60mediaplayeraudioendpointselector.cpp127
-rw-r--r--src/plugins/mediaservices/symbian/mediaplayer/s60mediaplayeraudioendpointselector.h81
-rw-r--r--src/plugins/mediaservices/symbian/mediaplayer/s60mediaplayercontrol.cpp274
-rw-r--r--src/plugins/mediaservices/symbian/mediaplayer/s60mediaplayercontrol.h143
-rw-r--r--src/plugins/mediaservices/symbian/mediaplayer/s60mediaplayerservice.cpp259
-rw-r--r--src/plugins/mediaservices/symbian/mediaplayer/s60mediaplayerservice.h105
-rw-r--r--src/plugins/mediaservices/symbian/mediaplayer/s60mediaplayersession.cpp496
-rw-r--r--src/plugins/mediaservices/symbian/mediaplayer/s60mediaplayersession.h167
-rw-r--r--src/plugins/mediaservices/symbian/mediaplayer/s60mediarecognizer.cpp127
-rw-r--r--src/plugins/mediaservices/symbian/mediaplayer/s60mediarecognizer.h83
-rw-r--r--src/plugins/mediaservices/symbian/mediaplayer/s60videooverlay.cpp209
-rw-r--r--src/plugins/mediaservices/symbian/mediaplayer/s60videooverlay.h109
-rw-r--r--src/plugins/mediaservices/symbian/mediaplayer/s60videoplayersession.cpp486
-rw-r--r--src/plugins/mediaservices/symbian/mediaplayer/s60videoplayersession.h148
-rw-r--r--src/plugins/mediaservices/symbian/mediaplayer/s60videorenderer.cpp69
-rw-r--r--src/plugins/mediaservices/symbian/mediaplayer/s60videorenderer.h68
-rw-r--r--src/plugins/mediaservices/symbian/mediaplayer/s60videosurface.cpp478
-rw-r--r--src/plugins/mediaservices/symbian/mediaplayer/s60videosurface.h112
-rw-r--r--src/plugins/mediaservices/symbian/mediaplayer/s60videowidget.cpp208
-rw-r--r--src/plugins/mediaservices/symbian/mediaplayer/s60videowidget.h115
-rw-r--r--src/plugins/mediaservices/symbian/s60mediaserviceplugin.cpp100
-rw-r--r--src/plugins/mediaservices/symbian/s60mediaserviceplugin.h64
-rw-r--r--src/plugins/mediaservices/symbian/s60videooutputcontrol.cpp76
-rw-r--r--src/plugins/mediaservices/symbian/s60videooutputcontrol.h72
-rw-r--r--src/plugins/mediaservices/symbian/symbian.pro27
-rw-r--r--src/s60installs/bwins/QtCoreu.def4
-rw-r--r--src/s60installs/bwins/QtDeclarativeu.def2
-rw-r--r--src/s60installs/eabi/QtCoreu.def1
-rw-r--r--src/s60installs/eabi/QtDeclarativeu.def40
-rw-r--r--src/s60installs/eabi/QtNetworku.def1
-rw-r--r--src/s60installs/s60installs.pro11
-rw-r--r--src/script/bridge/qscriptqobject_p.h2
-rw-r--r--src/sql/drivers/sqlite/qsql_sqlite.cpp1
-rw-r--r--src/testlib/qtestlogger.cpp29
-rw-r--r--src/testlib/qtestlogger_p.h1
-rw-r--r--src/testlib/qtestxmlstreamer.cpp58
-rw-r--r--src/testlib/qxmltestlogger.cpp2
-rw-r--r--src/xmlpatterns/schema/qxsdschemaresolver.cpp9
-rw-r--r--src/xmlpatterns/xmlpatterns.pro15
125 files changed, 6123 insertions, 496 deletions
diff --git a/src/3rdparty/webkit/WebCore/WebCore.pro b/src/3rdparty/webkit/WebCore/WebCore.pro
index 276ca04..3dfe803 100644
--- a/src/3rdparty/webkit/WebCore/WebCore.pro
+++ b/src/3rdparty/webkit/WebCore/WebCore.pro
@@ -55,8 +55,6 @@ CONFIG(standalone_package) {
isEmpty(JSC_GENERATED_SOURCES_DIR):JSC_GENERATED_SOURCES_DIR = $$PWD/../JavaScriptCore/generated
PRECOMPILED_HEADER = $$PWD/../WebKit/qt/WebKit_pch.h
-
- symbian: TARGET += $${QT_LIBINFIX}
} else {
isEmpty(WC_GENERATED_SOURCES_DIR):WC_GENERATED_SOURCES_DIR = generated
isEmpty(JSC_GENERATED_SOURCES_DIR):JSC_GENERATED_SOURCES_DIR = ../JavaScriptCore/generated
@@ -76,6 +74,7 @@ CONFIG(QTDIR_build) {
VERSION = $${QT_MAJOR_VERSION}.$${QT_MINOR_VERSION}.$${QT_PATCH_VERSION}
DESTDIR = $$OUTPUT_DIR/lib
!static: DEFINES += QT_MAKEDLL
+ symbian: TARGET +=$${QT_LIBINFIX}
}
unix {
diff --git a/src/3rdparty/webkit/WebKit/qt/Api/qwebkitversion.h b/src/3rdparty/webkit/WebKit/qt/Api/qwebkitversion.h
index f0fbef0..de79dd1 100644
--- a/src/3rdparty/webkit/WebKit/qt/Api/qwebkitversion.h
+++ b/src/3rdparty/webkit/WebKit/qt/Api/qwebkitversion.h
@@ -17,7 +17,7 @@
Boston, MA 02110-1301, USA.
*/
-#include <qstring.h>
+#include <QtCore/qstring.h>
#ifndef qwebkitversion_h
#define qwebkitversion_h
diff --git a/src/corelib/codecs/qiconvcodec.cpp b/src/corelib/codecs/qiconvcodec.cpp
index 0fcdf96..44a0a01 100644
--- a/src/corelib/codecs/qiconvcodec.cpp
+++ b/src/corelib/codecs/qiconvcodec.cpp
@@ -168,7 +168,7 @@ Q_GLOBAL_STATIC(QThreadStorage<QIconvCodec::IconvState *>, toUnicodeState)
QString QIconvCodec::convertToUnicode(const char* chars, int len, ConverterState *convState) const
{
if (utf16Codec == reinterpret_cast<QTextCodec *>(~0))
- return QString::fromAscii(chars, len);
+ return QString::fromLatin1(chars, len);
int invalidCount = 0;
int remainingCount = 0;
@@ -207,9 +207,9 @@ QString QIconvCodec::convertToUnicode(const char* chars, int len, ConverterState
static int reported = 0;
if (!reported++) {
fprintf(stderr,
- "QIconvCodec::convertToUnicode: using ASCII for conversion, iconv_open failed\n");
+ "QIconvCodec::convertToUnicode: using Latin-1 for conversion, iconv_open failed\n");
}
- return QString::fromAscii(chars, len);
+ return QString::fromLatin1(chars, len);
}
*pstate = new IconvState(cd);
@@ -273,14 +273,14 @@ QString QIconvCodec::convertToUnicode(const char* chars, int len, ConverterState
// some other error
// note, cannot use qWarning() since we are implementing the codecForLocale :)
- perror("QIconvCodec::convertToUnicode: using ASCII for conversion, iconv failed");
+ perror("QIconvCodec::convertToUnicode: using Latin-1 for conversion, iconv failed");
if (!convState) {
// reset state
iconv(state->cd, 0, &inBytesLeft, 0, &outBytesLeft);
}
- return QString::fromAscii(chars, len);
+ return QString::fromLatin1(chars, len);
}
} while (inBytesLeft != 0);
@@ -353,12 +353,12 @@ QByteArray QIconvCodec::convertFromUnicode(const QChar *uc, int len, ConverterSt
state = new IconvState(QIconvCodec::createIconv_t(0, UTF16));
if (state->cd == reinterpret_cast<iconv_t>(-1)) {
if (!setByteOrder(state->cd)) {
- perror("QIconvCodec::convertFromUnicode: using ASCII for conversion, iconv failed for BOM");
+ perror("QIconvCodec::convertFromUnicode: using Latin-1 for conversion, iconv failed for BOM");
iconv_close(state->cd);
state->cd = reinterpret_cast<iconv_t>(-1);
- return QString(uc, len).toAscii();
+ return QString(uc, len).toLatin1();
}
}
}
@@ -366,9 +366,9 @@ QByteArray QIconvCodec::convertFromUnicode(const QChar *uc, int len, ConverterSt
static int reported = 0;
if (!reported++) {
fprintf(stderr,
- "QIconvCodec::convertFromUnicode: using ASCII for conversion, iconv_open failed\n");
+ "QIconvCodec::convertFromUnicode: using Latin-1 for conversion, iconv_open failed\n");
}
- return QString(uc, len).toAscii();
+ return QString(uc, len).toLatin1();
}
size_t outBytesLeft = len;
@@ -425,12 +425,12 @@ QByteArray QIconvCodec::convertFromUnicode(const QChar *uc, int len, ConverterSt
default:
{
// note, cannot use qWarning() since we are implementing the codecForLocale :)
- perror("QIconvCodec::convertFromUnicode: using ASCII for conversion, iconv failed");
+ perror("QIconvCodec::convertFromUnicode: using Latin-1 for conversion, iconv failed");
// reset to initial state
iconv(state->cd, 0, &inBytesLeft, 0, &outBytesLeft);
- return QString(uc, len).toAscii();
+ return QString(uc, len).toLatin1();
}
}
}
diff --git a/src/corelib/global/qglobal.cpp b/src/corelib/global/qglobal.cpp
index dfa2c17..373c0b4 100644
--- a/src/corelib/global/qglobal.cpp
+++ b/src/corelib/global/qglobal.cpp
@@ -2079,7 +2079,28 @@ static void mac_default_handler(const char *msg)
}
#endif // Q_CC_MWERKS && Q_OS_MACX
-
+#if !defined(Q_OS_WIN) && !defined(QT_NO_THREAD) && !defined(Q_OS_INTEGRITY) && !defined(Q_OS_QNX) && \
+ defined(_POSIX_THREAD_SAFE_FUNCTIONS) && _POSIX_VERSION >= 200112L
+namespace {
+ // There are two incompatible versions of strerror_r:
+ // a) the XSI/POSIX.1 version, which returns an int,
+ // indicating success or not
+ // b) the GNU version, which returns a char*, which may or may not
+ // be the beginning of the buffer we used
+ // The GNU libc manpage for strerror_r says you should use the the XSI
+ // version in portable code. However, it's impossible to do that if
+ // _GNU_SOURCE is defined so we use C++ overloading to decide what to do
+ // depending on the return type
+ static inline QString fromstrerror_helper(int, const QByteArray &buf)
+ {
+ return QString::fromLocal8Bit(buf);
+ }
+ static inline QString fromstrerror_helper(const char *str, const QByteArray &)
+ {
+ return QString::fromLocal8Bit(str);
+ }
+}
+#endif
QString qt_error_string(int errorCode)
{
@@ -2122,12 +2143,9 @@ QString qt_error_string(int errorCode)
if (ret.isEmpty() && errorCode == ERROR_MOD_NOT_FOUND)
ret = QString::fromLatin1("The specified module could not be found.");
-
#elif !defined(QT_NO_THREAD) && defined(_POSIX_THREAD_SAFE_FUNCTIONS) && _POSIX_VERSION >= 200112L && !defined(Q_OS_INTEGRITY) && !defined(Q_OS_QNX)
-
QByteArray buf(1024, '\0');
- strerror_r(errorCode, buf.data(), buf.size());
- ret = QString::fromLocal8Bit(buf.constData());
+ ret = fromstrerror_helper(strerror_r(errorCode, buf.data(), buf.size()), buf);
#else
ret = QString::fromLocal8Bit(strerror(errorCode));
#endif
diff --git a/src/corelib/io/qiodevice.cpp b/src/corelib/io/qiodevice.cpp
index f2cef4e1..bb11d6b 100644
--- a/src/corelib/io/qiodevice.cpp
+++ b/src/corelib/io/qiodevice.cpp
@@ -755,7 +755,6 @@ qint64 QIODevice::bytesToWrite() const
qint64 QIODevice::read(char *data, qint64 maxSize)
{
Q_D(QIODevice);
- CHECK_READABLE(read, qint64(-1));
#if defined QIODEVICE_DEBUG
printf("%p QIODevice::read(%p, %d), d->pos = %d, d->buffer.size() = %d\n",
@@ -786,13 +785,13 @@ qint64 QIODevice::read(char *data, qint64 maxSize)
do {
// Try reading from the buffer.
int lastReadChunkSize = d->buffer.read(data, maxSize);
- *d->pPos += lastReadChunkSize;
- readSoFar += lastReadChunkSize;
- // fast exit when satisfied by buffer
- if (lastReadChunkSize == maxSize && !(d->openMode & Text))
- return readSoFar;
-
if (lastReadChunkSize > 0) {
+ *d->pPos += lastReadChunkSize;
+ readSoFar += lastReadChunkSize;
+ // fast exit when satisfied by buffer
+ if (lastReadChunkSize == maxSize && !(d->openMode & Text))
+ return readSoFar;
+
data += lastReadChunkSize;
maxSize -= lastReadChunkSize;
#if defined QIODEVICE_DEBUG
diff --git a/src/corelib/kernel/qeventdispatcher_symbian.cpp b/src/corelib/kernel/qeventdispatcher_symbian.cpp
index 3b86e89..4566ec0 100644
--- a/src/corelib/kernel/qeventdispatcher_symbian.cpp
+++ b/src/corelib/kernel/qeventdispatcher_symbian.cpp
@@ -43,7 +43,6 @@
#include <private/qthread_p.h>
#include <qcoreapplication.h>
#include <private/qcoreapplication_p.h>
-#include <qdatetime.h>
#include <unistd.h>
#include <errno.h>
@@ -636,6 +635,74 @@ void QSocketActiveObject::deleteLater()
}
}
+#ifdef QT_SYMBIAN_PRIORITY_DROP
+class QIdleDetectorThread
+{
+public:
+ QIdleDetectorThread()
+ : m_state(STATE_RUN), m_stop(false)
+ {
+ qt_symbian_throwIfError(m_lock.CreateLocal());
+ TInt err = m_idleDetectorThread.Create(KNullDesC(), &idleDetectorThreadFunc, 1024, &User::Allocator(), this);
+ if (err != KErrNone)
+ m_lock.Close();
+ qt_symbian_throwIfError(err);
+ m_idleDetectorThread.SetPriority(EPriorityAbsoluteBackgroundNormal);
+ m_idleDetectorThread.Resume();
+ }
+
+ ~QIdleDetectorThread()
+ {
+ // close down the idle thread because if corelib is loaded temporarily, this would leak threads into the host process
+ m_stop = true;
+ m_lock.Signal();
+ m_idleDetectorThread.SetPriority(EPriorityNormal);
+ TRequestStatus s;
+ m_idleDetectorThread.Logon(s);
+ User::WaitForRequest(s);
+ m_idleDetectorThread.Close();
+ m_lock.Close();
+ }
+
+ void kick()
+ {
+ m_state = STATE_KICKED;
+ m_lock.Signal();
+ }
+
+ bool hasRun()
+ {
+ return m_state == STATE_RUN;
+ }
+
+private:
+ static TInt idleDetectorThreadFunc(TAny* self)
+ {
+ static_cast<QIdleDetectorThread*>(self)->IdleLoop();
+ return KErrNone;
+ }
+
+ void IdleLoop()
+ {
+ while (!m_stop) {
+ m_lock.Wait();
+ m_state = STATE_RUN;
+ }
+ }
+
+private:
+ enum IdleStates {STATE_KICKED, STATE_RUN} m_state;
+ bool m_stop;
+ RThread m_idleDetectorThread;
+ RFastLock m_lock;
+};
+
+Q_GLOBAL_STATIC(QIdleDetectorThread, idleDetectorThread);
+
+const int maxBusyTime = 2000; // maximum time we allow idle detector to be blocked before worrying, in milliseconds
+const int baseDelay = 1000; // minimum delay time used when backing off to allow idling, in microseconds
+#endif
+
QEventDispatcherSymbian::QEventDispatcherSymbian(QObject *parent)
: QAbstractEventDispatcher(parent),
m_selectThread(0),
@@ -647,11 +714,15 @@ QEventDispatcherSymbian::QEventDispatcherSymbian(QObject *parent)
m_iterationCount(0),
m_noSocketEvents(false)
{
+#ifdef QT_SYMBIAN_PRIORITY_DROP
+ m_delay = baseDelay;
+ m_avgEventTime = 0;
+ idleDetectorThread();
+#endif
}
QEventDispatcherSymbian::~QEventDispatcherSymbian()
{
- m_processHandle.Close();
}
void QEventDispatcherSymbian::startingUp()
@@ -720,23 +791,7 @@ bool QEventDispatcherSymbian::processEvents ( QEventLoop::ProcessEventsFlags fla
m_interrupt = false;
#ifdef QT_SYMBIAN_PRIORITY_DROP
- /*
- * This QTime variable is used to measure the time it takes to finish
- * the event loop. If we take too long in the loop, other processes
- * may be starved and killed. After the first event has completed, we
- * take the current time, and if the remaining events take longer than
- * a preset time, we temporarily lower the priority to force a context
- * switch. For applications that do not take unecessarily long in the
- * event loop, the priority will not be altered.
- */
- QTime time;
- enum {
- FirstRun,
- SubsequentRun,
- TimeStarted
- } timeState = FirstRun;
-
- TProcessPriority priority;
+ QTime eventTimer;
#endif
while (1) {
@@ -752,10 +807,18 @@ bool QEventDispatcherSymbian::processEvents ( QEventLoop::ProcessEventsFlags fla
}
#ifdef QT_SYMBIAN_PRIORITY_DROP
- if (timeState == SubsequentRun) {
- time.start();
- timeState = TimeStarted;
+ if (idleDetectorThread()->hasRun()) {
+ if (m_delay > baseDelay)
+ m_delay -= baseDelay;
+ m_lastIdleRequestTimer.start();
+ idleDetectorThread()->kick();
+ } else if (m_lastIdleRequestTimer.elapsed() > maxBusyTime) {
+ User::AfterHighRes(m_delay);
+ // allow delay to be up to 1/4 of execution time
+ if (!idleDetectorThread()->hasRun() && m_delay*3 < m_avgEventTime)
+ m_delay += baseDelay;
}
+ eventTimer.start();
#endif
TInt error;
@@ -765,6 +828,12 @@ bool QEventDispatcherSymbian::processEvents ( QEventLoop::ProcessEventsFlags fla
CActiveScheduler::Current()->Error(error);
}
+#ifdef QT_SYMBIAN_PRIORITY_DROP
+ int eventDur = eventTimer.elapsed()*1000;
+ // average is calcualted as a 5% decaying exponential average
+ m_avgEventTime = (m_avgEventTime * 95 + eventDur * 5) / 100;
+#endif
+
if (!handledSymbianEvent) {
qFatal("QEventDispatcherSymbian::processEvents(): Caught Symbian stray signal");
}
@@ -773,20 +842,6 @@ bool QEventDispatcherSymbian::processEvents ( QEventLoop::ProcessEventsFlags fla
break;
}
block = false;
-#ifdef QT_SYMBIAN_PRIORITY_DROP
- if (timeState == TimeStarted && time.elapsed() > 100) {
- priority = m_processHandle.Priority();
- m_processHandle.SetPriority(EPriorityBackground);
- time.start();
- // Slight chance of race condition in the next lines, but nothing fatal
- // will happen, just wrong priority.
- if (m_processHandle.Priority() == EPriorityBackground) {
- m_processHandle.SetPriority(priority);
- }
- }
- if (timeState == FirstRun)
- timeState = SubsequentRun;
-#endif
};
emit awake();
diff --git a/src/corelib/kernel/qeventdispatcher_symbian_p.h b/src/corelib/kernel/qeventdispatcher_symbian_p.h
index 5281199..05758ca 100644
--- a/src/corelib/kernel/qeventdispatcher_symbian_p.h
+++ b/src/corelib/kernel/qeventdispatcher_symbian_p.h
@@ -62,6 +62,7 @@
#include <qmutex.h>
#include <qwaitcondition.h>
#include <qsocketnotifier.h>
+#include <qdatetime.h>
#include <e32base.h>
@@ -280,7 +281,9 @@ private:
QList<QActiveObject *> m_deferredActiveObjects;
- RProcess m_processHandle;
+ int m_delay;
+ int m_avgEventTime;
+ QTime m_lastIdleRequestTimer;
};
#ifdef QT_DEBUG
diff --git a/src/corelib/tools/qbytearray.cpp b/src/corelib/tools/qbytearray.cpp
index c5f70b0..29a7263 100644
--- a/src/corelib/tools/qbytearray.cpp
+++ b/src/corelib/tools/qbytearray.cpp
@@ -3814,7 +3814,7 @@ QByteArray QByteArray::number(double n, char f, int prec)
accepting a \c{const char *} expected to be '\\0'-terminated will
fail.
- \sa data(), constData()
+ \sa setRawData(), data(), constData()
*/
QByteArray QByteArray::fromRawData(const char *data, int size)
@@ -3834,6 +3834,37 @@ QByteArray QByteArray::fromRawData(const char *data, int size)
}
/*!
+ \since 4.7
+
+ Resets the QByteArray to use the first \a size bytes of the
+ \a data array. The bytes are \e not copied. The QByteArray will
+ contain the \a data pointer. The caller guarantees that \a data
+ will not be deleted or modified as long as this QByteArray and any
+ copies of it exist that have not been modified.
+
+ This function can be used instead of fromRawData() to re-use
+ existings QByteArray objects to save memory re-allocations.
+
+ \sa fromRawData(), data(), constData()
+*/
+QByteArray &QByteArray::setRawData(const char *data, uint size)
+{
+ if (d->ref != 1 || d->alloc) {
+ *this = fromRawData(data, size);
+ } else {
+ if (data) {
+ d->data = const_cast<char *>(data);
+ } else {
+ d->data = d->array;
+ size = 0;
+ }
+ d->alloc = d->size = size;
+ *d->array = '\0';
+ }
+ return *this;
+}
+
+/*!
Returns a decoded copy of the Base64 array \a base64. Input is not checked
for validity; invalid characters in the input are skipped, enabling the
decoding process to continue with subsequent characters.
@@ -4228,12 +4259,6 @@ QByteArray QByteArray::toPercentEncoding(const QByteArray &exclude, const QByteA
*/
/*!
- \fn QByteArray& QByteArray::setRawData(const char *a, uint n)
-
- Use fromRawData() instead.
-*/
-
-/*!
\fn void QByteArray::resetRawData(const char *data, uint n)
Use clear() instead.
diff --git a/src/corelib/tools/qbytearray.h b/src/corelib/tools/qbytearray.h
index 0b77512..a3fe3f5 100644
--- a/src/corelib/tools/qbytearray.h
+++ b/src/corelib/tools/qbytearray.h
@@ -299,6 +299,7 @@ public:
QByteArray &setNum(qulonglong, int base = 10);
QByteArray &setNum(float, char f = 'g', int prec = 6);
QByteArray &setNum(double, char f = 'g', int prec = 6);
+ QByteArray &setRawData(const char *a, uint n); // ### Qt 5: use an int
static QByteArray number(int, int base = 10);
static QByteArray number(uint, int base = 10);
@@ -343,8 +344,6 @@ public:
inline QT3_SUPPORT QByteArray& duplicate(const QByteArray& a) { *this = a; return *this; }
inline QT3_SUPPORT QByteArray& duplicate(const char *a, uint n)
{ *this = QByteArray(a, n); return *this; }
- inline QT3_SUPPORT QByteArray& setRawData(const char *a, uint n)
- { *this = fromRawData(a, n); return *this; }
inline QT3_SUPPORT void resetRawData(const char *, uint) { clear(); }
inline QT3_SUPPORT QByteArray lower() const { return toLower(); }
inline QT3_SUPPORT QByteArray upper() const { return toUpper(); }
diff --git a/src/corelib/tools/qbytedata_p.h b/src/corelib/tools/qbytedata_p.h
index c48bb33..08249e0 100644
--- a/src/corelib/tools/qbytedata_p.h
+++ b/src/corelib/tools/qbytedata_p.h
@@ -84,7 +84,7 @@ public:
}
- inline void append(QByteArray& bd)
+ inline void append(const QByteArray& bd)
{
if (bd.isEmpty())
return;
diff --git a/src/corelib/tools/qlist.cpp b/src/corelib/tools/qlist.cpp
index 6f5bb9b..6cc6fc1 100644
--- a/src/corelib/tools/qlist.cpp
+++ b/src/corelib/tools/qlist.cpp
@@ -853,9 +853,7 @@ void **QListData::erase(void **xi)
same as takeAt(0). This function assumes the list is not empty. To
avoid failure, call isEmpty() before calling this function.
- This operation is very fast (\l{constant time}), because QList
- preallocates extra space on both sides of its internal buffer to
- allow for fast growth at both ends of the list.
+ This operation takes \l{constant time}.
If you don't use the return value, removeFirst() is more
efficient.
@@ -870,9 +868,7 @@ void **QListData::erase(void **xi)
not empty. To avoid failure, call isEmpty() before calling this
function.
- This operation is very fast (\l{constant time}), because QList
- preallocates extra space on both sides of its internal buffer to
- allow for fast growth at both ends of the list.
+ This operation takes \l{constant time}.
If you don't use the return value, removeLast() is more
efficient.
diff --git a/src/corelib/tools/qstring.cpp b/src/corelib/tools/qstring.cpp
index 2f12b80..0169b20 100644
--- a/src/corelib/tools/qstring.cpp
+++ b/src/corelib/tools/qstring.cpp
@@ -7056,7 +7056,7 @@ void QString::updateProperties() const
'\\0'-terminated string (although utf16() does, at the cost of
copying the raw data).
- \sa fromUtf16()
+ \sa fromUtf16(), setRawData()
*/
QString QString::fromRawData(const QChar *unicode, int size)
{
@@ -7075,6 +7075,44 @@ QString QString::fromRawData(const QChar *unicode, int size)
return QString(x, 0);
}
+/*!
+ \since 4.7
+
+ Resets the QString to use the first \a size Unicode characters
+ in the array \a unicode. The data in \a unicode is \e not
+ copied. The caller must be able to guarantee that \a unicode will
+ not be deleted or modified as long as the QString (or an
+ unmodified copy of it) exists.
+
+ This function can be used instead of fromRawData() to re-use
+ existings QString objects to save memory re-allocations.
+
+ \sa fromRawData()
+*/
+QString &QString::setRawData(const QChar *unicode, int size)
+{
+ if (d->ref != 1 || d->alloc) {
+ *this = fromRawData(unicode, size);
+ } else {
+#ifdef QT3_SUPPORT
+ if (d->asciiCache) {
+ Q_ASSERT(asciiCache);
+ asciiCache->remove(d);
+ }
+#endif
+ if (unicode) {
+ d->data = (ushort *)unicode;
+ } else {
+ d->data = d->array;
+ size = 0;
+ }
+ d->alloc = d->size = size;
+ *d->array = '\0';
+ d->clean = d->asciiCache = d->simpletext = d->righttoleft = d->capacity = 0;
+ }
+ return *this;
+}
+
/*! \class QLatin1String
\brief The QLatin1String class provides a thin wrapper around an US-ASCII/Latin-1 encoded string literal.
diff --git a/src/corelib/tools/qstring.h b/src/corelib/tools/qstring.h
index ea12c2f..a1c4e77 100644
--- a/src/corelib/tools/qstring.h
+++ b/src/corelib/tools/qstring.h
@@ -343,6 +343,7 @@ public:
int toWCharArray(wchar_t *array) const;
static QString fromWCharArray(const wchar_t *, int size = -1);
+ QString &setRawData(const QChar *unicode, int size);
QString &setUnicode(const QChar *unicode, int size);
inline QString &setUtf16(const ushort *utf16, int size);
diff --git a/src/corelib/xml/qxmlstream.g b/src/corelib/xml/qxmlstream.g
index 1b882e0..e91408f 100644
--- a/src/corelib/xml/qxmlstream.g
+++ b/src/corelib/xml/qxmlstream.g
@@ -748,7 +748,7 @@ bool QXmlStreamReaderPrivate::parse()
state_stack[tos] = 0;
return true;
} else if (act > 0) {
- if (++tos == stack_size)
+ if (++tos == stack_size-1)
reallocateStack();
Value &val = sym_stack[tos];
diff --git a/src/corelib/xml/qxmlstream_p.h b/src/corelib/xml/qxmlstream_p.h
index ac421cf..f6ab3a1 100644
--- a/src/corelib/xml/qxmlstream_p.h
+++ b/src/corelib/xml/qxmlstream_p.h
@@ -61,7 +61,7 @@
class QXmlStreamReader_Table
{
public:
- enum {
+ enum VariousConstants {
EOF_SYMBOL = 0,
AMPERSAND = 5,
ANY = 41,
@@ -1242,7 +1242,7 @@ bool QXmlStreamReaderPrivate::parse()
state_stack[tos] = 0;
return true;
} else if (act > 0) {
- if (++tos == stack_size)
+ if (++tos == stack_size-1)
reallocateStack();
Value &val = sym_stack[tos];
diff --git a/src/declarative/graphicsitems/qdeclarativeitem.cpp b/src/declarative/graphicsitems/qdeclarativeitem.cpp
index bc0c65e..096e4bf 100644
--- a/src/declarative/graphicsitems/qdeclarativeitem.cpp
+++ b/src/declarative/graphicsitems/qdeclarativeitem.cpp
@@ -1268,11 +1268,6 @@ QDeclarativeKeysAttached *QDeclarativeKeysAttached::qmlAttachedProperties(QObjec
*/
/*!
- \property QDeclarativeItem::effect
- \internal
-*/
-
-/*!
\property QDeclarativeItem::focus
\internal
*/
diff --git a/src/gui/egl/qegl_p.h b/src/gui/egl/qegl_p.h
index 6c562ef..4fc1338 100644
--- a/src/gui/egl/qegl_p.h
+++ b/src/gui/egl/qegl_p.h
@@ -154,7 +154,13 @@ QT_BEGIN_NAMESPACE
// Declare/define the bits of EGL_KHR_image_base we need:
#if !defined(EGL_KHR_image) && !defined(EGL_KHR_image_base)
+#ifdef Q_OS_SYMBIAN
+//symbian version of eglext.h differs from the khronos reference
+typedef int EGLImageKHR;
+#else
typedef void *EGLImageKHR;
+#endif
+
#define EGL_NO_IMAGE_KHR ((EGLImageKHR)0)
#define EGL_IMAGE_PRESERVED_KHR 0x30D2
#define EGL_KHR_image_base
diff --git a/src/gui/egl/qegl_stub.cpp b/src/gui/egl/qegl_stub.cpp
index 0bd3451..86a7aab 100644
--- a/src/gui/egl/qegl_stub.cpp
+++ b/src/gui/egl/qegl_stub.cpp
@@ -183,14 +183,6 @@ int QEglContext::configAttrib(int name) const
return 0;
}
-typedef EGLImageKHR (EGLAPIENTRY *_eglCreateImageKHR)(EGLDisplay, EGLContext, EGLenum, EGLClientBuffer, const EGLint*);
-typedef EGLBoolean (EGLAPIENTRY *_eglDestroyImageKHR)(EGLDisplay, EGLImageKHR);
-
-// Defined in qegl.cpp:
-static _eglCreateImageKHR qt_eglCreateImageKHR = 0;
-static _eglDestroyImageKHR qt_eglDestroyImageKHR = 0;
-
-
EGLDisplay QEgl::display()
{
NOEGL
diff --git a/src/gui/graphicsview/qgraphicsitem_p.h b/src/gui/graphicsview/qgraphicsitem_p.h
index 6b22607..569a329 100644
--- a/src/gui/graphicsview/qgraphicsitem_p.h
+++ b/src/gui/graphicsview/qgraphicsitem_p.h
@@ -845,6 +845,13 @@ inline bool QGraphicsItemPrivate::insertionOrder(QGraphicsItem *a, QGraphicsItem
inline void QGraphicsItemPrivate::markParentDirty(bool updateBoundingRect)
{
QGraphicsItemPrivate *parentp = this;
+#ifndef QT_NO_GRAPHICSEFFECT
+ if (updateBoundingRect && parentp->graphicsEffect && !parentp->inSetPosHelper) {
+ parentp->notifyInvalidated = 1;
+ static_cast<QGraphicsItemEffectSourcePrivate *>(parentp->graphicsEffect->d_func()
+ ->source->d_func())->invalidateCache();
+ }
+#endif
while (parentp->parent) {
parentp = parentp->parent->d_ptr.data();
parentp->dirtyChildren = 1;
diff --git a/src/gui/graphicsview/qgraphicsproxywidget.cpp b/src/gui/graphicsview/qgraphicsproxywidget.cpp
index 1f89714..320395e 100644
--- a/src/gui/graphicsview/qgraphicsproxywidget.cpp
+++ b/src/gui/graphicsview/qgraphicsproxywidget.cpp
@@ -975,6 +975,7 @@ bool QGraphicsProxyWidget::eventFilter(QObject *object, QEvent *event)
d->styleChangeMode = QGraphicsProxyWidgetPrivate::NoMode;
}
break;
+#ifndef QT_NO_TOOLTIP
case QEvent::ToolTipChange:
// Propagate tooltip change to the proxy.
if (!d->tooltipChangeMode) {
@@ -983,6 +984,7 @@ bool QGraphicsProxyWidget::eventFilter(QObject *object, QEvent *event)
d->tooltipChangeMode = QGraphicsProxyWidgetPrivate::NoMode;
}
break;
+#endif
default:
break;
}
diff --git a/src/gui/graphicsview/qgraphicsview_p.h b/src/gui/graphicsview/qgraphicsview_p.h
index 729837a..80e3ec1 100644
--- a/src/gui/graphicsview/qgraphicsview_p.h
+++ b/src/gui/graphicsview/qgraphicsview_p.h
@@ -183,8 +183,12 @@ public:
else
QCoreApplication::sendPostedEvents(viewport->window(), QEvent::UpdateRequest);
#else
- QCoreApplication::processEvents(QEventLoop::AllEvents | QEventLoop::ExcludeSocketNotifiers
- | QEventLoop::ExcludeUserInputEvents);
+ // At this point either HIViewSetNeedsDisplay (Carbon) or setNeedsDisplay: YES (Cocoa)
+ // is called, which means there's a pending update request. We want to dispatch it
+ // now because otherwise graphics view updates would require two
+ // round-trips in the event loop before the item is painted.
+ extern void qt_mac_dispatchPendingUpdateRequests(QWidget *);
+ qt_mac_dispatchPendingUpdateRequests(viewport->window());
#endif
}
diff --git a/src/gui/graphicsview/qgraphicswidget.cpp b/src/gui/graphicsview/qgraphicswidget.cpp
index bc8ccb01..06a44b7 100644
--- a/src/gui/graphicsview/qgraphicswidget.cpp
+++ b/src/gui/graphicsview/qgraphicswidget.cpp
@@ -324,11 +324,9 @@ void QGraphicsWidget::resize(const QSizeF &size)
*/
/*!
-
\fn QGraphicsWidget::geometryChanged()
- This signal gets emitted whenever the geometry of the item changes
- \internal
+ This signal gets emitted whenever the geometry is changed in setGeometry().
*/
/*!
@@ -408,12 +406,6 @@ void QGraphicsWidget::setGeometry(const QRectF &rect)
}
/*!
- \fn QGraphicsWidget::geometryChanged()
-
- This signal gets emitted whenever the geometry is changed in setGeometry().
-*/
-
-/*!
\fn QRectF QGraphicsWidget::rect() const
Returns the item's local rect as a QRectF. This function is equivalent
diff --git a/src/gui/kernel/qapplication_s60.cpp b/src/gui/kernel/qapplication_s60.cpp
index c735d1f..5f7813b 100644
--- a/src/gui/kernel/qapplication_s60.cpp
+++ b/src/gui/kernel/qapplication_s60.cpp
@@ -73,6 +73,7 @@
# endif
# include <private/qs60mainapplication_p.h>
# include <centralrepository.h>
+# include "qs60mainappui.h"
#endif
#include "private/qstylesheetstyle_p.h"
@@ -539,6 +540,14 @@ void QSymbianControl::HandlePointerEvent(const TPointerEvent& pEvent)
sendMouseEvent(receiver, type, globalPos, button, modifiers);
}
+#ifdef Q_WS_S60
+void QSymbianControl::HandleStatusPaneSizeChange()
+{
+ QS60MainAppUi *s60AppUi = static_cast<QS60MainAppUi *>(S60->appUi());
+ s60AppUi->HandleStatusPaneSizeChange();
+}
+#endif
+
void QSymbianControl::sendMouseEvent(
QWidget *receiver,
QEvent::Type type,
@@ -982,15 +991,6 @@ void QSymbianControl::FocusChanged(TDrawNow /* aDrawNow */)
const TBool isFullscreen = qwidget->windowState() & Qt::WindowFullScreen;
const TBool cbaVisibilityHint = qwidget->windowFlags() & Qt::WindowSoftkeysVisibleHint;
buttonGroup->MakeVisible(visible || (isFullscreen && cbaVisibilityHint));
-
- // Responsiviness
- CEikCba *cba = static_cast<CEikCba *>( buttonGroup->ButtonGroup() ); // downcast from MEikButtonGroup
- TUint cbaFlags = cba->ButtonGroupFlags();
- if(qwidget->windowFlags() & Qt::WindowSoftkeysRespondHint)
- cbaFlags |= EAknCBAFlagRespondWhenInvisible;
- else
- cbaFlags &= ~EAknCBAFlagRespondWhenInvisible;
- cba->SetButtonGroupFlags(cbaFlags);
}
#endif
} else if (QApplication::activeWindow() == qwidget->window()) {
diff --git a/src/gui/kernel/qcocoasharedwindowmethods_mac_p.h b/src/gui/kernel/qcocoasharedwindowmethods_mac_p.h
index e94d247..8652816 100644
--- a/src/gui/kernel/qcocoasharedwindowmethods_mac_p.h
+++ b/src/gui/kernel/qcocoasharedwindowmethods_mac_p.h
@@ -363,3 +363,57 @@ QT_END_NAMESPACE
}
[super displayIfNeeded];
}
+
+// This is a hack and it should be removed once we find the real cause for
+// the painting problems.
+// We have a static variable that signals if we have been called before or not.
+static bool firstDrawingInvocation = true;
+
+// The method below exists only as a workaround to draw/not draw the baseline
+// in the title bar. This is to support unifiedToolbar look.
+
+// This method is very special. To begin with, it is a
+// method that will get called only if we enable documentMode.
+// Furthermore, it won't get called as a normal method, we swap
+// this method with the normal implementation of drawRect in
+// _NSThemeFrame. When this method is active, its mission is to
+// first call the original drawRect implementation so the widget
+// gets proper painting. After that, it needs to detect if there
+// is a toolbar or not, in order to decide how to handle the unified
+// look. The distinction is important since the presence and
+// visibility of a toolbar change the way we enter into unified mode.
+// When there is a toolbar and that toolbar is visible, the problem
+// is as simple as to tell the toolbar not to draw its baseline.
+// However when there is not toolbar or the toolbar is not visible,
+// we need to draw a line on top of the baseline, because the baseline
+// in that case will belong to the title. For this case we need to draw
+// a line on top of the baseline.
+// As usual, there is a special case. When we first are called, we might
+// need to repaint ourselves one more time. We only need that if we
+// didn't get the activation, i.e. when we are launched via the command
+// line. And this only if the toolbar is visible from the beginning,
+// so we have a special flag that signals if we need to repaint or not.
+- (void)drawRectSpecial:(NSRect)rect
+{
+ // Call the original drawing method.
+ [self drawRectOriginal:rect];
+ NSWindow *window = [self window];
+ NSToolbar *toolbar = [window toolbar];
+ if(!toolbar) {
+ // There is no toolbar, we have to draw a line on top of the line drawn by Cocoa.
+ macDrawRectOnTop((void *)window);
+ } else {
+ if([toolbar isVisible]) {
+ // We tell Cocoa to avoid drawing the line at the end.
+ if(firstDrawingInvocation) {
+ firstDrawingInvocation = false;
+ macSyncDrawingOnFirstInvocation((void *)window);
+ } else
+ [toolbar setShowsBaselineSeparator:NO];
+ } else {
+ // There is a toolbar but it is not visible so
+ // we have to draw a line on top of the line drawn by Cocoa.
+ macDrawRectOnTop((void *)window);
+ }
+ }
+}
diff --git a/src/gui/kernel/qcocoaview_mac.mm b/src/gui/kernel/qcocoaview_mac.mm
index dd12f65..4953c48 100644
--- a/src/gui/kernel/qcocoaview_mac.mm
+++ b/src/gui/kernel/qcocoaview_mac.mm
@@ -1554,7 +1554,8 @@ Qt::DropAction QDragManager::drag(QDrag *o)
qt_button_down = 0;
[dndParams.view release];
[image release];
- dragPrivate()->executed_action = Qt::IgnoreAction;
+ if (dragPrivate())
+ dragPrivate()->executed_action = Qt::IgnoreAction;
object = 0;
Qt::DropAction performedAction(qt_mac_mapNSDragOperation(qMacDnDParams()->performedAction));
// do post drag processing, if required.
diff --git a/src/gui/kernel/qsoftkeymanager_s60.cpp b/src/gui/kernel/qsoftkeymanager_s60.cpp
index e4990b1..6325d95 100644
--- a/src/gui/kernel/qsoftkeymanager_s60.cpp
+++ b/src/gui/kernel/qsoftkeymanager_s60.cpp
@@ -79,6 +79,8 @@ bool QSoftKeyManagerPrivateS60::skipCbaUpdate()
// Note: Cannot use IsDisplayingMenuOrDialog since CBA update can be triggered before
// menu/dialog CBA is actually displayed i.e. it is being costructed.
CEikButtonGroupContainer *appUiCba = S60->buttonGroupContainer();
+ if (!appUiCba)
+ return true;
// CEikButtonGroupContainer::Current returns 0 if CBA is not visible at all
CEikButtonGroupContainer *currentCba = CEikButtonGroupContainer::Current();
// Check if softkey need to be update even they are not visible
diff --git a/src/gui/kernel/qt_cocoa_helpers_mac.mm b/src/gui/kernel/qt_cocoa_helpers_mac.mm
index a05c7d5..8cef03c 100644
--- a/src/gui/kernel/qt_cocoa_helpers_mac.mm
+++ b/src/gui/kernel/qt_cocoa_helpers_mac.mm
@@ -1163,15 +1163,81 @@ void qt_mac_updateContentBorderMetricts(void * /*OSWindowRef */window, const ::H
#endif
}
+#if QT_MAC_USE_COCOA
+void qt_mac_replaceDrawRect(void * /*OSWindowRef */window, QWidgetPrivate *widget)
+{
+ QMacCocoaAutoReleasePool pool;
+ OSWindowRef theWindow = static_cast<OSWindowRef>(window);
+ if(!theWindow)
+ return;
+ id theClass = [[[theWindow contentView] superview] class];
+ // What we do here is basically to add a new selector to NSThemeFrame called
+ // "drawRectOriginal:" which will contain the original implementation of
+ // "drawRect:". After that we get the new implementation from QCocoaWindow
+ // and exchange them. The new implementation is called drawRectSpecial.
+ // We cannot just add the method because it might have been added before and since
+ // we cannot remove a method once it has been added we need to ask QCocoaWindow if
+ // we did the swap or not.
+ if(!widget->drawRectOriginalAdded) {
+ Method m2 = class_getInstanceMethod(theClass, @selector(drawRect:));
+ if(!m2) {
+ // This case is pretty extreme, no drawRect means no drawing!
+ return;
+ }
+ class_addMethod(theClass, @selector(drawRectOriginal:), method_getImplementation(m2), method_getTypeEncoding(m2));
+ widget->drawRectOriginalAdded = true;
+ }
+ if(widget->originalDrawMethod) {
+ Method m0 = class_getInstanceMethod([theWindow class], @selector(drawRectSpecial:));
+ if(!m0) {
+ // Ok, this means the methods were never swapped. Just ignore
+ return;
+ }
+ Method m1 = class_getInstanceMethod(theClass, @selector(drawRect:));
+ if(!m1) {
+ // Ok, this means the methods were never swapped. Just ignore
+ return;
+ }
+ // We have the original method here. Proceed and swap the methods.
+ method_exchangeImplementations(m1, m0);
+ widget->originalDrawMethod = false;
+ [window display];
+ }
+}
+
+void qt_mac_replaceDrawRectOriginal(void * /*OSWindowRef */window, QWidgetPrivate *widget)
+{
+ QMacCocoaAutoReleasePool pool;
+ OSWindowRef theWindow = static_cast<OSWindowRef>(window);
+ id theClass = [[[theWindow contentView] superview] class];
+ // Now we need to revert the methods to their original state.
+ // We cannot remove the method, so we just keep track of it in QCocoaWindow.
+ Method m0 = class_getInstanceMethod([theWindow class], @selector(drawRectSpecial:));
+ if(!m0) {
+ // Ok, this means the methods were never swapped. Just ignore
+ return;
+ }
+ Method m1 = class_getInstanceMethod(theClass, @selector(drawRect:));
+ if(!m1) {
+ // Ok, this means the methods were never swapped. Just ignore
+ return;
+ }
+ method_exchangeImplementations(m1, m0);
+ widget->originalDrawMethod = true;
+ [window display];
+}
+#endif // QT_MAC_USE_COCOA
+
void qt_mac_showBaseLineSeparator(void * /*OSWindowRef */window, bool show)
{
+ if(!window)
+ return;
#if QT_MAC_USE_COCOA
QMacCocoaAutoReleasePool pool;
OSWindowRef theWindow = static_cast<OSWindowRef>(window);
NSToolbar *macToolbar = [theWindow toolbar];
- if (macToolbar)
- [macToolbar setShowsBaselineSeparator: show];
-#endif
+ [macToolbar setShowsBaselineSeparator:show];
+#endif // QT_MAC_USE_COCOA
}
QStringList qt_mac_NSArrayToQStringList(void *nsarray)
@@ -1233,6 +1299,17 @@ CGContextRef qt_mac_graphicsContextFor(QWidget *widget)
return context;
}
+void qt_mac_dispatchPendingUpdateRequests(QWidget *widget)
+{
+ if (!widget)
+ return;
+#ifndef QT_MAC_USE_COCOA
+ HIViewRender(qt_mac_nativeview_for(widget));
+#else
+ [qt_mac_nativeview_for(widget) displayIfNeeded];
+#endif
+}
+
CGFloat qt_mac_get_scalefactor()
{
#ifndef QT_MAC_USE_COCOA
@@ -1403,4 +1480,52 @@ void qt_mac_post_retranslateAppMenu()
#endif
}
+#ifdef QT_MAC_USE_COCOA
+// This method implements the magic for the drawRectSpecial method.
+// We draw a line at the upper edge of the content view in order to
+// override the title baseline.
+void macDrawRectOnTop(void * /*OSWindowRef */window)
+{
+ OSWindowRef theWindow = static_cast<OSWindowRef>(window);
+ NSView *contentView = [theWindow contentView];
+ if(!contentView)
+ return;
+ // Get coordinates of the content view
+ NSRect contentRect = [contentView frame];
+ // Draw a line on top of the already drawn line.
+ // We need to check if we are active or not to use the proper color.
+ if([window isKeyWindow] || [window isMainWindow]) {
+ [[NSColor colorWithCalibratedRed:1.0 green:1.0 blue:1.0 alpha:1.0] set];
+ } else {
+ [[NSColor colorWithCalibratedRed:1.0 green:1.0 blue:1.0 alpha:1.0] set];
+ }
+ NSPoint origin = NSMakePoint(0, contentRect.size.height);
+ NSPoint end = NSMakePoint(contentRect.size.width, contentRect.size.height);
+ [NSBezierPath strokeLineFromPoint:origin toPoint:end];
+}
+
+// This method will (or at least should) get called only once.
+// Its mission is to find out if we are active or not. If we are active
+// we assume that we were launched via finder, otherwise we assume
+// we were called from the command line. The distinction is important,
+// since in the first case we don't need to trigger a paintEvent, while
+// in the second case we do.
+void macSyncDrawingOnFirstInvocation(void * /*OSWindowRef */window)
+{
+ OSWindowRef theWindow = static_cast<OSWindowRef>(window);
+ NSApplication *application = [NSApplication sharedApplication];
+ NSToolbar *toolbar = [window toolbar];
+ if([application isActive]) {
+ // Launched from finder
+ [toolbar setShowsBaselineSeparator:NO];
+ } else {
+ // Launched from commandline
+ [toolbar setVisible:false];
+ [toolbar setShowsBaselineSeparator:NO];
+ [toolbar setVisible:true];
+ [theWindow display];
+ }
+}
+#endif // QT_MAC_USE_COCOA
+
QT_END_NAMESPACE
diff --git a/src/gui/kernel/qt_cocoa_helpers_mac_p.h b/src/gui/kernel/qt_cocoa_helpers_mac_p.h
index 3fd62a4..5db121a 100644
--- a/src/gui/kernel/qt_cocoa_helpers_mac_p.h
+++ b/src/gui/kernel/qt_cocoa_helpers_mac_p.h
@@ -131,6 +131,8 @@ void macWindowSetHasShadow( void * /*OSWindowRef*/ window, bool hasShadow );
void macWindowFlush(void * /*OSWindowRef*/ window);
void macSendToolbarChangeEvent(QWidget *widget);
void qt_mac_updateContentBorderMetricts(void * /*OSWindowRef */window, const ::HIContentBorderMetrics &metrics);
+void qt_mac_replaceDrawRect(void * /*OSWindowRef */window, QWidgetPrivate *widget);
+void qt_mac_replaceDrawRectOriginal(void * /*OSWindowRef */window, QWidgetPrivate *widget);
void qt_mac_showBaseLineSeparator(void * /*OSWindowRef */window, bool show);
void * /*NSImage */qt_mac_create_nsimage(const QPixmap &pm);
void qt_mac_update_mouseTracking(QWidget *widget);
@@ -140,6 +142,9 @@ void qt_dispatchTabletProximityEvent(void * /*NSEvent * */ tabletEvent);
#ifdef QT_MAC_USE_COCOA
bool qt_dispatchKeyEventWithCocoa(void * /*NSEvent * */ keyEvent, QWidget *widgetToGetEvent);
void qt_cocoaChangeOverrideCursor(const QCursor &cursor);
+// These methods exists only for supporting unified mode.
+void macDrawRectOnTop(void * /*OSWindowRef */ window);
+void macSyncDrawingOnFirstInvocation(void * /*OSWindowRef */window);
#endif
void qt_mac_menu_collapseSeparators(void * /*NSMenu */ menu, bool collapse);
bool qt_dispatchKeyEvent(void * /*NSEvent * */ keyEvent, QWidget *widgetToGetEvent);
diff --git a/src/gui/kernel/qt_mac_p.h b/src/gui/kernel/qt_mac_p.h
index 7bfb257..3341ce1 100644
--- a/src/gui/kernel/qt_mac_p.h
+++ b/src/gui/kernel/qt_mac_p.h
@@ -57,6 +57,7 @@
#ifdef __OBJC__
#include <Cocoa/Cocoa.h>
+#include <objc/runtime.h>
#endif
#include <CoreServices/CoreServices.h>
diff --git a/src/gui/kernel/qt_s60_p.h b/src/gui/kernel/qt_s60_p.h
index a714221..58da302 100644
--- a/src/gui/kernel/qt_s60_p.h
+++ b/src/gui/kernel/qt_s60_p.h
@@ -155,7 +155,7 @@ class QLongTapTimer;
class QSymbianControl : public CCoeControl, public QAbstractLongTapObserver
#ifdef Q_WS_S60
-, public MAknFadedComponent
+, public MAknFadedComponent, public MEikStatusPaneObserver
#endif
{
public:
@@ -183,6 +183,7 @@ public:
#ifdef Q_WS_S60
void FadeBehindPopup(bool fade){ popupFader.FadeBehindPopup( this, this, fade); }
+ void HandleStatusPaneSizeChange();
protected: // from MAknFadedComponent
TInt CountFadedComponents() {return 1;}
diff --git a/src/gui/kernel/qwidget.cpp b/src/gui/kernel/qwidget.cpp
index fb70d7c..6f4a20f 100644
--- a/src/gui/kernel/qwidget.cpp
+++ b/src/gui/kernel/qwidget.cpp
@@ -220,6 +220,11 @@ QWidgetPrivate::QWidgetPrivate(int version)
isWidget = true;
memset(high_attributes, 0, sizeof(high_attributes));
+#if QT_MAC_USE_COCOA
+ drawRectOriginalAdded = false;
+ originalDrawMethod = true;
+ changeMethods = false;
+#endif // QT_MAC_USE_COCOA
#ifdef QWIDGET_EXTRA_DEBUG
static int count = 0;
qDebug() << "widgets" << ++count;
@@ -12309,6 +12314,28 @@ void QWidgetPrivate::_q_delayedDestroy(WId winId)
}
#endif
+#if QT_MAC_USE_COCOA
+void QWidgetPrivate::syncUnifiedMode() {
+ // The whole purpose of this method is to keep the unifiedToolbar in sync.
+ // That means making sure we either exchange the drawing methods or we let
+ // the toolbar know that it does not require to draw the baseline.
+ Q_Q(QWidget);
+ // This function makes sense only if this is a top level
+ if(!q->isWindow())
+ return;
+ OSWindowRef window = qt_mac_window_for(q);
+ if(changeMethods) {
+ // Ok, we are in documentMode.
+ if(originalDrawMethod)
+ qt_mac_replaceDrawRect(window, this);
+ } else {
+ if(!originalDrawMethod)
+ qt_mac_replaceDrawRectOriginal(window, this);
+ }
+}
+
+#endif // QT_MAC_USE_COCOA
+
QT_END_NAMESPACE
#include "moc_qwidget.cpp"
diff --git a/src/gui/kernel/qwidget_mac.mm b/src/gui/kernel/qwidget_mac.mm
index d7cd2eb..e29b755 100644
--- a/src/gui/kernel/qwidget_mac.mm
+++ b/src/gui/kernel/qwidget_mac.mm
@@ -2300,6 +2300,12 @@ void QWidgetPrivate::finishCreateWindow_sys_Cocoa(void * /*NSWindow * */ voidWin
if (q->testAttribute(Qt::WA_DropSiteRegistered))
registerDropSite(true);
transferChildren();
+
+ // Tell Cocoa explicit that we wan't the view to receive key events
+ // (regardless of focus policy) because this is how it works on other
+ // platforms (and in the carbon port):
+ if (!qApp->focusWidget())
+ [windowRef makeFirstResponder:nsview];
}
if (topExtra->posFromMove) {
diff --git a/src/gui/kernel/qwidget_p.h b/src/gui/kernel/qwidget_p.h
index 05a859c..9926b2c 100644
--- a/src/gui/kernel/qwidget_p.h
+++ b/src/gui/kernel/qwidget_p.h
@@ -774,6 +774,13 @@ public:
void finishCreateWindow_sys_Cocoa(void * /*NSWindow * */ windowRef);
void syncCocoaMask();
void finishCocoaMaskSetup();
+ void syncUnifiedMode();
+ // Did we add the drawRectOriginal method?
+ bool drawRectOriginalAdded;
+ // Is the original drawRect method available?
+ bool originalDrawMethod;
+ // Do we need to change the methods?
+ bool changeMethods;
#endif
void determineWindowClass();
void transferChildren();
diff --git a/src/gui/kernel/qwidget_s60.cpp b/src/gui/kernel/qwidget_s60.cpp
index bfa7050..a0429d3 100644
--- a/src/gui/kernel/qwidget_s60.cpp
+++ b/src/gui/kernel/qwidget_s60.cpp
@@ -387,16 +387,7 @@ void QWidgetPrivate::create_sys(WId window, bool /* initializeWindow */, bool de
| EPointerFilterMove | EPointerFilterDrag, 0);
drawableWindow->EnableVisibilityChangeEvents();
- if (!isOpaque) {
- RWindow *const window = static_cast<RWindow *>(drawableWindow);
-#ifdef Q_SYMBIAN_SEMITRANSPARENT_BG_SURFACE
- window->SetSurfaceTransparency(true);
-#else
- const TDisplayMode displayMode = static_cast<TDisplayMode>(window->SetRequiredDisplayMode(EColor16MA));
- if (window->SetTransparencyAlphaChannel() == KErrNone)
- window->SetBackgroundColor(TRgb(255, 255, 255, 0));
-#endif
- }
+ s60UpdateIsOpaque();
}
q->setAttribute(Qt::WA_WState_Created);
@@ -488,6 +479,47 @@ void QWidgetPrivate::show_sys()
QSymbianControl *id = static_cast<QSymbianControl *>(q->internalWinId());
+#ifdef Q_WS_S60
+ // Lazily initialize the S60 screen furniture when the first window is shown.
+ if (!QApplication::testAttribute(Qt::AA_S60DontConstructApplicationPanes)
+ && !S60->buttonGroupContainer() && !S60->statusPane()) {
+
+ bool isFullscreen = q->windowState() & Qt::WindowFullScreen;
+ bool cbaRequested = q->windowFlags() & Qt::WindowSoftkeysVisibleHint;
+
+ // If the window is fullscreen and has not explicitly requested that the CBA be visible
+ // we delay the creation even more.
+ if ((!isFullscreen || cbaRequested) && !q->testAttribute(Qt::WA_DontShowOnScreen)) {
+
+ // Create the status pane and CBA here
+ CEikAppUi *ui = static_cast<CEikAppUi *>(S60->appUi());
+ MEikAppUiFactory *factory = CEikonEnv::Static()->AppUiFactory();
+ TRAP_IGNORE(factory->ReadAppInfoResourceL(0, ui));
+ if (S60->buttonGroupContainer())
+ S60->buttonGroupContainer()->SetCommandSetL(R_AVKON_SOFTKEYS_EMPTY_WITH_IDS);
+
+ if (S60->statusPane()) {
+ // Use QDesktopWidget as the status pane observer to proxy for the AppUi.
+ // Can't use AppUi directly because it privately inherits from MEikStatusPaneObserver.
+ QSymbianControl *desktopControl = static_cast<QSymbianControl *>(QApplication::desktop()->winId());
+ S60->statusPane()->SetObserver(desktopControl);
+
+ // Hide the status pane if fullscreen OR
+ // Fill client area if maximized OR
+ // Put window below status pane unless the window has an explicit position.
+ if (isFullscreen) {
+ S60->statusPane()->MakeVisible(false);
+ } else if (q->windowState() & Qt::WindowMaximized) {
+ TRect r = static_cast<CEikAppUi*>(S60->appUi())->ClientRect();
+ id->SetExtent(r.iTl, r.Size());
+ } else if (!q->testAttribute(Qt::WA_Moved)) {
+ id->SetPosition(static_cast<CEikAppUi*>(S60->appUi())->ClientRect().iTl);
+ }
+ }
+ }
+ }
+#endif
+
id->MakeVisible(true);
if(q->isWindow())
@@ -1063,6 +1095,9 @@ void QWidget::setWindowState(Qt::WindowStates newstate)
return;
if (isWindow()) {
+ createWinId();
+ Q_ASSERT(testAttribute(Qt::WA_WState_Created));
+
const bool wasResized = testAttribute(Qt::WA_Resized);
const bool wasMoved = testAttribute(Qt::WA_Moved);
@@ -1088,35 +1123,35 @@ void QWidget::setWindowState(Qt::WindowStates newstate)
if (buttonGroup) {
// Visibility
buttonGroup->MakeVisible(visible || (isFullscreen && cbaRequested));
-
- // Responsiviness
- CEikCba *cba = static_cast<CEikCba *>( buttonGroup->ButtonGroup() ); // downcast from MEikButtonGroup
- TUint cbaFlags = cba->ButtonGroupFlags();
- if(windowFlags() & Qt::WindowSoftkeysRespondHint)
- cbaFlags |= EAknCBAFlagRespondWhenInvisible;
- else
- cbaFlags &= ~EAknCBAFlagRespondWhenInvisible;
- cba->SetButtonGroupFlags(cbaFlags);
}
#endif // Q_WS_S60
- createWinId();
- Q_ASSERT(testAttribute(Qt::WA_WState_Created));
// Ensure the initial size is valid, since we store it as normalGeometry below.
if (!wasResized && !isVisible())
adjustSize();
QTLWExtra *top = d->topData();
- const QRect normalGeometry = (top->normalGeometry.width() < 0) ? geometry() : top->normalGeometry;
-
+ QRect normalGeometry = (top->normalGeometry.width() < 0) ? geometry() : top->normalGeometry;
const bool cbaVisibilityHint = windowFlags() & Qt::WindowSoftkeysVisibleHint;
- if (newstate & Qt::WindowFullScreen && !cbaVisibilityHint)
- setGeometry(qApp->desktop()->screenGeometry(this));
- else if (newstate & Qt::WindowMaximized || ((newstate & Qt::WindowFullScreen) && cbaVisibilityHint))
- setGeometry(qApp->desktop()->availableGeometry(this));
- else
+ if (newstate & Qt::WindowFullScreen && !cbaVisibilityHint) {
+ window->SetExtentToWholeScreen();
+ } else if (newstate & Qt::WindowMaximized || ((newstate & Qt::WindowFullScreen) && cbaVisibilityHint)) {
+ TRect maxExtent = qt_QRect2TRect(qApp->desktop()->availableGeometry(this));
+ window->SetExtent(maxExtent.iTl, maxExtent.Size());
+ } else {
+#ifdef Q_WS_S60
+ // With delayed creation of S60 app panes, the normalGeometry calculated above is not
+ // accurate because it did not consider the status pane. This means that when returning
+ // normal mode after showing the status pane, the geometry would overlap so we should
+ // move it if it never had an explicit position.
+ if (!wasMoved && statusPane && visible) {
+ TPoint tl = static_cast<CEikAppUi*>(S60->appUi())->ClientRect().iTl;
+ normalGeometry.setTopLeft(QPoint(tl.iX, tl.iY));
+ }
+#endif
setGeometry(normalGeometry);
+ }
//restore normal geometry
top->normalGeometry = normalGeometry;
diff --git a/src/gui/painting/qprintengine_ps.cpp b/src/gui/painting/qprintengine_ps.cpp
index ac94de3..28e9a7a 100644
--- a/src/gui/painting/qprintengine_ps.cpp
+++ b/src/gui/painting/qprintengine_ps.cpp
@@ -485,7 +485,6 @@ void QPSPrintEnginePrivate::emitHeader(bool finished)
QByteArray header;
QPdf::ByteStream s(&header);
- s << "%!PS-Adobe-1.0";
qreal scale = 72. / ((qreal) q->metric(QPaintDevice::PdmDpiY));
QRect pageRect = this->pageRect();
@@ -497,28 +496,32 @@ void QPSPrintEnginePrivate::emitHeader(bool finished)
int width = pageRect.width();
int height = pageRect.height();
if (finished && pageCount == 1 && copies == 1 &&
- ((fullPage && qt_gen_epsf) || (outputFileName.endsWith(QLatin1String(".eps"))))
- ) {
+ ((fullPage && qt_gen_epsf) || (outputFileName.endsWith(QLatin1String(".eps")))))
+ {
+ // According to the EPSF 3.0 spec it is required that the PS
+ // version is PS-Adobe-3.0
+ s << "%!PS-Adobe-3.0";
if (!boundingBox.isValid())
boundingBox.setRect(0, 0, width, height);
if (orientation == QPrinter::Landscape) {
if (!fullPage)
boundingBox.translate(-mleft, -mtop);
s << " EPSF-3.0\n%%BoundingBox: "
- << (int)(printer->height() - boundingBox.bottom())*scale // llx
- << (int)(printer->width() - boundingBox.right())*scale - 1 // lly
- << (int)(printer->height() - boundingBox.top())*scale + 1 // urx
- << (int)(printer->width() - boundingBox.left())*scale; // ury
+ << int((printer->height() - boundingBox.bottom())*scale) // llx
+ << int((printer->width() - boundingBox.right())*scale - 1) // lly
+ << int((printer->height() - boundingBox.top())*scale + 1) // urx
+ << int((printer->width() - boundingBox.left())*scale); // ury
} else {
if (!fullPage)
boundingBox.translate(mleft, -mtop);
s << " EPSF-3.0\n%%BoundingBox: "
- << (int)(boundingBox.left())*scale
- << (int)(printer->height() - boundingBox.bottom())*scale - 1
- << (int)(boundingBox.right())*scale + 1
- << (int)(printer->height() - boundingBox.top())*scale;
+ << int((boundingBox.left())*scale)
+ << int((printer->height() - boundingBox.bottom())*scale - 1)
+ << int((boundingBox.right())*scale + 1)
+ << int((printer->height() - boundingBox.top())*scale);
}
} else {
+ s << "%!PS-Adobe-1.0";
int w = width + (fullPage ? 0 : mleft + mright);
int h = height + (fullPage ? 0 : mtop + mbottom);
w = (int)(w*scale);
diff --git a/src/gui/painting/qprintengine_win.cpp b/src/gui/painting/qprintengine_win.cpp
index ea9dc5d..dd4de99 100644
--- a/src/gui/painting/qprintengine_win.cpp
+++ b/src/gui/painting/qprintengine_win.cpp
@@ -965,12 +965,13 @@ void QWin32PrintEnginePrivate::queryDefault()
return;
QStringList info = output.split(QLatin1Char(','));
- if (info.size() > 0) {
+ int infoSize = info.size();
+ if (infoSize > 0) {
if (name.isEmpty())
name = info.at(0);
- if (program.isEmpty())
+ if (program.isEmpty() && infoSize > 1)
program = info.at(1);
- if (port.isEmpty())
+ if (port.isEmpty() && infoSize > 2)
port = info.at(2);
}
}
diff --git a/src/gui/s60framework/qs60mainappui.cpp b/src/gui/s60framework/qs60mainappui.cpp
index 3b5b9d3..feffc9f 100644
--- a/src/gui/s60framework/qs60mainappui.cpp
+++ b/src/gui/s60framework/qs60mainappui.cpp
@@ -112,16 +112,10 @@ void QS60MainAppUi::ConstructL()
// ENoAppResourceFile and ENonStandardResourceFile makes UI to work without
// resource files in most SDKs. S60 3rd FP1 public seems to require resource file
// even these flags are defined
- TInt flags = CAknAppUi::EAknEnableSkin;
- if (QApplication::testAttribute(Qt::AA_S60DontConstructApplicationPanes)) {
- flags |= CAknAppUi::ENoScreenFurniture | CAknAppUi::ENonStandardResourceFile;
- }
+ TInt flags = CAknAppUi::EAknEnableSkin
+ | CAknAppUi::ENoScreenFurniture
+ | CAknAppUi::ENonStandardResourceFile;
BaseConstructL(flags);
-
- if (!QApplication::testAttribute(Qt::AA_S60DontConstructApplicationPanes)) {
- CEikButtonGroupContainer* nativeContainer = Cba();
- nativeContainer->SetCommandSetL(R_AVKON_SOFTKEYS_EMPTY_WITH_IDS);
- }
}
/*!
diff --git a/src/gui/styles/qs60style.cpp b/src/gui/styles/qs60style.cpp
index 7587343..90b8be3 100644
--- a/src/gui/styles/qs60style.cpp
+++ b/src/gui/styles/qs60style.cpp
@@ -92,10 +92,10 @@ static const qreal goldenRatio = 1.618;
const layoutHeader QS60StylePrivate::m_layoutHeaders[] = {
// *** generated layout data ***
-{240,320,1,17,"QVGA Landscape"},
-{320,240,1,17,"QVGA Portrait"},
-{360,640,1,17,"NHD Landscape"},
-{640,360,1,17,"NHD Portrait"},
+{240,320,1,18,"QVGA Landscape"},
+{320,240,1,18,"QVGA Portrait"},
+{360,640,1,18,"NHD Landscape"},
+{640,360,1,18,"NHD Portrait"},
{352,800,1,12,"E90 Landscape"}
// *** End of generated data ***
};
@@ -104,11 +104,11 @@ const int QS60StylePrivate::m_numberOfLayouts =
const short QS60StylePrivate::data[][MAX_PIXELMETRICS] = {
// *** generated pixel metrics ***
-{5,0,-909,0,0,2,0,0,-1,7,12,19,13,13,6,200,-909,-909,-909,20,13,2,0,0,21,7,18,0,3,3,1,-909,-909,0,1,0,0,12,20,15,15,18,18,1,115,18,0,-909,-909,-909,-909,0,0,16,2,-909,0,0,-909,16,-909,-909,-909,-909,32,18,55,24,55,4,4,4,9,13,-909,5,51,11,5,0,3,3,6,8,3,3,-909,2,-909,-909,-909,-909,5,5,3,1, 106},
-{5,0,-909,0,0,1,0,0,-1,8,14,22,15,15,7,164,-909,-909,-909,19,15,2,0,0,21,8,27,0,4,4,1,-909,-909,0,7,6,0,13,23,17,17,21,21,7,115,21,0,-909,-909,-909,-909,0,0,15,1,-909,0,0,-909,15,-909,-909,-909,-909,32,21,65,27,65,3,3,5,10,15,-909,5,58,13,5,0,4,4,7,9,4,4,-909,2,-909,-909,-909,-909,6,6,3,1, 106},
-{7,0,-909,0,0,2,0,0,-1,25,69,28,19,19,9,258,-909,-909,-909,23,19,26,0,0,32,25,72,0,5,5,2,-909,-909,0,7,21,0,17,29,22,22,27,27,7,173,29,0,-909,-909,-909,-909,0,0,25,2,-909,0,0,-909,25,-909,-909,-909,-909,87,27,77,35,77,13,13,6,8,19,-909,7,74,19,7,0,5,5,8,12,5,5,-909,3,-909,-909,-909,-909,7,7,3,1, 135},
-{7,0,-909,0,0,2,0,0,-1,25,68,28,19,19,9,258,-909,-909,-909,31,19,6,0,0,32,25,60,0,5,5,2,-909,-909,0,7,32,0,17,29,22,22,27,27,7,173,29,0,-909,-909,-909,-909,0,0,26,2,-909,0,0,-909,26,-909,-909,-909,-909,87,27,96,35,96,12,12,6,8,19,-909,7,74,22,7,0,5,5,8,12,5,5,-909,3,-909,-909,-909,-909,7,7,3,1, 135},
-{7,0,-909,0,0,2,0,0,-1,10,20,27,18,18,9,301,-909,-909,-909,29,18,5,0,0,35,7,32,0,5,5,2,-909,-909,0,2,8,0,16,28,21,21,26,26,2,170,26,0,-909,-909,-909,-909,0,0,21,6,-909,0,0,-909,-909,-909,-909,-909,-909,54,26,265,34,265,5,5,6,3,18,-909,7,72,19,7,0,5,6,8,11,6,5,-909,2,-909,-909,-909,-909,5,5,3,1, 106}
+{5,0,-909,0,0,2,0,0,-1,7,12,19,13,13,6,200,-909,-909,-909,20,13,2,0,0,21,7,18,30,3,3,1,-909,-909,0,1,0,0,12,20,15,15,18,18,1,115,18,0,-909,-909,-909,-909,0,0,16,2,-909,0,0,-909,16,-909,-909,-909,-909,32,18,55,24,55,4,4,4,9,13,-909,5,51,11,5,0,3,3,6,8,3,3,-909,2,-909,-909,-909,-909,5,5,3,1, 106},
+{5,0,-909,0,0,1,0,0,-1,8,14,22,15,15,7,164,-909,-909,-909,19,15,2,0,0,21,8,27,28,4,4,1,-909,-909,0,7,6,0,13,23,17,17,21,21,7,115,21,0,-909,-909,-909,-909,0,0,15,1,-909,0,0,-909,15,-909,-909,-909,-909,32,21,65,27,65,3,3,5,10,15,-909,5,58,13,5,0,4,4,7,9,4,4,-909,2,-909,-909,-909,-909,6,6,3,1, 106},
+{7,0,-909,0,0,2,0,0,-1,25,69,28,19,19,9,258,-909,-909,-909,23,19,26,0,0,32,25,72,44,5,5,2,-909,-909,0,7,21,0,17,29,22,22,27,27,7,173,29,0,-909,-909,-909,-909,0,0,25,2,-909,0,0,-909,25,-909,-909,-909,-909,87,27,77,35,77,13,13,6,8,19,-909,7,74,19,7,0,5,5,8,12,5,5,-909,3,-909,-909,-909,-909,7,7,3,1, 135},
+{7,0,-909,0,0,2,0,0,-1,25,68,28,19,19,9,258,-909,-909,-909,31,19,6,0,0,32,25,60,52,5,5,2,-909,-909,0,7,32,0,17,29,22,22,27,27,7,173,29,0,-909,-909,-909,-909,0,0,26,2,-909,0,0,-909,26,-909,-909,-909,-909,87,27,96,35,96,12,12,6,8,19,-909,7,74,22,7,0,5,5,8,12,5,5,-909,3,-909,-909,-909,-909,7,7,3,1, 135},
+{7,0,-909,0,0,2,0,0,-1,10,20,27,18,18,9,301,-909,-909,-909,29,18,5,0,0,35,7,32,30,5,5,2,-909,-909,0,2,8,0,16,28,21,21,26,26,2,170,26,0,-909,-909,-909,-909,0,0,21,6,-909,0,0,-909,-909,-909,-909,-909,-909,54,26,265,34,265,5,5,6,3,18,-909,7,72,19,7,0,5,6,8,11,6,5,-909,2,-909,-909,-909,-909,5,5,3,1, 106}
// *** End of generated data ***
};
@@ -651,6 +651,8 @@ void QS60StylePrivate::setFont(QWidget *widget) const
fontCategory = QS60StyleEnums::FC_Title;
} else if (qobject_cast<QMessageBox *>(widget)){
fontCategory = QS60StyleEnums::FC_Primary;
+ } else if (qobject_cast<QMenu *>(widget)){
+ fontCategory = QS60StyleEnums::FC_Primary;
}
if (fontCategory != QS60StyleEnums::FC_Undefined) {
const bool resolveFontSize = widget->testAttribute(Qt::WA_SetFont)
@@ -1744,6 +1746,9 @@ void QS60Style::drawControl(ControlElement element, const QStyleOption *option,
optionCheckBox.QStyleOptionMenuItem::operator=(*menuItem);
optionCheckBox.rect.setWidth(pixelMetric(PM_IndicatorWidth));
optionCheckBox.rect.setHeight(pixelMetric(PM_IndicatorHeight));
+ optionCheckBox.rect.moveCenter(QPoint(
+ optionCheckBox.rect.center().x(),
+ menuItem->rect.center().y()));
const int moveByX = optionCheckBox.rect.width() + vSpacing;
if (optionMenuItem.direction == Qt::LeftToRight) {
textRect.translate(moveByX, 0);
@@ -2424,6 +2429,10 @@ int QS60Style::pixelMetric(PixelMetric metric, const QStyleOption *option, const
if (metricValue == KNotFound)
metricValue = QCommonStyle::pixelMetric(metric, option, widget);
+ // Menu scrollers should be set to zero height for combobox popups
+ if (metric == PM_MenuScrollerHeight && !qobject_cast<const QMenu *>(widget))
+ metricValue = 0;
+
//if layout direction is mirrored, switch left and right border margins
if (option && option->direction == Qt::RightToLeft) {
if (metric == PM_LayoutLeftMargin)
@@ -2483,7 +2492,14 @@ QSize QS60Style::sizeFromContents(ContentsType ct, const QStyleOption *opt,
sz.setHeight(naviPaneSize.height());
}
break;
+ case CT_MenuItem:
case CT_ItemViewItem:
+ if (const QStyleOptionMenuItem *menuItem = qstyleoption_cast<const QStyleOptionMenuItem *>(opt)) {
+ if (menuItem->menuItemType == QStyleOptionMenuItem::Separator) {
+ sz = QSize();
+ break;
+ }
+ }
sz = QCommonStyle::sizeFromContents( ct, opt, csz, widget);
if (QS60StylePrivate::isTouchSupported())
//Make itemview easier to use in touch devices
@@ -2564,6 +2580,9 @@ int QS60Style::styleHint(StyleHint sh, const QStyleOption *opt, const QWidget *w
case SH_Menu_SelectionWrap:
retValue = true;
break;
+ case SH_Menu_MouseTracking:
+ retValue = true;
+ break;
case SH_ItemView_ShowDecorationSelected:
retValue = true;
break;
@@ -3150,6 +3169,12 @@ bool QS60Style::event(QEvent *e)
#ifdef QT_KEYPAD_NAVIGATION
case QEvent::FocusIn:
if (QWidget *focusWidget = QApplication::focusWidget()) {
+
+ // Menus and combobox popups do not draw focus frame around them
+ if (qobject_cast<QComboBoxListView *>(focusWidget) ||
+ qobject_cast<QMenu *>(focusWidget))
+ break;
+
if (!d->m_focusFrame)
d->m_focusFrame = new QFocusFrame(focusWidget);
d->m_focusFrame->setWidget(focusWidget);
diff --git a/src/gui/styles/qs60style_s60.cpp b/src/gui/styles/qs60style_s60.cpp
index 58a7159..55aa6b0 100644
--- a/src/gui/styles/qs60style_s60.cpp
+++ b/src/gui/styles/qs60style_s60.cpp
@@ -310,7 +310,7 @@ const partMapEntry QS60StyleModeSpecifics::m_partMap[] = {
/* SP_QsnFrPopupSideB */ {KAknsIIDQsnFrPopupSideB, ENoDraw, ES60_All, -1,-1},
/* SP_QsnFrPopupSideL */ {KAknsIIDQsnFrPopupSideL, ENoDraw, ES60_All, -1,-1},
/* SP_QsnFrPopupSideR */ {KAknsIIDQsnFrPopupSideR, ENoDraw, ES60_All, -1,-1},
- /* SP_QsnFrPopupCenter */ {KAknsIIDQsnFrPopupCenter, ENoDraw, ES60_All, -1,-1},
+ /* SP_QsnFrPopupCenter */ {KAknsIIDQsnFrPopupCenterSubmenu, ENoDraw, ES60_All, -1,-1},
// ToolTip graphics different in 3.1 vs. 3.2+.
/* SP_QsnFrPopupPreviewCornerTl */ {KAknsIIDQsnFrPopupCornerTl, ENoDraw, ES60_3_1, EAknsMajorSkin, 0x19c5}, /* KAknsIIDQsnFrPopupPreviewCornerTl */
@@ -919,7 +919,7 @@ QPixmap QS60StyleModeSpecifics::createSkinnedGraphicsLX(QS60StylePrivate::SkinFr
result = fromFbsBitmap(frame, NULL, flags, targetSize);
}
} else {
- TDisplayMode maskDepth = EGray2;
+ TDisplayMode maskDepth = EGray256;
// Query the skin item for possible frame graphics mask details.
if (skinInstance) {
CAknsMaskedBitmapItemData* skinMaskedBmp = static_cast<CAknsMaskedBitmapItemData*>(
@@ -983,6 +983,10 @@ void QS60StyleModeSpecifics::frameIdAndCenterId(QS60StylePrivate::SkinFrameEleme
frameId.Set(KAknsIIDQsnFrPopupSub);
}
break;
+ case QS60StylePrivate::SF_PopupBackground:
+ centerId.Set(KAknsIIDQsnFrPopupCenterSubmenu);
+ frameId.Set(KAknsIIDQsnFrPopupSub);
+ break;
case QS60StylePrivate::SF_PanelBackground:
// remove center piece for panel graphics, so that only border is drawn
centerId.Set(KAknsIIDNone);
diff --git a/src/gui/styles/qstylesheetstyle.cpp b/src/gui/styles/qstylesheetstyle.cpp
index 81b923b..515b6c7 100644
--- a/src/gui/styles/qstylesheetstyle.cpp
+++ b/src/gui/styles/qstylesheetstyle.cpp
@@ -1539,7 +1539,9 @@ QVector<QCss::StyleRule> QStyleSheetStyle::styleRules(const QWidget *w) const
QHash<const void *, StyleSheet>::const_iterator defaultCacheIt = styleSheetCache->constFind(baseStyle());
if (defaultCacheIt == styleSheetCache->constEnd()) {
defaultSs = getDefaultStyleSheet();
- styleSheetCache->insert(baseStyle(), defaultSs);
+ QStyle *bs = baseStyle();
+ styleSheetCache->insert(bs, defaultSs);
+ QObject::connect(bs, SIGNAL(destroyed(QObject*)), this, SLOT(styleDestroyed(QObject*)), Qt::UniqueConnection);
} else {
defaultSs = defaultCacheIt.value();
}
@@ -2666,6 +2668,11 @@ void QStyleSheetStyle::widgetDestroyed(QObject *o)
autoFillDisabledWidgets->remove((const QWidget *)o);
}
+void QStyleSheetStyle::styleDestroyed(QObject *o)
+{
+ styleSheetCache->remove(o);
+}
+
/*!
* Make sure that the cache will be clean by connecting destroyed if needed.
* return false if the widget is not stylable;
diff --git a/src/gui/styles/qstylesheetstyle_p.h b/src/gui/styles/qstylesheetstyle_p.h
index 50abef9..fd81437 100644
--- a/src/gui/styles/qstylesheetstyle_p.h
+++ b/src/gui/styles/qstylesheetstyle_p.h
@@ -147,6 +147,7 @@ protected:
private Q_SLOTS:
void widgetDestroyed(QObject *);
+ void styleDestroyed(QObject *);
private:
int refcount;
diff --git a/src/gui/text/qfont.cpp b/src/gui/text/qfont.cpp
index 24887b5..21a31a3 100644
--- a/src/gui/text/qfont.cpp
+++ b/src/gui/text/qfont.cpp
@@ -2616,10 +2616,8 @@ void QFontCache::cleanup()
} QT_CATCH (const std::bad_alloc &) {
// no cache - just ignore
}
- if (cache && cache->hasLocalData()) {
- cache->localData()->clear();
+ if (cache && cache->hasLocalData())
cache->setLocalData(0);
- }
}
#endif // QT_NO_THREAD
@@ -2631,6 +2629,7 @@ QFontCache::QFontCache()
QFontCache::~QFontCache()
{
+ clear();
{
EngineDataCache::ConstIterator it = engineDataCache.constBegin(),
end = engineDataCache.constEnd();
diff --git a/src/gui/text/qfontdatabase.cpp b/src/gui/text/qfontdatabase.cpp
index ae5e9ca..ff29462 100644
--- a/src/gui/text/qfontdatabase.cpp
+++ b/src/gui/text/qfontdatabase.cpp
@@ -598,10 +598,10 @@ static QList<QFontDatabase::WritingSystem> determineWritingSystemsFromTrueTypeBi
#if defined(Q_OS_SYMBIAN) && defined(QT_NO_FREETYPE)
// class with virtual destructor, derived in qfontdatabase_s60.cpp
-class QFontDatabaseS60Store
+class QSymbianFontDatabaseExtras
{
public:
- virtual ~QFontDatabaseS60Store() {}
+ virtual ~QSymbianFontDatabaseExtras() {}
};
#endif
@@ -614,7 +614,7 @@ public:
, stream(0)
#endif
#if defined(Q_OS_SYMBIAN) && defined(QT_NO_FREETYPE)
- , s60Store(0)
+ , symbianExtras(0)
#endif
{ }
~QFontDatabasePrivate() {
@@ -628,9 +628,9 @@ public:
families = 0;
count = 0;
#if defined(Q_OS_SYMBIAN) && defined(QT_NO_FREETYPE)
- if (s60Store) {
- delete s60Store;
- s60Store = 0;
+ if (symbianExtras) {
+ delete symbianExtras;
+ symbianExtras = 0;
}
#endif
// don't clear the memory fonts!
@@ -675,7 +675,7 @@ public:
QDataStream *stream;
QStringList fallbackFamilies;
#elif defined(Q_OS_SYMBIAN) && defined(QT_NO_FREETYPE)
- const QFontDatabaseS60Store *s60Store;
+ const QSymbianFontDatabaseExtras *symbianExtras;
#endif
};
diff --git a/src/gui/text/qfontdatabase_s60.cpp b/src/gui/text/qfontdatabase_s60.cpp
index ef5e0c4..3ad0806 100644
--- a/src/gui/text/qfontdatabase_s60.cpp
+++ b/src/gui/text/qfontdatabase_s60.cpp
@@ -92,22 +92,22 @@ QFileInfoList alternativeFilePaths(const QString &path, const QStringList &nameF
}
#if defined(QT_NO_FREETYPE)
-class QFontDatabaseS60StoreImplementation : public QFontDatabaseS60Store
+class QSymbianFontDatabaseExtrasImplementation : public QSymbianFontDatabaseExtras
{
public:
- QFontDatabaseS60StoreImplementation();
- ~QFontDatabaseS60StoreImplementation();
+ QSymbianFontDatabaseExtrasImplementation();
+ ~QSymbianFontDatabaseExtrasImplementation();
- const QFontEngineS60Extensions *extension(const QString &typeface) const;
+ const QSymbianTypeFaceExtras *extras(const QString &typeface) const;
private:
RHeap* m_heap;
CFontStore *m_store;
COpenFontRasterizer *m_rasterizer;
- mutable QHash<QString, const QFontEngineS60Extensions *> m_extensions;
+ mutable QHash<QString, const QSymbianTypeFaceExtras *> m_extras;
};
-QFontDatabaseS60StoreImplementation::QFontDatabaseS60StoreImplementation()
+QSymbianFontDatabaseExtrasImplementation::QSymbianFontDatabaseExtrasImplementation()
{
m_heap = User::ChunkHeap(NULL, 0x1000, 0x100000);
QT_TRAP_THROWING(
@@ -127,10 +127,10 @@ QFontDatabaseS60StoreImplementation::QFontDatabaseS60StoreImplementation()
QT_TRAP_THROWING(m_store->AddFileL(fontFilePtr));
}
}
-QFontDatabaseS60StoreImplementation::~QFontDatabaseS60StoreImplementation()
+QSymbianFontDatabaseExtrasImplementation::~QSymbianFontDatabaseExtrasImplementation()
{
- typedef QHash<QString, const QFontEngineS60Extensions *>::iterator iterator;
- for (iterator p = m_extensions.begin(); p != m_extensions.end(); ++p) {
+ typedef QHash<QString, const QSymbianTypeFaceExtras *>::iterator iterator;
+ for (iterator p = m_extras.begin(); p != m_extras.end(); ++p) {
m_store->ReleaseFont((*p)->fontOwner());
delete *p;
}
@@ -156,9 +156,9 @@ COpenFont* OpenFontFromBitmapFont(const CBitmapFont* aBitmapFont)
}
#endif // FNTSTORE_H_INLINES_SUPPORT_FMM
-const QFontEngineS60Extensions *QFontDatabaseS60StoreImplementation::extension(const QString &typeface) const
+const QSymbianTypeFaceExtras *QSymbianFontDatabaseExtrasImplementation::extras(const QString &typeface) const
{
- if (!m_extensions.contains(typeface)) {
+ if (!m_extras.contains(typeface)) {
CFont* font = NULL;
TFontSpec spec(qt_QString2TPtrC(typeface), 1);
spec.iHeight = 1;
@@ -171,9 +171,9 @@ const QFontEngineS60Extensions *QFontDatabaseS60StoreImplementation::extension(c
#else
OpenFontFromBitmapFont(bitmapFont);
#endif // FNTSTORE_H_INLINES_SUPPORT_FMM
- m_extensions.insert(typeface, new QFontEngineS60Extensions(font, openFont));
+ m_extras.insert(typeface, new QSymbianTypeFaceExtras(font, openFont));
}
- return m_extensions.value(typeface);
+ return m_extras.value(typeface);
}
#else
class QFontEngineFTS60 : public QFontEngineFT
@@ -240,14 +240,14 @@ static void initializeDb()
return;
#if defined(QT_NO_FREETYPE)
- if (!db->s60Store)
- db->s60Store = new QFontDatabaseS60StoreImplementation;
+ if (!db->symbianExtras)
+ db->symbianExtras = new QSymbianFontDatabaseExtrasImplementation;
QSymbianFbsHeapLock lock(QSymbianFbsHeapLock::Unlock);
const int numTypeFaces = QS60Data::screenDevice()->NumTypefaces();
- const QFontDatabaseS60StoreImplementation *store =
- static_cast<const QFontDatabaseS60StoreImplementation*>(db->s60Store);
+ const QSymbianFontDatabaseExtrasImplementation *dbExtras =
+ static_cast<const QSymbianFontDatabaseExtrasImplementation*>(db->symbianExtras);
bool fontAdded = false;
for (int i = 0; i < numTypeFaces; i++) {
TTypefaceSupport typefaceSupport;
@@ -273,8 +273,8 @@ static void initializeDb()
style->smoothScalable = typefaceSupport.iIsScalable;
style->pixelSize(0, true);
- const QFontEngineS60Extensions *extension = store->extension(familyName);
- const QByteArray os2Table = extension->getSfntTable(MAKE_TAG('O', 'S', '/', '2'));
+ const QSymbianTypeFaceExtras *typeFaceExtras = dbExtras->extras(familyName);
+ const QByteArray os2Table = typeFaceExtras->getSfntTable(MAKE_TAG('O', 'S', '/', '2'));
const unsigned char* data = reinterpret_cast<const unsigned char*>(os2Table.constData());
const unsigned char* ulUnicodeRange = data + 42;
quint32 unicodeRange[4] = {
@@ -394,10 +394,10 @@ QFontEngine *QFontDatabase::findFont(int script, const QFontPrivate *, const QFo
QFontDef request = req;
request.family = fontFamily;
#if defined(QT_NO_FREETYPE)
- const QFontDatabaseS60StoreImplementation *store =
- static_cast<const QFontDatabaseS60StoreImplementation*>(db->s60Store);
- const QFontEngineS60Extensions *extension = store->extension(fontFamily);
- fe = new QFontEngineS60(request, extension);
+ const QSymbianFontDatabaseExtrasImplementation *dbExtras =
+ static_cast<const QSymbianFontDatabaseExtrasImplementation*>(db->symbianExtras);
+ const QSymbianTypeFaceExtras *typeFaceExtras = dbExtras->extras(fontFamily);
+ fe = new QFontEngineS60(request, typeFaceExtras);
#else
QFontEngine::FaceId faceId;
const QtFontFamily * const reqQtFontFamily = db->family(fontFamily);
diff --git a/src/gui/text/qfontengine_s60.cpp b/src/gui/text/qfontengine_s60.cpp
index c9ff661..a9960e4 100644
--- a/src/gui/text/qfontengine_s60.cpp
+++ b/src/gui/text/qfontengine_s60.cpp
@@ -53,7 +53,7 @@
QT_BEGIN_NAMESPACE
-QFontEngineS60Extensions::QFontEngineS60Extensions(CFont* fontOwner, COpenFont *font)
+QSymbianTypeFaceExtras::QSymbianTypeFaceExtras(CFont* fontOwner, COpenFont *font)
: m_font(font)
, m_cmap(0)
, m_symbolCMap(false)
@@ -68,7 +68,7 @@ QFontEngineS60Extensions::QFontEngineS60Extensions(CFont* fontOwner, COpenFont *
Q_ASSERT(m_shapingExtension && m_trueTypeExtension);
}
-QByteArray QFontEngineS60Extensions::getSfntTable(uint tag) const
+QByteArray QSymbianTypeFaceExtras::getSfntTable(uint tag) const
{
Q_ASSERT(m_trueTypeExtension->HasTrueTypeTable(tag));
TInt error = KErrNone;
@@ -79,7 +79,7 @@ QByteArray QFontEngineS60Extensions::getSfntTable(uint tag) const
return result;
}
-bool QFontEngineS60Extensions::getSfntTableData(uint tag, uchar *buffer, uint *length) const
+bool QSymbianTypeFaceExtras::getSfntTableData(uint tag, uchar *buffer, uint *length) const
{
if (!m_trueTypeExtension->HasTrueTypeTable(tag))
return false;
@@ -104,7 +104,7 @@ bool QFontEngineS60Extensions::getSfntTableData(uint tag, uchar *buffer, uint *l
return result;
}
-const unsigned char *QFontEngineS60Extensions::cmap() const
+const unsigned char *QSymbianTypeFaceExtras::cmap() const
{
if (!m_cmap) {
m_cmapTable = getSfntTable(MAKE_TAG('c', 'm', 'a', 'p'));
@@ -114,7 +114,7 @@ const unsigned char *QFontEngineS60Extensions::cmap() const
return m_cmap;
}
-QPainterPath QFontEngineS60Extensions::glyphOutline(glyph_t glyph) const
+QPainterPath QSymbianTypeFaceExtras::glyphOutline(glyph_t glyph) const
{
QPainterPath result;
QPolygonF polygon;
@@ -134,7 +134,7 @@ QPainterPath QFontEngineS60Extensions::glyphOutline(glyph_t glyph) const
return result;
}
-CFont *QFontEngineS60Extensions::fontOwner() const
+CFont *QSymbianTypeFaceExtras::fontOwner() const
{
return m_fontOwner;
}
@@ -192,8 +192,8 @@ void QFontEngineS60::releaseFont(CFont *&font)
}
}
-QFontEngineS60::QFontEngineS60(const QFontDef &request, const QFontEngineS60Extensions *extensions)
- : m_extensions(extensions)
+QFontEngineS60::QFontEngineS60(const QFontDef &request, const QSymbianTypeFaceExtras *extras)
+ : m_extras(extras)
, m_originalFont(0)
, m_originalFontSizeInPixels((request.pixelSize >= 0)?
request.pixelSize:pointsToPixels(request.pointSize))
@@ -220,10 +220,12 @@ bool QFontEngineS60::stringToCMap(const QChar *characters, int len, QGlyphLayout
}
HB_Glyph *g = glyphs->glyphs;
- const unsigned char* cmap = m_extensions->cmap();
+ const unsigned char* cmap = m_extras->cmap();
+ const bool isRtl = (flags & QTextEngine::RightToLeft);
for (int i = 0; i < len; ++i) {
const unsigned int uc = getChar(characters, i, len);
- *g++ = QFontEngine::getTrueTypeGlyphIndex(cmap, uc);
+ *g++ = QFontEngine::getTrueTypeGlyphIndex(cmap,
+ isRtl ? QChar::mirroredChar(uc) : uc);
}
glyphs->numGlyphs = g - glyphs->glyphs;
@@ -241,8 +243,8 @@ void QFontEngineS60::recalcAdvances(QGlyphLayout *glyphs, QTextEngine::ShaperFla
Q_UNUSED(flags);
for (int i = 0; i < glyphs->numGlyphs; i++) {
const glyph_metrics_t bbox = boundingBox_const(glyphs->glyphs[i]);
- glyphs->advances_x[i] = glyphs->offsets[i].x = bbox.xoff;
- glyphs->advances_y[i] = glyphs->offsets[i].y = bbox.yoff;
+ glyphs->advances_x[i] = bbox.xoff;
+ glyphs->advances_y[i] = bbox.yoff;
}
}
@@ -337,7 +339,7 @@ const char *QFontEngineS60::name() const
bool QFontEngineS60::canRender(const QChar *string, int len)
{
- const unsigned char *cmap = m_extensions->cmap();
+ const unsigned char *cmap = m_extras->cmap();
for (int i = 0; i < len; ++i) {
const unsigned int uc = getChar(string, i, len);
if (QFontEngine::getTrueTypeGlyphIndex(cmap, uc) == 0)
@@ -348,12 +350,12 @@ bool QFontEngineS60::canRender(const QChar *string, int len)
QByteArray QFontEngineS60::getSfntTable(uint tag) const
{
- return m_extensions->getSfntTable(tag);
+ return m_extras->getSfntTable(tag);
}
bool QFontEngineS60::getSfntTableData(uint tag, uchar *buffer, uint *length) const
{
- return m_extensions->getSfntTableData(tag, buffer, length);
+ return m_extras->getSfntTableData(tag, buffer, length);
}
QFontEngine::Type QFontEngineS60::type() const
diff --git a/src/gui/text/qfontengine_s60_p.h b/src/gui/text/qfontengine_s60_p.h
index a80af4d..b6b117f 100644
--- a/src/gui/text/qfontengine_s60_p.h
+++ b/src/gui/text/qfontengine_s60_p.h
@@ -63,10 +63,10 @@ class CFont;
QT_BEGIN_NAMESPACE
// ..gives us access to truetype tables, UTF-16<->GlyphID mapping, and glyph outlines
-class QFontEngineS60Extensions
+class QSymbianTypeFaceExtras
{
public:
- QFontEngineS60Extensions(CFont* fontOwner, COpenFont *font);
+ QSymbianTypeFaceExtras(CFont* fontOwner, COpenFont *font);
QByteArray getSfntTable(uint tag) const;
bool getSfntTableData(uint tag, uchar *buffer, uint *length) const;
@@ -87,7 +87,7 @@ private:
class QFontEngineS60 : public QFontEngine
{
public:
- QFontEngineS60(const QFontDef &fontDef, const QFontEngineS60Extensions *extensions);
+ QFontEngineS60(const QFontDef &fontDef, const QSymbianTypeFaceExtras *extras);
~QFontEngineS60();
bool stringToCMap(const QChar *str, int len, QGlyphLayout *glyphs, int *nglyphs, QTextEngine::ShaperFlags flags) const;
@@ -128,7 +128,7 @@ private:
CFont *fontWithSize(qreal size) const;
static void releaseFont(CFont *&font);
- const QFontEngineS60Extensions *m_extensions;
+ const QSymbianTypeFaceExtras *m_extras;
CFont* m_originalFont;
const qreal m_originalFontSizeInPixels;
CFont* m_scaledFont;
diff --git a/src/gui/widgets/qlineedit.cpp b/src/gui/widgets/qlineedit.cpp
index 655fc61..c1c4abf 100644
--- a/src/gui/widgets/qlineedit.cpp
+++ b/src/gui/widgets/qlineedit.cpp
@@ -740,8 +740,14 @@ bool QLineEdit::validateAndSet(const QString &newText, int newPos,
setText(oldText);
return false;
}
- setCursorPosition(newPos);
- setSelection(qMin(newMarkAnchor, newMarkDrag), qAbs(newMarkAnchor - newMarkDrag));
+ int selstart = qMin(newMarkAnchor, newMarkDrag);
+ int sellength = qAbs(newMarkAnchor - newMarkDrag);
+ if (selstart == newPos) {
+ selstart = qMax(newMarkAnchor, newMarkDrag);
+ sellength = -sellength;
+ }
+ //setSelection also set the position
+ setSelection(selstart, sellength);
return true;
}
#endif //QT3_SUPPORT
diff --git a/src/gui/widgets/qmenu.cpp b/src/gui/widgets/qmenu.cpp
index e0f1402..4698be4 100644
--- a/src/gui/widgets/qmenu.cpp
+++ b/src/gui/widgets/qmenu.cpp
@@ -2803,7 +2803,9 @@ void QMenu::mouseMoveEvent(QMouseEvent *e)
QAction *action = d->actionAt(e->pos());
if (!action) {
- if (d->hasHadMouse)
+ if (d->hasHadMouse
+ && (!d->currentAction
+ || !(d->currentAction->menu() && d->currentAction->menu()->isVisible())))
d->setCurrentAction(0);
return;
} else if(e->buttons()) {
diff --git a/src/gui/widgets/qmenu_mac.mm b/src/gui/widgets/qmenu_mac.mm
index e8400d6..aaa113b 100644
--- a/src/gui/widgets/qmenu_mac.mm
+++ b/src/gui/widgets/qmenu_mac.mm
@@ -2066,6 +2066,7 @@ bool QMenuBarPrivate::macUpdateMenuBarImmediatly()
cancelAllMenuTracking();
QWidget *w = findWindowThatShouldDisplayMenubar();
QMenuBar *mb = findMenubarForWindow(w);
+ extern bool qt_mac_app_fullscreen; //qapplication_mac.mm
// We need to see if we are in full screen mode, if so we need to
// switch the full screen mode to be able to show or hide the menubar.
@@ -2074,12 +2075,14 @@ bool QMenuBarPrivate::macUpdateMenuBarImmediatly()
if(w->isFullScreen()) {
// Ok, switch to showing the menubar when hovering over it.
SetSystemUIMode(kUIModeAllHidden, kUIOptionAutoShowMenuBar);
+ qt_mac_app_fullscreen = true;
}
} else if(w) {
// Removing a menubar
if(w->isFullScreen()) {
// Ok, switch to not showing the menubar when hovering on it
SetSystemUIMode(kUIModeAllHidden, 0);
+ qt_mac_app_fullscreen = true;
}
}
diff --git a/src/gui/widgets/qtabbar.cpp b/src/gui/widgets/qtabbar.cpp
index d03a2f4..8aaaade 100644
--- a/src/gui/widgets/qtabbar.cpp
+++ b/src/gui/widgets/qtabbar.cpp
@@ -69,6 +69,7 @@
QT_BEGIN_NAMESPACE
+
inline static bool verticalTabs(QTabBar::Shape shape)
{
return shape == QTabBar::RoundedWest
@@ -95,9 +96,20 @@ void QTabBarPrivate::updateMacBorderMetrics()
metrics.left = 0;
metrics.right = 0;
qt_mac_updateContentBorderMetricts(window, metrics);
-
- // hide the base line separator if the tabs have docuemnt mode enabled (Cocoa)
- qt_mac_showBaseLineSeparator(window, !documentMode);
+#if QT_MAC_USE_COCOA
+ // In Cocoa we need to keep track of the drawRect method.
+ // If documentMode is enabled we need to change it, unless
+ // a toolbar is present.
+ // Notice that all the information is kept in the window,
+ // that's why we get the private widget for it instead of
+ // the private widget for this widget.
+ QWidgetPrivate *privateWidget = qt_widget_private(q->window());
+ if(privateWidget)
+ privateWidget->changeMethods = documentMode;
+ // Since in Cocoa there is no simple way to remove the baseline, so we just ask the
+ // top level to do the magic for us.
+ privateWidget->syncUnifiedMode();
+#endif // QT_MAC_USE_COCOA
}
#endif
}
@@ -2193,6 +2205,7 @@ bool QTabBar::documentMode() const
void QTabBar::setDocumentMode(bool enabled)
{
Q_D(QTabBar);
+
d->documentMode = enabled;
d->updateMacBorderMetrics();
}
diff --git a/src/gui/widgets/qtabwidget.cpp b/src/gui/widgets/qtabwidget.cpp
index 01e9d40..82dfdef 100644
--- a/src/gui/widgets/qtabwidget.cpp
+++ b/src/gui/widgets/qtabwidget.cpp
@@ -552,6 +552,8 @@ void QTabWidget::setTabEnabled(int index, bool enable)
{
Q_D(QTabWidget);
d->tabs->setTabEnabled(index, enable);
+ if (QWidget *widget = d->stack->widget(index))
+ widget->setEnabled(enable);
}
/*!
diff --git a/src/imports/multimedia/qdeclarativeaudio.cpp b/src/imports/multimedia/qdeclarativeaudio.cpp
index 896f9b7..a163b10 100644
--- a/src/imports/multimedia/qdeclarativeaudio.cpp
+++ b/src/imports/multimedia/qdeclarativeaudio.cpp
@@ -57,7 +57,21 @@ QT_BEGIN_NAMESPACE
import Qt 4.7
import Qt.multimedia 4.7
- Audio { source: "audio/song.mp3" }
+ Text {
+ text: "Click Me!";
+ font.pointSize: 24;
+ width: 150; height: 50;
+
+ Audio {
+ id: playMusic
+ source: "music.wav"
+ }
+ MouseArea {
+ id: playArea
+ anchors.fill: parent
+ onPressed: { playMusic.play() }
+ }
+ }
\endqml
\sa Video
diff --git a/src/imports/multimedia/qdeclarativevideo.cpp b/src/imports/multimedia/qdeclarativevideo.cpp
index 9b02795..1b51e2c 100644
--- a/src/imports/multimedia/qdeclarativevideo.cpp
+++ b/src/imports/multimedia/qdeclarativevideo.cpp
@@ -79,7 +79,24 @@ void QDeclarativeVideo::_q_error(int errorCode, const QString &errorString)
import Qt 4.7
import Qt.multimedia 4.7
- Video { source: "video/movie.mpg" }
+ Video {
+ id: video
+ width : 800
+ height : 600
+ source: "video.avi"
+
+ MouseArea {
+ anchors.fill: parent
+ onClicked: {
+ video.play()
+ }
+ }
+
+ focus: true
+ Keys.onSpacePressed: video.paused = !video.paused
+ Keys.onLeftPressed: video.position -= 5000
+ Keys.onRightPressed: video.position += 5000
+ }
\endqml
The Video item supports untransformed, stretched, and uniformly scaled video presentation.
diff --git a/src/multimedia/mediaservices/effects/qsoundeffect.cpp b/src/multimedia/mediaservices/effects/qsoundeffect.cpp
index 1992ee5..3537566 100644
--- a/src/multimedia/mediaservices/effects/qsoundeffect.cpp
+++ b/src/multimedia/mediaservices/effects/qsoundeffect.cpp
@@ -64,17 +64,19 @@ QT_BEGIN_NAMESPACE
import Qt 4.7
import Qt.multimedia 4.7
- Item {
+ Text {
+ text: "Click Me!";
+ font.pointSize: 24;
+ width: 150; height: 50;
+
SoundEffect {
id: playSound
- source: "test.wav"
+ source: "soundeffect.wav"
}
MouseArea {
id: playArea
anchors.fill: parent
- onPressed: {
- playSound.play()
- }
+ onPressed: { playSound.play() }
}
}
\endqml
diff --git a/src/multimedia/multimedia/audio/qaudioinput.cpp b/src/multimedia/multimedia/audio/qaudioinput.cpp
index c99e870..3676f64 100644
--- a/src/multimedia/multimedia/audio/qaudioinput.cpp
+++ b/src/multimedia/multimedia/audio/qaudioinput.cpp
@@ -211,7 +211,7 @@ QAudioInput::~QAudioInput()
If a problem occurs during this process the error() is set to QAudio::OpenError,
state() is set to QAudio::StoppedState and stateChanged() signal is emitted.
- \sa {Symbian Platform Security Requirements}
+ \l{QAudioInput#Symbian Platform Security Requirements}
\sa QIODevice
*/
@@ -233,7 +233,7 @@ void QAudioInput::start(QIODevice* device)
If a problem occurs during this process the error() is set to QAudio::OpenError,
state() is set to QAudio::StoppedState and stateChanged() signal is emitted.
- \sa {Symbian Platform Security Requirements}
+ \l{QAudioInput#Symbian Platform Security Requirements}
\sa QIODevice
*/
diff --git a/src/multimedia/multimedia/audio/qaudioinput_alsa_p.cpp b/src/multimedia/multimedia/audio/qaudioinput_alsa_p.cpp
index 6b15008..c9a8b71 100644
--- a/src/multimedia/multimedia/audio/qaudioinput_alsa_p.cpp
+++ b/src/multimedia/multimedia/audio/qaudioinput_alsa_p.cpp
@@ -58,8 +58,6 @@ QT_BEGIN_NAMESPACE
//#define DEBUG_AUDIO 1
-static const int minimumIntervalTime = 50;
-
QAudioInputPrivate::QAudioInputPrivate(const QByteArray &device, const QAudioFormat& audioFormat):
settings(audioFormat)
{
@@ -594,10 +592,7 @@ int QAudioInputPrivate::periodSize() const
void QAudioInputPrivate::setNotifyInterval(int ms)
{
- if(ms >= minimumIntervalTime)
- intervalTime = ms;
- else
- intervalTime = minimumIntervalTime;
+ intervalTime = qMax(0, ms);
}
int QAudioInputPrivate::notifyInterval() const
@@ -649,7 +644,7 @@ bool QAudioInputPrivate::deviceReady()
if(deviceState != QAudio::ActiveState)
return true;
- if((timeStamp.elapsed() + elapsedTimeOffset) > intervalTime) {
+ if(intervalTime && (timeStamp.elapsed() + elapsedTimeOffset) > intervalTime) {
emit notify();
elapsedTimeOffset = timeStamp.elapsed() + elapsedTimeOffset - intervalTime;
timeStamp.restart();
diff --git a/src/multimedia/multimedia/audio/qaudioinput_win32_p.cpp b/src/multimedia/multimedia/audio/qaudioinput_win32_p.cpp
index b5d673e..14a1cf3 100644
--- a/src/multimedia/multimedia/audio/qaudioinput_win32_p.cpp
+++ b/src/multimedia/multimedia/audio/qaudioinput_win32_p.cpp
@@ -57,8 +57,6 @@ QT_BEGIN_NAMESPACE
//#define DEBUG_AUDIO 1
-static const int minimumIntervalTime = 50;
-
QAudioInputPrivate::QAudioInputPrivate(const QByteArray &device, const QAudioFormat& audioFormat):
settings(audioFormat)
{
@@ -74,16 +72,11 @@ QAudioInputPrivate::QAudioInputPrivate(const QByteArray &device, const QAudioFor
pullMode = true;
resuming = false;
finished = false;
-
- connect(this,SIGNAL(processMore()),SLOT(deviceReady()));
-
- InitializeCriticalSection(&waveInCriticalSection);
}
QAudioInputPrivate::~QAudioInputPrivate()
{
stop();
- DeleteCriticalSection(&waveInCriticalSection);
}
void QT_WIN_CALLBACK QAudioInputPrivate::waveInProc( HWAVEIN hWaveIn, UINT uMsg,
@@ -98,20 +91,18 @@ void QT_WIN_CALLBACK QAudioInputPrivate::waveInProc( HWAVEIN hWaveIn, UINT uMsg,
if(!qAudio)
return;
+ QMutexLocker(&qAudio->mutex);
+
switch(uMsg) {
case WIM_OPEN:
break;
case WIM_DATA:
- EnterCriticalSection(&qAudio->waveInCriticalSection);
if(qAudio->waveFreeBlockCount > 0)
qAudio->waveFreeBlockCount--;
qAudio->feedback();
- LeaveCriticalSection(&qAudio->waveInCriticalSection);
break;
case WIM_CLOSE:
- EnterCriticalSection(&qAudio->waveInCriticalSection);
qAudio->finished = true;
- LeaveCriticalSection(&qAudio->waveInCriticalSection);
break;
default:
return;
@@ -156,7 +147,7 @@ void QAudioInputPrivate::freeBlocks(WAVEHDR* blockArray)
int count = buffer_size/period_size;
for(int i = 0; i < count; i++) {
- waveInUnprepareHeader(hWaveIn,&blocks[i], sizeof(WAVEHDR));
+ waveInUnprepareHeader(hWaveIn,blocks, sizeof(WAVEHDR));
blocks+=sizeof(WAVEHDR);
}
HeapFree(GetProcessHeap(), 0, blockArray);
@@ -283,9 +274,9 @@ bool QAudioInputPrivate::open()
return false;
}
- EnterCriticalSection(&waveInCriticalSection);
+ mutex.lock();
waveFreeBlockCount = buffer_size/period_size;
- LeaveCriticalSection(&waveInCriticalSection);
+ mutex.unlock();
waveCurrentBlock = 0;
@@ -329,13 +320,11 @@ void QAudioInputPrivate::close()
Sleep(10);
}
- EnterCriticalSection(&waveInCriticalSection);
- for(int i=0; i<waveFreeBlockCount; i++) {
- if(waveBlocks[i].dwFlags & WHDR_PREPARED)
- waveInUnprepareHeader(hWaveIn,&waveBlocks[i],sizeof(WAVEHDR));
- }
- LeaveCriticalSection(&waveInCriticalSection);
+ mutex.lock();
+ for(int i=0; i<waveFreeBlockCount; i++)
+ waveInUnprepareHeader(hWaveIn,&waveBlocks[i],sizeof(WAVEHDR));
freeBlocks(waveBlocks);
+ mutex.unlock();
}
int QAudioInputPrivate::bytesReady() const
@@ -406,9 +395,10 @@ qint64 QAudioInputPrivate::read(char* data, qint64 len)
waveInUnprepareHeader(hWaveIn,&waveBlocks[header], sizeof(WAVEHDR));
- EnterCriticalSection(&waveInCriticalSection);
+ mutex.lock();
waveFreeBlockCount++;
- LeaveCriticalSection(&waveInCriticalSection);
+ mutex.unlock();
+
waveBlocks[header].dwBytesRecorded=0;
waveBlocks[header].dwFlags = 0L;
result = waveInPrepareHeader(hWaveIn,&waveBlocks[header], sizeof(WAVEHDR));
@@ -416,18 +406,22 @@ qint64 QAudioInputPrivate::read(char* data, qint64 len)
result = waveInPrepareHeader(hWaveIn,&waveBlocks[header], sizeof(WAVEHDR));
qWarning("QAudioInput: failed to prepare block %d,err=%d",header,result);
errorState = QAudio::IOError;
- EnterCriticalSection(&waveInCriticalSection);
+
+ mutex.lock();
waveFreeBlockCount--;
- LeaveCriticalSection(&waveInCriticalSection);
+ mutex.unlock();
+
return 0;
}
result = waveInAddBuffer(hWaveIn, &waveBlocks[header], sizeof(WAVEHDR));
if(result != MMSYSERR_NOERROR) {
qWarning("QAudioInput: failed to setup block %d,err=%d",header,result);
errorState = QAudio::IOError;
- EnterCriticalSection(&waveInCriticalSection);
+
+ mutex.lock();
waveFreeBlockCount--;
- LeaveCriticalSection(&waveInCriticalSection);
+ mutex.unlock();
+
return 0;
}
header++;
@@ -435,7 +429,7 @@ qint64 QAudioInputPrivate::read(char* data, qint64 len)
header = 0;
p+=l;
- EnterCriticalSection(&waveInCriticalSection);
+ mutex.lock();
if(!pullMode) {
if(l+period_size > len && waveFreeBlockCount == buffer_size/period_size)
done = true;
@@ -443,7 +437,7 @@ qint64 QAudioInputPrivate::read(char* data, qint64 len)
if(waveFreeBlockCount == buffer_size/period_size)
done = true;
}
- LeaveCriticalSection(&waveInCriticalSection);
+ mutex.unlock();
written+=l;
}
@@ -467,9 +461,10 @@ void QAudioInputPrivate::resume()
return;
}
}
- EnterCriticalSection(&waveInCriticalSection);
+
+ mutex.lock();
waveFreeBlockCount = buffer_size/period_size;
- LeaveCriticalSection(&waveInCriticalSection);
+ mutex.unlock();
waveCurrentBlock = 0;
header = 0;
@@ -497,10 +492,7 @@ int QAudioInputPrivate::periodSize() const
void QAudioInputPrivate::setNotifyInterval(int ms)
{
- if(ms >= minimumIntervalTime)
- intervalTime = ms;
- else
- intervalTime = minimumIntervalTime;
+ intervalTime = qMax(0, ms);
}
int QAudioInputPrivate::notifyInterval() const
@@ -534,14 +526,13 @@ void QAudioInputPrivate::feedback()
QTime now(QTime::currentTime());
qDebug()<<now.second()<<"s "<<now.msec()<<"ms :feedback() INPUT "<<this;
#endif
- bytesAvailable = bytesReady();
-
if(!(deviceState==QAudio::StoppedState||deviceState==QAudio::SuspendedState))
- emit processMore();
+ QMetaObject::invokeMethod(this, "deviceReady", Qt::QueuedConnection);
}
bool QAudioInputPrivate::deviceReady()
{
+ bytesAvailable = bytesReady();
#ifdef DEBUG_AUDIO
QTime now(QTime::currentTime());
qDebug()<<now.second()<<"s "<<now.msec()<<"ms :deviceReady() INPUT";
@@ -558,7 +549,7 @@ bool QAudioInputPrivate::deviceReady()
a->trigger();
}
- if((timeStamp.elapsed() + elapsedTimeOffset) > intervalTime) {
+ if(intervalTime && (timeStamp.elapsed() + elapsedTimeOffset) > intervalTime) {
emit notify();
elapsedTimeOffset = timeStamp.elapsed() + elapsedTimeOffset - intervalTime;
timeStamp.restart();
diff --git a/src/multimedia/multimedia/audio/qaudioinput_win32_p.h b/src/multimedia/multimedia/audio/qaudioinput_win32_p.h
index 66c2535..8a9b02b 100644
--- a/src/multimedia/multimedia/audio/qaudioinput_win32_p.h
+++ b/src/multimedia/multimedia/audio/qaudioinput_win32_p.h
@@ -62,6 +62,7 @@
#include <QtCore/qstring.h>
#include <QtCore/qstringlist.h>
#include <QtCore/qdatetime.h>
+#include <QtCore/qmutex.h>
#include <QtMultimedia/qaudio.h>
#include <QtMultimedia/qaudiodeviceinfo.h>
@@ -122,7 +123,7 @@ private:
volatile int waveFreeBlockCount;
int waveCurrentBlock;
- CRITICAL_SECTION waveInCriticalSection;
+ QMutex mutex;
static void QT_WIN_CALLBACK waveInProc( HWAVEIN hWaveIn, UINT uMsg,
DWORD dwInstance, DWORD dwParam1, DWORD dwParam2 );
diff --git a/src/multimedia/multimedia/audio/qaudiooutput_alsa_p.cpp b/src/multimedia/multimedia/audio/qaudiooutput_alsa_p.cpp
index cf3726b..49b32c0 100644
--- a/src/multimedia/multimedia/audio/qaudiooutput_alsa_p.cpp
+++ b/src/multimedia/multimedia/audio/qaudiooutput_alsa_p.cpp
@@ -58,8 +58,6 @@ QT_BEGIN_NAMESPACE
//#define DEBUG_AUDIO 1
-static const int minimumIntervalTime = 50;
-
QAudioOutputPrivate::QAudioOutputPrivate(const QByteArray &device, const QAudioFormat& audioFormat):
settings(audioFormat)
{
@@ -84,8 +82,7 @@ QAudioOutputPrivate::QAudioOutputPrivate(const QByteArray &device, const QAudioF
resuming = false;
opened = false;
- QStringList list1 = QString(QLatin1String(device)).split(QLatin1String(":"));
- m_device = QByteArray(list1.at(0).toLocal8Bit().constData());
+ m_device = device;
timer = new QTimer(this);
connect(timer,SIGNAL(timeout()),SLOT(userFeed()));
@@ -282,11 +279,11 @@ bool QAudioOutputPrivate::open()
int count=0;
unsigned int freakuency=settings.frequency();
- QString dev = QLatin1String(m_device.constData());
+ QString dev = QString(QLatin1String(m_device.constData()));
QList<QByteArray> devices = QAudioDeviceInfoInternal::availableDevices(QAudio::AudioOutput);
if(dev.compare(QLatin1String("default")) == 0) {
#if(SND_LIB_MAJOR == 1 && SND_LIB_MINOR == 0 && SND_LIB_SUBMINOR >= 14)
- dev = QLatin1String(devices.first().constData());
+ dev = QLatin1String(devices.first());
#else
dev = QLatin1String("hw:0,0");
#endif
@@ -574,10 +571,7 @@ int QAudioOutputPrivate::bufferSize() const
void QAudioOutputPrivate::setNotifyInterval(int ms)
{
- if(ms >= minimumIntervalTime)
- intervalTime = ms;
- else
- intervalTime = minimumIntervalTime;
+ intervalTime = qMax(0, ms);
}
int QAudioOutputPrivate::notifyInterval() const
@@ -719,7 +713,7 @@ bool QAudioOutputPrivate::deviceReady()
if(deviceState != QAudio::ActiveState)
return true;
- if((timeStamp.elapsed() + elapsedTimeOffset) > intervalTime) {
+ if(intervalTime && (timeStamp.elapsed() + elapsedTimeOffset) > intervalTime) {
emit notify();
elapsedTimeOffset = timeStamp.elapsed() + elapsedTimeOffset - intervalTime;
timeStamp.restart();
diff --git a/src/multimedia/multimedia/audio/qaudiooutput_win32_p.cpp b/src/multimedia/multimedia/audio/qaudiooutput_win32_p.cpp
index 13bce58..a8aeb41 100644
--- a/src/multimedia/multimedia/audio/qaudiooutput_win32_p.cpp
+++ b/src/multimedia/multimedia/audio/qaudiooutput_win32_p.cpp
@@ -56,8 +56,6 @@
QT_BEGIN_NAMESPACE
-static const int minimumIntervalTime = 50;
-
QAudioOutputPrivate::QAudioOutputPrivate(const QByteArray &device, const QAudioFormat& audioFormat):
settings(audioFormat)
{
@@ -73,17 +71,15 @@ QAudioOutputPrivate::QAudioOutputPrivate(const QByteArray &device, const QAudioF
audioSource = 0;
pullMode = true;
finished = false;
- InitializeCriticalSection(&waveOutCriticalSection);
}
QAudioOutputPrivate::~QAudioOutputPrivate()
{
- EnterCriticalSection(&waveOutCriticalSection);
+ mutex.lock();
finished = true;
- LeaveCriticalSection(&waveOutCriticalSection);
+ mutex.unlock();
close();
- DeleteCriticalSection(&waveOutCriticalSection);
}
void CALLBACK QAudioOutputPrivate::waveOutProc( HWAVEOUT hWaveOut, UINT uMsg,
@@ -98,6 +94,8 @@ void CALLBACK QAudioOutputPrivate::waveOutProc( HWAVEOUT hWaveOut, UINT uMsg,
if(!qAudio)
return;
+ QMutexLocker(&qAudio->mutex);
+
switch(uMsg) {
case WOM_OPEN:
qAudio->feedback();
@@ -105,16 +103,13 @@ void CALLBACK QAudioOutputPrivate::waveOutProc( HWAVEOUT hWaveOut, UINT uMsg,
case WOM_CLOSE:
return;
case WOM_DONE:
- EnterCriticalSection(&qAudio->waveOutCriticalSection);
if(qAudio->finished || qAudio->buffer_size == 0 || qAudio->period_size == 0) {
- LeaveCriticalSection(&qAudio->waveOutCriticalSection);
return;
}
qAudio->waveFreeBlockCount++;
if(qAudio->waveFreeBlockCount >= qAudio->buffer_size/qAudio->period_size)
qAudio->waveFreeBlockCount = qAudio->buffer_size/qAudio->period_size;
qAudio->feedback();
- LeaveCriticalSection(&qAudio->waveOutCriticalSection);
break;
default:
return;
@@ -150,7 +145,7 @@ void QAudioOutputPrivate::freeBlocks(WAVEHDR* blockArray)
int count = buffer_size/period_size;
for(int i = 0; i < count; i++) {
- waveOutUnprepareHeader(hWaveOut,&blocks[i], sizeof(WAVEHDR));
+ waveOutUnprepareHeader(hWaveOut,blocks, sizeof(WAVEHDR));
blocks+=sizeof(WAVEHDR);
}
HeapFree(GetProcessHeap(), 0, blockArray);
@@ -225,9 +220,9 @@ bool QAudioOutputPrivate::open()
}
waveBlocks = allocateBlocks(period_size, buffer_size/period_size);
- EnterCriticalSection(&waveOutCriticalSection);
+ mutex.lock();
waveFreeBlockCount = buffer_size/period_size;
- LeaveCriticalSection(&waveOutCriticalSection);
+ mutex.unlock();
waveCurrentBlock = 0;
@@ -333,10 +328,7 @@ int QAudioOutputPrivate::bufferSize() const
void QAudioOutputPrivate::setNotifyInterval(int ms)
{
- if(ms >= minimumIntervalTime)
- intervalTime = ms;
- else
- intervalTime = minimumIntervalTime;
+ intervalTime = qMax(0, ms);
}
int QAudioOutputPrivate::notifyInterval() const
@@ -368,12 +360,12 @@ qint64 QAudioOutputPrivate::write( const char *data, qint64 len )
int remain;
current = &waveBlocks[waveCurrentBlock];
while(l > 0) {
- EnterCriticalSection(&waveOutCriticalSection);
+ mutex.lock();
if(waveFreeBlockCount==0) {
- LeaveCriticalSection(&waveOutCriticalSection);
+ mutex.unlock();
break;
}
- LeaveCriticalSection(&waveOutCriticalSection);
+ mutex.unlock();
if(current->dwFlags & WHDR_PREPARED)
waveOutUnprepareHeader(hWaveOut, current, sizeof(WAVEHDR));
@@ -390,15 +382,13 @@ qint64 QAudioOutputPrivate::write( const char *data, qint64 len )
waveOutPrepareHeader(hWaveOut, current, sizeof(WAVEHDR));
waveOutWrite(hWaveOut, current, sizeof(WAVEHDR));
- EnterCriticalSection(&waveOutCriticalSection);
+ mutex.lock();
waveFreeBlockCount--;
- LeaveCriticalSection(&waveOutCriticalSection);
#ifdef DEBUG_AUDIO
- EnterCriticalSection(&waveOutCriticalSection);
qDebug("write out l=%d, waveFreeBlockCount=%d",
current->dwBufferLength,waveFreeBlockCount);
- LeaveCriticalSection(&waveOutCriticalSection);
#endif
+ mutex.unlock();
totalTimeValue += current->dwBufferLength;
waveCurrentBlock++;
waveCurrentBlock %= buffer_size/period_size;
@@ -453,7 +443,7 @@ void QAudioOutputPrivate::feedback()
bool QAudioOutputPrivate::deviceReady()
{
- if(deviceState == QAudio::StoppedState)
+ if(deviceState == QAudio::StoppedState || deviceState == QAudio::SuspendedState)
return false;
if(pullMode) {
@@ -467,14 +457,16 @@ bool QAudioOutputPrivate::deviceReady()
startup = true;
bool full=false;
- EnterCriticalSection(&waveOutCriticalSection);
+
+ mutex.lock();
if(waveFreeBlockCount==0) full = true;
- LeaveCriticalSection(&waveOutCriticalSection);
+ mutex.unlock();
+
if (full){
#ifdef DEBUG_AUDIO
qDebug() << "Skipping data as unable to write";
#endif
- if((timeStamp.elapsed() + elapsedTimeOffset) > intervalTime ) {
+ if(intervalTime && (timeStamp.elapsed() + elapsedTimeOffset) > intervalTime ) {
emit notify();
elapsedTimeOffset = timeStamp.elapsed() + elapsedTimeOffset - intervalTime;
timeStamp.restart();
@@ -504,12 +496,14 @@ bool QAudioOutputPrivate::deviceReady()
bytesAvailable = bytesFree();
int check = 0;
- EnterCriticalSection(&waveOutCriticalSection);
+
+ mutex.lock();
check = waveFreeBlockCount;
- LeaveCriticalSection(&waveOutCriticalSection);
+ mutex.unlock();
+
if(check == buffer_size/period_size) {
- errorState = QAudio::UnderrunError;
if (deviceState != QAudio::IdleState) {
+ errorState = QAudio::UnderrunError;
deviceState = QAudio::IdleState;
emit stateChanged(deviceState);
}
@@ -521,19 +515,23 @@ bool QAudioOutputPrivate::deviceReady()
}
} else {
int buffered;
- EnterCriticalSection(&waveOutCriticalSection);
+
+ mutex.lock();
buffered = waveFreeBlockCount;
- LeaveCriticalSection(&waveOutCriticalSection);
- errorState = QAudio::UnderrunError;
+ mutex.unlock();
+
if (buffered >= buffer_size/period_size && deviceState == QAudio::ActiveState) {
- deviceState = QAudio::IdleState;
- emit stateChanged(deviceState);
+ if (deviceState != QAudio::IdleState) {
+ errorState = QAudio::UnderrunError;
+ deviceState = QAudio::IdleState;
+ emit stateChanged(deviceState);
+ }
}
}
if(deviceState != QAudio::ActiveState && deviceState != QAudio::IdleState)
return true;
- if((timeStamp.elapsed() + elapsedTimeOffset) > intervalTime) {
+ if(intervalTime && (timeStamp.elapsed() + elapsedTimeOffset) > intervalTime) {
emit notify();
elapsedTimeOffset = timeStamp.elapsed() + elapsedTimeOffset - intervalTime;
timeStamp.restart();
diff --git a/src/multimedia/multimedia/audio/qaudiooutput_win32_p.h b/src/multimedia/multimedia/audio/qaudiooutput_win32_p.h
index 68a40f7..2d19225 100644
--- a/src/multimedia/multimedia/audio/qaudiooutput_win32_p.h
+++ b/src/multimedia/multimedia/audio/qaudiooutput_win32_p.h
@@ -61,6 +61,7 @@
#include <QtCore/qstring.h>
#include <QtCore/qstringlist.h>
#include <QtCore/qdatetime.h>
+#include <QtCore/qmutex.h>
#include <QtMultimedia/qaudio.h>
#include <QtMultimedia/qaudiodeviceinfo.h>
@@ -119,7 +120,7 @@ private:
static void QT_WIN_CALLBACK waveOutProc( HWAVEOUT hWaveOut, UINT uMsg,
DWORD dwInstance, DWORD dwParam1, DWORD dwParam2 );
- CRITICAL_SECTION waveOutCriticalSection;
+ QMutex mutex;
WAVEHDR* allocateBlocks(int size, int count);
void freeBlocks(WAVEHDR* blockArray);
diff --git a/src/network/access/qftp.cpp b/src/network/access/qftp.cpp
index 7f6df0a..97219f4 100644
--- a/src/network/access/qftp.cpp
+++ b/src/network/access/qftp.cpp
@@ -2311,7 +2311,7 @@ void QFtpPrivate::_q_piError(int errorCode, const QString &text)
Q_Q(QFtp);
if (pending.isEmpty()) {
- qWarning() << "QFtpPrivate::_q_piError was called without pending command!";
+ qWarning("QFtpPrivate::_q_piError was called without pending command!");
return;
}
diff --git a/src/network/access/qhttpnetworkconnection.cpp b/src/network/access/qhttpnetworkconnection.cpp
index a6322a3..559124f 100644
--- a/src/network/access/qhttpnetworkconnection.cpp
+++ b/src/network/access/qhttpnetworkconnection.cpp
@@ -489,7 +489,11 @@ void QHttpNetworkConnectionPrivate::fillPipeline(QAbstractSocket *socket)
int i = indexOf(socket);
- if (! (defaultPipelineLength - channels[i].alreadyPipelinedRequests.length() >= 2)) {
+ // return fast if there was no reply right now processed
+ if (channels[i].reply == 0)
+ return;
+
+ if (! (defaultPipelineLength - channels[i].alreadyPipelinedRequests.length() >= defaultRePipelineLength)) {
return;
}
diff --git a/src/network/access/qhttpnetworkconnectionchannel.cpp b/src/network/access/qhttpnetworkconnectionchannel.cpp
index f9a6de8..3b7bc9e 100644
--- a/src/network/access/qhttpnetworkconnectionchannel.cpp
+++ b/src/network/access/qhttpnetworkconnectionchannel.cpp
@@ -317,6 +317,13 @@ void QHttpNetworkConnectionChannel::_q_receiveReply()
return;
}
+ // only run when the QHttpNetworkConnection is not currently being destructed, e.g.
+ // this function is called from _q_disconnected which is called because
+ // of ~QHttpNetworkConnectionPrivate
+ if (!qobject_cast<QHttpNetworkConnection*>(connection)) {
+ return;
+ }
+
qint64 bytes = 0;
QAbstractSocket::SocketState socketState = socket->state();
@@ -384,7 +391,7 @@ void QHttpNetworkConnectionChannel::_q_receiveReply()
if (!replyPrivate->expectContent()) {
replyPrivate->state = QHttpNetworkReplyPrivate::AllDoneState;
allDone();
- return;
+ break;
}
}
break;
diff --git a/src/network/access/qnetworkaccesshttpbackend.cpp b/src/network/access/qnetworkaccesshttpbackend.cpp
index 7a48c2b..3154ed6 100644
--- a/src/network/access/qnetworkaccesshttpbackend.cpp
+++ b/src/network/access/qnetworkaccesshttpbackend.cpp
@@ -726,8 +726,7 @@ void QNetworkAccessHttpBackend::readFromHttp()
QByteDataBuffer list;
while (httpReply->bytesAvailable() != 0 && nextDownstreamBlockSize() != 0 && nextDownstreamBlockSize() > list.byteAmount()) {
- QByteArray data = httpReply->readAny();
- list.append(data);
+ list.append(httpReply->readAny());
}
if (!list.isEmpty())
diff --git a/src/network/access/qnetworkaccessmanager.h b/src/network/access/qnetworkaccessmanager.h
index a0ffb07..95e45f0 100644
--- a/src/network/access/qnetworkaccessmanager.h
+++ b/src/network/access/qnetworkaccessmanager.h
@@ -62,7 +62,7 @@ class QNetworkReply;
class QNetworkProxy;
class QNetworkProxyFactory;
class QSslError;
-#ifndef QT_NO_BEARERMANAGEMENT
+#if !defined(QT_NO_BEARERMANAGEMENT) && !defined(QT_MOBILITY_BEARER)
class QNetworkConfiguration;
#endif
@@ -121,11 +121,13 @@ public:
QNetworkReply *deleteResource(const QNetworkRequest &request);
QNetworkReply *sendCustomRequest(const QNetworkRequest &request, const QByteArray &verb, QIODevice *data = 0);
-#ifndef QT_NO_BEARERMANAGEMENT
+#if !defined(QT_NO_BEARERMANAGEMENT) && !defined(QT_MOBILITY_BEARER)
void setConfiguration(const QNetworkConfiguration &config);
QNetworkConfiguration configuration() const;
QNetworkConfiguration activeConfiguration() const;
+#endif
+#ifndef QT_NO_BEARERMANAGEMENT
void setNetworkAccessible(NetworkAccessibility accessible);
NetworkAccessibility networkAccessible() const;
#endif
@@ -140,9 +142,11 @@ Q_SIGNALS:
void sslErrors(QNetworkReply *reply, const QList<QSslError> &errors);
#endif
-#ifndef QT_NO_BEARERMANAGEMENT
+#if !defined(QT_NO_BEARERMANAGEMENT) && !defined(QT_MOBILITY_BEARER)
void networkSessionConnected();
+#endif
+#ifndef QT_NO_BEARERMANAGEMENT
void networkAccessibleChanged(QNetworkAccessManager::NetworkAccessibility accessible);
#endif
@@ -155,7 +159,7 @@ private:
Q_DECLARE_PRIVATE(QNetworkAccessManager)
Q_PRIVATE_SLOT(d_func(), void _q_replyFinished())
Q_PRIVATE_SLOT(d_func(), void _q_replySslErrors(QList<QSslError>))
-#ifndef QT_NO_BEARERMANAGEMENT
+#if !defined(QT_NO_BEARERMANAGEMENT) && !defined(QT_MOBILITY_BEARER)
Q_PRIVATE_SLOT(d_func(), void _q_networkSessionClosed())
Q_PRIVATE_SLOT(d_func(), void _q_networkSessionNewConfigurationActivated())
Q_PRIVATE_SLOT(d_func(), void _q_networkSessionPreferredConfigurationChanged(QNetworkConfiguration,bool))
diff --git a/src/network/access/qnetworkcookiejar.cpp b/src/network/access/qnetworkcookiejar.cpp
index 8727095..0b3a918 100644
--- a/src/network/access/qnetworkcookiejar.cpp
+++ b/src/network/access/qnetworkcookiejar.cpp
@@ -269,6 +269,7 @@ QList<QNetworkCookie> QNetworkCookieJar::cookiesForUrl(const QUrl &url) const
Q_D(const QNetworkCookieJar);
QDateTime now = QDateTime::currentDateTime();
QList<QNetworkCookie> result;
+ bool isEncrypted = url.scheme().toLower() == QLatin1String("https");
// scan our cookies for something that matches
QList<QNetworkCookie>::ConstIterator it = d->allCookies.constBegin(),
@@ -280,6 +281,8 @@ QList<QNetworkCookie> QNetworkCookieJar::cookiesForUrl(const QUrl &url) const
continue;
if (!(*it).isSessionCookie() && (*it).expirationDate() < now)
continue;
+ if ((*it).isSecure() && !isEncrypted)
+ continue;
// insert this cookie into result, sorted by path
QList<QNetworkCookie>::Iterator insertIt = result.begin();
diff --git a/src/network/access/qnetworkreplyimpl.cpp b/src/network/access/qnetworkreplyimpl.cpp
index c3dc168..128d18f 100644
--- a/src/network/access/qnetworkreplyimpl.cpp
+++ b/src/network/access/qnetworkreplyimpl.cpp
@@ -478,6 +478,37 @@ qint64 QNetworkReplyImplPrivate::nextDownstreamBlockSize() const
return qMax<qint64>(0, readBufferMaxSize - readBuffer.byteAmount());
}
+void QNetworkReplyImplPrivate::initCacheSaveDevice()
+{
+ Q_Q(QNetworkReplyImpl);
+
+ // save the meta data
+ QNetworkCacheMetaData metaData;
+ metaData.setUrl(url);
+ metaData = backend->fetchCacheMetaData(metaData);
+
+ // save the redirect request also in the cache
+ QVariant redirectionTarget = q->attribute(QNetworkRequest::RedirectionTargetAttribute);
+ if (redirectionTarget.isValid()) {
+ QNetworkCacheMetaData::AttributesMap attributes = metaData.attributes();
+ attributes.insert(QNetworkRequest::RedirectionTargetAttribute, redirectionTarget);
+ metaData.setAttributes(attributes);
+ }
+
+ cacheSaveDevice = networkCache()->prepare(metaData);
+
+ if (!cacheSaveDevice || (cacheSaveDevice && !cacheSaveDevice->isOpen())) {
+ if (cacheSaveDevice && !cacheSaveDevice->isOpen())
+ qCritical("QNetworkReplyImpl: network cache returned a device that is not open -- "
+ "class %s probably needs to be fixed",
+ networkCache()->metaObject()->className());
+
+ networkCache()->remove(url);
+ cacheSaveDevice = 0;
+ cacheEnabled = false;
+ }
+}
+
// we received downstream data and send this to the cache
// and to our readBuffer (which in turn gets read by the user of QNetworkReply)
void QNetworkReplyImplPrivate::appendDownstreamData(QByteDataBuffer &data)
@@ -487,36 +518,12 @@ void QNetworkReplyImplPrivate::appendDownstreamData(QByteDataBuffer &data)
return;
if (cacheEnabled && !cacheSaveDevice) {
- // save the meta data
- QNetworkCacheMetaData metaData;
- metaData.setUrl(url);
- metaData = backend->fetchCacheMetaData(metaData);
-
- // save the redirect request also in the cache
- QVariant redirectionTarget = q->attribute(QNetworkRequest::RedirectionTargetAttribute);
- if (redirectionTarget.isValid()) {
- QNetworkCacheMetaData::AttributesMap attributes = metaData.attributes();
- attributes.insert(QNetworkRequest::RedirectionTargetAttribute, redirectionTarget);
- metaData.setAttributes(attributes);
- }
-
- cacheSaveDevice = networkCache()->prepare(metaData);
-
- if (!cacheSaveDevice || (cacheSaveDevice && !cacheSaveDevice->isOpen())) {
- if (cacheSaveDevice && !cacheSaveDevice->isOpen())
- qCritical("QNetworkReplyImpl: network cache returned a device that is not open -- "
- "class %s probably needs to be fixed",
- networkCache()->metaObject()->className());
-
- networkCache()->remove(url);
- cacheSaveDevice = 0;
- cacheEnabled = false;
- }
+ initCacheSaveDevice();
}
qint64 bytesWritten = 0;
for (int i = 0; i < data.bufferCount(); i++) {
- QByteArray item = data[i];
+ QByteArray const &item = data[i];
if (cacheSaveDevice)
cacheSaveDevice->write(item.constData(), item.size());
@@ -529,6 +536,13 @@ void QNetworkReplyImplPrivate::appendDownstreamData(QByteDataBuffer &data)
bytesDownloaded += bytesWritten;
lastBytesDownloaded = bytesDownloaded;
+ appendDownstreamDataSignalEmissions();
+}
+
+void QNetworkReplyImplPrivate::appendDownstreamDataSignalEmissions()
+{
+ Q_Q(QNetworkReplyImpl);
+
QPointer<QNetworkReplyImpl> qq = q;
QVariant totalSize = cookedHeaders.value(QNetworkRequest::ContentLengthHeader);
@@ -572,6 +586,15 @@ void QNetworkReplyImplPrivate::appendDownstreamData(QIODevice *data)
_q_copyReadyRead();
}
+void QNetworkReplyImplPrivate::appendDownstreamData(const QByteArray &data)
+{
+ // TODO implement
+
+ // TODO call
+
+ qFatal("QNetworkReplyImplPrivate::appendDownstreamData not implemented");
+}
+
void QNetworkReplyImplPrivate::finished()
{
Q_Q(QNetworkReplyImpl);
@@ -689,8 +712,13 @@ QNetworkReplyImpl::QNetworkReplyImpl(QObject *parent)
QNetworkReplyImpl::~QNetworkReplyImpl()
{
Q_D(QNetworkReplyImpl);
+
+ // This code removes the data from the cache if it was prematurely aborted.
+ // See QNetworkReplyImplPrivate::completeCacheSave(), we disable caching there after the cache
+ // save had been properly finished. So if it is still enabled it means we got deleted/aborted.
if (d->isCachingEnabled())
d->networkCache()->remove(url());
+
if (d->outgoingDataBuffer)
delete d->outgoingDataBuffer;
}
diff --git a/src/network/access/qnetworkreplyimpl_p.h b/src/network/access/qnetworkreplyimpl_p.h
index bc7e408..38084bd 100644
--- a/src/network/access/qnetworkreplyimpl_p.h
+++ b/src/network/access/qnetworkreplyimpl_p.h
@@ -156,8 +156,13 @@ public:
void consume(qint64 count);
void emitUploadProgress(qint64 bytesSent, qint64 bytesTotal);
qint64 nextDownstreamBlockSize() const;
+
+ void initCacheSaveDevice();
+ void appendDownstreamDataSignalEmissions();
void appendDownstreamData(QByteDataBuffer &data);
void appendDownstreamData(QIODevice *data);
+ void appendDownstreamData(const QByteArray &data);
+
void finished();
void error(QNetworkReply::NetworkError code, const QString &errorString);
void metaDataChanged();
diff --git a/src/opengl/qgl.cpp b/src/opengl/qgl.cpp
index 72ed6be..bf77eda 100644
--- a/src/opengl/qgl.cpp
+++ b/src/opengl/qgl.cpp
@@ -1637,7 +1637,14 @@ static void convertFromGLImage(QImage &img, int w, int h, bool alpha_format, boo
uint *q = (uint*)img.scanLine(y);
for (int x=0; x < w; ++x) {
const uint pixel = *q;
- *q = ((pixel << 16) & 0xff0000) | ((pixel >> 16) & 0xff) | (pixel & 0xff00ff00);
+ if (alpha_format && include_alpha) {
+ *q = ((pixel << 16) & 0xff0000) | ((pixel >> 16) & 0xff)
+ | (pixel & 0xff00ff00);
+ } else {
+ *q = 0xff000000 | ((pixel << 16) & 0xff0000)
+ | ((pixel >> 16) & 0xff) | (pixel & 0x00ff00);
+ }
+
q++;
}
}
@@ -1648,7 +1655,8 @@ static void convertFromGLImage(QImage &img, int w, int h, bool alpha_format, boo
QImage qt_gl_read_framebuffer(const QSize &size, bool alpha_format, bool include_alpha)
{
- QImage img(size, alpha_format ? QImage::Format_ARGB32 : QImage::Format_RGB32);
+ QImage img(size, (alpha_format && include_alpha) ? QImage::Format_ARGB32
+ : QImage::Format_RGB32);
int w = size.width();
int h = size.height();
glReadPixels(0, 0, w, h, GL_RGBA, GL_UNSIGNED_BYTE, img.bits());
diff --git a/src/openvg/qpaintengine_vg.cpp b/src/openvg/qpaintengine_vg.cpp
index 5ae69cd..f602c73 100644
--- a/src/openvg/qpaintengine_vg.cpp
+++ b/src/openvg/qpaintengine_vg.cpp
@@ -182,7 +182,6 @@ public:
qreal penScale; // Pen scaling factor from "transform".
QTransform pathTransform; // Calculated VG path transformation.
- QTransform glyphTransform; // Calculated VG glyph transformation.
QTransform imageTransform; // Calculated VG image transformation.
bool pathTransformSet; // True if path transform set in the VG context.
@@ -507,24 +506,15 @@ void QVGPaintEnginePrivate::updateTransform(QPaintDevice *pdev)
// | 1 0 0 |
// | 0 -1 devh |
// | 0 0 1 |
- // The glyph transform uses a slightly different transformation:
- // | 1 0 0 | | 1 0 0.5 | | 1 0 0.5 |
- // | 0 -1 devh - 1 | * | 0 1 -0.5 | = | 0 -1 (devh - 0.5) |
- // | 0 0 1 | | 0 0 1 | | 0 0 1 |
// The full VG transform is effectively:
// 1. Apply the user's transformation matrix.
- // 2. Translate glyphs by an extra (0.5, -0.5).
- // 3. Flip the co-ordinate system upside down.
+ // 2. Flip the co-ordinate system upside down.
QTransform viewport(1.0f, 0.0f, 0.0f,
0.0f, -1.0f, 0.0f,
0.0f, devh, 1.0f);
- QTransform gviewport(1.0f, 0.0f, 0.0f,
- 0.0f, -1.0f, 0.0f,
- 0.5f, devh - 0.5f, 1.0f);
// Compute the path transform and determine if it is projective.
pathTransform = transform * viewport;
- glyphTransform = transform * gviewport;
bool projective = (pathTransform.m13() != 0.0f ||
pathTransform.m23() != 0.0f ||
pathTransform.m33() != 1.0f);
@@ -533,7 +523,6 @@ void QVGPaintEnginePrivate::updateTransform(QPaintDevice *pdev)
// so we will have to convert the co-ordinates ourselves.
// Change the matrix to just the viewport transformation.
pathTransform = viewport;
- glyphTransform = gviewport;
simpleTransform = false;
} else {
simpleTransform = true;
@@ -3242,10 +3231,10 @@ void QVGFontGlyphCache::cacheGlyphs(QVGPaintEnginePrivate *d,
vgImageSubData(vgImage, img.constBits(), img.bytesPerLine(), VG_sARGB_8888_PRE, 0, 0, img.width(), img.height());
}
}
- origin[0] = -metrics.x.toReal() + 0.5f;
- origin[1] = -metrics.y.toReal() + 0.5f;
- escapement[0] = metrics.xoff.toReal();
- escapement[1] = metrics.yoff.toReal();
+ origin[0] = -metrics.x.toReal();
+ origin[1] = -metrics.y.toReal();
+ escapement[0] = 0;
+ escapement[1] = 0;
vgSetGlyphToImage(font, glyph, vgImage, origin, escapement);
vgDestroyImage(vgImage); // Reduce reference count.
#else
@@ -3261,8 +3250,8 @@ void QVGFontGlyphCache::cacheGlyphs(QVGPaintEnginePrivate *d,
}
origin[0] = 0;
origin[1] = 0;
- escapement[0] = metrics.xoff.toReal();
- escapement[1] = metrics.yoff.toReal();
+ escapement[0] = 0;
+ escapement[1] = 0;
vgSetGlyphToPath(font, glyph, vgPath, VG_FALSE, origin, escapement);
vgDestroyPath(vgPath); // Reduce reference count.
#endif // !defined(QVG_NO_IMAGE_GLYPHS)
@@ -3287,12 +3276,10 @@ void QVGPaintEngine::drawTextItem(const QPointF &p, const QTextItem &textItem)
// Get the glyphs and positions associated with the text item.
QVarLengthArray<QFixedPoint> positions;
QVarLengthArray<glyph_t> glyphs;
- QTransform matrix = d->transform;
- matrix.translate(p.x(), p.y());
- ti.fontEngine->getGlyphPositions
- (ti.glyphs, matrix, ti.flags, glyphs, positions);
+ QTransform matrix;
+ ti.fontEngine->getGlyphPositions(ti.glyphs, matrix, ti.flags, glyphs, positions);
- if (!drawCachedGlyphs(glyphs.size(), glyphs.data(), ti.font(), ti.fontEngine, p))
+ if (!drawCachedGlyphs(glyphs.size(), glyphs.data(), ti.font(), ti.fontEngine, p, positions.data()))
QPaintEngineEx::drawTextItem(p, textItem);
#else
// OpenGL 1.0 does not have support for VGFont and glyphs,
@@ -3304,11 +3291,12 @@ void QVGPaintEngine::drawTextItem(const QPointF &p, const QTextItem &textItem)
void QVGPaintEngine::drawStaticTextItem(QStaticTextItem *textItem)
{
drawCachedGlyphs(textItem->numGlyphs, textItem->glyphs, textItem->font, textItem->fontEngine,
- QPointF(0, 0));
+ QPointF(0, 0), textItem->glyphPositions);
}
bool QVGPaintEngine::drawCachedGlyphs(int numGlyphs, const glyph_t *glyphs, const QFont &font,
- QFontEngine *fontEngine, const QPointF &p)
+ QFontEngine *fontEngine, const QPointF &p,
+ const QFixedPoint *positions)
{
#if !defined(QVG_NO_DRAW_GLYPHS)
Q_D(QVGPaintEngine);
@@ -3334,7 +3322,7 @@ void QVGPaintEngine::drawStaticTextItem(QStaticTextItem *textItem)
}
// Set the transformation to use for drawing the current glyphs.
- QTransform glyphTransform(d->glyphTransform);
+ QTransform glyphTransform(d->pathTransform);
glyphTransform.translate(p.x(), p.y());
#if defined(QVG_NO_IMAGE_GLYPHS)
glyphTransform.scale(glyphCache->scaleX, glyphCache->scaleY);
@@ -3344,10 +3332,18 @@ void QVGPaintEngine::drawStaticTextItem(QStaticTextItem *textItem)
// Add the glyphs from the text item into the glyph cache.
glyphCache->cacheGlyphs(d, fontEngine, glyphs, numGlyphs);
+ // Create the array of adjustments between glyphs
+ QVarLengthArray<VGfloat> adjustments_x(numGlyphs);
+ QVarLengthArray<VGfloat> adjustments_y(numGlyphs);
+ for (int i = 1; i < numGlyphs; ++i) {
+ adjustments_x[i-1] = (positions[i].x - positions[i-1].x).toReal();
+ adjustments_y[i-1] = (positions[i].y - positions[i-1].y).toReal();
+ }
+
// Set the glyph drawing origin.
VGfloat origin[2];
- origin[0] = 0;
- origin[1] = 0;
+ origin[0] = positions[0].x.toReal();
+ origin[1] = positions[0].y.toReal();
vgSetfv(VG_GLYPH_ORIGIN, 2, origin);
// Fast anti-aliasing for paths, better for images.
@@ -3362,8 +3358,7 @@ void QVGPaintEngine::drawStaticTextItem(QStaticTextItem *textItem)
// the Qt pen, not the Qt brush.
d->ensureBrush(state()->pen.brush());
vgDrawGlyphs(glyphCache->font, numGlyphs, (VGuint*)glyphs,
- NULL, NULL, VG_FILL_PATH, VG_TRUE);
-
+ adjustments_x.data(), adjustments_y.data(), VG_FILL_PATH, VG_TRUE);
return true;
#else
Q_UNUSED(numGlyphs);
@@ -3371,6 +3366,7 @@ void QVGPaintEngine::drawStaticTextItem(QStaticTextItem *textItem)
Q_UNUSED(font);
Q_UNUSED(fontEngine);
Q_UNUSED(p);
+ Q_UNUSED(positions);
return false;
#endif
}
diff --git a/src/openvg/qpaintengine_vg_p.h b/src/openvg/qpaintengine_vg_p.h
index 1e7e26c..33c49ba 100644
--- a/src/openvg/qpaintengine_vg_p.h
+++ b/src/openvg/qpaintengine_vg_p.h
@@ -58,6 +58,7 @@
QT_BEGIN_NAMESPACE
+class QFixedPoint;
class QVGPaintEnginePrivate;
class QPixmapData;
class QVGEGLWindowSurfacePrivate;
@@ -143,7 +144,8 @@ public:
void drawTextItem(const QPointF &p, const QTextItem &textItem);
void drawStaticTextItem(QStaticTextItem *staticTextItem);
bool drawCachedGlyphs(int numGlyphs, const glyph_t *glyphs, const QFont &font,
- QFontEngine *fontEngine, const QPointF &p);
+ QFontEngine *fontEngine, const QPointF &p,
+ const QFixedPoint *positions);
void setState(QPainterState *s);
QVGPainterState *state() { return static_cast<QVGPainterState *>(QPaintEngineEx::state()); }
diff --git a/src/plugins/accessible/widgets/simplewidgets.cpp b/src/plugins/accessible/widgets/simplewidgets.cpp
index daa827e..f39d538 100644
--- a/src/plugins/accessible/widgets/simplewidgets.cpp
+++ b/src/plugins/accessible/widgets/simplewidgets.cpp
@@ -605,7 +605,11 @@ int QAccessibleDisplay::navigate(RelationFlag rel, int entry, QAccessibleInterfa
/*! \reimp */
QString QAccessibleDisplay::imageDescription()
{
+#ifndef QT_NO_TOOLTIP
return widget()->toolTip();
+#else
+ return QString::null;
+#endif
}
/*! \reimp */
diff --git a/src/plugins/mediaservices/directshow/mediaplayer/directshowsamplescheduler.cpp b/src/plugins/mediaservices/directshow/mediaplayer/directshowsamplescheduler.cpp
index 150860f..23675fb 100644
--- a/src/plugins/mediaservices/directshow/mediaplayer/directshowsamplescheduler.cpp
+++ b/src/plugins/mediaservices/directshow/mediaplayer/directshowsamplescheduler.cpp
@@ -118,7 +118,7 @@ bool DirectShowTimedSample::isReady(IReferenceClock *clock) const
}
DirectShowSampleScheduler::DirectShowSampleScheduler(IUnknown *pin, QObject *parent)
- : QWinEventNotifier(parent)
+ : QObject(parent)
, m_pin(pin)
, m_clock(0)
, m_allocator(0)
@@ -131,13 +131,15 @@ DirectShowSampleScheduler::DirectShowSampleScheduler(IUnknown *pin, QObject *par
{
m_semaphore.release(m_maximumSamples);
- setHandle(m_timeoutEvent);
- setEnabled(true);
+ m_eventNotifier.setHandle(m_timeoutEvent);
+ m_eventNotifier.setEnabled(true);
+
+ connect(&m_eventNotifier, SIGNAL(activated(HANDLE)), this, SIGNAL(sampleReady()));
}
DirectShowSampleScheduler::~DirectShowSampleScheduler()
{
- setEnabled(false);
+ m_eventNotifier.setEnabled(false);
::CloseHandle(m_timeoutEvent);
@@ -398,17 +400,4 @@ bool DirectShowSampleScheduler::scheduleEndOfStream()
}
}
-bool DirectShowSampleScheduler::event(QEvent *event)
-{
- if (event->type() == QEvent::WinEventAct) {
- QObject::event(event);
-
- emit sampleReady();
-
- return true;
- } else {
- return QWinEventNotifier::event(event);
- }
-}
-
QT_END_NAMESPACE
diff --git a/src/plugins/mediaservices/directshow/mediaplayer/directshowsamplescheduler.h b/src/plugins/mediaservices/directshow/mediaplayer/directshowsamplescheduler.h
index 007fa99..21823c3 100644
--- a/src/plugins/mediaservices/directshow/mediaplayer/directshowsamplescheduler.h
+++ b/src/plugins/mediaservices/directshow/mediaplayer/directshowsamplescheduler.h
@@ -57,7 +57,7 @@ QT_BEGIN_NAMESPACE
class DirectShowTimedSample;
-class DirectShowSampleScheduler : public QWinEventNotifier, public IMemInputPin
+class DirectShowSampleScheduler : public QObject, public IMemInputPin
{
Q_OBJECT
public:
@@ -101,8 +101,6 @@ public:
IMediaSample *takeSample(bool *eos);
- bool event(QEvent *event);
-
Q_SIGNALS:
void sampleReady();
@@ -118,6 +116,7 @@ private:
HANDLE m_timeoutEvent;
QSemaphore m_semaphore;
QMutex m_mutex;
+ QWinEventNotifier m_eventNotifier;
};
QT_END_NAMESPACE
diff --git a/src/plugins/mediaservices/gstreamer/gstreamer.pro b/src/plugins/mediaservices/gstreamer/gstreamer.pro
index 0273139..6af9c3f 100644
--- a/src/plugins/mediaservices/gstreamer/gstreamer.pro
+++ b/src/plugins/mediaservices/gstreamer/gstreamer.pro
@@ -9,39 +9,48 @@ unix:contains(QT_CONFIG, alsa) {
}
QMAKE_CXXFLAGS += $$QT_CFLAGS_GSTREAMER
-LIBS += -lXv $$QT_LIBS_GSTREAMER -lgstinterfaces-0.10 -lgstvideo-0.10 -lgstbase-0.10 -lgstaudio-0.10
+LIBS += $$QT_LIBS_GSTREAMER -lgstinterfaces-0.10 -lgstvideo-0.10 -lgstbase-0.10 -lgstaudio-0.10
# Input
HEADERS += \
qgstreamermessage.h \
qgstreamerbushelper.h \
qgstreamervideooutputcontrol.h \
- qgstreamervideorendererinterface.h \
- qgstreamervideowidget.h \
+ qgstreamervideorendererinterface.h \
qgstreamerserviceplugin.h \
qgstreamervideoinputdevicecontrol.h \
- qgstreamervideooverlay.h \
qgstreamervideorenderer.h \
qgstvideobuffer.h \
- qvideosurfacegstsink.h \
- qx11videosurface.h \
- qgstxvimagebuffer.h
+ qvideosurfacegstsink.h
SOURCES += \
qgstreamermessage.cpp \
qgstreamerbushelper.cpp \
qgstreamervideooutputcontrol.cpp \
- qgstreamervideorendererinterface.cpp \
- qgstreamervideowidget.cpp \
+ qgstreamervideorendererinterface.cpp \
qgstreamerserviceplugin.cpp \
qgstreamervideoinputdevicecontrol.cpp \
- qgstreamervideooverlay.cpp \
qgstreamervideorenderer.cpp \
qgstvideobuffer.cpp \
- qvideosurfacegstsink.cpp \
- qx11videosurface.cpp \
- qgstxvimagebuffer.cpp
+ qvideosurfacegstsink.cpp
+
+
+x11 {
+ LIBS += -lXv
+
+ HEADERS += \
+ qgstreamervideooverlay.h \
+ qgstreamervideowidget.h \
+ qx11videosurface.h \
+ qgstxvimagebuffer.h
+
+ SOURCES += \
+ qgstreamervideooverlay.cpp \
+ qgstreamervideowidget.cpp \
+ qx11videosurface.cpp \
+ qgstxvimagebuffer.cpp
+}
include(mediaplayer/mediaplayer.pri)
diff --git a/src/plugins/mediaservices/gstreamer/mediaplayer/qgstreamerplayerservice.cpp b/src/plugins/mediaservices/gstreamer/mediaplayer/qgstreamerplayerservice.cpp
index d5d7bd0..3228722 100644
--- a/src/plugins/mediaservices/gstreamer/mediaplayer/qgstreamerplayerservice.cpp
+++ b/src/plugins/mediaservices/gstreamer/mediaplayer/qgstreamerplayerservice.cpp
@@ -63,7 +63,10 @@ QT_BEGIN_NAMESPACE
QGstreamerPlayerService::QGstreamerPlayerService(QObject *parent):
- QMediaService(parent)
+ QMediaService(parent),
+ m_videoRenderer(0),
+ m_videoWindow(0),
+ m_videoWidget(0)
{
m_session = new QGstreamerPlayerSession(this);
m_control = new QGstreamerPlayerControl(m_session, this);
@@ -74,13 +77,22 @@ QGstreamerPlayerService::QGstreamerPlayerService(QObject *parent):
connect(m_videoOutput, SIGNAL(outputChanged(QVideoOutputControl::Output)),
this, SLOT(videoOutputChanged(QVideoOutputControl::Output)));
m_videoRenderer = new QGstreamerVideoRenderer(this);
+
+#ifdef Q_WS_X11
m_videoWindow = new QGstreamerVideoOverlay(this);
m_videoWidget = new QGstreamerVideoWidgetControl(this);
+#endif
+
+ QList<QVideoOutputControl::Output> outputs;
+
+ if (m_videoRenderer)
+ outputs << QVideoOutputControl::RendererOutput;
+ if (m_videoWidget)
+ outputs << QVideoOutputControl::WidgetOutput;
+ if (m_videoWindow)
+ outputs << QVideoOutputControl::WindowOutput;
- m_videoOutput->setAvailableOutputs(QList<QVideoOutputControl::Output>()
- << QVideoOutputControl::RendererOutput
- << QVideoOutputControl::WindowOutput
- << QVideoOutputControl::WidgetOutput);
+ m_videoOutput->setAvailableOutputs(outputs);
}
QGstreamerPlayerService::~QGstreamerPlayerService()
diff --git a/src/plugins/mediaservices/gstreamer/qvideosurfacegstsink.cpp b/src/plugins/mediaservices/gstreamer/qvideosurfacegstsink.cpp
index 76d87ce..596e39d 100644
--- a/src/plugins/mediaservices/gstreamer/qvideosurfacegstsink.cpp
+++ b/src/plugins/mediaservices/gstreamer/qvideosurfacegstsink.cpp
@@ -44,12 +44,16 @@
#include <QtCore/qdebug.h>
#include <QMap>
#include <QThread>
+
+#include "qgstvideobuffer.h"
+
+#ifdef Q_WS_X11
#include <QtGui/qx11info_x11.h>
+#include "qgstxvimagebuffer.h"
+#endif
#include "qvideosurfacegstsink.h"
-#include "qgstvideobuffer.h"
-#include "qgstxvimagebuffer.h"
@@ -131,11 +135,13 @@ GstFlowReturn QVideoSurfaceGstDelegate::render(GstBuffer *buffer)
QGstVideoBuffer *videoBuffer = 0;
+#ifdef Q_WS_X11
if (G_TYPE_CHECK_INSTANCE_TYPE(buffer, QGstXvImageBuffer::get_type())) {
QGstXvImageBuffer *xvBuffer = reinterpret_cast<QGstXvImageBuffer *>(buffer);
QVariant handle = QVariant::fromValue(xvBuffer->xvImage);
videoBuffer = new QGstVideoBuffer(buffer, m_bytesPerLine, XvHandleType, handle);
} else
+#endif
videoBuffer = new QGstVideoBuffer(buffer, m_bytesPerLine);
m_frame = QVideoFrame(
@@ -387,7 +393,9 @@ void QVideoSurfaceGstSink::instance_init(GTypeInstance *instance, gpointer g_cla
Q_UNUSED(g_class);
sink->delegate = 0;
+#ifdef Q_WS_X11
sink->pool = new QGstXvImageBufferPool();
+#endif
sink->lastRequestedCaps = 0;
sink->lastBufferCaps = 0;
sink->lastSurfaceFormat = new QVideoSurfaceFormat;
@@ -396,8 +404,11 @@ void QVideoSurfaceGstSink::instance_init(GTypeInstance *instance, gpointer g_cla
void QVideoSurfaceGstSink::finalize(GObject *object)
{
VO_SINK(object);
+#ifdef Q_WS_X11
delete sink->pool;
sink->pool = 0;
+#endif
+
delete sink->lastSurfaceFormat;
sink->lastSurfaceFormat = 0;
@@ -588,6 +599,8 @@ GstFlowReturn QVideoSurfaceGstSink::buffer_alloc(
*buffer = 0;
+#ifdef Q_WS_X11
+
if (sink->lastRequestedCaps && gst_caps_is_equal(sink->lastRequestedCaps, caps)) {
//qDebug() << "reusing last caps";
*buffer = GST_BUFFER(sink->pool->takeBuffer(*sink->lastSurfaceFormat, sink->lastBufferCaps));
@@ -649,6 +662,7 @@ GstFlowReturn QVideoSurfaceGstSink::buffer_alloc(
*buffer = GST_BUFFER(sink->pool->takeBuffer(surfaceFormat, intersection));
+#endif
return GST_FLOW_OK;
}
diff --git a/src/plugins/mediaservices/gstreamer/qvideosurfacegstsink.h b/src/plugins/mediaservices/gstreamer/qvideosurfacegstsink.h
index f59a43c..75fa854 100644
--- a/src/plugins/mediaservices/gstreamer/qvideosurfacegstsink.h
+++ b/src/plugins/mediaservices/gstreamer/qvideosurfacegstsink.h
@@ -59,8 +59,10 @@ QT_BEGIN_NAMESPACE
class QAbstractVideoSurface;
+#ifdef Q_WS_X11
class QGstXvImageBuffer;
class QGstXvImageBufferPool;
+#endif
class QVideoSurfaceGstDelegate : public QObject
@@ -137,7 +139,11 @@ private:
private:
QVideoSurfaceGstDelegate *delegate;
+
+#ifdef Q_WS_X11
QGstXvImageBufferPool *pool;
+#endif
+
GstCaps *lastRequestedCaps;
GstCaps *lastBufferCaps;
QVideoSurfaceFormat *lastSurfaceFormat;
diff --git a/src/plugins/mediaservices/mediaservices.pro b/src/plugins/mediaservices/mediaservices.pro
index 6a00a14..27f05bc 100644
--- a/src/plugins/mediaservices/mediaservices.pro
+++ b/src/plugins/mediaservices/mediaservices.pro
@@ -5,7 +5,9 @@ contains(QT_CONFIG, media-backend) {
mac: SUBDIRS += qt7
- unix:!mac:!symbian:contains(QT_CONFIG, xvideo):contains(QT_CONFIG, gstreamer) {
+ unix:!mac:!symbian:contains(QT_CONFIG, gstreamer) {
SUBDIRS += gstreamer
}
+
+ symbian:SUBDIRS += symbian
}
diff --git a/src/plugins/mediaservices/symbian/mediaplayer/mediaplayer.pri b/src/plugins/mediaservices/symbian/mediaplayer/mediaplayer.pri
new file mode 100644
index 0000000..205e014
--- /dev/null
+++ b/src/plugins/mediaservices/symbian/mediaplayer/mediaplayer.pri
@@ -0,0 +1,63 @@
+INCLUDEPATH += $$PWD
+LIBS += -lmediaclientvideo \
+ -lmediaclientaudio \
+ -lws32 \
+ -lfbscli \
+ -lcone \
+ -lmmfcontrollerframework \
+ -lefsrv \
+ -lbitgdi \
+ -lapgrfx \
+ -lapmime
+
+
+# We are building Symbian backend with media player support
+DEFINES += QMEDIA_MMF_PLAYER
+
+
+HEADERS += \
+ $$PWD/s60mediaplayercontrol.h \
+ $$PWD/s60mediaplayerservice.h \
+ $$PWD/s60mediaplayersession.h \
+ $$PWD/s60videoplayersession.h \
+ $$PWD/s60mediametadataprovider.h \
+ $$PWD/s60videosurface.h \
+ $$PWD/s60videooverlay.h \
+ $$PWD/s60videorenderer.h \
+ $$PWD/s60mediarecognizer.h \
+ $$PWD/s60audioplayersession.h \
+ $$PWD/ms60mediaplayerresolver.h \
+ $$PWD/s60videowidget.h \
+ $$PWD/s60mediaplayeraudioendpointselector.h
+
+SOURCES += \
+ $$PWD/s60mediaplayercontrol.cpp \
+ $$PWD/s60mediaplayerservice.cpp \
+ $$PWD/s60mediaplayersession.cpp \
+ $$PWD/s60videoplayersession.cpp \
+ $$PWD/s60mediametadataprovider.cpp \
+ $$PWD/s60videosurface.cpp \
+ $$PWD/s60videooverlay.cpp \
+ $$PWD/s60videorenderer.cpp \
+ $$PWD/s60mediarecognizer.cpp \
+ $$PWD/s60audioplayersession.cpp \
+ $$PWD/s60videowidget.cpp \
+ $$PWD/s60mediaplayeraudioendpointselector.cpp
+
+contains(S60_VERSION, 3.1) {
+
+ #3.1 doesn't provide audio routing in videoplayer
+ DEFINES += HAS_NO_AUDIOROUTING_IN_VIDEOPLAYER
+
+ !exists($${EPOCROOT}epoc32\release\winscw\udeb\audiooutputrouting.lib) {
+ MMP_RULES += "$${LITERAL_HASH}ifdef WINSCW" \
+ "MACRO HAS_NO_AUDIOROUTING" \
+ "$${LITERAL_HASH}else" \
+ "LIBRARY audiooutputrouting.lib" \
+ "$${LITERAL_HASH}endif"
+ }
+
+} else {
+ LIBS += -laudiooutputrouting
+}
+
diff --git a/src/plugins/mediaservices/symbian/mediaplayer/ms60mediaplayerresolver.h b/src/plugins/mediaservices/symbian/mediaplayer/ms60mediaplayerresolver.h
new file mode 100644
index 0000000..b655a83
--- /dev/null
+++ b/src/plugins/mediaservices/symbian/mediaplayer/ms60mediaplayerresolver.h
@@ -0,0 +1,58 @@
+/****************************************************************************
+**
+** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies).
+** All rights reserved.
+** Contact: Nokia Corporation (qt-info@nokia.com)
+**
+** This file is part of the plugins of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** No Commercial Usage
+** This file contains pre-release code and may not be distributed.
+** You may use this file in accordance with the terms and conditions
+** contained in the Technology Preview License Agreement accompanying
+** this package.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 2.1 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 2.1 requirements
+** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+**
+** In addition, as a special exception, Nokia gives you certain additional
+** rights. These rights are described in the Nokia Qt LGPL Exception
+** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+**
+** If you have questions regarding the use of this file, please contact
+** Nokia at qt-info@nokia.com.
+**
+**
+**
+**
+**
+**
+**
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+#ifndef MS60MEDIAPLAYERRESOLVER_H
+#define MS60MEDIAPLAYERRESOLVER_H
+
+QT_BEGIN_NAMESPACE
+
+class S60MediaPlayerSession;
+
+class MS60MediaPlayerResolver
+{
+ public:
+ virtual S60MediaPlayerSession* PlayerSession() = 0;
+ virtual S60MediaPlayerSession* VideoPlayerSession() = 0;
+ virtual S60MediaPlayerSession* AudioPlayerSession() = 0;
+};
+
+QT_END_NAMESPACE
+
+#endif
diff --git a/src/plugins/mediaservices/symbian/mediaplayer/s60audioplayersession.cpp b/src/plugins/mediaservices/symbian/mediaplayer/s60audioplayersession.cpp
new file mode 100644
index 0000000..f4065e4
--- /dev/null
+++ b/src/plugins/mediaservices/symbian/mediaplayer/s60audioplayersession.cpp
@@ -0,0 +1,268 @@
+/****************************************************************************
+**
+** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies).
+** All rights reserved.
+** Contact: Nokia Corporation (qt-info@nokia.com)
+**
+** This file is part of the plugins of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** No Commercial Usage
+** This file contains pre-release code and may not be distributed.
+** You may use this file in accordance with the terms and conditions
+** contained in the Technology Preview License Agreement accompanying
+** this package.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 2.1 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 2.1 requirements
+** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+**
+** In addition, as a special exception, Nokia gives you certain additional
+** rights. These rights are described in the Nokia Qt LGPL Exception
+** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+**
+** If you have questions regarding the use of this file, please contact
+** Nokia at qt-info@nokia.com.
+**
+**
+**
+**
+**
+**
+**
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#include "s60audioplayersession.h"
+#include <QtCore/qdebug.h>
+#include <QtCore/qvariant.h>
+
+#include <AudioOutput.h>
+#include <MAudioOutputObserver.h>
+
+QT_BEGIN_NAMESPACE
+
+S60AudioPlayerSession::S60AudioPlayerSession(QObject *parent)
+ : S60MediaPlayerSession(parent)
+ , m_player(0)
+ , m_audioOutput(0)
+ , m_audioEndpoint("Default")
+{
+ QT_TRAP_THROWING(m_player = CAudioPlayer::NewL(*this, 0, EMdaPriorityPreferenceNone));
+ m_player->RegisterForAudioLoadingNotification(*this);
+}
+
+S60AudioPlayerSession::~S60AudioPlayerSession()
+{
+#if !defined(HAS_NO_AUDIOROUTING)
+ if (m_audioOutput)
+ m_audioOutput->UnregisterObserver(*this);
+ delete m_audioOutput;
+#endif
+ m_player->Close();
+ delete m_player;
+}
+
+void S60AudioPlayerSession::doLoadL(const TDesC &path)
+{
+ // m_audioOutput needs to be reinitialized after MapcInitComplete
+ if (m_audioOutput)
+ m_audioOutput->UnregisterObserver(*this);
+ delete m_audioOutput;
+ m_audioOutput = NULL;
+
+ m_player->OpenFileL(path);
+}
+
+qint64 S60AudioPlayerSession::doGetDurationL() const
+{
+ return m_player->Duration().Int64() / qint64(1000);
+}
+
+qint64 S60AudioPlayerSession::doGetPositionL() const
+{
+ TTimeIntervalMicroSeconds ms = 0;
+ m_player->GetPosition(ms);
+ return ms.Int64() / qint64(1000);
+}
+
+bool S60AudioPlayerSession::isVideoAvailable() const
+{
+ return false;
+}
+bool S60AudioPlayerSession::isAudioAvailable() const
+{
+ return true; // this is a bit happy scenario, but we do emit error that we can't play
+}
+
+void S60AudioPlayerSession::MaloLoadingStarted()
+{
+ buffering();
+}
+
+void S60AudioPlayerSession::MaloLoadingComplete()
+{
+ buffered();
+}
+
+void S60AudioPlayerSession::doPlay()
+{
+// For some reason loading progress callbalck are not called on emulator
+#ifdef __WINSCW__
+ buffering();
+#endif
+ m_player->Play();
+#ifdef __WINSCW__
+ buffered();
+#endif
+
+}
+
+void S60AudioPlayerSession::doPauseL()
+{
+ m_player->Pause();
+}
+
+void S60AudioPlayerSession::doStop()
+{
+ m_player->Stop();
+}
+
+void S60AudioPlayerSession::doSetVolumeL(int volume)
+{
+ m_player->SetVolume((volume / 100.0) * m_player->MaxVolume());
+}
+
+void S60AudioPlayerSession::doSetPositionL(qint64 microSeconds)
+{
+ m_player->SetPosition(TTimeIntervalMicroSeconds(microSeconds));
+}
+
+void S60AudioPlayerSession::updateMetaDataEntriesL()
+{
+ metaDataEntries().clear();
+ int numberOfMetaDataEntries = 0;
+
+ m_player->GetNumberOfMetaDataEntries(numberOfMetaDataEntries);
+
+ for (int i = 0; i < numberOfMetaDataEntries; i++) {
+ CMMFMetaDataEntry *entry = NULL;
+ entry = m_player->GetMetaDataEntryL(i);
+ metaDataEntries().insert(QString::fromUtf16(entry->Name().Ptr(), entry->Name().Length()), QString::fromUtf16(entry->Value().Ptr(), entry->Value().Length()));
+ delete entry;
+ }
+ emit metaDataChanged();
+}
+
+int S60AudioPlayerSession::doGetBufferStatusL() const
+{
+ int progress = 0;
+ m_player->GetAudioLoadingProgressL(progress);
+ return progress;
+}
+
+void S60AudioPlayerSession::MapcInitComplete(TInt aError, const TTimeIntervalMicroSeconds& aDuration)
+{
+ Q_UNUSED(aDuration);
+ setError(aError);
+ TRAPD(err,
+ m_audioOutput = CAudioOutput::NewL(*m_player);
+ m_audioOutput->RegisterObserverL(*this);
+ );
+ setActiveEndpoint(m_audioEndpoint);
+ setError(err);
+ loaded();
+}
+
+void S60AudioPlayerSession::MapcPlayComplete(TInt aError)
+{
+ setError(aError);
+ endOfMedia();
+}
+
+void S60AudioPlayerSession::doSetAudioEndpoint(const QString& audioEndpoint)
+{
+ m_audioEndpoint = audioEndpoint;
+}
+
+QString S60AudioPlayerSession::activeEndpoint() const
+{
+ QString outputName = QString("Default");
+#if !defined(HAS_NO_AUDIOROUTING)
+ if (m_audioOutput) {
+ CAudioOutput::TAudioOutputPreference output = m_audioOutput->AudioOutput();
+ outputName = qStringFromTAudioOutputPreference(output);
+ }
+#endif
+ return outputName;
+}
+
+QString S60AudioPlayerSession::defaultEndpoint() const
+{
+ QString outputName = QString("Default");
+#if !defined(HAS_NO_AUDIOROUTING)
+ if (m_audioOutput) {
+ CAudioOutput::TAudioOutputPreference output = m_audioOutput->DefaultAudioOutput();
+ outputName = qStringFromTAudioOutputPreference(output);
+ }
+#endif
+ return outputName;
+}
+
+void S60AudioPlayerSession::setActiveEndpoint(const QString& name)
+{
+ CAudioOutput::TAudioOutputPreference output = CAudioOutput::ENoPreference;
+
+ if (name == QString("Default"))
+ output = CAudioOutput::ENoPreference;
+ else if (name == QString("All"))
+ output = CAudioOutput::EAll;
+ else if (name == QString("None"))
+ output = CAudioOutput::ENoOutput;
+ else if (name == QString("Earphone"))
+ output = CAudioOutput::EPrivate;
+ else if (name == QString("Speaker"))
+ output = CAudioOutput::EPublic;
+#if !defined(HAS_NO_AUDIOROUTING)
+ if (m_audioOutput) {
+ TRAPD(err, m_audioOutput->SetAudioOutputL(output));
+ setError(err);
+
+ if (m_audioEndpoint != name) {
+ m_audioEndpoint = name;
+ emit activeEndpointChanged(name);
+ }
+ }
+#endif
+}
+
+void S60AudioPlayerSession::DefaultAudioOutputChanged(CAudioOutput& aAudioOutput,
+ CAudioOutput::TAudioOutputPreference aNewDefault)
+{
+ // Emit already implemented in setActiveEndpoint function
+ Q_UNUSED(aAudioOutput)
+ Q_UNUSED(aNewDefault)
+}
+
+QString S60AudioPlayerSession::qStringFromTAudioOutputPreference(CAudioOutput::TAudioOutputPreference output) const
+{
+ if (output == CAudioOutput::ENoPreference)
+ return QString("Default");
+ else if (output == CAudioOutput::EAll)
+ return QString("All");
+ else if (output == CAudioOutput::ENoOutput)
+ return QString("None");
+ else if (output == CAudioOutput::EPrivate)
+ return QString("Earphone");
+ else if (output == CAudioOutput::EPublic)
+ return QString("Speaker");
+ return QString("Default");
+}
+
+QT_END_NAMESPACE
diff --git a/src/plugins/mediaservices/symbian/mediaplayer/s60audioplayersession.h b/src/plugins/mediaservices/symbian/mediaplayer/s60audioplayersession.h
new file mode 100644
index 0000000..fca66b3
--- /dev/null
+++ b/src/plugins/mediaservices/symbian/mediaplayer/s60audioplayersession.h
@@ -0,0 +1,116 @@
+/****************************************************************************
+**
+** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies).
+** All rights reserved.
+** Contact: Nokia Corporation (qt-info@nokia.com)
+**
+** This file is part of the plugins of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** No Commercial Usage
+** This file contains pre-release code and may not be distributed.
+** You may use this file in accordance with the terms and conditions
+** contained in the Technology Preview License Agreement accompanying
+** this package.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 2.1 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 2.1 requirements
+** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+**
+** In addition, as a special exception, Nokia gives you certain additional
+** rights. These rights are described in the Nokia Qt LGPL Exception
+** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+**
+** If you have questions regarding the use of this file, please contact
+** Nokia at qt-info@nokia.com.
+**
+**
+**
+**
+**
+**
+**
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#ifndef S60AUDIOPLAYERSESSION_H
+#define S60AUDIOPLAYERSESSION_H
+
+#include "s60mediaplayersession.h"
+
+#include <mdaaudiosampleplayer.h>
+typedef CMdaAudioPlayerUtility CAudioPlayer;
+typedef MMdaAudioPlayerCallback MAudioPlayerObserver;
+
+#include <AudioOutput.h>
+#include <MAudioOutputObserver.h>
+
+QT_BEGIN_NAMESPACE
+
+class S60AudioPlayerSession : public S60MediaPlayerSession
+ , public MAudioPlayerObserver
+ , public MAudioLoadingObserver
+ , public MAudioOutputObserver
+{
+ Q_OBJECT
+
+public:
+ S60AudioPlayerSession(QObject *parent);
+ ~S60AudioPlayerSession();
+
+ //From S60MediaPlayerSession
+ bool isVideoAvailable() const;
+ bool isAudioAvailable() const;
+
+ // From MAudioLoadingObserver
+ void MaloLoadingStarted();
+ void MaloLoadingComplete();
+
+ // From MAudioOutputObserver
+ void DefaultAudioOutputChanged( CAudioOutput& aAudioOutput,
+ CAudioOutput::TAudioOutputPreference aNewDefault );
+
+public:
+ // From S60MediaPlayerAudioEndpointSelector
+ QString activeEndpoint() const;
+ QString defaultEndpoint() const;
+public Q_SLOTS:
+ void setActiveEndpoint(const QString& name);
+Q_SIGNALS:
+ void activeEndpointChanged(const QString & name);
+
+protected:
+ //From S60MediaPlayerSession
+ void doLoadL(const TDesC &path);
+ void doLoadUrlL(const TDesC &path){Q_UNUSED(path)/*empty implementation*/}
+ void doPlay();
+ void doStop();
+ void doPauseL();
+ void doSetVolumeL(int volume);
+ qint64 doGetPositionL() const;
+ void doSetPositionL(qint64 microSeconds);
+ void updateMetaDataEntriesL();
+ int doGetBufferStatusL() const;
+ qint64 doGetDurationL() const;
+ void doSetAudioEndpoint(const QString& audioEndpoint);
+
+private:
+ void MapcInitComplete(TInt aError, const TTimeIntervalMicroSeconds& aDuration);
+ void MapcPlayComplete(TInt aError);
+ QString qStringFromTAudioOutputPreference(CAudioOutput::TAudioOutputPreference output) const;
+
+private:
+ CAudioPlayer *m_player;
+ CAudioOutput *m_audioOutput;
+ QString m_audioEndpoint;
+};
+
+QT_END_NAMESPACE
+
+#endif
diff --git a/src/plugins/mediaservices/symbian/mediaplayer/s60mediametadataprovider.cpp b/src/plugins/mediaservices/symbian/mediaplayer/s60mediametadataprovider.cpp
new file mode 100644
index 0000000..e80c487
--- /dev/null
+++ b/src/plugins/mediaservices/symbian/mediaplayer/s60mediametadataprovider.cpp
@@ -0,0 +1,185 @@
+/****************************************************************************
+**
+** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies).
+** All rights reserved.
+** Contact: Nokia Corporation (qt-info@nokia.com)
+**
+** This file is part of the plugins of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** No Commercial Usage
+** This file contains pre-release code and may not be distributed.
+** You may use this file in accordance with the terms and conditions
+** contained in the Technology Preview License Agreement accompanying
+** this package.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 2.1 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 2.1 requirements
+** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+**
+** In addition, as a special exception, Nokia gives you certain additional
+** rights. These rights are described in the Nokia Qt LGPL Exception
+** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+**
+** If you have questions regarding the use of this file, please contact
+** Nokia at qt-info@nokia.com.
+**
+**
+**
+**
+**
+**
+**
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#include "s60mediametadataprovider.h"
+#include "s60mediaplayersession.h"
+#include <QtCore/qdebug.h>
+
+QT_BEGIN_NAMESPACE
+
+S60MediaMetaDataProvider::S60MediaMetaDataProvider(MS60MediaPlayerResolver& mediaPlayerResolver, QObject *parent)
+ : QMetaDataControl(parent)
+ , m_mediaPlayerResolver(mediaPlayerResolver)
+ , m_session(NULL)
+{
+}
+
+S60MediaMetaDataProvider::~S60MediaMetaDataProvider()
+{
+}
+
+bool S60MediaMetaDataProvider::isMetaDataAvailable() const
+{
+ m_session = m_mediaPlayerResolver.PlayerSession();
+ if (m_session)
+ return m_session->isMetadataAvailable();
+ return false;
+}
+
+bool S60MediaMetaDataProvider::isWritable() const
+{
+ return false;
+}
+
+QVariant S60MediaMetaDataProvider::metaData(QtMediaServices::MetaData key) const
+{
+ m_session = m_mediaPlayerResolver.PlayerSession();
+ if (m_session && m_session->isMetadataAvailable())
+ return m_session->metaData(metaDataKeyAsString(key));
+ return QVariant();
+}
+
+void S60MediaMetaDataProvider::setMetaData(QtMediaServices::MetaData key, QVariant const &value)
+{
+ Q_UNUSED(key);
+ Q_UNUSED(value);
+}
+QList<QtMediaServices::MetaData> S60MediaMetaDataProvider::availableMetaData() const
+{
+ m_session = m_mediaPlayerResolver.PlayerSession();
+ QList<QtMediaServices::MetaData> metaDataTags;
+ if (m_session && m_session->isMetadataAvailable()) {
+ for (int i = QtMediaServices::Title; i <= QtMediaServices::DeviceSettingDescription; i++) {
+ QString metaData = metaDataKeyAsString((QtMediaServices::MetaData)i);
+ if (!metaData.isEmpty()) {
+ if (!m_session->metaData(metaData).toString().isEmpty()) {
+ metaDataTags.append((QtMediaServices::MetaData)i);
+ }
+ }
+ }
+ }
+ return metaDataTags;
+}
+
+QVariant S60MediaMetaDataProvider::extendedMetaData(const QString &key) const
+{
+ m_session = m_mediaPlayerResolver.PlayerSession();
+ if (m_session && m_session->isMetadataAvailable())
+ return m_session->metaData(key);
+ return QVariant();
+}
+
+void S60MediaMetaDataProvider::setExtendedMetaData(const QString &key, QVariant const &value)
+{
+ Q_UNUSED(key);
+ Q_UNUSED(value);
+}
+
+QStringList S60MediaMetaDataProvider::availableExtendedMetaData() const
+{
+ m_session = m_mediaPlayerResolver.PlayerSession();
+ if (m_session && m_session->isMetadataAvailable())
+ return m_session->availableMetaData().keys();
+ return QStringList();
+}
+
+QString S60MediaMetaDataProvider::metaDataKeyAsString(QtMediaServices::MetaData key) const
+{
+ switch(key) {
+ case QtMediaServices::Title: return "title";
+ case QtMediaServices::AlbumArtist: return "artist";
+ case QtMediaServices::Comment: return "comment";
+ case QtMediaServices::Genre: return "genre";
+ case QtMediaServices::Year: return "year";
+ case QtMediaServices::Copyright: return "copyright";
+ case QtMediaServices::AlbumTitle: return "album";
+ case QtMediaServices::Composer: return "composer";
+ case QtMediaServices::TrackNumber: return "albumtrack";
+ case QtMediaServices::AudioBitRate: return "audiobitrate";
+ case QtMediaServices::VideoBitRate: return "videobitrate";
+ case QtMediaServices::Duration: return "duration";
+ case QtMediaServices::MediaType: return "contenttype";
+ case QtMediaServices::SubTitle: // TODO: Find the matching metadata keys
+ case QtMediaServices::Description:
+ case QtMediaServices::Category:
+ case QtMediaServices::Date:
+ case QtMediaServices::UserRating:
+ case QtMediaServices::Keywords:
+ case QtMediaServices::Language:
+ case QtMediaServices::Publisher:
+ case QtMediaServices::ParentalRating:
+ case QtMediaServices::RatingOrganisation:
+ case QtMediaServices::Size:
+ case QtMediaServices::AudioCodec:
+ case QtMediaServices::AverageLevel:
+ case QtMediaServices::ChannelCount:
+ case QtMediaServices::PeakValue:
+ case QtMediaServices::SampleRate:
+ case QtMediaServices::Author:
+ case QtMediaServices::ContributingArtist:
+ case QtMediaServices::Conductor:
+ case QtMediaServices::Lyrics:
+ case QtMediaServices::Mood:
+ case QtMediaServices::TrackCount:
+ case QtMediaServices::CoverArtUrlSmall:
+ case QtMediaServices::CoverArtUrlLarge:
+ case QtMediaServices::Resolution:
+ case QtMediaServices::PixelAspectRatio:
+ case QtMediaServices::VideoFrameRate:
+ case QtMediaServices::VideoCodec:
+ case QtMediaServices::PosterUrl:
+ case QtMediaServices::ChapterNumber:
+ case QtMediaServices::Director:
+ case QtMediaServices::LeadPerformer:
+ case QtMediaServices::Writer:
+ case QtMediaServices::CameraManufacturer:
+ case QtMediaServices::CameraModel:
+ case QtMediaServices::Event:
+ case QtMediaServices::Subject:
+ default:
+ break;
+ }
+
+ return QString();
+}
+
+QT_END_NAMESPACE
+
diff --git a/src/plugins/mediaservices/symbian/mediaplayer/s60mediametadataprovider.h b/src/plugins/mediaservices/symbian/mediaplayer/s60mediametadataprovider.h
new file mode 100644
index 0000000..07ae494
--- /dev/null
+++ b/src/plugins/mediaservices/symbian/mediaplayer/s60mediametadataprovider.h
@@ -0,0 +1,81 @@
+/****************************************************************************
+**
+** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies).
+** All rights reserved.
+** Contact: Nokia Corporation (qt-info@nokia.com)
+**
+** This file is part of the plugins of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** No Commercial Usage
+** This file contains pre-release code and may not be distributed.
+** You may use this file in accordance with the terms and conditions
+** contained in the Technology Preview License Agreement accompanying
+** this package.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 2.1 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 2.1 requirements
+** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+**
+** In addition, as a special exception, Nokia gives you certain additional
+** rights. These rights are described in the Nokia Qt LGPL Exception
+** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+**
+** If you have questions regarding the use of this file, please contact
+** Nokia at qt-info@nokia.com.
+**
+**
+**
+**
+**
+**
+**
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#ifndef S60MEDIAMETADATAPROVIDER_H
+#define S60MEDIAMETADATAPROVIDER_H
+
+#include <qmetadatacontrol.h>
+#include "ms60mediaplayerresolver.h"
+
+QT_BEGIN_NAMESPACE
+
+class S60MediaPlayerSession;
+
+class S60MediaMetaDataProvider : public QMetaDataControl
+{
+ Q_OBJECT
+
+public:
+ S60MediaMetaDataProvider(MS60MediaPlayerResolver& mediaPlayerResolver, QObject *parent = 0);
+ ~S60MediaMetaDataProvider();
+
+ bool isMetaDataAvailable() const;
+ bool isWritable() const;
+
+ QVariant metaData(QtMediaServices::MetaData key) const;
+ void setMetaData(QtMediaServices::MetaData key, const QVariant &value);
+ QList<QtMediaServices::MetaData> availableMetaData() const;
+
+ QVariant extendedMetaData(const QString &key) const ;
+ void setExtendedMetaData(const QString &key, const QVariant &value);
+ QStringList availableExtendedMetaData() const;
+
+private:
+ QString metaDataKeyAsString(QtMediaServices::MetaData key) const;
+
+private:
+ MS60MediaPlayerResolver& m_mediaPlayerResolver;
+ mutable S60MediaPlayerSession *m_session;
+};
+
+QT_END_NAMESPACE
+
+#endif // S60VIDEOMETADATAPROVIDER_H
diff --git a/src/plugins/mediaservices/symbian/mediaplayer/s60mediaplayeraudioendpointselector.cpp b/src/plugins/mediaservices/symbian/mediaplayer/s60mediaplayeraudioendpointselector.cpp
new file mode 100644
index 0000000..dbeed90
--- /dev/null
+++ b/src/plugins/mediaservices/symbian/mediaplayer/s60mediaplayeraudioendpointselector.cpp
@@ -0,0 +1,127 @@
+/****************************************************************************
+**
+** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies).
+** All rights reserved.
+** Contact: Nokia Corporation (qt-info@nokia.com)
+**
+** This file is part of the plugins of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** No Commercial Usage
+** This file contains pre-release code and may not be distributed.
+** You may use this file in accordance with the terms and conditions
+** contained in the Technology Preview License Agreement accompanying
+** this package.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 2.1 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 2.1 requirements
+** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+**
+** In addition, as a special exception, Nokia gives you certain additional
+** rights. These rights are described in the Nokia Qt LGPL Exception
+** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+**
+** If you have questions regarding the use of this file, please contact
+** Nokia at qt-info@nokia.com.
+**
+**
+**
+**
+**
+**
+**
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#include "s60mediaplayercontrol.h"
+#include "s60mediaplayersession.h"
+#include "s60mediaplayeraudioendpointselector.h"
+
+#include <QtGui/QIcon>
+#include <QtCore/QDebug>
+
+QT_BEGIN_NAMESPACE
+
+S60MediaPlayerAudioEndpointSelector::S60MediaPlayerAudioEndpointSelector(QObject *control, QObject *parent)
+ :QMediaControl(parent)
+ , m_control(0)
+ , m_audioEndpointNames(0)
+{
+ m_control = qobject_cast<S60MediaPlayerControl*>(control);
+}
+
+S60MediaPlayerAudioEndpointSelector::~S60MediaPlayerAudioEndpointSelector()
+{
+ delete m_audioEndpointNames;
+}
+
+QList<QString> S60MediaPlayerAudioEndpointSelector::availableEndpoints() const
+{
+ if(m_audioEndpointNames->count() == 0) {
+ m_audioEndpointNames->append("Default");
+ m_audioEndpointNames->append("All");
+ m_audioEndpointNames->append("None");
+ m_audioEndpointNames->append("Earphone");
+ m_audioEndpointNames->append("Speaker");
+ }
+ return *m_audioEndpointNames;
+}
+
+QString S60MediaPlayerAudioEndpointSelector::endpointDescription(const QString& name) const
+{
+ if (name == QString("Default")) //ENoPreference
+ return QString("Used to indicate that the playing audio can be routed to"
+ "any speaker. This is the default value for audio.");
+ else if (name == QString("All")) //EAll
+ return QString("Used to indicate that the playing audio should be routed to all speakers.");
+ else if (name == QString("None")) //ENoOutput
+ return QString("Used to indicate that the playing audio should not be routed to any output.");
+ else if (name == QString("Earphone")) //EPrivate
+ return QString("Used to indicate that the playing audio should be routed to"
+ "the default private speaker. A private speaker is one that can only"
+ "be heard by one person.");
+ else if (name == QString("Speaker")) //EPublic
+ return QString("Used to indicate that the playing audio should be routed to"
+ "the default public speaker. A public speaker is one that can "
+ "be heard by multiple people.");
+
+ return QString();
+}
+
+QString S60MediaPlayerAudioEndpointSelector::activeEndpoint() const
+{
+ if (m_control->session())
+ return m_control->session()->activeEndpoint();
+ else
+ return m_control->mediaControlSettings().audioEndpoint();
+}
+
+QString S60MediaPlayerAudioEndpointSelector::defaultEndpoint() const
+{
+ if (m_control->session())
+ return m_control->session()->defaultEndpoint();
+ else
+ return m_control->mediaControlSettings().audioEndpoint();
+}
+
+void S60MediaPlayerAudioEndpointSelector::setActiveEndpoint(const QString& name)
+{
+ QString oldEndpoint = m_control->mediaControlSettings().audioEndpoint();
+
+ if (name != oldEndpoint && (name == QString("Default") || name == QString("All") ||
+ name == QString("None") || name == QString("Earphone") || name == QString("Speaker"))) {
+
+ if (m_control->session()) {
+ m_control->session()->setActiveEndpoint(name);
+ }
+ m_control->setAudioEndpoint(name);
+ }
+}
+
+QT_END_NAMESPACE
diff --git a/src/plugins/mediaservices/symbian/mediaplayer/s60mediaplayeraudioendpointselector.h b/src/plugins/mediaservices/symbian/mediaplayer/s60mediaplayeraudioendpointselector.h
new file mode 100644
index 0000000..a110ae8
--- /dev/null
+++ b/src/plugins/mediaservices/symbian/mediaplayer/s60mediaplayeraudioendpointselector.h
@@ -0,0 +1,81 @@
+/****************************************************************************
+**
+** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies).
+** All rights reserved.
+** Contact: Nokia Corporation (qt-info@nokia.com)
+**
+** This file is part of the plugins of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** No Commercial Usage
+** This file contains pre-release code and may not be distributed.
+** You may use this file in accordance with the terms and conditions
+** contained in the Technology Preview License Agreement accompanying
+** this package.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 2.1 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 2.1 requirements
+** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+**
+** In addition, as a special exception, Nokia gives you certain additional
+** rights. These rights are described in the Nokia Qt LGPL Exception
+** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+**
+** If you have questions regarding the use of this file, please contact
+** Nokia at qt-info@nokia.com.
+**
+**
+**
+**
+**
+**
+**
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#ifndef S60MEDIAPLAYERAUDIOENDPOINTSELECTOR_H
+#define S60MEDIAPLAYERAUDIOENDPOINTSELECTOR_H
+
+#include <QStringList>
+
+#include <QtMediaServices/qmediacontrol.h>
+
+QT_BEGIN_NAMESPACE
+
+class S60MediaPlayerControl;
+class S60MediaPlayerSession;
+
+class S60MediaPlayerAudioEndpointSelector : public QMediaControl
+{
+
+Q_OBJECT
+
+public:
+ S60MediaPlayerAudioEndpointSelector(QObject *control, QObject *parent = 0);
+ ~S60MediaPlayerAudioEndpointSelector();
+
+ QList<QString> availableEndpoints() const ;
+ QString endpointDescription(const QString& name) const;
+ QString defaultEndpoint() const;
+ QString activeEndpoint() const;
+
+public Q_SLOTS:
+ void setActiveEndpoint(const QString& name);
+
+private:
+ S60MediaPlayerControl* m_control;
+ QString m_audioInput;
+ QList<QString> *m_audioEndpointNames;
+};
+
+#define QAudioEndpointSelector_iid "com.nokia.Qt.QAudioEndpointSelector/1.0"
+
+QT_END_NAMESPACE
+
+#endif // S60MEDIAPLAYERAUDIOENDPOINTSELECTOR_H
diff --git a/src/plugins/mediaservices/symbian/mediaplayer/s60mediaplayercontrol.cpp b/src/plugins/mediaservices/symbian/mediaplayer/s60mediaplayercontrol.cpp
new file mode 100644
index 0000000..8e03afd
--- /dev/null
+++ b/src/plugins/mediaservices/symbian/mediaplayer/s60mediaplayercontrol.cpp
@@ -0,0 +1,274 @@
+
+/****************************************************************************
+**
+** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies).
+** All rights reserved.
+** Contact: Nokia Corporation (qt-info@nokia.com)
+**
+** This file is part of the plugins of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** No Commercial Usage
+** This file contains pre-release code and may not be distributed.
+** You may use this file in accordance with the terms and conditions
+** contained in the Technology Preview License Agreement accompanying
+** this package.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 2.1 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 2.1 requirements
+** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+**
+** In addition, as a special exception, Nokia gives you certain additional
+** rights. These rights are described in the Nokia Qt LGPL Exception
+** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+**
+** If you have questions regarding the use of this file, please contact
+** Nokia at qt-info@nokia.com.
+**
+**
+**
+**
+**
+**
+**
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#include "s60mediaplayercontrol.h"
+#include "s60mediaplayersession.h"
+
+#include <QtCore/qdir.h>
+#include <QtCore/qurl.h>
+#include <QtCore/qdebug.h>
+
+QT_BEGIN_NAMESPACE
+
+S60MediaPlayerControl::S60MediaPlayerControl(MS60MediaPlayerResolver& mediaPlayerResolver, QObject *parent)
+ : QMediaPlayerControl(parent),
+ m_mediaPlayerResolver(mediaPlayerResolver),
+ m_session(NULL),
+ m_stream(NULL)
+{
+}
+
+S60MediaPlayerControl::~S60MediaPlayerControl()
+{
+}
+
+qint64 S60MediaPlayerControl::position() const
+{
+ if (m_session)
+ return m_session->position();
+ return 0;
+}
+
+qint64 S60MediaPlayerControl::duration() const
+{
+ if (m_session)
+ return m_session->duration();
+ return -1;
+}
+
+QMediaPlayer::State S60MediaPlayerControl::state() const
+{
+ if (m_session)
+ return m_session->state();
+ return QMediaPlayer::StoppedState;
+}
+
+QMediaPlayer::MediaStatus S60MediaPlayerControl::mediaStatus() const
+{
+ if (m_session)
+ return m_session->mediaStatus();
+ return m_mediaSettings.mediaStatus();
+}
+
+int S60MediaPlayerControl::bufferStatus() const
+{
+ if (m_session)
+ return m_session->bufferStatus();
+ return 0;
+}
+
+int S60MediaPlayerControl::volume() const
+{
+ if (m_session)
+ return m_session->volume();
+ return m_mediaSettings.volume();
+}
+
+bool S60MediaPlayerControl::isMuted() const
+{
+ if (m_session)
+ return m_session->isMuted();
+ return m_mediaSettings.isMuted();
+}
+
+bool S60MediaPlayerControl::isSeekable() const
+{
+ if (m_session)
+ return m_session->isSeekable();
+ return false;
+}
+
+QMediaTimeRange S60MediaPlayerControl::availablePlaybackRanges() const
+{
+ QMediaTimeRange ranges;
+
+ if(m_session && m_session->isSeekable())
+ ranges.addInterval(0, m_session->duration());
+
+ return ranges;
+}
+
+qreal S60MediaPlayerControl::playbackRate() const
+{
+ //None of symbian players supports this.
+ return m_mediaSettings.playbackRate();
+}
+
+void S60MediaPlayerControl::setPlaybackRate(qreal rate)
+{
+ //None of symbian players supports this.
+ m_mediaSettings.setPlaybackRate(rate);
+ emit playbackRateChanged(playbackRate());
+
+}
+
+void S60MediaPlayerControl::setPosition(qint64 pos)
+{
+ if (m_session)
+ m_session->setPosition(pos);
+}
+
+void S60MediaPlayerControl::play()
+{
+ if (m_session)
+ m_session->play();
+}
+
+void S60MediaPlayerControl::pause()
+{
+ if (m_session)
+ m_session->pause();
+}
+
+void S60MediaPlayerControl::stop()
+{
+ if (m_session)
+ m_session->stop();
+}
+
+void S60MediaPlayerControl::setVolume(int volume)
+{
+ int boundVolume = qBound(0, volume, 100);
+ if (boundVolume == m_mediaSettings.volume())
+ return;
+
+ m_mediaSettings.setVolume(boundVolume);
+ if (m_session)
+ m_session->setVolume(boundVolume);
+
+ emit volumeChanged(boundVolume);
+}
+
+void S60MediaPlayerControl::setMuted(bool muted)
+{
+ if (m_mediaSettings.isMuted() == muted)
+ return;
+
+ m_mediaSettings.setMuted(muted);
+ if (m_session)
+ m_session->setMuted(muted);
+
+ emit mutedChanged(muted);
+}
+
+QMediaContent S60MediaPlayerControl::media() const
+{
+ return m_currentResource;
+}
+
+const QIODevice *S60MediaPlayerControl::mediaStream() const
+{
+ return m_stream;
+}
+
+void S60MediaPlayerControl::setMedia(const QMediaContent &source, QIODevice *stream)
+{
+ Q_UNUSED(stream)
+ // we don't want to set & load media again when it is already loaded
+ if (m_session && m_currentResource == source)
+ return;
+
+ // store to variable as session is created based on the content type.
+ m_currentResource = source;
+ S60MediaPlayerSession *newSession = m_mediaPlayerResolver.PlayerSession();
+ m_mediaSettings.setMediaStatus(QMediaPlayer::UnknownMediaStatus);
+
+ if (m_session)
+ m_session->reset();
+ else {
+ emit mediaStatusChanged(QMediaPlayer::UnknownMediaStatus);
+ emit error(QMediaPlayer::NoError, QString());
+ }
+
+ m_session = newSession;
+
+ if (m_session)
+ m_session->load(source.canonicalUrl());
+ else {
+ QMediaPlayer::MediaStatus status = (source.isNull()) ? QMediaPlayer::NoMedia : QMediaPlayer::InvalidMedia;
+ m_mediaSettings.setMediaStatus(status);
+ emit stateChanged(QMediaPlayer::StoppedState);
+ emit error((source.isNull()) ? QMediaPlayer::NoError : QMediaPlayer::ResourceError,
+ (source.isNull()) ? "" : tr("Media couldn't be resolved"));
+ emit mediaStatusChanged(status);
+ }
+ emit mediaChanged(m_currentResource);
+ }
+
+S60MediaPlayerSession* S60MediaPlayerControl::session()
+{
+ return m_session;
+}
+
+void S60MediaPlayerControl::setVideoOutput(QObject *output)
+{
+ S60MediaPlayerSession *session = NULL;
+ session = m_mediaPlayerResolver.VideoPlayerSession();
+ session->setVideoRenderer(output);
+}
+
+bool S60MediaPlayerControl::isAudioAvailable() const
+{
+ if (m_session)
+ return m_session->isAudioAvailable();
+ return false;
+}
+
+bool S60MediaPlayerControl::isVideoAvailable() const
+{
+ if (m_session)
+ return m_session->isVideoAvailable();
+ return false;
+}
+
+const S60MediaSettings& S60MediaPlayerControl::mediaControlSettings() const
+{
+ return m_mediaSettings;
+}
+
+void S60MediaPlayerControl::setAudioEndpoint(const QString& name)
+{
+ m_mediaSettings.setAudioEndpoint(name);
+}
+
+QT_END_NAMESPACE
+
diff --git a/src/plugins/mediaservices/symbian/mediaplayer/s60mediaplayercontrol.h b/src/plugins/mediaservices/symbian/mediaplayer/s60mediaplayercontrol.h
new file mode 100644
index 0000000..3d26a5e
--- /dev/null
+++ b/src/plugins/mediaservices/symbian/mediaplayer/s60mediaplayercontrol.h
@@ -0,0 +1,143 @@
+/****************************************************************************
+**
+** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies).
+** All rights reserved.
+** Contact: Nokia Corporation (qt-info@nokia.com)
+**
+** This file is part of the plugins of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** No Commercial Usage
+** This file contains pre-release code and may not be distributed.
+** You may use this file in accordance with the terms and conditions
+** contained in the Technology Preview License Agreement accompanying
+** this package.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 2.1 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 2.1 requirements
+** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+**
+** In addition, as a special exception, Nokia gives you certain additional
+** rights. These rights are described in the Nokia Qt LGPL Exception
+** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+**
+** If you have questions regarding the use of this file, please contact
+** Nokia at qt-info@nokia.com.
+**
+**
+**
+**
+**
+**
+**
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#ifndef S60MEDIAPLAYERCONTROL_H
+#define S60MEDIAPLAYERCONTROL_H
+
+#include <QtCore/qobject.h>
+
+#include <qmediaplayercontrol.h>
+
+#include "ms60mediaplayerresolver.h"
+#include <QtCore/qdebug.h>
+
+QT_BEGIN_NAMESPACE
+
+class QMediaPlayer;
+class QMediaTimeRange;
+class QMediaContent;
+
+
+class S60MediaPlayerSession;
+class S60MediaPlayerService;
+
+class S60MediaSettings
+{
+
+public:
+ S60MediaSettings()
+ : m_volume(0)
+ , m_muted(false)
+ , m_playbackRate(0)
+ , m_mediaStatus(QMediaPlayer::UnknownMediaStatus)
+ , m_audioEndpoint(QString("Default"))
+ {
+ }
+
+ void setVolume(int volume) { m_volume = volume; }
+ void setMuted(bool muted) { m_muted = muted; }
+ void setPlaybackRate(int rate) { m_playbackRate = rate; }
+ void setMediaStatus(QMediaPlayer::MediaStatus status) {m_mediaStatus=status;}
+ void setAudioEndpoint(const QString& audioEndpoint) { m_audioEndpoint = audioEndpoint; }
+
+ int volume() const { return m_volume; }
+ bool isMuted() const { return m_muted; }
+ qreal playbackRate() const { return m_playbackRate; }
+ QMediaPlayer::MediaStatus mediaStatus() const {return m_mediaStatus;}
+ QString audioEndpoint() const { return m_audioEndpoint; }
+
+private:
+ int m_volume;
+ bool m_muted;
+ qreal m_playbackRate;
+ QMediaPlayer::MediaStatus m_mediaStatus;
+ QString m_audioEndpoint;
+};
+
+class S60MediaPlayerControl : public QMediaPlayerControl
+{
+ Q_OBJECT
+
+public:
+ S60MediaPlayerControl(MS60MediaPlayerResolver& mediaPlayerResolver, QObject *parent = 0);
+ ~S60MediaPlayerControl();
+
+ // from QMediaPlayerControl
+ virtual QMediaPlayer::State state() const;
+ virtual QMediaPlayer::MediaStatus mediaStatus() const;
+ virtual qint64 duration() const;
+ virtual qint64 position() const;
+ virtual void setPosition(qint64 pos);
+ virtual int volume() const;
+ virtual void setVolume(int volume);
+ virtual bool isMuted() const;
+ virtual void setMuted(bool muted);
+ virtual int bufferStatus() const;
+ virtual bool isAudioAvailable() const;
+ virtual bool isVideoAvailable() const;
+ virtual bool isSeekable() const;
+ virtual QMediaTimeRange availablePlaybackRanges() const;
+ virtual qreal playbackRate() const;
+ virtual void setPlaybackRate(qreal rate);
+ virtual QMediaContent media() const;
+ virtual const QIODevice *mediaStream() const;
+ virtual void setMedia(const QMediaContent&, QIODevice *);
+ virtual void play();
+ virtual void pause();
+ virtual void stop();
+ S60MediaPlayerSession* session();
+ void setAudioEndpoint(const QString& name);
+
+ // Own methods
+ void setVideoOutput(QObject *output);
+ const S60MediaSettings& mediaControlSettings() const;
+
+private:
+ MS60MediaPlayerResolver &m_mediaPlayerResolver;
+ S60MediaPlayerSession *m_session;
+ QMediaContent m_currentResource;
+ QIODevice *m_stream;
+ S60MediaSettings m_mediaSettings;
+};
+
+QT_END_NAMESPACE
+
+#endif
diff --git a/src/plugins/mediaservices/symbian/mediaplayer/s60mediaplayerservice.cpp b/src/plugins/mediaservices/symbian/mediaplayer/s60mediaplayerservice.cpp
new file mode 100644
index 0000000..0b1c7d5
--- /dev/null
+++ b/src/plugins/mediaservices/symbian/mediaplayer/s60mediaplayerservice.cpp
@@ -0,0 +1,259 @@
+/****************************************************************************
+**
+** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies).
+** All rights reserved.
+** Contact: Nokia Corporation (qt-info@nokia.com)
+**
+** This file is part of the plugins of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** No Commercial Usage
+** This file contains pre-release code and may not be distributed.
+** You may use this file in accordance with the terms and conditions
+** contained in the Technology Preview License Agreement accompanying
+** this package.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 2.1 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 2.1 requirements
+** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+**
+** In addition, as a special exception, Nokia gives you certain additional
+** rights. These rights are described in the Nokia Qt LGPL Exception
+** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+**
+** If you have questions regarding the use of this file, please contact
+** Nokia at qt-info@nokia.com.
+**
+**
+**
+**
+**
+**
+**
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#include <QtCore/qvariant.h>
+#include <QtCore/qdebug.h>
+#include <QtGui/qwidget.h>
+
+#include "s60mediaplayerservice.h"
+#include "s60mediaplayercontrol.h"
+#include "s60videoplayersession.h"
+#include "s60audioplayersession.h"
+#include "s60mediametadataprovider.h"
+#include "s60videowidget.h"
+#include "s60mediarecognizer.h"
+//#include <qmediatimerange.h>
+#include "s60videooverlay.h"
+#include "s60videorenderer.h"
+#include "s60mediaplayeraudioendpointselector.h"
+
+#include <qmediaplaylistnavigator.h>
+#include <qmediaplaylist.h>
+
+QT_BEGIN_NAMESPACE
+
+S60MediaPlayerService::S60MediaPlayerService(QObject *parent)
+ : QMediaService(parent)
+ , m_control(NULL)
+ , m_videoOutput(NULL)
+ , m_videoPlayerSession(NULL)
+ , m_audioPlayerSession(NULL)
+ , m_metaData(NULL)
+ , m_videoWidget(NULL)
+ , m_videoWindow(NULL)
+ , m_videoRenderer(NULL)
+ , m_audioEndpointSelector(NULL)
+{
+ m_control = new S60MediaPlayerControl(*this, this);
+ m_metaData = new S60MediaMetaDataProvider(*this);
+ m_audioEndpointSelector = new S60MediaPlayerAudioEndpointSelector(m_control, this);
+}
+
+S60MediaPlayerService::~S60MediaPlayerService()
+{
+ delete m_videoWidget;
+ delete m_videoRenderer;
+ delete m_videoWindow;
+ delete m_videoOutput;
+}
+
+QMediaControl *S60MediaPlayerService::control(const char *name) const
+{
+ if (qstrcmp(name, QMediaPlayerControl_iid) == 0)
+ return m_control;
+
+ if (qstrcmp(name, QMetaDataControl_iid) == 0) {
+ return m_metaData;
+ }
+
+ if (qstrcmp(name, QVideoOutputControl_iid) == 0) {
+ if (!m_videoOutput) {
+ m_videoOutput = new S60VideoOutputControl;
+ connect(m_videoOutput, SIGNAL(outputChanged(QVideoOutputControl::Output)),
+ this, SLOT(videoOutputChanged(QVideoOutputControl::Output)));
+ m_videoOutput->setAvailableOutputs(QList<QVideoOutputControl::Output>()
+// << QVideoOutputControl::RendererOutput
+// << QVideoOutputControl::WindowOutput
+ << QVideoOutputControl::WidgetOutput);
+
+ }
+ return m_videoOutput;
+ }
+
+ if (qstrcmp(name, QVideoWidgetControl_iid) == 0) {
+ if (!m_videoWidget)
+ m_videoWidget = new S60VideoWidgetControl;
+ return m_videoWidget;
+ }
+
+ if (qstrcmp(name, QVideoRendererControl_iid) == 0) {
+ if (m_videoRenderer)
+ m_videoRenderer = new S60VideoRenderer;
+ return m_videoRenderer;
+ }
+
+ if (qstrcmp(name, QVideoWindowControl_iid) == 0) {
+ if (!m_videoWindow)
+ m_videoWindow = new S60VideoOverlay;
+ return m_videoWindow;
+ }
+
+ if (qstrcmp(name, QAudioEndpointSelector_iid) == 0) {
+ return m_audioEndpointSelector;
+ }
+
+ return 0;
+
+}
+
+void S60MediaPlayerService::videoOutputChanged(QVideoOutputControl::Output output)
+{
+ switch (output) {
+ case QVideoOutputControl::NoOutput:
+ m_control->setVideoOutput(0);
+ break;
+
+ case QVideoOutputControl::RendererOutput:
+ m_control->setVideoOutput(m_videoRenderer);
+ break;
+ case QVideoOutputControl::WindowOutput:
+ m_control->setVideoOutput(m_videoWindow);
+ break;
+
+ case QVideoOutputControl::WidgetOutput:
+ m_control->setVideoOutput(m_videoWidget);
+ break;
+ default:
+ qWarning("Invalid video output selection");
+ break;
+ }
+}
+
+S60MediaPlayerSession* S60MediaPlayerService::PlayerSession()
+{
+ QUrl url = m_control->media().canonicalUrl();
+
+ if (url.isEmpty() == true) {
+ return NULL;
+ }
+
+ S60MediaRecognizer *m_mediaRecognizer = new S60MediaRecognizer(this);
+ S60MediaRecognizer::MediaType mediaType = m_mediaRecognizer->mediaType(url);
+
+ switch (mediaType) {
+ case S60MediaRecognizer::Video:
+ case S60MediaRecognizer::Url:
+ return VideoPlayerSession();
+ case S60MediaRecognizer::Audio:
+ return AudioPlayerSession();
+ default:
+ break;
+ }
+
+ return NULL;
+}
+
+S60MediaPlayerSession* S60MediaPlayerService::VideoPlayerSession()
+{
+ if (!m_videoPlayerSession) {
+ m_videoPlayerSession = new S60VideoPlayerSession(this);
+
+ connect(m_videoPlayerSession, SIGNAL(positionChanged(qint64)),
+ m_control, SIGNAL(positionChanged(qint64)));
+ connect(m_videoPlayerSession, SIGNAL(durationChanged(qint64)),
+ m_control, SIGNAL(durationChanged(qint64)));
+ connect(m_videoPlayerSession, SIGNAL(stateChanged(QMediaPlayer::State)),
+ m_control, SIGNAL(stateChanged(QMediaPlayer::State)));
+ connect(m_videoPlayerSession, SIGNAL(mediaStatusChanged(QMediaPlayer::MediaStatus)),
+ m_control, SIGNAL(mediaStatusChanged(QMediaPlayer::MediaStatus)));
+ connect(m_videoPlayerSession,SIGNAL(bufferStatusChanged(int)),
+ m_control, SIGNAL(bufferStatusChanged(int)));
+ connect(m_videoPlayerSession, SIGNAL(videoAvailableChanged(bool)),
+ m_control, SIGNAL(videoAvailableChanged(bool)));
+ connect(m_videoPlayerSession, SIGNAL(audioAvailableChanged(bool)),
+ m_control, SIGNAL(audioAvailableChanged(bool)));
+ connect(m_videoPlayerSession, SIGNAL(seekableChanged(bool)),
+ m_control, SIGNAL(seekableChanged(bool)));
+ connect(m_videoPlayerSession, SIGNAL(availablePlaybackRangesChanged(const QMediaTimeRange&)),
+ m_control, SIGNAL(availablePlaybackRangesChanged(const QMediaTimeRange&)));
+ connect(m_videoPlayerSession, SIGNAL(error(int, const QString &)),
+ m_control, SIGNAL(error(int, const QString &)));
+ connect(m_videoPlayerSession, SIGNAL(metaDataChanged()),
+ m_metaData, SIGNAL(metaDataChanged()));
+ connect(m_videoPlayerSession, SIGNAL(activeEndpointChanged(const QString&)),
+ m_audioEndpointSelector, SIGNAL(activeEndpointChanged(const QString&)));
+ }
+
+ m_videoPlayerSession->setVolume(m_control->mediaControlSettings().volume());
+ m_videoPlayerSession->setMuted(m_control->mediaControlSettings().isMuted());
+ m_videoPlayerSession->setAudioEndpoint(m_control->mediaControlSettings().audioEndpoint());
+ return m_videoPlayerSession;
+}
+
+S60MediaPlayerSession* S60MediaPlayerService::AudioPlayerSession()
+{
+ if (!m_audioPlayerSession) {
+ m_audioPlayerSession = new S60AudioPlayerSession(this);
+
+ connect(m_audioPlayerSession, SIGNAL(positionChanged(qint64)),
+ m_control, SIGNAL(positionChanged(qint64)));
+ connect(m_audioPlayerSession, SIGNAL(durationChanged(qint64)),
+ m_control, SIGNAL(durationChanged(qint64)));
+ connect(m_audioPlayerSession, SIGNAL(stateChanged(QMediaPlayer::State)),
+ m_control, SIGNAL(stateChanged(QMediaPlayer::State)));
+ connect(m_audioPlayerSession, SIGNAL(mediaStatusChanged(QMediaPlayer::MediaStatus)),
+ m_control, SIGNAL(mediaStatusChanged(QMediaPlayer::MediaStatus)));
+ connect(m_audioPlayerSession,SIGNAL(bufferStatusChanged(int)),
+ m_control, SIGNAL(bufferStatusChanged(int)));
+ connect(m_audioPlayerSession, SIGNAL(videoAvailableChanged(bool)),
+ m_control, SIGNAL(videoAvailableChanged(bool)));
+ connect(m_audioPlayerSession, SIGNAL(audioAvailableChanged(bool)),
+ m_control, SIGNAL(audioAvailableChanged(bool)));
+ connect(m_audioPlayerSession, SIGNAL(seekableChanged(bool)),
+ m_control, SIGNAL(seekableChanged(bool)));
+ connect(m_audioPlayerSession, SIGNAL(availablePlaybackRangesChanged(const QMediaTimeRange&)),
+ m_control, SIGNAL(availablePlaybackRangesChanged(const QMediaTimeRange&)));
+ connect(m_audioPlayerSession, SIGNAL(error(int, const QString &)),
+ m_control, SIGNAL(error(int, const QString &)));
+ connect(m_audioPlayerSession, SIGNAL(metaDataChanged()),
+ m_metaData, SIGNAL(metaDataChanged()));
+ connect(m_audioPlayerSession, SIGNAL(activeEndpointChanged(const QString&)),
+ m_audioEndpointSelector, SIGNAL(activeEndpointChanged(const QString&)));
+ }
+
+ m_audioPlayerSession->setVolume(m_control->mediaControlSettings().volume());
+ m_audioPlayerSession->setMuted(m_control->mediaControlSettings().isMuted());
+ m_audioPlayerSession->setAudioEndpoint(m_control->mediaControlSettings().audioEndpoint());
+ return m_audioPlayerSession;
+}
+
+QT_END_NAMESPACE
+
diff --git a/src/plugins/mediaservices/symbian/mediaplayer/s60mediaplayerservice.h b/src/plugins/mediaservices/symbian/mediaplayer/s60mediaplayerservice.h
new file mode 100644
index 0000000..6c8155d
--- /dev/null
+++ b/src/plugins/mediaservices/symbian/mediaplayer/s60mediaplayerservice.h
@@ -0,0 +1,105 @@
+/****************************************************************************
+**
+** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies).
+** All rights reserved.
+** Contact: Nokia Corporation (qt-info@nokia.com)
+**
+** This file is part of the plugins of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** No Commercial Usage
+** This file contains pre-release code and may not be distributed.
+** You may use this file in accordance with the terms and conditions
+** contained in the Technology Preview License Agreement accompanying
+** this package.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 2.1 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 2.1 requirements
+** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+**
+** In addition, as a special exception, Nokia gives you certain additional
+** rights. These rights are described in the Nokia Qt LGPL Exception
+** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+**
+** If you have questions regarding the use of this file, please contact
+** Nokia at qt-info@nokia.com.
+**
+**
+**
+**
+**
+**
+**
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#ifndef S60VIDEOPLAYERSERVICE_H
+#define S60VIDEOPLAYERSERVICE_H
+
+#include <QtCore/qobject.h>
+
+#include <qmediaservice.h>
+#include <qvideooutputcontrol.h>
+
+#include "s60videooutputcontrol.h"
+#include "ms60mediaplayerresolver.h"
+
+#include "s60mediaplayeraudioendpointselector.h"
+
+QT_BEGIN_NAMESPACE
+
+class QMediaMetaData;
+class QMediaPlayerControl;
+class QMediaPlaylist;
+
+
+class S60VideoPlayerSession;
+class S60AudioPlayerSession;
+class S60MediaPlayerControl;
+class S60MediaMetaDataProvider;
+class S60VideoWidgetControl;
+class S60MediaRecognizer;
+class S60VideoRenderer;
+class S60VideoOverlay;
+
+class QMediaPlaylistNavigator;
+
+class S60MediaPlayerService : public QMediaService, public MS60MediaPlayerResolver
+{
+ Q_OBJECT
+
+public:
+ S60MediaPlayerService(QObject *parent = 0);
+ ~S60MediaPlayerService();
+
+ QMediaControl *control(const char *name) const;
+
+private slots:
+ void videoOutputChanged(QVideoOutputControl::Output output);
+
+protected: // From MS60MediaPlayerResolver
+ S60MediaPlayerSession* PlayerSession();
+ S60MediaPlayerSession* VideoPlayerSession();
+ S60MediaPlayerSession* AudioPlayerSession();
+
+private:
+ S60MediaPlayerControl *m_control;
+ mutable S60VideoOutputControl *m_videoOutput;
+ S60VideoPlayerSession *m_videoPlayerSession;
+ S60AudioPlayerSession *m_audioPlayerSession;
+ mutable S60MediaMetaDataProvider *m_metaData;
+ mutable S60VideoWidgetControl *m_videoWidget;
+ mutable S60VideoOverlay *m_videoWindow;
+ mutable S60VideoRenderer *m_videoRenderer;
+ S60MediaPlayerAudioEndpointSelector *m_audioEndpointSelector;
+};
+
+QT_END_NAMESPACE
+
+#endif
diff --git a/src/plugins/mediaservices/symbian/mediaplayer/s60mediaplayersession.cpp b/src/plugins/mediaservices/symbian/mediaplayer/s60mediaplayersession.cpp
new file mode 100644
index 0000000..693c103
--- /dev/null
+++ b/src/plugins/mediaservices/symbian/mediaplayer/s60mediaplayersession.cpp
@@ -0,0 +1,496 @@
+/****************************************************************************
+**
+** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies).
+** All rights reserved.
+** Contact: Nokia Corporation (qt-info@nokia.com)
+**
+** This file is part of the plugins of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** No Commercial Usage
+** This file contains pre-release code and may not be distributed.
+** You may use this file in accordance with the terms and conditions
+** contained in the Technology Preview License Agreement accompanying
+** this package.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 2.1 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 2.1 requirements
+** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+**
+** In addition, as a special exception, Nokia gives you certain additional
+** rights. These rights are described in the Nokia Qt LGPL Exception
+** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+**
+** If you have questions regarding the use of this file, please contact
+** Nokia at qt-info@nokia.com.
+**
+**
+**
+**
+**
+**
+**
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#include "s60mediaplayersession.h"
+
+#include <QtCore/qdebug.h>
+#include <QtCore/qdir.h>
+#include <QtCore/qvariant.h>
+#include <QtCore/qtimer.h>
+#include <mmf/common/mmferrors.h>
+#include <qmediatimerange.h>
+
+QT_BEGIN_NAMESPACE
+
+S60MediaPlayerSession::S60MediaPlayerSession(QObject *parent)
+ : QObject(parent)
+ , m_playbackRate(0)
+ , m_muted(false)
+ , m_volume(0)
+ , m_state(QMediaPlayer::StoppedState)
+ , m_mediaStatus(QMediaPlayer::UnknownMediaStatus)
+ , m_progressTimer(new QTimer(this))
+ , m_stalledTimer(new QTimer(this))
+ , m_error(KErrNone)
+ , m_play_requested(false)
+ , m_stream(false)
+{
+ connect(m_progressTimer, SIGNAL(timeout()), this, SLOT(tick()));
+ connect(m_stalledTimer, SIGNAL(timeout()), this, SLOT(stalled()));
+}
+
+S60MediaPlayerSession::~S60MediaPlayerSession()
+{
+}
+
+int S60MediaPlayerSession::volume() const
+{
+ return m_volume;
+}
+
+void S60MediaPlayerSession::setVolume(int volume)
+{
+ if (m_volume == volume)
+ return;
+
+ m_volume = volume;
+ // Dont set symbian players volume until media loaded.
+ // Leaves with KerrNotReady although documentation says otherwise.
+ if (!m_muted &&
+ ( mediaStatus() == QMediaPlayer::LoadedMedia
+ || mediaStatus() == QMediaPlayer::StalledMedia
+ || mediaStatus() == QMediaPlayer::BufferingMedia
+ || mediaStatus() == QMediaPlayer::BufferedMedia
+ || mediaStatus() == QMediaPlayer::EndOfMedia)) {
+ TRAPD(err, doSetVolumeL(m_volume));
+ setError(err);
+ }
+}
+
+bool S60MediaPlayerSession::isMuted() const
+{
+ return m_muted;
+}
+
+bool S60MediaPlayerSession::isSeekable() const
+{
+ return (m_stream)?false:true;
+}
+
+void S60MediaPlayerSession::setMediaStatus(QMediaPlayer::MediaStatus status)
+{
+ if (m_mediaStatus == status)
+ return;
+
+ m_mediaStatus = status;
+
+ emit mediaStatusChanged(m_mediaStatus);
+
+ if (m_play_requested)
+ play();
+}
+
+void S60MediaPlayerSession::setState(QMediaPlayer::State state)
+{
+ if (m_state == state)
+ return;
+
+ m_state = state;
+ emit stateChanged(m_state);
+}
+
+QMediaPlayer::State S60MediaPlayerSession::state() const
+{
+ return m_state;
+}
+
+QMediaPlayer::MediaStatus S60MediaPlayerSession::mediaStatus() const
+{
+ return m_mediaStatus;
+}
+
+void S60MediaPlayerSession::load(QUrl url)
+{
+ setMediaStatus(QMediaPlayer::LoadingMedia);
+ startStalledTimer();
+ m_stream = (url.scheme() == "file")?false:true;
+ TRAPD(err,
+ if(m_stream)
+ doLoadUrlL(QString2TPtrC(url.toString()));
+ else
+ doLoadL(QString2TPtrC(QDir::toNativeSeparators(url.toLocalFile()))));
+ setError(err);
+}
+
+void S60MediaPlayerSession::play()
+{
+ if (state() == QMediaPlayer::PlayingState
+ || mediaStatus() == QMediaPlayer::UnknownMediaStatus
+ || mediaStatus() == QMediaPlayer::NoMedia
+ || mediaStatus() == QMediaPlayer::InvalidMedia)
+ return;
+
+ if (mediaStatus() == QMediaPlayer::LoadingMedia) {
+ m_play_requested = true;
+ return;
+ }
+
+ m_play_requested = false;
+ setState(QMediaPlayer::PlayingState);
+ startProgressTimer();
+ doPlay();
+}
+
+void S60MediaPlayerSession::pause()
+{
+ if (mediaStatus() == QMediaPlayer::NoMedia ||
+ mediaStatus() == QMediaPlayer::InvalidMedia)
+ return;
+
+ setState(QMediaPlayer::PausedState);
+ stopProgressTimer();
+ TRAP_IGNORE(doPauseL());
+}
+
+void S60MediaPlayerSession::stop()
+{
+ m_play_requested = false;
+ setState(QMediaPlayer::StoppedState);
+ if (mediaStatus() == QMediaPlayer::BufferingMedia ||
+ mediaStatus() == QMediaPlayer::BufferedMedia)
+ setMediaStatus(QMediaPlayer::LoadedMedia);
+ if (mediaStatus() == QMediaPlayer::LoadingMedia)
+ setMediaStatus(QMediaPlayer::UnknownMediaStatus);
+ stopProgressTimer();
+ stopStalledTimer();
+ doStop();
+ emit positionChanged(0);
+}
+void S60MediaPlayerSession::reset()
+{
+ m_play_requested = false;
+ setError(KErrNone, QString(), true);
+ stopProgressTimer();
+ stopStalledTimer();
+ doStop();
+ setState(QMediaPlayer::StoppedState);
+ setMediaStatus(QMediaPlayer::UnknownMediaStatus);
+}
+
+void S60MediaPlayerSession::setVideoRenderer(QObject *renderer)
+{
+ Q_UNUSED(renderer);
+}
+
+int S60MediaPlayerSession::bufferStatus()
+{
+ if( mediaStatus() == QMediaPlayer::LoadingMedia
+ || mediaStatus() == QMediaPlayer::UnknownMediaStatus
+ || mediaStatus() == QMediaPlayer::NoMedia
+ || mediaStatus() == QMediaPlayer::InvalidMedia)
+ return 0;
+
+ int progress = 0;
+ TRAPD(err, progress = doGetBufferStatusL());
+
+ // If buffer status query not supported by codec return 100
+ // do not set error
+ if(err == KErrNotSupported)
+ return 100;
+
+ setError(err);
+ return progress;
+}
+
+bool S60MediaPlayerSession::isMetadataAvailable() const
+{
+ return !m_metaDataMap.isEmpty();
+}
+
+QVariant S60MediaPlayerSession::metaData(const QString &key) const
+{
+ return m_metaDataMap.value(key);
+}
+
+QMap<QString, QVariant> S60MediaPlayerSession::availableMetaData() const
+{
+ return m_metaDataMap;
+}
+
+void S60MediaPlayerSession::setMuted(bool muted)
+{
+ m_muted = muted;
+
+ if( m_mediaStatus == QMediaPlayer::LoadedMedia
+ || m_mediaStatus == QMediaPlayer::StalledMedia
+ || m_mediaStatus == QMediaPlayer::BufferingMedia
+ || m_mediaStatus == QMediaPlayer::BufferedMedia
+ || m_mediaStatus == QMediaPlayer::EndOfMedia) {
+ TRAPD(err, doSetVolumeL((m_muted)?0:m_volume));
+ setError(err);
+ }
+}
+
+qint64 S60MediaPlayerSession::duration() const
+{
+ if( mediaStatus() == QMediaPlayer::LoadingMedia
+ || mediaStatus() == QMediaPlayer::UnknownMediaStatus
+ || mediaStatus() == QMediaPlayer::NoMedia
+ || mediaStatus() == QMediaPlayer::InvalidMedia)
+ return -1;
+
+ qint64 pos = 0;
+ TRAP_IGNORE(pos = doGetDurationL());
+ return pos;
+}
+
+qint64 S60MediaPlayerSession::position() const
+{
+ if( mediaStatus() == QMediaPlayer::LoadingMedia
+ || mediaStatus() == QMediaPlayer::UnknownMediaStatus
+ || mediaStatus() == QMediaPlayer::NoMedia
+ || mediaStatus() == QMediaPlayer::InvalidMedia)
+ return 0;
+
+ qint64 pos = 0;
+ TRAP_IGNORE(pos = doGetPositionL());
+ return pos;
+}
+
+void S60MediaPlayerSession::setPosition(qint64 pos)
+{
+ if (position() == pos)
+ return;
+
+ if (state() == QMediaPlayer::PlayingState)
+ pause();
+
+ TRAPD(err, doSetPositionL(pos * 1000));
+ setError(err);
+
+ if (state() == QMediaPlayer::PausedState)
+ play();
+
+ emit positionChanged(position());
+}
+
+void S60MediaPlayerSession::setAudioEndpoint(const QString& audioEndpoint)
+{
+ doSetAudioEndpoint(audioEndpoint);
+}
+
+void S60MediaPlayerSession::loaded()
+{
+ stopStalledTimer();
+ if (m_error == KErrNone || m_error == KErrMMPartialPlayback) {
+ setMediaStatus(QMediaPlayer::LoadedMedia);
+ TRAPD(err, updateMetaDataEntriesL());
+ setError(err);
+ setVolume(m_volume);
+ setMuted(m_muted);
+ emit durationChanged(duration());
+ emit videoAvailableChanged(isVideoAvailable());
+ emit audioAvailableChanged(isAudioAvailable());
+ }
+}
+
+void S60MediaPlayerSession::endOfMedia()
+{
+ setMediaStatus(QMediaPlayer::EndOfMedia);
+ setState(QMediaPlayer::StoppedState);
+ emit positionChanged(0);
+}
+
+void S60MediaPlayerSession::buffering()
+{
+ startStalledTimer();
+ setMediaStatus(QMediaPlayer::BufferingMedia);
+}
+
+void S60MediaPlayerSession::buffered()
+{
+ stopStalledTimer();
+ setMediaStatus(QMediaPlayer::BufferedMedia);
+}
+void S60MediaPlayerSession::stalled()
+{
+ setMediaStatus(QMediaPlayer::StalledMedia);
+}
+
+QMap<QString, QVariant>& S60MediaPlayerSession::metaDataEntries()
+{
+ return m_metaDataMap;
+}
+
+QMediaPlayer::Error S60MediaPlayerSession::fromSymbianErrorToMultimediaError(int error)
+{
+ switch(error) {
+ case KErrNoMemory:
+ case KErrNotFound:
+ case KErrBadHandle:
+ case KErrAbort:
+ case KErrNotSupported:
+ case KErrCorrupt:
+ case KErrGeneral:
+ case KErrArgument:
+ case KErrPathNotFound:
+ case KErrDied:
+ case KErrServerTerminated:
+ case KErrServerBusy:
+ case KErrCompletion:
+ case KErrBadPower:
+ return QMediaPlayer::ResourceError;
+
+ case KErrMMPartialPlayback:
+ return QMediaPlayer::FormatError;
+
+ case KErrMMAudioDevice:
+ case KErrMMVideoDevice:
+ case KErrMMDecoder:
+ case KErrUnknown:
+ return QMediaPlayer::ServiceMissingError;
+
+ case KErrMMNotEnoughBandwidth:
+ case KErrMMSocketServiceNotFound:
+ case KErrMMNetworkRead:
+ case KErrMMNetworkWrite:
+ case KErrMMServerSocket:
+ case KErrMMServerNotSupported:
+ case KErrMMUDPReceive:
+ case KErrMMInvalidProtocol:
+ case KErrMMInvalidURL:
+ case KErrMMMulticast:
+ case KErrMMProxyServer:
+ case KErrMMProxyServerNotSupported:
+ case KErrMMProxyServerConnect:
+ return QMediaPlayer::NetworkError;
+
+ case KErrNotReady:
+ case KErrInUse:
+ case KErrAccessDenied:
+ case KErrLocked:
+ case KErrMMDRMNotAuthorized:
+ case KErrPermissionDenied:
+ case KErrCancel:
+ case KErrAlreadyExists:
+ return QMediaPlayer::AccessDeniedError;
+
+ case KErrNone:
+ default:
+ return QMediaPlayer::NoError;
+ }
+}
+
+void S60MediaPlayerSession::setError(int error, const QString &errorString, bool forceReset)
+{
+ if( forceReset ) {
+ m_error = KErrNone;
+ emit this->error(QMediaPlayer::NoError, QString());
+ return;
+ }
+
+ // If error does not change and m_error is reseted without forceReset flag
+ if (error == m_error ||
+ (m_error != KErrNone && error == KErrNone))
+ return;
+
+ m_error = error;
+ QMediaPlayer::Error mediaError = fromSymbianErrorToMultimediaError(m_error);
+ QString symbianError = QString(errorString);
+
+ if (mediaError != QMediaPlayer::NoError) {
+ // TODO: fix to user friendly string at some point
+ // These error string are only dev usable
+ symbianError.append("Symbian:");
+ symbianError.append(QString::number(m_error));
+ }
+
+ emit this->error(mediaError, symbianError);
+
+ switch(mediaError){
+ case QMediaPlayer::ResourceError:
+ case QMediaPlayer::NetworkError:
+ case QMediaPlayer::AccessDeniedError:
+ case QMediaPlayer::ServiceMissingError:
+ m_play_requested = false;
+ setMediaStatus(QMediaPlayer::InvalidMedia);
+ stop();
+ break;
+ }
+}
+
+void S60MediaPlayerSession::tick()
+{
+ emit positionChanged(position());
+
+ if (bufferStatus() < 100)
+ emit bufferStatusChanged(bufferStatus());
+}
+
+void S60MediaPlayerSession::startProgressTimer()
+{
+ m_progressTimer->start(500);
+}
+
+void S60MediaPlayerSession::stopProgressTimer()
+{
+ m_progressTimer->stop();
+}
+
+void S60MediaPlayerSession::startStalledTimer()
+{
+ m_stalledTimer->start(30000);
+}
+
+void S60MediaPlayerSession::stopStalledTimer()
+{
+ m_stalledTimer->stop();
+}
+QString S60MediaPlayerSession::TDesC2QString(const TDesC& aDescriptor)
+{
+ return QString::fromUtf16(aDescriptor.Ptr(), aDescriptor.Length());
+}
+TPtrC S60MediaPlayerSession::QString2TPtrC( const QString& string )
+{
+ // Returned TPtrC is valid as long as the given parameter is valid and unmodified
+ return TPtrC16(static_cast<const TUint16*>(string.utf16()), string.length());
+}
+QRect S60MediaPlayerSession::TRect2QRect(const TRect& tr)
+{
+ return QRect(tr.iTl.iX, tr.iTl.iY, tr.Width(), tr.Height());
+}
+TRect S60MediaPlayerSession::QRect2TRect(const QRect& qr)
+{
+ return TRect(TPoint(qr.left(), qr.top()), TSize(qr.width(), qr.height()));
+}
+
+QT_END_NAMESPACE
+
diff --git a/src/plugins/mediaservices/symbian/mediaplayer/s60mediaplayersession.h b/src/plugins/mediaservices/symbian/mediaplayer/s60mediaplayersession.h
new file mode 100644
index 0000000..bb9eddd
--- /dev/null
+++ b/src/plugins/mediaservices/symbian/mediaplayer/s60mediaplayersession.h
@@ -0,0 +1,167 @@
+/****************************************************************************
+**
+** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies).
+** All rights reserved.
+** Contact: Nokia Corporation (qt-info@nokia.com)
+**
+** This file is part of the plugins of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** No Commercial Usage
+** This file contains pre-release code and may not be distributed.
+** You may use this file in accordance with the terms and conditions
+** contained in the Technology Preview License Agreement accompanying
+** this package.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 2.1 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 2.1 requirements
+** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+**
+** In addition, as a special exception, Nokia gives you certain additional
+** rights. These rights are described in the Nokia Qt LGPL Exception
+** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+**
+** If you have questions regarding the use of this file, please contact
+** Nokia at qt-info@nokia.com.
+**
+**
+**
+**
+**
+**
+**
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#ifndef S60MEDIAPLAYERSESSION_H
+#define S60MEDIAPLAYERSESSION_H
+
+#include <QtCore/qobject.h>
+#include <QtCore/qurl.h>
+#include <QtCore/qpair.h>
+#include <qmediaplayer.h>
+#include <e32cmn.h> // for TDesC
+#include <QRect>
+#include "s60mediaplayerservice.h"
+
+QT_BEGIN_NAMESPACE
+
+class QMediaTimeRange;
+
+class QTimer;
+
+class S60MediaPlayerSession : public QObject
+{
+ Q_OBJECT
+
+public:
+ S60MediaPlayerSession(QObject *parent);
+ virtual ~S60MediaPlayerSession();
+
+ // for player control interface to use
+ QMediaPlayer::State state() const;
+ QMediaPlayer::MediaStatus mediaStatus() const;
+ qint64 duration() const;
+ qint64 position() const;
+ void setPosition(qint64 pos);
+ int volume() const;
+ void setVolume(int volume);
+ bool isMuted() const;
+ void setMuted(bool muted);
+ virtual bool isVideoAvailable() const = 0;
+ virtual bool isAudioAvailable() const = 0;
+ bool isSeekable() const;
+ void play();
+ void pause();
+ void stop();
+ void reset();
+ bool isMetadataAvailable() const;
+ QVariant metaData(const QString &key) const;
+ QMap<QString, QVariant> availableMetaData() const;
+ void load(QUrl url);
+ int bufferStatus();
+ virtual void setVideoRenderer(QObject *renderer);
+ void setMediaStatus(QMediaPlayer::MediaStatus);
+ void setState(QMediaPlayer::State state);
+ void setAudioEndpoint(const QString& audioEndpoint);
+
+protected:
+ virtual void doLoadL(const TDesC &path) = 0;
+ virtual void doLoadUrlL(const TDesC &path) = 0;
+ virtual void doPlay() = 0;
+ virtual void doStop() = 0;
+ virtual void doPauseL() = 0;
+ virtual void doSetVolumeL(int volume) = 0;
+ virtual void doSetPositionL(qint64 microSeconds) = 0;
+ virtual qint64 doGetPositionL() const = 0;
+ virtual void updateMetaDataEntriesL() = 0;
+ virtual int doGetBufferStatusL() const = 0;
+ virtual qint64 doGetDurationL() const = 0;
+ virtual void doSetAudioEndpoint(const QString& audioEndpoint) = 0;
+
+public:
+ // From S60MediaPlayerAudioEndpointSelector
+ virtual QString activeEndpoint() const = 0;
+ virtual QString defaultEndpoint() const = 0;
+public Q_SLOTS:
+ virtual void setActiveEndpoint(const QString& name) = 0;
+
+protected:
+ void setError(int error, const QString &errorString = QString(), bool forceReset = false);
+ void loaded();
+ void buffering();
+ void buffered();
+ void endOfMedia();
+ QMap<QString, QVariant>& metaDataEntries();
+ QMediaPlayer::Error fromSymbianErrorToMultimediaError(int error);
+ void startProgressTimer();
+ void stopProgressTimer();
+ void startStalledTimer();
+ void stopStalledTimer();
+ QString TDesC2QString(const TDesC& aDescriptor);
+ TPtrC QString2TPtrC( const QString& string );
+ QRect TRect2QRect(const TRect& tr);
+ TRect QRect2TRect(const QRect& qr);
+
+
+protected slots:
+ void tick();
+ void stalled();
+
+signals:
+ void durationChanged(qint64 duration);
+ void positionChanged(qint64 position);
+ void stateChanged(QMediaPlayer::State state);
+ void mediaStatusChanged(QMediaPlayer::MediaStatus mediaStatus);
+ void videoAvailableChanged(bool videoAvailable);
+ void audioAvailableChanged(bool audioAvailable);
+ void bufferStatusChanged(int percentFilled);
+ void seekableChanged(bool);
+ void availablePlaybackRangesChanged(const QMediaTimeRange&);
+ void metaDataChanged();
+ void error(int error, const QString &errorString);
+ void activeEndpointChanged(const QString &name);
+
+private:
+ qreal m_playbackRate;
+ QMap<QString, QVariant> m_metaDataMap;
+ bool m_muted;
+ int m_volume;
+ QMediaPlayer::State m_state;
+ QMediaPlayer::MediaStatus m_mediaStatus;
+ QTimer *m_progressTimer;
+ QTimer *m_stalledTimer;
+ int m_error;
+ bool m_play_requested;
+ bool m_stream;
+};
+
+QT_END_NAMESPACE
+
+#endif
diff --git a/src/plugins/mediaservices/symbian/mediaplayer/s60mediarecognizer.cpp b/src/plugins/mediaservices/symbian/mediaplayer/s60mediarecognizer.cpp
new file mode 100644
index 0000000..b563dd9
--- /dev/null
+++ b/src/plugins/mediaservices/symbian/mediaplayer/s60mediarecognizer.cpp
@@ -0,0 +1,127 @@
+/****************************************************************************
+**
+** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies).
+** All rights reserved.
+** Contact: Nokia Corporation (qt-info@nokia.com)
+**
+** This file is part of the plugins of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** No Commercial Usage
+** This file contains pre-release code and may not be distributed.
+** You may use this file in accordance with the terms and conditions
+** contained in the Technology Preview License Agreement accompanying
+** this package.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 2.1 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 2.1 requirements
+** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+**
+** In addition, as a special exception, Nokia gives you certain additional
+** rights. These rights are described in the Nokia Qt LGPL Exception
+** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+**
+** If you have questions regarding the use of this file, please contact
+** Nokia at qt-info@nokia.com.
+**
+**
+**
+**
+**
+**
+**
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#include "S60mediarecognizer.h"
+#include <e32def.h>
+#include <e32cmn.h>
+#include <QtCore/qurl.h>
+#include <QtCore/qdir.h>
+#include <QtCore/qdebug.h>
+
+#include <apgcli.h>
+
+QT_BEGIN_NAMESPACE
+
+static const TInt KMimeTypePrefixLength = 6; // "audio/" or "video/"
+_LIT(KMimeTypePrefixAudio, "audio/");
+_LIT(KMimeTypePrefixVideo, "video/");
+
+S60MediaRecognizer::S60MediaRecognizer(QObject *parent) : QObject(parent)
+{
+}
+
+S60MediaRecognizer::~S60MediaRecognizer()
+{
+ m_file.Close();
+ m_fileServer.Close();
+ m_recognizer.Close();
+}
+
+S60MediaRecognizer::MediaType S60MediaRecognizer::mediaType(const QUrl &url)
+{
+ bool isStream = (url.scheme() == "file")?false:true;
+
+ if (isStream)
+ return Url;
+ else
+ return identifyMediaType(url.toLocalFile());
+}
+
+S60MediaRecognizer::MediaType S60MediaRecognizer::identifyMediaType(const QString& fileName)
+{
+ S60MediaRecognizer::MediaType result = NotSupported;
+ bool recognizerOpened = false;
+
+ TInt err = m_recognizer.Connect();
+ if (err == KErrNone) {
+ recognizerOpened = true;
+ }
+
+ err = m_fileServer.Connect();
+ if (err == KErrNone) {
+ recognizerOpened = true;
+ }
+
+ // This is needed for sharing file handles for the recognizer
+ err = m_fileServer.ShareProtected();
+ if (err == KErrNone) {
+ recognizerOpened = true;
+ }
+
+ if (recognizerOpened) {
+ m_file.Close();
+ err = m_file.Open(m_fileServer, QString2TPtrC(QDir::toNativeSeparators(fileName)), EFileRead |
+ EFileShareReadersOnly);
+
+ if (err == KErrNone) {
+ TDataRecognitionResult recognizerResult;
+ err = m_recognizer.RecognizeData(m_file, recognizerResult);
+ if (err == KErrNone) {
+ const TPtrC mimeType = recognizerResult.iDataType.Des();
+
+ if (mimeType.Left(KMimeTypePrefixLength).Compare(KMimeTypePrefixAudio) == 0) {
+ result = Audio;
+ } else if (mimeType.Left(KMimeTypePrefixLength).Compare(KMimeTypePrefixVideo) == 0) {
+ result = Video;
+ }
+ }
+ }
+ }
+ return result;
+}
+
+TPtrC S60MediaRecognizer::QString2TPtrC( const QString& string )
+{
+ // Returned TPtrC is valid as long as the given parameter is valid and unmodified
+ return TPtrC16(static_cast<const TUint16*>(string.utf16()), string.length());
+}
+
+QT_END_NAMESPACE
diff --git a/src/plugins/mediaservices/symbian/mediaplayer/s60mediarecognizer.h b/src/plugins/mediaservices/symbian/mediaplayer/s60mediarecognizer.h
new file mode 100644
index 0000000..320c34c
--- /dev/null
+++ b/src/plugins/mediaservices/symbian/mediaplayer/s60mediarecognizer.h
@@ -0,0 +1,83 @@
+/****************************************************************************
+**
+** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies).
+** All rights reserved.
+** Contact: Nokia Corporation (qt-info@nokia.com)
+**
+** This file is part of the plugins of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** No Commercial Usage
+** This file contains pre-release code and may not be distributed.
+** You may use this file in accordance with the terms and conditions
+** contained in the Technology Preview License Agreement accompanying
+** this package.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 2.1 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 2.1 requirements
+** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+**
+** In addition, as a special exception, Nokia gives you certain additional
+** rights. These rights are described in the Nokia Qt LGPL Exception
+** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+**
+** If you have questions regarding the use of this file, please contact
+** Nokia at qt-info@nokia.com.
+**
+**
+**
+**
+**
+**
+**
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#ifndef S60MEDIARECOGNIZER_H_
+#define S60MEDIARECOGNIZER_H_
+
+#include <QtCore/qobject.h>
+
+#include <apgcli.h>
+#include <f32file.h>
+
+QT_BEGIN_NAMESPACE
+
+class QUrl;
+
+class S60MediaRecognizer : public QObject
+{
+ Q_OBJECT
+
+public:
+ enum MediaType {
+ Audio,
+ Video,
+ Url,
+ NotSupported = -1
+ };
+
+ S60MediaRecognizer(QObject *parent = 0);
+ ~S60MediaRecognizer();
+
+ S60MediaRecognizer::MediaType mediaType(const QUrl &url);
+ S60MediaRecognizer::MediaType identifyMediaType(const QString& fileName);
+
+protected:
+ TPtrC QString2TPtrC( const QString& string );
+
+private:
+ RApaLsSession m_recognizer;
+ RFile m_file;
+ RFs m_fileServer;
+};
+
+QT_END_NAMESPACE
+
+#endif /* S60MEDIARECOGNIZER_H_ */
diff --git a/src/plugins/mediaservices/symbian/mediaplayer/s60videooverlay.cpp b/src/plugins/mediaservices/symbian/mediaplayer/s60videooverlay.cpp
new file mode 100644
index 0000000..489b2e3
--- /dev/null
+++ b/src/plugins/mediaservices/symbian/mediaplayer/s60videooverlay.cpp
@@ -0,0 +1,209 @@
+/****************************************************************************
+**
+** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies).
+** All rights reserved.
+** Contact: Nokia Corporation (qt-info@nokia.com)
+**
+** This file is part of the plugins of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** No Commercial Usage
+** This file contains pre-release code and may not be distributed.
+** You may use this file in accordance with the terms and conditions
+** contained in the Technology Preview License Agreement accompanying
+** this package.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 2.1 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 2.1 requirements
+** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+**
+** In addition, as a special exception, Nokia gives you certain additional
+** rights. These rights are described in the Nokia Qt LGPL Exception
+** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+**
+** If you have questions regarding the use of this file, please contact
+** Nokia at qt-info@nokia.com.
+**
+**
+**
+**
+**
+**
+**
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#include <QtMultimedia/qvideosurfaceformat.h>
+#include "s60videooverlay.h"
+#include "s60videosurface.h"
+
+QT_BEGIN_NAMESPACE
+
+S60VideoOverlay::S60VideoOverlay(QObject *parent)
+ : QVideoWindowControl(parent)
+ , m_surface(new S60VideoSurface)
+ , m_aspectRatioMode(Qt::KeepAspectRatio)
+ , m_fullScreen(false)
+{
+ connect(m_surface, SIGNAL(surfaceFormatChanged(QVideoSurfaceFormat)),
+ this, SLOT(surfaceFormatChanged()));
+}
+
+S60VideoOverlay::~S60VideoOverlay()
+{
+ delete m_surface;
+}
+
+WId S60VideoOverlay::winId() const
+{
+ return m_surface->winId();
+}
+
+void S60VideoOverlay::setWinId(WId id)
+{
+ m_surface->setWinId(id);
+}
+
+QRect S60VideoOverlay::displayRect() const
+{
+ return m_displayRect;
+}
+
+void S60VideoOverlay::setDisplayRect(const QRect &rect)
+{
+ m_displayRect = rect;
+
+ setScaledDisplayRect();
+}
+
+Qt::AspectRatioMode S60VideoOverlay::aspectRatioMode() const
+{
+ return m_aspectRatioMode;
+}
+
+void S60VideoOverlay::setAspectRatioMode(Qt::AspectRatioMode ratio)
+{
+ m_aspectRatioMode = ratio;
+
+ setScaledDisplayRect();
+}
+
+QSize S60VideoOverlay::customAspectRatio() const
+{
+ return m_aspectRatio;
+}
+
+void S60VideoOverlay::setCustomAspectRatio(const QSize &customRatio)
+{
+ m_aspectRatio = customRatio;
+
+ setScaledDisplayRect();
+}
+
+void S60VideoOverlay::repaint()
+{
+}
+
+int S60VideoOverlay::brightness() const
+{
+ return m_surface->brightness();
+}
+
+void S60VideoOverlay::setBrightness(int brightness)
+{
+ m_surface->setBrightness(brightness);
+
+ emit brightnessChanged(m_surface->brightness());
+}
+
+int S60VideoOverlay::contrast() const
+{
+ return m_surface->contrast();
+}
+
+void S60VideoOverlay::setContrast(int contrast)
+{
+ m_surface->setContrast(contrast);
+
+ emit contrastChanged(m_surface->contrast());
+}
+
+int S60VideoOverlay::hue() const
+{
+ return m_surface->hue();
+}
+
+void S60VideoOverlay::setHue(int hue)
+{
+ m_surface->setHue(hue);
+
+ emit hueChanged(m_surface->hue());
+}
+
+int S60VideoOverlay::saturation() const
+{
+ return m_surface->saturation();
+}
+
+void S60VideoOverlay::setSaturation(int saturation)
+{
+ m_surface->setSaturation(saturation);
+
+ emit saturationChanged(m_surface->saturation());
+}
+
+bool S60VideoOverlay::isFullScreen() const
+{
+ return m_fullScreen;
+}
+
+void S60VideoOverlay::setFullScreen(bool fullScreen)
+{
+ emit fullScreenChanged(m_fullScreen = fullScreen);
+}
+
+QSize S60VideoOverlay::nativeSize() const
+{
+ return m_surface->surfaceFormat().sizeHint();
+}
+
+QAbstractVideoSurface *S60VideoOverlay::surface() const
+{
+ return m_surface;
+}
+
+void S60VideoOverlay::surfaceFormatChanged()
+{
+ setScaledDisplayRect();
+
+ emit nativeSizeChanged();
+}
+
+void S60VideoOverlay::setScaledDisplayRect()
+{
+ switch (m_aspectRatioMode) {
+ case Qt::KeepAspectRatio:
+ {
+ QSize size = m_surface->surfaceFormat().viewport().size();
+
+ size.scale(m_displayRect.size(), Qt::KeepAspectRatio);
+
+ QRect rect(QPoint(0, 0), size);
+ rect.moveCenter(m_displayRect.center());
+
+ m_surface->setDisplayRect(rect);
+ }
+ break;
+ case Qt::IgnoreAspectRatio:
+ m_surface->setDisplayRect(m_displayRect);
+ break;
+ };
+}
+
+QT_END_NAMESPACE
diff --git a/src/plugins/mediaservices/symbian/mediaplayer/s60videooverlay.h b/src/plugins/mediaservices/symbian/mediaplayer/s60videooverlay.h
new file mode 100644
index 0000000..d846f32
--- /dev/null
+++ b/src/plugins/mediaservices/symbian/mediaplayer/s60videooverlay.h
@@ -0,0 +1,109 @@
+/****************************************************************************
+**
+** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies).
+** All rights reserved.
+** Contact: Nokia Corporation (qt-info@nokia.com)
+**
+** This file is part of the plugins of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** No Commercial Usage
+** This file contains pre-release code and may not be distributed.
+** You may use this file in accordance with the terms and conditions
+** contained in the Technology Preview License Agreement accompanying
+** this package.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 2.1 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 2.1 requirements
+** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+**
+** In addition, as a special exception, Nokia gives you certain additional
+** rights. These rights are described in the Nokia Qt LGPL Exception
+** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+**
+** If you have questions regarding the use of this file, please contact
+** Nokia at qt-info@nokia.com.
+**
+**
+**
+**
+**
+**
+**
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#ifndef S60VIDEOOVERLAY_H
+#define S60VIDEOOVERLAY_H
+
+#include <QtCore/qobject.h>
+#include <qvideowindowcontrol.h>
+
+QT_BEGIN_NAMESPACE
+
+class QAbstractVideoSurface;
+class S60VideoSurface;
+
+class S60VideoOverlay : public QVideoWindowControl
+{
+ Q_OBJECT
+
+public:
+ S60VideoOverlay(QObject *parent = 0);
+ ~S60VideoOverlay();
+
+ WId winId() const;
+ void setWinId(WId id);
+
+ QRect displayRect() const;
+ void setDisplayRect(const QRect &rect);
+
+ bool isFullScreen() const;
+ void setFullScreen(bool fullScreen);
+
+ QSize nativeSize() const;
+
+ Qt::AspectRatioMode aspectRatioMode() const;
+ void setAspectRatioMode(Qt::AspectRatioMode mode);
+
+ QSize customAspectRatio() const;
+ void setCustomAspectRatio(const QSize &customRatio);
+
+ void repaint();
+
+ int brightness() const;
+ void setBrightness(int brightness);
+
+ int contrast() const;
+ void setContrast(int contrast);
+
+ int hue() const;
+ void setHue(int hue);
+
+ int saturation() const;
+ void setSaturation(int saturation);
+
+ QAbstractVideoSurface *surface() const;
+
+private slots:
+ void surfaceFormatChanged();
+
+private:
+ void setScaledDisplayRect();
+
+ S60VideoSurface *m_surface;
+ Qt::AspectRatioMode m_aspectRatioMode;
+ QRect m_displayRect;
+ QSize m_aspectRatio;
+ bool m_fullScreen;
+};
+
+QT_END_NAMESPACE
+
+#endif // S60VIDEOOVERLAY_H
diff --git a/src/plugins/mediaservices/symbian/mediaplayer/s60videoplayersession.cpp b/src/plugins/mediaservices/symbian/mediaplayer/s60videoplayersession.cpp
new file mode 100644
index 0000000..134d5a0
--- /dev/null
+++ b/src/plugins/mediaservices/symbian/mediaplayer/s60videoplayersession.cpp
@@ -0,0 +1,486 @@
+/****************************************************************************
+**
+** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies).
+** All rights reserved.
+** Contact: Nokia Corporation (qt-info@nokia.com)
+**
+** This file is part of the plugins of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** No Commercial Usage
+** This file contains pre-release code and may not be distributed.
+** You may use this file in accordance with the terms and conditions
+** contained in the Technology Preview License Agreement accompanying
+** this package.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 2.1 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 2.1 requirements
+** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+**
+** In addition, as a special exception, Nokia gives you certain additional
+** rights. These rights are described in the Nokia Qt LGPL Exception
+** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+**
+** If you have questions regarding the use of this file, please contact
+** Nokia at qt-info@nokia.com.
+**
+**
+**
+**
+**
+**
+**
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#include "s60videoplayersession.h"
+#include "s60videowidget.h"
+#include "s60mediaplayerservice.h"
+#include "s60videooverlay.h"
+
+#include <QtCore/qdebug.h>
+#include <QtGui/qwidget.h>
+#include <QtCore/qtimer.h>
+#include <QApplication>
+
+#include <coecntrl.h>
+#include <coemain.h> // For CCoeEnv
+#include <w32std.h>
+#include <mmf/common/mmfcontrollerframeworkbase.h>
+
+#include <AudioOutput.h>
+#include <MAudioOutputObserver.h>
+
+QT_BEGIN_NAMESPACE
+
+S60VideoPlayerSession::S60VideoPlayerSession(QMediaService *service)
+ : S60MediaPlayerSession(service)
+ , m_player(0)
+ , m_rect(0, 0, 0, 0)
+ , m_output(QVideoOutputControl::NoOutput)
+ , m_windowId(0)
+ , m_dsaActive(false)
+ , m_dsaStopped(false)
+ , m_wsSession(CCoeEnv::Static()->WsSession())
+ , m_screenDevice(*CCoeEnv::Static()->ScreenDevice())
+ , m_window(0)
+ , m_service(*service)
+ , m_aspectRatioMode(Qt::KeepAspectRatio)
+ , m_originalSize(1, 1)
+ , m_audioOutput(0)
+ , m_audioEndpoint("Default")
+{
+ resetNativeHandles();
+ QT_TRAP_THROWING(m_player = CVideoPlayerUtility::NewL(
+ *this,
+ 0,
+ EMdaPriorityPreferenceNone,
+ m_wsSession,
+ m_screenDevice,
+ *m_window,
+ m_rect,
+ m_rect));
+ m_dsaActive = true;
+ m_player->RegisterForVideoLoadingNotification(*this);
+}
+
+S60VideoPlayerSession::~S60VideoPlayerSession()
+{
+#if !defined(HAS_NO_AUDIOROUTING_IN_VIDEOPLAYER)
+ if (m_audioOutput)
+ m_audioOutput->UnregisterObserver(*this);
+ delete m_audioOutput;
+#endif
+ m_player->Close();
+ delete m_player;
+}
+
+void S60VideoPlayerSession::doLoadL(const TDesC &path)
+{
+ // m_audioOutput needs to be reinitialized after MapcInitComplete
+ if (m_audioOutput)
+ m_audioOutput->UnregisterObserver(*this);
+ delete m_audioOutput;
+ m_audioOutput = NULL;
+
+ m_player->OpenFileL(path);
+}
+
+void S60VideoPlayerSession::doLoadUrlL(const TDesC &path)
+{
+ // m_audioOutput needs to be reinitialized after MapcInitComplete
+ if (m_audioOutput)
+ m_audioOutput->UnregisterObserver(*this);
+ delete m_audioOutput;
+ m_audioOutput = NULL;
+
+ m_player->OpenUrlL(path);
+}
+
+int S60VideoPlayerSession::doGetBufferStatusL() const
+{
+ int progress = 0;
+ m_player->GetVideoLoadingProgressL(progress);
+ return progress;
+}
+
+qint64 S60VideoPlayerSession::doGetDurationL() const
+{
+ return m_player->DurationL().Int64() / qint64(1000);
+}
+
+void S60VideoPlayerSession::setVideoRenderer(QObject *videoOutput)
+{
+ Q_UNUSED(videoOutput)
+ QVideoOutputControl *videoControl = qobject_cast<QVideoOutputControl *>(m_service.control(QVideoOutputControl_iid));
+
+ //Render changes
+ if (m_output != videoControl->output()) {
+
+ if (m_output == QVideoOutputControl::WidgetOutput) {
+ S60VideoWidgetControl *widgetControl = qobject_cast<S60VideoWidgetControl *>(m_service.control(QVideoWidgetControl_iid));
+ disconnect(widgetControl, SIGNAL(widgetUpdated()), this, SLOT(resetVideoDisplay()));
+ disconnect(widgetControl, SIGNAL(beginVideoWindowNativePaint()), this, SLOT(suspendDirectScreenAccess()));
+ disconnect(widgetControl, SIGNAL(endVideoWindowNativePaint()), this, SLOT(resumeDirectScreenAccess()));
+ disconnect(this, SIGNAL(stateChanged(QMediaPlayer::State)), widgetControl, SLOT(videoStateChanged(QMediaPlayer::State)));
+ }
+
+ if (videoControl->output() == QVideoOutputControl::WidgetOutput) {
+ S60VideoWidgetControl *widgetControl = qobject_cast<S60VideoWidgetControl *>(m_service.control(QVideoWidgetControl_iid));
+ connect(widgetControl, SIGNAL(widgetUpdated()), this, SLOT(resetVideoDisplay()));
+ connect(widgetControl, SIGNAL(beginVideoWindowNativePaint()), this, SLOT(suspendDirectScreenAccess()));
+ connect(widgetControl, SIGNAL(endVideoWindowNativePaint()), this, SLOT(resumeDirectScreenAccess()));
+ connect(this, SIGNAL(stateChanged(QMediaPlayer::State)), widgetControl, SLOT(videoStateChanged(QMediaPlayer::State)));
+ }
+
+ m_output = videoControl->output();
+ resetVideoDisplay();
+ }
+}
+
+bool S60VideoPlayerSession::resetNativeHandles()
+{
+ QVideoOutputControl* videoControl = qobject_cast<QVideoOutputControl *>(m_service.control(QVideoOutputControl_iid));
+ WId newId = 0;
+ TRect newRect = TRect(0,0,0,0);
+ Qt::AspectRatioMode aspectRatioMode = Qt::KeepAspectRatio;
+
+ if (videoControl->output() == QVideoOutputControl::WidgetOutput) {
+ S60VideoWidgetControl* widgetControl = qobject_cast<S60VideoWidgetControl *>(m_service.control(QVideoWidgetControl_iid));
+ QWidget *videoWidget = widgetControl->videoWidget();
+ newId = widgetControl->videoWidgetWId();
+ newRect = QRect2TRect(QRect(videoWidget->mapToGlobal(videoWidget->pos()), videoWidget->size()));
+ aspectRatioMode = widgetControl->aspectRatioMode();
+ } else if (videoControl->output() == QVideoOutputControl::WindowOutput) {
+ S60VideoOverlay* windowControl = qobject_cast<S60VideoOverlay *>(m_service.control(QVideoWindowControl_iid));
+ newId = windowControl->winId();
+ newRect = TRect( newId->DrawableWindow()->AbsPosition(), newId->DrawableWindow()->Size());
+ } else {
+ if (QApplication::activeWindow())
+ newId = QApplication::activeWindow()->effectiveWinId();
+
+ if (!newId && QApplication::allWidgets().count())
+ newId = QApplication::allWidgets().at(0)->effectiveWinId();
+
+ Q_ASSERT(newId != 0);
+ }
+
+ if (newRect == m_rect && newId == m_windowId && aspectRatioMode == m_aspectRatioMode)
+ return false;
+
+ if (newId) {
+ m_rect = newRect;
+ m_windowId = newId;
+ m_window = m_windowId->DrawableWindow();
+ m_aspectRatioMode = aspectRatioMode;
+ return true;
+ }
+ return false;
+}
+
+bool S60VideoPlayerSession::isVideoAvailable() const
+{
+#ifdef PRE_S60_50_PLATFORM
+ return true; // this is not support in pre 5th platforms
+#else
+ if (m_player)
+ return m_player->VideoEnabledL();
+ else
+ return false;
+#endif
+}
+
+bool S60VideoPlayerSession::isAudioAvailable() const
+{
+ if (m_player)
+ return m_player->AudioEnabledL();
+ else
+ return false;
+}
+
+void S60VideoPlayerSession::doPlay()
+{
+ m_player->Play();
+}
+
+void S60VideoPlayerSession::doPauseL()
+{
+ m_player->PauseL();
+}
+
+void S60VideoPlayerSession::doStop()
+{
+ m_player->Stop();
+}
+
+qint64 S60VideoPlayerSession::doGetPositionL() const
+{
+ return m_player->PositionL().Int64() / qint64(1000);
+}
+
+void S60VideoPlayerSession::doSetPositionL(qint64 microSeconds)
+{
+ m_player->SetPositionL(TTimeIntervalMicroSeconds(microSeconds));
+}
+
+void S60VideoPlayerSession::doSetVolumeL(int volume)
+{
+ m_player->SetVolumeL((volume / 100.0)* m_player->MaxVolume());
+}
+
+QPair<qreal, qreal> S60VideoPlayerSession::scaleFactor()
+{
+ QSize scaled = m_originalSize;
+ if (m_aspectRatioMode == Qt::IgnoreAspectRatio)
+ scaled.scale(TRect2QRect(m_rect).size(), Qt::IgnoreAspectRatio);
+ else if(m_aspectRatioMode == Qt::KeepAspectRatio)
+ scaled.scale(TRect2QRect(m_rect).size(), Qt::KeepAspectRatio);
+
+ qreal width = qreal(scaled.width()) / qreal(m_originalSize.width()) * qreal(100);
+ qreal height = qreal(scaled.height()) / qreal(m_originalSize.height()) * qreal(100);
+
+ return QPair<qreal, qreal>(width, height);
+}
+
+void S60VideoPlayerSession::startDirectScreenAccess()
+{
+ if(m_dsaActive)
+ return;
+
+ TRAPD(err, m_player->StartDirectScreenAccessL());
+ if(err == KErrNone)
+ m_dsaActive = true;
+ setError(err);
+}
+
+bool S60VideoPlayerSession::stopDirectScreenAccess()
+{
+ if(!m_dsaActive)
+ return false;
+
+ TRAPD(err, m_player->StopDirectScreenAccessL());
+ if(err == KErrNone)
+ m_dsaActive = false;
+
+ setError(err);
+ return true;
+}
+
+void S60VideoPlayerSession::MvpuoOpenComplete(TInt aError)
+{
+ setError(aError);
+ m_player->Prepare();
+}
+
+void S60VideoPlayerSession::MvpuoPrepareComplete(TInt aError)
+{
+ setError(aError);
+ TRAPD(err,
+ m_player->SetDisplayWindowL(m_wsSession,
+ m_screenDevice,
+ *m_window,
+ m_rect,
+ m_rect);
+ TSize originalSize;
+ m_player->VideoFrameSizeL(originalSize);
+ m_originalSize = QSize(originalSize.iWidth, originalSize.iHeight);
+ m_player->SetScaleFactorL(scaleFactor().first, scaleFactor().second, true));
+
+ setError(err);
+ m_dsaActive = true;
+#if !defined(HAS_NO_AUDIOROUTING_IN_VIDEOPLAYER)
+ TRAP(err,
+ m_audioOutput = CAudioOutput::NewL(*m_player);
+ m_audioOutput->RegisterObserverL(*this);
+ );
+ setActiveEndpoint(m_audioEndpoint);
+ setError(err);
+#endif
+ loaded();
+}
+
+void S60VideoPlayerSession::MvpuoFrameReady(CFbsBitmap &aFrame, TInt aError)
+{
+ Q_UNUSED(aFrame);
+ Q_UNUSED(aError);
+}
+
+void S60VideoPlayerSession::MvpuoPlayComplete(TInt aError)
+{
+ setError(aError);
+ endOfMedia();
+}
+
+void S60VideoPlayerSession::MvpuoEvent(const TMMFEvent &aEvent)
+{
+ Q_UNUSED(aEvent);
+}
+
+void S60VideoPlayerSession::updateMetaDataEntriesL()
+{
+ metaDataEntries().clear();
+ int numberOfMetaDataEntries = 0;
+
+ numberOfMetaDataEntries = m_player->NumberOfMetaDataEntriesL();
+
+ for (int i = 0; i < numberOfMetaDataEntries; i++) {
+ CMMFMetaDataEntry *entry = NULL;
+ entry = m_player->MetaDataEntryL(i);
+ metaDataEntries().insert(TDesC2QString(entry->Name()), TDesC2QString(entry->Value()));
+ delete entry;
+ }
+ emit metaDataChanged();
+}
+
+void S60VideoPlayerSession::resetVideoDisplay()
+{
+ if (resetNativeHandles()) {
+ TRAPD(err,
+ m_player->SetDisplayWindowL(m_wsSession,
+ m_screenDevice,
+ *m_window,
+ m_rect,
+ m_rect));
+ setError(err);
+ if( mediaStatus() == QMediaPlayer::LoadedMedia
+ || mediaStatus() == QMediaPlayer::StalledMedia
+ || mediaStatus() == QMediaPlayer::BufferingMedia
+ || mediaStatus() == QMediaPlayer::BufferedMedia
+ || mediaStatus() == QMediaPlayer::EndOfMedia) {
+ TRAPD(err, m_player->SetScaleFactorL(scaleFactor().first, scaleFactor().second, true));
+ setError(err);
+ }
+ }
+}
+
+void S60VideoPlayerSession::suspendDirectScreenAccess()
+{
+ m_dsaStopped = stopDirectScreenAccess();
+}
+
+void S60VideoPlayerSession::resumeDirectScreenAccess()
+{
+ if(!m_dsaStopped)
+ return;
+
+ startDirectScreenAccess();
+ m_dsaStopped = false;
+}
+
+void S60VideoPlayerSession::MvloLoadingStarted()
+{
+ buffering();
+}
+
+void S60VideoPlayerSession::MvloLoadingComplete()
+{
+ buffered();
+}
+
+void S60VideoPlayerSession::doSetAudioEndpoint(const QString& audioEndpoint)
+{
+ m_audioEndpoint = audioEndpoint;
+}
+
+QString S60VideoPlayerSession::activeEndpoint() const
+{
+ QString outputName = QString("Default");
+#if !defined(HAS_NO_AUDIOROUTING_IN_VIDEOPLAYER)
+ if (m_audioOutput) {
+ CAudioOutput::TAudioOutputPreference output = m_audioOutput->AudioOutput();
+ outputName = qStringFromTAudioOutputPreference(output);
+ }
+#endif
+ return outputName;
+}
+
+QString S60VideoPlayerSession::defaultEndpoint() const
+{
+ QString outputName = QString("Default");
+#if !defined(HAS_NO_AUDIOROUTING_IN_VIDEOPLAYER)
+ if (m_audioOutput) {
+ CAudioOutput::TAudioOutputPreference output = m_audioOutput->DefaultAudioOutput();
+ outputName = qStringFromTAudioOutputPreference(output);
+ }
+#endif
+ return outputName;
+}
+
+void S60VideoPlayerSession::setActiveEndpoint(const QString& name)
+{
+ CAudioOutput::TAudioOutputPreference output = CAudioOutput::ENoPreference;
+
+ if (name == QString("Default"))
+ output = CAudioOutput::ENoPreference;
+ else if (name == QString("All"))
+ output = CAudioOutput::EAll;
+ else if (name == QString("None"))
+ output = CAudioOutput::ENoOutput;
+ else if (name == QString("Earphone"))
+ output = CAudioOutput::EPrivate;
+ else if (name == QString("Speaker"))
+ output = CAudioOutput::EPublic;
+#if !defined(HAS_NO_AUDIOROUTING_IN_VIDEOPLAYER)
+ if (m_audioOutput) {
+ TRAPD(err, m_audioOutput->SetAudioOutputL(output));
+ setError(err);
+
+ if (m_audioEndpoint != name) {
+ m_audioEndpoint = name;
+ emit activeEndpointChanged(name);
+ }
+ }
+#endif
+}
+
+void S60VideoPlayerSession::DefaultAudioOutputChanged( CAudioOutput& aAudioOutput,
+ CAudioOutput::TAudioOutputPreference aNewDefault )
+{
+ // Emit already implemented in setActiveEndpoint function
+ Q_UNUSED(aAudioOutput)
+ Q_UNUSED(aNewDefault)
+}
+
+QString S60VideoPlayerSession::qStringFromTAudioOutputPreference(CAudioOutput::TAudioOutputPreference output) const
+{
+ if (output == CAudioOutput::ENoPreference)
+ return QString("Default");
+ else if (output == CAudioOutput::EAll)
+ return QString("All");
+ else if (output == CAudioOutput::ENoOutput)
+ return QString("None");
+ else if (output == CAudioOutput::EPrivate)
+ return QString("Earphone");
+ else if (output == CAudioOutput::EPublic)
+ return QString("Speaker");
+ return QString("Default");
+}
+
+QT_END_NAMESPACE
+
diff --git a/src/plugins/mediaservices/symbian/mediaplayer/s60videoplayersession.h b/src/plugins/mediaservices/symbian/mediaplayer/s60videoplayersession.h
new file mode 100644
index 0000000..52e311a
--- /dev/null
+++ b/src/plugins/mediaservices/symbian/mediaplayer/s60videoplayersession.h
@@ -0,0 +1,148 @@
+/****************************************************************************
+**
+** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies).
+** All rights reserved.
+** Contact: Nokia Corporation (qt-info@nokia.com)
+**
+** This file is part of the plugins of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** No Commercial Usage
+** This file contains pre-release code and may not be distributed.
+** You may use this file in accordance with the terms and conditions
+** contained in the Technology Preview License Agreement accompanying
+** this package.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 2.1 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 2.1 requirements
+** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+**
+** In addition, as a special exception, Nokia gives you certain additional
+** rights. These rights are described in the Nokia Qt LGPL Exception
+** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+**
+** If you have questions regarding the use of this file, please contact
+** Nokia at qt-info@nokia.com.
+**
+**
+**
+**
+**
+**
+**
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#ifndef S60VIDEOPLAYERSESSION_H
+#define S60VIDEOPLAYERSESSION_H
+
+#include "s60mediaplayersession.h"
+#include "s60mediaplayeraudioendpointselector.h"
+#include <videoplayer.h>
+#include <QtGui/qwidget.h>
+#include <qvideowidget.h>
+
+#include <AudioOutput.h>
+#include <MAudioOutputObserver.h>
+
+QT_BEGIN_NAMESPACE
+
+class QTimer;
+
+class S60VideoPlayerSession : public S60MediaPlayerSession,
+ public MVideoPlayerUtilityObserver,
+ public MVideoLoadingObserver,
+ public MAudioOutputObserver
+{
+ Q_OBJECT
+
+public:
+ S60VideoPlayerSession(QMediaService *service);
+ ~S60VideoPlayerSession();
+
+ //From S60MediaPlayerSession
+ bool isVideoAvailable() const;
+ bool isAudioAvailable() const;
+ void setVideoRenderer(QObject *renderer);
+
+ //From MVideoLoadingObserver
+ void MvloLoadingStarted();
+ void MvloLoadingComplete();
+
+ // From MAudioOutputObserver
+ void DefaultAudioOutputChanged(CAudioOutput& aAudioOutput,
+ CAudioOutput::TAudioOutputPreference aNewDefault);
+
+public:
+ // From S60MediaPlayerAudioEndpointSelector
+ QString activeEndpoint() const;
+ QString defaultEndpoint() const;
+public Q_SLOTS:
+ void setActiveEndpoint(const QString& name);
+Q_SIGNALS:
+ void activeEndpointChanged(const QString &name);
+
+protected:
+ //From S60MediaPlayerSession
+ void doLoadL(const TDesC &path);
+ void doLoadUrlL(const TDesC &path);
+ void doPlay();
+ void doStop();
+ void doPauseL();
+ void doSetVolumeL(int volume);
+ qint64 doGetPositionL() const;
+ void doSetPositionL(qint64 microSeconds);
+ void updateMetaDataEntriesL();
+ int doGetBufferStatusL() const;
+ qint64 doGetDurationL() const;
+ void doSetAudioEndpoint(const QString& audioEndpoint);
+
+private slots:
+ void resetVideoDisplay();
+ void suspendDirectScreenAccess();
+ void resumeDirectScreenAccess();
+
+private:
+ bool resetNativeHandles();
+ QPair<qreal, qreal> scaleFactor();
+ void startDirectScreenAccess();
+ bool stopDirectScreenAccess();
+ QString qStringFromTAudioOutputPreference(CAudioOutput::TAudioOutputPreference output) const;
+
+
+ // From MVideoPlayerUtilityObserver
+ void MvpuoOpenComplete(TInt aError);
+ void MvpuoPrepareComplete(TInt aError);
+ void MvpuoFrameReady(CFbsBitmap &aFrame, TInt aError);
+ void MvpuoPlayComplete(TInt aError);
+ void MvpuoEvent(const TMMFEvent &aEvent);
+
+private:
+ // Qwn
+ CVideoPlayerUtility *m_player;
+ TRect m_rect;
+ QVideoOutputControl::Output m_output;
+ WId m_windowId;
+ bool m_dsaActive;
+ bool m_dsaStopped;
+
+ //Reference
+ RWsSession &m_wsSession;
+ CWsScreenDevice &m_screenDevice;
+ RWindowBase *m_window;
+ QMediaService &m_service;
+ Qt::AspectRatioMode m_aspectRatioMode;
+ QSize m_originalSize;
+ CAudioOutput *m_audioOutput;
+ QString m_audioEndpoint;
+};
+
+QT_END_NAMESPACE
+
+#endif
diff --git a/src/plugins/mediaservices/symbian/mediaplayer/s60videorenderer.cpp b/src/plugins/mediaservices/symbian/mediaplayer/s60videorenderer.cpp
new file mode 100644
index 0000000..269dd43
--- /dev/null
+++ b/src/plugins/mediaservices/symbian/mediaplayer/s60videorenderer.cpp
@@ -0,0 +1,69 @@
+/****************************************************************************
+**
+** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies).
+** All rights reserved.
+** Contact: Nokia Corporation (qt-info@nokia.com)
+**
+** This file is part of the plugins of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** No Commercial Usage
+** This file contains pre-release code and may not be distributed.
+** You may use this file in accordance with the terms and conditions
+** contained in the Technology Preview License Agreement accompanying
+** this package.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 2.1 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 2.1 requirements
+** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+**
+** In addition, as a special exception, Nokia gives you certain additional
+** rights. These rights are described in the Nokia Qt LGPL Exception
+** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+**
+** If you have questions regarding the use of this file, please contact
+** Nokia at qt-info@nokia.com.
+**
+**
+**
+**
+**
+**
+**
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#include "s60videorenderer.h"
+
+#include <QtCore/qcoreevent.h>
+#include <QtGui/qapplication.h>
+
+QT_BEGIN_NAMESPACE
+
+S60VideoRenderer::S60VideoRenderer(QObject *parent)
+ : QVideoRendererControl(parent)
+{
+}
+
+S60VideoRenderer::~S60VideoRenderer()
+{
+}
+
+
+QAbstractVideoSurface *S60VideoRenderer::surface() const
+{
+ return m_surface;
+}
+
+void S60VideoRenderer::setSurface(QAbstractVideoSurface *surface)
+{
+ m_surface = surface;
+}
+
+QT_END_NAMESPACE
diff --git a/src/plugins/mediaservices/symbian/mediaplayer/s60videorenderer.h b/src/plugins/mediaservices/symbian/mediaplayer/s60videorenderer.h
new file mode 100644
index 0000000..260dc8b
--- /dev/null
+++ b/src/plugins/mediaservices/symbian/mediaplayer/s60videorenderer.h
@@ -0,0 +1,68 @@
+/****************************************************************************
+**
+** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies).
+** All rights reserved.
+** Contact: Nokia Corporation (qt-info@nokia.com)
+**
+** This file is part of the plugins of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** No Commercial Usage
+** This file contains pre-release code and may not be distributed.
+** You may use this file in accordance with the terms and conditions
+** contained in the Technology Preview License Agreement accompanying
+** this package.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 2.1 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 2.1 requirements
+** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+**
+** In addition, as a special exception, Nokia gives you certain additional
+** rights. These rights are described in the Nokia Qt LGPL Exception
+** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+**
+** If you have questions regarding the use of this file, please contact
+** Nokia at qt-info@nokia.com.
+**
+**
+**
+**
+**
+**
+**
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#ifndef S60VIDEORENDERER_H
+#define S60VIDEORENDERER_H
+
+#include <QtCore/qobject.h>
+#include <qvideorenderercontrol.h>
+
+QT_BEGIN_NAMESPACE
+
+class S60VideoRenderer : public QVideoRendererControl
+{
+ Q_OBJECT
+
+public:
+ S60VideoRenderer(QObject *parent = 0);
+ virtual ~S60VideoRenderer();
+
+ QAbstractVideoSurface *surface() const;
+ void setSurface(QAbstractVideoSurface *surface);
+
+private:
+
+ QAbstractVideoSurface *m_surface;
+};
+
+QT_END_NAMESPACE
+
+#endif // S60VIDEORENDERER_H
diff --git a/src/plugins/mediaservices/symbian/mediaplayer/s60videosurface.cpp b/src/plugins/mediaservices/symbian/mediaplayer/s60videosurface.cpp
new file mode 100644
index 0000000..bfa7a13
--- /dev/null
+++ b/src/plugins/mediaservices/symbian/mediaplayer/s60videosurface.cpp
@@ -0,0 +1,478 @@
+/****************************************************************************
+**
+** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies).
+** All rights reserved.
+** Contact: Nokia Corporation (qt-info@nokia.com)
+**
+** This file is part of the plugins of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** No Commercial Usage
+** This file contains pre-release code and may not be distributed.
+** You may use this file in accordance with the terms and conditions
+** contained in the Technology Preview License Agreement accompanying
+** this package.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 2.1 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 2.1 requirements
+** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+**
+** In addition, as a special exception, Nokia gives you certain additional
+** rights. These rights are described in the Nokia Qt LGPL Exception
+** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+**
+** If you have questions regarding the use of this file, please contact
+** Nokia at qt-info@nokia.com.
+**
+**
+**
+**
+**
+**
+**
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+//#include <QtGui/qx11info_x11.h>
+
+#include "s60videosurface.h"
+
+QT_BEGIN_NAMESPACE
+
+/*struct XvFormatRgb
+{
+ QVideoFrame::PixelFormat pixelFormat;
+ int bits_per_pixel;
+ int format;
+ int num_planes;
+
+ int depth;
+ unsigned int red_mask;
+ unsigned int green_mask;
+ unsigned int blue_mask;
+
+};*/
+/*
+bool operator ==(const XvImageFormatValues &format, const XvFormatRgb &rgb)
+{
+ return format.type == XvRGB
+ && format.bits_per_pixel == rgb.bits_per_pixel
+ && format.format == rgb.format
+ && format.num_planes == rgb.num_planes
+ && format.depth == rgb.depth
+ && format.red_mask == rgb.red_mask
+ && format.blue_mask == rgb.blue_mask;
+}
+
+static const XvFormatRgb qt_xvRgbLookup[] =
+{
+ { QVideoFrame::Format_ARGB32, 32, XvPacked, 1, 32, 0x00FF0000, 0x0000FF00, 0x000000FF },
+ { QVideoFrame::Format_RGB32 , 32, XvPacked, 1, 24, 0x00FF0000, 0x0000FF00, 0x000000FF },
+ { QVideoFrame::Format_RGB24 , 24, XvPacked, 1, 24, 0x00FF0000, 0x0000FF00, 0x000000FF },
+ { QVideoFrame::Format_RGB565, 16, XvPacked, 1, 16, 0x0000F800, 0x000007E0, 0x0000001F },
+ { QVideoFrame::Format_BGRA32, 32, XvPacked, 1, 32, 0xFF000000, 0x00FF0000, 0x0000FF00 },
+ { QVideoFrame::Format_BGR32 , 32, XvPacked, 1, 24, 0x00FF0000, 0x0000FF00, 0x000000FF },
+ { QVideoFrame::Format_BGR24 , 24, XvPacked, 1, 24, 0x00FF0000, 0x0000FF00, 0x000000FF },
+ { QVideoFrame::Format_BGR565, 16, XvPacked, 1, 16, 0x0000F800, 0x000007E0, 0x0000001F }
+};
+
+struct XvFormatYuv
+{
+ QVideoFrame::PixelFormat pixelFormat;
+ int bits_per_pixel;
+ int format;
+ int num_planes;
+
+ unsigned int y_sample_bits;
+ unsigned int u_sample_bits;
+ unsigned int v_sample_bits;
+ unsigned int horz_y_period;
+ unsigned int horz_u_period;
+ unsigned int horz_v_period;
+ unsigned int vert_y_period;
+ unsigned int vert_u_period;
+ unsigned int vert_v_period;
+ char component_order[32];
+};
+
+bool operator ==(const XvImageFormatValues &format, const XvFormatYuv &yuv)
+{
+ return format.type == XvYUV
+ && format.bits_per_pixel == yuv.bits_per_pixel
+ && format.format == yuv.format
+ && format.num_planes == yuv.num_planes
+ && format.y_sample_bits == yuv.y_sample_bits
+ && format.u_sample_bits == yuv.u_sample_bits
+ && format.v_sample_bits == yuv.v_sample_bits
+ && format.horz_y_period == yuv.horz_y_period
+ && format.horz_u_period == yuv.horz_u_period
+ && format.horz_v_period == yuv.horz_v_period
+ && format.horz_y_period == yuv.vert_y_period
+ && format.vert_u_period == yuv.vert_u_period
+ && format.vert_v_period == yuv.vert_v_period
+ && qstrncmp(format.component_order, yuv.component_order, 32) == 0;
+}
+
+static const XvFormatYuv qt_xvYuvLookup[] =
+{
+ { QVideoFrame::Format_YUV444 , 24, XvPacked, 1, 8, 8, 8, 1, 1, 1, 1, 1, 1, "YUV" },
+ { QVideoFrame::Format_YUV420P, 12, XvPlanar, 3, 8, 8, 8, 1, 2, 2, 1, 2, 2, "YUV" },
+ { QVideoFrame::Format_YV12 , 12, XvPlanar, 3, 8, 8, 8, 1, 2, 2, 1, 2, 2, "YVU" },
+ { QVideoFrame::Format_UYVY , 16, XvPacked, 1, 8, 8, 8, 1, 2, 2, 1, 1, 1, "UYVY" },
+ { QVideoFrame::Format_YUYV , 16, XvPacked, 1, 8, 8, 8, 1, 2, 2, 1, 1, 1, "YUYV" },
+ { QVideoFrame::Format_NV12 , 12, XvPlanar, 2, 8, 8, 8, 1, 2, 2, 1, 2, 2, "YUV" },
+ { QVideoFrame::Format_NV12 , 12, XvPlanar, 2, 8, 8, 8, 1, 2, 2, 1, 2, 2, "YVU" },
+ { QVideoFrame::Format_Y8 , 8 , XvPlanar, 1, 8, 0, 0, 1, 0, 0, 1, 0, 0, "Y" }
+};
+*/
+
+S60VideoSurface::S60VideoSurface(QObject *parent)
+ : QAbstractVideoSurface(parent)
+ , m_winId(0)
+ //, m_portId(0)
+ //, m_gc(0)
+ //, m_image(0)
+{
+}
+
+S60VideoSurface::~S60VideoSurface()
+{
+ /*if (m_gc)
+ XFreeGC(QX11Info::display(), m_gc);
+
+ if (m_portId != 0)
+ XvUngrabPort(QX11Info::display(), m_portId, 0);
+ */
+}
+
+WId S60VideoSurface::winId() const
+{
+ return m_winId;
+}
+
+void S60VideoSurface::setWinId(WId id)
+{
+ /*if (id == m_winId)
+ return;
+
+ if (m_image)
+ XFree(m_image);
+
+ if (m_gc) {
+ XFreeGC(QX11Info::display(), m_gc);
+ m_gc = 0;
+ }
+
+ if (m_portId != 0)
+ XvUngrabPort(QX11Info::display(), m_portId, 0);
+
+ m_supportedPixelFormats.clear();
+ m_formatIds.clear();
+
+ m_winId = id;
+
+ if (m_winId && findPort()) {
+ querySupportedFormats();
+
+ m_gc = XCreateGC(QX11Info::display(), m_winId, 0, 0);
+
+ if (m_image) {
+ m_image = 0;
+
+ if (!start(surfaceFormat()))
+ QAbstractVideoSurface::stop();
+ }
+ } else if (m_image) {
+ m_image = 0;
+
+ QAbstractVideoSurface::stop();
+ }*/
+}
+
+QRect S60VideoSurface::displayRect() const
+{
+ return m_displayRect;
+}
+
+void S60VideoSurface::setDisplayRect(const QRect &rect)
+{
+ m_displayRect = rect;
+}
+
+int S60VideoSurface::brightness() const
+{
+ //return getAttribute("XV_BRIGHTNESS", m_brightnessRange.first, m_brightnessRange.second);
+}
+
+void S60VideoSurface::setBrightness(int brightness)
+{
+ //setAttribute("XV_BRIGHTNESS", brightness, m_brightnessRange.first, m_brightnessRange.second);
+}
+
+int S60VideoSurface::contrast() const
+{
+ //return getAttribute("XV_CONTRAST", m_contrastRange.first, m_contrastRange.second);
+}
+
+void S60VideoSurface::setContrast(int contrast)
+{
+ //setAttribute("XV_CONTRAST", contrast, m_contrastRange.first, m_contrastRange.second);
+}
+
+int S60VideoSurface::hue() const
+{
+ //return getAttribute("XV_HUE", m_hueRange.first, m_hueRange.second);
+}
+
+void S60VideoSurface::setHue(int hue)
+{
+ // setAttribute("XV_HUE", hue, m_hueRange.first, m_hueRange.second);
+}
+
+int S60VideoSurface::saturation() const
+{
+ //return getAttribute("XV_SATURATION", m_saturationRange.first, m_saturationRange.second);
+}
+
+void S60VideoSurface::setSaturation(int saturation)
+{
+ //setAttribute("XV_SATURATION", saturation, m_saturationRange.first, m_saturationRange.second);
+}
+
+int S60VideoSurface::getAttribute(const char *attribute, int minimum, int maximum) const
+{
+ /*if (m_portId != 0) {
+ Display *display = QX11Info::display();
+
+ Atom atom = XInternAtom(display, attribute, True);
+
+ int value = 0;
+
+ XvGetPortAttribute(display, m_portId, atom, &value);
+
+ return redistribute(value, minimum, maximum, -100, 100);
+ } else {
+ return 0;
+ }*/
+}
+
+void S60VideoSurface::setAttribute(const char *attribute, int value, int minimum, int maximum)
+{
+ /* if (m_portId != 0) {
+ Display *display = QX11Info::display();
+
+ Atom atom = XInternAtom(display, attribute, True);
+
+ XvSetPortAttribute(
+ display, m_portId, atom, redistribute(value, -100, 100, minimum, maximum));
+ }*/
+}
+
+int S60VideoSurface::redistribute(
+ int value, int fromLower, int fromUpper, int toLower, int toUpper)
+{
+ /*return fromUpper != fromLower
+ ? ((value - fromLower) * (toUpper - toLower) / (fromUpper - fromLower)) + toLower
+ : 0;*/
+}
+
+QList<QVideoFrame::PixelFormat> S60VideoSurface::supportedPixelFormats(
+ QAbstractVideoBuffer::HandleType handleType) const
+{
+ /*return handleType == QAbstractVideoBuffer::NoHandle
+ ? m_supportedPixelFormats
+ : QList<QVideoFrame::PixelFormat>();*/
+}
+
+bool S60VideoSurface::start(const QVideoSurfaceFormat &format)
+{
+ /*if (m_image)
+ XFree(m_image);
+
+ int xvFormatId = 0;
+ for (int i = 0; i < m_supportedPixelFormats.count(); ++i) {
+ if (m_supportedPixelFormats.at(i) == format.pixelFormat()) {
+ xvFormatId = m_formatIds.at(i);
+ break;
+ }
+ }
+
+ if (xvFormatId == 0) {
+ setError(UnsupportedFormatError);
+ } else {
+ XvImage *image = XvCreateImage(
+ QX11Info::display(),
+ m_portId,
+ xvFormatId,
+ 0,
+ format.frameWidth(),
+ format.frameHeight());
+
+ if (!image) {
+ setError(ResourceError);
+ } else {
+ m_viewport = format.viewport();
+ m_image = image;
+
+ return QAbstractVideoSurface::start(format);
+ }
+ }
+
+ if (m_image) {
+ m_image = 0;
+
+ QAbstractVideoSurface::stop();
+ }
+*/
+ return false;
+}
+
+void S60VideoSurface::stop()
+{/*
+ if (m_image) {
+ XFree(m_image);
+ m_image = 0;
+
+ QAbstractVideoSurface::stop();
+ }*/
+}
+
+bool S60VideoSurface::present(const QVideoFrame &frame)
+{/*
+ if (!m_image) {
+ setError(StoppedError);
+ return false;
+ } else if (m_image->width != frame.width() || m_image->height != frame.height()) {
+ setError(IncorrectFormatError);
+ return false;
+ } else {
+ QVideoFrame frameCopy(frame);
+
+ if (!frameCopy.map(QAbstractVideoBuffer::ReadOnly)) {
+ setError(IncorrectFormatError);
+ return false;
+ } else {
+ bool presented = false;
+
+ if (m_image->data_size > frame.numBytes()) {
+ qWarning("Insufficient frame buffer size");
+ setError(IncorrectFormatError);
+ } else if (m_image->num_planes > 0 && m_image->pitches[0] != frame.bytesPerLine()) {
+ qWarning("Incompatible frame pitches");
+ setError(IncorrectFormatError);
+ } else {
+ m_image->data = reinterpret_cast<char *>(frameCopy.bits());
+
+ XvPutImage(
+ QX11Info::display(),
+ m_portId,
+ m_winId,
+ m_gc,
+ m_image,
+ m_viewport.x(),
+ m_viewport.y(),
+ m_viewport.width(),
+ m_viewport.height(),
+ m_displayRect.x(),
+ m_displayRect.y(),
+ m_displayRect.width(),
+ m_displayRect.height());
+
+ m_image->data = 0;
+
+ presented = true;
+ }
+
+ frameCopy.unmap();
+
+ return presented;
+ }
+ }*/
+}
+
+bool S60VideoSurface::findPort()
+{/*
+ unsigned int count = 0;
+ XvAdaptorInfo *adaptors = 0;
+ bool portFound = false;
+
+ if (XvQueryAdaptors(QX11Info::display(), m_winId, &count, &adaptors) == Success) {
+ for (unsigned int i = 0; i < count && !portFound; ++i) {
+ if (adaptors[i].type & XvImageMask) {
+ m_portId = adaptors[i].base_id;
+
+ for (unsigned int j = 0; j < adaptors[i].num_ports && !portFound; ++j, ++m_portId)
+ portFound = XvGrabPort(QX11Info::display(), m_portId, 0) == Success;
+ }
+ }
+ XvFreeAdaptorInfo(adaptors);
+ }
+
+ return portFound;*/
+}
+
+void S60VideoSurface::querySupportedFormats()
+{/*
+ int count = 0;
+ if (XvImageFormatValues *imageFormats = XvListImageFormats(
+ QX11Info::display(), m_portId, &count)) {
+ const int rgbCount = sizeof(qt_xvRgbLookup) / sizeof(XvFormatRgb);
+ const int yuvCount = sizeof(qt_xvYuvLookup) / sizeof(XvFormatYuv);
+
+ for (int i = 0; i < count; ++i) {
+ switch (imageFormats[i].type) {
+ case XvRGB:
+ for (int j = 0; j < rgbCount; ++j) {
+ if (imageFormats[i] == qt_xvRgbLookup[j]) {
+ m_supportedPixelFormats.append(qt_xvRgbLookup[j].pixelFormat);
+ m_formatIds.append(imageFormats[i].id);
+ break;
+ }
+ }
+ break;
+ case XvYUV:
+ for (int j = 0; j < yuvCount; ++j) {
+ if (imageFormats[i] == qt_xvYuvLookup[j]) {
+ m_supportedPixelFormats.append(qt_xvYuvLookup[j].pixelFormat);
+ m_formatIds.append(imageFormats[i].id);
+ break;
+ }
+ }
+ break;
+ }
+ }
+ XFree(imageFormats);
+ }
+
+ m_brightnessRange = qMakePair(0, 0);
+ m_contrastRange = qMakePair(0, 0);
+ m_hueRange = qMakePair(0, 0);
+ m_saturationRange = qMakePair(0, 0);
+
+ if (XvAttribute *attributes = XvQueryPortAttributes(QX11Info::display(), m_portId, &count)) {
+ for (int i = 0; i < count; ++i) {
+ if (qstrcmp(attributes[i].name, "XV_BRIGHTNESS") == 0)
+ m_brightnessRange = qMakePair(attributes[i].min_value, attributes[i].max_value);
+ else if (qstrcmp(attributes[i].name, "XV_CONTRAST") == 0)
+ m_contrastRange = qMakePair(attributes[i].min_value, attributes[i].max_value);
+ else if (qstrcmp(attributes[i].name, "XV_HUE") == 0)
+ m_hueRange = qMakePair(attributes[i].min_value, attributes[i].max_value);
+ else if (qstrcmp(attributes[i].name, "XV_SATURATION") == 0)
+ m_saturationRange = qMakePair(attributes[i].min_value, attributes[i].max_value);
+ }
+
+ XFree(attributes);
+ }*/
+}
+
+bool S60VideoSurface::isFormatSupported(const QVideoSurfaceFormat &format) const
+{
+}
+
+QT_END_NAMESPACE
diff --git a/src/plugins/mediaservices/symbian/mediaplayer/s60videosurface.h b/src/plugins/mediaservices/symbian/mediaplayer/s60videosurface.h
new file mode 100644
index 0000000..836e52f
--- /dev/null
+++ b/src/plugins/mediaservices/symbian/mediaplayer/s60videosurface.h
@@ -0,0 +1,112 @@
+/****************************************************************************
+**
+** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies).
+** All rights reserved.
+** Contact: Nokia Corporation (qt-info@nokia.com)
+**
+** This file is part of the plugins of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** No Commercial Usage
+** This file contains pre-release code and may not be distributed.
+** You may use this file in accordance with the terms and conditions
+** contained in the Technology Preview License Agreement accompanying
+** this package.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 2.1 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 2.1 requirements
+** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+**
+** In addition, as a special exception, Nokia gives you certain additional
+** rights. These rights are described in the Nokia Qt LGPL Exception
+** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+**
+** If you have questions regarding the use of this file, please contact
+** Nokia at qt-info@nokia.com.
+**
+**
+**
+**
+**
+**
+**
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#ifndef S60VIDEOSURFACE_H
+#define S60VIDEOSURFACE_H
+
+#include <QtGui/qwidget.h>
+#include <QtMultimedia/qabstractvideosurface.h>
+
+QT_BEGIN_NAMESPACE
+
+class QVideoSurfaceFormat;
+
+class S60VideoSurface : public QAbstractVideoSurface
+{
+ Q_OBJECT
+public:
+ S60VideoSurface(QObject *parent = 0);
+ ~S60VideoSurface();
+
+ WId winId() const;
+ void setWinId(WId id);
+
+ QRect displayRect() const;
+ void setDisplayRect(const QRect &rect);
+
+ int brightness() const;
+ void setBrightness(int brightness);
+
+ int contrast() const;
+ void setContrast(int contrast);
+
+ int hue() const;
+ void setHue(int hue);
+
+ int saturation() const;
+ void setSaturation(int saturation);
+
+ QList<QVideoFrame::PixelFormat> supportedPixelFormats(
+ QAbstractVideoBuffer::HandleType handleType = QAbstractVideoBuffer::NoHandle) const;
+
+ bool isFormatSupported(const QVideoSurfaceFormat &format) const;
+
+ bool start(const QVideoSurfaceFormat &format);
+ void stop();
+
+ bool present(const QVideoFrame &frame);
+
+private:
+ WId m_winId;
+ //XvPortID m_portId;
+ //GC m_gc;
+ //XvImage *m_image;
+ QList<QVideoFrame::PixelFormat> m_supportedPixelFormats;
+ QVector<int> m_formatIds;
+ QRect m_viewport;
+ QRect m_displayRect;
+ QPair<int, int> m_brightnessRange;
+ QPair<int, int> m_contrastRange;
+ QPair<int, int> m_hueRange;
+ QPair<int, int> m_saturationRange;
+
+ bool findPort();
+ void querySupportedFormats();
+
+ int getAttribute(const char *attribute, int minimum, int maximum) const;
+ void setAttribute(const char *attribute, int value, int minimum, int maximum);
+
+ static int redistribute(int value, int fromLower, int fromUpper, int toLower, int toUpper);
+};
+
+QT_END_NAMESPACE
+
+#endif
diff --git a/src/plugins/mediaservices/symbian/mediaplayer/s60videowidget.cpp b/src/plugins/mediaservices/symbian/mediaplayer/s60videowidget.cpp
new file mode 100644
index 0000000..84000d5
--- /dev/null
+++ b/src/plugins/mediaservices/symbian/mediaplayer/s60videowidget.cpp
@@ -0,0 +1,208 @@
+/****************************************************************************
+**
+** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies).
+** All rights reserved.
+** Contact: Nokia Corporation (qt-info@nokia.com)
+**
+** This file is part of the plugins of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** No Commercial Usage
+** This file contains pre-release code and may not be distributed.
+** You may use this file in accordance with the terms and conditions
+** contained in the Technology Preview License Agreement accompanying
+** this package.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 2.1 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 2.1 requirements
+** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+**
+** In addition, as a special exception, Nokia gives you certain additional
+** rights. These rights are described in the Nokia Qt LGPL Exception
+** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+**
+** If you have questions regarding the use of this file, please contact
+** Nokia at qt-info@nokia.com.
+**
+**
+**
+**
+**
+**
+**
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#include "s60videowidget.h"
+#include <QtGui/private/qwidget_p.h>
+#include <QEvent>
+#include <coemain.h> // For CCoeEnv
+
+QT_BEGIN_NAMESPACE
+
+QBlackWidget::QBlackWidget(QWidget *parent)
+ : QWidget(parent)
+{
+ setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);
+ setAttribute(Qt::WA_OpaquePaintEvent, true);
+ setAttribute(Qt::WA_NoSystemBackground, true);
+ setAutoFillBackground(false);
+ setPalette(QPalette(Qt::black));
+#if QT_VERSION >= 0x040601 && !defined(__WINSCW__)
+ qt_widget_private(this)->extraData()->nativePaintMode = QWExtra::ZeroFill;
+ qt_widget_private(this)->extraData()->receiveNativePaintEvents = true;
+#endif
+}
+
+QBlackWidget::~QBlackWidget()
+{
+}
+
+void QBlackWidget::beginNativePaintEvent(const QRect& /*controlRect*/)
+{
+ emit beginVideoWindowNativePaint();
+}
+
+void QBlackWidget::endNativePaintEvent(const QRect& /*controlRect*/)
+{
+ CCoeEnv::Static()->WsSession().Flush();
+ emit endVideoWindowNativePaint();
+}
+
+void QBlackWidget::paintEvent(QPaintEvent *event)
+{
+ Q_UNUSED(event);
+ // Do nothing
+}
+
+S60VideoWidgetControl::S60VideoWidgetControl(QObject *parent)
+ : QVideoWidgetControl(parent)
+ , m_widget(0)
+ , m_aspectRatioMode(Qt::KeepAspectRatio)
+{
+ m_widget = new QBlackWidget();
+ connect(m_widget, SIGNAL(beginVideoWindowNativePaint()), this, SIGNAL(beginVideoWindowNativePaint()));
+ connect(m_widget, SIGNAL(endVideoWindowNativePaint()), this, SIGNAL(endVideoWindowNativePaint()));
+ m_widget->installEventFilter(this);
+ m_widget->winId();
+}
+
+S60VideoWidgetControl::~S60VideoWidgetControl()
+{
+ delete m_widget;
+}
+
+QWidget *S60VideoWidgetControl::videoWidget()
+{
+ return m_widget;
+}
+
+Qt::AspectRatioMode S60VideoWidgetControl::aspectRatioMode() const
+{
+ return m_aspectRatioMode;
+}
+
+void S60VideoWidgetControl::setAspectRatioMode(Qt::AspectRatioMode ratio)
+{
+ if (m_aspectRatioMode == ratio)
+ return;
+
+ m_aspectRatioMode = ratio;
+ emit widgetUpdated();
+}
+
+bool S60VideoWidgetControl::isFullScreen() const
+{
+ return m_widget->isFullScreen();
+}
+
+void S60VideoWidgetControl::setFullScreen(bool fullScreen)
+{
+ emit fullScreenChanged(fullScreen);
+}
+
+int S60VideoWidgetControl::brightness() const
+{
+ return 0;
+}
+
+void S60VideoWidgetControl::setBrightness(int brightness)
+{
+ Q_UNUSED(brightness);
+}
+
+int S60VideoWidgetControl::contrast() const
+{
+ return 0;
+}
+
+void S60VideoWidgetControl::setContrast(int contrast)
+{
+ Q_UNUSED(contrast);
+}
+
+int S60VideoWidgetControl::hue() const
+{
+ return 0;
+}
+
+void S60VideoWidgetControl::setHue(int hue)
+{
+ Q_UNUSED(hue);
+}
+
+int S60VideoWidgetControl::saturation() const
+{
+ return 0;
+}
+
+void S60VideoWidgetControl::setSaturation(int saturation)
+{
+ Q_UNUSED(saturation);
+}
+
+bool S60VideoWidgetControl::eventFilter(QObject *object, QEvent *e)
+{
+ if (object == m_widget) {
+ if ( e->type() == QEvent::Resize
+ || e->type() == QEvent::Move
+ || e->type() == QEvent::WinIdChange
+ || e->type() == QEvent::ParentChange
+ || e->type() == QEvent::Show)
+ emit widgetUpdated();
+ }
+ return false;
+}
+
+WId S60VideoWidgetControl::videoWidgetWId()
+{
+ if (m_widget->internalWinId())
+ return m_widget->internalWinId();
+
+ if (m_widget->effectiveWinId())
+ return m_widget->effectiveWinId();
+
+ return NULL;
+}
+
+void S60VideoWidgetControl::videoStateChanged(QMediaPlayer::State state)
+{
+ if (state == QMediaPlayer::StoppedState) {
+#if QT_VERSION <= 0x040600 && !defined(FF_QT)
+ qt_widget_private(m_widget)->extraData()->disableBlit = false;
+#endif
+ m_widget->repaint();
+ } else if (state == QMediaPlayer::PlayingState) {
+#if QT_VERSION <= 0x040600 && !defined(FF_QT)
+ qt_widget_private(m_widget)->extraData()->disableBlit = true;
+#endif
+ }
+}
+
+QT_END_NAMESPACE
diff --git a/src/plugins/mediaservices/symbian/mediaplayer/s60videowidget.h b/src/plugins/mediaservices/symbian/mediaplayer/s60videowidget.h
new file mode 100644
index 0000000..28a1455
--- /dev/null
+++ b/src/plugins/mediaservices/symbian/mediaplayer/s60videowidget.h
@@ -0,0 +1,115 @@
+/****************************************************************************
+**
+** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies).
+** All rights reserved.
+** Contact: Nokia Corporation (qt-info@nokia.com)
+**
+** This file is part of the plugins of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** No Commercial Usage
+** This file contains pre-release code and may not be distributed.
+** You may use this file in accordance with the terms and conditions
+** contained in the Technology Preview License Agreement accompanying
+** this package.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 2.1 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 2.1 requirements
+** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+**
+** In addition, as a special exception, Nokia gives you certain additional
+** rights. These rights are described in the Nokia Qt LGPL Exception
+** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+**
+** If you have questions regarding the use of this file, please contact
+** Nokia at qt-info@nokia.com.
+**
+**
+**
+**
+**
+**
+**
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#ifndef S60VIDEOWIDGET_H
+#define S60VIDEOWIDGET_H
+
+#include <qvideowidgetcontrol.h>
+#include <qmediaplayer.h>
+
+QT_BEGIN_NAMESPACE
+
+class QBlackWidget : public QWidget
+{
+ Q_OBJECT
+
+public:
+ QBlackWidget(QWidget *parent = 0);
+ virtual ~QBlackWidget();
+
+signals:
+ void beginVideoWindowNativePaint();
+ void endVideoWindowNativePaint();
+
+public slots:
+ void beginNativePaintEvent(const QRect&);
+ void endNativePaintEvent(const QRect&);
+
+protected:
+ void paintEvent(QPaintEvent *event);
+};
+
+class S60VideoWidgetControl : public QVideoWidgetControl
+{
+ Q_OBJECT
+
+public:
+ S60VideoWidgetControl(QObject *parent = 0);
+ virtual ~S60VideoWidgetControl();
+
+ // from QVideoWidgetControl
+ QWidget *videoWidget();
+ Qt::AspectRatioMode aspectRatioMode() const;
+ void setAspectRatioMode(Qt::AspectRatioMode ratio);
+ bool isFullScreen() const;
+ void setFullScreen(bool fullScreen);
+ int brightness() const;
+ void setBrightness(int brightness);
+ int contrast() const;
+ void setContrast(int contrast);
+ int hue() const;
+ void setHue(int hue);
+ int saturation() const;
+ void setSaturation(int saturation);
+
+ // from QObject
+ bool eventFilter(QObject *object, QEvent *event);
+
+ //new methods
+ WId videoWidgetWId();
+
+signals:
+ void widgetUpdated();
+ void beginVideoWindowNativePaint();
+ void endVideoWindowNativePaint();
+
+private slots:
+ void videoStateChanged(QMediaPlayer::State state);
+
+private:
+ QBlackWidget *m_widget;
+ Qt::AspectRatioMode m_aspectRatioMode;
+};
+
+QT_END_NAMESPACE
+
+
+#endif // S60VIDEOWIDGET_H
diff --git a/src/plugins/mediaservices/symbian/s60mediaserviceplugin.cpp b/src/plugins/mediaservices/symbian/s60mediaserviceplugin.cpp
new file mode 100644
index 0000000..1185583
--- /dev/null
+++ b/src/plugins/mediaservices/symbian/s60mediaserviceplugin.cpp
@@ -0,0 +1,100 @@
+/****************************************************************************
+**
+** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies).
+** All rights reserved.
+** Contact: Nokia Corporation (qt-info@nokia.com)
+**
+** This file is part of the plugins of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** No Commercial Usage
+** This file contains pre-release code and may not be distributed.
+** You may use this file in accordance with the terms and conditions
+** contained in the Technology Preview License Agreement accompanying
+** this package.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 2.1 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 2.1 requirements
+** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+**
+** In addition, as a special exception, Nokia gives you certain additional
+** rights. These rights are described in the Nokia Qt LGPL Exception
+** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+**
+** If you have questions regarding the use of this file, please contact
+** Nokia at qt-info@nokia.com.
+**
+**
+**
+**
+**
+**
+**
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#include <QtCore/qstring.h>
+#include <QtCore/qdebug.h>
+
+#include "s60mediaserviceplugin.h"
+#ifdef QMEDIA_MMF_RADIO
+#include "s60radiotunerservice.h"
+#endif
+#ifdef QMEDIA_MMF_PLAYER
+#include "s60mediaplayerservice.h"
+#endif
+#ifdef QMEDIA_MMF_CAPTURE
+#include "s60audiocaptureservice.h"
+#endif
+
+QT_BEGIN_NAMESPACE
+
+QStringList S60MediaServicePlugin::keys() const
+{
+ QStringList list;
+#ifdef QMEDIA_MMF_RADIO
+ list << QLatin1String(Q_MEDIASERVICE_RADIO);
+#endif
+
+#ifdef QMEDIA_MMF_PLAYER
+ list << QLatin1String(Q_MEDIASERVICE_MEDIAPLAYER);
+#endif
+#ifdef QMEDIA_MMF_CAPTURE
+ list << QLatin1String(Q_MEDIASERVICE_AUDIOSOURCE);
+#endif
+ return list;
+}
+
+QMediaService* S60MediaServicePlugin::create(QString const& key)
+{
+#ifdef QMEDIA_MMF_PLAYER
+ if (key == QLatin1String(Q_MEDIASERVICE_MEDIAPLAYER))
+ return new S60MediaPlayerService;
+#endif
+#ifdef QMEDIA_MMF_CAPTURE
+ if (key == QLatin1String(Q_MEDIASERVICE_AUDIOSOURCE))
+ return new S60AudioCaptureService;
+#endif
+#ifdef QMEDIA_MMF_RADIO
+ if (key == QLatin1String(Q_MEDIASERVICE_RADIO))
+ return new S60RadioTunerService;
+#endif
+
+ return 0;
+}
+
+void S60MediaServicePlugin::release(QMediaService *service)
+{
+ delete service;
+}
+
+QT_END_NAMESPACE
+
+Q_EXPORT_PLUGIN2(qmmfengine, S60MediaServicePlugin);
+
diff --git a/src/plugins/mediaservices/symbian/s60mediaserviceplugin.h b/src/plugins/mediaservices/symbian/s60mediaserviceplugin.h
new file mode 100644
index 0000000..be2e05d
--- /dev/null
+++ b/src/plugins/mediaservices/symbian/s60mediaserviceplugin.h
@@ -0,0 +1,64 @@
+/****************************************************************************
+**
+** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies).
+** All rights reserved.
+** Contact: Nokia Corporation (qt-info@nokia.com)
+**
+** This file is part of the plugins of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** No Commercial Usage
+** This file contains pre-release code and may not be distributed.
+** You may use this file in accordance with the terms and conditions
+** contained in the Technology Preview License Agreement accompanying
+** this package.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 2.1 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 2.1 requirements
+** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+**
+** In addition, as a special exception, Nokia gives you certain additional
+** rights. These rights are described in the Nokia Qt LGPL Exception
+** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+**
+** If you have questions regarding the use of this file, please contact
+** Nokia at qt-info@nokia.com.
+**
+**
+**
+**
+**
+**
+**
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+
+#ifndef S60SERVICEPLUGIN_H
+#define S60SERVICEPLUGIN_H
+
+#include <QtCore/qobject.h>
+#include <qmediaservice.h>
+#include <qmediaserviceproviderplugin.h>
+
+QT_BEGIN_NAMESPACE
+
+class S60MediaServicePlugin : public QMediaServiceProviderPlugin
+{
+ Q_OBJECT
+public:
+
+ QStringList keys() const;
+ QMediaService* create(QString const& key);
+ void release(QMediaService *service);
+};
+
+QT_END_NAMESPACE
+
+#endif // S60SERVICEPLUGIN_H
diff --git a/src/plugins/mediaservices/symbian/s60videooutputcontrol.cpp b/src/plugins/mediaservices/symbian/s60videooutputcontrol.cpp
new file mode 100644
index 0000000..da07a7d
--- /dev/null
+++ b/src/plugins/mediaservices/symbian/s60videooutputcontrol.cpp
@@ -0,0 +1,76 @@
+/****************************************************************************
+**
+** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies).
+** All rights reserved.
+** Contact: Nokia Corporation (qt-info@nokia.com)
+**
+** This file is part of the plugins of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** No Commercial Usage
+** This file contains pre-release code and may not be distributed.
+** You may use this file in accordance with the terms and conditions
+** contained in the Technology Preview License Agreement accompanying
+** this package.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 2.1 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 2.1 requirements
+** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+**
+** In addition, as a special exception, Nokia gives you certain additional
+** rights. These rights are described in the Nokia Qt LGPL Exception
+** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+**
+** If you have questions regarding the use of this file, please contact
+** Nokia at qt-info@nokia.com.
+**
+**
+**
+**
+**
+**
+**
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#include "s60videooutputcontrol.h"
+
+QT_BEGIN_NAMESPACE
+
+S60VideoOutputControl::S60VideoOutputControl(QObject *parent)
+ : QVideoOutputControl(parent)
+ , m_output(NoOutput)
+{
+}
+
+QList<QVideoOutputControl::Output> S60VideoOutputControl::availableOutputs() const
+{
+ return m_outputs;
+}
+
+void S60VideoOutputControl::setAvailableOutputs(const QList<Output> &outputs)
+{
+ emit availableOutputsChanged(m_outputs = outputs);
+}
+
+QVideoOutputControl::Output S60VideoOutputControl::output() const
+{
+ return m_output;
+}
+
+void S60VideoOutputControl::setOutput(Output output)
+{
+ if (!m_outputs.contains(output))
+ output = NoOutput;
+
+ if (m_output != output)
+ emit outputChanged(m_output = output);
+}
+
+QT_END_NAMESPACE
diff --git a/src/plugins/mediaservices/symbian/s60videooutputcontrol.h b/src/plugins/mediaservices/symbian/s60videooutputcontrol.h
new file mode 100644
index 0000000..dbad889
--- /dev/null
+++ b/src/plugins/mediaservices/symbian/s60videooutputcontrol.h
@@ -0,0 +1,72 @@
+/****************************************************************************
+**
+** Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies).
+** All rights reserved.
+** Contact: Nokia Corporation (qt-info@nokia.com)
+**
+** This file is part of the plugins of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** No Commercial Usage
+** This file contains pre-release code and may not be distributed.
+** You may use this file in accordance with the terms and conditions
+** contained in the Technology Preview License Agreement accompanying
+** this package.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 2.1 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 2.1 requirements
+** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
+**
+** In addition, as a special exception, Nokia gives you certain additional
+** rights. These rights are described in the Nokia Qt LGPL Exception
+** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
+**
+** If you have questions regarding the use of this file, please contact
+** Nokia at qt-info@nokia.com.
+**
+**
+**
+**
+**
+**
+**
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#ifndef S60VIDEOOUTPUTCONTROL_H
+#define S60VIDEOOUTPUTCONTROL_H
+
+#include <QObject>
+#include <qvideooutputcontrol.h>
+
+QT_BEGIN_NAMESPACE
+
+class S60VideoOutputControl : public QVideoOutputControl
+{
+ Q_OBJECT
+public:
+ S60VideoOutputControl(QObject *parent = 0);
+
+ QList<Output> availableOutputs() const;
+ void setAvailableOutputs(const QList<Output> &outputs);
+
+ Output output() const;
+ void setOutput(Output output);
+
+Q_SIGNALS:
+ void outputChanged(QVideoOutputControl::Output output);
+
+private:
+ QList<Output> m_outputs;
+ Output m_output;
+};
+
+QT_END_NAMESPACE
+
+#endif
diff --git a/src/plugins/mediaservices/symbian/symbian.pro b/src/plugins/mediaservices/symbian/symbian.pro
new file mode 100644
index 0000000..f76858f
--- /dev/null
+++ b/src/plugins/mediaservices/symbian/symbian.pro
@@ -0,0 +1,27 @@
+TARGET = qmmfengine
+QT += multimedia mediaservices
+
+load(data_caging_paths)
+
+include (../../qpluginbase.pri)
+include(mediaplayer/mediaplayer.pri)
+
+HEADERS += s60mediaserviceplugin.h \
+ s60videooutputcontrol.h
+
+SOURCES += s60mediaserviceplugin.cpp \
+ s60videooutputcontrol.cpp
+
+contains(S60_VERSION, 3.2)|contains(S60_VERSION, 3.1) {
+ DEFINES += PRE_S60_50_PLATFORM
+}
+
+INCLUDEPATH += $$APP_LAYER_SYSTEMINCLUDE
+symbian-abld:INCLUDEPATH += $$QT_BUILD_TREE/include/QtWidget/private
+
+# This is needed for having the .qtplugin file properly created on Symbian.
+QTDIR_build:DESTDIR = $$QT_BUILD_TREE/plugins/mediaservices
+target.path += $$[QT_INSTALL_PLUGINS]/mediaservices
+INSTALLS += target
+
+TARGET.UID3=0x20021318
diff --git a/src/s60installs/bwins/QtCoreu.def b/src/s60installs/bwins/QtCoreu.def
index d0a446b..e309e25 100644
--- a/src/s60installs/bwins/QtCoreu.def
+++ b/src/s60installs/bwins/QtCoreu.def
@@ -3122,7 +3122,7 @@ EXPORTS
?reset@QIODevice@@UAE_NXZ @ 3121 NONAME ; bool QIODevice::reset(void)
?reset@QMetaProperty@@QBE_NPAVQObject@@@Z @ 3122 NONAME ; bool QMetaProperty::reset(class QObject *) const
?reset@QTextStream@@QAEXXZ @ 3123 NONAME ; void QTextStream::reset(void)
- ?resetCurrentSender@QObjectPrivate@@SAXPAVQObject@@PAUSender@1@1@Z @ 3124 NONAME ; void QObjectPrivate::resetCurrentSender(class QObject *, struct QObjectPrivate::Sender *, struct QObjectPrivate::Sender *)
+ ?resetCurrentSender@QObjectPrivate@@SAXPAVQObject@@PAUSender@1@1@Z @ 3124 NONAME ABSENT ; void QObjectPrivate::resetCurrentSender(class QObject *, struct QObjectPrivate::Sender *, struct QObjectPrivate::Sender *)
?resetDeleteWatch@QObjectPrivate@@SAXPAV1@PAHH@Z @ 3125 NONAME ; void QObjectPrivate::resetDeleteWatch(class QObjectPrivate *, int *, int)
?resetStatus@QDataStream@@QAEXXZ @ 3126 NONAME ; void QDataStream::resetStatus(void)
?resetStatus@QTextStream@@QAEXXZ @ 3127 NONAME ; void QTextStream::resetStatus(void)
@@ -3281,7 +3281,7 @@ EXPORTS
?setCoords@QRectF@@QAEXMMMM@Z @ 3280 NONAME ; void QRectF::setCoords(float, float, float, float)
?setCurrent@QDir@@SA_NABVQString@@@Z @ 3281 NONAME ; bool QDir::setCurrent(class QString const &)
?setCurrentPath@QFSFileEngine@@SA_NABVQString@@@Z @ 3282 NONAME ; bool QFSFileEngine::setCurrentPath(class QString const &)
- ?setCurrentSender@QObjectPrivate@@SAPAUSender@1@PAVQObject@@PAU21@@Z @ 3283 NONAME ; struct QObjectPrivate::Sender * QObjectPrivate::setCurrentSender(class QObject *, struct QObjectPrivate::Sender *)
+ ?setCurrentSender@QObjectPrivate@@SAPAUSender@1@PAVQObject@@PAU21@@Z @ 3283 NONAME ABSENT ; struct QObjectPrivate::Sender * QObjectPrivate::setCurrentSender(class QObject *, struct QObjectPrivate::Sender *)
?setCurrentTime@QAbstractAnimation@@QAEXH@Z @ 3284 NONAME ; void QAbstractAnimation::setCurrentTime(int)
?setCurrentTime@QTimeLine@@QAEXH@Z @ 3285 NONAME ; void QTimeLine::setCurrentTime(int)
?setCurveShape@QTimeLine@@QAEXW4CurveShape@1@@Z @ 3286 NONAME ; void QTimeLine::setCurveShape(enum QTimeLine::CurveShape)
diff --git a/src/s60installs/bwins/QtDeclarativeu.def b/src/s60installs/bwins/QtDeclarativeu.def
index ec25b5c..5f05f08 100644
--- a/src/s60installs/bwins/QtDeclarativeu.def
+++ b/src/s60installs/bwins/QtDeclarativeu.def
@@ -3950,7 +3950,7 @@ EXPORTS
?qmlInfo@@YA?AVQDeclarativeInfo@@PBVQObject@@ABVQDeclarativeError@@@Z @ 3949 NONAME ; class QDeclarativeInfo qmlInfo(class QObject const *, class QDeclarativeError const &)
?error@QDeclarativeCustomParser@@IAEXABVQString@@@Z @ 3950 NONAME ; void QDeclarativeCustomParser::error(class QString const &)
?activeChanged@QDeclarativeDrag@@IAEXXZ @ 3951 NONAME ; void QDeclarativeDrag::activeChanged(void)
- ??0QDeclarativeInfo@@AAE@PAUQDeclarativeInfoPrivate@@@Z @ 3952 NONAME ; QDeclarativeInfo::QDeclarativeInfo(struct QDeclarativeInfoPrivate *)
+ ??0QDeclarativeInfo@@AAE@PAUQDeclarativeInfoPrivate@@@Z @ 3952 NONAME ABSENT ; QDeclarativeInfo::QDeclarativeInfo(struct QDeclarativeInfoPrivate *)
?warnings@QDeclarativeEngine@@IAEXABV?$QList@VQDeclarativeError@@@@@Z @ 3953 NONAME ; void QDeclarativeEngine::warnings(class QList<class QDeclarativeError> const &)
?parentModelIndex@QDeclarativeVisualDataModel@@QBE?AVQVariant@@XZ @ 3954 NONAME ; class QVariant QDeclarativeVisualDataModel::parentModelIndex(void) const
?usedAnchors@QDeclarativeAnchors@@QBE?AV?$QFlags@W4Anchor@QDeclarativeAnchors@@@@XZ @ 3955 NONAME ; class QFlags<enum QDeclarativeAnchors::Anchor> QDeclarativeAnchors::usedAnchors(void) const
diff --git a/src/s60installs/eabi/QtCoreu.def b/src/s60installs/eabi/QtCoreu.def
index daa9dc6..92a4020 100644
--- a/src/s60installs/eabi/QtCoreu.def
+++ b/src/s60installs/eabi/QtCoreu.def
@@ -3697,4 +3697,5 @@ EXPORTS
_ZN16QDeclarativeData9destroyedE @ 3696 NONAME DATA 4 ABSENT
_ZN24QAbstractDeclarativeData13parentChangedE @ 3697 NONAME DATA 4
_ZN24QAbstractDeclarativeData9destroyedE @ 3698 NONAME DATA 4
+ _ZN23QEventDispatcherSymbian12selectThreadEv @ 3699 NONAME
diff --git a/src/s60installs/eabi/QtDeclarativeu.def b/src/s60installs/eabi/QtDeclarativeu.def
index 953d0a1..ad12166 100644
--- a/src/s60installs/eabi/QtDeclarativeu.def
+++ b/src/s60installs/eabi/QtDeclarativeu.def
@@ -3496,4 +3496,44 @@ EXPORTS
_ZTIN14QDeclarativeJS3AST18FunctionExpressionE @ 3495 NONAME ABSENT
_ZTIN14QDeclarativeJS3AST4NodeE @ 3496 NONAME ABSENT
_ZTIN14QDeclarativeJS3AST9StatementE @ 3497 NONAME ABSENT
+ _Z7qmlInfoPK7QObjectRK17QDeclarativeError @ 3498 NONAME
+ _Z7qmlInfoPK7QObjectRK5QListI17QDeclarativeErrorE @ 3499 NONAME
+ _ZN16QDeclarativeDrag13activeChangedEv @ 3500 NONAME
+ _ZN16QDeclarativeDrag9setActiveEb @ 3501 NONAME
+ _ZN16QDeclarativeInfoC1EP23QDeclarativeInfoPrivate @ 3502 NONAME
+ _ZN16QDeclarativeInfoC1ERKS_ @ 3503 NONAME
+ _ZN16QDeclarativeInfoC2EP23QDeclarativeInfoPrivate @ 3504 NONAME
+ _ZN16QDeclarativeInfoC2ERKS_ @ 3505 NONAME
+ _ZN16QDeclarativeItem10forceFocusEv @ 3506 NONAME
+ _ZN16QDeclarativeView11eventFilterEP7QObjectP6QEvent @ 3507 NONAME
+ _ZN18QDeclarativeEngine32setOutputWarningsToStandardErrorEb @ 3508 NONAME
+ _ZN18QDeclarativeEngine8warningsERK5QListI17QDeclarativeErrorE @ 3509 NONAME
+ _ZN18QDeclarativeLoader20resetSourceComponentEv @ 3510 NONAME
+ _ZN20QDeclarativeFlipable15retransformBackEv @ 3511 NONAME
+ _ZN20QDeclarativeGridView11animStoppedEv @ 3512 NONAME
+ _ZN21QDeclarativeFlickable17setBoundsBehaviorENS_14BoundsBehaviorE @ 3513 NONAME
+ _ZN21QDeclarativeFlickable21boundsBehaviorChangedEv @ 3514 NONAME
+ _ZN21QDeclarativeMouseArea15geometryChangedERK6QRectFS2_ @ 3515 NONAME
+ _ZN21QDeclarativeMouseArea20mousePositionChangedEP22QDeclarativeMouseEvent @ 3516 NONAME
+ _ZN22QDeclarativeExpression8evaluateEPb @ 3517 NONAME
+ _ZN23QDeclarativeItemPrivate16transformChangedEv @ 3518 NONAME
+ _ZN24QDeclarativeCustomParser5errorERK7QString @ 3519 NONAME
+ _ZN24QDeclarativeDebugService18hasDebuggingClientEv @ 3520 NONAME
+ _ZN24QDeclarativeParentChange7executeEN23QDeclarativeActionEvent6ReasonE @ 3521 NONAME
+ _ZN24QDeclarativeParentChange7reverseEN23QDeclarativeActionEvent6ReasonE @ 3522 NONAME
+ _ZN25QDeclarativeAnchorChanges7executeEN23QDeclarativeActionEvent6ReasonE @ 3523 NONAME
+ _ZN25QDeclarativeAnchorChanges7reverseEN23QDeclarativeActionEvent6ReasonE @ 3524 NONAME
+ _ZN27QDeclarativeVisualDataModel12setRootIndexERK8QVariant @ 3525 NONAME
+ _ZN29QDeclarativeStateChangeScript7executeEN23QDeclarativeActionEvent6ReasonE @ 3526 NONAME
+ _ZNK16QDeclarativeDrag6activeEv @ 3527 NONAME
+ _ZNK16QDeclarativeType16noCreationReasonEv @ 3528 NONAME
+ _ZNK18QDeclarativeEngine29outputWarningsToStandardErrorEv @ 3529 NONAME
+ _ZNK21QDeclarativeFlickable14boundsBehaviorEv @ 3530 NONAME
+ _ZNK27QDeclarativeVisualDataModel10modelIndexEi @ 3531 NONAME
+ _ZNK27QDeclarativeVisualDataModel16parentModelIndexEv @ 3532 NONAME
+ _ZThn8_N24QDeclarativeParentChange7executeEN23QDeclarativeActionEvent6ReasonE @ 3533 NONAME
+ _ZThn8_N24QDeclarativeParentChange7reverseEN23QDeclarativeActionEvent6ReasonE @ 3534 NONAME
+ _ZThn8_N25QDeclarativeAnchorChanges7executeEN23QDeclarativeActionEvent6ReasonE @ 3535 NONAME
+ _ZThn8_N25QDeclarativeAnchorChanges7reverseEN23QDeclarativeActionEvent6ReasonE @ 3536 NONAME
+ _ZThn8_N29QDeclarativeStateChangeScript7executeEN23QDeclarativeActionEvent6ReasonE @ 3537 NONAME
diff --git a/src/s60installs/eabi/QtNetworku.def b/src/s60installs/eabi/QtNetworku.def
index 2796778..2566415 100644
--- a/src/s60installs/eabi/QtNetworku.def
+++ b/src/s60installs/eabi/QtNetworku.def
@@ -1166,4 +1166,5 @@ EXPORTS
_ZNK13QBearerEngine15requiresPollingEv @ 1165 NONAME
_ZNK13QBearerEngine19configurationsInUseEv @ 1166 NONAME
_ZNK21QNetworkAccessManager17networkAccessibleEv @ 1167 NONAME
+ _ZN35QNetworkConfigurationManagerPrivate12capabilitiesEv @ 1168 NONAME
diff --git a/src/s60installs/s60installs.pro b/src/s60installs/s60installs.pro
index ad196a8..dfd2694 100644
--- a/src/s60installs/s60installs.pro
+++ b/src/s60installs/s60installs.pro
@@ -151,9 +151,18 @@ symbian: {
graphicssystems_plugins.sources += $$QT_BUILD_TREE/plugins/graphicssystems/qvggraphicssystem$${QT_LIBINFIX}.dll
}
- contains(QT_CONFIG, multimedia) {
+ contains(QT_CONFIG, multimedia):contains(QT_CONFIG, mediaservices):contains(QT_CONFIG, media-backend) {
qtlibraries.sources += $$QMAKE_LIBDIR_QT/QtMultimedia$${QT_LIBINFIX}.dll
+ }
+
+ contains(QT_CONFIG, media-backend) {
qtlibraries.sources += $$QMAKE_LIBDIR_QT/QtMediaServices$${QT_LIBINFIX}.dll
+
+ mediaservices_plugins.path = c:$$QT_PLUGINS_BASE_DIR/mediaservices
+ mediaservices_plugins.sources += $$QT_BUILD_TREE/plugins/mediaservices/qmmfengine$${QT_LIBINFIX}.dll
+
+ DEPLOYMENT += mediaservices_plugins
+
}
BLD_INF_RULES.prj_exports += "qt.iby $$CORE_MW_LAYER_IBY_EXPORT_PATH(qt.iby)"
diff --git a/src/script/bridge/qscriptqobject_p.h b/src/script/bridge/qscriptqobject_p.h
index b82bcb7..412a784 100644
--- a/src/script/bridge/qscriptqobject_p.h
+++ b/src/script/bridge/qscriptqobject_p.h
@@ -303,7 +303,7 @@ public:
}
protected:
- static const unsigned StructureFlags = JSC::OverridesGetOwnPropertySlot | JSC::OverridesMarkChildren | JSC::OverridesGetPropertyNames | JSObject::StructureFlags;
+ static const unsigned StructureFlags = JSC::OverridesGetOwnPropertySlot | JSC::OverridesMarkChildren | JSC::OverridesGetPropertyNames | JSC::ImplementsHasInstance | JSObject::StructureFlags;
Data *data;
};
diff --git a/src/sql/drivers/sqlite/qsql_sqlite.cpp b/src/sql/drivers/sqlite/qsql_sqlite.cpp
index 24dcad9..4344af4 100644
--- a/src/sql/drivers/sqlite/qsql_sqlite.cpp
+++ b/src/sql/drivers/sqlite/qsql_sqlite.cpp
@@ -259,6 +259,7 @@ bool QSQLiteResultPrivate::fetchNext(QSqlCachedResult::ValueCache &values, int i
q->setAt(QSql::AfterLastRow);
sqlite3_reset(stmt);
return false;
+ case SQLITE_CONSTRAINT:
case SQLITE_ERROR:
// SQLITE_ERROR is a generic error code and we must call sqlite3_reset()
// to get the specific error message.
diff --git a/src/testlib/qtestlogger.cpp b/src/testlib/qtestlogger.cpp
index 6c76388..f0be6be 100644
--- a/src/testlib/qtestlogger.cpp
+++ b/src/testlib/qtestlogger.cpp
@@ -211,10 +211,7 @@ void QTestLogger::addIncident(IncidentTypes type, const char *description,
QTest::qt_snprintf(buf, sizeof(buf), "%i", line);
failureElement->addAttribute(QTest::AI_Line, buf);
failureElement->addAttribute(QTest::AI_Description, description);
- const char* tag = QTestResult::currentDataTag();
- if (tag) {
- failureElement->addAttribute(QTest::AI_Tag, tag);
- }
+ addTag(failureElement);
currentLogElement->addLogElement(failureElement);
}
@@ -279,6 +276,27 @@ void QTestLogger::addBenchmarkResult(const QBenchmarkResult &result)
currentLogElement->addLogElement(benchmarkElement);
}
+void QTestLogger::addTag(QTestElement* element)
+{
+ const char *tag = QTestResult::currentDataTag();
+ const char *gtag = QTestResult::currentGlobalDataTag();
+ const char *filler = (tag && gtag) ? ":" : "";
+ if ((!tag || !tag[0]) && (!gtag || !gtag[0])) {
+ return;
+ }
+
+ if (!tag) {
+ tag = "";
+ }
+ if (!gtag) {
+ gtag = "";
+ }
+
+ QTestCharBuffer buf;
+ QTest::qt_asprintf(&buf, "%s%s%s", gtag, filler, tag);
+ element->addAttribute(QTest::AI_Tag, buf.constData());
+}
+
void QTestLogger::addMessage(MessageTypes type, const char *message, const char *file, int line)
{
QTestElement *errorElement = new QTestElement(QTest::LET_Error);
@@ -299,7 +317,7 @@ void QTestLogger::addMessage(MessageTypes type, const char *message, const char
break;
case QAbstractTestLogger::QWarning:
++qwarnCounter;
- typeBuf = "qwarning";
+ typeBuf = "qwarn";
break;
case QAbstractTestLogger::QFatal:
++qfatalCounter;
@@ -320,6 +338,7 @@ void QTestLogger::addMessage(MessageTypes type, const char *message, const char
errorElement->addAttribute(QTest::AI_Type, typeBuf);
errorElement->addAttribute(QTest::AI_Description, message);
+ addTag(errorElement);
if(file)
errorElement->addAttribute(QTest::AI_File, file);
diff --git a/src/testlib/qtestlogger_p.h b/src/testlib/qtestlogger_p.h
index 31f7d55..bb7a358 100644
--- a/src/testlib/qtestlogger_p.h
+++ b/src/testlib/qtestlogger_p.h
@@ -83,6 +83,7 @@ class QTestLogger : public QAbstractTestLogger
void addIncident(IncidentTypes type, const char *description,
const char *file = 0, int line = 0);
void addBenchmarkResult(const QBenchmarkResult &result);
+ void addTag(QTestElement* element);
void addMessage(MessageTypes type, const char *message,
const char *file = 0, int line = 0);
diff --git a/src/testlib/qtestxmlstreamer.cpp b/src/testlib/qtestxmlstreamer.cpp
index b9946e5..f63c221 100644
--- a/src/testlib/qtestxmlstreamer.cpp
+++ b/src/testlib/qtestxmlstreamer.cpp
@@ -111,12 +111,20 @@ void QTestXmlStreamer::formatStart(const QTestElement *element, QTestCharBuffer
QXmlTestLogger::xmlQuote(&quotedFile, element->attributeValue(QTest::AI_File));
QXmlTestLogger::xmlCdata(&cdataDesc, element->attributeValue(QTest::AI_Description));
- QTest::qt_asprintf(formatted, "<Message type=\"%s\" %s=\"%s\" %s=\"%s\">\n <Description><![CDATA[%s]]></Description>\n</Message>\n",
+ QTestCharBuffer tagbuf;
+ if (element->attribute(QTest::AI_Tag)) {
+ QTestCharBuffer cdataTag;
+ QXmlTestLogger::xmlCdata(&cdataTag, element->attributeValue(QTest::AI_Tag));
+ QTest::qt_asprintf(&tagbuf, " <DataTag><![CDATA[%s]]></DataTag>\n", cdataTag.constData());
+ }
+
+ QTest::qt_asprintf(formatted, "<Message type=\"%s\" %s=\"%s\" %s=\"%s\">\n%s <Description><![CDATA[%s]]></Description>\n</Message>\n",
element->attributeValue(QTest::AI_Type),
element->attributeName(QTest::AI_File),
quotedFile.constData(),
element->attributeName(QTest::AI_Line),
element->attributeValue(QTest::AI_Line),
+ tagbuf.constData(),
cdataDesc.constData());
break;
}
@@ -149,7 +157,29 @@ void QTestXmlStreamer::formatEnd(const QTestElement *element, QTestCharBuffer *f
return;
if (element->elementType() == QTest::LET_TestCase) {
- QTest::qt_asprintf(formatted, "</TestFunction>\n");
+ bool failed = false;
+ for (QTestElement* child = element->childElements(); child; child = child->nextElement()) {
+ if ( child->elementType() == QTest::LET_Failure
+ && child->attribute(QTest::AI_Result)
+ && ( !strcmp(child->attributeValue(QTest::AI_Result), "fail")
+ || !strcmp(child->attributeValue(QTest::AI_Result), "xpass"))
+ )
+ {
+ failed = true;
+ break;
+ }
+ }
+
+ // For passing functions, no Incident has been output yet.
+ // For failing functions, we already output one.
+ // Please note: we are outputting "pass" even if there was an xfail etc.
+ // This is by design (arguably bad design, but dangerous to change now!)
+ if (element->attribute(QTest::AI_Result) && !failed) {
+ QTest::qt_asprintf(formatted, "<Incident type=\"pass\" file=\"\" line=\"0\" />\n</TestFunction>\n");
+ }
+ else {
+ QTest::qt_asprintf(formatted, "</TestFunction>\n");
+ }
} else {
formatted->data()[0] = '\0';
}
@@ -157,29 +187,11 @@ void QTestXmlStreamer::formatEnd(const QTestElement *element, QTestCharBuffer *f
void QTestXmlStreamer::formatBeforeAttributes(const QTestElement *element, QTestCharBuffer *formatted) const
{
- if(!element || !formatted)
+ Q_UNUSED(element);
+ if (!formatted)
return;
- if (element->elementType() == QTest::LET_TestCase && element->attribute(QTest::AI_Result)){
- QTestCharBuffer buf;
- QTestCharBuffer quotedFile;
- QXmlTestLogger::xmlQuote(&quotedFile, element->attributeValue(QTest::AI_File));
-
- QTest::qt_asprintf(&buf, "%s=\"%s\" %s=\"%s\"",
- element->attributeName(QTest::AI_File),
- quotedFile.constData(),
- element->attributeName(QTest::AI_Line),
- element->attributeValue(QTest::AI_Line));
-
- if( !element->childElements() ) {
- QTest::qt_asprintf(formatted, "<Incident type=\"%s\" %s/>\n",
- element->attributeValue(QTest::AI_Result), buf.constData());
- } else {
- formatted->data()[0] = '\0';
- }
- } else {
- formatted->data()[0] = '\0';
- }
+ formatted->data()[0] = '\0';
}
void QTestXmlStreamer::output(QTestElement *element) const
diff --git a/src/testlib/qxmltestlogger.cpp b/src/testlib/qxmltestlogger.cpp
index 2236666..07e8ef0 100644
--- a/src/testlib/qxmltestlogger.cpp
+++ b/src/testlib/qxmltestlogger.cpp
@@ -244,7 +244,7 @@ void QXmlTestLogger::addBenchmarkResult(const QBenchmarkResult &result)
QTestCharBuffer quotedTag;
xmlQuote(&quotedMetric,
- benchmarkMetricUnit(result.metric));
+ benchmarkMetricName(result.metric));
xmlQuote(&quotedTag, result.context.tag.toAscii().constData());
QTest::qt_asprintf(
diff --git a/src/xmlpatterns/schema/qxsdschemaresolver.cpp b/src/xmlpatterns/schema/qxsdschemaresolver.cpp
index 34eb12c..f3d1ed0 100644
--- a/src/xmlpatterns/schema/qxsdschemaresolver.cpp
+++ b/src/xmlpatterns/schema/qxsdschemaresolver.cpp
@@ -632,7 +632,14 @@ void XsdSchemaResolver::resolveSimpleContentComplexTypes(const XsdComplexType::P
} else {
// 1.2
const XsdSimpleType::Ptr anonType(new XsdSimpleType());
- anonType->setCategory(complexBaseType->contentType()->simpleType()->category());
+ XsdSimpleType::TypeCategory baseCategory = complexBaseType->contentType()->simpleType()->category();
+ anonType->setCategory(baseCategory);
+
+ if (baseCategory == XsdSimpleType::SimpleTypeList) {
+ const XsdSimpleType::Ptr baseSimpleType = complexBaseType->contentType()->simpleType();
+ anonType->setItemType(baseSimpleType->itemType());
+ }
+
anonType->setDerivationMethod(XsdSimpleType::DerivationRestriction);
anonType->setWxsSuperType(complexBaseType->contentType()->simpleType());
anonType->setFacets(complexTypeFacets(complexType));
diff --git a/src/xmlpatterns/xmlpatterns.pro b/src/xmlpatterns/xmlpatterns.pro
index a224762..e50d184 100644
--- a/src/xmlpatterns/xmlpatterns.pro
+++ b/src/xmlpatterns/xmlpatterns.pro
@@ -24,13 +24,14 @@ include($$PWD/schema/schema.pri)
include($$PWD/type/type.pri)
include($$PWD/utils/utils.pri)
include($$PWD/qobjectmodel/qobjectmodel.pri, "", true)
-wince*:# The Microsoft MIPS compiler crashes if /Og is specified
-:
-# -O2/1 expands to /Og plus additional arguments.
-contains(DEFINES, MIPS): {
- QMAKE_CXXFLAGS_RELEASE ~= s/-O2/-Oi -Ot -Oy -Ob2/
- QMAKE_CXXFLAGS_RELEASE ~= s/-O1/-Os -Oy -Ob2/
+wince* {
+ # The Microsoft MIPS compiler crashes if /Og is specified.
+ # -O2/1 expands to /Og plus additional arguments.
+ contains(DEFINES, MIPS) {
+ QMAKE_CXXFLAGS_RELEASE ~= s/-O2/-Oi -Ot -Oy -Ob2/
+ QMAKE_CXXFLAGS_RELEASE ~= s/-O1/-Os -Oy -Ob2/
+ }
}
+
symbian:TARGET.UID3 = 0x2001E62B
-HEADERS +=