summaryrefslogtreecommitdiffstats
path: root/src/gui/kernel/qevent.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'src/gui/kernel/qevent.cpp')
-rw-r--r--src/gui/kernel/qevent.cpp308
1 files changed, 262 insertions, 46 deletions
diff --git a/src/gui/kernel/qevent.cpp b/src/gui/kernel/qevent.cpp
index d6741af152..492f2a11c9 100644
--- a/src/gui/kernel/qevent.cpp
+++ b/src/gui/kernel/qevent.cpp
@@ -287,6 +287,8 @@ QMouseEvent::~QMouseEvent()
\l Qt::MouseEventNotSynthesized is returned always.
\sa Qt::MouseEventSource
+ \sa QGraphicsSceneMouseEvent::source()
+ \sa QGraphicsSceneMouseEvent::setSource()
*/
Qt::MouseEventSource QMouseEvent::source() const
{
@@ -301,6 +303,8 @@ Qt::MouseEventSource QMouseEvent::source() const
The mouse event flags provide additional information about a mouse event.
\sa Qt::MouseEventFlag
+ \sa QGraphicsSceneMouseEvent::flags()
+ \sa QGraphicsSceneMouseEvent::setFlags()
*/
Qt::MouseEventFlags QMouseEvent::flags() const
{
@@ -1185,7 +1189,7 @@ Qt::FocusReason QFocusEvent::reason() const
The event contains a region() that needs to be updated, and a
rect() that is the bounding rectangle of that region. Both are
- provided because many widgets can't make much use of region(),
+ provided because many widgets cannot make much use of region(),
and rect() can be much faster than region().boundingRect().
\section1 Automatic Clipping
@@ -1977,40 +1981,63 @@ QVariant QInputMethodQueryEvent::value(Qt::InputMethodQuery query) const
\ingroup events
- Tablet Events are generated from a Wacom tablet. Most of the time you will
- want to deal with events from the tablet as if they were events from a
- mouse; for example, you would retrieve the cursor position with x(), y(),
- pos(), globalX(), globalY(), and globalPos(). In some situations you may
- wish to retrieve the extra information provided by the tablet device
- driver; for example, you might want to do subpixeling with higher
- resolution coordinates or you may want to adjust color brightness based on
- pressure. QTabletEvent allows you to read the pressure(), the xTilt(), and
- yTilt(), as well as the type of device being used with device() (see
- \l{TabletDevice}). It can also give you the minimum and maximum values for
- each device's pressure and high resolution coordinates.
-
- A tablet event contains a special accept flag that indicates whether the
- receiver wants the event. You should call QTabletEvent::accept() if you
- handle the tablet event; otherwise it will be sent to the parent widget.
- The exception are TabletEnterProximity and TabletLeaveProximity events,
- these are only sent to QApplication and don't check whether or not they are
- accepted.
-
- The QWidget::setEnabled() function can be used to enable or
- disable mouse and keyboard events for a widget.
-
- The event handler QWidget::tabletEvent() receives all three types of
- tablet events. Qt will first send a tabletEvent then, if it is not
- accepted, it will send a mouse event. This allows applications that
- don't utilize tablets to use a tablet like a mouse, while also
- enabling those who want to use both tablets and mouses differently.
+ \e{Tablet events} are generated from tablet peripherals such as Wacom
+ tablets and various other brands, and electromagnetic stylus devices
+ included with some types of tablet computers. (It is not the same as
+ \l QTouchEvent which a touchscreen generates, even when a passive stylus is
+ used on a touchscreen.)
+
+ Tablet events are similar to mouse events; for example, the \l x(), \l y(),
+ \l pos(), \l globalX(), \l globalY(), and \l globalPos() accessors provide
+ the cursor position, and you can see which \l buttons() are pressed
+ (pressing the stylus tip against the tablet surface is equivalent to a left
+ mouse button). But tablet events also pass through some extra information
+ that the tablet device driver provides; for example, you might want to do
+ subpixel rendering with higher resolution coordinates (\l hiResGlobalX()
+ and \l hiResGlobalY()), adjust color brightness based on the \l pressure()
+ of the tool against the tablet surface, use different brushes depending on
+ the type of tool in use (\l device()), modulate the brush shape in some way
+ according to the X-axis and Y-axis tilt of the tool with respect to the
+ tablet surface (\l xTilt() and \l yTilt()), and use a virtual eraser
+ instead of a brush if the user switches to the other end of a double-ended
+ stylus (\l pointerType()).
+
+ Every event contains an accept flag that indicates whether the receiver
+ wants the event. You should call QTabletEvent::accept() if you handle the
+ tablet event; otherwise it will be sent to the parent widget. The exception
+ are TabletEnterProximity and TabletLeaveProximity events: these are only
+ sent to QApplication and do not check whether or not they are accepted.
+
+ The QWidget::setEnabled() function can be used to enable or disable
+ mouse, tablet and keyboard events for a widget.
+
+ The event handler QWidget::tabletEvent() receives TabletPress,
+ TabletRelease and TabletMove events. Qt will first send a
+ tablet event, then if it is not accepted by any widget, it will send a
+ mouse event. This allows users of applications that are not designed for
+ tablets to use a tablet like a mouse. However high-resolution drawing
+ applications should handle the tablet events, because they can occur at a
+ higher frequency, which is a benefit for smooth and accurate drawing.
+ If the tablet events are rejected, the synthetic mouse events may be
+ compressed for efficiency.
+
+ New in Qt 5.4: QTabletEvent includes all information available from the
+ device, including \l QTabletEvent::buttons(). Previously it was not
+ possible to accept all tablet events and also know which stylus buttons
+ were pressed.
+
+ Note that pressing the stylus button while the stylus hovers over the
+ tablet will generate a button press on some types of tablets, while on
+ other types it will be necessary to press the stylus against the tablet
+ surface in order to register the simultaneous stylus button press.
\section1 Notes for X11 Users
- Qt uses the following hard-coded names to identify tablet
- devices from the xorg.conf file on X11 (apart from IRIX):
- 'stylus', 'pen', and 'eraser'. If the devices have other names,
- they will not be picked up Qt.
+ If the tablet is configured in xorg.conf to use the Wacom driver, there
+ will be separate XInput "devices" for the stylus, eraser, and (optionally)
+ cursor and touchpad. Qt recognizes these by their names. Otherwise, if the
+ tablet is configured to use the evdev driver, there will be only one device
+ and applications may not be able to distinguish the stylus from the eraser.
*/
/*!
@@ -2068,11 +2095,73 @@ QVariant QInputMethodQueryEvent::value(Qt::InputMethodQuery query) const
The \a tangentialPressure parameter contins the tangential pressure of an air
brush. If the device does not support tangential pressure, pass 0 here.
+ \a rotation contains the device's rotation in degrees. 4D mice and the Wacom
+ Art Pen support rotation. If the device does not support rotation, pass 0 here.
+
+ The \a button that caused the event is given as a value from the
+ \l Qt::MouseButton enum. If the event \a type is not \l TabletPress or
+ \l TabletRelease, the appropriate button for this event is \l Qt::NoButton.
+
+ \a buttons is the state of all buttons at the time of the event.
+
+ \sa pos(), globalPos(), device(), pressure(), xTilt(), yTilt(), uniqueId(), rotation(),
+ tangentialPressure(), z()
+*/
+
+QTabletEvent::QTabletEvent(Type type, const QPointF &pos, const QPointF &globalPos,
+ int device, int pointerType,
+ qreal pressure, int xTilt, int yTilt, qreal tangentialPressure,
+ qreal rotation, int z, Qt::KeyboardModifiers keyState, qint64 uniqueID,
+ Qt::MouseButton button, Qt::MouseButtons buttons)
+ : QInputEvent(type, keyState),
+ mPos(pos),
+ mGPos(globalPos),
+ mDev(device),
+ mPointerType(pointerType),
+ mXT(xTilt),
+ mYT(yTilt),
+ mZ(z),
+ mPress(pressure),
+ mTangential(tangentialPressure),
+ mRot(rotation),
+ mUnique(uniqueID),
+ mExtra(new QTabletEventPrivate(button, buttons))
+{
+}
+
+/*!
+ Construct a tablet event of the given \a type.
+
+ The \a pos parameter indicates where the event occurred in the
+ widget; \a globalPos is the corresponding position in absolute
+ coordinates.
+
+ \a pressure contains the pressure exerted on the \a device.
+
+ \a pointerType describes the type of pen that is being used.
+
+ \a xTilt and \a yTilt contain the device's degree of tilt from the
+ x and y axes respectively.
+
+ \a keyState specifies which keyboard modifiers are pressed (e.g.,
+ \uicontrol{Ctrl}).
+
+ The \a uniqueID parameter contains the unique ID for the current device.
+
+ The \a z parameter contains the coordinate of the device on the tablet, this
+ is usually given by a wheel on 4D mouse. If the device does not support a
+ Z-axis, pass zero here.
+
+ The \a tangentialPressure parameter contins the tangential pressure of an air
+ brush. If the device does not support tangential pressure, pass 0 here.
+
\a rotation contains the device's rotation in degrees. 4D mice support
rotation. If the device does not support rotation, pass 0 here.
\sa pos(), globalPos(), device(), pressure(), xTilt(), yTilt(), uniqueId(), rotation(),
tangentialPressure(), z()
+
+ \deprecated in 5.4: use the constructor with MouseButton status
*/
QTabletEvent::QTabletEvent(Type type, const QPointF &pos, const QPointF &globalPos,
@@ -2091,7 +2180,7 @@ QTabletEvent::QTabletEvent(Type type, const QPointF &pos, const QPointF &globalP
mTangential(tangentialPressure),
mRot(rotation),
mUnique(uniqueID),
- mExtra(0)
+ mExtra(new QTabletEventPrivate(Qt::NoButton, Qt::NoButton))
{
}
@@ -2103,6 +2192,34 @@ QTabletEvent::~QTabletEvent()
}
/*!
+ Returns the button that caused the event.
+
+ Note that the returned value is always Qt::NoButton for \l TabletMove,
+ \l TabletEnterProximity and \l TabletLeaveProximity events.
+
+ \sa buttons(), Qt::MouseButton
+*/
+Qt::MouseButton QTabletEvent::button() const
+{
+ return static_cast<QTabletEventPrivate *>(mExtra)->b;
+}
+
+/*!
+ Returns the button state when the event was generated. The button state is
+ a combination of buttons from the \l Qt::MouseButton enum using the OR
+ operator. For \l TabletMove events, this is all buttons that are pressed
+ down. For \l TabletPress events this includes the button that caused the
+ event. For \l TabletRelease events this excludes the button that caused the
+ event.
+
+ \sa button(), Qt::MouseButton
+*/
+Qt::MouseButtons QTabletEvent::buttons() const
+{
+ return static_cast<QTabletEventPrivate *>(mExtra)->buttonState;
+}
+
+/*!
\fn TabletDevices QTabletEvent::device() const
Returns the type of device that generated the event.
@@ -2132,7 +2249,7 @@ QTabletEvent::~QTabletEvent()
\fn qreal QTabletEvent::rotation() const
Returns the rotation of the current device in degress. This is usually
- given by a 4D Mouse. If the device doesn't support rotation this value is
+ given by a 4D Mouse. If the device does not support rotation this value is
always 0.0.
*/
@@ -3036,7 +3153,7 @@ QActionEvent::~QActionEvent()
If spontaneous() is true, the event originated outside the
application. In this case, the user hid the window using the
window manager controls, either by iconifying the window or by
- switching to another virtual desktop where the window isn't
+ switching to another virtual desktop where the window is not
visible. The window will become hidden but not withdrawn. If the
window was iconified, QWidget::isMinimized() returns \c true.
@@ -3265,6 +3382,61 @@ static inline void formatTouchEvent(QDebug d, const char *name, const QTouchEven
d << ')';
}
+static void formatUnicodeString(QDebug d, const QString &s)
+{
+ d << '"' << hex;
+ for (int i = 0; i < s.size(); ++i) {
+ if (i)
+ d << ',';
+ d << "U+" << s.at(i).unicode();
+ }
+ d << dec << '"';
+}
+
+static inline void formatInputMethodEvent(QDebug d, const QInputMethodEvent *e)
+{
+ d << "QInputMethodEvent(";
+ if (!e->preeditString().isEmpty()) {
+ d << "preedit=";
+ formatUnicodeString(d, e->preeditString());
+ }
+ if (!e->commitString().isEmpty()) {
+ d << ", commit=";
+ formatUnicodeString(d, e->commitString());
+ }
+ if (e->replacementLength()) {
+ d << ", replacementStart=" << e->replacementStart() << ", replacementLength="
+ << e->replacementLength();
+ }
+ if (const int attributeCount = e->attributes().size()) {
+ d << ", attributes= {";
+ for (int a = 0; a < attributeCount; ++a) {
+ const QInputMethodEvent::Attribute &at = e->attributes().at(a);
+ if (a)
+ d << ',';
+ d << "[type= " << at.type << ", start=" << at.start << ", length=" << at.length
+ << ", value=" << at.value << ']';
+ }
+ d << '}';
+ }
+ d << ')';
+}
+
+static inline void formatInputMethodQueryEvent(QDebug d, const QInputMethodQueryEvent *e)
+{
+ const Qt::InputMethodQueries queries = e->queries();
+ d << "QInputMethodQueryEvent(queries=" << showbase << hex << int(queries)
+ << noshowbase << dec << ", {";
+ for (unsigned mask = 1; mask <= Qt::ImTextAfterCursor; mask<<=1) {
+ if (queries & mask) {
+ const QVariant value = e->value(static_cast<Qt::InputMethodQuery>(mask));
+ if (value.isValid())
+ d << '[' << showbase << hex << mask << noshowbase << dec << '=' << value << "],";
+ }
+ }
+ d << "})";
+}
+
QDebug operator<<(QDebug dbg, const QEvent *e) {
// More useful event output could be added here
if (!e)
@@ -3302,6 +3474,8 @@ QDebug operator<<(QDebug dbg, const QEvent *e) {
<< ", " << hex << (int)me->modifiers() << dec;
if (const Qt::MouseEventSource source = me->source())
nsp << ", source = " << source;
+ if (const Qt::MouseEventFlags flags = me->flags())
+ nsp << ", flags = " << hex << int(flags) << dec;
nsp << ')';
}
return dbg.space();
@@ -3355,11 +3529,13 @@ QDebug operator<<(QDebug dbg, const QEvent *e) {
}
return dbg.space();
case QEvent::FocusIn:
- n = "FocusIn";
- break;
+ dbg.nospace() << "QFocusEvent(FocusIn, reason="
+ << static_cast<const QFocusEvent *>(e)->reason() << ')';
+ return dbg.space();
case QEvent::FocusOut:
- n = "FocusOut";
- break;
+ dbg.nospace() << "QFocusEvent(FocusOut, reason="
+ << static_cast<const QFocusEvent *>(e)->reason() << ')';
+ return dbg.space();
case QEvent::Enter:
n = "Enter";
break;
@@ -3381,12 +3557,24 @@ QDebug operator<<(QDebug dbg, const QEvent *e) {
case QEvent::Paint:
n = "Paint";
break;
- case QEvent::Move:
- n = "Move";
- break;
- case QEvent::Resize:
- n = "Resize";
- break;
+ case QEvent::Move: {
+ const QMoveEvent *me = static_cast<const QMoveEvent *>(e);
+ QDebug nospace = dbg.nospace();
+ nospace << "QMoveEvent(" << me->pos();
+ if (!me->spontaneous())
+ nospace << ", non-spontaneous";
+ nospace << ')';
+ }
+ return dbg.space();
+ case QEvent::Resize: {
+ const QResizeEvent *re = static_cast<const QResizeEvent *>(e);
+ QDebug nospace = dbg.nospace();
+ nospace << "QResizeEvent(" << re->size();
+ if (!re->spontaneous())
+ nospace << ", non-spontaneous";
+ nospace << ')';
+ }
+ return dbg.space();
case QEvent::Create:
n = "Create";
break;
@@ -3498,6 +3686,18 @@ QDebug operator<<(QDebug dbg, const QEvent *e) {
case QEvent::GraphicsSceneMove:
n = "GraphicsSceneMove";
break;
+ case QEvent::InputMethod: {
+ QDebugStateSaver saver(dbg);
+ dbg.nospace();
+ formatInputMethodEvent(dbg, static_cast<const QInputMethodEvent *>(e));
+ }
+ return dbg;
+ case QEvent::InputMethodQuery: {
+ QDebugStateSaver saver(dbg);
+ dbg.nospace();
+ formatInputMethodQueryEvent(dbg, static_cast<const QInputMethodQueryEvent *>(e));
+ }
+ return dbg;
case QEvent::CursorChange:
n = "CursorChange";
break;
@@ -3551,7 +3751,23 @@ QDebug operator<<(QDebug dbg, const QEvent *e) {
case QEvent::Gesture:
n = "Gesture";
break;
+ case QEvent::GestureOverride:
+ n = "GestureOverride";
+ break;
#endif
+ case QEvent::MetaCall:
+ n = "MetaCall";
+ break;
+ case QEvent::ApplicationStateChange:
+ dbg.nospace() << "QApplicationStateChangeEvent("
+ << static_cast<const QApplicationStateChangeEvent *>(e)->applicationState() << ')';
+ return dbg.space();
+ case QEvent::WindowTitleChange:
+ n = "WindowTitleChange";
+ break;
+ case QEvent::Expose:
+ n = "Expose";
+ break;
default:
dbg.nospace() << "QEvent(" << (const void *)e << ", type = " << e->type() << ')';
return dbg.space();
@@ -3570,7 +3786,7 @@ QDebug operator<<(QDebug dbg, const QEvent *e) {
\ingroup events
\inmodule QtGui
- Normally you don't need to use this class directly; QShortcut
+ Normally you do not need to use this class directly; QShortcut
provides a higher-level interface to handle shortcut keys.
\sa QShortcut