With the introduction of multi-touch and gesture support coming in Qt, application developers now have the possibility of introducing new types of input and interaction to their applications. We will examine the various types of devices that one can expect to encounter in the multi-touch and gesture "world". This presentation will also introduce and explain the new API, walk through some example code, and show some demos of some of the possibilities we foresee with this technology.
Presentation by Jens Bache-Wiig held during Qt Developer Days 2009.
http://qt.nokia.com/developer/learning/elearning
6. Concepts
A widget reacts to multiple touch-points
For example, to zoom/scale content...
Lorem ipsum dolor sit Lorem ipsum dolor
eamt. Dolore magna
aliquam erat volupat. Ut sit eamt. Dolore
enim ad minimum magna aliquam
veniami quis. Duis sutem
vel eum irure dolor in
erat volupat...cvc
rerit laputum
6
7. Concepts
Multiple widgets react to multiple touch-points
For example, moving several sliders at once...
7
8. Concepts
Real life is multi-touch
Do you open a bottle with one finger?
Applications could do it too...
1
2
8
13. Concepts
A way to make common multi-touch use-cases
easy to use in your application
• Standard, platform-specific touch-based gestures
• Extensible API for custom gestures
13
14. Concepts
What are standard gestures?
• Built-in multi-touch gestures that work in standard Qt
widgets
14
15. Concepts
Pan gesture
• Scrolls content
• Works in all scrollable Qt widgets
Lorem ipsum dolor sit Ut enim ad minimum
eamt. Dolore magna veniami quis. Duis sutem
aliquam erat volupat. vel eum irure dolor in
Ut enim ad minimum rerit laputum
veniami quis. Duis
sutem vel eum irure
dolor in rerit laputum
15
21. API
QEvent::TouchEnd
• Final event in sequence
• No more events without a new TouchBegin
21
22. API
TouchBegin propagation
• When ignored, propagate to widget under first touch-
point
• Widgets never receive multiple TouchBegin
• New touch-points on children are combined with first
touch-point
1 1 2
One event, one point, to grey widget One event, two points, to grey widget
22
24. API
QTouchEvent
• Event class for QWidget and QGraphicsItem
• Contains list of active touch points
• Device type – TouchScreen or TouchPad
24
25. API
QTouchEvent::TouchPoint
• Information about one touch-point
• Integer identifier
• Primary touch-point flag
• State - Pressed, Moved, Stationary, or Released
• Current, previous, starting positions
• Local, scene, screen, normalized translations
• Area, pressure (if supported by device)
25
26. API
Touch events are not sent by default
• Must be enabled first
• When enabled, TouchBegin event will be accepted
unless explicitly ignored
26
27. API
Qt::WA_AcceptsTouchEvents
• Set on QWidget to receive touch events
• To handle events, reimplement QWidget::event()
• Default implementation emulates mouse events for first
non-primary touch-point
• Set on viewport() of QAbstractScrollArea based
widgets
• To handle events, reimplement
QAbstractScrollArea::viewportEvent()
27
29. API
Gestures
• QGesture and QGestureRecognizer classes
• Widgets subscribe to gestures
• Using standard gestures
• Implementing custom gestures
29
30. API
QGesture
• Base class for more complex gestures
• Basic properties and convenience functions
• Delivered to QWidget or QGraphicsObject
• State (Started, Updated, Finished, Canceled)
QGestureEvent
• Contains a list of QGestures
• Normal event propagation rules apply
30
31. API
QGestureRecognizer
• “Just” an event filter + state machine
• Registered in QApplication
• Announces when a gesture is triggered
31
32. API
How do I use a gesture?
• Use grabGesture() to request it
• Handle the QGestureEvent and get:
QPanGesture
- Offset property
QPinchGesture
- Center-point, rotation, scale properties
32
33. API
Implementing custom gestures
• Create a state machine:
- subclass QGestureRecognizer
- implement filterEvent(), createGesture(), reset()
• Create a gesture object:
- subclass QGesture (optional)
- fill QGesture with properties
33
34. API
Gestures can be simple : Four finger tap
class FourFingerTapGesture : public QGestureRecognizer
{
virtual Result filterEvent(QGesture *, QObject *, QEvent *event)
{
if (event->type() == QEvent::TouchUpdate)
if (static_cast<QTouchEvent *>(event)->touchPoints.size() == 4)
return GestureFinished;
return Ignore;
}
};
34
35. API
Gestures can be complex
• Event filter could implement a state machine
• Continuous gesture going through Qt::GestureStated
to Qt::GestureUpdated to Qt::GestureFinished
states.
• Gesture may need to hijack events, store them, and
replay them later
35
37. API
Single gesture on parent widget with children
• Should the parent's gesture filter events for children?
GestureContext
• widget-only gesture
• widget-with-children gesture
37
38. API
Multiple gestures on a single widget
• All gestures filter incoming events in undefined order
• Ignored gestures will be propagated
• You can partially ignore a gesture:
bool gestureEvent(QGestureEvent *event) {
event->ignore(Qt::PanGesture);
event->accept(Qt::PinchGesture);
return true;
}
38
39. API
Gesture has priority over normal event
handling
• Gesture may need several events before
starting
• Normal event handling interferes with
gesture
• Events should be delayed
39