summaryrefslogtreecommitdiffstats
path: root/src/gui
diff options
context:
space:
mode:
authorGunnar Sletta <gunnar@trolltech.com>2009-10-19 04:58:20 (GMT)
committerGunnar Sletta <gunnar@trolltech.com>2009-10-19 04:58:20 (GMT)
commit91e133d9eeba0b7ea87a3ddb3f10d2a2b345473d (patch)
tree499f3a3e0ba67c76da18a33fd331569670578a79 /src/gui
parent4a0e3170c779a6a37954c3dfcfd0b9f0ce144701 (diff)
parentc3bab81d5966c9bd3a42d9c5cbb9d8ad35a1b330 (diff)
downloadQt-91e133d9eeba0b7ea87a3ddb3f10d2a2b345473d.zip
Qt-91e133d9eeba0b7ea87a3ddb3f10d2a2b345473d.tar.gz
Qt-91e133d9eeba0b7ea87a3ddb3f10d2a2b345473d.tar.bz2
Merge branch '4.6' of git@scm.dev.nokia.troll.no:qt/qt into 4.6
Diffstat (limited to 'src/gui')
-rw-r--r--src/gui/dialogs/qcolordialog_mac.mm4
-rw-r--r--src/gui/dialogs/qerrormessage.cpp13
-rw-r--r--src/gui/dialogs/qfiledialog_mac.mm3
-rw-r--r--src/gui/dialogs/qprintdialog_mac.mm10
-rw-r--r--src/gui/dialogs/qprogressdialog.cpp2
-rw-r--r--src/gui/dialogs/qwizard.cpp2
-rw-r--r--src/gui/egl/qegl_qws.cpp3
-rw-r--r--src/gui/embedded/directfb.pri2
-rw-r--r--src/gui/graphicsview/qgraphicsitem.cpp15
-rw-r--r--src/gui/graphicsview/qgraphicsitem.h4
-rw-r--r--src/gui/graphicsview/qgraphicsitem_p.h1
-rw-r--r--src/gui/graphicsview/qgraphicsproxywidget.cpp2
-rw-r--r--src/gui/graphicsview/qgraphicsscene.cpp24
-rw-r--r--src/gui/graphicsview/qgraphicsscene.h1
-rw-r--r--src/gui/graphicsview/qgraphicsscene_p.h2
-rw-r--r--src/gui/image/qiconloader.cpp6
-rw-r--r--src/gui/image/qpixmap_s60.cpp2
-rw-r--r--src/gui/itemviews/qabstractitemview.cpp7
-rw-r--r--src/gui/itemviews/qheaderview.cpp4
-rw-r--r--src/gui/itemviews/qtableview.cpp207
-rw-r--r--src/gui/itemviews/qtableview_p.h4
-rw-r--r--src/gui/itemviews/qtablewidget.cpp2
-rw-r--r--src/gui/itemviews/qtreewidget.cpp2
-rw-r--r--src/gui/kernel/kernel.pri27
-rw-r--r--src/gui/kernel/qapplication.cpp116
-rw-r--r--src/gui/kernel/qapplication.h5
-rw-r--r--src/gui/kernel/qapplication_p.h22
-rw-r--r--src/gui/kernel/qapplication_s60.cpp157
-rw-r--r--src/gui/kernel/qapplication_win.cpp48
-rw-r--r--src/gui/kernel/qcocoaview_mac.mm27
-rw-r--r--src/gui/kernel/qcursor_s60.cpp24
-rw-r--r--src/gui/kernel/qdnd_s60.cpp4
-rw-r--r--src/gui/kernel/qevent.cpp172
-rw-r--r--src/gui/kernel/qevent.h34
-rw-r--r--src/gui/kernel/qeventdispatcher_mac.mm23
-rw-r--r--src/gui/kernel/qgesture.cpp685
-rw-r--r--src/gui/kernel/qgesture.h154
-rw-r--r--src/gui/kernel/qgesture_p.h76
-rw-r--r--src/gui/kernel/qgesturemanager.cpp467
-rw-r--r--src/gui/kernel/qgesturemanager_p.h125
-rw-r--r--src/gui/kernel/qgesturerecognizer.cpp200
-rw-r--r--src/gui/kernel/qgesturerecognizer.h93
-rw-r--r--src/gui/kernel/qmacgesturerecognizer_mac.mm267
-rw-r--r--src/gui/kernel/qmacgesturerecognizer_mac_p.h103
-rw-r--r--src/gui/kernel/qsoftkeymanager.cpp7
-rw-r--r--src/gui/kernel/qstandardgestures.cpp775
-rw-r--r--src/gui/kernel/qstandardgestures.h174
-rw-r--r--src/gui/kernel/qstandardgestures_p.h77
-rw-r--r--src/gui/kernel/qwidget.cpp40
-rw-r--r--src/gui/kernel/qwidget.h11
-rw-r--r--src/gui/kernel/qwidget_p.h7
-rw-r--r--src/gui/kernel/qwidget_s60.cpp78
-rw-r--r--src/gui/kernel/qwidget_win.cpp29
-rw-r--r--src/gui/kernel/qwinnativepangesturerecognizer_win.cpp124
-rw-r--r--src/gui/kernel/qwinnativepangesturerecognizer_win_p.h73
-rw-r--r--src/gui/painting/qcolor.cpp27
-rw-r--r--src/gui/painting/qpaintdevice.cpp5
-rw-r--r--src/gui/painting/qpaintdevice.h1
-rw-r--r--src/gui/painting/qpaintengine_raster.cpp9
-rw-r--r--src/gui/painting/qpaintengine_s60.cpp2
-rw-r--r--src/gui/painting/qpaintengineex_p.h7
-rw-r--r--src/gui/s60framework/qs60mainapplication.cpp47
-rw-r--r--src/gui/s60framework/qs60mainappui.cpp44
-rw-r--r--src/gui/s60framework/qs60maindocument.cpp44
-rw-r--r--src/gui/styles/gtksymbols.cpp9
-rw-r--r--src/gui/text/qfontdatabase.cpp9
-rw-r--r--src/gui/text/qfontdatabase_x11.cpp26
-rw-r--r--src/gui/text/qfontengine_mac.mm7
-rw-r--r--src/gui/text/qfontengine_x11.cpp5
-rw-r--r--src/gui/text/qtextcontrol.cpp8
-rw-r--r--src/gui/text/qtextodfwriter.cpp4
-rw-r--r--src/gui/widgets/qabstractscrollarea.cpp56
-rw-r--r--src/gui/widgets/qabstractscrollarea.h4
-rw-r--r--src/gui/widgets/qabstractscrollarea_p.h3
-rw-r--r--src/gui/widgets/qcombobox.cpp5
-rw-r--r--src/gui/widgets/qdialogbuttonbox.cpp3
-rw-r--r--src/gui/widgets/qlinecontrol.cpp2
-rw-r--r--src/gui/widgets/qmainwindow.cpp6
-rw-r--r--src/gui/widgets/qmenu_mac.mm4
-rw-r--r--src/gui/widgets/qplaintextedit.cpp55
-rw-r--r--src/gui/widgets/qplaintextedit.h4
-rw-r--r--src/gui/widgets/qplaintextedit_p.h5
82 files changed, 3317 insertions, 1630 deletions
diff --git a/src/gui/dialogs/qcolordialog_mac.mm b/src/gui/dialogs/qcolordialog_mac.mm
index f6b88bb..9e4fdd1 100644
--- a/src/gui/dialogs/qcolordialog_mac.mm
+++ b/src/gui/dialogs/qcolordialog_mac.mm
@@ -44,6 +44,7 @@
#include <qapplication.h>
#include <qtimer.h>
#include <qdialogbuttonbox.h>
+#include <qabstracteventdispatcher.h>
#include <private/qapplication_p.h>
#include <private/qt_mac_p.h>
#include <qdebug.h>
@@ -319,6 +320,7 @@ QT_USE_NAMESPACE
QMacCocoaAutoReleasePool pool;
mDialogIsExecuting = true;
[NSApp runModalForWindow:mColorPanel];
+ QAbstractEventDispatcher::instance()->interrupt();
if (mResultCode == NSCancelButton)
mPriv->colorDialog()->reject();
else
@@ -411,7 +413,7 @@ void QColorDialogPrivate::openCocoaColorPanel(const QColor &initial,
void QColorDialogPrivate::closeCocoaColorPanel()
{
- [[static_cast<QCocoaColorPanelDelegate *>(delegate) colorPanel] close];
+ [static_cast<QCocoaColorPanelDelegate *>(delegate) onCancelClicked];
}
void QColorDialogPrivate::releaseCocoaColorPanelDelegate()
diff --git a/src/gui/dialogs/qerrormessage.cpp b/src/gui/dialogs/qerrormessage.cpp
index 436ef94..762936a 100644
--- a/src/gui/dialogs/qerrormessage.cpp
+++ b/src/gui/dialogs/qerrormessage.cpp
@@ -245,12 +245,6 @@ QErrorMessage::QErrorMessage(QWidget * parent)
Q_D(QErrorMessage);
QGridLayout * grid = new QGridLayout(this);
d->icon = new QLabel(this);
-#ifdef QT_SOFTKEYS_ENABLED
- d->okAction = new QAction(this);
- d->okAction->setSoftKeyRole(QAction::PositiveSoftKey);
- connect(d->okAction, SIGNAL(triggered()), this, SLOT(accept()));
- addAction(d->okAction);
-#endif
#ifndef QT_NO_MESSAGEBOX
d->icon->setPixmap(QMessageBox::standardIcon(QMessageBox::Information));
d->icon->setAlignment(Qt::AlignHCenter | Qt::AlignTop);
@@ -262,6 +256,13 @@ QErrorMessage::QErrorMessage(QWidget * parent)
d->again->setChecked(true);
grid->addWidget(d->again, 1, 1, Qt::AlignTop);
d->ok = new QPushButton(this);
+#ifdef QT_SOFTKEYS_ENABLED
+ d->okAction = new QAction(d->ok);
+ d->okAction->setSoftKeyRole(QAction::PositiveSoftKey);
+ connect(d->okAction, SIGNAL(triggered()), this, SLOT(accept()));
+ addAction(d->okAction);
+#endif
+
#if defined(Q_WS_WINCE) || defined(Q_WS_S60)
d->ok->setFixedSize(0,0);
diff --git a/src/gui/dialogs/qfiledialog_mac.mm b/src/gui/dialogs/qfiledialog_mac.mm
index 3a4ecce..8e4c461 100644
--- a/src/gui/dialogs/qfiledialog_mac.mm
+++ b/src/gui/dialogs/qfiledialog_mac.mm
@@ -62,6 +62,7 @@
#include <qvarlengtharray.h>
#include <qdesktopwidget.h>
#include <stdlib.h>
+#include <qabstracteventdispatcher.h>
#include "ui_qfiledialog.h"
QT_BEGIN_NAMESPACE
@@ -245,6 +246,8 @@ QT_USE_NAMESPACE
mReturnCode = [mSavePanel
runModalForDirectory:mCurrentDir
file:selectable ? filename : @"untitled"];
+
+ QAbstractEventDispatcher::instance()->interrupt();
return (mReturnCode == NSOKButton);
}
diff --git a/src/gui/dialogs/qprintdialog_mac.mm b/src/gui/dialogs/qprintdialog_mac.mm
index a7587b1..56a065a 100644
--- a/src/gui/dialogs/qprintdialog_mac.mm
+++ b/src/gui/dialogs/qprintdialog_mac.mm
@@ -122,6 +122,8 @@ QT_END_NAMESPACE
QT_USE_NAMESPACE
+#ifdef QT_MAC_USE_COCOA
+
@class QCocoaPrintPanelDelegate;
@interface QCocoaPrintPanelDelegate : NSObject {
@@ -166,6 +168,12 @@ QT_USE_NAMESPACE
}
// Keep us in sync with file output
PMDestinationType dest;
+
+ // If the user selected print to file, the session has been
+ // changed behind our back and our d->ep->session object is a
+ // dangling pointer. Update it based on the "current" session
+ d->ep->session = static_cast<PMPrintSession>([d->ep->printInfo PMPrintSession]);
+
PMSessionGetDestinationType(d->ep->session, d->ep->settings, &dest);
if (dest == kPMDestinationFile) {
QCFType<CFURLRef> file;
@@ -191,6 +199,8 @@ QT_USE_NAMESPACE
}
@end
+#endif
+
QT_BEGIN_NAMESPACE
extern void macStartInterceptWindowTitle(QWidget *window);
diff --git a/src/gui/dialogs/qprogressdialog.cpp b/src/gui/dialogs/qprogressdialog.cpp
index 5fb10bf..f5024bb 100644
--- a/src/gui/dialogs/qprogressdialog.cpp
+++ b/src/gui/dialogs/qprogressdialog.cpp
@@ -453,7 +453,7 @@ void QProgressDialog::setCancelButton(QPushButton *cancelButton)
cancelButton->show();
#else
{
- d->cancelAction = new QAction(cancelButton->text(), this);
+ d->cancelAction = new QAction(cancelButton->text(), cancelButton);
d->cancelAction->setSoftKeyRole(QAction::NegativeSoftKey);
connect(d->cancelAction, SIGNAL(triggered()), this, SIGNAL(canceled()));
addAction(d->cancelAction);
diff --git a/src/gui/dialogs/qwizard.cpp b/src/gui/dialogs/qwizard.cpp
index 0f6d353..0102e25 100644
--- a/src/gui/dialogs/qwizard.cpp
+++ b/src/gui/dialogs/qwizard.cpp
@@ -1340,7 +1340,7 @@ bool QWizardPrivate::ensureButton(QWizard::WizardButton which) const
pushButton->setText(buttonDefaultText(wizStyle, which, this));
#ifdef QT_SOFTKEYS_ENABLED
- QAction *softKey = new QAction(pushButton->text(), antiFlickerWidget);
+ QAction *softKey = new QAction(pushButton->text(), pushButton);
QAction::SoftKeyRole softKeyRole;
switch(which) {
case QWizard::NextButton:
diff --git a/src/gui/egl/qegl_qws.cpp b/src/gui/egl/qegl_qws.cpp
index 590b666..df1179a 100644
--- a/src/gui/egl/qegl_qws.cpp
+++ b/src/gui/egl/qegl_qws.cpp
@@ -83,7 +83,8 @@ static QScreen *screenForDevice(QPaintDevice *device)
screenNumber = 0;
screen = screen->subScreens()[screenNumber];
}
- while (screen->classId() == QScreen::ProxyClass) {
+ while (screen->classId() == QScreen::ProxyClass ||
+ screen->classId() == QScreen::TransformedClass) {
screen = static_cast<QProxyScreen *>(screen)->screen();
}
return screen;
diff --git a/src/gui/embedded/directfb.pri b/src/gui/embedded/directfb.pri
index fa4dd68..84253b5 100644
--- a/src/gui/embedded/directfb.pri
+++ b/src/gui/embedded/directfb.pri
@@ -1,7 +1,7 @@
# These defines might be necessary if your DirectFB driver doesn't
# support all of the DirectFB API.
#
-#DEFINES += QT_NO_DIRECTFB_SUBSURFACE
+#DEFINES += QT_DIRECTFB_SUBSURFACE
#DEFINES += QT_DIRECTFB_WINDOW_AS_CURSOR
#DEFINES += QT_NO_DIRECTFB_IMAGEPROVIDER
#DEFINES += QT_DIRECTFB_IMAGEPROVIDER_KEEPALIVE
diff --git a/src/gui/graphicsview/qgraphicsitem.cpp b/src/gui/graphicsview/qgraphicsitem.cpp
index 3069733..45627f6 100644
--- a/src/gui/graphicsview/qgraphicsitem.cpp
+++ b/src/gui/graphicsview/qgraphicsitem.cpp
@@ -663,6 +663,8 @@
#include <private/qpixmap_x11_p.h>
#endif
+#include <private/qgesturemanager_p.h>
+
#include <math.h>
QT_BEGIN_NAMESPACE
@@ -7286,6 +7288,19 @@ QGraphicsObject::QGraphicsObject(QGraphicsItemPrivate &dd, QGraphicsItem *parent
}
/*!
+ Subscribes the graphics object to the given \a gesture for the specified \a context.
+
+ \sa QGestureEvent
+*/
+
+void QGraphicsObject::grabGesture(Qt::GestureType gesture, Qt::GestureContext context)
+{
+ QGraphicsItemPrivate * const d = QGraphicsItem::d_func();
+ d->gestureContext.insert(gesture, context);
+ (void)QGestureManager::instance(); // create a gesture manager
+}
+
+/*!
\property QGraphicsObject::parent
\brief the parent of the item
diff --git a/src/gui/graphicsview/qgraphicsitem.h b/src/gui/graphicsview/qgraphicsitem.h
index e6e324a..2665235 100644
--- a/src/gui/graphicsview/qgraphicsitem.h
+++ b/src/gui/graphicsview/qgraphicsitem.h
@@ -464,6 +464,7 @@ private:
friend class QGraphicsSceneBspTree;
friend class QGraphicsView;
friend class QGraphicsViewPrivate;
+ friend class QGraphicsObject;
friend class QGraphicsWidget;
friend class QGraphicsWidgetPrivate;
friend class QGraphicsProxyWidgetPrivate;
@@ -473,6 +474,7 @@ private:
friend class QGraphicsSceneBspTreeIndexPrivate;
friend class QGraphicsItemEffectSourcePrivate;
friend class QGraphicsTransformPrivate;
+ friend class QGestureManager;
friend class ::tst_QGraphicsItem;
friend bool qt_closestLeaf(const QGraphicsItem *, const QGraphicsItem *);
friend bool qt_closestItemFirst(const QGraphicsItem *, const QGraphicsItem *);
@@ -553,6 +555,8 @@ public:
using QObject::children;
#endif
+ void grabGesture(Qt::GestureType type, Qt::GestureContext context = Qt::WidgetWithChildrenGesture);
+
Q_SIGNALS:
void parentChanged();
void opacityChanged();
diff --git a/src/gui/graphicsview/qgraphicsitem_p.h b/src/gui/graphicsview/qgraphicsitem_p.h
index 51bfea1..6550362 100644
--- a/src/gui/graphicsview/qgraphicsitem_p.h
+++ b/src/gui/graphicsview/qgraphicsitem_p.h
@@ -450,6 +450,7 @@ public:
QGraphicsItem *focusScopeItem;
Qt::InputMethodHints imHints;
QGraphicsItem::PanelModality panelModality;
+ QMap<Qt::GestureType, Qt::GestureContext> gestureContext;
// Packed 32 bits
quint32 acceptedMouseButtons : 5;
diff --git a/src/gui/graphicsview/qgraphicsproxywidget.cpp b/src/gui/graphicsview/qgraphicsproxywidget.cpp
index 15b9ff3..b7a3962 100644
--- a/src/gui/graphicsview/qgraphicsproxywidget.cpp
+++ b/src/gui/graphicsview/qgraphicsproxywidget.cpp
@@ -973,7 +973,7 @@ void QGraphicsProxyWidget::hideEvent(QHideEvent *event)
void QGraphicsProxyWidget::contextMenuEvent(QGraphicsSceneContextMenuEvent *event)
{
Q_D(QGraphicsProxyWidget);
- if (!event || !d->widget || !d->widget->isVisible())
+ if (!event || !d->widget || !d->widget->isVisible() || !hasFocus())
return;
// Find widget position and receiver.
diff --git a/src/gui/graphicsview/qgraphicsscene.cpp b/src/gui/graphicsview/qgraphicsscene.cpp
index 961f44f..a624b10 100644
--- a/src/gui/graphicsview/qgraphicsscene.cpp
+++ b/src/gui/graphicsview/qgraphicsscene.cpp
@@ -420,8 +420,12 @@ void QGraphicsScenePrivate::unregisterTopLevelItem(QGraphicsItem *item)
*/
void QGraphicsScenePrivate::_q_polishItems()
{
+ QSet<QGraphicsItem *>::Iterator it;
const QVariant booleanTrueVariant(true);
- foreach (QGraphicsItem *item, unpolishedItems) {
+ while (!unpolishedItems.isEmpty()) {
+ it = unpolishedItems.begin();
+ QGraphicsItem *item = *it;
+ unpolishedItems.erase(it);
if (!item->d_ptr->explicitlyHidden) {
item->itemChange(QGraphicsItem::ItemVisibleChange, booleanTrueVariant);
item->itemChange(QGraphicsItem::ItemVisibleHasChanged, booleanTrueVariant);
@@ -431,7 +435,6 @@ void QGraphicsScenePrivate::_q_polishItems()
QApplication::sendEvent((QGraphicsWidget *)item, &event);
}
}
- unpolishedItems.clear();
}
void QGraphicsScenePrivate::_q_processDirtyItems()
@@ -549,7 +552,7 @@ void QGraphicsScenePrivate::removeItemHelper(QGraphicsItem *item)
selectedItems.remove(item);
hoverItems.removeAll(item);
cachedItemsUnderMouse.removeAll(item);
- unpolishedItems.removeAll(item);
+ unpolishedItems.remove(item);
resetDirtyItem(item);
//We remove all references of item from the sceneEventFilter arrays
@@ -2484,7 +2487,7 @@ void QGraphicsScene::addItem(QGraphicsItem *item)
if (!item->d_ptr->explicitlyHidden) {
if (d->unpolishedItems.isEmpty())
QMetaObject::invokeMethod(this, "_q_polishItems", Qt::QueuedConnection);
- d->unpolishedItems << item;
+ d->unpolishedItems.insert(item);
}
// Reenable selectionChanged() for individual items
@@ -5294,7 +5297,7 @@ void QGraphicsScene::setActivePanel(QGraphicsItem *item)
/*!
\since 4.4
- Returns the current active window, or 0 if there is no window is currently
+ Returns the current active window, or 0 if no window is currently
active.
\sa QGraphicsScene::setActiveWindow()
@@ -5475,11 +5478,11 @@ void QGraphicsScenePrivate::touchEventHandler(QTouchEvent *sceneTouchEvent)
}
if (itemsNeedingEvents.isEmpty()) {
- sceneTouchEvent->ignore();
+ sceneTouchEvent->accept();
return;
}
- bool acceptSceneTouchEvent = false;
+ bool ignoreSceneTouchEvent = true;
QHash<QGraphicsItem *, StatesAndTouchPoints>::ConstIterator it = itemsNeedingEvents.constBegin();
const QHash<QGraphicsItem *, StatesAndTouchPoints>::ConstIterator end = itemsNeedingEvents.constEnd();
for (; it != end; ++it) {
@@ -5522,19 +5525,20 @@ void QGraphicsScenePrivate::touchEventHandler(QTouchEvent *sceneTouchEvent)
item->d_ptr->acceptedTouchBeginEvent = true;
bool res = sendTouchBeginEvent(item, &touchEvent)
&& touchEvent.isAccepted();
- acceptSceneTouchEvent = acceptSceneTouchEvent || res;
+ if (!res)
+ ignoreSceneTouchEvent = false;
break;
}
default:
if (item->d_ptr->acceptedTouchBeginEvent) {
updateTouchPointsForItem(item, &touchEvent);
(void) sendEvent(item, &touchEvent);
- acceptSceneTouchEvent = true;
+ ignoreSceneTouchEvent = false;
}
break;
}
}
- sceneTouchEvent->setAccepted(acceptSceneTouchEvent);
+ sceneTouchEvent->setAccepted(ignoreSceneTouchEvent);
}
bool QGraphicsScenePrivate::sendTouchBeginEvent(QGraphicsItem *origin, QTouchEvent *touchEvent)
diff --git a/src/gui/graphicsview/qgraphicsscene.h b/src/gui/graphicsview/qgraphicsscene.h
index ba47530..d6d48d7 100644
--- a/src/gui/graphicsview/qgraphicsscene.h
+++ b/src/gui/graphicsview/qgraphicsscene.h
@@ -311,6 +311,7 @@ private:
friend class QGraphicsSceneBspTreeIndex;
friend class QGraphicsSceneBspTreeIndexPrivate;
friend class QGraphicsItemEffectSourcePrivate;
+ friend class QGesture;
};
Q_DECLARE_OPERATORS_FOR_FLAGS(QGraphicsScene::SceneLayers)
diff --git a/src/gui/graphicsview/qgraphicsscene_p.h b/src/gui/graphicsview/qgraphicsscene_p.h
index 5000860..8073695 100644
--- a/src/gui/graphicsview/qgraphicsscene_p.h
+++ b/src/gui/graphicsview/qgraphicsscene_p.h
@@ -108,7 +108,7 @@ public:
QPainterPath selectionArea;
int selectionChanging;
QSet<QGraphicsItem *> selectedItems;
- QList<QGraphicsItem *> unpolishedItems;
+ QSet<QGraphicsItem *> unpolishedItems;
QList<QGraphicsItem *> topLevelItems;
bool needSortTopLevelItems;
bool holesInTopLevelSiblingIndex;
diff --git a/src/gui/image/qiconloader.cpp b/src/gui/image/qiconloader.cpp
index 5412e11..46c5431 100644
--- a/src/gui/image/qiconloader.cpp
+++ b/src/gui/image/qiconloader.cpp
@@ -78,6 +78,8 @@ static QString fallbackTheme()
return X11->desktopVersion >= 4
? QString::fromLatin1("oxygen")
: QString::fromLatin1("crystalsvg");
+ } else {
+ return QLatin1String("hicolor");
}
#endif
return QString();
@@ -87,6 +89,8 @@ QIconLoader::QIconLoader() :
m_themeKey(1), m_supportsSvg(false)
{
m_systemTheme = qt_guiPlatformPlugin()->systemIconThemeName();
+ if (m_systemTheme.isEmpty())
+ m_systemTheme = fallbackTheme();
QFactoryLoader iconFactoryLoader(QIconEngineFactoryInterfaceV2_iid,
QLatin1String("/iconengines"),
@@ -107,6 +111,8 @@ void QIconLoader::updateSystemTheme()
// Only change if this is not explicitly set by the user
if (m_userTheme.isEmpty()) {
QString theme = qt_guiPlatformPlugin()->systemIconThemeName();
+ if (theme.isEmpty())
+ theme = fallbackTheme();
if (theme != m_systemTheme) {
m_systemTheme = theme;
invalidateKey();
diff --git a/src/gui/image/qpixmap_s60.cpp b/src/gui/image/qpixmap_s60.cpp
index 554c0f3..9ae8d72 100644
--- a/src/gui/image/qpixmap_s60.cpp
+++ b/src/gui/image/qpixmap_s60.cpp
@@ -716,6 +716,8 @@ void QS60PixmapData::beginDataAccess()
void QS60PixmapData::endDataAccess(bool readOnly) const
{
+ Q_UNUSED(readOnly);
+
if(!cfbsBitmap)
return;
diff --git a/src/gui/itemviews/qabstractitemview.cpp b/src/gui/itemviews/qabstractitemview.cpp
index 37f4184..d91cedd 100644
--- a/src/gui/itemviews/qabstractitemview.cpp
+++ b/src/gui/itemviews/qabstractitemview.cpp
@@ -1697,7 +1697,7 @@ void QAbstractItemView::mouseMoveEvent(QMouseEvent *event)
if ((event->buttons() & Qt::LeftButton) && d->selectionAllowed(index) && d->selectionModel) {
setState(DragSelectingState);
QItemSelectionModel::SelectionFlags command = selectionCommand(index, event);
- if (command.testFlag(QItemSelectionModel::Toggle)) {
+ if (d->ctrlDragSelectionFlag != QItemSelectionModel::NoUpdate && command.testFlag(QItemSelectionModel::Toggle)) {
command &= ~QItemSelectionModel::Toggle;
command |= d->ctrlDragSelectionFlag;
}
@@ -2185,6 +2185,9 @@ void QAbstractItemView::keyPressEvent(QKeyEvent *event)
} else {
d->selectionModel->setCurrentIndex(newCurrent, command);
d->pressedPosition = visualRect(newCurrent).center() + d->offset();
+ // We copy the same behaviour as for mousePressEvent().
+ QRect rect(d->pressedPosition - d->offset(), QSize(1, 1));
+ setSelection(rect, command);
}
return;
}
@@ -3026,7 +3029,7 @@ void QAbstractItemView::update(const QModelIndex &index)
//this test is important for peformance reason
//For example in dataChanged we simply update all the cells without checking
//it can be a major bottleneck to update rects that aren't even part of the viewport
- if (d->viewport->geometry().intersects(rect))
+ if (d->viewport->rect().intersects(rect))
d->viewport->update(rect);
}
}
diff --git a/src/gui/itemviews/qheaderview.cpp b/src/gui/itemviews/qheaderview.cpp
index a754579..fc9820f 100644
--- a/src/gui/itemviews/qheaderview.cpp
+++ b/src/gui/itemviews/qheaderview.cpp
@@ -524,10 +524,8 @@ QSize QHeaderView::sizeHint() const
Q_D(const QHeaderView);
if (d->cachedSizeHint.isValid())
return d->cachedSizeHint;
- int width = 0;
- int height = 0;
+ d->cachedSizeHint = QSize(0, 0); //reinitialize the cached size hint
const int sectionCount = count();
- d->executePostedLayout();
// get size hint for the first n sections
int i = 0;
diff --git a/src/gui/itemviews/qtableview.cpp b/src/gui/itemviews/qtableview.cpp
index 15bd445..a610b73 100644
--- a/src/gui/itemviews/qtableview.cpp
+++ b/src/gui/itemviews/qtableview.cpp
@@ -779,8 +779,6 @@ void QTableViewPrivate::drawAndClipSpans(const QRegion &area, QPainter *painter,
foreach (QSpanCollection::Span *span, visibleSpans) {
int row = span->top();
int col = span->left();
- if (isHidden(row, col))
- continue;
QModelIndex index = model->index(row, col, root);
if (!index.isValid())
continue;
@@ -1119,6 +1117,9 @@ void QTableView::setHorizontalHeader(QHeaderView *header)
connect(d->horizontalHeader, SIGNAL(sectionHandleDoubleClicked(int)),
this, SLOT(resizeColumnToContents(int)));
connect(d->horizontalHeader, SIGNAL(geometriesChanged()), this, SLOT(updateGeometries()));
+
+ //update the sorting enabled states on the new header
+ setSortingEnabled(d->sortingEnabled);
}
/*!
@@ -1480,12 +1481,30 @@ QModelIndex QTableView::moveCursor(CursorAction cursorAction, Qt::KeyboardModifi
++column;
while (isRowHidden(d->logicalRow(row)) && row < bottom)
++row;
+ d->visualCursor = QPoint(column, row);
return d->model->index(d->logicalRow(row), d->logicalColumn(column), d->root);
}
- int visualRow = d->visualRow(current.row());
+ // Update visual cursor if current index has changed.
+ QPoint visualCurrent(d->visualColumn(current.column()), d->visualRow(current.row()));
+ if (visualCurrent != d->visualCursor) {
+ if (d->hasSpans()) {
+ QSpanCollection::Span span = d->span(current.row(), current.column());
+ if (span.top() > d->visualCursor.y() || d->visualCursor.y() > span.bottom()
+ || span.left() > d->visualCursor.x() || d->visualCursor.x() > span.right())
+ d->visualCursor = visualCurrent;
+ } else {
+ d->visualCursor = visualCurrent;
+ }
+ }
+
+ int visualRow = d->visualCursor.y();
+ if (visualRow > bottom)
+ visualRow = bottom;
Q_ASSERT(visualRow != -1);
- int visualColumn = d->visualColumn(current.column());
+ int visualColumn = d->visualCursor.x();
+ if (visualColumn > right)
+ visualColumn = right;
Q_ASSERT(visualColumn != -1);
if (isRightToLeft()) {
@@ -1496,22 +1515,33 @@ QModelIndex QTableView::moveCursor(CursorAction cursorAction, Qt::KeyboardModifi
}
switch (cursorAction) {
- case MoveUp:
+ case MoveUp: {
+ int originalRow = visualRow;
#ifdef QT_KEYPAD_NAVIGATION
if (QApplication::keypadNavigationEnabled() && visualRow == 0)
visualRow = d->visualRow(model()->rowCount() - 1) + 1;
+ // FIXME? visualRow = bottom + 1;
#endif
- --visualRow;
- while (visualRow > 0 && d->isVisualRowHiddenOrDisabled(visualRow, visualColumn))
+ int r = d->logicalRow(visualRow);
+ int c = d->logicalColumn(visualColumn);
+ if (r != -1 && d->hasSpans()) {
+ QSpanCollection::Span span = d->span(r, c);
+ if (span.width() > 1 || span.height() > 1)
+ visualRow = d->visualRow(span.top());
+ }
+ while (visualRow >= 0) {
--visualRow;
- if (d->hasSpans()) {
- int row = d->logicalRow(visualRow);
- QSpanCollection::Span span = d->span(row, current.column());
- visualRow = d->visualRow(span.top());
- visualColumn = d->visualColumn(span.left());
+ r = d->logicalRow(visualRow);
+ c = d->logicalColumn(visualColumn);
+ if (r == -1 || (!isRowHidden(r) && d->isCellEnabled(r, c)))
+ break;
}
+ if (visualRow < 0)
+ visualRow = originalRow;
break;
- case MoveDown:
+ }
+ case MoveDown: {
+ int originalRow = visualRow;
if (d->hasSpans()) {
QSpanCollection::Span span = d->span(current.row(), current.column());
visualRow = d->visualRow(d->rowSpanEndLogical(span.top(), span.height()));
@@ -1520,71 +1550,106 @@ QModelIndex QTableView::moveCursor(CursorAction cursorAction, Qt::KeyboardModifi
if (QApplication::keypadNavigationEnabled() && visualRow >= bottom)
visualRow = -1;
#endif
- ++visualRow;
- while (visualRow < bottom && d->isVisualRowHiddenOrDisabled(visualRow, visualColumn))
+ int r = d->logicalRow(visualRow);
+ int c = d->logicalColumn(visualColumn);
+ if (r != -1 && d->hasSpans()) {
+ QSpanCollection::Span span = d->span(r, c);
+ if (span.width() > 1 || span.height() > 1)
+ visualRow = d->visualRow(d->rowSpanEndLogical(span.top(), span.height()));
+ }
+ while (visualRow <= bottom) {
++visualRow;
- if (d->hasSpans()) {
- int row = d->logicalRow(visualRow);
- QSpanCollection::Span span = d->span(row, current.column());
- visualColumn = d->visualColumn(span.left());
+ r = d->logicalRow(visualRow);
+ c = d->logicalColumn(visualColumn);
+ if (r == -1 || (!isRowHidden(r) && d->isCellEnabled(r, c)))
+ break;
}
+ if (visualRow > bottom)
+ visualRow = originalRow;
break;
- case MovePrevious: {
- int left = 0;
- while (d->isVisualColumnHiddenOrDisabled(visualRow, left) && left < right)
- ++left;
- if (visualColumn == left) {
- visualColumn = right;
- int top = 0;
- while (top < bottom && d->isVisualRowHiddenOrDisabled(top, visualColumn))
- ++top;
- if (visualRow == top)
+ }
+ case MovePrevious:
+ case MoveLeft: {
+ int originalRow = visualRow;
+ int originalColumn = visualColumn;
+ bool firstTime = true;
+ bool looped = false;
+ bool wrapped = false;
+ do {
+ int r = d->logicalRow(visualRow);
+ int c = d->logicalColumn(visualColumn);
+ if (firstTime && c != -1 && d->hasSpans()) {
+ firstTime = false;
+ QSpanCollection::Span span = d->span(r, c);
+ if (span.width() > 1 || span.height() > 1)
+ visualColumn = d->visualColumn(span.left());
+ }
+ while (visualColumn >= 0) {
+ --visualColumn;
+ r = d->logicalRow(visualRow);
+ c = d->logicalColumn(visualColumn);
+ if (r == -1 || c == -1 || (!isRowHidden(r) && !isColumnHidden(c) && d->isCellEnabled(r, c)))
+ break;
+ if (wrapped && (originalRow < visualRow || (originalRow == visualRow && originalColumn <= visualColumn))) {
+ looped = true;
+ break;
+ }
+ }
+ if (cursorAction == MoveLeft || visualColumn >= 0)
+ break;
+ visualColumn = right + 1;
+ if (visualRow == 0) {
+ wrapped == true;
visualRow = bottom;
- else
- --visualRow;
- while (visualRow > 0 && d->isVisualRowHiddenOrDisabled(visualRow, visualColumn))
+ } else {
--visualRow;
- break;
- } // else MoveLeft
- }
- case MoveLeft:
- --visualColumn;
- while (visualColumn > 0 && d->isVisualColumnHiddenOrDisabled(visualRow, visualColumn))
- --visualColumn;
- if (d->hasSpans()) {
- int column = d->logicalColumn(visualColumn);
- QSpanCollection::Span span = d->span(current.row(), column);
- visualRow = d->visualRow(span.top());
- visualColumn = d->visualColumn(span.left());
- }
+ }
+ } while (!looped);
+ if (visualColumn < 0)
+ visualColumn = originalColumn;
break;
+ }
case MoveNext:
- if (visualColumn == right) {
- visualColumn = 0;
- while (visualColumn < right && d->isVisualColumnHiddenOrDisabled(visualRow, visualColumn))
+ case MoveRight: {
+ int originalRow = visualRow;
+ int originalColumn = visualColumn;
+ bool firstTime = true;
+ bool looped = false;
+ bool wrapped = false;
+ do {
+ int r = d->logicalRow(visualRow);
+ int c = d->logicalColumn(visualColumn);
+ if (firstTime && c != -1 && d->hasSpans()) {
+ firstTime = false;
+ QSpanCollection::Span span = d->span(r, c);
+ if (span.width() > 1 || span.height() > 1)
+ visualColumn = d->visualColumn(d->columnSpanEndLogical(span.left(), span.width()));
+ }
+ while (visualColumn <= right) {
++visualColumn;
- if (visualRow == bottom)
+ r = d->logicalRow(visualRow);
+ c = d->logicalColumn(visualColumn);
+ if (r == -1 || c == -1 || (!isRowHidden(r) && !isColumnHidden(c) && d->isCellEnabled(r, c)))
+ break;
+ if (wrapped && (originalRow > visualRow || (originalRow == visualRow && originalColumn >= visualColumn))) {
+ looped = true;
+ break;
+ }
+ }
+ if (cursorAction == MoveRight || visualColumn <= right)
+ break;
+ visualColumn = -1;
+ if (visualRow == bottom) {
+ wrapped = true;
visualRow = 0;
- else
- ++visualRow;
- while (visualRow < bottom && d->isVisualRowHiddenOrDisabled(visualRow, visualColumn))
+ } else {
++visualRow;
- break;
- } // else MoveRight
- case MoveRight:
- if (d->hasSpans()) {
- QSpanCollection::Span span = d->span(current.row(), current.column());
- visualColumn = d->visualColumn(d->columnSpanEndLogical(span.left(), span.width()));
- }
- ++visualColumn;
- while (visualColumn < right && d->isVisualColumnHiddenOrDisabled(visualRow, visualColumn))
- ++visualColumn;
- if (d->hasSpans()) {
- int column = d->logicalColumn(visualColumn);
- QSpanCollection::Span span = d->span(current.row(), column);
- visualRow = d->visualRow(span.top());
- }
+ }
+ } while (!looped);
+ if (visualColumn > right)
+ visualColumn = originalColumn;
break;
+ }
case MoveHome:
visualColumn = 0;
while (visualColumn < right && d->isVisualColumnHiddenOrDisabled(visualRow, visualColumn))
@@ -1613,14 +1678,15 @@ QModelIndex QTableView::moveCursor(CursorAction cursorAction, Qt::KeyboardModifi
return d->model->index(newRow, current.column(), d->root);
}}
+ d->visualCursor = QPoint(visualColumn, visualRow);
int logicalRow = d->logicalRow(visualRow);
int logicalColumn = d->logicalColumn(visualColumn);
if (!d->model->hasIndex(logicalRow, logicalColumn, d->root))
return QModelIndex();
QModelIndex result = d->model->index(logicalRow, logicalColumn, d->root);
- if (!isIndexHidden(result) && d->isIndexEnabled(result))
- return d->model->index(logicalRow, logicalColumn, d->root);
+ if (!d->isRowHidden(logicalRow) && !d->isColumnHidden(logicalColumn) && d->isIndexEnabled(result))
+ return result;
return QModelIndex();
}
@@ -2375,7 +2441,8 @@ bool QTableView::isCornerButtonEnabled() const
QRect QTableView::visualRect(const QModelIndex &index) const
{
Q_D(const QTableView);
- if (!d->isIndexValid(index) || index.parent() != d->root || isIndexHidden(index) )
+ if (!d->isIndexValid(index) || index.parent() != d->root
+ || (!d->hasSpans() && isIndexHidden(index)))
return QRect();
d->executePostedLayout();
diff --git a/src/gui/itemviews/qtableview_p.h b/src/gui/itemviews/qtableview_p.h
index c785bd7..9fa14c2 100644
--- a/src/gui/itemviews/qtableview_p.h
+++ b/src/gui/itemviews/qtableview_p.h
@@ -135,7 +135,8 @@ public:
rowSectionAnchor(-1), columnSectionAnchor(-1),
columnResizeTimerID(0), rowResizeTimerID(0),
horizontalHeader(0), verticalHeader(0),
- sortingEnabled(false), geometryRecursionBlock(false)
+ sortingEnabled(false), geometryRecursionBlock(false),
+ visualCursor(QPoint())
{
wrapItemText = true;
#ifndef QT_NO_DRAGANDDROP
@@ -183,6 +184,7 @@ public:
QWidget *cornerWidget;
bool sortingEnabled;
bool geometryRecursionBlock;
+ QPoint visualCursor; // (Row,column) cell coordinates to track through span navigation.
QSpanCollection spans;
diff --git a/src/gui/itemviews/qtablewidget.cpp b/src/gui/itemviews/qtablewidget.cpp
index a086498..21c4e0a 100644
--- a/src/gui/itemviews/qtablewidget.cpp
+++ b/src/gui/itemviews/qtablewidget.cpp
@@ -571,6 +571,8 @@ void QTableModel::ensureSorted(int column, Qt::SortOrder order,
colItems.remove(oldRow);
vit = sortedInsertionIterator(vit, colItems.end(), order, item);
int newRow = qMax((int)(vit - colItems.begin()), 0);
+ if ((newRow < oldRow) && !(*item < *colItems.at(oldRow - 1)) && !(*colItems.at(oldRow - 1) < *item))
+ newRow = oldRow;
vit = colItems.insert(vit, item);
if (newRow != oldRow) {
changed = true;
diff --git a/src/gui/itemviews/qtreewidget.cpp b/src/gui/itemviews/qtreewidget.cpp
index 06342d8..040c498 100644
--- a/src/gui/itemviews/qtreewidget.cpp
+++ b/src/gui/itemviews/qtreewidget.cpp
@@ -623,7 +623,7 @@ void QTreeModel::ensureSorted(int column, Qt::SortOrder order,
lit = sortedInsertionIterator(lit, lst.end(), order, item);
int newRow = qMax(lit - lst.begin(), 0);
- if ((newRow < oldRow) && !(*item < *lst.at(oldRow - 1)))
+ if ((newRow < oldRow) && !(*item < *lst.at(oldRow - 1)) && !(*lst.at(oldRow - 1) < *item ))
newRow = oldRow;
lit = lst.insert(lit, item);
diff --git a/src/gui/kernel/kernel.pri b/src/gui/kernel/kernel.pri
index 760d73c..53c2611 100644
--- a/src/gui/kernel/kernel.pri
+++ b/src/gui/kernel/kernel.pri
@@ -45,10 +45,11 @@ HEADERS += \
kernel/qkeymapper_p.h \
kernel/qgesture.h \
kernel/qgesture_p.h \
- kernel/qstandardgestures.h \
- kernel/qstandardgestures_p.h \
- kernel/qsoftkeymanager_p.h \
- kernel/qguiplatformplugin_p.h
+ kernel/qstandardgestures_p.h \
+ kernel/qgesturerecognizer.h \
+ kernel/qgesturemanager_p.h \
+ kernel/qsoftkeymanager_p.h \
+ kernel/qguiplatformplugin_p.h
SOURCES += \
kernel/qaction.cpp \
@@ -79,13 +80,18 @@ SOURCES += \
kernel/qwidgetaction.cpp \
kernel/qkeymapper.cpp \
kernel/qgesture.cpp \
- kernel/qstandardgestures.cpp \
- kernel/qsoftkeymanager.cpp \
- kernel/qguiplatformplugin.cpp
+ kernel/qstandardgestures.cpp \
+ kernel/qgesturerecognizer.cpp \
+ kernel/qgesturemanager.cpp \
+ kernel/qsoftkeymanager.cpp \
+ kernel/qguiplatformplugin.cpp
win32 {
DEFINES += QT_NO_DIRECTDRAW
+ HEADERS += \
+ kernel/qwinnativepangesturerecognizer_win_p.h
+
SOURCES += \
kernel/qapplication_win.cpp \
kernel/qclipboard_win.cpp \
@@ -96,7 +102,8 @@ win32 {
kernel/qsound_win.cpp \
kernel/qwidget_win.cpp \
kernel/qole_win.cpp \
- kernel/qkeymapper_win.cpp
+ kernel/qkeymapper_win.cpp \
+ kernel/qwinnativepangesturerecognizer_win.cpp
!contains(DEFINES, QT_NO_DIRECTDRAW):LIBS += ddraw.lib
}
@@ -198,6 +205,7 @@ embedded {
qcocoaview_mac_p.h \
qcocoaapplication_mac_p.h \
qcocoaapplicationdelegate_mac_p.h \
+ qmacgesturerecognizer_mac_p.h \
qmultitouch_mac_p.h
OBJECTIVE_SOURCES += \
@@ -217,7 +225,8 @@ embedded {
kernel/qdesktopwidget_mac.mm \
kernel/qeventdispatcher_mac.mm \
kernel/qcocoawindowcustomthemeframe_mac.mm \
- kernel/qmultitouch_mac.mm \
+ kernel/qmacgesturerecognizer_mac.mm \
+ kernel/qmultitouch_mac.mm
HEADERS += \
kernel/qt_cocoa_helpers_mac_p.h \
diff --git a/src/gui/kernel/qapplication.cpp b/src/gui/kernel/qapplication.cpp
index 43addb6..6f6d706 100644
--- a/src/gui/kernel/qapplication.cpp
+++ b/src/gui/kernel/qapplication.cpp
@@ -99,6 +99,9 @@
#include "qapplication.h"
+#include "qgesture.h"
+#include "private/qgesturemanager_p.h"
+
#ifndef QT_NO_LIBRARY
#include "qlibrary.h"
#endif
@@ -154,6 +157,14 @@ bool QApplicationPrivate::autoSipEnabled = false;
bool QApplicationPrivate::autoSipEnabled = true;
#endif
+QGestureManager* QGestureManager::instance()
+{
+ QApplicationPrivate *d = qApp->d_func();
+ if (!d->gestureManager)
+ d->gestureManager = new QGestureManager(qApp);
+ return d->gestureManager;
+}
+
QApplicationPrivate::QApplicationPrivate(int &argc, char **argv, QApplication::Type type)
: QCoreApplicationPrivate(argc, argv)
{
@@ -177,6 +188,8 @@ QApplicationPrivate::QApplicationPrivate(int &argc, char **argv, QApplication::T
directPainters = 0;
#endif
+ gestureManager = 0;
+
if (!self)
self = this;
}
@@ -930,7 +943,7 @@ void QApplicationPrivate::initialize()
graphics_system = QGraphicsSystemFactory::create(graphics_system_name);
#endif
#ifndef QT_NO_WHEELEVENT
-#ifdef Q_OS_MAC
+#ifdef Q_OS_MAC
QApplicationPrivate::wheel_scroll_lines = 1;
#else
QApplicationPrivate::wheel_scroll_lines = 3;
@@ -1021,11 +1034,11 @@ QApplication::~QApplication()
d->eventDispatcher->closingDown();
d->eventDispatcher = 0;
+ QApplicationPrivate::is_app_closing = true;
+ QApplicationPrivate::is_app_running = false;
delete qt_desktopWidget;
qt_desktopWidget = 0;
- QApplicationPrivate::is_app_closing = true;
- QApplicationPrivate::is_app_running = false;
#ifndef QT_NO_CLIPBOARD
delete qt_clipboard;
@@ -3632,6 +3645,13 @@ bool QApplication::notify(QObject *receiver, QEvent *e)
#endif // !QT_NO_WHEELEVENT || !QT_NO_TABLETEVENT
}
+ // walk through parents and check for gestures
+ if (d->gestureManager) {
+ if (d->gestureManager->filterEvent(receiver, e))
+ return true;
+ }
+
+
// User input and window activation makes tooltips sleep
switch (e->type()) {
case QEvent::Wheel:
@@ -4133,6 +4153,65 @@ bool QApplication::notify(QObject *receiver, QEvent *e)
}
break;
}
+ case QEvent::Gesture:
+ case QEvent::GestureOverride:
+ {
+ if (receiver->isWidgetType()) {
+ QWidget *w = static_cast<QWidget *>(receiver);
+ QGestureEvent *gestureEvent = static_cast<QGestureEvent *>(e);
+ QList<QGesture *> allGestures = gestureEvent->allGestures();
+
+ bool eventAccepted = gestureEvent->isAccepted();
+ bool wasAccepted = eventAccepted;
+ while (w) {
+ // send only gestures the widget expects
+ QList<QGesture *> gestures;
+ QWidgetPrivate *wd = w->d_func();
+ for (int i = 0; i < allGestures.size();) {
+ QGesture *g = allGestures.at(i);
+ Qt::GestureType type = g->gestureType();
+ if (wd->gestureContext.contains(type)) {
+ allGestures.removeAt(i);
+ gestures.append(g);
+ gestureEvent->setAccepted(g, false);
+ } else {
+ ++i;
+ }
+ }
+ if (!gestures.isEmpty()) {
+ QGestureEvent ge(gestures);
+ ge.t = gestureEvent->t;
+ ge.spont = gestureEvent->spont;
+ ge.m_accept = wasAccepted;
+ res = d->notify_helper(w, &ge);
+ gestureEvent->spont = false;
+ eventAccepted = ge.isAccepted();
+ if (res && eventAccepted)
+ break;
+ if (!eventAccepted) {
+ // ### two ways to ignore the event/gesture
+
+ // if the whole event wasn't accepted, put back those
+ // gestures that were not accepted.
+ for (int i = 0; i < gestures.size(); ++i) {
+ QGesture *g = gestures.at(i);
+ if (!ge.isAccepted(g))
+ allGestures.append(g);
+ }
+ }
+ }
+ if (allGestures.isEmpty())
+ break;
+ if (w->isWindow())
+ break;
+ w = w->parentWidget();
+ }
+ gestureEvent->m_accept = eventAccepted;
+ } else {
+ res = d->notify_helper(receiver, e);
+ }
+ break;
+ }
default:
res = d->notify_helper(receiver, e);
break;
@@ -5540,6 +5619,37 @@ Q_GUI_EXPORT void qt_translateRawTouchEvent(QWidget *window,
QApplicationPrivate::translateRawTouchEvent(window, deviceType, touchPoints);
}
+/*!
+ \since 4.6
+
+ Registers the given \a recognizer in the gesture framework and returns a gesture ID
+ for it.
+
+ The application takes ownership of the \a recognizer and returns the gesture type
+ ID associated with it. For gesture recognizers which handle custom QGesture
+ objects (i.e., those which return Qt::CustomGesture in a QGesture::gestureType()
+ function) the return value is a gesture ID between Qt::CustomGesture and
+ Qt::LastGestureType, inclusive.
+
+ \sa unregisterGestureRecognizer(), QGestureRecognizer::createGesture(), QGesture
+*/
+Qt::GestureType QApplication::registerGestureRecognizer(QGestureRecognizer *recognizer)
+{
+ return QGestureManager::instance()->registerGestureRecognizer(recognizer);
+}
+
+/*!
+ \since 4.6
+
+ Unregisters all gesture recognizers of the specified \a type.
+
+ \sa registerGestureRecognizer()
+*/
+void QApplication::unregisterGestureRecognizer(Qt::GestureType type)
+{
+ QGestureManager::instance()->unregisterGestureRecognizer(type);
+}
+
QT_END_NAMESPACE
#include "moc_qapplication.cpp"
diff --git a/src/gui/kernel/qapplication.h b/src/gui/kernel/qapplication.h
index 5f21a56..12b398d 100644
--- a/src/gui/kernel/qapplication.h
+++ b/src/gui/kernel/qapplication.h
@@ -86,6 +86,7 @@ class QDecoration;
class QApplication;
class QApplicationPrivate;
+class QGestureRecognizer;
#if defined(qApp)
#undef qApp
#endif
@@ -289,6 +290,9 @@ public:
static Qt::NavigationMode navigationMode();
#endif
+ Qt::GestureType registerGestureRecognizer(QGestureRecognizer *recognizer);
+ void unregisterGestureRecognizer(Qt::GestureType type);
+
Q_SIGNALS:
void lastWindowClosed();
void focusChanged(QWidget *old, QWidget *now);
@@ -400,6 +404,7 @@ private:
friend class QDirectPainter;
friend class QDirectPainterPrivate;
#endif
+ friend class QGestureManager;
#if defined(Q_WS_MAC) || defined(Q_WS_X11)
Q_PRIVATE_SLOT(d_func(), void _q_alertTimeOut())
diff --git a/src/gui/kernel/qapplication_p.h b/src/gui/kernel/qapplication_p.h
index 95b6d28..2d3d18c 100644
--- a/src/gui/kernel/qapplication_p.h
+++ b/src/gui/kernel/qapplication_p.h
@@ -83,8 +83,8 @@ class QGraphicsSystem;
class QInputContext;
class QObject;
class QWidget;
-class QGestureManager;
class QSocketNotifier;
+class QGestureManager;
extern bool qt_is_gui_used;
#ifndef QT_NO_CLIPBOARD
@@ -265,20 +265,6 @@ typedef struct tagGESTURECONFIG
#endif // Q_WS_WIN
-class QPanGesture;
-class QPinchGesture;
-class QSwipeGesture;
-
-struct QStandardGestures
-{
- QPanGesture *pan;
- QPinchGesture *pinch;
- QSwipeGesture *swipe;
-
- QStandardGestures() : pan(0), pinch(0), swipe(0) { }
-};
-
-
class QScopedLoopLevelCounter
{
QThreadData *threadData;
@@ -522,6 +508,8 @@ public:
void sendSyntheticEnterLeave(QWidget *widget);
#endif
+ QGestureManager *gestureManager;
+
QMap<int, QWidget *> widgetForTouchPointId;
QMap<int, QTouchEvent::TouchPoint> appCurrentTouchPoints;
static void updateTouchPointsForWidget(QWidget *widget, QTouchEvent *touchEvent);
@@ -536,9 +524,6 @@ public:
QTouchEvent::DeviceType deviceType,
const QList<QTouchEvent::TouchPoint> &touchPoints);
- typedef QMap<QWidget*, QStandardGestures> WidgetStandardGesturesMap;
- WidgetStandardGesturesMap widgetGestures;
-
#if defined(Q_WS_WIN)
static PtrRegisterTouchWindow RegisterTouchWindow;
static PtrGetTouchInputInfo GetTouchInputInfo;
@@ -555,7 +540,6 @@ public:
PtrBeginPanningFeedback BeginPanningFeedback;
PtrUpdatePanningFeedback UpdatePanningFeedback;
PtrEndPanningFeedback EndPanningFeedback;
- QWidget *gestureWidget;
#endif
#ifdef QT_RX71_MULTITOUCH
diff --git a/src/gui/kernel/qapplication_s60.cpp b/src/gui/kernel/qapplication_s60.cpp
index acd1041..cb9dda4 100644
--- a/src/gui/kernel/qapplication_s60.cpp
+++ b/src/gui/kernel/qapplication_s60.cpp
@@ -352,7 +352,8 @@ QSymbianControl::~QSymbianControl()
{
if (S60->curWin == this)
S60->curWin = 0;
- setFocusSafely(false);
+ if (!QApplicationPrivate::is_app_closing)
+ setFocusSafely(false);
S60->appUi()->RemoveFromStack(this);
delete m_longTapDetector;
}
@@ -463,12 +464,47 @@ void QSymbianControl::HandlePointerEventL(const TPointerEvent& pEvent)
QT_TRYCATCH_LEAVING(HandlePointerEvent(pEvent));
}
+typedef QPair<QWidget*,QMouseEvent> Event;
+
+/*
+ * Helper function called by HandlePointerEvent - separated to keep that function readable
+ */
+static void generateEnterLeaveEvents(QList<Event> &events, QWidget *widgetUnderPointer,
+ QPoint globalPos, Qt::MouseButton button, Qt::KeyboardModifiers modifiers)
+{
+ //moved to another widget, create enter and leave events
+ if (S60->lastPointerEventTarget) {
+ QMouseEvent mEventLeave(QEvent::Leave, S60->lastPointerEventTarget->mapFromGlobal(
+ S60->lastCursorPos), S60->lastCursorPos, button, QApplicationPrivate::mouse_buttons,
+ modifiers);
+ events.append(Event(S60->lastPointerEventTarget, mEventLeave));
+ }
+ if (widgetUnderPointer) {
+ QMouseEvent mEventEnter(QEvent::Enter, widgetUnderPointer->mapFromGlobal(globalPos),
+ globalPos, button, QApplicationPrivate::mouse_buttons, modifiers);
+
+ events.append(Event(widgetUnderPointer, mEventEnter));
+#ifndef QT_NO_CURSOR
+ S60->curWin = widgetUnderPointer->effectiveWinId();
+ if (!QApplication::overrideCursor()) {
+#ifndef Q_SYMBIAN_FIXED_POINTER_CURSORS
+ if (S60->brokenPointerCursors)
+ qt_symbian_set_pointer_sprite(widgetUnderPointer->cursor());
+ else
+#endif
+ qt_symbian_setWindowCursor(widgetUnderPointer->cursor(), S60->curWin);
+ }
+#endif
+ }
+}
+
+
void QSymbianControl::HandlePointerEvent(const TPointerEvent& pEvent)
{
- //### refactor me, getting too complex
QMouseEvent::Type type;
Qt::MouseButton button;
mapS60MouseEventTypeToQt(&type, &button, &pEvent);
+ Qt::KeyboardModifiers modifiers = mapToQtModifiers(pEvent.iModifiers);
if (m_previousEventLongTap)
if (type == QEvent::MouseButtonRelease){
@@ -480,79 +516,76 @@ void QSymbianControl::HandlePointerEvent(const TPointerEvent& pEvent)
return;
// store events for later sending/saving
- QWidget *alienWidget;
- typedef QPair<QWidget*,QMouseEvent> Event;
QList<Event > events;
QPoint widgetPos = QPoint(pEvent.iPosition.iX, pEvent.iPosition.iY);
TPoint controlScreenPos = PositionRelativeToScreen();
QPoint globalPos = QPoint(controlScreenPos.iX, controlScreenPos.iY) + widgetPos;
- if (type == QEvent::MouseButtonPress || type == QEvent::MouseButtonDblClick || type == QEvent::MouseMove)
- {
- // get the widget where the event happened
- alienWidget = qwidget->childAt(widgetPos);
- if (!alienWidget)
- alienWidget = qwidget;
- S60->mousePressTarget = alienWidget;
+ // widgets interested in the event
+ QWidget *widgetUnderPointer = qwidget->childAt(widgetPos);
+ if (!widgetUnderPointer)
+ widgetUnderPointer = qwidget; //i.e. this container widget
+
+ QWidget *widgetWithMouseGrab = QWidget::mouseGrabber();
+
+ // handle auto grab of pointer when pressing / releasing
+ if (!widgetWithMouseGrab && type == QEvent::MouseButtonPress) {
+ //if previously auto-grabbed, generate a fake mouse release (platform bug: mouse release event was lost)
+ if (S60->mousePressTarget) {
+ QMouseEvent mEvent(QEvent::MouseButtonRelease, S60->mousePressTarget->mapFromGlobal(globalPos), globalPos,
+ button, QApplicationPrivate::mouse_buttons, modifiers);
+ events.append(Event(S60->mousePressTarget,mEvent));
+ }
+ //auto grab the mouse
+ widgetWithMouseGrab = S60->mousePressTarget = widgetUnderPointer;
+ widgetWithMouseGrab->grabMouse();
+ }
+ if (widgetWithMouseGrab && widgetWithMouseGrab == S60->mousePressTarget && type == QEvent::MouseButtonRelease) {
+ //release the auto grab - note this release event still goes to the autograb widget
+ S60->mousePressTarget = 0;
+ widgetWithMouseGrab->releaseMouse();
}
- alienWidget = S60->mousePressTarget;
+ QWidget *widgetToReceiveMouseEvent;
+ if (widgetWithMouseGrab)
+ widgetToReceiveMouseEvent = widgetWithMouseGrab;
+ else
+ widgetToReceiveMouseEvent = widgetUnderPointer;
- if (alienWidget != S60->lastPointerEventTarget)
- if (type == QEvent::MouseButtonPress || type == QEvent::MouseButtonDblClick || type == QEvent::MouseMove)
- {
- //moved to another widget, create enter and leave events
- if (S60->lastPointerEventTarget)
- {
- QMouseEvent mEventLeave(QEvent::Leave, S60->lastPointerEventTarget->mapFromGlobal(S60->lastCursorPos), S60->lastCursorPos,
- button, QApplicationPrivate::mouse_buttons, mapToQtModifiers(pEvent.iModifiers));
- events.append(Event(S60->lastPointerEventTarget,mEventLeave));
- }
- if (alienWidget) {
- QMouseEvent mEventEnter(QEvent::Enter, alienWidget->mapFromGlobal(globalPos),
- globalPos, button, QApplicationPrivate::mouse_buttons, mapToQtModifiers(
- pEvent.iModifiers));
+ //queue QEvent::Enter and QEvent::Leave, if the pointer has moved
+ if (widgetUnderPointer != S60->lastPointerEventTarget && (type == QEvent::MouseButtonPress || type == QEvent::MouseButtonDblClick || type == QEvent::MouseMove))
+ generateEnterLeaveEvents(events, widgetUnderPointer, globalPos, button, modifiers);
- events.append(Event(alienWidget, mEventEnter));
-#ifndef QT_NO_CURSOR
- S60->curWin = alienWidget->effectiveWinId();
- if (!QApplication::overrideCursor()) {
-#ifndef Q_SYMBIAN_FIXED_POINTER_CURSORS
- if (S60->brokenPointerCursors)
- qt_symbian_set_pointer_sprite(alienWidget->cursor());
- else
-#endif
- qt_symbian_setWindowCursor(alienWidget->cursor(), S60->curWin);
- }
-#endif
- }
- }
+ //save global state
S60->lastCursorPos = globalPos;
+ S60->lastPointerEventPos = widgetPos;
+ S60->lastPointerEventTarget = widgetUnderPointer;
+
#if !defined(QT_NO_CURSOR) && !defined(Q_SYMBIAN_FIXED_POINTER_CURSORS)
if (S60->brokenPointerCursors)
qt_symbian_move_cursor_sprite();
#endif
- S60->lastPointerEventPos = widgetPos;
- S60->lastPointerEventTarget = alienWidget;
- if (alienWidget)
- {
- QMouseEvent mEvent(type, alienWidget->mapFromGlobal(globalPos), globalPos,
- button, QApplicationPrivate::mouse_buttons, mapToQtModifiers(pEvent.iModifiers));
- events.append(Event(alienWidget,mEvent));
- QEventDispatcherS60 *dispatcher;
- // It is theoretically possible for someone to install a different event dispatcher.
- if ((dispatcher = qobject_cast<QEventDispatcherS60 *>(alienWidget->d_func()->threadData->eventDispatcher)) != 0) {
- if (dispatcher->excludeUserInputEvents()) {
- for (int i=0;i < events.count();++i)
- {
- Event next = events[i];
- dispatcher->saveInputEvent(this, next.first, new QMouseEvent(next.second));
- }
- return;
+
+ //queue this event.
+ Q_ASSERT(widgetToReceiveMouseEvent);
+ QMouseEvent mEvent(type, widgetToReceiveMouseEvent->mapFromGlobal(globalPos), globalPos,
+ button, QApplicationPrivate::mouse_buttons, modifiers);
+ events.append(Event(widgetToReceiveMouseEvent,mEvent));
+ QEventDispatcherS60 *dispatcher;
+ // It is theoretically possible for someone to install a different event dispatcher.
+ if ((dispatcher = qobject_cast<QEventDispatcherS60 *>(widgetToReceiveMouseEvent->d_func()->threadData->eventDispatcher)) != 0) {
+ if (dispatcher->excludeUserInputEvents()) {
+ for (int i=0;i < events.count();++i)
+ {
+ Event next = events[i];
+ dispatcher->saveInputEvent(this, next.first, new QMouseEvent(next.second));
}
+ return;
}
}
+
+ //send events in the queue
for (int i=0;i < events.count();++i)
{
Event next = events[i];
@@ -688,7 +721,7 @@ TKeyResponse QSymbianControl::OfferKeyEvent(const TKeyEvent& keyEvent, TEventCod
Qt::KeyboardModifiers mods = mapToQtModifiers(keyEvent.iModifiers);
QKeyEventEx qKeyEvent(type == EEventKeyUp ? QEvent::KeyRelease : QEvent::KeyPress, keyCode,
mods, qt_keymapper_private()->translateKeyEvent(keyCode, mods),
- false, 1, keyEvent.iScanCode, s60Keysym, mods);
+ false, 1, keyEvent.iScanCode, s60Keysym, keyEvent.iModifiers);
// WId wid = reinterpret_cast<RWindowGroup *>(keyEvent.Handle())->Child();
// if (!wid)
// Could happen if window isn't shown yet.
@@ -948,7 +981,8 @@ void QSymbianControl::setFocusSafely(bool focus)
S60->appUi()->RemoveFromStack(this);
QT_TRAP_THROWING(S60->appUi()->AddToStackL(this,
ECoeStackPriorityDefault, ECoeStackFlagStandard));
- lastFocusedControl = 0;
+ if(this == lastFocusedControl)
+ lastFocusedControl = 0;
this->SetFocus(false);
}
}
@@ -1121,6 +1155,11 @@ void qt_init(QApplicationPrivate * /* priv */, int)
;
}
*/
+
+ // Register WId with the metatype system. This is to enable
+ // QWidgetPrivate::create_sys to used delayed slot invokation in order
+ // to destroy WId objects during reparenting.
+ qRegisterMetaType<WId>("WId");
}
/*****************************************************************************
diff --git a/src/gui/kernel/qapplication_win.cpp b/src/gui/kernel/qapplication_win.cpp
index 270562f..5bb25fa 100644
--- a/src/gui/kernel/qapplication_win.cpp
+++ b/src/gui/kernel/qapplication_win.cpp
@@ -92,8 +92,6 @@ extern void qt_wince_hide_taskbar(HWND hwnd); //defined in qguifunctions_wince.c
#include <private/qkeymapper_p.h>
#include <private/qlocale_p.h>
#include "qevent_p.h"
-#include "qstandardgestures.h"
-#include "qstandardgestures_p.h"
//#define ALIEN_DEBUG
@@ -821,13 +819,16 @@ void qt_init(QApplicationPrivate *priv, int)
priv->GetGestureInfo = 0;
priv->GetGestureExtraArgs = 0;
+ priv->CloseGestureInfoHandle = 0;
+ priv->SetGestureConfig = 0;
+ priv->GetGestureConfig = 0;
+ priv->BeginPanningFeedback = 0;
+ priv->UpdatePanningFeedback = 0;
+ priv->EndPanningFeedback = 0;
#if defined(Q_WS_WINCE_WM) && defined(QT_WINCE_GESTURES)
priv->GetGestureInfo = (PtrGetGestureInfo) &TKGetGestureInfo;
priv->GetGestureExtraArgs = (PtrGetGestureExtraArgs) &TKGetGestureExtraArguments;
- priv->CloseGestureInfoHandle = (PtrCloseGestureInfoHandle) 0;
- priv->SetGestureConfig = (PtrSetGestureConfig) 0;
- priv->GetGestureConfig = (PtrGetGestureConfig) 0;
#elif !defined(Q_WS_WINCE)
priv->GetGestureInfo =
(PtrGetGestureInfo)QLibrary::resolve(QLatin1String("user32"),
@@ -854,7 +855,6 @@ void qt_init(QApplicationPrivate *priv, int)
(PtrEndPanningFeedback)QLibrary::resolve(QLatin1String("uxtheme"),
"EndPanningFeedback");
#endif
- priv->gestureWidget = 0;
}
/*****************************************************************************
@@ -2499,24 +2499,24 @@ LRESULT CALLBACK QtWndProc(HWND hwnd, UINT message, WPARAM wParam, LPARAM lParam
if (qAppPriv->GetGestureInfo)
bResult = qAppPriv->GetGestureInfo((HANDLE)msg.lParam, &gi);
if (bResult) {
- if (gi.dwID == GID_BEGIN) {
- // find the alien widget for the gesture position.
- // This might not be accurate as the position is the center
- // point of two fingers for multi-finger gestures.
- QPoint pt(gi.ptsLocation.x, gi.ptsLocation.y);
- QWidget *w = widget->childAt(widget->mapFromGlobal(pt));
- qAppPriv->gestureWidget = w ? w : widget;
- }
- if (qAppPriv->gestureWidget)
- static_cast<QETWidget*>(qAppPriv->gestureWidget)->translateGestureEvent(msg, gi);
- if (qAppPriv->CloseGestureInfoHandle)
- qAppPriv->CloseGestureInfoHandle((HANDLE)msg.lParam);
- if (gi.dwID == GID_END)
- qAppPriv->gestureWidget = 0;
- } else {
- DWORD dwErr = GetLastError();
- if (dwErr > 0)
- qWarning() << "translateGestureEvent: error = " << dwErr;
+// if (gi.dwID == GID_BEGIN) {
+// // find the alien widget for the gesture position.
+// // This might not be accurate as the position is the center
+// // point of two fingers for multi-finger gestures.
+// QPoint pt(gi.ptsLocation.x, gi.ptsLocation.y);
+// QWidget *w = widget->childAt(widget->mapFromGlobal(pt));
+// qAppPriv->gestureWidget = w ? w : widget;
+// }
+// if (qAppPriv->gestureWidget)
+// static_cast<QETWidget*>(qAppPriv->gestureWidget)->translateGestureEvent(msg, gi);
+// if (qAppPriv->CloseGestureInfoHandle)
+// qAppPriv->CloseGestureInfoHandle((HANDLE)msg.lParam);
+// if (gi.dwID == GID_END)
+// qAppPriv->gestureWidget = 0;
+// } else {
+// DWORD dwErr = GetLastError();
+// if (dwErr > 0)
+// qWarning() << "translateGestureEvent: error = " << dwErr;
}
result = true;
break;
diff --git a/src/gui/kernel/qcocoaview_mac.mm b/src/gui/kernel/qcocoaview_mac.mm
index b1c5fc5..4c2a14a 100644
--- a/src/gui/kernel/qcocoaview_mac.mm
+++ b/src/gui/kernel/qcocoaview_mac.mm
@@ -1066,7 +1066,10 @@ extern "C" {
sendToPopup = true;
}
- if (widgetToGetKey->testAttribute(Qt::WA_InputMethodEnabled)) {
+ if (widgetToGetKey->testAttribute(Qt::WA_InputMethodEnabled)
+ && !(widgetToGetKey->inputMethodHints() & Qt::ImhDigitsOnly
+ || widgetToGetKey->inputMethodHints() & Qt::ImhFormattedNumbersOnly
+ || widgetToGetKey->inputMethodHints() & Qt::ImhHiddenText)) {
[qt_mac_nativeview_for(widgetToGetKey) interpretKeyEvents:[NSArray arrayWithObject: theEvent]];
}
if (sendKeyEvents && !composing) {
@@ -1420,29 +1423,29 @@ Qt::DropAction QDragManager::drag(QDrag *o)
// convert the image to NSImage.
NSImage *image = (NSImage *)qt_mac_create_nsimage(pix);
[image retain];
- DnDParams *dndParams = [QT_MANGLE_NAMESPACE(QCocoaView) currentMouseEvent];
+ DnDParams dndParams = *[QT_MANGLE_NAMESPACE(QCocoaView) currentMouseEvent];
// save supported actions
- [dndParams->view setSupportedActions: qt_mac_mapDropActions(dragPrivate()->possible_actions)];
- NSPoint imageLoc = {dndParams->localPoint.x - hotspot.x(),
- dndParams->localPoint.y + pix.height() - hotspot.y()};
+ [dndParams.view setSupportedActions: qt_mac_mapDropActions(dragPrivate()->possible_actions)];
+ NSPoint imageLoc = {dndParams.localPoint.x - hotspot.x(),
+ dndParams.localPoint.y + pix.height() - hotspot.y()};
NSSize mouseOffset = {0.0, 0.0};
NSPasteboard *pboard = [NSPasteboard pasteboardWithName:NSDragPboard];
- NSPoint windowPoint = [dndParams->theEvent locationInWindow];
+ NSPoint windowPoint = [dndParams.theEvent locationInWindow];
dragPrivate()->executed_action = Qt::ActionMask;
// do the drag
- [dndParams->view retain];
- [dndParams->view dragImage:image
+ [dndParams.view retain];
+ [dndParams.view dragImage:image
at:imageLoc
offset:mouseOffset
- event:dndParams->theEvent
+ event:dndParams.theEvent
pasteboard:pboard
- source:dndParams->view
+ source:dndParams.view
slideBack:YES];
- [dndParams->view release];
+ [dndParams.view release];
[image release];
dragPrivate()->executed_action = Qt::IgnoreAction;
object = 0;
- Qt::DropAction performedAction(qt_mac_mapNSDragOperation(dndParams->performedAction));
+ Qt::DropAction performedAction(qt_mac_mapNSDragOperation(dndParams.performedAction));
// do post drag processing, if required.
if(performedAction != Qt::IgnoreAction) {
// check if the receiver points us to a file location.
diff --git a/src/gui/kernel/qcursor_s60.cpp b/src/gui/kernel/qcursor_s60.cpp
index 0d8283d..7f5c32a 100644
--- a/src/gui/kernel/qcursor_s60.cpp
+++ b/src/gui/kernel/qcursor_s60.cpp
@@ -110,7 +110,7 @@ void qt_symbian_set_cursor_visible(bool visible) {
else
cursorSpriteVisible--;
Q_ASSERT(cursorSpriteVisible >=0);
-
+
if (cursorSpriteVisible && !S60->mouseInteractionEnabled) {
#ifndef Q_SYMBIAN_FIXED_POINTER_CURSORS
if (S60->brokenPointerCursors)
@@ -119,7 +119,7 @@ void qt_symbian_set_cursor_visible(bool visible) {
#endif
S60->wsSession().SetPointerCursorMode(EPointerCursorNormal);
} else if (!cursorSpriteVisible && S60->mouseInteractionEnabled) {
-#ifndef Q_SYMBIAN_FIXED_POINTER_CURSORS
+#ifndef Q_SYMBIAN_FIXED_POINTER_CURSORS
if (S60->brokenPointerCursors)
qt_symbian_hide_pointer_sprite();
else
@@ -188,7 +188,7 @@ Qt::HANDLE QCursor::handle() const
return reinterpret_cast<Qt::HANDLE> (&(d->pcurs));
#ifdef Q_SYMBIAN_HAS_SYSTEM_CURSORS
- // don't construct shape cursors, QApplication_s60 will use the system cursor instead
+ // don't construct shape cursors, QApplication_s60 will use the system cursor instead
if (!(d->bm))
return 0;
#endif
@@ -228,12 +228,12 @@ void QCursorData::loadShapeFromResource(RWsSpriteBase& target, QString resource,
/*
* Constructs the native cursor from resources compiled into QtGui
* This is needed only when the platform doesn't have system cursors.
- *
+ *
* System cursors are higher performance, since they are constructed once
* and shared by all applications by specifying the shape number.
* Due to symbian platform security considerations, and the fact most
* existing phones have a broken RWsPointerCursor, system cursors are not
- * being used.
+ * being used.
*/
void QCursorData::constructShapeSprite(RWsSpriteBase& target)
{
@@ -346,7 +346,7 @@ void QCursorData::constructCursorSprite(RWsSpriteBase& target)
member->iMaskBitmap = pixmap.mask().toSymbianCFbsBitmap();
}
else {
- member->iMaskBitmap = pixmap.createHeuristicMask().toSymbianCFbsBitmap();
+ member->iMaskBitmap = 0; //opaque rectangle cursor (due to EDrawModePEN)
}
}
@@ -371,11 +371,11 @@ void qt_symbian_show_pointer_sprite()
} else {
cursorSprite = QCursor(Qt::ArrowCursor);
}
-
+
cursorSprite.d->scurs = RWsSprite(S60->wsSession());
QPoint pos = QCursor::pos();
cursorSprite.d->scurs.Construct(S60->windowGroup(), TPoint(pos.x(), pos.y()), ESpriteNoChildClip | ESpriteNoShadows);
-
+
cursorSprite.d->constructCursorSprite(cursorSprite.d->scurs);
cursorSprite.d->scurs.Activate();
}
@@ -409,7 +409,7 @@ void qt_symbian_set_pointer_sprite(const QCursor& cursor)
* RWsPointerCursor, this function is called in response to pointer events
* and when QCursor::setPos() is called.
* Performance is worse than a real pointer cursor, due to extra context
- * switches vs. the window server moving the cursor by itself.
+ * switches vs. the window server moving the cursor by itself.
*/
void qt_symbian_move_cursor_sprite()
{
@@ -421,7 +421,7 @@ void qt_symbian_move_cursor_sprite()
/*
* Translate from Qt::CursorShape to OS system pointer cursor list index.
* Currently we control the implementation of the system pointer cursor list,
- * so this function is trivial. That may not always be the case.
+ * so this function is trivial. That may not always be the case.
*/
TInt qt_symbian_translate_cursor_shape(Qt::CursorShape shape)
{
@@ -462,7 +462,7 @@ void qt_symbian_set_cursor(QWidget *w, bool force)
/*
* Makes the specified cursor appear above a specific native window group
* Called from QSymbianControl and QApplication::restoreOverrideCursor
- *
+ *
* Window server is needed for this, so there is no equivalent when using
* the sprite workaround.
*/
@@ -486,7 +486,7 @@ void qt_symbian_setWindowGroupCursor(const QCursor &cursor, RWindowTreeNode &nod
/*
* Makes the specified cursor appear above a specific native window
* Called from QSymbianControl and QApplication::restoreOverrideCursor
- *
+ *
* Window server is needed for this, so there is no equivalent when using
* the sprite workaround.
*/
diff --git a/src/gui/kernel/qdnd_s60.cpp b/src/gui/kernel/qdnd_s60.cpp
index 3d6ecd2..a8d3ac5 100644
--- a/src/gui/kernel/qdnd_s60.cpp
+++ b/src/gui/kernel/qdnd_s60.cpp
@@ -277,7 +277,7 @@ Qt::DropAction QDragManager::drag(QDrag *o)
qApp->installEventFilter(this);
- global_accepted_action = Qt::MoveAction;
+ global_accepted_action = defaultAction(dragPrivate()->possible_actions, Qt::NoModifier);
qt_symbian_dnd_dragging = true;
eventLoop = new QEventLoop;
@@ -288,7 +288,7 @@ Qt::DropAction QDragManager::drag(QDrag *o)
#ifndef QT_NO_CURSOR
qt_symbian_set_cursor_visible(false);
-
+
overrideCursor = QCursor(); //deref the cursor data
qt_symbian_dnd_dragging = false;
#endif
diff --git a/src/gui/kernel/qevent.cpp b/src/gui/kernel/qevent.cpp
index 7b9cc9a..2ff6d65 100644
--- a/src/gui/kernel/qevent.cpp
+++ b/src/gui/kernel/qevent.cpp
@@ -49,6 +49,8 @@
#include "qmime.h"
#include "qdnd_p.h"
#include "qevent_p.h"
+#include "qgesture.h"
+#include "qgesture_p.h"
QT_BEGIN_NAMESPACE
@@ -3357,6 +3359,9 @@ QDebug operator<<(QDebug dbg, const QEvent *e) {
case QEvent::ChildRemoved: n = n ? n : "ChildRemoved";
dbg.nospace() << "QChildEvent(" << n << ", " << (static_cast<const QChildEvent*>(e))->child();
return dbg.space();
+ case QEvent::Gesture:
+ n = "Gesture";
+ break;
default:
dbg.nospace() << "QEvent(" << (const void *)e << ", type = " << e->type() << ')';
return dbg.space();
@@ -3558,6 +3563,7 @@ QMenubarUpdatedEvent::QMenubarUpdatedEvent(QMenuBar * const menuBar)
\brief The QTouchEvent class contains parameters that describe a touch event.
\since 4.6
\ingroup events
+ \ingroup multitouch
\section1 Enabling Touch Events
@@ -4186,4 +4192,170 @@ QTouchEvent::TouchPoint &QTouchEvent::TouchPoint::operator=(const QTouchEvent::T
return *this;
}
+/*!
+ \class QGestureEvent
+ \since 4.6
+ \ingroup events
+ \ingroup gestures
+
+ \brief The QGestureEvent class provides the description of triggered gestures.
+
+ The QGestureEvent class contains a list of gestures, which can be obtained using the
+ allGestures() function.
+
+ The gestures are either active or canceled. A list of those that are currently being
+ executed can be obtained using the activeGestures() function. A list of those which
+ were previously active and have been canceled can be accessed using the
+ canceledGestures() function. A gesture might be canceled if the current window loses
+ focus, for example, or because of a timeout, or for other reasons.
+
+ If the event handler does not accept the event by calling the generic
+ QEvent::accept() function, all individual QGesture object that were not accepted
+ will be propagated up the parent widget chain until a widget accepts them
+ individually, by calling QGestureEvent::accept() for each of them, or an event
+ filter consumes the event.
+
+ \sa QGesture, QGestureRecognizer,
+ QWidget::grabGesture(), QGraphicsObject::grabGesture()
+*/
+
+/*!
+ Creates new QGestureEvent containing a list of \a gestures.
+*/
+QGestureEvent::QGestureEvent(const QList<QGesture *> &gestures)
+ : QEvent(QEvent::Gesture), gestures_(gestures)
+{
+}
+
+/*!
+ Returns all gestures that are delivered in the event.
+*/
+QList<QGesture *> QGestureEvent::allGestures() const
+{
+ return gestures_;
+}
+
+/*!
+ Returns a gesture object by \a type.
+*/
+QGesture *QGestureEvent::gesture(Qt::GestureType type) const
+{
+ for(int i = 0; i < gestures_.size(); ++i)
+ if (gestures_.at(i)->gestureType() == type)
+ return gestures_.at(i);
+ return 0;
+}
+
+/*!
+ Returns a list of active (not canceled) gestures.
+*/
+QList<QGesture *> QGestureEvent::activeGestures() const
+{
+ return gestures_;
+}
+
+/*!
+ Returns a list of canceled gestures.
+*/
+QList<QGesture *> QGestureEvent::canceledGestures() const
+{
+ return gestures_;
+}
+
+/*!
+ Sets the accept flag of the given \a gesture object to the specified \a value.
+
+ Setting the accept flag indicates that the event receiver wants the \a gesture.
+ Unwanted gestures may be propagated to the parent widget.
+
+ By default, gestures in events of type QEvent::Gesture are accepted, and
+ gestures in QEvent::GestureOverride events are ignored.
+
+ For convenience, the accept flag can also be set with
+ \l{QGestureEvent::accept()}{accept(gesture)}, and cleared with
+ \l{QGestureEvent::ignore()}{ignore(gesture)}.
+*/
+void QGestureEvent::setAccepted(QGesture *gesture, bool value)
+{
+ setAccepted(false);
+ if (gesture)
+ gesture->d_func()->accept = value;
+}
+
+/*!
+ Sets the accept flag of the given \a gesture object, the equivalent of calling
+ \l{QGestureEvent::setAccepted()}{setAccepted(gesture, true)}.
+
+ Setting the accept flag indicates that the event receiver wants the
+ gesture. Unwanted gestures may be propagated to the parent widget.
+
+ \sa QGestureEvent::ignore()
+*/
+void QGestureEvent::accept(QGesture *gesture)
+{
+ setAccepted(gesture, true);
+}
+
+/*!
+ Clears the accept flag parameter of the given \a gesture object, the equivalent
+ of calling \l{QGestureEvent::setAccepted()}{setAccepted(gesture, false)}.
+
+ Clearing the accept flag indicates that the event receiver does not
+ want the gesture. Unwanted gestures may be propgated to the parent widget.
+
+ \sa QGestureEvent::accept()
+*/
+void QGestureEvent::ignore(QGesture *gesture)
+{
+ setAccepted(gesture, false);
+}
+
+/*!
+ Returns true if the \a gesture is accepted; otherwise returns false.
+*/
+bool QGestureEvent::isAccepted(QGesture *gesture) const
+{
+ return gesture ? gesture->d_func()->accept : false;
+}
+
+#ifdef Q_NO_USING_KEYWORD
+/*!
+ \fn void QGestureEvent::setAccepted(bool accepted)
+
+ Sets or clears the event's internal flag that determines whether it should
+ be delivered to other objects.
+
+ Calling this function with a value of true for \a accepted indicates that the
+ caller has accepted the event and that it should not be propagated further.
+ Calling this function with a value of false indicates that the caller has
+ ignored the event and that it should be delivered to other objects.
+
+ For convenience, the accept flag can also be set with accept(), and cleared
+ with ignore().
+
+ \sa QEvent::accepted
+*/
+/*!
+ \fn bool QGestureEvent::isAccepted() const
+
+ Returns true is the event has been accepted; otherwise returns false.
+
+ \sa QEvent::accepted
+*/
+/*!
+ \fn void QGestureEvent::accept()
+
+ Accepts the event, the equivalent of calling setAccepted(true).
+
+ \sa QEvent::accept()
+*/
+/*!
+ \fn void QGestureEvent::ignore()
+
+ Ignores the event, the equivalent of calling setAccepted(false).
+
+ \sa QEvent::ignore()
+*/
+#endif
+
QT_END_NAMESPACE
diff --git a/src/gui/kernel/qevent.h b/src/gui/kernel/qevent.h
index 4396766..3516222 100644
--- a/src/gui/kernel/qevent.h
+++ b/src/gui/kernel/qevent.h
@@ -819,6 +819,40 @@ protected:
friend class QApplicationPrivate;
};
+class QGesture;
+class Q_GUI_EXPORT QGestureEvent : public QEvent
+{
+public:
+ QGestureEvent(const QList<QGesture *> &gestures);
+
+ QList<QGesture *> allGestures() const;
+ QGesture *gesture(Qt::GestureType type) const;
+
+ QList<QGesture *> activeGestures() const;
+ QList<QGesture *> canceledGestures() const;
+
+#ifdef Q_NO_USING_KEYWORD
+ inline void setAccepted(bool accepted) { QEvent::setAccepted(accepted); }
+ inline bool isAccepted() const { return QEvent::isAccepted(); }
+
+ inline void accept() { QEvent::accept(); }
+ inline void ignore() { QEvent::ignore(); }
+#else
+ using QEvent::setAccepted;
+ using QEvent::isAccepted;
+ using QEvent::accept;
+ using QEvent::ignore;
+#endif
+
+ void setAccepted(QGesture *, bool);
+ void accept(QGesture *);
+ void ignore(QGesture *);
+ bool isAccepted(QGesture *) const;
+
+private:
+ QList<QGesture *> gestures_;
+};
+
QT_END_NAMESPACE
QT_END_HEADER
diff --git a/src/gui/kernel/qeventdispatcher_mac.mm b/src/gui/kernel/qeventdispatcher_mac.mm
index 7152705..c9dd949 100644
--- a/src/gui/kernel/qeventdispatcher_mac.mm
+++ b/src/gui/kernel/qeventdispatcher_mac.mm
@@ -136,14 +136,19 @@ void QEventDispatcherMacPrivate::activateTimer(CFRunLoopTimerRef, void *info)
if (tmr == 0 || tmr->pending == true)
return; // Can't send another timer event if it's pending.
- tmr->pending = true;
- QTimerEvent e(tmr->id);
- qt_sendSpontaneousEvent(tmr->obj, &e);
- // Get the value again in case the timer gets unregistered during the sendEvent.
- tmr = macTimerHash.value(timerID);
- if (tmr != 0)
- tmr->pending = false;
+ if (blockSendPostedEvents) {
+ QCoreApplication::postEvent(tmr->obj, new QTimerEvent(tmr->id));
+ } else {
+ tmr->pending = true;
+ QTimerEvent e(tmr->id);
+ qt_sendSpontaneousEvent(tmr->obj, &e);
+ // Get the value again in case the timer gets unregistered during the sendEvent.
+ tmr = macTimerHash.value(timerID);
+ if (tmr != 0)
+ tmr->pending = false;
+ }
+
}
void QEventDispatcherMac::registerTimer(int timerId, int interval, QObject *obj)
@@ -767,7 +772,7 @@ NSModalSession QEventDispatcherMacPrivate::currentModalSession()
// Sadly, we need to introduce this little event flush
// to stop dialogs from blinking/poping in front if a
// modal session restart was needed:
- while (NSEvent *event = [NSApp nextEventMatchingMask:NSAnyEventMask
+ while (NSEvent *event = [NSApp nextEventMatchingMask:0
untilDate:nil
inMode:NSDefaultRunLoopMode
dequeue: YES]) {
@@ -942,7 +947,7 @@ Boolean QEventDispatcherMacPrivate::postedEventSourceEqualCallback(const void *i
inline static void processPostedEvents(QEventDispatcherMacPrivate *const d, const bool blockSendPostedEvents)
{
- if (blockSendPostedEvents) {
+ if (blockSendPostedEvents || d->interrupt) {
CFRunLoopSourceSignal(d->postedEventsSource);
} else {
if (!d->threadData->canWait || (d->serialNumber != d->lastSerial)) {
diff --git a/src/gui/kernel/qgesture.cpp b/src/gui/kernel/qgesture.cpp
index 237ce46..fc8df49 100644
--- a/src/gui/kernel/qgesture.cpp
+++ b/src/gui/kernel/qgesture.cpp
@@ -40,274 +40,585 @@
****************************************************************************/
#include "qgesture.h"
-#include <private/qgesture_p.h>
-#include "qgraphicsitem.h"
+#include "private/qgesture_p.h"
QT_BEGIN_NAMESPACE
-
-class QEventFilterProxyGraphicsItem : public QGraphicsItem
-{
-public:
- QEventFilterProxyGraphicsItem(QGesture *g)
- : gesture(g)
- {
- }
- bool sceneEventFilter(QGraphicsItem *, QEvent *event)
- {
- return gesture ? gesture->filterEvent(event) : false;
- }
- QRectF boundingRect() const { return QRectF(); }
- void paint(QPainter*, const QStyleOptionGraphicsItem*, QWidget*) { }
-
-private:
- QGesture *gesture;
-};
-
-/*!
+ /*!
\class QGesture
\since 4.6
- \preliminary
+ \ingroup gestures
+
+ \brief The QGesture class represents a gesture, containing properties that
+ describe the corresponding user input.
- \brief The QGesture class is the base class for implementing custom
- gestures.
+ Gesture objects are not constructed directly by developers. They are created by
+ the QGestureRecognizer object that is registered with the application; see
+ QApplication::registerGestureRecognizer().
- This class represents both an object that recognizes a gesture out of a set
- of input events (a gesture recognizer), and a gesture object itself that
- can be used to get extended information about the triggered gesture.
+ \section1 Gesture Properties
The class has a list of properties that can be queried by the user to get
- some gesture-specific parameters (for example, an offset of a Pan gesture).
+ some gesture-specific arguments. For example, the pinch gesture has a scale
+ factor that is exposed as a property.
+
+ Developers of custom gesture recognizers can add additional properties in
+ order to provide additional information about a gesture. This can be done
+ by adding new dynamic properties to a QGesture object, or by subclassing
+ the QGesture class (or one of its subclasses).
+
+ \section1 Lifecycle of a Gesture Object
- Usually gesture recognizer implements a state machine, storing its state
- internally in the recognizer object. The recognizer receives input events
- through the \l{QGesture::}{filterEvent()} virtual function and decides
- whether the event should change the state of the recognizer by emitting an
- appropriate signal.
+ A QGesture instance is created when the application calls QWidget::grabGesture()
+ or QGraphicsObject::grabGesture() to configure a widget or graphics object (the
+ target object) for gesture input. One gesture object is created for each target
+ object.
- Input events should be either fed to the recognizer one by one with a
- filterEvent() function, or the gesture recognizer should be attached to an
- object it filters events for by specifying it as a parent object. The
- QGesture object installs itself as an event filter to the parent object
- automatically, the unsetObject() function should be used to remove an event
- filter from the parent object. To make a
- gesture that operates on a QGraphicsItem, both the appropriate QGraphicsView
- should be passed as a parent object and setGraphicsItem() functions should
- be used to attach a gesture to a graphics item.
+ The registered gesture recognizer monitors the input events for the target
+ object via its \l{QGestureRecognizer::}{filterEvent()} function, updating the
+ properties of the gesture object as required.
- This is a base class, to create a custom gesture type, you should subclass
- it and implement its pure virtual functions.
+ The gesture object may be delivered to the target object in a QGestureEvent if
+ the corresponding gesture is active or has just been canceled. Each event that
+ is delivered contains a list of gesture objects, since support for more than
+ one gesture may be enabled for the target object. Due to the way events are
+ handled in Qt, gesture events may be filtered by other objects.
- \sa QPanGesture
+ \sa QGestureEvent, QGestureRecognizer
*/
-/*! \fn bool QGesture::filterEvent(QEvent *event)
+/*!
+ Constructs a new gesture object with the given \a parent.
+
+ QGesture objects are created by gesture recognizers in the
+ QGestureRecognizer::createGesture() function.
+*/
+QGesture::QGesture(QObject *parent)
+ : QObject(*new QGesturePrivate, parent)
+{
+ d_func()->gestureType = Qt::CustomGesture;
+}
+
+/*!
+ \internal
+*/
+QGesture::QGesture(QGesturePrivate &dd, QObject *parent)
+ : QObject(dd, parent)
+{
+}
- Parses input \a event and emits a signal when detects a gesture.
+/*!
+ Destroys the gesture object.
+*/
+QGesture::~QGesture()
+{
+}
- In your reimplementation of this function, if you want to filter the \a
- event out, i.e. stop it being handled further, return true; otherwise
- return false;
+/*!
+ \property QGesture::state
+ \brief the current state of the gesture
+*/
- This is a pure virtual function that needs to be implemented in subclasses.
+/*!
+ \property QGesture::gestureType
+ \brief the type of the gesture
*/
-/*! \fn void QGesture::started()
+/*!
+ \property QGesture::hotSpot
+
+ \brief The point that is used to find the receiver for the gesture event.
+
+ If the hot-spot is not set, the targetObject is used as the receiver of the
+ gesture event.
+*/
- The signal is emitted when the gesture is started. Extended information
- about the gesture is contained in the signal sender object.
+/*!
+ \property QGesture::hasHotSpot
+ \brief whether the gesture has a hot-spot
+*/
- In addition to started(), a triggered() signal should also be emitted.
+/*!
+ \property QGesture::targetObject
+ \brief the target object which will receive the gesture event if the hotSpot is
+ not set
*/
-/*! \fn void QGesture::triggered()
+Qt::GestureType QGesture::gestureType() const
+{
+ return d_func()->gestureType;
+}
+
+Qt::GestureState QGesture::state() const
+{
+ return d_func()->state;
+}
+
+QObject *QGesture::targetObject() const
+{
+ return d_func()->targetObject;
+}
+
+void QGesture::setTargetObject(QObject *value)
+{
+ d_func()->targetObject = value;
+}
+
+QPointF QGesture::hotSpot() const
+{
+ return d_func()->hotSpot;
+}
+
+void QGesture::setHotSpot(const QPointF &value)
+{
+ Q_D(QGesture);
+ d->hotSpot = value;
+ d->isHotSpotSet = true;
+}
+
+bool QGesture::hasHotSpot() const
+{
+ return d_func()->isHotSpotSet;
+}
+
+void QGesture::unsetHotSpot()
+{
+ d_func()->isHotSpotSet = false;
+}
+
+/*!
+ \class QPanGesture
+ \since 4.6
+ \brief The QPanGesture class describes a panning gesture made by the user.
+ \ingroup gestures
- The signal is emitted when the gesture is detected. Extended information
- about the gesture is contained in the signal sender object.
+ \image pangesture.png
+
+ \sa {Gestures Programming}, QPinchGesture, QSwipeGesture
*/
-/*! \fn void QGesture::finished()
+/*!
+ \property QPanGesture::totalOffset
+ \brief the total offset from the first input position to the current input
+ position
- The signal is emitted when the gesture is finished. Extended information
- about the gesture is contained in the signal sender object.
+ The total offset measures the total change in position of the user's input
+ covered by the gesture on the input device.
*/
-/*! \fn void QGesture::canceled()
+/*!
+ \property QPanGesture::lastOffset
+ \brief the last offset recorded for this gesture
+
+ The last offset contains the change in position of the user's input as
+ reported in the \l offset property when a previous gesture event was
+ delivered for this gesture.
- The signal is emitted when the gesture is canceled, for example the
- reset() function is called while the gesture was in the process of
- emitting a triggered() signal. Extended information about the
- gesture is contained in the sender object.
+ If no previous event was delivered with information about this gesture
+ (i.e., this gesture object contains information about the first movement
+ in the gesture) then this property contains a zero size.
*/
/*!
- Creates a new gesture handler object and marks it as a child of \a
- parent. \a gestureTarget is the object that the gesture will watch
- for events.
+ \property QPanGesture::offset
+ \brief the offset from the previous input position to the current input
+ position
- The \a parent object is also the default event source for the
- gesture, meaning that the gesture installs itself as an event filter
- for the \a parent.
+ The offset measures the change in position of the user's input on the
+ input device.
+*/
- \sa setGraphicsItem()
+/*!
+ \property QPanGesture::acceleration
*/
-QGesture::QGesture(QObject *gestureTarget, QObject *parent)
- : QObject(*new QGesturePrivate, parent)
+
+/*!
+ \internal
+*/
+QPanGesture::QPanGesture(QObject *parent)
+ : QGesture(*new QPanGesturePrivate, parent)
{
- setGestureTarget(gestureTarget);
+ d_func()->gestureType = Qt::PanGesture;
}
-/*! \internal
- */
-QGesture::QGesture(QGesturePrivate &dd, QObject *gestureTarget, QObject *parent)
- : QObject(dd, parent)
+QSizeF QPanGesture::totalOffset() const
{
- setGestureTarget(gestureTarget);
+ return d_func()->totalOffset;
}
-/*!
- Destroys the gesture object.
-*/
-QGesture::~QGesture()
+QSizeF QPanGesture::lastOffset() const
{
+ return d_func()->lastOffset;
}
-/*!
- \property QGesture::gestureTarget
+QSizeF QPanGesture::offset() const
+{
+ return d_func()->offset;
+}
- Gesture target is the object that the gesture will watch for events.
- Typically this means that the gesture installs an event filter on the
- target object.
-*/
-void QGesture::setGestureTarget(QObject *object)
+qreal QPanGesture::acceleration() const
{
- d_func()->setupGestureTarget(object);
+ return d_func()->acceleration;
}
-QObject* QGesture::gestureTarget() const
+
+void QPanGesture::setTotalOffset(const QSizeF &value)
{
- return d_func()->gestureTarget;
+ d_func()->totalOffset = value;
}
-void QGesturePrivate::setupGestureTarget(QObject *object)
+void QPanGesture::setLastOffset(const QSizeF &value)
{
- Q_Q(QGesture);
- if (gestureTarget)
- gestureTarget->removeEventFilter(q);
- if (object)
- object->installEventFilter(q);
- gestureTarget = object;
+ d_func()->lastOffset = value;
}
-/*! \internal
- */
-bool QGesture::eventFilter(QObject *receiver, QEvent *event)
+void QPanGesture::setOffset(const QSizeF &value)
{
- Q_D(QGesture);
- if (d->graphicsItem && receiver == parent())
- return false;
- return filterEvent(event);
+ d_func()->offset = value;
+}
+
+void QPanGesture::setAcceleration(qreal value)
+{
+ d_func()->acceleration = value;
}
/*!
- \property QGesture::state
+ \class QPinchGesture
+ \since 4.6
+ \brief The QPinchGesture class describes a pinch gesture made my the user.
+ \ingroup multitouch
+ \ingroup gestures
+
+ A pinch gesture is a form of multitouch user input in which the user typically
+ touches two points on the input device with a thumb and finger, before moving
+ them closer together or further apart to change the scale factor, zoom, or level
+ of detail of the user interface.
+
+ \image pinchgesture.png
- \brief The current state of the gesture.
+ Instead of repeatedly applying the same pinching gesture, the user may
+ continue to touch the input device in one place, and apply a second touch
+ to a new point, continuing the gesture. When this occurs, gesture events
+ will continue to be delivered to the target object, containing an instance
+ of QPinchGesture in the Qt::GestureUpdated state.
+
+ \sa {Gestures Programming}, QPanGesture, QSwipeGesture
*/
/*!
- Returns the gesture recognition state.
- */
-Qt::GestureState QGesture::state() const
+ \enum QPinchGesture::WhatChange
+
+ This enum describes the changes that can occur to the properties of
+ the gesture object.
+
+ \value ScaleFactorChanged The scale factor held by scaleFactor changed.
+ \value RotationAngleChanged The rotation angle held by rotationAngle changed.
+ \value CenterPointChanged The center point held by centerPoint changed.
+
+ \sa whatChanged
+*/
+
+/*!
+ \property QPinchGesture::whatChanged
+ \brief the property of the gesture that has changed
+
+ This property indicates which of the other properties has changed since
+ the previous gesture event included information about this gesture. You
+ can use this information to determine which aspect of your user interface
+ needs to be updated.
+
+ \sa scaleFactor, rotationAngle, centerPoint
+*/
+
+/*!
+ \property QPinchGesture::totalScaleFactor
+ \brief the total scale factor
+
+ The total scale factor measures the total change in scale factor from the
+ original value to the current scale factor.
+
+ \sa scaleFactor, lastScaleFactor
+*/
+/*!
+ \property QPinchGesture::lastScaleFactor
+ \brief the last scale factor recorded for this gesture
+
+ The last scale factor contains the scale factor reported in the
+ \l scaleFactor property when a previous gesture event included
+ information about this gesture.
+
+ If no previous event was delivered with information about this gesture
+ (i.e., this gesture object contains information about the first movement
+ in the gesture) then this property contains zero.
+
+ \sa scaleFactor, totalScaleFactor
+*/
+/*!
+ \property QPinchGesture::scaleFactor
+ \brief the current scale factor
+
+ The scale factor measures the scale factor associated with the distance
+ between two of the user's inputs on a multitouch device.
+
+ \sa totalScaleFactor, lastScaleFactor
+*/
+
+/*!
+ \property QPinchGesture::totalRotationAngle
+ \brief the total angle covered by the gesture
+
+ This total angle measures the complete angle covered by the gesture. Usually, this
+ is equal to the value held by the \l rotationAngle property, except in the case where
+ the user performs multiple rotations by removing and repositioning one of the touch
+ points, as described above. In this case, the total angle will be the sum of the
+ rotation angles for the multiple stages of the gesture.
+
+ \sa rotationAngle, lastRotationAngle
+*/
+/*!
+ \property QPinchGesture::lastRotationAngle
+ \brief the last reported angle covered by the gesture motion
+
+ The last rotation angle is the angle as reported in the \l rotationAngle property
+ when a previous gesture event was delivered for this gesture.
+
+ \sa rotationAngle, totalRotationAngle
+*/
+/*!
+ \property QPinchGesture::rotationAngle
+ \brief the angle covered by the gesture motion
+
+ \sa totalRotationAngle, lastRotationAngle
+*/
+
+/*!
+ \property QPinchGesture::startCenterPoint
+ \brief the starting position of the center point
+
+ \sa centerPoint, lastCenterPoint
+*/
+/*!
+ \property QPinchGesture::lastCenterPoint
+ \brief the last position of the center point recorded for this gesture
+
+ \sa centerPoint, startCenterPoint
+*/
+/*!
+ \property QPinchGesture::centerPoint
+ \brief the current center point
+
+ The center point is the midpoint between the two input points in the gesture.
+
+ \sa startCenterPoint, lastCenterPoint
+*/
+
+/*!
+ \internal
+*/
+QPinchGesture::QPinchGesture(QObject *parent)
+ : QGesture(*new QPinchGesturePrivate, parent)
{
- return d_func()->state;
+ d_func()->gestureType = Qt::PinchGesture;
}
-/*!
- Sets this gesture's recognition state to \a state and emits appropriate
- signals.
+QPinchGesture::WhatChanged QPinchGesture::whatChanged() const
+{
+ return d_func()->whatChanged;
+}
+
+void QPinchGesture::setWhatChanged(QPinchGesture::WhatChanged value)
+{
+ d_func()->whatChanged = value;
+}
- This functions emits the signals according to the old state and the new
- \a state, and it should be called after all the internal properties have been
- initialized.
- \sa started(), triggered(), finished(), canceled()
- */
-void QGesture::updateState(Qt::GestureState state)
+QPointF QPinchGesture::startCenterPoint() const
{
- Q_D(QGesture);
- if (d->state == state) {
- if (state == Qt::GestureUpdated)
- emit triggered();
- return;
- }
- const Qt::GestureState oldState = d->state;
- if (state != Qt::NoGesture && oldState > state) {
- // comparing the state as ints: state should only be changed from
- // started to (optionally) updated and to finished.
- d->state = state;
- qWarning("QGesture::updateState: incorrect new state");
- return;
- }
- if (oldState == Qt::NoGesture) {
- d->state = Qt::GestureStarted;
- emit started();
- }
- d->state = state;
- if (state == Qt::GestureUpdated)
- emit triggered();
- else if (state == Qt::GestureFinished)
- emit finished();
- else if (state == Qt::NoGesture)
- emit canceled();
-
- if (state == Qt::GestureFinished) {
- // gesture is finished, so we reset the internal state.
- d->state = Qt::NoGesture;
- }
-}
-
-/*!
- Sets the \a graphicsItem the gesture is filtering events for.
-
- The gesture will install an event filter to the \a graphicsItem and
- redirect them to the filterEvent() function.
-
- \sa graphicsItem()
-*/
-void QGesture::setGraphicsItem(QGraphicsItem *graphicsItem)
+ return d_func()->startCenterPoint;
+}
+
+QPointF QPinchGesture::lastCenterPoint() const
{
- Q_D(QGesture);
- if (d->graphicsItem && d->eventFilterProxyGraphicsItem)
- d->graphicsItem->removeSceneEventFilter(d->eventFilterProxyGraphicsItem);
- d->graphicsItem = graphicsItem;
- if (!d->eventFilterProxyGraphicsItem)
- d->eventFilterProxyGraphicsItem = new QEventFilterProxyGraphicsItem(this);
- if (graphicsItem)
- graphicsItem->installSceneEventFilter(d->eventFilterProxyGraphicsItem);
+ return d_func()->lastCenterPoint;
+}
+
+QPointF QPinchGesture::centerPoint() const
+{
+ return d_func()->centerPoint;
+}
+
+void QPinchGesture::setStartCenterPoint(const QPointF &value)
+{
+ d_func()->startCenterPoint = value;
+}
+
+void QPinchGesture::setLastCenterPoint(const QPointF &value)
+{
+ d_func()->lastCenterPoint = value;
+}
+
+void QPinchGesture::setCenterPoint(const QPointF &value)
+{
+ d_func()->centerPoint = value;
+}
+
+
+qreal QPinchGesture::totalScaleFactor() const
+{
+ return d_func()->totalScaleFactor;
+}
+
+qreal QPinchGesture::lastScaleFactor() const
+{
+ return d_func()->lastScaleFactor;
+}
+
+qreal QPinchGesture::scaleFactor() const
+{
+ return d_func()->scaleFactor;
+}
+
+void QPinchGesture::setTotalScaleFactor(qreal value)
+{
+ d_func()->totalScaleFactor = value;
+}
+
+void QPinchGesture::setLastScaleFactor(qreal value)
+{
+ d_func()->lastScaleFactor = value;
+}
+
+void QPinchGesture::setScaleFactor(qreal value)
+{
+ d_func()->scaleFactor = value;
+}
+
+
+qreal QPinchGesture::totalRotationAngle() const
+{
+ return d_func()->totalRotationAngle;
+}
+
+qreal QPinchGesture::lastRotationAngle() const
+{
+ return d_func()->lastRotationAngle;
+}
+
+qreal QPinchGesture::rotationAngle() const
+{
+ return d_func()->rotationAngle;
+}
+
+void QPinchGesture::setTotalRotationAngle(qreal value)
+{
+ d_func()->totalRotationAngle = value;
+}
+
+void QPinchGesture::setLastRotationAngle(qreal value)
+{
+ d_func()->lastRotationAngle = value;
+}
+
+void QPinchGesture::setRotationAngle(qreal value)
+{
+ d_func()->rotationAngle = value;
}
/*!
- Returns the graphics item the gesture is filtering events for.
+ \class QSwipeGesture
+ \since 4.6
+ \brief The QSwipeGesture class describes a swipe gesture made by the user.
+ \ingroup gestures
+
+ \image swipegesture.png
- \sa setGraphicsItem()
+ \sa {Gestures Programming}, QPanGesture, QPinchGesture
*/
-QGraphicsItem* QGesture::graphicsItem() const
+
+/*!
+ \enum QSwipeGesture::SwipeDirection
+
+ This enum describes the possible directions for the gesture's motion
+ along the horizontal and vertical axes.
+
+ \value NoDirection The gesture had no motion associated with it on a particular axis.
+ \value Left The gesture involved a horizontal motion to the left.
+ \value Right The gesture involved a horizontal motion to the right.
+ \value Up The gesture involved an upward vertical motion.
+ \value Down The gesture involved a downward vertical motion.
+*/
+
+/*!
+ \property QSwipeGesture::horizontalDirection
+ \brief the horizontal direction of the gesture
+
+ If the gesture has a horizontal component, the horizontal direction
+ is either Left or Right; otherwise, it is NoDirection.
+
+ \sa verticalDirection, swipeAngle
+*/
+
+/*!
+ \property QSwipeGesture::verticalDirection
+ \brief the vertical direction of the gesture
+
+ If the gesture has a vertical component, the vertical direction
+ is either Up or Down; otherwise, it is NoDirection.
+
+ \sa horizontalDirection, swipeAngle
+*/
+
+/*!
+ \property QSwipeGesture::swipeAngle
+ \brief the angle of the motion associated with the gesture
+
+ If the gesture has either a horizontal or vertical component, the
+ swipe angle describes the angle between the direction of motion and the
+ x-axis as defined using the standard widget
+ \l{The Coordinate System}{coordinate system}.
+
+ \sa horizontalDirection, verticalDirection
+*/
+
+/*!
+ \internal
+*/
+QSwipeGesture::QSwipeGesture(QObject *parent)
+ : QGesture(*new QSwipeGesturePrivate, parent)
+{
+ d_func()->gestureType = Qt::SwipeGesture;
+}
+
+QSwipeGesture::SwipeDirection QSwipeGesture::horizontalDirection() const
{
- return d_func()->graphicsItem;
+ Q_D(const QSwipeGesture);
+ if (d->swipeAngle < 0 || d->swipeAngle == 90 || d->swipeAngle == 270)
+ return QSwipeGesture::NoDirection;
+ else if (d->swipeAngle < 90 || d->swipeAngle > 270)
+ return QSwipeGesture::Right;
+ else
+ return QSwipeGesture::Left;
}
-/*! \fn void QGesture::reset()
+QSwipeGesture::SwipeDirection QSwipeGesture::verticalDirection() const
+{
+ Q_D(const QSwipeGesture);
+ if (d->swipeAngle <= 0 || d->swipeAngle == 180)
+ return QSwipeGesture::NoDirection;
+ else if (d->swipeAngle < 180)
+ return QSwipeGesture::Up;
+ else
+ return QSwipeGesture::Down;
+}
- Resets the internal state of the gesture. This function might be called by
- the filterEvent() implementation in a derived class, or by the user to
- cancel a gesture. The base class implementation calls
- updateState(Qt::NoGesture) which emits the canceled()
- signal if the state() of the gesture indicated it was active.
-*/
-void QGesture::reset()
+qreal QSwipeGesture::swipeAngle() const
+{
+ return d_func()->swipeAngle;
+}
+
+void QSwipeGesture::setSwipeAngle(qreal value)
{
- updateState(Qt::NoGesture);
+ d_func()->swipeAngle = value;
}
QT_END_NAMESPACE
diff --git a/src/gui/kernel/qgesture.h b/src/gui/kernel/qgesture.h
index 440565e..02eb526 100644
--- a/src/gui/kernel/qgesture.h
+++ b/src/gui/kernel/qgesture.h
@@ -51,11 +51,12 @@
QT_BEGIN_HEADER
+Q_DECLARE_METATYPE(Qt::GestureState)
+
QT_BEGIN_NAMESPACE
QT_MODULE(Gui)
-class QGraphicsItem;
class QGesturePrivate;
class Q_GUI_EXPORT QGesture : public QObject
{
@@ -63,37 +64,150 @@ class Q_GUI_EXPORT QGesture : public QObject
Q_DECLARE_PRIVATE(QGesture)
Q_PROPERTY(Qt::GestureState state READ state)
- Q_PROPERTY(QObject* gestureTarget READ gestureTarget WRITE setGestureTarget)
+ Q_PROPERTY(Qt::GestureType gestureType READ gestureType)
+ Q_PROPERTY(QPointF hotSpot READ hotSpot WRITE setHotSpot RESET unsetHotSpot)
+ Q_PROPERTY(bool hasHotSpot READ hasHotSpot)
+ Q_PROPERTY(QObject* targetObject READ targetObject WRITE setTargetObject)
public:
- explicit QGesture(QObject *gestureTarget = 0, QObject *parent = 0);
+ explicit QGesture(QObject *parent = 0);
~QGesture();
- virtual bool filterEvent(QEvent *event) = 0;
+ Qt::GestureType gestureType() const;
- void setGestureTarget(QObject *object);
- QObject* gestureTarget() const;
+ Qt::GestureState state() const;
- void setGraphicsItem(QGraphicsItem *);
- QGraphicsItem *graphicsItem() const;
+ QObject *targetObject() const;
+ void setTargetObject(QObject *value);
- Qt::GestureState state() const;
+ QPointF hotSpot() const;
+ void setHotSpot(const QPointF &value);
+ bool hasHotSpot() const;
+ void unsetHotSpot();
protected:
- QGesture(QGesturePrivate &dd, QObject *gestureTarget, QObject *parent);
- bool eventFilter(QObject*, QEvent*);
+ QGesture(QGesturePrivate &dd, QObject *parent);
+
+private:
+ friend class QGestureEvent;
+ friend class QGestureRecognizer;
+ friend class QGestureManager;
+};
- virtual void reset();
- void updateState(Qt::GestureState state);
+class QPanGesturePrivate;
+class Q_GUI_EXPORT QPanGesture : public QGesture
+{
+ Q_OBJECT
+ Q_DECLARE_PRIVATE(QPanGesture)
-Q_SIGNALS:
- void started();
- void triggered();
- void finished();
- void canceled();
+ Q_PROPERTY(QSizeF totalOffset READ totalOffset WRITE setTotalOffset)
+ Q_PROPERTY(QSizeF lastOffset READ lastOffset WRITE setLastOffset)
+ Q_PROPERTY(QSizeF offset READ offset WRITE setOffset)
+ Q_PROPERTY(qreal acceleration READ acceleration WRITE setAcceleration)
-private:
- friend class QWidget;
+public:
+ QPanGesture(QObject *parent = 0);
+
+ QSizeF totalOffset() const;
+ QSizeF lastOffset() const;
+ QSizeF offset() const;
+ qreal acceleration() const;
+
+ void setTotalOffset(const QSizeF &value);
+ void setLastOffset(const QSizeF &value);
+ void setOffset(const QSizeF &value);
+ void setAcceleration(qreal value);
+
+ friend class QPanGestureRecognizer;
+ friend class QWinNativePanGestureRecognizer;
+};
+
+class QPinchGesturePrivate;
+class Q_GUI_EXPORT QPinchGesture : public QGesture
+{
+ Q_OBJECT
+ Q_DECLARE_PRIVATE(QPinchGesture)
+
+public:
+ enum WhatChange {
+ ScaleFactorChanged = 0x1,
+ RotationAngleChanged = 0x2,
+ CenterPointChanged = 0x4
+ };
+ Q_DECLARE_FLAGS(WhatChanged, WhatChange)
+
+ Q_PROPERTY(WhatChanged whatChanged READ whatChanged WRITE setWhatChanged)
+
+ Q_PROPERTY(qreal totalScaleFactor READ totalScaleFactor WRITE setTotalScaleFactor)
+ Q_PROPERTY(qreal lastScaleFactor READ lastScaleFactor WRITE setLastScaleFactor)
+ Q_PROPERTY(qreal scaleFactor READ scaleFactor WRITE setScaleFactor)
+
+ Q_PROPERTY(qreal totalRotationAngle READ totalRotationAngle WRITE setTotalRotationAngle)
+ Q_PROPERTY(qreal lastRotationAngle READ lastRotationAngle WRITE setLastRotationAngle)
+ Q_PROPERTY(qreal rotationAngle READ rotationAngle WRITE setRotationAngle)
+
+ Q_PROPERTY(QPointF startCenterPoint READ startCenterPoint WRITE setStartCenterPoint)
+ Q_PROPERTY(QPointF lastCenterPoint READ lastCenterPoint WRITE setLastCenterPoint)
+ Q_PROPERTY(QPointF centerPoint READ centerPoint WRITE setCenterPoint)
+
+public:
+ QPinchGesture(QObject *parent = 0);
+
+ WhatChanged whatChanged() const;
+ void setWhatChanged(WhatChanged value);
+
+ QPointF startCenterPoint() const;
+ QPointF lastCenterPoint() const;
+ QPointF centerPoint() const;
+ void setStartCenterPoint(const QPointF &value);
+ void setLastCenterPoint(const QPointF &value);
+ void setCenterPoint(const QPointF &value);
+
+ qreal totalScaleFactor() const;
+ qreal lastScaleFactor() const;
+ qreal scaleFactor() const;
+ void setTotalScaleFactor(qreal value);
+ void setLastScaleFactor(qreal value);
+ void setScaleFactor(qreal value);
+
+ qreal totalRotationAngle() const;
+ qreal lastRotationAngle() const;
+ qreal rotationAngle() const;
+ void setTotalRotationAngle(qreal value);
+ void setLastRotationAngle(qreal value);
+ void setRotationAngle(qreal value);
+
+ friend class QPinchGestureRecognizer;
+};
+
+QT_END_NAMESPACE
+
+Q_DECLARE_METATYPE(QPinchGesture::WhatChanged)
+
+QT_BEGIN_NAMESPACE
+
+class QSwipeGesturePrivate;
+class Q_GUI_EXPORT QSwipeGesture : public QGesture
+{
+ Q_OBJECT
+ Q_DECLARE_PRIVATE(QSwipeGesture)
+ Q_ENUMS(SwipeDirection)
+
+ Q_PROPERTY(SwipeDirection horizontalDirection READ horizontalDirection STORED false)
+ Q_PROPERTY(SwipeDirection verticalDirection READ verticalDirection STORED false)
+ Q_PROPERTY(qreal swipeAngle READ swipeAngle WRITE setSwipeAngle)
+
+public:
+ enum SwipeDirection { NoDirection, Left, Right, Up, Down };
+ QSwipeGesture(QObject *parent = 0);
+
+ SwipeDirection horizontalDirection() const;
+ SwipeDirection verticalDirection() const;
+
+ qreal swipeAngle() const;
+ void setSwipeAngle(qreal value);
+
+ friend class QSwipeGestureRecognizer;
};
QT_END_NAMESPACE
diff --git a/src/gui/kernel/qgesture_p.h b/src/gui/kernel/qgesture_p.h
index 52e399f..7f69a4e 100644
--- a/src/gui/kernel/qgesture_p.h
+++ b/src/gui/kernel/qgesture_p.h
@@ -61,29 +61,83 @@
QT_BEGIN_NAMESPACE
-class QObject;
-class QGraphicsItem;
class QGesturePrivate : public QObjectPrivate
{
Q_DECLARE_PUBLIC(QGesture)
public:
QGesturePrivate()
- : gestureTarget(0), graphicsItem(0), eventFilterProxyGraphicsItem(0),
- state(Qt::NoGesture), implicitGesture(false)
+ : gestureType(Qt::CustomGesture), state(Qt::NoGesture), isHotSpotSet(false),
+ targetObject(0), accept(true)
{
}
- virtual void setupGestureTarget(QObject *o);
+ Qt::GestureType gestureType;
+ Qt::GestureState state;
+ QPointF hotSpot;
+ bool isHotSpotSet;
+ QObject *targetObject;
+ bool accept;
+};
- QPointer<QObject> gestureTarget;
- QGraphicsItem *graphicsItem;
- QGraphicsItem *eventFilterProxyGraphicsItem;
+class QPanGesturePrivate : public QGesturePrivate
+{
+ Q_DECLARE_PUBLIC(QPanGesture)
- Qt::GestureState state;
+public:
+ QPanGesturePrivate()
+ : acceleration(0)
+ {
+ }
+
+ QSizeF totalOffset;
+ QSizeF lastOffset;
+ QSizeF offset;
+ QPoint lastPosition;
+ qreal acceleration;
+};
+
+class QPinchGesturePrivate : public QGesturePrivate
+{
+ Q_DECLARE_PUBLIC(QPinchGesture)
+
+public:
+ QPinchGesturePrivate()
+ : whatChanged(0), totalScaleFactor(0), lastScaleFactor(0), scaleFactor(0),
+ totalRotationAngle(0), lastRotationAngle(0), rotationAngle(0)
+ {
+ }
+
+ QPinchGesture::WhatChanged whatChanged;
+
+ QPointF startCenterPoint;
+ QPointF lastCenterPoint;
+ QPointF centerPoint;
+
+ qreal totalScaleFactor;
+ qreal lastScaleFactor;
+ qreal scaleFactor;
+
+ qreal totalRotationAngle;
+ qreal lastRotationAngle;
+ qreal rotationAngle;
+};
+
+class QSwipeGesturePrivate : public QGesturePrivate
+{
+ Q_DECLARE_PUBLIC(QSwipeGesture)
+
+public:
+ QSwipeGesturePrivate()
+ : horizontalDirection(QSwipeGesture::NoDirection),
+ verticalDirection(QSwipeGesture::NoDirection),
+ swipeAngle(0)
+ {
+ }
- // the flag specifies if the gesture was created implicitely by Qt.
- bool implicitGesture;
+ QSwipeGesture::SwipeDirection horizontalDirection;
+ QSwipeGesture::SwipeDirection verticalDirection;
+ qreal swipeAngle;
};
QT_END_NAMESPACE
diff --git a/src/gui/kernel/qgesturemanager.cpp b/src/gui/kernel/qgesturemanager.cpp
new file mode 100644
index 0000000..0f0aef2
--- /dev/null
+++ b/src/gui/kernel/qgesturemanager.cpp
@@ -0,0 +1,467 @@
+/****************************************************************************
+**
+** 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 QtGui module 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 "private/qgesturemanager_p.h"
+#include "private/qstandardgestures_p.h"
+#include "private/qwidget_p.h"
+#include "private/qgesture_p.h"
+#include "private/qgraphicsitem_p.h"
+#include "qgesture.h"
+#include "qevent.h"
+#include "qgraphicsitem.h"
+
+#ifdef Q_WS_MAC
+#include "qmacgesturerecognizer_mac_p.h"
+#endif
+
+#include "qdebug.h"
+
+// #define GESTURE_DEBUG
+#ifndef GESTURE_DEBUG
+# define DEBUG if (0) qDebug
+#else
+# define DEBUG qDebug
+#endif
+
+QT_BEGIN_NAMESPACE
+
+QGestureManager::QGestureManager(QObject *parent)
+ : QObject(parent), state(NotGesture), lastCustomGestureId(0)
+{
+ qRegisterMetaType<Qt::GestureState>();
+
+#if defined(Q_WS_MAC)
+ registerGestureRecognizer(new QMacSwipeGestureRecognizer);
+ registerGestureRecognizer(new QMacPinchGestureRecognizer);
+ #if defined(QT_MAC_USE_COCOA)
+ registerGestureRecognizer(new QMacPanGestureRecognizer);
+ #endif
+#else
+ registerGestureRecognizer(new QPanGestureRecognizer);
+#endif
+}
+
+QGestureManager::~QGestureManager()
+{
+
+}
+
+Qt::GestureType QGestureManager::registerGestureRecognizer(QGestureRecognizer *recognizer)
+{
+ QGesture *dummy = recognizer->createGesture(0);
+ if (!dummy) {
+ qWarning("QGestureManager::registerGestureRecognizer: the recognizer doesn't provide gesture object");
+ return Qt::GestureType(0);
+ }
+ Qt::GestureType type = dummy->gestureType();
+ if (type == Qt::CustomGesture) {
+ // generate a new custom gesture id
+ ++lastCustomGestureId;
+ type = Qt::GestureType(Qt::CustomGesture + lastCustomGestureId);
+ }
+ recognizers.insertMulti(type, recognizer);
+ delete dummy;
+ return type;
+}
+
+void QGestureManager::unregisterGestureRecognizer(Qt::GestureType)
+{
+
+}
+
+QGesture* QGestureManager::getState(QObject *object, Qt::GestureType type)
+{
+ // if the widget is being deleted we should be carefull and not to
+ // create a new state, as it will create QWeakPointer which doesnt work
+ // from the destructor.
+ if (object->isWidgetType()) {
+ if (static_cast<QWidget *>(object)->d_func()->data.in_destructor)
+ return 0;
+ }
+
+ QWeakPointer<QGesture> state = objectGestures.value(QGestureManager::ObjectGesture(object, type));
+ if (!state) {
+ QGestureRecognizer *recognizer = recognizers.value(type);
+ if (recognizer) {
+ state = recognizer->createGesture(object);
+ if (!state)
+ return 0;
+ if (state.data()->gestureType() == Qt::CustomGesture) {
+ // if the recognizer didn't fill in the gesture type, then this
+ // is a custom gesture with autogenerated it and we fill it.
+ state.data()->d_func()->gestureType = type;
+ }
+ objectGestures.insert(QGestureManager::ObjectGesture(object, type), state);
+ gestureToRecognizer[state.data()] = recognizer;
+ }
+ }
+ return state.data();
+}
+
+bool QGestureManager::filterEvent(QObject *receiver, QEvent *event)
+{
+ QSet<QGesture *> triggeredGestures;
+ QSet<QGesture *> finishedGestures;
+ QSet<QGesture *> newMaybeGestures;
+ QSet<QGesture *> canceledGestures;
+ QSet<QGesture *> notGestures;
+
+ QGraphicsObject *graphicsObject = qobject_cast<QGraphicsObject *>(receiver);
+ if (receiver->isWidgetType() || graphicsObject) {
+ QMap<QObject *, Qt::GestureType> contexts;
+ if (receiver->isWidgetType()) {
+ QWidget *w = static_cast<QWidget *>(receiver);
+ if (!w->d_func()->gestureContext.isEmpty()) {
+ typedef QMap<Qt::GestureType, Qt::GestureContext>::const_iterator ContextIterator;
+ for(ContextIterator it = w->d_func()->gestureContext.begin(),
+ e = w->d_func()->gestureContext.end(); it != e; ++it) {
+ contexts.insertMulti(w, it.key());
+ }
+ }
+ // find all gesture contexts for the widget tree
+ w = w->parentWidget();
+ while (w)
+ {
+ typedef QMap<Qt::GestureType, Qt::GestureContext>::const_iterator ContextIterator;
+ for (ContextIterator it = w->d_func()->gestureContext.begin(),
+ e = w->d_func()->gestureContext.end(); it != e; ++it) {
+ if (it.value() == Qt::WidgetWithChildrenGesture)
+ contexts.insertMulti(w, it.key());
+ }
+ w = w->parentWidget();
+ }
+ } else {
+ QGraphicsObject *item = graphicsObject;
+ if (!item->QGraphicsItem::d_func()->gestureContext.isEmpty()) {
+ typedef QMap<Qt::GestureType, Qt::GestureContext>::const_iterator ContextIterator;
+ for(ContextIterator it = item->QGraphicsItem::d_func()->gestureContext.begin(),
+ e = item->QGraphicsItem::d_func()->gestureContext.end(); it != e; ++it) {
+ contexts.insertMulti(item, it.key());
+ }
+ }
+ // find all gesture contexts for the widget tree
+ item = item->parentObject();
+ while (item)
+ {
+ typedef QMap<Qt::GestureType, Qt::GestureContext>::const_iterator ContextIterator;
+ for (ContextIterator it = item->QGraphicsItem::d_func()->gestureContext.begin(),
+ e = item->QGraphicsItem::d_func()->gestureContext.end(); it != e; ++it) {
+ if (it.value() == Qt::WidgetWithChildrenGesture)
+ contexts.insertMulti(item, it.key());
+ }
+ item = item->parentObject();
+ }
+ }
+ // filter the event through recognizers
+ typedef QMap<QObject *, Qt::GestureType>::const_iterator ContextIterator;
+ for (ContextIterator cit = contexts.begin(), ce = contexts.end(); cit != ce; ++cit) {
+ Qt::GestureType gestureType = cit.value();
+ QMap<Qt::GestureType, QGestureRecognizer *>::const_iterator
+ rit = recognizers.lowerBound(gestureType),
+ re = recognizers.upperBound(gestureType);
+ for (; rit != re; ++rit) {
+ QGestureRecognizer *recognizer = rit.value();
+ QObject *target = cit.key();
+ QGesture *state = getState(target, gestureType);
+ if (!state)
+ continue;
+ QGestureRecognizer::Result result = recognizer->filterEvent(state, target, event);
+ QGestureRecognizer::Result type = result & QGestureRecognizer::ResultState_Mask;
+ if (type == QGestureRecognizer::GestureTriggered) {
+ DEBUG() << "QGestureManager: gesture triggered: " << state;
+ triggeredGestures << state;
+ } else if (type == QGestureRecognizer::GestureFinished) {
+ DEBUG() << "QGestureManager: gesture finished: " << state;
+ finishedGestures << state;
+ } else if (type == QGestureRecognizer::MaybeGesture) {
+ DEBUG() << "QGestureManager: maybe gesture: " << state;
+ newMaybeGestures << state;
+ } else if (type == QGestureRecognizer::NotGesture) {
+ DEBUG() << "QGestureManager: not gesture: " << state;
+ notGestures << state;
+ } else if (type == QGestureRecognizer::Ignore) {
+ DEBUG() << "QGestureManager: gesture ignored the event: " << state;
+ } else {
+ DEBUG() << "QGestureManager: hm, lets assume the recognizer ignored the event: " << state;
+ }
+ if (result & QGestureRecognizer::ConsumeEventHint) {
+ DEBUG() << "QGestureManager: we were asked to consume the event: " << state;
+ //TODO: consume events if asked
+ }
+ }
+ }
+ } else if (QGesture *state = qobject_cast<QGesture*>(receiver)) {
+ if (QGestureRecognizer *recognizer = gestureToRecognizer.value(state)) {
+ QGestureRecognizer::Result result = recognizer->filterEvent(state, state, event);
+ QGestureRecognizer::Result type = result & QGestureRecognizer::ResultState_Mask;
+ if (type == QGestureRecognizer::GestureTriggered) {
+ DEBUG() << "QGestureManager: gesture triggered: " << state;
+ triggeredGestures << state;
+ } else if (type == QGestureRecognizer::GestureFinished) {
+ DEBUG() << "QGestureManager: gesture finished: " << state;
+ finishedGestures << state;
+ } else if (type == QGestureRecognizer::MaybeGesture) {
+ DEBUG() << "QGestureManager: maybe gesture: " << state;
+ newMaybeGestures << state;
+ } else if (type == QGestureRecognizer::NotGesture) {
+ DEBUG() << "QGestureManager: not gesture: " << state;
+ notGestures << state;
+ } else if (type == QGestureRecognizer::Ignore) {
+ DEBUG() << "QGestureManager: gesture ignored the event: " << state;
+ } else {
+ DEBUG() << "QGestureManager: hm, lets assume the recognizer ignored the event: " << state;
+ }
+ }
+ } else {
+ return false;
+ }
+
+ QSet<QGesture *> startedGestures = triggeredGestures - activeGestures;
+ triggeredGestures &= activeGestures;
+
+ // check if a running gesture switched back to maybe state
+ QSet<QGesture *> activeToMaybeGestures = activeGestures & newMaybeGestures;
+
+ // check if a running gesture switched back to not gesture state, i.e. were canceled
+ QSet<QGesture *> activeToCancelGestures = activeGestures & notGestures;
+ canceledGestures += activeToCancelGestures;
+
+ // start timers for new gestures in maybe state
+ foreach (QGesture *state, newMaybeGestures) {
+ QBasicTimer &timer = maybeGestures[state];
+ if (!timer.isActive())
+ timer.start(3000, this);
+ }
+ // kill timers for gestures that were in maybe state
+ QSet<QGesture *> notMaybeGestures = (startedGestures | triggeredGestures | finishedGestures | canceledGestures | notGestures);
+ foreach(QGesture *gesture, notMaybeGestures) {
+ QMap<QGesture *, QBasicTimer>::iterator it =
+ maybeGestures.find(gesture);
+ if (it != maybeGestures.end()) {
+ it.value().stop();
+ maybeGestures.erase(it);
+ }
+ }
+
+ Q_ASSERT((startedGestures & finishedGestures).isEmpty());
+ Q_ASSERT((startedGestures & newMaybeGestures).isEmpty());
+ Q_ASSERT((startedGestures & canceledGestures).isEmpty());
+ Q_ASSERT((finishedGestures & newMaybeGestures).isEmpty());
+ Q_ASSERT((finishedGestures & canceledGestures).isEmpty());
+ Q_ASSERT((canceledGestures & newMaybeGestures).isEmpty());
+
+ QSet<QGesture *> notStarted = finishedGestures - activeGestures;
+ if (!notStarted.isEmpty()) {
+ // there are some gestures that claim to be finished, but never started.
+ // probably those are "singleshot" gestures so we'll fake the started state.
+ foreach (QGesture *gesture, notStarted)
+ gesture->d_func()->state = Qt::GestureStarted;
+ deliverEvents(notStarted, receiver);
+ }
+
+ activeGestures += startedGestures;
+ // sanity check: all triggered gestures should already be in active gestures list
+ Q_ASSERT((activeGestures & triggeredGestures).size() == triggeredGestures.size());
+ activeGestures -= finishedGestures;
+ activeGestures -= activeToMaybeGestures;
+ activeGestures -= canceledGestures;
+
+ // set the proper gesture state on each gesture
+ foreach (QGesture *gesture, startedGestures)
+ gesture->d_func()->state = Qt::GestureStarted;
+ foreach (QGesture *gesture, triggeredGestures)
+ gesture->d_func()->state = Qt::GestureUpdated;
+ foreach (QGesture *gesture, finishedGestures)
+ gesture->d_func()->state = Qt::GestureFinished;
+ foreach (QGesture *gesture, canceledGestures)
+ gesture->d_func()->state = Qt::GestureCanceled;
+ foreach (QGesture *gesture, activeToMaybeGestures)
+ gesture->d_func()->state = Qt::GestureFinished;
+
+ if (!activeGestures.isEmpty() || !maybeGestures.isEmpty() ||
+ !startedGestures.isEmpty() || !triggeredGestures.isEmpty() ||
+ !finishedGestures.isEmpty() || !canceledGestures.isEmpty()) {
+ DEBUG() << "QGestureManager::filterEvent:"
+ << "\n\tactiveGestures:" << activeGestures
+ << "\n\tmaybeGestures:" << maybeGestures.keys()
+ << "\n\tstarted:" << startedGestures
+ << "\n\ttriggered:" << triggeredGestures
+ << "\n\tfinished:" << finishedGestures
+ << "\n\tcanceled:" << canceledGestures;
+ }
+
+ deliverEvents(startedGestures+triggeredGestures+finishedGestures+canceledGestures, receiver);
+
+ // reset gestures that ended
+ QSet<QGesture *> endedGestures = finishedGestures + canceledGestures;
+ foreach (QGesture *gesture, endedGestures) {
+ if (QGestureRecognizer *recognizer = gestureToRecognizer.value(gesture, 0)) {
+ recognizer->reset(gesture);
+ }
+ gestureTargets.remove(gesture);
+ }
+ return false;
+}
+
+void QGestureManager::deliverEvents(const QSet<QGesture*> &gestures, QObject *lastReceiver)
+{
+ if (gestures.isEmpty())
+ return;
+
+ // group gestures by widgets
+ typedef QMap<QObject *, QList<QGesture *> > GesturesPerReceiver;
+ GesturesPerReceiver groupedGestures;
+ // for conflicted gestures the key is always the innermost widget (i.e. the child)
+ GesturesPerReceiver conflictedGestures;
+ QMultiHash<QObject *, QGesture *> objectGestures;
+
+ foreach (QGesture *gesture, gestures) {
+ QObject *target = gestureTargets.value(gesture, 0);
+ if (!target) {
+ Q_ASSERT(gesture->state() == Qt::GestureStarted);
+ if (gesture->hasHotSpot()) {
+ // guess the target using the hotspot of the gesture
+ QPoint pt = gesture->hotSpot().toPoint();
+ if (!pt.isNull()) {
+ if (QWidget *w = qApp->topLevelAt(pt))
+ target = w->childAt(w->mapFromGlobal(pt));
+ }
+ }
+ if (!target) {
+ target = gesture->targetObject();
+ if (!target)
+ target = lastReceiver;
+ }
+ }
+ if (target) {
+ gestureTargets.insert(gesture, target);
+ if (target->isWidgetType())
+ objectGestures.insert(target, gesture);
+ groupedGestures[target].append(gesture);
+ } else {
+ qWarning() << "QGestureManager::deliverEvent: could not find the target for gesture"
+ << gesture->gestureType();
+ }
+ }
+
+ typedef QMultiHash<QObject *, QGesture *>::const_iterator ObjectGesturesIterator;
+ for (ObjectGesturesIterator it = objectGestures.begin(), e = objectGestures.end(); it != e; ++it) {
+ QObject *object1 = it.key();
+ QWidget *widget1 = qobject_cast<QWidget *>(object1);
+ QGraphicsObject *item1 = qobject_cast<QGraphicsObject *>(object1);
+ QGesture *gesture1 = it.value();
+ ObjectGesturesIterator cit = it;
+ for (++cit; cit != e; ++cit) {
+ QObject *object2 = cit.key();
+ QWidget *widget2 = qobject_cast<QWidget *>(object2);
+ QGraphicsObject *item2 = qobject_cast<QGraphicsObject *>(object2);
+ QGesture *gesture2 = cit.value();
+ // TODO: ugly, rewrite this.
+ if ((widget1 && widget2 && widget2->isAncestorOf(widget1)) ||
+ (item1 && item2 && item2->isAncestorOf(item1))) {
+ groupedGestures[object2].removeOne(gesture2);
+ groupedGestures[object1].removeOne(gesture1);
+ conflictedGestures[object1].append(gesture1);
+ } else if ((widget1 && widget2 && widget1->isAncestorOf(widget2)) ||
+ (item1 && item2 && item1->isAncestorOf(item2))) {
+ groupedGestures[object2].removeOne(gesture2);
+ groupedGestures[object1].removeOne(gesture1);
+ conflictedGestures[object2].append(gesture2);
+ }
+ }
+ }
+
+ DEBUG() << "deliverEvents: conflicted =" << conflictedGestures.values()
+ << " grouped =" << groupedGestures.values();
+
+ // if there are conflicting gestures, send the GestureOverride event
+ for (GesturesPerReceiver::const_iterator it = conflictedGestures.begin(),
+ e = conflictedGestures.end(); it != e; ++it) {
+ DEBUG() << "QGestureManager::deliverEvents: sending GestureOverride to"
+ << it.key()
+ << " gestures:" << it.value();
+ QGestureEvent event(it.value());
+ event.t = QEvent::GestureOverride;
+ event.ignore();
+ QApplication::sendEvent(it.key(), &event);
+ if (!event.isAccepted()) {
+ // nobody accepted the GestureOverride, put it back to deliver to
+ // the closest context (i.e. to the inner-most widget).
+ DEBUG() <<" override was not accepted";
+ groupedGestures[it.key()].append(it.value());
+ }
+ }
+
+ for (GesturesPerReceiver::const_iterator it = groupedGestures.begin(),
+ e = groupedGestures.end(); it != e; ++it) {
+ if (!it.value().isEmpty()) {
+ DEBUG() << "QGestureManager::deliverEvents: sending to" << it.key()
+ << " gestures:" << it.value();
+ QGestureEvent event(it.value());
+ QApplication::sendEvent(it.key(), &event);
+ }
+ }
+}
+
+void QGestureManager::timerEvent(QTimerEvent *event)
+{
+ QMap<QGesture*, QBasicTimer>::iterator it = maybeGestures.begin(),
+ e = maybeGestures.end();
+ for (; it != e; ) {
+ QBasicTimer &timer = it.value();
+ Q_ASSERT(timer.isActive());
+ if (timer.timerId() == event->timerId()) {
+ timer.stop();
+ QGesture *gesture = it.key();
+ it = maybeGestures.erase(it);
+ DEBUG() << "QGestureManager::timerEvent: gesture stopped due to timeout:" << gesture;
+ QGestureRecognizer *recognizer = gestureToRecognizer.value(gesture, 0);
+ if (recognizer)
+ recognizer->reset(gesture);
+ } else {
+ ++it;
+ }
+ }
+}
+
+QT_END_NAMESPACE
+
+#include "moc_qgesturemanager_p.cpp"
diff --git a/src/gui/kernel/qgesturemanager_p.h b/src/gui/kernel/qgesturemanager_p.h
new file mode 100644
index 0000000..c61819f
--- /dev/null
+++ b/src/gui/kernel/qgesturemanager_p.h
@@ -0,0 +1,125 @@
+/****************************************************************************
+**
+** 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 QtGui module 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 QGESTUREMANAGER_P_H
+#define QGESTUREMANAGER_P_H
+
+//
+// W A R N I N G
+// -------------
+//
+// This file is not part of the Qt API. It exists for the convenience
+// of other Qt classes. This header file may change from version to
+// version without notice, or even be removed.
+//
+// We mean it.
+//
+
+#include "qobject.h"
+#include "qbasictimer.h"
+#include "private/qwidget_p.h"
+#include "qgesturerecognizer.h"
+
+QT_BEGIN_NAMESPACE
+
+class QBasicTimer;
+class QGestureManager : public QObject
+{
+ Q_OBJECT
+public:
+ QGestureManager(QObject *parent);
+ ~QGestureManager();
+
+ Qt::GestureType registerGestureRecognizer(QGestureRecognizer *recognizer);
+ void unregisterGestureRecognizer(Qt::GestureType type);
+
+ bool filterEvent(QObject *receiver, QEvent *event);
+
+ // declared in qapplication.cpp
+ static QGestureManager* instance();
+
+protected:
+ void timerEvent(QTimerEvent *event);
+
+private:
+ QMultiMap<Qt::GestureType, QGestureRecognizer *> recognizers;
+
+ QSet<QGesture *> activeGestures;
+ QMap<QGesture *, QBasicTimer> maybeGestures;
+
+ enum State {
+ Gesture,
+ NotGesture,
+ MaybeGesture // this means timers are up and waiting for some
+ // more events, and input events are handled by
+ // gesture recognizer explicitely
+ } state;
+
+ struct ObjectGesture
+ {
+ QWeakPointer<QObject> object;
+ Qt::GestureType gesture;
+
+ ObjectGesture(QObject *o, const Qt::GestureType &g) : object(o), gesture(g) { }
+ inline bool operator<(const ObjectGesture& rhs) const
+ {
+ if (object.data() < rhs.object.data())
+ return true;
+ if (object == rhs.object)
+ return gesture < rhs.gesture;
+ return false;
+ }
+ };
+
+ QMap<ObjectGesture, QWeakPointer<QGesture> > objectGestures;
+ QMap<QGesture *, QGestureRecognizer *> gestureToRecognizer;
+
+ QHash<QGesture *, QObject *> gestureTargets;
+
+ int lastCustomGestureId;
+
+ QGesture *getState(QObject *widget, Qt::GestureType gesture);
+ void deliverEvents(const QSet<QGesture *> &gestures, QObject *lastReceiver);
+};
+
+QT_END_NAMESPACE
+
+#endif // QGESTUREMANAGER_P_H
diff --git a/src/gui/kernel/qgesturerecognizer.cpp b/src/gui/kernel/qgesturerecognizer.cpp
new file mode 100644
index 0000000..9de3bcc
--- /dev/null
+++ b/src/gui/kernel/qgesturerecognizer.cpp
@@ -0,0 +1,200 @@
+/****************************************************************************
+**
+** 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 QtGui module 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 "qgesturerecognizer.h"
+
+#include "private/qgesture_p.h"
+
+QT_BEGIN_NAMESPACE
+
+/*!
+ \class QGestureRecognizer
+ \since 4.6
+ \brief The QGestureRecognizer class provides the infrastructure for gesture recognition.
+ \ingroup gestures
+
+ Gesture recognizers are responsible for creating and managing QGesture objects and
+ monitoring input events sent to QWidget and QGraphicsObject subclasses.
+ QGestureRecognizer is the base class for implementing custom gestures.
+
+ Developers that only need to provide gesture recognition for standard gestures do not
+ need to use this class directly. Instances will be created behind the scenes by the
+ framework.
+
+ \section1 Recognizing Gestures
+
+ The process of recognizing gestures involves filtering input events sent to specific
+ objects, and modifying the associated QGesture objects to include relevant information
+ about the user's input.
+
+ Gestures are created when the framework calls createGesture() to handle user input
+ for a particular instance of a QWidget or QGraphicsObject subclass. A QGesture object
+ is created for each widget or item that is configured to use gestures.
+
+ Once a QGesture has been created for a target object, the gesture recognizer will
+ receive events for it in its filterEvent() handler function.
+
+ When a gesture is canceled, the reset() function is called, giving the recognizer the
+ chance to update the appropriate properties in the corresponding QGesture object.
+
+ \section1 Supporting New Gestures
+
+ To add support for new gestures, you need to derive from QGestureRecognizer to create
+ a custom recognizer class, construct an instance of this class, and register it with
+ the application by calling QApplication::registerGestureRecognizer(). You can also
+ subclass QGesture to create a custom gesture class, or rely on dynamic properties
+ to express specific details of the gesture you want to handle.
+
+ Your custom QGestureRecognizer subclass needs to reimplement the filterEvent() function
+ to handle and filter the incoming input events for QWidget and QGraphicsObject subclasses.
+ Although the logic for gesture recognition is implemented in this function, you can
+ store persistent information about the state of the recognition process in the QGesture
+ object supplied. The filterEvent() function must return a value of Qt::GestureState that
+ indicates the state of recognition for a given gesture and target object. This determines
+ whether or not a gesture event will be delivered to a target object.
+
+ If you choose to represent a gesture by a custom QGesture subclass, you will need to
+ reimplement the createGesture() function to construct instances of your gesture class.
+ Similarly, you may need to reimplement the reset() function if your custom gesture
+ objects need to be specially handled when a gesture is canceled.
+
+ \sa QGesture
+*/
+
+/*!
+ \enum QGestureRecognizer::ResultFlags
+
+ This enum describes the result of the current event filtering step in
+ a gesture recognizer state machine.
+
+ The result consists of a state value (one of Ignore, NotGesture,
+ MaybeGesture, GestureTriggered, GestureFinished) and an optional hint
+ (ConsumeEventHint).
+
+ \value Ignore The event does not change the state of the recognizer.
+
+ \value NotGesture The event made it clear that it is not a gesture. If the
+ gesture recognizer was in GestureTriggered state before, then the gesture
+ is canceled and the appropriate QGesture object will be delivered to the
+ target as a part of a QGestureEvent.
+
+ \value MaybeGesture The event changed the internal state of the recognizer,
+ but it isn't clear yet if it is a gesture or not. The recognizer needs to
+ filter more events to decide. Gesture recognizers in the MaybeGesture state
+ may be reset automatically if they take too long to recognize gestures.
+
+ \value GestureTriggered The gesture has been triggered and the appropriate
+ QGesture object will be delivered to the target as a part of a
+ QGestureEvent.
+
+ \value GestureFinished The gesture has been finished successfully and the
+ appropriate QGesture object will be delivered to the target as a part of a
+ QGestureEvent.
+
+ \value ConsumeEventHint This hint specifies that the gesture framework should
+ consume the filtered event and not deliver it to the receiver.
+
+ \omitvalue ResultState_Mask
+ \omitvalue ResultHint_Mask
+
+ \sa QGestureRecognizer::filterEvent()
+*/
+
+/*!
+ Constructs a new gesture recognizer object.
+*/
+QGestureRecognizer::QGestureRecognizer()
+{
+}
+
+/*!
+ Destroys the gesture recognizer.
+*/
+QGestureRecognizer::~QGestureRecognizer()
+{
+}
+
+/*!
+ This function is called by Qt to create a new QGesture object for the
+ given \a target (QWidget or QGraphicsObject).
+
+ Reimplement this function to create a custom QGesture-derived gesture
+ object if necessary.
+*/
+QGesture *QGestureRecognizer::createGesture(QObject *target)
+{
+ Q_UNUSED(target);
+ return new QGesture;
+}
+
+/*!
+ This function is called by the framework to reset a given \a gesture.
+
+ Reimplement this function to implement additional requirements for custom QGesture
+ objects. This may be necessary if you implement a custom QGesture whose properties
+ need special handling when the gesture is reset.
+*/
+void QGestureRecognizer::reset(QGesture *gesture)
+{
+ if (gesture) {
+ QGesturePrivate *d = gesture->d_func();
+ d->state = Qt::NoGesture;
+ d->hotSpot = QPointF();
+ d->targetObject = 0;
+ }
+}
+
+/*!
+ \fn QGestureRecognizer::filterEvent(QGesture *gesture, QObject *watched, QEvent *event)
+
+ Handles the given \a event for the \a watched object, updating the state of the \a gesture
+ object as required, and returns a suitable Result for the current recognition step.
+
+ This function is called by the framework to allow the recognizer to filter input events
+ dispatched to QWidget or QGraphicsObject instances that it is monitoring.
+
+ The result reflects how much of the gesture has been recognized. The state of the
+ \a gesture object is set depending on the result.
+
+ \sa Qt::GestureState
+*/
+
+QT_END_NAMESPACE
diff --git a/src/gui/kernel/qgesturerecognizer.h b/src/gui/kernel/qgesturerecognizer.h
new file mode 100644
index 0000000..efd8565
--- /dev/null
+++ b/src/gui/kernel/qgesturerecognizer.h
@@ -0,0 +1,93 @@
+/****************************************************************************
+**
+** 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 QtGui module 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 QGESTURERECOGNIZER_H
+#define QGESTURERECOGNIZER_H
+
+#include <QtCore/qglobal.h>
+
+QT_BEGIN_HEADER
+
+QT_BEGIN_NAMESPACE
+
+QT_MODULE(Gui)
+
+class QObject;
+class QEvent;
+class QGesture;
+class Q_GUI_EXPORT QGestureRecognizer
+{
+public:
+ enum ResultFlags
+ {
+ Ignore = 0x0001,
+ NotGesture = 0x0002,
+ MaybeGesture = 0x0004,
+ GestureTriggered = 0x0008, // Gesture started or updated
+ GestureFinished = 0x0010,
+
+ ResultState_Mask = 0x00ff,
+
+ ConsumeEventHint = 0x0100,
+ // StoreEventHint = 0x0200,
+ // ReplayStoredEventsHint = 0x0400,
+ // DiscardStoredEventsHint = 0x0800,
+
+ ResultHint_Mask = 0xff00
+ };
+ Q_DECLARE_FLAGS(Result, ResultFlags)
+
+ QGestureRecognizer();
+ virtual ~QGestureRecognizer();
+
+ virtual QGesture *createGesture(QObject *target);
+ virtual QGestureRecognizer::Result filterEvent(QGesture *state, QObject *watched, QEvent *event) = 0;
+
+ virtual void reset(QGesture *state);
+};
+
+Q_DECLARE_OPERATORS_FOR_FLAGS(QGestureRecognizer::Result)
+
+QT_END_NAMESPACE
+
+QT_END_HEADER
+
+#endif // QGESTURERECOGNIZER_H
diff --git a/src/gui/kernel/qmacgesturerecognizer_mac.mm b/src/gui/kernel/qmacgesturerecognizer_mac.mm
new file mode 100644
index 0000000..7b19a54
--- /dev/null
+++ b/src/gui/kernel/qmacgesturerecognizer_mac.mm
@@ -0,0 +1,267 @@
+/****************************************************************************
+**
+** 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 QtGui module 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 "qmacgesturerecognizer_mac_p.h"
+#include "qgesture.h"
+#include "qgesture_p.h"
+#include "qevent.h"
+#include "qevent_p.h"
+#include "qwidget.h"
+#include "qdebug.h"
+
+QT_BEGIN_NAMESPACE
+
+QMacSwipeGestureRecognizer::QMacSwipeGestureRecognizer()
+{
+}
+
+QGesture *QMacSwipeGestureRecognizer::createGesture(QObject * /*target*/)
+{
+ return new QSwipeGesture;
+}
+
+QGestureRecognizer::Result
+QMacSwipeGestureRecognizer::filterEvent(QGesture *gesture, QObject *obj, QEvent *event)
+{
+ if (event->type() == QEvent::NativeGesture && obj->isWidgetType()) {
+ QNativeGestureEvent *ev = static_cast<QNativeGestureEvent*>(event);
+ switch (ev->gestureType) {
+ case QNativeGestureEvent::Swipe: {
+ QSwipeGesture *g = static_cast<QSwipeGesture *>(gesture);
+ g->setSwipeAngle(ev->angle);
+ return QGestureRecognizer::GestureTriggered | QGestureRecognizer::ConsumeEventHint;
+ break; }
+ default:
+ break;
+ }
+ }
+
+ return QGestureRecognizer::Ignore;
+}
+
+void QMacSwipeGestureRecognizer::reset(QGesture *gesture)
+{
+ QSwipeGesture *g = static_cast<QSwipeGesture *>(gesture);
+ g->setSwipeAngle(0);
+ QGestureRecognizer::reset(gesture);
+}
+
+////////////////////////////////////////////////////////////////////////
+
+QMacPinchGestureRecognizer::QMacPinchGestureRecognizer()
+{
+}
+
+QGesture *QMacPinchGestureRecognizer::createGesture(QObject * /*target*/)
+{
+ return new QPinchGesture;
+}
+
+QGestureRecognizer::Result
+QMacPinchGestureRecognizer::filterEvent(QGesture *gesture, QObject *obj, QEvent *event)
+{
+ if (event->type() == QEvent::NativeGesture && obj->isWidgetType()) {
+ QPinchGesture *g = static_cast<QPinchGesture *>(gesture);
+ QNativeGestureEvent *ev = static_cast<QNativeGestureEvent*>(event);
+ switch(ev->gestureType) {
+ case QNativeGestureEvent::GestureBegin:
+ reset(gesture);
+ g->setStartCenterPoint(static_cast<QWidget*>(obj)->mapFromGlobal(ev->position));
+ g->setCenterPoint(g->startCenterPoint());
+ g->setWhatChanged(QPinchGesture::CenterPointChanged);
+ return QGestureRecognizer::MaybeGesture | QGestureRecognizer::ConsumeEventHint;
+ case QNativeGestureEvent::Rotate: {
+ g->setLastScaleFactor(g->scaleFactor());
+ g->setLastRotationAngle(g->rotationAngle());
+ g->setRotationAngle(g->rotationAngle() + ev->percentage);
+ g->setWhatChanged(QPinchGesture::RotationAngleChanged);
+ return QGestureRecognizer::GestureTriggered | QGestureRecognizer::ConsumeEventHint;
+ break;
+ }
+ case QNativeGestureEvent::Zoom:
+ g->setLastScaleFactor(g->scaleFactor());
+ g->setLastRotationAngle(g->rotationAngle());
+ g->setScaleFactor(g->scaleFactor() + ev->percentage);
+ g->setWhatChanged(QPinchGesture::ScaleFactorChanged);
+ return QGestureRecognizer::GestureTriggered | QGestureRecognizer::ConsumeEventHint;
+ break;
+ case QNativeGestureEvent::GestureEnd:
+ return QGestureRecognizer::GestureFinished | QGestureRecognizer::ConsumeEventHint;
+ break;
+ default:
+ break;
+ }
+ }
+
+ return QGestureRecognizer::Ignore;
+}
+
+void QMacPinchGestureRecognizer::reset(QGesture *gesture)
+{
+ QPinchGesture *g = static_cast<QPinchGesture *>(gesture);
+ g->setWhatChanged(0);
+ g->setScaleFactor(1.0f);
+ g->setTotalScaleFactor(1.0f);
+ g->setLastScaleFactor(1.0f);
+ g->setRotationAngle(0.0f);
+ g->setTotalRotationAngle(0.0f);
+ g->setLastRotationAngle(0.0f);
+ g->setCenterPoint(QPointF());
+ g->setStartCenterPoint(QPointF());
+ g->setLastCenterPoint(QPointF());
+ QGestureRecognizer::reset(gesture);
+}
+
+////////////////////////////////////////////////////////////////////////
+
+#if defined(QT_MAC_USE_COCOA)
+
+QMacPanGestureRecognizer::QMacPanGestureRecognizer() : _panCanceled(true)
+{
+}
+
+QGesture *QMacPanGestureRecognizer::createGesture(QObject *target)
+{
+ if (!target)
+ return new QPanGesture;
+
+ if (QWidget *w = qobject_cast<QWidget *>(target)) {
+ w->setAttribute(Qt::WA_AcceptTouchEvents);
+ w->setAttribute(Qt::WA_TouchPadAcceptSingleTouchEvents);
+ return new QPanGesture;
+ }
+ return 0;
+}
+
+QGestureRecognizer::Result
+QMacPanGestureRecognizer::filterEvent(QGesture *gesture, QObject *target, QEvent *event)
+{
+ const int panBeginDelay = 300;
+ const int panBeginRadius = 3;
+
+ QPanGesture *g = static_cast<QPanGesture *>(gesture);
+
+ switch (event->type()) {
+ case QEvent::TouchBegin: {
+ const QTouchEvent *ev = static_cast<const QTouchEvent*>(event);
+ if (ev->touchPoints().size() == 1) {
+ reset(gesture);
+ _startPos = QCursor::pos();
+ _lastPos = _startPos;
+ _panTimer.start(panBeginDelay, target);
+ _panCanceled = false;
+ return QGestureRecognizer::MaybeGesture;
+ }
+ break;}
+ case QEvent::TouchEnd: {
+ if (_panCanceled)
+ break;
+
+ const QTouchEvent *ev = static_cast<const QTouchEvent*>(event);
+ if (ev->touchPoints().size() == 1)
+ return QGestureRecognizer::GestureFinished;
+ break;}
+ case QEvent::TouchUpdate: {
+ if (_panCanceled)
+ break;
+
+ const QTouchEvent *ev = static_cast<const QTouchEvent*>(event);
+ if (ev->touchPoints().size() == 1) {
+ if (_panTimer.isActive()) {
+ // INVARIANT: Still in maybeGesture. Check if the user
+ // moved his finger so much that it makes sense to cancel the pan:
+ const QPointF p = QCursor::pos();
+ if ((p - _startPos).manhattanLength() > panBeginRadius) {
+ _panCanceled = true;
+ _panTimer.stop();
+ return QGestureRecognizer::NotGesture;
+ }
+ } else {
+ const QPointF p = QCursor::pos();
+ const QPointF posOffset = p - _lastPos;
+ g->setLastOffset(g->offset());
+ g->setOffset(QSizeF(posOffset.x(), posOffset.y()));
+ g->setTotalOffset(g->lastOffset() + g->offset());
+ _lastPos = p;
+ return QGestureRecognizer::GestureTriggered;
+ }
+ } else if (_panTimer.isActive()) {
+ // I only want to cancel the pan if the user is pressing
+ // more than one finger, and the pan hasn't started yet:
+ _panCanceled = true;
+ _panTimer.stop();
+ return QGestureRecognizer::NotGesture;
+ }
+ break;}
+ case QEvent::Timer: {
+ QTimerEvent *ev = static_cast<QTimerEvent *>(event);
+ if (ev->timerId() == _panTimer.timerId()) {
+ _panTimer.stop();
+ if (_panCanceled)
+ break;
+ // Begin new pan session!
+ _startPos = QCursor::pos();
+ _lastPos = _startPos;
+ return QGestureRecognizer::GestureTriggered | QGestureRecognizer::ConsumeEventHint;
+ }
+ break; }
+ default:
+ break;
+ }
+
+ return QGestureRecognizer::Ignore;
+}
+
+void QMacPanGestureRecognizer::reset(QGesture *gesture)
+{
+ QPanGesture *g = static_cast<QPanGesture *>(gesture);
+ _startPos = QPointF();
+ _lastPos = QPointF();
+ _panCanceled = true;
+ g->setOffset(QSizeF(0, 0));
+ g->setLastOffset(QSizeF(0, 0));
+ g->setTotalOffset(QSizeF(0, 0));
+ g->setAcceleration(qreal(1));
+ QGestureRecognizer::reset(gesture);
+}
+#endif // QT_MAC_USE_COCOA
+
+QT_END_NAMESPACE
diff --git a/src/gui/kernel/qmacgesturerecognizer_mac_p.h b/src/gui/kernel/qmacgesturerecognizer_mac_p.h
new file mode 100644
index 0000000..bdc2e08
--- /dev/null
+++ b/src/gui/kernel/qmacgesturerecognizer_mac_p.h
@@ -0,0 +1,103 @@
+/****************************************************************************
+**
+** 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 QtGui module 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 QMACSWIPEGESTURERECOGNIZER_MAC_P_H
+#define QMACSWIPEGESTURERECOGNIZER_MAC_P_H
+
+//
+// W A R N I N G
+// -------------
+//
+// This file is not part of the Qt API. It exists for the convenience
+// of other Qt classes. This header file may change from version to
+// version without notice, or even be removed.
+//
+// We mean it.
+//
+
+#include "qtimer.h"
+#include "qpoint.h"
+#include "qgesturerecognizer.h"
+
+QT_BEGIN_NAMESPACE
+
+class QMacSwipeGestureRecognizer : public QGestureRecognizer
+{
+public:
+ QMacSwipeGestureRecognizer();
+
+ QGesture *createGesture(QObject *target);
+ QGestureRecognizer::Result filterEvent(QGesture *gesture, QObject *watched, QEvent *event);
+ void reset(QGesture *gesture);
+};
+
+class QMacPinchGestureRecognizer : public QGestureRecognizer
+{
+public:
+ QMacPinchGestureRecognizer();
+
+ QGesture *createGesture(QObject *target);
+ QGestureRecognizer::Result filterEvent(QGesture *gesture, QObject *watched, QEvent *event);
+ void reset(QGesture *gesture);
+};
+
+#if defined(QT_MAC_USE_COCOA)
+
+class QMacPanGestureRecognizer : public QObject, public QGestureRecognizer
+{
+public:
+ QMacPanGestureRecognizer();
+
+ QGesture *createGesture(QObject *target);
+ QGestureRecognizer::Result filterEvent(QGesture *gesture, QObject *watched, QEvent *event);
+ void reset(QGesture *gesture);
+private:
+ QPointF _startPos;
+ QPointF _lastPos;
+ QBasicTimer _panTimer;
+ bool _panCanceled;
+};
+
+#endif
+
+QT_END_NAMESPACE
+
+#endif // QMACSWIPEGESTURERECOGNIZER_MAC_P_H
diff --git a/src/gui/kernel/qsoftkeymanager.cpp b/src/gui/kernel/qsoftkeymanager.cpp
index cd3ad22..6116a5e 100644
--- a/src/gui/kernel/qsoftkeymanager.cpp
+++ b/src/gui/kernel/qsoftkeymanager.cpp
@@ -125,7 +125,6 @@ QAction *QSoftKeyManager::createAction(StandardSoftKey standardKey, QWidget *act
break;
}
action->setSoftKeyRole(softKeyRole);
- action->setEnabled(actionWidget->isEnabled());
return action;
}
@@ -200,6 +199,7 @@ bool QSoftKeyManager::event(QEvent *e)
void QSoftKeyManagerPrivate::updateSoftKeys_sys(const QList<QAction*> &softkeys)
{
CEikButtonGroupContainer* nativeContainer = S60->buttonGroupContainer();
+ nativeContainer->DrawableWindow()->SetPointerCapturePriority(1); //keep softkeys available in modal dialog
QT_TRAP_THROWING(nativeContainer->SetCommandSetL(R_AVKON_SOFTKEYS_EMPTY_WITH_IDS));
int position = -1;
@@ -209,7 +209,7 @@ void QSoftKeyManagerPrivate::updateSoftKeys_sys(const QList<QAction*> &softkeys)
for (int index = 0; index < softkeys.count(); index++) {
const QAction* softKeyAction = softkeys.at(index);
switch (softKeyAction->softKeyRole()) {
- // Positive Actions go on LSK
+ // Positive Actions on the LSK
case QAction::PositiveSoftKey:
position = 0;
break;
@@ -252,7 +252,8 @@ bool QSoftKeyManager::handleCommand(int command)
QAction *action = softKeys.at(i);
if (action->softKeyRole() != QAction::NoSoftKey) {
if (j == index) {
- if (action->isEnabled()) {
+ QWidget *parent = action->parentWidget();
+ if (parent && parent->isEnabled()) {
action->activate(QAction::Trigger);
return true;
}
diff --git a/src/gui/kernel/qstandardgestures.cpp b/src/gui/kernel/qstandardgestures.cpp
index 3cfb987..dfc3499 100644
--- a/src/gui/kernel/qstandardgestures.cpp
+++ b/src/gui/kernel/qstandardgestures.cpp
@@ -39,174 +39,45 @@
**
****************************************************************************/
-#include "qstandardgestures.h"
#include "qstandardgestures_p.h"
-
-#include <qabstractscrollarea.h>
-#include <qscrollbar.h>
-#include <private/qapplication_p.h>
-#include <private/qevent_p.h>
-#include <private/qwidget_p.h>
-#include <qmath.h>
+#include "qgesture.h"
+#include "qgesture_p.h"
+#include "qevent.h"
+#include "qwidget.h"
QT_BEGIN_NAMESPACE
-#ifdef Q_WS_WIN
-QWidgetPrivate *qt_widget_private(QWidget *widget);
-#endif
-
-/*!
- \class QPanGesture
- \preliminary
- \since 4.6
-
- \brief The QPanGesture class represents a Pan gesture,
- providing additional information related to panning.
-*/
-
-/*!
- \enum QSwipeGesture::SwipeDirection
- \brief This enum specifies the direction of the swipe gesture.
-
- \value NoDirection
- \value Left
- \value Right
- \value Up
- \value Down
-*/
-
-/*!
- Creates a new pan gesture handler object and marks it as a child of
- \a parent. The pan gesture handler watches \a gestureTarget for its
- events.
-
- On some platform like Windows it's necessary to provide a non-null
- widget as \a parent to get native gesture support.
-*/
-QPanGesture::QPanGesture(QWidget *gestureTarget, QObject *parent)
- : QGesture(*new QPanGesturePrivate, gestureTarget, parent)
+QPanGestureRecognizer::QPanGestureRecognizer()
{
- setObjectName(QLatin1String("QPanGesture"));
-}
-
-void QPanGesturePrivate::setupGestureTarget(QObject *newGestureTarget)
-{
- Q_Q(QPanGesture);
- QApplicationPrivate *qAppPriv = QApplicationPrivate::instance();
-
- if (gestureTarget && gestureTarget->isWidgetType()) {
- QWidget *w = static_cast<QWidget*>(gestureTarget.data());
- if (qAppPriv->widgetGestures[w].pan == q)
- qAppPriv->widgetGestures[w].pan = 0;
-#if defined(Q_WS_WIN)
- qt_widget_private(w)->winSetupGestures();
-#elif defined(Q_WS_MAC)
- w->setAttribute(Qt::WA_AcceptTouchEvents, false);
- w->setAttribute(Qt::WA_TouchPadAcceptSingleTouchEvents, false);
-#endif
- }
-
- if (newGestureTarget && newGestureTarget->isWidgetType()) {
- QWidget *w = static_cast<QWidget*>(newGestureTarget);
- qAppPriv->widgetGestures[w].pan = q;
-#if defined(Q_WS_WIN)
- qt_widget_private(w)->winSetupGestures();
-#elif defined(Q_WS_MAC)
- w->setAttribute(Qt::WA_AcceptTouchEvents);
- w->setAttribute(Qt::WA_TouchPadAcceptSingleTouchEvents);
-#endif
- }
- QGesturePrivate::setupGestureTarget(newGestureTarget);
-}
-
-/*! \internal */
-bool QPanGesture::event(QEvent *event)
-{
-#if defined(QT_MAC_USE_COCOA)
- Q_D(QPanGesture);
- if (event->type() == QEvent::Timer) {
- const QTimerEvent *te = static_cast<QTimerEvent *>(event);
- if (te->timerId() == d->singleTouchPanTimer.timerId()) {
- d->singleTouchPanTimer.stop();
- updateState(Qt::GestureStarted);
- }
- }
-#endif
-
- return QObject::event(event);
}
-bool QPanGesture::eventFilter(QObject *receiver, QEvent *event)
+QGesture *QPanGestureRecognizer::createGesture(QObject *target)
{
- Q_D(QPanGesture);
-
- if (d->implicitGesture && d->gestureTarget && d->gestureTarget->isWidgetType() &&
- static_cast<QWidget*>(d->gestureTarget.data())->testAttribute(Qt::WA_DontUseStandardGestures))
- return false;
-
-#ifdef Q_WS_WIN
- if (receiver->isWidgetType() && event->type() == QEvent::NativeGesture) {
- QNativeGestureEvent *ev = static_cast<QNativeGestureEvent*>(event);
- QApplicationPrivate *qAppPriv = QApplicationPrivate::instance();
- QApplicationPrivate::WidgetStandardGesturesMap::iterator it;
- it = qAppPriv->widgetGestures.find(static_cast<QWidget*>(receiver));
- if (it == qAppPriv->widgetGestures.end())
- return false;
- if (this != it.value().pan)
- return false;
- Qt::GestureState nextState = Qt::NoGesture;
- switch(ev->gestureType) {
- case QNativeGestureEvent::GestureBegin:
- // next we might receive the first gesture update event, so we
- // prepare for it.
- d->state = Qt::NoGesture;
- return false;
- case QNativeGestureEvent::Pan:
- nextState = Qt::GestureUpdated;
- event->accept();
- break;
- case QNativeGestureEvent::GestureEnd:
- if (state() == Qt::NoGesture)
- return false; // some other gesture has ended
- nextState = Qt::GestureFinished;
- break;
- default:
- return false;
- }
- if (state() == Qt::NoGesture) {
- d->lastOffset = d->totalOffset = d->offset = QSize();
- } else {
- d->lastOffset = d->offset;
- d->offset = QSize(ev->position.x() - d->lastPosition.x(),
- ev->position.y() - d->lastPosition.y());
- d->totalOffset += d->offset;
- }
- d->lastPosition = ev->position;
- updateState(nextState);
- return true;
+ if (target && target->isWidgetType()) {
+ static_cast<QWidget *>(target)->setAttribute(Qt::WA_AcceptTouchEvents);
}
-#endif
- return QGesture::eventFilter(receiver, event);
+ return new QPanGesture;
}
-/*! \internal */
-bool QPanGesture::filterEvent(QEvent *event)
+QGestureRecognizer::Result QPanGestureRecognizer::filterEvent(QGesture *state, QObject *, QEvent *event)
{
- Q_D(QPanGesture);
+ QPanGesture *q = static_cast<QPanGesture*>(state);
+ QPanGesturePrivate *d = q->d_func();
- if (d->implicitGesture && d->gestureTarget && d->gestureTarget->isWidgetType() &&
- static_cast<QWidget*>(d->gestureTarget.data())->testAttribute(Qt::WA_DontUseStandardGestures))
- return false;
-
-#if defined(Q_WS_WIN)
const QTouchEvent *ev = static_cast<const QTouchEvent*>(event);
- if (event->type() == QEvent::TouchBegin) {
+ QGestureRecognizer::Result result;
+
+ switch (event->type()) {
+ case QEvent::TouchBegin: {
+ result = QGestureRecognizer::MaybeGesture;
QTouchEvent::TouchPoint p = ev->touchPoints().at(0);
d->lastPosition = p.pos().toPoint();
d->lastOffset = d->totalOffset = d->offset = QSize();
- } else if (event->type() == QEvent::TouchEnd) {
- if (state() != Qt::NoGesture) {
+ break;
+ }
+ case QEvent::TouchEnd: {
+ if (q->state() != Qt::NoGesture) {
if (ev->touchPoints().size() == 2) {
QTouchEvent::TouchPoint p1 = ev->touchPoints().at(0);
QTouchEvent::TouchPoint p2 = ev->touchPoints().at(1);
@@ -216,11 +87,14 @@ bool QPanGesture::filterEvent(QEvent *event)
p1.pos().y() - p1.lastPos().y() + p2.pos().y() - p2.lastPos().y()) / 2;
d->totalOffset += d->offset;
}
- updateState(Qt::GestureFinished);
+ result = QGestureRecognizer::GestureFinished;
+ } else {
+ result = QGestureRecognizer::NotGesture;
}
- reset();
- } else if (event->type() == QEvent::TouchUpdate) {
- if (ev->touchPoints().size() == 2) {
+ break;
+ }
+ case QEvent::TouchUpdate: {
+ if (ev->touchPoints().size() >= 2) {
QTouchEvent::TouchPoint p1 = ev->touchPoints().at(0);
QTouchEvent::TouchPoint p2 = ev->touchPoints().at(1);
d->lastOffset = d->offset;
@@ -230,10 +104,60 @@ bool QPanGesture::filterEvent(QEvent *event)
d->totalOffset += d->offset;
if (d->totalOffset.width() > 10 || d->totalOffset.height() > 10 ||
d->totalOffset.width() < -10 || d->totalOffset.height() < -10) {
- updateState(Qt::GestureUpdated);
+ result = QGestureRecognizer::GestureTriggered;
+ } else {
+ result = QGestureRecognizer::MaybeGesture;
}
}
+ break;
+ }
+ case QEvent::MouseButtonPress:
+ case QEvent::MouseMove:
+ case QEvent::MouseButtonRelease:
+ result = QGestureRecognizer::Ignore;
+ break;
+ default:
+ result = QGestureRecognizer::Ignore;
+ break;
+ }
+ return result;
+}
+
+void QPanGestureRecognizer::reset(QGesture *state)
+{
+ QPanGesture *pan = static_cast<QPanGesture*>(state);
+ QPanGesturePrivate *d = pan->d_func();
+
+ d->totalOffset = d->lastOffset = d->offset = QSizeF();
+ d->lastPosition = QPoint();
+ d->acceleration = 0;
+
+//#if defined(QT_MAC_USE_COCOA)
+// d->singleTouchPanTimer.stop();
+// d->prevMousePos = QPointF(0, 0);
+//#endif
+
+ QGestureRecognizer::reset(state);
+}
+
+/*! \internal */
+/*
+bool QPanGestureRecognizer::event(QEvent *event)
+{
+#if defined(QT_MAC_USE_COCOA)
+ Q_D(QPanGesture);
+ if (event->type() == QEvent::Timer) {
+ const QTimerEvent *te = static_cast<QTimerEvent *>(event);
+ if (te->timerId() == d->singleTouchPanTimer.timerId()) {
+ d->singleTouchPanTimer.stop();
+ updateState(Qt::GestureStarted);
+ }
}
+#endif
+
+ bool consume = false;
+
+#if defined(Q_WS_WIN)
#elif defined(QT_MAC_USE_COCOA)
// The following implements single touch
// panning on Mac:
@@ -244,16 +168,25 @@ bool QPanGesture::filterEvent(QEvent *event)
switch (event->type()) {
case QEvent::TouchBegin: {
if (ev->touchPoints().size() == 1) {
+ d->delayManager->setEnabled(true);
+ consume = d->delayManager->append(d->gestureTarget, *event);
d->lastPosition = QCursor::pos();
d->singleTouchPanTimer.start(panBeginDelay, this);
}
break;}
case QEvent::TouchEnd: {
- if (state() != Qt::NoGesture)
+ d->delayManager->setEnabled(false);
+ if (state() != Qt::NoGesture) {
updateState(Qt::GestureFinished);
+ consume = true;
+ d->delayManager->clear();
+ } else {
+ d->delayManager->replay();
+ }
reset();
break;}
case QEvent::TouchUpdate: {
+ consume = d->delayManager->append(d->gestureTarget, *event);
if (ev->touchPoints().size() == 1) {
if (state() == Qt::NoGesture) {
// INVARIANT: The singleTouchTimer has still not fired.
@@ -261,11 +194,15 @@ bool QPanGesture::filterEvent(QEvent *event)
// the starting point that it makes sense to cancel:
const QPointF startPos = ev->touchPoints().at(0).startPos().toPoint();
const QPointF p = ev->touchPoints().at(0).pos().toPoint();
- if ((startPos - p).manhattanLength() > panBeginRadius)
+ if ((startPos - p).manhattanLength() > panBeginRadius) {
+ d->delayManager->replay();
+ consume = false;
reset();
- else
+ } else {
d->lastPosition = QCursor::pos();
+ }
} else {
+ d->delayManager->clear();
QPointF mousePos = QCursor::pos();
QPointF dist = mousePos - d->lastPosition;
d->lastPosition = mousePos;
@@ -275,527 +212,25 @@ bool QPanGesture::filterEvent(QEvent *event)
updateState(Qt::GestureUpdated);
}
} else if (state() == Qt::NoGesture) {
+ d->delayManager->replay();
+ consume = false;
reset();
}
break;}
+ case QEvent::MouseButtonPress:
+ case QEvent::MouseMove:
+ case QEvent::MouseButtonRelease:
+ if (d->delayManager->isEnabled())
+ consume = d->delayManager->append(d->gestureTarget, *event);
+ break;
default:
return false;
}
#else
Q_UNUSED(event);
#endif
- return false;
-}
-
-/*! \internal */
-void QPanGesture::reset()
-{
- Q_D(QPanGesture);
- d->lastOffset = d->totalOffset = d->offset = QSize(0, 0);
- d->lastPosition = QPoint(0, 0);
-
-#if defined(QT_MAC_USE_COCOA)
- d->singleTouchPanTimer.stop();
- d->prevMousePos = QPointF(0, 0);
-#endif
-
- QGesture::reset();
-}
-
-/*!
- \property QPanGesture::totalOffset
-
- Specifies a total pan offset since the start of the gesture.
-*/
-QSizeF QPanGesture::totalOffset() const
-{
- Q_D(const QPanGesture);
- return d->totalOffset;
-}
-
-/*!
- \property QPanGesture::lastOffset
-
- Specifies a pan offset the last time the gesture was triggered.
-*/
-QSizeF QPanGesture::lastOffset() const
-{
- Q_D(const QPanGesture);
- return d->lastOffset;
-}
-
-/*!
- \property QPanGesture::offset
-
- Specifies the current pan offset since the last time the gesture was
- triggered.
-*/
-QSizeF QPanGesture::offset() const
-{
- Q_D(const QPanGesture);
- return d->offset;
-}
-
-//////////////////////////////////////////////////////////////////////////////
-
-/*!
- \class QPinchGesture
- \preliminary
- \since 4.6
-
- \brief The QPinchGesture class represents a Pinch gesture,
- providing additional information related to zooming and/or rotation.
-*/
-
-/*!
- Creates a new Pinch gesture handler object and marks it as a child
- of \a parent. The pan gesture handler watches \a gestureTarget for its
- events.
-
- On some platform like Windows it's necessary to provide a non-null
- widget as \a parent to get native gesture support.
-*/
-QPinchGesture::QPinchGesture(QWidget *gestureTarget, QObject *parent)
- : QGesture(*new QPinchGesturePrivate, gestureTarget, parent)
-{
- setObjectName(QLatin1String("QPinchGesture"));
-}
-
-void QPinchGesturePrivate::setupGestureTarget(QObject *newGestureTarget)
-{
- Q_Q(QPinchGesture);
- if (gestureTarget && gestureTarget->isWidgetType()) {
- QWidget *w = static_cast<QWidget*>(gestureTarget.data());
- QApplicationPrivate::instance()->widgetGestures[w].pinch = 0;
-#ifdef Q_WS_WIN
- qt_widget_private(w)->winSetupGestures();
-#endif
- }
-
- if (newGestureTarget && newGestureTarget->isWidgetType()) {
- QWidget *w = static_cast<QWidget*>(newGestureTarget);
- QApplicationPrivate::instance()->widgetGestures[w].pinch = q;
-#ifdef Q_WS_WIN
- qt_widget_private(w)->winSetupGestures();
-#endif
- }
- QGesturePrivate::setupGestureTarget(newGestureTarget);
-}
-
-/*! \internal */
-bool QPinchGesture::event(QEvent *event)
-{
- return QObject::event(event);
-}
-
-bool QPinchGesture::eventFilter(QObject *receiver, QEvent *event)
-{
- Q_D(QPinchGesture);
-
- if (d->implicitGesture && d->gestureTarget && d->gestureTarget->isWidgetType() &&
- static_cast<QWidget*>(d->gestureTarget.data())->testAttribute(Qt::WA_DontUseStandardGestures))
- return false;
-
-#if defined(Q_WS_WIN) || defined(Q_WS_MAC)
- if (receiver->isWidgetType() && event->type() == QEvent::NativeGesture) {
- QNativeGestureEvent *ev = static_cast<QNativeGestureEvent*>(event);
-#if defined(Q_WS_WIN)
- QApplicationPrivate *qAppPriv = QApplicationPrivate::instance();
- QApplicationPrivate::WidgetStandardGesturesMap::iterator it;
- it = qAppPriv->widgetGestures.find(static_cast<QWidget*>(receiver));
- if (it == qAppPriv->widgetGestures.end())
- return false;
- if (this != it.value().pinch)
- return false;
-#endif
- Qt::GestureState nextState = Qt::NoGesture;
-
- switch(ev->gestureType) {
- case QNativeGestureEvent::GestureBegin:
- // next we might receive the first gesture update event, so we
- // prepare for it.
- d->state = Qt::NoGesture;
- d->changes = 0;
- d->totalScaleFactor = d->scaleFactor = d->lastScaleFactor = 1.;
- d->totalRotationAngle = d->rotationAngle = d->lastRotationAngle = 0.;
- d->startCenterPoint = d->centerPoint = d->lastCenterPoint = QPointF();
-#if defined(Q_WS_WIN)
- d->initialDistance = 0;
- d->lastSequenceId = ev->sequenceId;
-#endif
- return false;
- case QNativeGestureEvent::Rotate: {
- d->lastScaleFactor = d->scaleFactor;
- d->lastRotationAngle = d->rotationAngle;
-#if defined(Q_WS_MAC)
- d->rotationAngle += ev->percentage;
- nextState = Qt::GestureUpdated;
-#elif defined(Q_WS_WIN)
- // This is a workaround for an issue with the native rotation
- // gesture on Windows 7. For some reason the rotation angle in the
- // first WM_GESTURE message in a sequence contains value that is
- // off a little bit and causes the rotating item to "jump", so
- // we just ignore the first WM_GESTURE in every sequence.
- bool windowsRotateWorkaround = false;
- if (!d->lastSequenceId) {
- windowsRotateWorkaround = true;
- d->lastSequenceId = ev->sequenceId;
- }
- if (d->lastSequenceId > 0 && d->lastSequenceId != (ulong)-1 && ev->sequenceId != d->lastSequenceId) {
- // this is the first WM_GESTURE message in a sequence.
- d->totalRotationAngle += d->rotationAngle;
- windowsRotateWorkaround = true;
- // a magic value to mark that the next WM_GESTURE message is
- // the second message in a sequence and we should clear the
- // lastRotationAngle
- d->lastSequenceId = (ulong)-1;
- }
- if (!windowsRotateWorkaround) {
- d->rotationAngle = -1 * GID_ROTATE_ANGLE_FROM_ARGUMENT(ev->argument) * 180. / M_PI;
- if (d->lastSequenceId == (ulong)-1) {
- // a special case since we need to set the lastRotationAngle to
- // rotationAngle when the first WM_GESTURE is received in each
- // sequence.
- d->lastRotationAngle = d->rotationAngle;
- }
- d->lastSequenceId = ev->sequenceId;
- }
- if (!windowsRotateWorkaround)
- nextState = Qt::GestureUpdated;
-#endif
- d->changes = QPinchGesture::RotationAngleChanged;
- event->accept();
- break;
- }
- case QNativeGestureEvent::Zoom:
- d->lastRotationAngle = d->rotationAngle;
- d->lastScaleFactor = d->scaleFactor;
-#if defined(Q_WS_WIN)
- if (d->initialDistance != 0) {
- int distance = int(qint64(ev->argument));
- if (d->lastSequenceId && ev->sequenceId != d->lastSequenceId) {
- d->totalScaleFactor *= d->scaleFactor;
- d->initialDistance = int(qint64(ev->argument));
- d->lastScaleFactor = d->scaleFactor = (qreal) distance / d->initialDistance;
- } else {
- d->scaleFactor = (qreal) distance / d->initialDistance;
- }
- d->lastSequenceId = ev->sequenceId;
- } else {
- d->initialDistance = int(qint64(ev->argument));
- }
-#elif defined(Q_WS_MAC)
- d->scaleFactor += ev->percentage;
-#endif
- nextState = Qt::GestureUpdated;
- d->changes = QPinchGesture::ScaleFactorChanged;
- event->accept();
- break;
- case QNativeGestureEvent::GestureEnd:
- if (state() == Qt::NoGesture)
- return false; // some other gesture has ended
- nextState = Qt::GestureFinished;
- break;
- default:
- return false;
- }
- if (d->startCenterPoint.isNull())
- d->startCenterPoint = d->centerPoint;
- d->lastCenterPoint = d->centerPoint;
- d->centerPoint = static_cast<QWidget*>(receiver)->mapFromGlobal(ev->position);
- if (d->lastCenterPoint != d->centerPoint)
- d->changes |= QPinchGesture::CenterPointChanged;
- updateState(nextState);
- return true;
- }
-#endif
- return QGesture::eventFilter(receiver, event);
-}
-
-
-/*! \internal */
-bool QPinchGesture::filterEvent(QEvent *event)
-{
- Q_D(QPinchGesture);
-
- if (d->implicitGesture && d->gestureTarget && d->gestureTarget->isWidgetType() &&
- static_cast<QWidget*>(d->gestureTarget.data())->testAttribute(Qt::WA_DontUseStandardGestures))
- return false;
-
- Q_UNUSED(event);
- return false;
-}
-
-/*! \internal */
-void QPinchGesture::reset()
-{
- Q_D(QPinchGesture);
- d->changes = 0;
- d->totalScaleFactor = d->scaleFactor = d->lastScaleFactor = 1.;
- d->totalRotationAngle = d->rotationAngle = d->lastRotationAngle = 0.;
- d->startCenterPoint = d->centerPoint = d->lastCenterPoint = QPointF();
- QGesture::reset();
-}
-
-/*! \enum QPinchGesture::WhatChange
- \value ScaleFactorChanged
- \value RotationAngleChanged
- \value CenterPointChanged
-*/
-
-/*!
- \property QPinchGesture::whatChanged
-
- Specifies which values were changed in the gesture.
-*/
-QPinchGesture::WhatChanged QPinchGesture::whatChanged() const
-{
- return d_func()->changes;
-}
-
-/*!
- \property QPinchGesture::totalScaleFactor
-
- Specifies a total scale factor of the pinch gesture since the gesture
- started.
-*/
-qreal QPinchGesture::totalScaleFactor() const
-{
- Q_D(const QPinchGesture);
- return d->totalScaleFactor * d->scaleFactor;
-}
-
-/*!
- \property QPinchGesture::scaleFactor
-
- Specifies a scale factor of the pinch gesture.
-
- If the gesture consists of several pinch sequences (i.e. zoom and rotate
- sequences), then this property specifies the scale factor in the current
- sequence. When pinching changes the rotation angle only, the value of this
- property is 1.
-*/
-qreal QPinchGesture::scaleFactor() const
-{
- return d_func()->scaleFactor;
-}
-
-/*!
- \property QPinchGesture::lastScaleFactor
-
- Specifies a previous scale factor of the pinch gesture.
-*/
-qreal QPinchGesture::lastScaleFactor() const
-{
- return d_func()->lastScaleFactor;
-}
-
-/*!
- \property QPinchGesture::totalRotationAngle
-
- Specifies a total rotation angle of the gesture since the gesture started.
-
- The angle is specified in degrees.
-*/
-qreal QPinchGesture::totalRotationAngle() const
-{
- Q_D(const QPinchGesture);
- return d->totalRotationAngle + d->rotationAngle;
-}
-
-/*!
- \property QPinchGesture::rotationAngle
-
- Specifies a rotation angle of the gesture.
-
- If the gesture consists of several pinch sequences (i.e. zoom and rotate
- sequences), then this property specifies the rotation angle in the current
- sequence. When pinching changes the scale factor only, the value of this
- property is 0.
-
- The angle is specified in degrees.
-*/
-qreal QPinchGesture::rotationAngle() const
-{
- return d_func()->rotationAngle;
-}
-
-/*!
- \property QPinchGesture::lastRotationAngle
-
- Specifies a previous rotation angle of the gesture.
-
- The angle is specified in degrees.
-*/
-qreal QPinchGesture::lastRotationAngle() const
-{
- return d_func()->lastRotationAngle;
-}
-
-/*!
- \property QPinchGesture::centerPoint
-
- Specifies a center point of the gesture. The point can be used as a center
- point that the object is rotated around.
-*/
-QPointF QPinchGesture::centerPoint() const
-{
- return d_func()->centerPoint;
-}
-
-/*!
- \property QPinchGesture::lastCenterPoint
-
- Specifies a previous center point of the gesture.
-*/
-QPointF QPinchGesture::lastCenterPoint() const
-{
- return d_func()->lastCenterPoint;
-}
-
-/*!
- \property QPinchGesture::startCenterPoint
-
- Specifies an initial center point of the gesture. Difference between the
- startCenterPoint and the centerPoint is the distance at which pinching
- fingers has shifted.
-*/
-QPointF QPinchGesture::startCenterPoint() const
-{
- return d_func()->startCenterPoint;
-}
-
-//////////////////////////////////////////////////////////////////////////////
-
-/*!
- \class QSwipeGesture
- \preliminary
- \since 4.6
-
- \brief The QSwipeGesture class represents a swipe gesture,
- providing additional information related to swiping.
-*/
-
-/*!
- Creates a new Swipe gesture handler object and marks it as a
- child of \a parent. The swipe gesture handler watches \a
- gestureTarget for its events.
-
- On some platform like Windows it's necessary to provide a non-null
- widget as \a parent to get native gesture support.
-*/
-QSwipeGesture::QSwipeGesture(QWidget *gestureTarget, QObject *parent)
- : QGesture(*new QSwipeGesturePrivate, gestureTarget, parent)
-{
- setObjectName(QLatin1String("QSwipeGesture"));
-}
-
-void QSwipeGesturePrivate::setupGestureTarget(QObject *newGestureTarget)
-{
- Q_Q(QSwipeGesture);
- if (gestureTarget && gestureTarget->isWidgetType()) {
- QWidget *w = static_cast<QWidget*>(gestureTarget.data());
- QApplicationPrivate::instance()->widgetGestures[w].swipe = 0;
-#if defined(Q_WS_WIN)
- qt_widget_private(w)->winSetupGestures();
-#endif
- }
-
- if (newGestureTarget && newGestureTarget->isWidgetType()) {
- QWidget *w = static_cast<QWidget*>(newGestureTarget);
- QApplicationPrivate::instance()->widgetGestures[w].swipe = q;
-#if defined(Q_WS_WIN)
- qt_widget_private(w)->winSetupGestures();
-#endif
- }
- QGesturePrivate::setupGestureTarget(newGestureTarget);
-}
-
-/*!
- \property QSwipeGesture::swipeAngle
-
- Holds the angle of the swipe gesture, 0..360.
-*/
-qreal QSwipeGesture::swipeAngle() const
-{
- Q_D(const QSwipeGesture);
- return d->swipeAngle;
-}
-
-/*!
- \property QSwipeGesture::horizontalDirection
-
- Holds the direction for the horizontal component of the swipe
- gesture, SwipeDirection::Left or SwipeDirection::Right.
- SwipeDirection::NoDirection if there is no horizontal
- component to the swipe gesture.
-*/
-QSwipeGesture::SwipeDirection QSwipeGesture::horizontalDirection() const
-{
- Q_D(const QSwipeGesture);
- if (d->swipeAngle < 0 || d->swipeAngle == 90 || d->swipeAngle == 270)
- return QSwipeGesture::NoDirection;
- else if (d->swipeAngle < 90 || d->swipeAngle > 270)
- return QSwipeGesture::Right;
- else
- return QSwipeGesture::Left;
-}
-
-
-/*!
- \property QSwipeGesture::verticalDirection
-
- Holds the direction for the vertical component of the swipe
- gesture, SwipeDirection::Down or SwipeDirection::Up.
- SwipeDirection::NoDirection if there is no vertical
- component to the swipe gesture.
-*/
-QSwipeGesture::SwipeDirection QSwipeGesture::verticalDirection() const
-{
- Q_D(const QSwipeGesture);
- if (d->swipeAngle <= 0 || d->swipeAngle == 180)
- return QSwipeGesture::NoDirection;
- else if (d->swipeAngle < 180)
- return QSwipeGesture::Up;
- else
- return QSwipeGesture::Down;
-}
-
-bool QSwipeGesture::eventFilter(QObject *receiver, QEvent *event)
-{
- Q_D(QSwipeGesture);
- if (receiver->isWidgetType() && event->type() == QEvent::NativeGesture) {
- QNativeGestureEvent *ev = static_cast<QNativeGestureEvent*>(event);
- switch (ev->gestureType) {
- case QNativeGestureEvent::Swipe:
- d->swipeAngle = ev->angle;
- updateState(Qt::GestureStarted);
- updateState(Qt::GestureUpdated);
- updateState(Qt::GestureFinished);
- break;
- default:
- return false;
- }
- return true;
- }
- return QGesture::eventFilter(receiver, event);
-}
-
-/*! \internal */
-bool QSwipeGesture::filterEvent(QEvent *)
-{
- return false;
-}
-
-/*! \internal */
-void QSwipeGesture::reset()
-{
- Q_D(QSwipeGesture);
- d->swipeAngle = -1;
- QGesture::reset();
+ return QGestureRecognizer::Ignore;
}
+ */
QT_END_NAMESPACE
-
-#include "moc_qstandardgestures.cpp"
-
diff --git a/src/gui/kernel/qstandardgestures.h b/src/gui/kernel/qstandardgestures.h
deleted file mode 100644
index 9e8291b..0000000
--- a/src/gui/kernel/qstandardgestures.h
+++ /dev/null
@@ -1,174 +0,0 @@
-/****************************************************************************
-**
-** 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 QtGui module 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 QSTANDARDGESTURES_H
-#define QSTANDARDGESTURES_H
-
-#include <QtGui/qevent.h>
-#include <QtCore/qbasictimer.h>
-
-#include <QtGui/qgesture.h>
-
-QT_BEGIN_HEADER
-
-QT_BEGIN_NAMESPACE
-
-QT_MODULE(Gui)
-
-class QPanGesturePrivate;
-class Q_GUI_EXPORT QPanGesture : public QGesture
-{
- Q_OBJECT
- Q_DECLARE_PRIVATE(QPanGesture)
-
- Q_PROPERTY(QSizeF totalOffset READ totalOffset)
- Q_PROPERTY(QSizeF lastOffset READ lastOffset)
- Q_PROPERTY(QSizeF offset READ offset)
-
-public:
- QPanGesture(QWidget *gestureTarget, QObject *parent = 0);
-
- bool filterEvent(QEvent *event);
-
- QSizeF totalOffset() const;
- QSizeF lastOffset() const;
- QSizeF offset() const;
-
-protected:
- void reset();
-
-private:
- bool event(QEvent *event);
- bool eventFilter(QObject *receiver, QEvent *event);
-
- friend class QWidget;
- friend class QAbstractScrollAreaPrivate;
-};
-
-class QPinchGesturePrivate;
-class Q_GUI_EXPORT QPinchGesture : public QGesture
-{
- Q_OBJECT
- Q_DECLARE_PRIVATE(QPinchGesture)
-
-public:
- enum WhatChange {
- ScaleFactorChanged = 0x1,
- RotationAngleChanged = 0x2,
- CenterPointChanged = 0x4
- };
- Q_DECLARE_FLAGS(WhatChanged, WhatChange)
-
- Q_PROPERTY(WhatChanged whatChanged READ whatChanged)
-
- Q_PROPERTY(qreal totalScaleFactor READ totalScaleFactor)
- Q_PROPERTY(qreal lastScaleFactor READ lastScaleFactor)
- Q_PROPERTY(qreal scaleFactor READ scaleFactor)
-
- Q_PROPERTY(qreal totalRotationAngle READ totalRotationAngle)
- Q_PROPERTY(qreal lastRotationAngle READ lastRotationAngle)
- Q_PROPERTY(qreal rotationAngle READ rotationAngle)
-
- Q_PROPERTY(QPointF startCenterPoint READ startCenterPoint)
- Q_PROPERTY(QPointF lastCenterPoint READ lastCenterPoint)
- Q_PROPERTY(QPointF centerPoint READ centerPoint)
-
-public:
-
- QPinchGesture(QWidget *gestureTarget, QObject *parent = 0);
-
- bool filterEvent(QEvent *event);
- void reset();
-
- WhatChanged whatChanged() const;
-
- QPointF startCenterPoint() const;
- QPointF lastCenterPoint() const;
- QPointF centerPoint() const;
-
- qreal totalScaleFactor() const;
- qreal lastScaleFactor() const;
- qreal scaleFactor() const;
-
- qreal totalRotationAngle() const;
- qreal lastRotationAngle() const;
- qreal rotationAngle() const;
-
-private:
- bool event(QEvent *event);
- bool eventFilter(QObject *receiver, QEvent *event);
-
- friend class QWidget;
-};
-
-class QSwipeGesturePrivate;
-class Q_GUI_EXPORT QSwipeGesture : public QGesture
-{
- Q_OBJECT
- Q_ENUMS(SwipeDirection)
-
- Q_PROPERTY(SwipeDirection horizontalDirection READ horizontalDirection)
- Q_PROPERTY(SwipeDirection verticalDirection READ verticalDirection)
- Q_PROPERTY(qreal swipeAngle READ swipeAngle)
-
- Q_DECLARE_PRIVATE(QSwipeGesture)
-
-public:
- enum SwipeDirection { NoDirection, Left, Right, Up, Down };
- QSwipeGesture(QWidget *gestureTarget, QObject *parent = 0);
-
- bool filterEvent(QEvent *event);
- void reset();
-
- SwipeDirection horizontalDirection() const;
- SwipeDirection verticalDirection() const;
- qreal swipeAngle() const;
-
-private:
- bool eventFilter(QObject *receiver, QEvent *event);
-
- friend class QWidget;
-};
-QT_END_NAMESPACE
-
-QT_END_HEADER
-
-#endif // QSTANDARDGESTURES_H
diff --git a/src/gui/kernel/qstandardgestures_p.h b/src/gui/kernel/qstandardgestures_p.h
index 79aadfd..fec5c2f 100644
--- a/src/gui/kernel/qstandardgestures_p.h
+++ b/src/gui/kernel/qstandardgestures_p.h
@@ -53,83 +53,20 @@
// We mean it.
//
-#include "qevent.h"
-#include "qbasictimer.h"
-#include "qdebug.h"
-
-#include "qgesture.h"
-#include "qgesture_p.h"
-
-#include "qstandardgestures.h"
-#include "qbasictimer.h"
+#include "qgesturerecognizer.h"
+#include "private/qgesture_p.h"
QT_BEGIN_NAMESPACE
-class QPanGesturePrivate : public QGesturePrivate
-{
- Q_DECLARE_PUBLIC(QPanGesture)
-
-public:
- void setupGestureTarget(QObject *o);
-
- QSizeF totalOffset;
- QSizeF lastOffset;
- QSizeF offset;
- QPointF lastPosition;
-
-#if defined(QT_MAC_USE_COCOA)
- QBasicTimer singleTouchPanTimer;
- QPointF prevMousePos;
-#endif
-};
-
-class QPinchGesturePrivate : public QGesturePrivate
+class QPanGestureRecognizer : public QGestureRecognizer
{
- Q_DECLARE_PUBLIC(QPinchGesture)
-
public:
- QPinchGesturePrivate()
- : changes(0), totalScaleFactor(0.), lastScaleFactor(0.), scaleFactor(0.),
- totalRotationAngle(0.), lastRotationAngle(0.), rotationAngle(0.)
-#ifdef Q_WS_WIN
- ,initialDistance(0), lastSequenceId(0)
-#endif
- {
- }
+ QPanGestureRecognizer();
- void setupGestureTarget(QObject *o);
-
- QPinchGesture::WhatChanged changes;
-
- qreal totalScaleFactor; // total scale factor, excluding the current sequence.
- qreal lastScaleFactor;
- qreal scaleFactor; // scale factor in the current sequence.
-
- qreal totalRotationAngle; // total rotation angle, excluding the current sequence.
- qreal lastRotationAngle;
- qreal rotationAngle; // rotation angle in the current sequence.
-
- QPointF startCenterPoint;
- QPointF lastCenterPoint;
- QPointF centerPoint;
-#ifdef Q_WS_WIN
- int initialDistance;
- ulong lastSequenceId;
-#endif
-};
-
-class QSwipeGesturePrivate : public QGesturePrivate
-{
- Q_DECLARE_PUBLIC(QSwipeGesture)
-
-public:
- QSwipeGesturePrivate()
- : swipeAngle(-1)
- {
- }
+ QGesture *createGesture(QObject *target);
- void setupGestureTarget(QObject *o);
- qreal swipeAngle;
+ QGestureRecognizer::Result filterEvent(QGesture *state, QObject *watched, QEvent *event);
+ void reset(QGesture *state);
};
QT_END_NAMESPACE
diff --git a/src/gui/kernel/qwidget.cpp b/src/gui/kernel/qwidget.cpp
index a071ba6..de08312 100644
--- a/src/gui/kernel/qwidget.cpp
+++ b/src/gui/kernel/qwidget.cpp
@@ -115,6 +115,7 @@
#include "private/qevent_p.h"
#include "private/qgraphicssystem_p.h"
+#include "private/qgesturemanager_p.h"
// widget/widget data creation count
//#define QWIDGET_EXTRA_DEBUG
@@ -1503,6 +1504,8 @@ void QWidgetPrivate::setWinId(WId id) // set widget identifier
mapper->remove(data.winid);
}
+ const WId oldWinId = data.winid;
+
data.winid = id;
#if defined(Q_WS_X11)
hd = id; // X11: hd == ident
@@ -1510,6 +1513,16 @@ void QWidgetPrivate::setWinId(WId id) // set widget identifier
if (mapper && id && !userDesktopWidget) {
mapper->insert(data.winid, q);
}
+
+ if(oldWinId != id) {
+ // Do not emit an event when the old winId is destroyed. This only
+ // happens (a) during widget destruction, and (b) immediately prior
+ // to creation of a new winId, for example as a result of re-parenting.
+ if(id != 0) {
+ QEvent e(QEvent::WinIdChange);
+ QCoreApplication::sendEvent(q, &e);
+ }
+ }
}
void QWidgetPrivate::createTLExtra()
@@ -2228,8 +2241,8 @@ QWidget *QWidget::find(WId id)
against. If Qt is using Carbon, the {WId} is actually an HIViewRef. If Qt
is using Cocoa, {WId} is a pointer to an NSView.
- \note We recommend that you do not store this value as it is likely to
- change at run-time.
+ This value may change at run-time. An event with type QEvent::WinIdChange
+ will be sent to the widget following a change in window system identifier.
\sa find()
*/
@@ -8333,6 +8346,9 @@ bool QWidget::event(QEvent *event)
(void) QApplication::sendEvent(this, &mouseEvent);
break;
}
+ case QEvent::Gesture:
+ event->ignore();
+ break;
#ifndef QT_NO_PROPERTIES
case QEvent::DynamicPropertyChange: {
const QByteArray &propName = static_cast<QDynamicPropertyChangeEvent *>(event)->propertyName();
@@ -11669,6 +11685,19 @@ QGraphicsProxyWidget *QWidget::graphicsProxyWidget() const
Synonym for QList<QWidget *>.
*/
+/*!
+ Subscribes the widget to a given \a gesture with a \a context.
+
+ \sa QGestureEvent
+ \since 4.6
+*/
+void QWidget::grabGesture(Qt::GestureType gesture, Qt::GestureContext context)
+{
+ Q_D(QWidget);
+ d->gestureContext.insert(gesture, context);
+ (void)QGestureManager::instance(); // create a gesture manager
+}
+
QT_END_NAMESPACE
#include "moc_qwidget.cpp"
@@ -11982,3 +12011,10 @@ void QWidget::clearMask()
XRender extension is not supported on the X11 display, or if the
handle could not be created.
*/
+
+#ifdef Q_OS_SYMBIAN
+void QWidgetPrivate::_q_delayedDestroy(WId winId)
+{
+ delete winId;
+}
+#endif
diff --git a/src/gui/kernel/qwidget.h b/src/gui/kernel/qwidget.h
index 76418af..e603a1a 100644
--- a/src/gui/kernel/qwidget.h
+++ b/src/gui/kernel/qwidget.h
@@ -96,7 +96,6 @@ class QIcon;
class QWindowSurface;
class QLocale;
class QGraphicsProxyWidget;
-class QGestureManager;
class QGraphicsEffect;
#if defined(Q_WS_X11)
class QX11Info;
@@ -355,6 +354,8 @@ public:
QGraphicsEffect *graphicsEffect() const;
void setGraphicsEffect(QGraphicsEffect *effect);
+ void grabGesture(Qt::GestureType type, Qt::GestureContext context = Qt::WidgetWithChildrenGesture);
+
public Q_SLOTS:
void setWindowTitle(const QString &);
#ifndef QT_NO_STYLE_STYLESHEET
@@ -725,18 +726,17 @@ private:
friend class QGLContext;
friend class QGLWidget;
friend class QGLWindowSurface;
- friend class QGLWindowSurfaceGLPaintDevice;
- friend class QVGWindowSurface;
friend class QX11PaintEngine;
friend class QWin32PaintEngine;
friend class QShortcutPrivate;
friend class QShortcutMap;
friend class QWindowSurface;
- friend class QD3DWindowSurface;
friend class QGraphicsProxyWidget;
friend class QGraphicsProxyWidgetPrivate;
friend class QStyleSheetStyle;
friend struct QWidgetExceptionCleaner;
+ friend class QGestureManager;
+ friend class QWinNativePanGestureRecognizer;
#ifdef Q_WS_MAC
friend class QCoreGraphicsPaintEnginePrivate;
@@ -773,6 +773,9 @@ private:
private:
Q_DISABLE_COPY(QWidget)
Q_PRIVATE_SLOT(d_func(), void _q_showIfNotHidden())
+#ifdef Q_OS_SYMBIAN
+ Q_PRIVATE_SLOT(d_func(), void _q_delayedDestroy(WId winId))
+#endif
QWidgetData *data;
diff --git a/src/gui/kernel/qwidget_p.h b/src/gui/kernel/qwidget_p.h
index c06ef73..f7c2712 100644
--- a/src/gui/kernel/qwidget_p.h
+++ b/src/gui/kernel/qwidget_p.h
@@ -64,6 +64,8 @@
#include "QtGui/qapplication.h"
#include <private/qgraphicseffect_p.h>
+#include <private/qgesture_p.h>
+
#ifdef Q_WS_WIN
#include "QtCore/qt_windows.h"
#include <private/qdnd_p.h>
@@ -294,7 +296,8 @@ public:
void setMask_sys(const QRegion &);
#ifdef Q_OS_SYMBIAN
void setSoftKeys_sys(const QList<QAction*> &softkeys);
- void activateSymbianWindow();
+ void activateSymbianWindow(WId wid = 0);
+ void _q_delayedDestroy(WId winId);
#endif
void raise_sys();
@@ -578,6 +581,7 @@ public:
#ifndef QT_NO_ACTION
QList<QAction*> actions;
#endif
+ QMap<Qt::GestureType, Qt::GestureContext> gestureContext;
// Bit fields.
uint high_attributes[3]; // the low ones are in QWidget::widget_attributes
@@ -604,6 +608,7 @@ public:
bool isBackgroundInherited() const;
#elif defined(Q_WS_WIN) // <--------------------------------------------------------- WIN
uint noPaintOnScreen : 1; // see qwidget_win.cpp ::paintEngine()
+ uint nativeGesturePanEnabled : 1;
bool shouldShowMaximizeButton();
void winUpdateIsOpaque();
diff --git a/src/gui/kernel/qwidget_s60.cpp b/src/gui/kernel/qwidget_s60.cpp
index b0d405a..8ce5001 100644
--- a/src/gui/kernel/qwidget_s60.cpp
+++ b/src/gui/kernel/qwidget_s60.cpp
@@ -56,6 +56,12 @@
#include <aknappui.h>
#endif
+// This is necessary in order to be able to perform delayed invokation on slots
+// which take arguments of type WId. One example is
+// QWidgetPrivate::_q_delayedDestroy, which is used to delay destruction of
+// CCoeControl objects until after the CONE event handler has finished running.
+Q_DECLARE_METATYPE(WId)
+
QT_BEGIN_NAMESPACE
extern bool qt_nograb();
@@ -318,8 +324,6 @@ void QWidgetPrivate::create_sys(WId window, bool /* initializeWindow */, bool de
bool desktop = (type == Qt::Desktop);
//bool tool = (type == Qt::Tool || type == Qt::Drawer);
- WId id = 0;
-
if (popup)
flags |= Qt::WindowStaysOnTopHint; // a popup stays on top
@@ -341,13 +345,10 @@ void QWidgetPrivate::create_sys(WId window, bool /* initializeWindow */, bool de
data.crect.setSize(QSize(width, height));
}
- CCoeControl *destroyw = 0;
+ CCoeControl *const destroyw = destroyOldWindow ? data.winid : 0;
createExtra();
if (window) {
- if (destroyOldWindow)
- destroyw = data.winid;
- id = window;
setWinId(window);
TRect tr = window->Rect();
data.crect.setRect(tr.iTl.iX, tr.iTl.iY, tr.Width(), tr.Height());
@@ -355,10 +356,15 @@ void QWidgetPrivate::create_sys(WId window, bool /* initializeWindow */, bool de
} else if (topLevel) {
if (!q->testAttribute(Qt::WA_Moved) && !q->testAttribute(Qt::WA_DontShowOnScreen))
data.crect.moveTopLeft(QPoint(clientRect.iTl.iX, clientRect.iTl.iY));
- QSymbianControl *control= q_check_ptr(new QSymbianControl(q));
- id = (WId)control;
- setWinId(id);
- QT_TRAP_THROWING(control->ConstructL(true,desktop));
+
+ QScopedPointer<QSymbianControl> control( q_check_ptr(new QSymbianControl(q)) );
+ QT_TRAP_THROWING(control->ConstructL(true, desktop));
+
+ // Symbian windows are always created in an inactive state
+ // We perform this assignment for the case where the window is being re-created
+ // as aa result of a call to setParent_sys, on either this widget or one of its
+ // ancestors.
+ extra->activated = 0;
if (!desktop) {
TInt stackingFlags;
@@ -368,7 +374,7 @@ void QWidgetPrivate::create_sys(WId window, bool /* initializeWindow */, bool de
stackingFlags = ECoeStackFlagStandard;
}
control->MakeVisible(false);
- QT_TRAP_THROWING(control->ControlEnv()->AppUi()->AddToStackL(control, ECoeStackPriorityDefault, stackingFlags));
+ QT_TRAP_THROWING(control->ControlEnv()->AppUi()->AddToStackL(control.data(), ECoeStackPriorityDefault, stackingFlags));
// Avoid keyboard focus to a hidden window.
control->setFocusSafely(false);
@@ -391,11 +397,22 @@ void QWidgetPrivate::create_sys(WId window, bool /* initializeWindow */, bool de
int x, y, w, h;
data.crect.getRect(&x, &y, &w, &h);
control->SetRect(TRect(TPoint(x, y), TSize(w, h)));
+
+ // We wait until the control is fully constructed before calling setWinId, because
+ // this generates a WinIdChanged event.
+ setWinId(control.take());
+
} else if (q->testAttribute(Qt::WA_NativeWindow) || paintOnScreen()) { // create native child widget
- QSymbianControl *control = new QSymbianControl(q);
- setWinId(control);
+
+ QScopedPointer<QSymbianControl> control( q_check_ptr(new QSymbianControl(q)) );
QT_TRAP_THROWING(control->ConstructL(!parentWidget));
+ // Symbian windows are always created in an inactive state
+ // We perform this assignment for the case where the window is being re-created
+ // as aa result of a call to setParent_sys, on either this widget or one of its
+ // ancestors.
+ extra->activated = 0;
+
TInt stackingFlags;
if ((q->windowType() & Qt::Popup) == Qt::Popup) {
stackingFlags = ECoeStackFlagRefusesAllKeys | ECoeStackFlagRefusesFocus;
@@ -403,7 +420,7 @@ void QWidgetPrivate::create_sys(WId window, bool /* initializeWindow */, bool de
stackingFlags = ECoeStackFlagStandard;
}
control->MakeVisible(false);
- QT_TRAP_THROWING(control->ControlEnv()->AppUi()->AddToStackL(control, ECoeStackPriorityDefault, stackingFlags));
+ QT_TRAP_THROWING(control->ControlEnv()->AppUi()->AddToStackL(control.data(), ECoeStackPriorityDefault, stackingFlags));
// Avoid keyboard focus to a hidden window.
control->setFocusSafely(false);
@@ -418,12 +435,21 @@ void QWidgetPrivate::create_sys(WId window, bool /* initializeWindow */, bool de
| EPointerFilterMove | EPointerFilterDrag, 0);
if (q->isVisible() && q->testAttribute(Qt::WA_Mapped))
- activateSymbianWindow();
+ activateSymbianWindow(control.data());
+
+ // We wait until the control is fully constructed before calling setWinId, because
+ // this generates a WinIdChanged event.
+ setWinId(control.take());
}
if (destroyw) {
destroyw->ControlEnv()->AppUi()->RemoveFromStack(destroyw);
- CBase::Delete(destroyw);
+
+ // Delay deletion of the control in case this function is called in the
+ // context of a CONE event handler such as
+ // CCoeControl::ProcessPointerEventL
+ QMetaObject::invokeMethod(q, "_q_delayedDestroy",
+ Qt::QueuedConnection, Q_ARG(WId, destroyw));
}
if (q->testAttribute(Qt::WA_AcceptTouchEvents))
@@ -468,7 +494,7 @@ void QWidgetPrivate::show_sys()
invalidateBuffer(q->rect());
}
-void QWidgetPrivate::activateSymbianWindow()
+void QWidgetPrivate::activateSymbianWindow(WId wid)
{
Q_Q(QWidget);
@@ -476,8 +502,12 @@ void QWidgetPrivate::activateSymbianWindow()
Q_ASSERT(q->testAttribute(Qt::WA_Mapped));
Q_ASSERT(!extra->activated);
- WId id = q->internalWinId();
- QT_TRAP_THROWING(id->ActivateL());
+ if(!wid)
+ wid = q->internalWinId();
+
+ Q_ASSERT(wid);
+
+ QT_TRAP_THROWING(wid->ActivateL());
extra->activated = 1;
}
@@ -571,8 +601,14 @@ void QWidgetPrivate::reparentChildren()
w->d_func()->invalidateBuffer(w->rect());
WId parent = q->effectiveWinId();
WId child = w->effectiveWinId();
- if (parent != child)
- child->SetParent(parent);
+ if (parent != child) {
+ // Child widget is native. Because Symbian windows cannot be
+ // re-parented, we must re-create the window.
+ const WId window = 0;
+ const bool initializeWindow = false;
+ const bool destroyOldWindow = true;
+ w->d_func()->create_sys(window, initializeWindow, destroyOldWindow);
+ }
// ### TODO: We probably also need to update the component array here
w->d_func()->reparentChildren();
} else {
diff --git a/src/gui/kernel/qwidget_win.cpp b/src/gui/kernel/qwidget_win.cpp
index a0982f4..2b11bec 100644
--- a/src/gui/kernel/qwidget_win.cpp
+++ b/src/gui/kernel/qwidget_win.cpp
@@ -2029,11 +2029,6 @@ void QWidgetPrivate::winSetupGestures()
if (!q || !q->isVisible())
return;
QApplicationPrivate *qAppPriv = QApplicationPrivate::instance();
- QApplicationPrivate::WidgetStandardGesturesMap::const_iterator it =
- qAppPriv->widgetGestures.find(q);
- if (it == qAppPriv->widgetGestures.end())
- return;
- const QStandardGestures &gestures = it.value();
WId winid = q->effectiveWinId();
bool needh = false;
@@ -2052,10 +2047,10 @@ void QWidgetPrivate::winSetupGestures()
singleFingerPanEnabled = asa->d_func()->singleFingerPanEnabled;
}
if (winid && qAppPriv->SetGestureConfig) {
- GESTURECONFIG gc[3];
+ GESTURECONFIG gc[1];
memset(gc, 0, sizeof(gc));
gc[0].dwID = GID_PAN;
- if (gestures.pan) {
+ if (nativeGesturePanEnabled) {
gc[0].dwWant = GC_PAN;
if (needv && singleFingerPanEnabled)
gc[0].dwWant |= GC_PAN_WITH_SINGLE_FINGER_VERTICALLY;
@@ -2069,16 +2064,16 @@ void QWidgetPrivate::winSetupGestures()
gc[0].dwBlock = GC_PAN;
}
- gc[1].dwID = GID_ZOOM;
- if (gestures.pinch)
- gc[1].dwWant = GC_ZOOM;
- else
- gc[1].dwBlock = GC_ZOOM;
- gc[2].dwID = GID_ROTATE;
- if (gestures.pinch)
- gc[2].dwWant = GC_ROTATE;
- else
- gc[2].dwBlock = GC_ROTATE;
+// gc[1].dwID = GID_ZOOM;
+// if (gestures.pinch)
+// gc[1].dwWant = GC_ZOOM;
+// else
+// gc[1].dwBlock = GC_ZOOM;
+// gc[2].dwID = GID_ROTATE;
+// if (gestures.pinch)
+// gc[2].dwWant = GC_ROTATE;
+// else
+// gc[2].dwBlock = GC_ROTATE;
qAppPriv->SetGestureConfig(winid, 0, sizeof(gc)/sizeof(gc[0]), gc, sizeof(gc[0]));
}
diff --git a/src/gui/kernel/qwinnativepangesturerecognizer_win.cpp b/src/gui/kernel/qwinnativepangesturerecognizer_win.cpp
new file mode 100644
index 0000000..4619594
--- /dev/null
+++ b/src/gui/kernel/qwinnativepangesturerecognizer_win.cpp
@@ -0,0 +1,124 @@
+/****************************************************************************
+**
+** 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 QtGui module 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 "private/qwinnativepangesturerecognizer_win_p.h"
+
+#include "qevent.h"
+#include "qgraphicsitem.h"
+#include "qgesture.h"
+
+#include "private/qgesture_p.h"
+#include "private/qevent_p.h"
+#include "private/qapplication_p.h"
+#include "private/qwidget_p.h"
+
+QT_BEGIN_NAMESPACE
+
+QWinNativePanGestureRecognizer::QWinNativePanGestureRecognizer()
+{
+}
+
+QGesture* QWinNativePanGestureRecognizer::createGesture(QObject *target) const
+{
+ if (!target)
+ return new QPanGesture; // a special case
+ if (qobject_cast<QGraphicsObject*>(target))
+ return 0;
+ if (!target->isWidgetType())
+ return 0;
+
+ QWidget *q = static_cast<QWidget*>(target);
+ QWidgetPrivate *d = q->d_func();
+ d->nativeGesturePanEnabled = true;
+ d->winSetupGestures();
+
+ return new QPanGesture;
+}
+
+QGestureRecognizer::Result QWinNativePanGestureRecognizer::filterEvent(QGesture *state, QObject *, QEvent *event)
+{
+ QPanGesture *q = static_cast<QPanGesture*>(state);
+ QPanGesturePrivate *d = q->d_func();
+
+ QGestureRecognizer::Result result = QGestureRecognizer::Ignore;
+ if (event->type() == QEvent::NativeGesture) {
+ QNativeGestureEvent *ev = static_cast<QNativeGestureEvent*>(event);
+ switch(ev->gestureType) {
+ case QNativeGestureEvent::GestureBegin:
+ break;
+ case QNativeGestureEvent::Pan:
+ result = QGestureRecognizer::GestureTriggered;
+ event->accept();
+ break;
+ case QNativeGestureEvent::GestureEnd:
+ if (q->state() == Qt::NoGesture)
+ return QGestureRecognizer::Ignore; // some other gesture has ended
+ result = QGestureRecognizer::GestureFinished;
+ break;
+ default:
+ return QGestureRecognizer::Ignore;
+ }
+ if (q->state() == Qt::NoGesture) {
+ d->lastOffset = d->totalOffset = d->offset = QSize();
+ } else {
+ d->lastOffset = d->offset;
+ d->offset = QSize(ev->position.x() - d->lastPosition.x(),
+ ev->position.y() - d->lastPosition.y());
+ d->totalOffset += d->offset;
+ }
+ d->lastPosition = ev->position;
+ }
+ return result;
+}
+
+void QWinNativePanGestureRecognizer::reset(QGesture *state)
+{
+ QPanGesture *pan = static_cast<QPanGesture*>(state);
+ QPanGesturePrivate *d = pan->d_func();
+
+ d->totalOffset = d->lastOffset = d->offset = QSizeF();
+ d->lastPosition = QPoint();
+ d->acceleration = 0;
+
+ QGestureRecognizer::reset(state);
+}
+
+QT_END_NAMESPACE
diff --git a/src/gui/kernel/qwinnativepangesturerecognizer_win_p.h b/src/gui/kernel/qwinnativepangesturerecognizer_win_p.h
new file mode 100644
index 0000000..a1e8511
--- /dev/null
+++ b/src/gui/kernel/qwinnativepangesturerecognizer_win_p.h
@@ -0,0 +1,73 @@
+/****************************************************************************
+**
+** 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 QtGui module 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 QWINNATIVEPANGESTURERECOGNIZER_WIN_P_H
+#define QWINNATIVEPANGESTURERECOGNIZER_WIN_P_H
+
+//
+// W A R N I N G
+// -------------
+//
+// This file is not part of the Qt API. It exists for the convenience
+// of other Qt classes. This header file may change from version to
+// version without notice, or even be removed.
+//
+// We mean it.
+//
+
+#include <QGestureRecognizer>
+
+QT_BEGIN_NAMESPACE
+
+class QWinNativePanGestureRecognizer : public QGestureRecognizer
+{
+public:
+ QWinNativePanGestureRecognizer();
+
+ QGesture* createGesture(QObject *target) const;
+
+ QGestureRecognizer::Result filterEvent(QGesture *state, QObject *watched, QEvent *event);
+ void reset(QGesture *state);
+};
+
+QT_END_NAMESPACE
+
+#endif // QWINNATIVEPANGESTURERECOGNIZER_WIN_P_H
diff --git a/src/gui/painting/qcolor.cpp b/src/gui/painting/qcolor.cpp
index d9b824b..4da993b 100644
--- a/src/gui/painting/qcolor.cpp
+++ b/src/gui/painting/qcolor.cpp
@@ -176,22 +176,25 @@ QT_BEGIN_NAMESPACE
\section1 Predefined Colors
- There are 20 predefined QColors: Qt::white, Qt::black,
- Qt::red, Qt::darkRed, Qt::green, Qt::darkGreen, Qt::blue,
- Qt::darkBlue, Qt::cyan, Qt::darkCyan, Qt::magenta,
- Qt::darkMagenta, Qt::yellow, Qt::darkYellow, Qt::gray,
- Qt::darkGray, Qt::lightGray, Qt::color0, Qt::color1, and
- Qt::transparent.
+ There are 20 predefined QColors described by the Qt::GlobalColor enum,
+ including black, white, primary and secondary colors, darker versions
+ of these colors and three shades of gray. QColor also recognizes a
+ variety of color names; the static colorNames() function returns a
+ QStringList color names that QColor knows about.
\img qt-colors.png Qt Colors
- QColor provides the static colorNames() function which returns a
- QStringList containing the color names Qt knows about.
+ Additionally, the Qt::color0, Qt::color1 and Qt::transparent colors
+ are used for special purposes.
- The colors Qt::color0 (zero pixel value) and Qt::color1 (non-zero
- pixel value) are special colors for drawing in QBitmaps. Painting with
- Qt::color0 sets the bitmap bits to 0 (transparent, i.e. background), and
- painting with Qt::color1 sets the bits to 1 (opaque, i.e. foreground).
+ Qt::color0 (zero pixel value) and Qt::color1 (non-zero pixel value)
+ are special colors for drawing in QBitmaps. Painting with Qt::color0
+ sets the bitmap bits to 0 (transparent; i.e., background), and painting
+ with Qt::color1 sets the bits to 1 (opaque; i.e., foreground).
+
+ Qt::transparent is used to indicate a transparent pixel. When painting
+ with this value, a pixel value will be used that is appropriate for the
+ underlying pixel format in use.
\section1 The HSV Color Model
diff --git a/src/gui/painting/qpaintdevice.cpp b/src/gui/painting/qpaintdevice.cpp
index 95c0b44..6114938 100644
--- a/src/gui/painting/qpaintdevice.cpp
+++ b/src/gui/painting/qpaintdevice.cpp
@@ -65,4 +65,9 @@ int QPaintDevice::metric(PaintDeviceMetric) const
return 0;
}
+Q_GUI_EXPORT int qt_paint_device_metric(const QPaintDevice *device, QPaintDevice::PaintDeviceMetric metric)
+{
+ return device->metric(metric);
+}
+
QT_END_NAMESPACE
diff --git a/src/gui/painting/qpaintdevice.h b/src/gui/painting/qpaintdevice.h
index 92aa3cb..c8e86b8 100644
--- a/src/gui/painting/qpaintdevice.h
+++ b/src/gui/painting/qpaintdevice.h
@@ -137,6 +137,7 @@ public:
friend class QPainter;
friend class QFontEngineMac;
friend class QX11PaintEngine;
+ friend Q_GUI_EXPORT int qt_paint_device_metric(const QPaintDevice *device, PaintDeviceMetric metric);
};
#ifdef QT3_SUPPORT
diff --git a/src/gui/painting/qpaintengine_raster.cpp b/src/gui/painting/qpaintengine_raster.cpp
index 995f0ac..fab2d8d 100644
--- a/src/gui/painting/qpaintengine_raster.cpp
+++ b/src/gui/painting/qpaintengine_raster.cpp
@@ -4215,13 +4215,6 @@ void QRasterBuffer::prepare(QCustomRasterPaintDevice *device)
drawHelper = qDrawHelper + format;
}
-class MetricAccessor : public QWidget {
-public:
- int metric(PaintDeviceMetric m) {
- return QWidget::metric(m);
- }
-};
-
int QCustomRasterPaintDevice::metric(PaintDeviceMetric m) const
{
switch (m) {
@@ -4233,7 +4226,7 @@ int QCustomRasterPaintDevice::metric(PaintDeviceMetric m) const
break;
}
- return (static_cast<MetricAccessor*>(widget)->metric(m));
+ return qt_paint_device_metric(widget, m);
}
int QCustomRasterPaintDevice::bytesPerLine() const
diff --git a/src/gui/painting/qpaintengine_s60.cpp b/src/gui/painting/qpaintengine_s60.cpp
index e17dba1..6f4f398 100644
--- a/src/gui/painting/qpaintengine_s60.cpp
+++ b/src/gui/painting/qpaintengine_s60.cpp
@@ -47,7 +47,7 @@ QT_BEGIN_NAMESPACE
class QS60PaintEnginePrivate : public QRasterPaintEnginePrivate
{
public:
- QS60PaintEnginePrivate(QS60PaintEngine *engine) { }
+ QS60PaintEnginePrivate(QS60PaintEngine *engine) { Q_UNUSED(engine); }
};
QS60PaintEngine::QS60PaintEngine(QPaintDevice *device, QS60PixmapData *data)
diff --git a/src/gui/painting/qpaintengineex_p.h b/src/gui/painting/qpaintengineex_p.h
index 81ed06b..3ec9bd6 100644
--- a/src/gui/painting/qpaintengineex_p.h
+++ b/src/gui/painting/qpaintengineex_p.h
@@ -54,6 +54,7 @@
//
#include <QtGui/qpaintengine.h>
+#include <QtGui/qdrawutil.h>
#include <private/qpaintengine_p.h>
#include <private/qstroker_p.h>
@@ -71,12 +72,6 @@ class QPainterState;
class QPaintEngineExPrivate;
struct StrokeHandler;
-namespace QDrawPixmaps
-{
- struct Data;
- enum DrawingHint;
-}
-
struct QIntRect {
int x1, y1, x2, y2;
inline void set(const QRect &r) {
diff --git a/src/gui/s60framework/qs60mainapplication.cpp b/src/gui/s60framework/qs60mainapplication.cpp
index 2973c97..82e7743 100644
--- a/src/gui/s60framework/qs60mainapplication.cpp
+++ b/src/gui/s60framework/qs60mainapplication.cpp
@@ -60,27 +60,32 @@ CApaApplication *newS60Application()
_LIT(KQtWrapperResourceFile, "\\resource\\apps\\s60main.rsc");
/*!
- * \class QS60MainApplication
- * \obsolete
- * \since 4.6
- * \brief The QS60MainApplication class provides support for migration from S60.
- *
- * The QS60MainApplication provides a helper class for use in migrating from existing S60 based
- * applications to Qt based applications. It is used in the exact same way as the
- * \c CAknApplication class from Symbian, but internally provides extensions used by Qt.
- *
- * When modifying old S60 applications that rely on implementing functions in \c CAknApplication,
- * the class should be modified to inherit from this class instead of \c CAknApplication. Then the
- * application can choose to override only certain functions. To make Qt use the custom application
- * objects, pass a factory function to
- * QApplication::QApplication(QApplication::QS60MainApplicationFactory, int &, char **).
- *
- * For more information on \c CAknApplication, please see the S60 documentation.
- *
- * Unlike other Qt classes, QS60MainApplication behaves like an S60 class, and can throw Symbian
- * leaves.
- *
- * \sa QS60MainDocument, QS60MainAppUi, QApplication::QS60MainApplicationFactory
+ \class QS60MainApplication
+ \since 4.6
+ \brief The QS60MainApplication class provides support for migration from S60.
+
+ \warning This class is provided only to get access to S60 specific
+ functionality in the application framework classes. It is not
+ portable. We strongly recommend against using it in new applications.
+
+ The QS60MainApplication provides a helper class for use in migrating
+ from existing S60 based applications to Qt based applications. It is
+ used in the exact same way as the \c CAknApplication class from
+ Symbian, but internally provides extensions used by Qt.
+
+ When modifying old S60 applications that rely on implementing
+ functions in \c CAknApplication, the class should be modified to
+ inherit from this class instead of \c CAknApplication. Then the
+ application can choose to override only certain functions. To make
+ Qt use the custom application objects, pass a factory function to
+ \c{QApplication::QApplication(QApplication::QS60MainApplicationFactory, int &, char **)}.
+
+ For more information on \c CAknApplication, please see the S60 documentation.
+
+ Unlike other Qt classes, QS60MainApplication behaves like an S60 class, and can throw Symbian
+ leaves.
+
+ \sa QS60MainDocument, QS60MainAppUi, QApplication::QS60MainApplicationFactory
*/
/*!
diff --git a/src/gui/s60framework/qs60mainappui.cpp b/src/gui/s60framework/qs60mainappui.cpp
index d8181f8..e630253 100644
--- a/src/gui/s60framework/qs60mainappui.cpp
+++ b/src/gui/s60framework/qs60mainappui.cpp
@@ -58,25 +58,31 @@
QT_BEGIN_NAMESPACE
/*!
- * \class QS60MainAppUi
- * \obsolete
- * \since 4.6
- * \brief Helper class for S60 migration
- *
- * The QS60MainAppUi provides a helper class for use in migrating from existing S60 based
- * applications to Qt based applications. It is used in the exact same way as the
- * \c CAknAppUi class from Symbian, but internally provides extensions used by Qt.
- *
- * When modifying old S60 applications that rely on implementing functions in \c CAknAppUi,
- * the class should be modified to inherit from this class instead of \c CAknAppUi. Then the
- * application can choose to override only certain functions.
- *
- * For more information on \c CAknAppUi, please see the S60 documentation.
- *
- * Unlike other Qt classes, QS60MainAppUi behaves like an S60 class, and can throw Symbian
- * leaves.
- *
- * \sa QS60MainDocument, QS60MainApplication
+ \class QS60MainAppUi
+ \since 4.6
+ \brief The QS60MainAppUi class is a helper class for S60 migration.
+
+ \warning This class is provided only to get access to S60 specific
+ functionality in the application framework classes. It is not
+ portable. We strongly recommend against using it in new applications.
+
+ The QS60MainAppUi provides a helper class for use in migrating from
+ existing S60 based applications to Qt based applications. It is used
+ in the exact same way as the \c CAknAppUi class from Symbian, but
+ internally provides extensions used by Qt.
+
+ When modifying old S60 applications that rely on implementing
+ functions in \c CAknAppUi, the class should be modified to inherit
+ from this class instead of \c CAknAppUi. Then the application can
+ choose to override only certain functions.
+
+ For more information on \c CAknAppUi, please see the S60
+ documentation.
+
+ Unlike other Qt classes, QS60MainAppUi behaves like an S60 class,
+ and can throw Symbian leaves.
+
+ \sa QS60MainDocument, QS60MainApplication
*/
/*!
diff --git a/src/gui/s60framework/qs60maindocument.cpp b/src/gui/s60framework/qs60maindocument.cpp
index 52595db..7405784 100644
--- a/src/gui/s60framework/qs60maindocument.cpp
+++ b/src/gui/s60framework/qs60maindocument.cpp
@@ -47,25 +47,31 @@
QT_BEGIN_NAMESPACE
/*!
- * \class QS60MainDocument
- * \obsolete
- * \since 4.6
- * \brief Helper class for S60 migration
- *
- * The QS60MainDocument provides a helper class for use in migrating from existing S60 based
- * applications to Qt based applications. It is used in the exact same way as the
- * \c CAknDocument class from Symbian, but internally provides extensions used by Qt.
- *
- * When modifying old S60 applications that rely on implementing functions in \c CAknDocument,
- * the class should be modified to inherit from this class instead of \c CAknDocument. Then the
- * application can choose to override only certain functions.
- *
- * For more information on \c CAknDocument, please see the S60 documentation.
- *
- * Unlike other Qt classes, QS60MainDocument behaves like an S60 class, and can throw Symbian
- * leaves.
- *
- * \sa QS60MainApplication, QS60MainAppUi
+ \class QS60MainDocument
+ \since 4.6
+ \brief The QS60MainDocument class is a helper class for S60 migration.
+
+ \warning This class is provided only to get access to S60 specific
+ functionality in the application framework classes. It is not
+ portable. We strongly recommend against using it in new applications.
+
+ The QS60MainDocument provides a helper class for use in migrating
+ from existing S60 based applications to Qt based applications. It is
+ used in the exact same way as the \c CAknDocument class from
+ Symbian, but internally provides extensions used by Qt.
+
+ When modifying old S60 applications that rely on implementing
+ functions in \c CAknDocument, the class should be modified to
+ inherit from this class instead of \c CAknDocument. Then the
+ application can choose to override only certain functions.
+
+ For more information on \c CAknDocument, please see the S60
+ documentation.
+
+ Unlike other Qt classes, QS60MainDocument behaves like an S60 class,
+ and can throw Symbian leaves.
+
+ \sa QS60MainApplication, QS60MainAppUi
*/
/*!
diff --git a/src/gui/styles/gtksymbols.cpp b/src/gui/styles/gtksymbols.cpp
index d62f717..6ec5796 100644
--- a/src/gui/styles/gtksymbols.cpp
+++ b/src/gui/styles/gtksymbols.cpp
@@ -984,15 +984,18 @@ QIcon QGtk::getFilesystemIcon(const QFileInfo &info)
if (QGtk::gnome_vfs_init && QGtk::gnome_icon_lookup_sync) {
QGtk::gnome_vfs_init();
GtkIconTheme *theme = QGtk::gtk_icon_theme_get_default();
- QString fileurl = QUrl::fromLocalFile(info.absoluteFilePath()).toEncoded();
+ QByteArray fileurl = QUrl::fromLocalFile(info.absoluteFilePath()).toEncoded();
char * icon_name = QGtk::gnome_icon_lookup_sync(theme,
NULL,
- qPrintable(fileurl),
+ fileurl.data(),
NULL,
GNOME_ICON_LOOKUP_FLAGS_NONE,
NULL);
- return QIcon::fromTheme(icon_name);
+ QString iconName = QString::fromUtf8(icon_name);
g_free(icon_name);
+ if (iconName.startsWith(QLatin1Char('/')))
+ return QIcon(iconName);
+ return QIcon::fromTheme(iconName);
}
return icon;
}
diff --git a/src/gui/text/qfontdatabase.cpp b/src/gui/text/qfontdatabase.cpp
index 0aed71a..738e36a 100644
--- a/src/gui/text/qfontdatabase.cpp
+++ b/src/gui/text/qfontdatabase.cpp
@@ -949,7 +949,7 @@ struct QtFontDesc
#if !defined(Q_WS_MAC)
static void match(int script, const QFontDef &request,
const QString &family_name, const QString &foundry_name, int force_encoding_id,
- QtFontDesc *desc, const QList<int> &blacklistedFamilies = QList<int>());
+ QtFontDesc *desc, const QList<int> &blacklistedFamilies = QList<int>(), bool forceXLFD=false);
#if defined(Q_WS_X11) || defined(Q_WS_QWS)
static void initFontDef(const QtFontDesc &desc, const QFontDef &request, QFontDef *fontDef)
@@ -1316,7 +1316,7 @@ unsigned int bestFoundry(int script, unsigned int score, int styleStrategy,
*/
static void match(int script, const QFontDef &request,
const QString &family_name, const QString &foundry_name, int force_encoding_id,
- QtFontDesc *desc, const QList<int> &blacklistedFamilies)
+ QtFontDesc *desc, const QList<int> &blacklistedFamilies, bool forceXLFD)
{
Q_UNUSED(force_encoding_id);
@@ -1351,7 +1351,12 @@ static void match(int script, const QFontDef &request,
unsigned int score = ~0u;
+#ifdef Q_WS_X11
+ load(family_name, script, forceXLFD);
+#else
+ Q_UNUSED(forceXLFD);
load(family_name, script);
+#endif
QFontDatabasePrivate *db = privateDb();
for (int x = 0; x < db->count; ++x) {
diff --git a/src/gui/text/qfontdatabase_x11.cpp b/src/gui/text/qfontdatabase_x11.cpp
index ae93f90..382c4fe 100644
--- a/src/gui/text/qfontdatabase_x11.cpp
+++ b/src/gui/text/qfontdatabase_x11.cpp
@@ -1204,9 +1204,9 @@ static void loadFontConfig()
static void initializeDb();
-static void load(const QString &family = QString(), int script = -1)
+static void load(const QString &family = QString(), int script = -1, bool forceXLFD = false)
{
- if (X11->has_fontconfig) {
+ if (X11->has_fontconfig && !forceXLFD) {
initializeDb();
return;
}
@@ -1784,7 +1784,7 @@ QFontEngine *QFontDatabase::loadXlfd(int screen, int script, const QFontDef &req
QString family, foundry;
QT_PREPEND_NAMESPACE(parseFontName)(families_and_foundries.at(i), foundry, family);
FM_DEBUG("loadXlfd: >>>>>>>>>>>>>>trying to match '%s' encoding=%d", family.toLatin1().data(), force_encoding_id);
- QT_PREPEND_NAMESPACE(match)(script, request, family, foundry, force_encoding_id, &desc);
+ QT_PREPEND_NAMESPACE(match)(script, request, family, foundry, force_encoding_id, &desc, QList<int>(), true);
if (desc.family)
break;
}
@@ -1847,23 +1847,26 @@ QFontEngine *QFontDatabase::loadXlfd(int screen, int script, const QFontDef &req
}
} else {
QList<int> encodings;
- if (desc.encoding)
- encodings.append(int(desc.encoding->encoding));
+ if (desc.encoding) {
+ if (desc.encoding->encoding >= 0)
+ encodings.append(int(desc.encoding->encoding));
+ }
if (desc.size) {
// append all other encodings for the matched font
for (int i = 0; i < desc.size->count; ++i) {
QtFontEncoding *e = desc.size->encodings + i;
- if (e == desc.encoding)
- continue;
+ if (e == desc.encoding || e->encoding < 0)
+ continue;
encodings.append(int(e->encoding));
}
}
// fill in the missing encodings
const XlfdEncoding *enc = xlfd_encoding;
for (; enc->name; ++enc) {
- if (!encodings.contains(enc->id))
+ if (!encodings.contains(enc->id) && enc->id >= 0) {
encodings.append(enc->id);
+ }
}
#if defined(FONT_MATCH_DEBUG)
@@ -1925,6 +1928,13 @@ void QFontDatabase::load(const QFontPrivate *d, int script)
#ifndef QT_NO_FONTCONFIG
} else if (X11->has_fontconfig) {
fe = loadFc(d, script, req);
+
+ if (fe != 0 && fe->fontDef.pixelSize != req.pixelSize) {
+ delete fe;
+ fe = loadXlfd(d->screen, script, req);
+ }
+
+
#endif
} else if (mainThread) {
fe = loadXlfd(d->screen, script, req);
diff --git a/src/gui/text/qfontengine_mac.mm b/src/gui/text/qfontengine_mac.mm
index 40db7b4..758d8af 100644
--- a/src/gui/text/qfontengine_mac.mm
+++ b/src/gui/text/qfontengine_mac.mm
@@ -138,9 +138,10 @@ QCoreTextFontEngineMulti::QCoreTextFontEngineMulti(const ATSFontFamilyRef &, con
QCFString name;
ATSFontGetName(atsFontRef, kATSOptionFlagsDefault, &name);
- QCFType<CTFontDescriptorRef> descriptor = CTFontDescriptorCreateWithNameAndSize(name, fontDef.pointSize);
- QCFType<CTFontRef> baseFont = CTFontCreateWithFontDescriptor(descriptor, fontDef.pointSize, 0);
- ctfont = CTFontCreateCopyWithSymbolicTraits(baseFont, fontDef.pointSize, 0, symbolicTraits, symbolicTraits);
+
+ QCFType<CTFontDescriptorRef> descriptor = CTFontDescriptorCreateWithNameAndSize(name, fontDef.pixelSize);
+ QCFType<CTFontRef> baseFont = CTFontCreateWithFontDescriptor(descriptor, fontDef.pixelSize, 0);
+ ctfont = CTFontCreateCopyWithSymbolicTraits(baseFont, fontDef.pixelSize, 0, symbolicTraits, symbolicTraits);
// CTFontCreateCopyWithSymbolicTraits returns NULL if we ask for a trait that does
// not exist for the given font. (for example italic)
diff --git a/src/gui/text/qfontengine_x11.cpp b/src/gui/text/qfontengine_x11.cpp
index 5ea4554..ff3f628 100644
--- a/src/gui/text/qfontengine_x11.cpp
+++ b/src/gui/text/qfontengine_x11.cpp
@@ -488,9 +488,10 @@ glyph_metrics_t QFontEngineXLFD::boundingBox(const QGlyphLayout &glyphs)
QFixed y = overall.yoff + glyphs.offsets[i].y - xcs->ascent;
overall.x = qMin(overall.x, x);
overall.y = qMin(overall.y, y);
+ // XCharStruct::rbearing is defined as distance from left edge to rightmost pixel
xmax = qMax(xmax, overall.xoff + glyphs.offsets[i].x + xcs->rbearing);
ymax = qMax(ymax, y + xcs->ascent + xcs->descent);
- overall.xoff += glyphs.advances_x[i];
+ overall.xoff += glyphs.advances_x[i] + QFixed::fromFixed(glyphs.justifications[i].space_18d6);
} else {
QFixed size = _fs->ascent;
overall.x = qMin(overall.x, overall.xoff);
@@ -511,6 +512,8 @@ glyph_metrics_t QFontEngineXLFD::boundingBox(glyph_t glyph)
glyph_metrics_t gm;
XCharStruct *xcs = charStruct(_fs, glyph);
if (xcs) {
+ // XCharStruct::rbearing is defined as distance from left edge to rightmost pixel
+ // XCharStruct::width is defined as the advance
gm = glyph_metrics_t(xcs->lbearing, -xcs->ascent, xcs->rbearing- xcs->lbearing, xcs->ascent + xcs->descent,
xcs->width, 0);
} else {
diff --git a/src/gui/text/qtextcontrol.cpp b/src/gui/text/qtextcontrol.cpp
index db4c07c..ee8b751 100644
--- a/src/gui/text/qtextcontrol.cpp
+++ b/src/gui/text/qtextcontrol.cpp
@@ -505,9 +505,13 @@ void QTextControlPrivate::startDrag()
drag->setMimeData(data);
Qt::DropActions actions = Qt::CopyAction;
- if (interactionFlags & Qt::TextEditable)
+ Qt::DropAction action;
+ if (interactionFlags & Qt::TextEditable) {
actions |= Qt::MoveAction;
- Qt::DropAction action = drag->exec(actions, Qt::MoveAction);
+ action = drag->exec(actions, Qt::MoveAction);
+ } else {
+ action = drag->exec(actions, Qt::CopyAction);
+ }
if (action == Qt::MoveAction && drag->target() != contextWidget)
cursor.removeSelectedText();
diff --git a/src/gui/text/qtextodfwriter.cpp b/src/gui/text/qtextodfwriter.cpp
index 3521ade..9b7e8de 100644
--- a/src/gui/text/qtextodfwriter.cpp
+++ b/src/gui/text/qtextodfwriter.cpp
@@ -550,9 +550,9 @@ void QTextOdfWriter::writeCharacterFormat(QXmlStreamWriter &writer, QTextCharFor
}
}
if (format.hasProperty(QTextFormat::FontLetterSpacing))
- writer.writeAttribute(foNS, QString::fromLatin1("letter-spacing"), pixelToPoint(format.fontLetterSpacing()) );
+ writer.writeAttribute(foNS, QString::fromLatin1("letter-spacing"), pixelToPoint(format.fontLetterSpacing()));
if (format.hasProperty(QTextFormat::FontWordSpacing))
- writer.writeAttribute(foNS, QString::fromLatin1("letter-spacing"), pixelToPoint(format.fontWordSpacing()) );
+ writer.writeAttribute(foNS, QString::fromLatin1("word-spacing"), pixelToPoint(format.fontWordSpacing()));
if (format.hasProperty(QTextFormat::FontUnderline))
writer.writeAttribute(styleNS, QString::fromLatin1("text-underline-type"),
format.fontUnderline() ? QString::fromLatin1("single") : QString::fromLatin1("none"));
diff --git a/src/gui/widgets/qabstractscrollarea.cpp b/src/gui/widgets/qabstractscrollarea.cpp
index d8702cf..0896256 100644
--- a/src/gui/widgets/qabstractscrollarea.cpp
+++ b/src/gui/widgets/qabstractscrollarea.cpp
@@ -52,11 +52,6 @@
#include "qboxlayout.h"
#include "qpainter.h"
-#ifdef Q_WS_WIN
-#include "qstandardgestures.h"
-#include <private/qstandardgestures_p.h>
-#endif
-
#include "qabstractscrollarea_p.h"
#include <qwidget.h>
@@ -165,7 +160,7 @@ QAbstractScrollAreaPrivate::QAbstractScrollAreaPrivate()
viewport(0), cornerWidget(0), left(0), top(0), right(0), bottom(0),
xoffset(0), yoffset(0), viewportFilter(0)
#ifdef Q_WS_WIN
- , panGesture(0), singleFingerPanEnabled(false)
+ , singleFingerPanEnabled(false)
#endif
{
}
@@ -298,14 +293,6 @@ void QAbstractScrollAreaPrivate::init()
q->setFrameStyle(QFrame::StyledPanel | QFrame::Sunken);
q->setSizePolicy(QSizePolicy::Expanding, QSizePolicy::Expanding);
layoutChildren();
-
-#ifdef Q_WS_WIN
- panGesture = new QPanGesture(viewport, q);
- panGesture->d_func()->implicitGesture = true;
- QObject::connect(panGesture, SIGNAL(started()), q, SLOT(_q_gestureTriggered()));
- QObject::connect(panGesture, SIGNAL(triggered()), q, SLOT(_q_gestureTriggered()));
- QObject::connect(panGesture, SIGNAL(finished()), q, SLOT(_q_gestureTriggered()));
-#endif // Q_WS_WIN
}
#ifdef Q_WS_WIN
@@ -556,9 +543,6 @@ void QAbstractScrollArea::setViewport(QWidget *widget)
if (isVisible())
d->viewport->show();
QMetaObject::invokeMethod(this, "setupViewport", Q_ARG(QWidget *, widget));
-#ifdef Q_WS_WIN
- d->panGesture->setGestureTarget(widget);
-#endif
delete oldViewport;
}
}
@@ -1351,26 +1335,24 @@ void QAbstractScrollArea::setupViewport(QWidget *viewport)
Q_UNUSED(viewport);
}
-#ifdef Q_WS_WIN
-void QAbstractScrollAreaPrivate::_q_gestureTriggered()
-{
- Q_Q(QAbstractScrollArea);
- QPanGesture *g = qobject_cast<QPanGesture*>(q->sender());
- if (!g)
- return;
- QScrollBar *hBar = q->horizontalScrollBar();
- QScrollBar *vBar = q->verticalScrollBar();
- QSizeF delta = g->lastOffset();
- if (!delta.isNull()) {
- if (QApplication::isRightToLeft())
- delta.rwidth() *= -1;
- int newX = hBar->value() - delta.width();
- int newY = vBar->value() - delta.height();
- hbar->setValue(newX);
- vbar->setValue(newY);
- }
-}
-#endif
+//void QAbstractScrollAreaPrivate::_q_gestureTriggered()
+//{
+// Q_Q(QAbstractScrollArea);
+// QPanGesture *g = qobject_cast<QPanGesture*>(q->sender());
+// if (!g)
+// return;
+// QScrollBar *hBar = q->horizontalScrollBar();
+// QScrollBar *vBar = q->verticalScrollBar();
+// QSizeF delta = g->lastOffset();
+// if (!delta.isNull()) {
+// if (QApplication::isRightToLeft())
+// delta.rwidth() *= -1;
+// int newX = hBar->value() - delta.width();
+// int newY = vBar->value() - delta.height();
+// hbar->setValue(newX);
+// vbar->setValue(newY);
+// }
+//}
QT_END_NAMESPACE
diff --git a/src/gui/widgets/qabstractscrollarea.h b/src/gui/widgets/qabstractscrollarea.h
index 3773477..b3a1861 100644
--- a/src/gui/widgets/qabstractscrollarea.h
+++ b/src/gui/widgets/qabstractscrollarea.h
@@ -129,10 +129,6 @@ private:
Q_PRIVATE_SLOT(d_func(), void _q_vslide(int))
Q_PRIVATE_SLOT(d_func(), void _q_showOrHideScrollBars())
-#ifdef Q_WS_WIN
- Q_PRIVATE_SLOT(d_func(), void _q_gestureTriggered())
-#endif
-
friend class QStyleSheetStyle;
friend class QWidgetPrivate;
};
diff --git a/src/gui/widgets/qabstractscrollarea_p.h b/src/gui/widgets/qabstractscrollarea_p.h
index 0bb2851..bfb8917 100644
--- a/src/gui/widgets/qabstractscrollarea_p.h
+++ b/src/gui/widgets/qabstractscrollarea_p.h
@@ -60,7 +60,6 @@ QT_BEGIN_NAMESPACE
#ifndef QT_NO_SCROLLAREA
-class QPanGesture;
class QScrollBar;
class QAbstractScrollAreaScrollBarContainer;
class Q_AUTOTEST_EXPORT QAbstractScrollAreaPrivate: public QFramePrivate
@@ -102,8 +101,6 @@ public:
QScopedPointer<QObject> viewportFilter;
#ifdef Q_WS_WIN
- QPanGesture *panGesture;
- virtual void _q_gestureTriggered();
bool singleFingerPanEnabled;
void setSingleFingerPanEnabled(bool on = true);
#endif
diff --git a/src/gui/widgets/qcombobox.cpp b/src/gui/widgets/qcombobox.cpp
index b606538..0e888d6 100644
--- a/src/gui/widgets/qcombobox.cpp
+++ b/src/gui/widgets/qcombobox.cpp
@@ -2174,11 +2174,14 @@ void QComboBox::insertSeparator(int index)
/*!
Removes the item at the given \a index from the combobox.
This will update the current index if the index is removed.
+
+ This function does nothing if \a index is out of range.
*/
void QComboBox::removeItem(int index)
{
- Q_ASSERT(index >= 0 && index < count());
Q_D(QComboBox);
+ if (index < 0 || index >= count())
+ return;
d->model->removeRows(index, 1, d->root);
}
diff --git a/src/gui/widgets/qdialogbuttonbox.cpp b/src/gui/widgets/qdialogbuttonbox.cpp
index 280ca63..10f8db8 100644
--- a/src/gui/widgets/qdialogbuttonbox.cpp
+++ b/src/gui/widgets/qdialogbuttonbox.cpp
@@ -560,7 +560,7 @@ QAction* QDialogButtonBoxPrivate::createSoftKey(QAbstractButton *button, QDialog
Q_Q(QDialogButtonBox);
QAction::SoftKeyRole softkeyRole;
- QAction *action = new QAction(button->text(), q);
+ QAction *action = new QAction(button->text(), button);
switch (role) {
case ApplyRole:
@@ -581,7 +581,6 @@ QAction* QDialogButtonBoxPrivate::createSoftKey(QAbstractButton *button, QDialog
}
QObject::connect(action, SIGNAL(triggered()), button, SIGNAL(clicked()));
action->setSoftKeyRole(softkeyRole);
- action->setEnabled(button->isEnabled());
return action;
}
#endif
diff --git a/src/gui/widgets/qlinecontrol.cpp b/src/gui/widgets/qlinecontrol.cpp
index 5930540..7f9ff82 100644
--- a/src/gui/widgets/qlinecontrol.cpp
+++ b/src/gui/widgets/qlinecontrol.cpp
@@ -1290,7 +1290,7 @@ void QLineControl::setCursorBlinkPeriod(int msec)
m_blinkStatus = 1;
} else {
m_blinkTimer = 0;
- if (m_blinkStatus == 0)
+ if (m_blinkStatus == 1)
emit updateNeeded(inputMask().isEmpty() ? cursorRect() : QRect());
}
m_blinkPeriod = msec;
diff --git a/src/gui/widgets/qmainwindow.cpp b/src/gui/widgets/qmainwindow.cpp
index 0947e1b..501e62f 100644
--- a/src/gui/widgets/qmainwindow.cpp
+++ b/src/gui/widgets/qmainwindow.cpp
@@ -119,7 +119,7 @@ void QMainWindowPrivate::init()
q->setAttribute(Qt::WA_Hover);
#ifdef QT_SOFTKEYS_ENABLED
menuBarAction = QSoftKeyManager::createAction(QSoftKeyManager::MenuSoftKey, q);
- menuBarAction->setObjectName("_q_menuSoftKeyAction");
+ menuBarAction->setObjectName(QLatin1String("_q_menuSoftKeyAction"));
#endif
}
@@ -933,7 +933,7 @@ static bool checkDockWidgetArea(Qt::DockWidgetArea area, const char *where)
}
#ifndef QT_NO_TABBAR
-/*!
+/*!
\property QMainWindow::documentMode
\brief whether the tab bar for tabbed dockwidgets is set to document mode.
\since 4.5
@@ -954,7 +954,7 @@ void QMainWindow::setDocumentMode(bool enabled)
#endif // QT_NO_TABBAR
#ifndef QT_NO_TABWIDGET
-/*!
+/*!
\property QMainWindow::tabShape
\brief the tab shape used for tabbed dock widgets.
\since 4.5
diff --git a/src/gui/widgets/qmenu_mac.mm b/src/gui/widgets/qmenu_mac.mm
index 4fc3d3d..cee38ee 100644
--- a/src/gui/widgets/qmenu_mac.mm
+++ b/src/gui/widgets/qmenu_mac.mm
@@ -1425,7 +1425,7 @@ QMenuPrivate::QMacMenuPrivate::syncAction(QMacMenuAction *action)
SetMenuItemProperty(data.submenuHandle, 0, kMenuCreatorQt, kMenuPropertyCausedQWidget, sizeof(caused), &caused);
#else
NSMenu *subMenu = static_cast<NSMenu *>(action->action->menu()->macMenu());
- if ([subMenu supermenu] != nil) {
+ if ([subMenu supermenu] && [subMenu supermenu] != [item menu]) {
// The menu is already a sub-menu of another one. Cocoa will throw an exception,
// in such cases. For the time being, a new QMenu with same set of actions is the
// only workaround.
@@ -1718,7 +1718,7 @@ QMenuBarPrivate::QMacMenuBarPrivate::syncAction(QMacMenuAction *action)
GetMenuItemProperty(action->menu, 0, kMenuCreatorQt, kMenuPropertyQWidget, sizeof(caused), 0, &caused);
SetMenuItemProperty(submenu, 0, kMenuCreatorQt, kMenuPropertyCausedQWidget, sizeof(caused), &caused);
#else
- if ([submenu supermenu] != nil)
+ if ([submenu supermenu] && [submenu supermenu] != [item menu])
return;
else
[item setSubmenu:submenu];
diff --git a/src/gui/widgets/qplaintextedit.cpp b/src/gui/widgets/qplaintextedit.cpp
index 2ed6cd7..22438bf 100644
--- a/src/gui/widgets/qplaintextedit.cpp
+++ b/src/gui/widgets/qplaintextedit.cpp
@@ -65,11 +65,6 @@
#include <limits.h>
#include <qtexttable.h>
#include <qvariant.h>
-
-#ifdef Q_WS_WIN
-#include <qstandardgestures.h>
-#endif
-
#include <qinputcontext.h>
#ifndef QT_NO_TEXTEDIT
@@ -2937,33 +2932,29 @@ QAbstractTextDocumentLayout::PaintContext QPlainTextEdit::getPaintContext() cons
(\a available is true) or unavailable (\a available is false).
*/
-#ifdef Q_WS_WIN
-
-void QPlainTextEditPrivate::_q_gestureTriggered()
-{
- Q_Q(QPlainTextEdit);
- QPanGesture *g = qobject_cast<QPanGesture*>(q->sender());
- if (!g)
- return;
- QScrollBar *hBar = q->horizontalScrollBar();
- QScrollBar *vBar = q->verticalScrollBar();
- if (g->state() == Qt::GestureStarted)
- originalOffsetY = vBar->value();
- QSizeF totalOffset = g->totalOffset();
- if (!totalOffset.isNull()) {
- if (QApplication::isRightToLeft())
- totalOffset.rwidth() *= -1;
- // QPlainTextEdit scrolls by lines only in vertical direction
- QFontMetrics fm(q->document()->defaultFont());
- int lineHeight = fm.height();
- int newX = hBar->value() - g->lastOffset().width();
- int newY = originalOffsetY - totalOffset.height()/lineHeight;
- hbar->setValue(newX);
- vbar->setValue(newY);
- }
-}
-
-#endif
+//void QPlainTextEditPrivate::_q_gestureTriggered()
+//{
+// Q_Q(QPlainTextEdit);
+// QPanGesture *g = qobject_cast<QPanGesture*>(q->sender());
+// if (!g)
+// return;
+// QScrollBar *hBar = q->horizontalScrollBar();
+// QScrollBar *vBar = q->verticalScrollBar();
+// if (g->state() == Qt::GestureStarted)
+// originalOffsetY = vBar->value();
+// QSizeF totalOffset = g->totalOffset();
+// if (!totalOffset.isNull()) {
+// if (QApplication::isRightToLeft())
+// totalOffset.rwidth() *= -1;
+// // QPlainTextEdit scrolls by lines only in vertical direction
+// QFontMetrics fm(q->document()->defaultFont());
+// int lineHeight = fm.height();
+// int newX = hBar->value() - g->lastOffset().width();
+// int newY = originalOffsetY - totalOffset.height()/lineHeight;
+// hbar->setValue(newX);
+// vbar->setValue(newY);
+// }
+//}
QT_END_NAMESPACE
diff --git a/src/gui/widgets/qplaintextedit.h b/src/gui/widgets/qplaintextedit.h
index 1d6881b..60aed1d 100644
--- a/src/gui/widgets/qplaintextedit.h
+++ b/src/gui/widgets/qplaintextedit.h
@@ -270,10 +270,6 @@ private:
Q_PRIVATE_SLOT(d_func(), void _q_verticalScrollbarActionTriggered(int))
Q_PRIVATE_SLOT(d_func(), void _q_cursorPositionChanged())
-#ifdef Q_WS_WIN
- Q_PRIVATE_SLOT(d_func(), void _q_gestureTriggered())
-#endif
-
friend class QPlainTextEditControl;
};
diff --git a/src/gui/widgets/qplaintextedit_p.h b/src/gui/widgets/qplaintextedit_p.h
index 5fe6f4d..7adf403 100644
--- a/src/gui/widgets/qplaintextedit_p.h
+++ b/src/gui/widgets/qplaintextedit_p.h
@@ -72,7 +72,6 @@ class QMimeData;
class QPlainTextEdit;
class ExtraArea;
-class QPanGesture;
class QPlainTextEditControl : public QTextControl
{
@@ -179,10 +178,6 @@ public:
void _q_modificationChanged(bool);
int originalOffsetY;
-
-#ifdef Q_WS_WIN
- void _q_gestureTriggered();
-#endif
};
QT_END_NAMESPACE