summaryrefslogtreecommitdiffstats
path: root/src/gui/kernel
diff options
context:
space:
mode:
authorBradley T. Hughes <bradley.hughes@nokia.com>2009-08-11 07:39:26 (GMT)
committerJason Barron <jbarron@trolltech.com>2009-09-23 13:10:40 (GMT)
commit48d0f84958fdc2dcffab75f33842a9dbc3d4d7b1 (patch)
tree86bff59c6dcc57dc0ca29ffd0effaa6de4fb55ae /src/gui/kernel
parent5e11ae8dc8594f648105f8a62baf1b82c909fd2a (diff)
downloadQt-48d0f84958fdc2dcffab75f33842a9dbc3d4d7b1.zip
Qt-48d0f84958fdc2dcffab75f33842a9dbc3d4d7b1.tar.gz
Qt-48d0f84958fdc2dcffab75f33842a9dbc3d4d7b1.tar.bz2
Implement advanced pointer handling on S60
Since we only get one pointer event at a time, we need to keep a list of all known touch points in QApplicationPrivate (otherwise the QTouchEvent won't contain enough points). The QApplication machinery can handle having inactive touch-points in the list, so at the moment we don't clear the list. We treat PointerNumber zero as the primary touch point, and only send regular mouse events for that pointer, never for the others. Reviewed-by: Jason Barron
Diffstat (limited to 'src/gui/kernel')
-rw-r--r--src/gui/kernel/qapplication_p.h5
-rw-r--r--src/gui/kernel/qapplication_s60.cpp76
-rw-r--r--src/gui/kernel/qt_s60_p.h1
3 files changed, 80 insertions, 2 deletions
diff --git a/src/gui/kernel/qapplication_p.h b/src/gui/kernel/qapplication_p.h
index 707caaa..aec21fd 100644
--- a/src/gui/kernel/qapplication_p.h
+++ b/src/gui/kernel/qapplication_p.h
@@ -576,6 +576,11 @@ public:
void _q_readRX71MultiTouchEvents();
#endif
+#if defined(Q_WS_S60)
+ int maxTouchPressure;
+ QList<QTouchEvent::TouchPoint> appAllTouchPoints;
+#endif
+
private:
#ifdef Q_WS_QWS
QMap<const QScreen*, QRect> maxWindowRects;
diff --git a/src/gui/kernel/qapplication_s60.cpp b/src/gui/kernel/qapplication_s60.cpp
index a5d07fd..58aca83 100644
--- a/src/gui/kernel/qapplication_s60.cpp
+++ b/src/gui/kernel/qapplication_s60.cpp
@@ -368,8 +368,77 @@ void QSymbianControl::HandleLongTapEventL( const TPoint& aPenEventLocation, cons
m_previousEventLongTap = true;
}
+void QSymbianControl::translateAdvancedPointerEvent(const TAdvancedPointerEvent *event)
+{
+ QApplicationPrivate *d = QApplicationPrivate::instance();
+
+ QRect screenGeometry = qApp->desktop()->screenGeometry(qwidget);
+
+ while (d->appAllTouchPoints.count() <= event->PointerNumber())
+ d->appAllTouchPoints.append(QTouchEvent::TouchPoint(d->appAllTouchPoints.count()));
+
+ Qt::TouchPointStates allStates = 0;
+ for (int i = 0; i < d->appAllTouchPoints.count(); ++i) {
+ QTouchEvent::TouchPoint &touchPoint = d->appAllTouchPoints[i];
+
+ if (touchPoint.id() == event->PointerNumber()) {
+ Qt::TouchPointStates state;
+ switch (event->iType) {
+ case TPointerEvent::EButton1Down:
+ case TPointerEvent::EEnterHighPressure:
+ state = Qt::TouchPointPressed;
+ break;
+ case TPointerEvent::EButton1Up:
+ case TPointerEvent::EExitCloseProximity:
+ state = Qt::TouchPointReleased;
+ break;
+ case TPointerEvent::EDrag:
+ state = Qt::TouchPointMoved;
+ break;
+ default:
+ // how likely is this to happen?
+ state = Qt::TouchPointStationary;
+ break;
+ }
+ if (event->PointerNumber() == 0)
+ state |= Qt::TouchPointPrimary;
+ touchPoint.setState(state);
+
+ QPointF screenPos = QPointF(event->iPosition.iX, event->iPosition.iY);
+ touchPoint.setScreenPos(screenPos);
+ touchPoint.setNormalizedPos(QPointF(screenPos.x() / screenGeometry.width(),
+ screenPos.y() / screenGeometry.height()));
+
+ touchPoint.setPressure(event->Pressure() / qreal(d->maxTouchPressure));
+ } else if (touchPoint.state() != Qt::TouchPointReleased) {
+ // all other active touch points should be marked as stationary
+ touchPoint.setState(Qt::TouchPointStationary);
+ }
+
+ allStates |= touchPoint.state();
+ }
+
+ if ((allStates & Qt::TouchPointStateMask) == Qt::TouchPointReleased) {
+ // all touch points released
+ d->appAllTouchPoints.clear();
+ }
+
+ QApplicationPrivate::translateRawTouchEvent(qwidget,
+ QTouchEvent::TouchScreen,
+ d->appAllTouchPoints);
+}
+
void QSymbianControl::HandlePointerEventL(const TPointerEvent& pEvent)
{
+ if (pEvent.IsAdvancedPointerEvent()) {
+ const TAdvancedPointerEvent *advancedPointerEvent = pEvent.AdvancedPointerEvent();
+ translateAdvancedPointerEvent(advancedPointerEvent);
+ if (advancedPointerEvent->PointerNumber() != 0) {
+ // only send mouse events for the first touch point
+ return;
+ }
+ }
+
m_longTapDetector->PointerEventL(pEvent);
QT_TRYCATCH_LEAVING(HandlePointerEvent(pEvent));
}
@@ -1441,9 +1510,12 @@ TUint QApplicationPrivate::resolveS60ScanCode(TInt scanCode, TUint keysym)
}
}
-
void QApplicationPrivate::initializeMultitouch_sys()
-{ }
+{
+ if (HAL::Get(HALData::EPointer3DMaxPressure, maxTouchPressure) != KErrNone)
+ maxTouchPressure = KMaxTInt;
+}
+
void QApplicationPrivate::cleanupMultitouch_sys()
{ }
diff --git a/src/gui/kernel/qt_s60_p.h b/src/gui/kernel/qt_s60_p.h
index aa39f9d..9939f2c 100644
--- a/src/gui/kernel/qt_s60_p.h
+++ b/src/gui/kernel/qt_s60_p.h
@@ -167,6 +167,7 @@ private:
TKeyResponse sendKeyEvent(QWidget *widget, QKeyEvent *keyEvent);
bool sendMouseEvent(QWidget *widget, QMouseEvent *mEvent);
void HandleLongTapEventL( const TPoint& aPenEventLocation, const TPoint& aPenEventScreenLocation );
+ void translateAdvancedPointerEvent(const TAdvancedPointerEvent *event);
private:
QWidget *qwidget;