Rewrite debug output of event classes.

- Introduce functions to return class name and type name by type.
- Move QDebugStateSaver up.
- Add verbose output for DnD, tablet, native gestures,  context
  menu, enter and expose events.

Task-number: QTBUG-38858

[ChangeLog][QtGui][QEvent] The debug output for events has
been significantly improved.

Change-Id: I3f11e34c3c9d6a3c6db596be4051b801f00e6153
Reviewed-by: Shawn Rutledge <shawn.rutledge@digia.com>
This commit is contained in:
Friedemann Kleint 2014-08-01 11:03:22 +02:00
parent 61269c26f6
commit 14f9c09542

View File

@ -46,6 +46,7 @@
#include "qpa/qplatformdrag.h" #include "qpa/qplatformdrag.h"
#include "private/qevent_p.h" #include "private/qevent_p.h"
#include "qdebug.h" #include "qdebug.h"
#include "qmetaobject.h"
#include "qmimedata.h" #include "qmimedata.h"
#include "private/qdnd_p.h" #include "private/qdnd_p.h"
#include "qevent_p.h" #include "qevent_p.h"
@ -3437,346 +3438,353 @@ static inline void formatInputMethodQueryEvent(QDebug d, const QInputMethodQuery
d << "})"; d << "})";
} }
QDebug operator<<(QDebug dbg, const QEvent *e) { static const char *eventTypeName(QEvent::Type t)
// More useful event output could be added here {
if (!e) static const int enumIdx = QEvent::staticMetaObject.indexOfEnumerator("Type");
return dbg << "QEvent(this = 0x0)"; return t <= QEvent::User
const char *n = 0; ? QEvent::staticMetaObject.enumerator(enumIdx).valueToKey(t)
switch (e->type()) { : "User";
}
static const char *eventClassName(QEvent::Type t)
{
switch (t) {
case QEvent::ActionAdded:
case QEvent::ActionRemoved:
case QEvent::ActionChanged:
return "QActionEvent";
case QEvent::MouseButtonPress:
case QEvent::MouseButtonRelease:
case QEvent::MouseButtonDblClick:
case QEvent::MouseMove:
case QEvent::NonClientAreaMouseMove:
case QEvent::NonClientAreaMouseButtonPress:
case QEvent::NonClientAreaMouseButtonRelease:
case QEvent::NonClientAreaMouseButtonDblClick:
return "QMouseEvent";
case QEvent::DragEnter:
return "QDragEnterEvent";
case QEvent::DragMove:
return "QDragMoveEvent";
case QEvent::Drop:
return "QDropEvent";
case QEvent::KeyPress:
case QEvent::KeyRelease:
case QEvent::ShortcutOverride:
return "QKeyEvent";
case QEvent::FocusIn:
case QEvent::FocusOut:
case QEvent::FocusAboutToChange:
return "QFocusEvent";
case QEvent::ChildAdded:
case QEvent::ChildPolished:
case QEvent::ChildRemoved:
return "QChildEvent";
case QEvent::Paint:
return "QPaintEvent";
case QEvent::Move:
return "QMoveEvent";
case QEvent::Resize:
return "QResizeEvent";
case QEvent::Show:
return "QShowEvent";
case QEvent::Hide:
return "QHideEvent";
case QEvent::Enter:
return "QEnterEvent";
case QEvent::Close:
return "QCloseEvent";
case QEvent::FileOpen:
return "QFileOpenEvent";
case QEvent::NativeGesture:
return "QNativeGestureEvent";
case QEvent::Gesture:
case QEvent::GestureOverride:
return "QGestureEvent";
case QEvent::HoverEnter:
case QEvent::HoverLeave:
case QEvent::HoverMove:
return "QHoverEvent";
case QEvent::TabletEnterProximity:
case QEvent::TabletLeaveProximity:
case QEvent::TabletPress:
case QEvent::TabletMove:
case QEvent::TabletRelease:
return "QTabletEvent";
case QEvent::StatusTip:
return "QStatusTipEvent";
case QEvent::ToolTip:
return "QHelpEvent";
case QEvent::WindowStateChange:
return "QWindowStateChangeEvent";
case QEvent::Wheel:
return "QWheelEvent";
case QEvent::TouchBegin:
case QEvent::TouchUpdate:
case QEvent::TouchEnd:
return "QTouchEvent";
case QEvent::Shortcut:
return "QShortcutEvent";
case QEvent::InputMethod:
return "QInputMethodEvent";
case QEvent::InputMethodQuery:
return "QInputMethodQueryEvent";
case QEvent::OrientationChange:
return "QScreenOrientationChangeEvent";
case QEvent::ScrollPrepare:
return "QScrollPrepareEvent";
case QEvent::Scroll:
return "QScrollEvent";
case QEvent::GraphicsSceneMouseMove:
case QEvent::GraphicsSceneMousePress:
case QEvent::GraphicsSceneMouseRelease:
case QEvent::GraphicsSceneMouseDoubleClick:
return "QGraphicsSceneMouseEvent";
case QEvent::GraphicsSceneContextMenu:
case QEvent::GraphicsSceneHoverEnter:
case QEvent::GraphicsSceneHoverMove:
case QEvent::GraphicsSceneHoverLeave:
case QEvent::GraphicsSceneHelp:
case QEvent::GraphicsSceneDragEnter:
case QEvent::GraphicsSceneDragMove:
case QEvent::GraphicsSceneDragLeave:
case QEvent::GraphicsSceneDrop:
case QEvent::GraphicsSceneWheel:
return "QGraphicsSceneEvent";
case QEvent::Timer: case QEvent::Timer:
n = "Timer"; return "QTimerEvent";
default:
break;
}
return "QEvent";
}
namespace {
// Make protected QObject::staticQtMetaObject accessible for formatting enums.
class DebugHelper : public QObject {
public:
static const char *mouseButtonToString(Qt::MouseButton button)
{
static const int enumIdx = QObject::staticQtMetaObject.indexOfEnumerator("MouseButtons");
return QObject::staticQtMetaObject.enumerator(enumIdx).valueToKey(button);
}
static QByteArray mouseButtonsToString(Qt::MouseButtons buttons)
{
QByteArray result;
for (int i = 0; (uint)(1 << i) <= Qt::MaxMouseButton; ++i) {
const Qt::MouseButton button = static_cast<Qt::MouseButton>(1 << i);
if (buttons.testFlag(button)) {
if (!result.isEmpty())
result.append('|');
result.append(mouseButtonToString(button));
}
}
if (result.isEmpty())
result.append("NoButton");
return result;
}
static const char *mouseEventSourceToString(Qt::MouseEventSource source)
{
static const int enumIdx = QObject::staticQtMetaObject.indexOfEnumerator("MouseEventSource");
return QObject::staticQtMetaObject.enumerator(enumIdx).valueToKey(source);
}
static const char *focusReasonToString(Qt::FocusReason reason)
{
static const int enumIdx = QObject::staticQtMetaObject.indexOfEnumerator("FocusReason");
return QObject::staticQtMetaObject.enumerator(enumIdx).valueToKey(reason);
}
};
} // namespace
# ifndef QT_NO_DRAGANDDROP
static void formatDropEvent(QDebug d, const QDropEvent *e)
{
const QEvent::Type type = e->type();
d << eventClassName(type) << "(dropAction=" << e->dropAction() << ", proposedAction="
<< e->proposedAction() << ", possibleActions=" << e->possibleActions()
<< ", posF=" << e->posF();
if (type == QEvent::DragMove || type == QEvent::DragEnter)
d << ", answerRect=" << static_cast<const QDragMoveEvent *>(e)->answerRect();
d << ", formats=" << e->mimeData()->formats();
if (const Qt::KeyboardModifiers mods = e->keyboardModifiers())
d << ", keyboardModifiers=" << mods;
d << ", " << DebugHelper::mouseButtonsToString(e->mouseButtons()).constData();
}
# endif // !QT_NO_DRAGANDDROP
# ifndef QT_NO_TABLETEVENT
static void formatTabletEvent(QDebug d, const QTabletEvent *e)
{
const QEvent::Type type = e->type();
d << eventClassName(type) << '(' << eventTypeName(type) << ", pos=" << e->posF()
<< ", pointerType=" << e->pointerType()
<< ", pressure=" << e->pressure() << ", rotation=" << e->rotation()
<< ", " << DebugHelper::mouseButtonsToString(e->buttons()).constData();
}
# endif // !QT_NO_TABLETEVENT
QDebug operator<<(QDebug dbg, const QEvent *e)
{
QDebugStateSaver saver(dbg);
dbg.nospace();
if (!e) {
dbg << "QEvent(this = 0x0)";
return dbg;
}
// More useful event output could be added here
const QEvent::Type type = e->type();
switch (type) {
case QEvent::Expose:
dbg << "QExposeEvent(" << static_cast<const QExposeEvent *>(e)->region() << ')';
break; break;
case QEvent::MouseButtonPress: case QEvent::MouseButtonPress:
case QEvent::MouseMove: case QEvent::MouseMove:
case QEvent::MouseButtonRelease: case QEvent::MouseButtonRelease:
case QEvent::MouseButtonDblClick: case QEvent::MouseButtonDblClick:
case QEvent::NonClientAreaMouseButtonPress:
case QEvent::NonClientAreaMouseMove:
case QEvent::NonClientAreaMouseButtonRelease:
case QEvent::NonClientAreaMouseButtonDblClick:
{ {
const QMouseEvent *me = static_cast<const QMouseEvent*>(e); const QMouseEvent *me = static_cast<const QMouseEvent*>(e);
switch(me->type()) { const Qt::MouseButton button = me->button();
case QEvent::MouseButtonPress: const Qt::MouseButtons buttons = me->buttons();
n = "MouseButtonPress"; dbg << "QMouseEvent(" << eventTypeName(type);
break; if (type != QEvent::MouseMove && type != QEvent::NonClientAreaMouseMove)
case QEvent::MouseMove: dbg << ", " << DebugHelper::mouseButtonToString(button);
n = "MouseMove"; if (buttons && button != buttons)
break; dbg << ", buttons=" << DebugHelper::mouseButtonsToString(buttons).constData();
case QEvent::MouseButtonRelease: if (const int mods = int(me->modifiers()))
n = "MouseButtonRelease"; dbg << ", modifiers=0x" << hex << mods << dec;
break; dbg << ", localPos=" << me->localPos() << ", screenPos=" << me->screenPos();
case QEvent::MouseButtonDblClick: if (me->source())
default: dbg << ", " << DebugHelper::mouseEventSourceToString(me->source());
n = "MouseButtonDblClick";
break;
}
QDebug nsp = dbg.nospace();
nsp << "QMouseEvent(" << n
<< ", " << me->button()
<< ", " << hex << (int)me->buttons()
<< ", " << hex << (int)me->modifiers() << dec;
if (const Qt::MouseEventSource source = me->source())
nsp << ", source = " << source;
if (const Qt::MouseEventFlags flags = me->flags()) if (const Qt::MouseEventFlags flags = me->flags())
nsp << ", flags = " << hex << int(flags) << dec; dbg << ", flags = " << hex << int(flags) << dec;
nsp << ')'; dbg << ')';
} }
return dbg.space();
#ifndef QT_NO_TOOLTIP
case QEvent::ToolTip:
n = "ToolTip";
break;
#endif
case QEvent::WindowActivate:
n = "WindowActivate";
break;
case QEvent::WindowDeactivate:
n = "WindowDeactivate";
break;
case QEvent::ActivationChange:
n = "ActivationChange";
break; break;
# ifndef QT_NO_WHEELEVENT # ifndef QT_NO_WHEELEVENT
case QEvent::Wheel: case QEvent::Wheel: {
dbg.nospace() << "QWheelEvent(" const QWheelEvent *we = static_cast<const QWheelEvent *>(e);
<< static_cast<const QWheelEvent *>(e)->pixelDelta() dbg << "QWheelEvent(" << "pixelDelta=" << we->pixelDelta() << ", angleDelta=" << we->angleDelta() << ')';
<< static_cast<const QWheelEvent *>(e)->angleDelta() }
<< ')'; break;
return dbg.space(); # endif // !QT_NO_WHEELEVENT
#endif
case QEvent::KeyPress: case QEvent::KeyPress:
case QEvent::KeyRelease: case QEvent::KeyRelease:
case QEvent::ShortcutOverride: case QEvent::ShortcutOverride:
{ {
const QKeyEvent *ke = static_cast<const QKeyEvent *>(e); const QKeyEvent *ke = static_cast<const QKeyEvent *>(e);
switch(ke->type()) { dbg << "QKeyEvent(" << eventTypeName(type)
case QEvent::ShortcutOverride: << ", key=0x" << hex << ke->key() << dec;
n = "ShortcutOverride"; if (const int mods = ke->modifiers())
break; dbg << ", modifiers=0x" << hex << mods << dec;
case QEvent::KeyRelease: if (!ke->text().isEmpty())
n = "KeyRelease"; dbg << ", text=" << ke->text();
break; if (ke->isAutoRepeat())
case QEvent::KeyPress: dbg << ", autorepeat, count=" << ke->count();
default: dbg << ')';
n = "KeyPress";
break;
} }
dbg.nospace() << "QKeyEvent(" << n break;
<< ", " << hex << ke->key() case QEvent::Shortcut: {
<< ", " << hex << (int)ke->modifiers() const QShortcutEvent *se = static_cast<const QShortcutEvent *>(e);
<< ", \"" << ke->text() dbg << "QShortcutEvent(" << se->key().toString() << ", id=" << se->shortcutId();
<< "\", " << ke->isAutoRepeat() if (se->isAmbiguous())
<< ", " << ke->count() dbg << ", ambiguous";
<< ')'; dbg << ')';
} }
return dbg.space(); break;
case QEvent::FocusAboutToChange:
case QEvent::FocusIn: case QEvent::FocusIn:
dbg.nospace() << "QFocusEvent(FocusIn, reason="
<< static_cast<const QFocusEvent *>(e)->reason() << ')';
return dbg.space();
case QEvent::FocusOut: case QEvent::FocusOut:
dbg.nospace() << "QFocusEvent(FocusOut, reason=" dbg << "QFocusEvent(" << eventTypeName(type) << ", "
<< static_cast<const QFocusEvent *>(e)->reason() << ')'; << DebugHelper::focusReasonToString(static_cast<const QFocusEvent *>(e)->reason())
return dbg.space(); << ')';
case QEvent::Enter:
n = "Enter";
break;
case QEvent::Leave:
n = "Leave";
break;
case QEvent::PaletteChange:
n = "PaletteChange";
break;
case QEvent::PolishRequest:
n = "PolishRequest";
break;
case QEvent::Polish:
n = "Polish";
break;
case QEvent::UpdateRequest:
n = "UpdateRequest";
break;
case QEvent::Paint:
n = "Paint";
break; break;
case QEvent::Move: { case QEvent::Move: {
const QMoveEvent *me = static_cast<const QMoveEvent *>(e); const QMoveEvent *me = static_cast<const QMoveEvent *>(e);
QDebug nospace = dbg.nospace(); dbg << "QMoveEvent(" << me->pos();
nospace << "QMoveEvent(" << me->pos();
if (!me->spontaneous()) if (!me->spontaneous())
nospace << ", non-spontaneous"; dbg << ", non-spontaneous";
nospace << ')'; dbg << ')';
} }
return dbg.space(); break;
case QEvent::Resize: { case QEvent::Resize: {
const QResizeEvent *re = static_cast<const QResizeEvent *>(e); const QResizeEvent *re = static_cast<const QResizeEvent *>(e);
QDebug nospace = dbg.nospace(); dbg << "QResizeEvent(" << re->size();
nospace << "QResizeEvent(" << re->size();
if (!re->spontaneous()) if (!re->spontaneous())
nospace << ", non-spontaneous"; dbg << ", non-spontaneous";
nospace << ')'; dbg << ')';
} }
return dbg.space();
case QEvent::Create:
n = "Create";
break;
case QEvent::Destroy:
n = "Destroy";
break;
case QEvent::Close:
n = "Close";
break;
case QEvent::Quit:
n = "Quit";
break;
case QEvent::FileOpen:
n = "FileOpen";
break;
case QEvent::Show:
n = "Show";
break;
case QEvent::ShowToParent:
n = "ShowToParent";
break;
case QEvent::Hide:
n = "Hide";
break;
case QEvent::HideToParent:
n = "HideToParent";
break;
case QEvent::None:
n = "None";
break;
case QEvent::ParentChange:
n = "ParentChange";
break;
case QEvent::ParentAboutToChange:
n = "ParentAboutToChange";
break;
case QEvent::HoverEnter:
n = "HoverEnter";
break;
case QEvent::HoverMove:
n = "HoverMove";
break;
case QEvent::HoverLeave:
n = "HoverLeave";
break;
case QEvent::ZOrderChange:
n = "ZOrderChange";
break;
case QEvent::StyleChange:
n = "StyleChange";
break; break;
# ifndef QT_NO_DRAGANDDROP
case QEvent::DragEnter: case QEvent::DragEnter:
n = "DragEnter";
break;
case QEvent::DragMove: case QEvent::DragMove:
n = "DragMove";
break;
case QEvent::DragLeave:
n = "DragLeave";
break;
case QEvent::Drop: case QEvent::Drop:
n = "Drop"; formatDropEvent(dbg, static_cast<const QDropEvent *>(e));
break; break;
case QEvent::GraphicsSceneMouseMove: # endif // !QT_NO_DRAGANDDROP
n = "GraphicsSceneMouseMove"; case QEvent::InputMethod:
break;
case QEvent::GraphicsSceneMousePress:
n = "GraphicsSceneMousePress";
break;
case QEvent::GraphicsSceneMouseRelease:
n = "GraphicsSceneMouseRelease";
break;
case QEvent::GraphicsSceneMouseDoubleClick:
n = "GraphicsSceneMouseDoubleClick";
break;
case QEvent::GraphicsSceneContextMenu:
n = "GraphicsSceneContextMenu";
break;
case QEvent::GraphicsSceneHoverEnter:
n = "GraphicsSceneHoverEnter";
break;
case QEvent::GraphicsSceneHoverMove:
n = "GraphicsSceneHoverMove";
break;
case QEvent::GraphicsSceneHoverLeave:
n = "GraphicsSceneHoverLeave";
break;
case QEvent::GraphicsSceneHelp:
n = "GraphicsSceneHelp";
break;
case QEvent::GraphicsSceneDragEnter:
n = "GraphicsSceneDragEnter";
break;
case QEvent::GraphicsSceneDragMove:
n = "GraphicsSceneDragMove";
break;
case QEvent::GraphicsSceneDragLeave:
n = "GraphicsSceneDragLeave";
break;
case QEvent::GraphicsSceneDrop:
n = "GraphicsSceneDrop";
break;
case QEvent::GraphicsSceneWheel:
n = "GraphicsSceneWheel";
break;
case QEvent::GraphicsSceneResize:
n = "GraphicsSceneResize";
break;
case QEvent::GraphicsSceneMove:
n = "GraphicsSceneMove";
break;
case QEvent::InputMethod: {
QDebugStateSaver saver(dbg);
dbg.nospace();
formatInputMethodEvent(dbg, static_cast<const QInputMethodEvent *>(e)); formatInputMethodEvent(dbg, static_cast<const QInputMethodEvent *>(e));
} break;
return dbg; case QEvent::InputMethodQuery:
case QEvent::InputMethodQuery: {
QDebugStateSaver saver(dbg);
dbg.nospace();
formatInputMethodQueryEvent(dbg, static_cast<const QInputMethodQueryEvent *>(e)); formatInputMethodQueryEvent(dbg, static_cast<const QInputMethodQueryEvent *>(e));
}
return dbg;
case QEvent::CursorChange:
n = "CursorChange";
break;
case QEvent::ToolTipChange:
n = "ToolTipChange";
break;
case QEvent::StatusTip:
n = "StatusTip";
break;
case QEvent::WhatsThis:
n = "WhatsThis";
break;
case QEvent::FontChange:
n = "FontChange";
break;
case QEvent::Style:
n = "Style";
break;
case QEvent::KeyboardLayoutChange:
n = "KeyboardLayoutChange";
break;
case QEvent::DynamicPropertyChange:
n = "DynamicPropertyChange";
break;
case QEvent::GrabMouse:
n = "GrabMouse";
break;
case QEvent::UngrabMouse:
n = "UngrabMouse";
break;
case QEvent::GrabKeyboard:
n = "GrabKeyboard";
break;
case QEvent::UngrabKeyboard:
n = "UngrabKeyboard";
break; break;
case QEvent::TouchBegin: case QEvent::TouchBegin:
n = "TouchBegin";
case QEvent::TouchUpdate: case QEvent::TouchUpdate:
n = n ? n : "TouchUpdate";
case QEvent::TouchEnd: case QEvent::TouchEnd:
n = n ? n : "TouchEnd"; formatTouchEvent(dbg, eventTypeName(type), *static_cast<const QTouchEvent*>(e));
formatTouchEvent(dbg.nospace(), n, *static_cast<const QTouchEvent*>(e)); break;
return dbg.space(); case QEvent::ChildAdded:
case QEvent::ChildAdded: n = n ? n : "ChildAdded"; case QEvent::ChildPolished:
case QEvent::ChildPolished: n = n ? n : "ChildPolished"; case QEvent::ChildRemoved:
case QEvent::ChildRemoved: n = n ? n : "ChildRemoved"; dbg << "QChildEvent(" << eventTypeName(type) << ", " << (static_cast<const QChildEvent*>(e))->child() << ')';
dbg.nospace() << "QChildEvent(" << n << ", " << (static_cast<const QChildEvent*>(e))->child(); break;
return dbg.space();
# ifndef QT_NO_GESTURES # ifndef QT_NO_GESTURES
case QEvent::Gesture: case QEvent::NativeGesture: {
n = "Gesture"; const QNativeGestureEvent *ne = static_cast<const QNativeGestureEvent *>(e);
break; dbg << "QNativeGestureEvent(localPos=" << ne->localPos() << ", value=" << ne->value() << ')';
case QEvent::GestureOverride: }
n = "GestureOverride";
break;
#endif
case QEvent::MetaCall:
n = "MetaCall";
break; break;
# endif // !QT_NO_GESTURES
case QEvent::ApplicationStateChange: case QEvent::ApplicationStateChange:
dbg.nospace() << "QApplicationStateChangeEvent(" dbg << "QApplicationStateChangeEvent("
<< static_cast<const QApplicationStateChangeEvent *>(e)->applicationState() << ')'; << static_cast<const QApplicationStateChangeEvent *>(e)->applicationState() << ')';
return dbg.space();
case QEvent::WindowTitleChange:
n = "WindowTitleChange";
break; break;
case QEvent::Expose: case QEvent::ContextMenu:
n = "Expose"; dbg << "QContextMenuEvent(" << static_cast<const QContextMenuEvent *>(e)->pos() << ')';
break;
# ifndef QT_NO_TABLETEVENT
case QEvent::TabletEnterProximity:
case QEvent::TabletLeaveProximity:
case QEvent::TabletPress:
case QEvent::TabletMove:
case QEvent::TabletRelease:
formatTabletEvent(dbg, static_cast<const QTabletEvent *>(e));
break;
# endif // !QT_NO_TABLETEVENT
case QEvent::Enter:
dbg << "QEnterEvent(" << static_cast<const QEnterEvent *>(e)->pos() << ')';
break;
case QEvent::Timer:
dbg << "QTimerEvent(id=" << static_cast<const QTimerEvent *>(e)->timerId() << ')';
break; break;
default: default:
dbg.nospace() << "QEvent(" << (const void *)e << ", type = " << e->type() << ')'; dbg << eventClassName(type) << '(' << eventTypeName(type) << ", "
return dbg.space(); << (const void *)e << ", type = " << e->type() << ')';
break;
} }
return dbg;
dbg.nospace() << 'Q' << n << "Event(" << (const void *)e << ')';
return dbg.space();
} }
#endif #endif // !QT_NO_DEBUG_STREAM
/*! /*!
\class QShortcutEvent \class QShortcutEvent