xcb XInput: use categorized logging for devices and events

[ChangeLog][Platform Specific Changes][X11 / XCB] environment variables
QT_XCB_DEBUG_XINPUT and QT_XCB_DEBUG_XINPUT_DEVICES are deprecated and
replaced with logging categories qt.qpa.events.input and
qt.qpa.devices respectively

Change-Id: I287a56de5cb9ece2ac14df6510b9aa52c864c99b
Reviewed-by: Allan Sandfeld Jensen <allan.jensen@digia.com>
This commit is contained in:
Shawn Rutledge 2014-08-18 10:07:35 +02:00
parent 6efa8cd70a
commit 59ba84d31c
3 changed files with 60 additions and 56 deletions

View File

@ -92,6 +92,9 @@
QT_BEGIN_NAMESPACE
Q_LOGGING_CATEGORY(lcQpaXInput, "qt.qpa.events.input")
Q_LOGGING_CATEGORY(lcQpaXInputDevices, "qt.qpa.devices")
#ifdef XCB_USE_XLIB
static const char * const xcbConnectionErrors[] = {
"No error", /* Error 0 */
@ -324,8 +327,6 @@ QXcbConnection::QXcbConnection(QXcbNativeInterface *nativeInterface, bool canGra
, has_input_shape(false)
, has_touch_without_mouse_emulation(false)
, has_xkb(false)
, debug_xinput_devices(false)
, debug_xinput(false)
, m_buttons(0)
, m_focusWindow(0)
, m_systemTrayTracker(0)
@ -798,8 +799,7 @@ void QXcbConnection::handleButtonPress(xcb_generic_event_t *ev)
// the rest we need to manage ourselves
m_buttons = (m_buttons & ~0x7) | translateMouseButtons(event->state);
m_buttons |= translateMouseButton(event->detail);
if (Q_UNLIKELY(debug_xinput))
qDebug("xcb: pressed mouse button %d, button state %X", event->detail, static_cast<unsigned int>(m_buttons));
qCDebug(lcQpaXInput, "xcb: pressed mouse button %d, button state %X", event->detail, static_cast<unsigned int>(m_buttons));
}
void QXcbConnection::handleButtonRelease(xcb_generic_event_t *ev)
@ -810,8 +810,7 @@ void QXcbConnection::handleButtonRelease(xcb_generic_event_t *ev)
// the rest we need to manage ourselves
m_buttons = (m_buttons & ~0x7) | translateMouseButtons(event->state);
m_buttons &= ~translateMouseButton(event->detail);
if (Q_UNLIKELY(debug_xinput))
qDebug("xcb: released mouse button %d, button state %X", event->detail, static_cast<unsigned int>(m_buttons));
qCDebug(lcQpaXInput, "xcb: released mouse button %d, button state %X", event->detail, static_cast<unsigned int>(m_buttons));
}
#ifndef QT_NO_XKB
@ -864,7 +863,7 @@ void QXcbConnection::handleXcbEvent(xcb_generic_event_t *event)
handleButtonRelease(event);
HANDLE_PLATFORM_WINDOW_EVENT(xcb_button_release_event_t, event, handleButtonReleaseEvent);
case XCB_MOTION_NOTIFY:
if (Q_UNLIKELY(debug_xinput)) {
if (Q_UNLIKELY(lcQpaXInput().isDebugEnabled())) {
xcb_motion_notify_event_t *mev = (xcb_motion_notify_event_t *)event;
qDebug("xcb: moved mouse to %4d, %4d; button state %X", mev->event_x, mev->event_y, static_cast<unsigned int>(m_buttons));
}

View File

@ -52,6 +52,7 @@
#include <QVector>
#include <QVarLengthArray>
#include <qpa/qwindowsysteminterface.h>
#include <QtCore/QLoggingCategory>
// This is needed to make Qt compile together with XKB. xkb.h is using a variable
// which is called 'explicit', this is a reserved keyword in c++
@ -81,6 +82,9 @@ struct xcb_randr_get_output_info_reply_t;
QT_BEGIN_NAMESPACE
Q_DECLARE_LOGGING_CATEGORY(lcQpaXInput)
Q_DECLARE_LOGGING_CATEGORY(lcQpaXInputDevices)
class QXcbScreen;
class QXcbWindow;
class QXcbDrag;
@ -613,8 +617,6 @@ private:
bool has_input_shape;
bool has_touch_without_mouse_emulation;
bool has_xkb;
bool debug_xinput_devices;
bool debug_xinput;
Qt::MouseButtons m_buttons;

View File

@ -71,8 +71,11 @@ struct XInput2DeviceData {
void QXcbConnection::initializeXInput2()
{
debug_xinput = qEnvironmentVariableIsSet("QT_XCB_DEBUG_XINPUT");
debug_xinput_devices = qEnvironmentVariableIsSet("QT_XCB_DEBUG_XINPUT_DEVICES");
// TODO Qt 6 (or perhaps earlier): remove these redundant env variables
if (qEnvironmentVariableIsSet("QT_XCB_DEBUG_XINPUT"))
const_cast<QLoggingCategory&>(lcQpaXInput()).setEnabled(QtDebugMsg, true);
if (qEnvironmentVariableIsSet("QT_XCB_DEBUG_XINPUT_DEVICES"))
const_cast<QLoggingCategory&>(lcQpaXInputDevices()).setEnabled(QtDebugMsg, true);
Display *xDisplay = static_cast<Display *>(m_xlib_display);
if (XQueryExtension(xDisplay, "XInputExtension", &m_xiOpCode, &m_xiEventBase, &m_xiErrorBase)) {
int xiMajor = 2;
@ -87,11 +90,10 @@ void QXcbConnection::initializeXInput2()
} else
m_xi2Enabled = true;
if (m_xi2Enabled) {
if (Q_UNLIKELY(debug_xinput_devices))
#ifdef XCB_USE_XINPUT22
qDebug("XInput version %d.%d is available and Qt supports 2.2 or greater", xiMajor, m_xi2Minor);
qCDebug(lcQpaXInputDevices, "XInput version %d.%d is available and Qt supports 2.2 or greater", xiMajor, m_xi2Minor);
#else
qDebug("XInput version %d.%d is available and Qt supports 2.0", xiMajor, m_xi2Minor);
qCDebug(lcQpaXInputDevices, "XInput version %d.%d is available and Qt supports 2.0", xiMajor, m_xi2Minor);
#endif
}
@ -116,8 +118,7 @@ void QXcbConnection::xi2SetupDevices()
// Only non-master pointing devices are relevant here.
if (devices[i].use != XISlavePointer)
continue;
if (Q_UNLIKELY(debug_xinput_devices))
qDebug() << "input device "<< devices[i].name;
qCDebug(lcQpaXInputDevices) << "input device "<< devices[i].name;
#ifndef QT_NO_TABLETEVENT
TabletData tabletData;
#endif
@ -127,8 +128,7 @@ void QXcbConnection::xi2SetupDevices()
case XIValuatorClass: {
XIValuatorClassInfo *vci = reinterpret_cast<XIValuatorClassInfo *>(devices[i].classes[c]);
const int valuatorAtom = qatom(vci->label);
if (Q_UNLIKELY(debug_xinput_devices))
qDebug() << " has valuator" << atomName(vci->label) << "recognized?" << (valuatorAtom < QXcbAtom::NAtoms);
qCDebug(lcQpaXInputDevices) << " has valuator" << atomName(vci->label) << "recognized?" << (valuatorAtom < QXcbAtom::NAtoms);
#ifndef QT_NO_TABLETEVENT
if (valuatorAtom < QXcbAtom::NAtoms) {
TabletData::ValuatorClassInfo info;
@ -173,10 +173,18 @@ void QXcbConnection::xi2SetupDevices()
if ((!label6 || qatom(label6) == QXcbAtom::ButtonHorizWheelLeft) && (!label7 || qatom(label7) == QXcbAtom::ButtonHorizWheelRight))
scrollingDevice.legacyOrientations |= Qt::Horizontal;
}
qCDebug(lcQpaXInputDevices, " has %d buttons", bci->num_buttons);
break;
}
#endif
case XIKeyClass:
qCDebug(lcQpaXInputDevices) << " it's a keyboard";
break;
case XITouchClass:
// will be handled in deviceForId()
break;
default:
qCDebug(lcQpaXInputDevices) << " has class" << devices[i].classes[c]->type;
break;
}
}
@ -192,8 +200,7 @@ void QXcbConnection::xi2SetupDevices()
tabletData.pointerType = QTabletEvent::Eraser;
m_tabletData.append(tabletData);
isTablet = true;
if (Q_UNLIKELY(debug_xinput_devices))
qDebug() << " it's a tablet with pointer type" << tabletData.pointerType;
qCDebug(lcQpaXInputDevices) << " it's a tablet with pointer type" << tabletData.pointerType;
}
#endif // QT_NO_TABLETEVENT
@ -203,24 +210,21 @@ void QXcbConnection::xi2SetupDevices()
// Only use legacy wheel button events when we don't have real scroll valuators.
scrollingDevice.legacyOrientations &= ~scrollingDevice.orientations;
m_scrollingDevices.insert(scrollingDevice.deviceId, scrollingDevice);
if (Q_UNLIKELY(debug_xinput_devices))
qDebug() << " it's a scrolling device";
qCDebug(lcQpaXInputDevices) << " it's a scrolling device";
}
#endif
if (!isTablet) {
if (!isTablet && lcQpaXInputDevices().isDebugEnabled()) {
XInput2DeviceData *dev = deviceForId(devices[i].deviceid);
if (Q_UNLIKELY(debug_xinput_devices)) {
if (dev && dev->qtTouchDevice->type() == QTouchDevice::TouchScreen)
qDebug(" it's a touchscreen with type %d capabilities 0x%X max touch points %d",
dev->qtTouchDevice->type(), (unsigned int)dev->qtTouchDevice->capabilities(),
dev->qtTouchDevice->maximumTouchPoints());
else if (dev && dev->qtTouchDevice->type() == QTouchDevice::TouchPad)
qDebug(" it's a touchpad with type %d capabilities 0x%X max touch points %d size %f x %f",
dev->qtTouchDevice->type(), (unsigned int)dev->qtTouchDevice->capabilities(),
dev->qtTouchDevice->maximumTouchPoints(),
dev->size.width(), dev->size.height());
}
if (dev && dev->qtTouchDevice->type() == QTouchDevice::TouchScreen)
qCDebug(lcQpaXInputDevices, " it's a touchscreen with type %d capabilities 0x%X max touch points %d",
dev->qtTouchDevice->type(), (unsigned int)dev->qtTouchDevice->capabilities(),
dev->qtTouchDevice->maximumTouchPoints());
else if (dev && dev->qtTouchDevice->type() == QTouchDevice::TouchPad)
qCDebug(lcQpaXInputDevices, " it's a touchpad with type %d capabilities 0x%X max touch points %d size %f x %f",
dev->qtTouchDevice->type(), (unsigned int)dev->qtTouchDevice->capabilities(),
dev->qtTouchDevice->maximumTouchPoints(),
dev->size.width(), dev->size.height());
}
}
XIFreeDeviceInfo(devices);
@ -342,8 +346,7 @@ XInput2DeviceData *QXcbConnection::deviceForId(int id)
case XITouchClass: {
XITouchClassInfo *tci = reinterpret_cast<XITouchClassInfo *>(classinfo);
maxTouchPoints = tci->num_touches;
if (Q_UNLIKELY(debug_xinput_devices))
qDebug(" has touch class with mode %d", tci->mode);
qCDebug(lcQpaXInputDevices, " has touch class with mode %d", tci->mode);
switch (tci->mode) {
case XIDependentTouch:
type = QTouchDevice::TouchPad;
@ -372,6 +375,8 @@ XInput2DeviceData *QXcbConnection::deviceForId(int id)
}
break;
}
default:
break;
}
}
if (type < 0 && caps && hasRelativeCoords) {
@ -444,11 +449,11 @@ void QXcbConnection::xi2HandleEvent(xcb_ge_event_t *event)
#ifdef XCB_USE_XINPUT22
if (xiEvent->evtype == XI_TouchBegin || xiEvent->evtype == XI_TouchUpdate || xiEvent->evtype == XI_TouchEnd) {
xXIDeviceEvent* xiDeviceEvent = reinterpret_cast<xXIDeviceEvent *>(event);
if (Q_UNLIKELY(debug_xinput))
qDebug("XI2 touch event type %d seq %d detail %d pos %6.1f, %6.1f root pos %6.1f, %6.1f",
event->event_type, xiEvent->sequenceNumber, xiDeviceEvent->detail,
fixed1616ToReal(xiDeviceEvent->event_x), fixed1616ToReal(xiDeviceEvent->event_y),
fixed1616ToReal(xiDeviceEvent->root_x), fixed1616ToReal(xiDeviceEvent->root_y) );
if (Q_UNLIKELY(lcQpaXInput().isDebugEnabled()))
qCDebug(lcQpaXInput, "XI2 touch event type %d seq %d detail %d pos %6.1f, %6.1f root pos %6.1f, %6.1f",
event->event_type, xiEvent->sequenceNumber, xiDeviceEvent->detail,
fixed1616ToReal(xiDeviceEvent->event_x), fixed1616ToReal(xiDeviceEvent->event_y),
fixed1616ToReal(xiDeviceEvent->root_x), fixed1616ToReal(xiDeviceEvent->root_y) );
if (QXcbWindow *platformWindow = platformWindowFromId(xiDeviceEvent->event)) {
XInput2DeviceData *dev = deviceForId(xiDeviceEvent->sourceid);
@ -474,9 +479,9 @@ void QXcbConnection::xi2HandleEvent(xcb_ge_event_t *event)
double value;
if (!xi2GetValuatorValueIfSet(xiDeviceEvent, n, &value))
continue;
if (Q_UNLIKELY(debug_xinput))
qDebug(" valuator %20s value %lf from range %lf -> %lf",
atomName(vci->label).constData(), value, vci->min, vci->max );
if (Q_UNLIKELY(lcQpaXInput().isDebugEnabled()))
qCDebug(lcQpaXInput, " valuator %20s value %lf from range %lf -> %lf",
atomName(vci->label).constData(), value, vci->min, vci->max );
if (vci->label == atom(QXcbAtom::RelX)) {
nx = valuatorNormalized(value, vci);
} else if (vci->label == atom(QXcbAtom::RelY)) {
@ -552,9 +557,9 @@ void QXcbConnection::xi2HandleEvent(xcb_ge_event_t *event)
touchPoint.area = QRectF(x - w/2, y - h/2, w, h);
touchPoint.normalPosition = QPointF(nx, ny);
if (Q_UNLIKELY(debug_xinput))
qDebug() << " touchpoint " << touchPoint.id << " state " << touchPoint.state << " pos norm " << touchPoint.normalPosition <<
" area " << touchPoint.area << " pressure " << touchPoint.pressure;
if (Q_UNLIKELY(lcQpaXInput().isDebugEnabled()))
qCDebug(lcQpaXInput) << " touchpoint " << touchPoint.id << " state " << touchPoint.state << " pos norm " << touchPoint.normalPosition <<
" area " << touchPoint.area << " pressure " << touchPoint.pressure;
QWindowSystemInterface::handleTouchEvent(platformWindow->window(), xiEvent->time, dev->qtTouchDevice, m_touchPoints.values());
if (touchPoint.state == Qt::TouchPointReleased)
// If a touchpoint was released, we can forget it, because the ID won't be reused.
@ -805,13 +810,11 @@ bool QXcbConnection::xi2HandleTabletEvent(void *event, TabletData *tabletData)
tabletData->pointerType,
tabletData->serialId);
}
if (Q_UNLIKELY(debug_xinput)) {
// TODO maybe have a hash of tabletData->deviceId to device data so we can
// look up the tablet name here, and distinguish multiple tablets
qDebug("XI2 proximity change on tablet %d (USB %x): last tool: %x id %x current tool: %x id %x TabletDevice %d",
ev->deviceid, ptr[_WACSER_USB_ID], ptr[_WACSER_LAST_TOOL_SERIAL], ptr[_WACSER_LAST_TOOL_ID],
ptr[_WACSER_TOOL_SERIAL], ptr[_WACSER_TOOL_ID], tabletData->tool);
}
// TODO maybe have a hash of tabletData->deviceId to device data so we can
// look up the tablet name here, and distinguish multiple tablets
qCDebug(lcQpaXInput, "XI2 proximity change on tablet %d (USB %x): last tool: %x id %x current tool: %x id %x TabletDevice %d",
ev->deviceid, ptr[_WACSER_USB_ID], ptr[_WACSER_LAST_TOOL_SERIAL], ptr[_WACSER_LAST_TOOL_ID],
ptr[_WACSER_TOOL_SERIAL], ptr[_WACSER_TOOL_ID], tabletData->tool);
}
XFree(data);
}
@ -872,8 +875,8 @@ void QXcbConnection::xi2ReportTabletEvent(TabletData &tabletData, void *event)
}
}
if (Q_UNLIKELY(debug_xinput))
qDebug("XI2 event on tablet %d with tool %d type %d seq %d detail %d pos %6.1f, %6.1f root pos %6.1f, %6.1f buttons 0x%x pressure %4.2lf tilt %d, %d rotation %6.2lf",
if (Q_UNLIKELY(lcQpaXInput().isDebugEnabled()))
qCDebug(lcQpaXInput, "XI2 event on tablet %d with tool %d type %d seq %d detail %d pos %6.1f, %6.1f root pos %6.1f, %6.1f buttons 0x%x pressure %4.2lf tilt %d, %d rotation %6.2lf",
ev->deviceid, tabletData.tool, ev->evtype, ev->sequenceNumber, ev->detail,
fixed1616ToReal(ev->event_x), fixed1616ToReal(ev->event_y),
fixed1616ToReal(ev->root_x), fixed1616ToReal(ev->root_y),