void *QXcbGlxWindow::createVisual() { QXcbScreen *scr = xcbScreen(); if (!scr) return Q_NULLPTR; return qglx_findVisualInfo(DISPLAY_FROM_XCB(scr), scr->screenNumber(), &m_format); }
QXcbWindowSurface::QXcbWindowSurface(QWidget *widget, bool setDefaultSurface) : QWindowSurface(widget, setDefaultSurface) , m_image(0) , m_syncingResize(false) { QXcbScreen *screen = static_cast<QXcbScreen *>(QPlatformScreen::platformScreenForWidget(widget)); setConnection(screen->connection()); }
QXcbBackingStore::QXcbBackingStore(QWindow *window) : QPlatformBackingStore(window) , m_image(0) , m_syncingResize(false) { QXcbScreen *screen = static_cast<QXcbScreen *>(window->screen()->handle()); setConnection(screen->connection()); }
void *QXcbNativeInterface::eglDisplayForWidget(QWidget *widget) { #if defined(XCB_USE_DRI2) || defined(XCB_USE_EGL) QXcbScreen *screen = qPlatformScreenForWidget(widget); return screen->connection()->egl_display(); #else Q_UNUSED(widget) return 0; #endif }
void *QXcbNativeInterface::displayForWidget(QWidget *widget) { #if defined(XCB_USE_XLIB) QXcbScreen *screen = qPlatformScreenForWidget(widget); return screen->connection()->xlib_display(); #else Q_UNUSED(widget); return 0; #endif }
QPlatformOpenGLContext *QXcbEglIntegration::createPlatformOpenGLContext(QOpenGLContext *context) const { QXcbScreen *screen = static_cast<QXcbScreen *>(context->screen()->handle()); QXcbEglContext *platformContext = new QXcbEglContext(screen->surfaceFormatFor(context->format()), context->shareHandle(), eglDisplay(), context->nativeHandle()); context->setNativeHandle(platformContext->nativeHandle()); return platformContext; }
QPlatformOpenGLContext *QXcbIntegration::createPlatformOpenGLContext(QOpenGLContext *context) const { QXcbScreen *screen = static_cast<QXcbScreen *>(context->screen()->handle()); QXcbGlIntegration *glIntegration = screen->connection()->glIntegration(); if (!glIntegration) { qWarning("QXcbIntegration: Cannot create platform OpenGL context, neither GLX nor EGL are enabled"); return Q_NULLPTR; } return glIntegration->createPlatformOpenGLContext(context); }
QPlatformOffscreenSurface *QXcbIntegration::createPlatformOffscreenSurface(QOffscreenSurface *surface) const { QXcbScreen *screen = static_cast<QXcbScreen *>(surface->screen()->handle()); QXcbGlIntegration *glIntegration = screen->connection()->glIntegration(); if (!glIntegration) { qWarning("QXcbIntegration: Cannot create platform offscreen surface, neither GLX nor EGL are enabled"); return Q_NULLPTR; } return glIntegration->createPlatformOffscreenSurface(surface); }
void *QXcbNativeInterface::graphicsDeviceForWidget(QWidget *widget) { #if defined(XCB_USE_DRI2) QXcbScreen *screen = qPlatformScreenForWidget(widget); QByteArray deviceName = screen->connection()->dri2DeviceName(); return deviceName.data(); #else Q_UNUSED(widget); return 0; #endif }
QPlatformOffscreenSurface *QXcbIntegration::createPlatformOffscreenSurface(QOffscreenSurface *surface) const { #if defined(XCB_USE_GLX) return new QGLXPbuffer(surface); #elif defined(XCB_USE_EGL) QXcbScreen *screen = static_cast<QXcbScreen *>(surface->screen()->handle()); return new QEGLPbuffer(screen->connection()->egl_display(), surface->requestedFormat(), surface); #else Q_UNUSED(surface); qWarning("QXcbIntegration: Cannot create platform offscreen surface, neither GLX nor EGL are enabled"); return 0; #endif }
QPlatformOpenGLContext *QXcbIntegration::createPlatformOpenGLContext(QOpenGLContext *context) const { QXcbScreen *screen = static_cast<QXcbScreen *>(context->screen()->handle()); #if defined(XCB_USE_GLX) return new QGLXContext(screen, context->format(), context->shareHandle()); #elif defined(XCB_USE_EGL) return new QEGLXcbPlatformContext(context->format(), context->shareHandle(), screen->connection()->egl_display(), screen->connection()); #else Q_UNUSED(screen); qWarning("QXcbIntegration: Cannot create platform OpenGL context, neither GLX nor EGL are enabled"); return 0; #endif }
void QIrrlichtWidget::setAutoRepeatKeys(bool mode) { qDebug() << "QIrrlichtWidget::setAutoRepeatKeys"; XKeyboardControl control; control.auto_repeat_mode = (mode ? 1 : 0); // Set mode to 1 for // autorepeat, 0 to disable control.key = -1; // We want to change the behaviour for all keys QList<QScreen*> screens = QGuiApplication::screens(); QXcbScreen *xcbscreen = static_cast<QXcbScreen*>(screens.at(0)->handle()); Display *display = static_cast<Display*>(xcbscreen->connection()->xlib_display()); XChangeKeyboardControl(display, KBAutoRepeatMode, &control); }
QPlatformWindow *QXcbIntegration::createPlatformWindow(QWindow *window) const { QXcbScreen *screen = static_cast<QXcbScreen *>(window->screen()->handle()); QXcbGlIntegration *glIntegration = screen->connection()->glIntegration(); if (window->type() != Qt::Desktop) { if (glIntegration) { QXcbWindow *xcbWindow = glIntegration->createWindow(window); xcbWindow->create(); return xcbWindow; } } Q_ASSERT(window->type() == Qt::Desktop || !window->supportsOpenGL() || (!glIntegration && window->surfaceType() == QSurface::RasterGLSurface)); // for VNC QXcbWindow *xcbWindow = new QXcbWindow(window); xcbWindow->create(); return xcbWindow; }
void QXcbConnection::xi2HandleEvent(xcb_ge_event_t *event) { if (xi2PrepareXIGenericDeviceEvent(event, m_xiOpCode)) { xXIGenericDeviceEvent *xiEvent = reinterpret_cast<xXIGenericDeviceEvent *>(event); #ifndef QT_NO_TABLETEVENT for (int i = 0; i < m_tabletData.count(); ++i) { if (m_tabletData.at(i).deviceId == xiEvent->deviceid) { if (xi2HandleTabletEvent(xiEvent, &m_tabletData[i])) return; } } #endif // QT_NO_TABLETEVENT #ifdef XCB_USE_XINPUT22 if (xiEvent->evtype == XI_TouchBegin || xiEvent->evtype == XI_TouchUpdate || xiEvent->evtype == XI_TouchEnd) { xXIDeviceEvent* xiDeviceEvent = reinterpret_cast<xXIDeviceEvent *>(event); #ifdef XI2_TOUCH_DEBUG qDebug("XI2 event type %d seq %d detail %d pos 0x%X,0x%X %f,%f root pos %f,%f", event->event_type, xiEvent->sequenceNumber, xiDeviceEvent->detail, xiDeviceEvent->event_x, xiDeviceEvent->event_y, fixed1616ToReal(xiDeviceEvent->event_x), fixed1616ToReal(xiDeviceEvent->event_y), fixed1616ToReal(xiDeviceEvent->root_x), fixed1616ToReal(xiDeviceEvent->root_y) ); #endif if (QXcbWindow *platformWindow = platformWindowFromId(xiDeviceEvent->event)) { XInput2DeviceData *dev = deviceForId(xiEvent->deviceid); if (xiEvent->evtype == XI_TouchBegin) { QWindowSystemInterface::TouchPoint tp; tp.id = xiDeviceEvent->detail % INT_MAX; tp.state = Qt::TouchPointPressed; tp.pressure = -1.0; m_touchPoints[tp.id] = tp; } QWindowSystemInterface::TouchPoint &touchPoint = m_touchPoints[xiDeviceEvent->detail]; qreal x = fixed1616ToReal(xiDeviceEvent->root_x); qreal y = fixed1616ToReal(xiDeviceEvent->root_y); qreal nx = -1.0, ny = -1.0, w = 0.0, h = 0.0; QXcbScreen* screen = m_screens.at(0); for (int i = 0; i < dev->xiDeviceInfo->num_classes; ++i) { XIAnyClassInfo *classinfo = dev->xiDeviceInfo->classes[i]; if (classinfo->type == XIValuatorClass) { XIValuatorClassInfo *vci = reinterpret_cast<XIValuatorClassInfo *>(classinfo); int n = vci->number; double value; if (!xi2GetValuatorValueIfSet(xiDeviceEvent, n, &value)) continue; #ifdef XI2_TOUCH_DEBUG qDebug(" valuator class label %d value %lf from range %lf -> %lf name %s", vci->label, value, vci->min, vci->max, XGetAtomName(static_cast<Display *>(m_xlib_display), vci->label) ); #endif if (vci->label == atom(QXcbAtom::AbsMTPositionX)) { nx = valuatorNormalized(value, vci); } else if (vci->label == atom(QXcbAtom::AbsMTPositionY)) { ny = valuatorNormalized(value, vci); } else if (vci->label == atom(QXcbAtom::AbsMTTouchMajor)) { // Convert the value within its range as a fraction of a finger's max (contact patch) // width in mm, and from there to pixels depending on screen resolution w = valuatorNormalized(value, vci) * FINGER_MAX_WIDTH_MM * screen->geometry().width() / screen->physicalSize().width(); } else if (vci->label == atom(QXcbAtom::AbsMTTouchMinor)) { h = valuatorNormalized(value, vci) * FINGER_MAX_WIDTH_MM * screen->geometry().height() / screen->physicalSize().height(); } else if (vci->label == atom(QXcbAtom::AbsMTPressure) || vci->label == atom(QXcbAtom::AbsPressure)) { touchPoint.pressure = valuatorNormalized(value, vci); } } } // If any value was not updated, use the last-known value. if (nx == -1.0) { x = touchPoint.area.center().x(); nx = x / screen->geometry().width(); } if (ny == -1.0) { y = touchPoint.area.center().y(); ny = y / screen->geometry().height(); } if (xiEvent->evtype != XI_TouchEnd) { if (w == 0.0) w = touchPoint.area.width(); if (h == 0.0) h = touchPoint.area.height(); } switch (xiEvent->evtype) { case XI_TouchUpdate: if (touchPoint.area.center() != QPoint(x, y)) touchPoint.state = Qt::TouchPointMoved; else touchPoint.state = Qt::TouchPointStationary; break; case XI_TouchEnd: touchPoint.state = Qt::TouchPointReleased; } touchPoint.area = QRectF(x - w/2, y - h/2, w, h); touchPoint.normalPosition = QPointF(nx, ny); #ifdef XI2_TOUCH_DEBUG qDebug() << " tp " << touchPoint.id << " state " << touchPoint.state << " pos norm " << touchPoint.normalPosition << " area " << touchPoint.area << " pressure " << touchPoint.pressure; #endif QWindowSystemInterface::handleTouchEvent(platformWindow->window(), xiEvent->time, dev->qtTouchDevice, m_touchPoints.values()); // If a touchpoint was released, we can forget it, because the ID won't be reused. if (touchPoint.state == Qt::TouchPointReleased) m_touchPoints.remove(touchPoint.id); } } #endif } }
void *QXcbNativeInterface::screenForWidget(QWidget *widget) { QXcbScreen *screen = qPlatformScreenForWidget(widget); return screen->screen(); }
void *QXcbNativeInterface::connectionForWidget(QWidget *widget) { QXcbScreen *screen = qPlatformScreenForWidget(widget); return screen->xcb_connection(); }
void *QXcbNativeInterface::screenForWindow(QWindow *window) { QXcbScreen *screen = qPlatformScreenForWindow(window); return screen->screen(); }
void *QXcbNativeInterface::connectionForWindow(QWindow *window) { QXcbScreen *screen = qPlatformScreenForWindow(window); return screen->xcb_connection(); }
QPlatformOffscreenSurface *QXcbEglIntegration::createPlatformOffscreenSurface(QOffscreenSurface *surface) const { QXcbScreen *screen = static_cast<QXcbScreen *>(surface->screen()->handle()); return new QEGLPbuffer(eglDisplay(), screen->surfaceFormatFor(surface->requestedFormat()), surface); }
QPixmap QXcbScreen::grabWindow(WId window, int x, int y, int width, int height) const { if (width == 0 || height == 0) return QPixmap(); // TODO: handle multiple screens QXcbScreen *screen = const_cast<QXcbScreen *>(this); xcb_window_t root = screen->root(); if (window == 0) window = root; xcb_get_geometry_cookie_t geometry_cookie = xcb_get_geometry_unchecked(xcb_connection(), window); xcb_get_geometry_reply_t *reply = xcb_get_geometry_reply(xcb_connection(), geometry_cookie, NULL); if (!reply) { return QPixmap(); } if (width < 0) width = reply->width - x; if (height < 0) height = reply->height - y; geometry_cookie = xcb_get_geometry_unchecked(xcb_connection(), root); xcb_get_geometry_reply_t *root_reply = xcb_get_geometry_reply(xcb_connection(), geometry_cookie, NULL); if (!root_reply) { free(reply); return QPixmap(); } if (reply->depth == root_reply->depth) { // if the depth of the specified window and the root window are the // same, grab pixels from the root window (so that we get the any // overlapping windows and window manager frames) // map x and y to the root window xcb_translate_coordinates_cookie_t translate_cookie = xcb_translate_coordinates_unchecked(xcb_connection(), window, root, x, y); xcb_translate_coordinates_reply_t *translate_reply = xcb_translate_coordinates_reply(xcb_connection(), translate_cookie, NULL); if (!translate_reply) { free(reply); free(root_reply); return QPixmap(); } x = translate_reply->dst_x; y = translate_reply->dst_y; window = root; free(translate_reply); free(reply); reply = root_reply; } else { free(root_reply); root_reply = 0; } xcb_get_window_attributes_reply_t *attributes_reply = xcb_get_window_attributes_reply(xcb_connection(), xcb_get_window_attributes_unchecked(xcb_connection(), window), NULL); if (!attributes_reply) { free(reply); return QPixmap(); } const xcb_visualtype_t *visual = screen->visualForId(attributes_reply->visual); free(attributes_reply); xcb_pixmap_t pixmap = xcb_generate_id(xcb_connection()); xcb_create_pixmap(xcb_connection(), reply->depth, pixmap, window, width, height); uint32_t gc_value_mask = XCB_GC_SUBWINDOW_MODE; uint32_t gc_value_list[] = { XCB_SUBWINDOW_MODE_INCLUDE_INFERIORS }; xcb_gcontext_t gc = xcb_generate_id(xcb_connection()); xcb_create_gc(xcb_connection(), gc, pixmap, gc_value_mask, gc_value_list); xcb_copy_area(xcb_connection(), window, pixmap, gc, x, y, 0, 0, width, height); QPixmap result = qt_xcb_pixmapFromXPixmap(connection(), pixmap, width, height, reply->depth, visual); free(reply); xcb_free_gc(xcb_connection(), gc); xcb_free_pixmap(xcb_connection(), pixmap); return result; }