uint32_t createSurface(const IntSize& size) { XVisualInfo* visualInfo = glXGetVisualFromFBConfig(m_display, m_fbConfig); if (!visualInfo) return 0; Colormap cmap = XCreateColormap(m_display, m_offScreenWindow.getXWindow(), visualInfo->visual, AllocNone); XSetWindowAttributes a; a.background_pixel = WhitePixel(m_display, 0); a.border_pixel = BlackPixel(m_display, 0); a.colormap = cmap; m_surface = XCreateWindow(m_display, m_offScreenWindow.getXWindow(), 0, 0, size.width(), size.height(), 0, visualInfo->depth, InputOutput, visualInfo->visual, CWBackPixel | CWBorderPixel | CWColormap, &a); XSetWindowBackgroundPixmap(m_display, m_surface, 0); XCompositeRedirectWindow(m_display, m_surface, CompositeRedirectManual); m_glxSurface = glXCreateWindow(m_display, m_fbConfig, m_surface, 0); XFree(visualInfo); // Make sure the XRender Extension is available. int eventBasep, errorBasep; if (!XRenderQueryExtension(m_display, &eventBasep, &errorBasep)) return 0; XMapWindow(m_display, m_surface); return m_surface; }
void QWaylandXCompositeGLXWindow::createSurface() { QSize size(geometry().size()); if (size.isEmpty()) { //QGLWidget wants a context for a window without geometry size = QSize(1,1); } if (!m_glxIntegration->xDisplay()) { qWarning("XCompositeGLXWindow: X display still null?!"); return; } XVisualInfo *visualInfo = glXGetVisualFromFBConfig(m_glxIntegration->xDisplay(), m_config); Colormap cmap = XCreateColormap(m_glxIntegration->xDisplay(), m_glxIntegration->rootWindow(), visualInfo->visual, AllocNone); XSetWindowAttributes a; a.background_pixel = WhitePixel(m_glxIntegration->xDisplay(), m_glxIntegration->screen()); a.border_pixel = BlackPixel(m_glxIntegration->xDisplay(), m_glxIntegration->screen()); a.colormap = cmap; m_xWindow = XCreateWindow(m_glxIntegration->xDisplay(), m_glxIntegration->rootWindow(),0, 0, size.width(), size.height(), 0, visualInfo->depth, InputOutput, visualInfo->visual, CWBackPixel|CWBorderPixel|CWColormap, &a); XCompositeRedirectWindow(m_glxIntegration->xDisplay(), m_xWindow, CompositeRedirectManual); XMapWindow(m_glxIntegration->xDisplay(), m_xWindow); XSync(m_glxIntegration->xDisplay(), False); mBuffer = new QWaylandXCompositeBuffer(m_glxIntegration->waylandXComposite(), (uint32_t)m_xWindow, size); }
static void hd_panel_window_dialog_realize (GtkWidget *widget) { GTK_WIDGET_CLASS (hd_panel_window_dialog_parent_class)->realize (widget); XCompositeRedirectWindow (GDK_DISPLAY (), GDK_WINDOW_XID (widget->window), CompositeRedirectAutomatic); }
void compzillaWindow::RedirectWindow () { if (mIsRedirected) return; XCompositeRedirectWindow (mDisplay, mWindow, CompositeRedirectManual); mIsRedirected = true; }
RedirectedXCompositeWindow::RedirectedXCompositeWindow(const IntSize& size, GLContextNeeded needsContext) : m_size(size) , m_window(0) , m_parentWindow(0) , m_pixmap(0) , m_needsContext(needsContext) , m_surface(0) , m_needsNewPixmapAfterResize(false) , m_damage(0) , m_damageNotifyCallback(0) , m_damageNotifyData(0) { Display* display = GDK_DISPLAY_XDISPLAY(gdk_display_get_default()); Screen* screen = DefaultScreenOfDisplay(display); // This is based on code from Chromium: src/content/common/gpu/image_transport_surface_linux.cc XSetWindowAttributes windowAttributes; windowAttributes.override_redirect = True; m_parentWindow = XCreateWindow(display, RootWindowOfScreen(screen), WidthOfScreen(screen) + 1, 0, 1, 1, 0, CopyFromParent, InputOutput, CopyFromParent, CWOverrideRedirect, &windowAttributes); XMapWindow(display, m_parentWindow); windowAttributes.event_mask = StructureNotifyMask; windowAttributes.override_redirect = False; m_window = XCreateWindow(display, m_parentWindow, 0, 0, size.width(), size.height(), 0, CopyFromParent, InputOutput, CopyFromParent, CWEventMask, &windowAttributes); XMapWindow(display, m_window); if (getWindowHashMap().isEmpty()) gdk_window_add_filter(0, reinterpret_cast<GdkFilterFunc>(filterXDamageEvent), 0); getWindowHashMap().add(m_window, this); while (1) { XEvent event; XWindowEvent(display, m_window, StructureNotifyMask, &event); if (event.type == MapNotify && event.xmap.window == m_window) break; } XSelectInput(display, m_window, NoEventMask); XCompositeRedirectWindow(display, m_window, CompositeRedirectManual); m_damage = XDamageCreate(display, m_window, XDamageReportNonEmpty); }
PyObject * X11Display_PyObject__composite_redirect(X11Display_PyObject * self, PyObject * args) { #ifdef HAVE_X11_COMPOSITE int wid = 0; if (!PyArg_ParseTuple(args, "i", &wid)) return NULL; XCompositeRedirectWindow( self->display, wid, CompositeRedirectManual); return Py_INCREF(Py_None), Py_None; #else PyErr_Format(PyExc_SystemError, "Composite extention not supported"); return NULL; #endif }
uint32_t createSurface(const IntSize& size) { m_surface = adoptPtr(new QWindow(m_offScreenWindow.get(m_display))); m_surface->setSurfaceType(QSurface::OpenGLSurface); m_surface->setGeometry(0, 0, size.width(), size.height()); m_surface->create(); XCompositeRedirectWindow(m_display, m_surface->handle()->winId(), CompositeRedirectManual); // Make sure the XRender Extension is available. int eventBasep, errorBasep; if (!XRenderQueryExtension(m_display, &eventBasep, &errorBasep)) return 0; m_surface->show(); return m_surface->handle()->winId(); }
void X11Helper::createOffScreenWindow(uint32_t* handleId, const XVisualInfo& visInfo, const IntSize& size) { #if USE(GRAPHICS_SURFACE) Display* display = nativeDisplay(); if (!display) return; if (!visInfo.visual) { LOG_ERROR("Failed to find valid XVisual."); return; } Window xWindow = offscreenRootWindow(); if (!xWindow) return; Colormap cmap = XCreateColormap(display, xWindow, visInfo.visual, AllocNone); XSetWindowAttributes attribute; attribute.background_pixel = WhitePixel(display, 0); attribute.border_pixel = BlackPixel(display, 0); attribute.colormap = cmap; #if USE(GLX) attribute.event_mask = ResizeRedirectMask; #endif uint32_t tempHandleId = XCreateWindow(display, xWindow, 0, 0, size.width(), size.height(), 0, visInfo.depth, InputOutput, visInfo.visual, CWBackPixel | CWBorderPixel | CWColormap, &attribute); if (!tempHandleId) { LOG_ERROR("Failed to create offscreen window."); return; } XSetWindowBackgroundPixmap(display, tempHandleId, 0); #if USE(GLX) XCompositeRedirectWindow(display, tempHandleId, CompositeRedirectManual); #endif XMapWindow(display, tempHandleId); *handleId = tempHandleId; #else UNUSED_PARAM(handleId); UNUSED_PARAM(visInfo); UNUSED_PARAM(size); #endif }
// ===== EmbedWindow() ===== bool LX11::EmbedWindow(WId win, WId container){ Display *disp = QX11Info::display(); if(win==0 || container==0){ return false; } //Reparent the window //XCompositeRedirectSubwindows(disp, container, CompositeRedirectAutomatic); //container/window should be aware of each other //qDebug() << "Embed Window:" << win << container; XReparentWindow(disp, win, container,0,0); XSync(disp, false); //Check that the window has _XEMBED_INFO //qDebug() << " - check for _XEMBED_INFO"; Atom embinfo = XInternAtom(disp, "_XEMBED_INFO",false); uchar *data=0; ulong num, bytes; int fmt; Atom junk; if(Success != XGetWindowProperty(disp, win, embinfo, 0, 2, false, embinfo, &junk, &fmt, &num, &bytes, &data) ){ return false; //Embedding error (no info?) } if(data){ XFree(data); } // clean up any data found //Now send the embed event to the app //qDebug() << " - send _XEMBED event"; XEvent ev; ev.xclient.type=ClientMessage; ev.xclient.serial=0; ev.xclient.send_event=true; ev.xclient.message_type = XInternAtom(disp, "_XEMBED", false); ev.xclient.window = win; ev.xclient.format = 32; ev.xclient.data.l[0] = CurrentTime; ev.xclient.data.l[1] = 0; //XEMBED_EMBEDDED_NOTIFY ev.xclient.data.l[2] = 0; ev.xclient.data.l[3] = container; ev.xclient.data.l[4] = 0; XSendEvent(disp, win, false, 0xFFFFFF, &ev); //Now setup any redirects and return //qDebug() << " - select Input"; XSelectInput(disp, win, StructureNotifyMask); //Notify of structure changes //qDebug() << " - Composite Redirect"; XCompositeRedirectWindow(disp, win, CompositeRedirectManual); //qDebug() << " - Done"; return true; }
static void sync_unredirected (MetaSurfaceActorX11 *self) { MetaSurfaceActorX11Private *priv = meta_surface_actor_x11_get_instance_private (self); MetaDisplay *display = priv->display; Display *xdisplay = meta_display_get_xdisplay (display); Window xwindow = meta_window_x11_get_toplevel_xwindow (priv->window); meta_error_trap_push (display); if (priv->unredirected) { detach_pixmap (self); XCompositeUnredirectWindow (xdisplay, xwindow, CompositeRedirectManual); } else { XCompositeRedirectWindow (xdisplay, xwindow, CompositeRedirectManual); } meta_error_trap_pop (display); }
void CompositeWindow::redirect () { if (priv->redirected || !priv->cScreen->compositingActive ()) return; XCompositeRedirectWindow (screen->dpy (), ROOTPARENT (priv->window), CompositeRedirectManual); priv->redirected = true; if (priv->overlayWindow) { priv->cScreen->overlayWindowCount ()--; priv->overlayWindow = false; } if (priv->cScreen->overlayWindowCount () < 1) priv->cScreen->showOutputWindow (); else priv->cScreen->updateOutputWindow (); }
void SceneXrender::selfCheckSetup() { KXErrorHandler err; QImage img( selfCheckWidth(), selfCheckHeight(), QImage::Format_RGB32 ); img.setPixel( 0, 0, QColor( Qt::red ).rgb()); img.setPixel( 1, 0, QColor( Qt::green ).rgb()); img.setPixel( 2, 0, QColor( Qt::blue ).rgb()); img.setPixel( 0, 1, QColor( Qt::white ).rgb()); img.setPixel( 1, 1, QColor( Qt::black ).rgb()); img.setPixel( 2, 1, QColor( Qt::white ).rgb()); QPixmap pix = QPixmap::fromImage( img ); foreach( const QPoint& p, selfCheckPoints()) { XSetWindowAttributes wa; wa.override_redirect = True; ::Window window = XCreateWindow( display(), rootWindow(), 0, 0, selfCheckWidth(), selfCheckHeight(), 0, QX11Info::appDepth(), CopyFromParent, CopyFromParent, CWOverrideRedirect, &wa ); XSetWindowBackgroundPixmap( display(), window, pix.handle()); XClearWindow( display(), window ); XMapWindow( display(), window ); // move the window one down to where the result will be rendered too, just in case // the render would fail completely and eventual check would try to read this window's contents XMoveWindow( display(), window, p.x() + 1, p.y()); XCompositeRedirectWindow( display(), window, CompositeRedirectAutomatic ); Pixmap wpix = XCompositeNameWindowPixmap( display(), window ); XWindowAttributes attrs; XGetWindowAttributes( display(), window, &attrs ); XRenderPictFormat* format = XRenderFindVisualFormat( display(), attrs.visual ); Picture pic = XRenderCreatePicture( display(), wpix, format, 0, 0 ); QRect rect( p.x(), p.y(), selfCheckWidth(), selfCheckHeight()); XRenderComposite( display(), PictOpSrc, pic, None, buffer, 0, 0, 0, 0, rect.x(), rect.y(), rect.width(), rect.height()); XRenderFreePicture( display(), pic ); XFreePixmap( display(), wpix ); XDestroyWindow( display(), window ); }
RedirectedXCompositeWindow::RedirectedXCompositeWindow(GdkWindow* parentWindow, std::function<void()> damageNotify) : m_display(GDK_DISPLAY_XDISPLAY(gdk_window_get_display(parentWindow))) , m_window(0) , m_parentWindow(0) , m_pixmap(0) , m_damage(0) , m_needsNewPixmapAfterResize(false) { Screen* screen = DefaultScreenOfDisplay(m_display); GdkVisual* visual = gdk_window_get_visual(parentWindow); Colormap colormap = XCreateColormap(m_display, RootWindowOfScreen(screen), GDK_VISUAL_XVISUAL(visual), AllocNone); // This is based on code from Chromium: src/content/common/gpu/image_transport_surface_linux.cc XSetWindowAttributes windowAttributes; windowAttributes.override_redirect = True; windowAttributes.colormap = colormap; // CWBorderPixel must be present when the depth doesn't match the parent's one. // See http://cgit.freedesktop.org/xorg/xserver/tree/dix/window.c?id=xorg-server-1.16.0#n703. windowAttributes.border_pixel = 0; m_parentWindow = XCreateWindow(m_display, RootWindowOfScreen(screen), WidthOfScreen(screen) + 1, 0, 1, 1, 0, gdk_visual_get_depth(visual), InputOutput, GDK_VISUAL_XVISUAL(visual), CWOverrideRedirect | CWColormap | CWBorderPixel, &windowAttributes); XMapWindow(m_display, m_parentWindow); windowAttributes.event_mask = StructureNotifyMask; windowAttributes.override_redirect = False; // Create the window of at last 1x1 since X doesn't allow to create empty windows. m_window = XCreateWindow(m_display, m_parentWindow, 0, 0, std::max(1, m_size.width()), std::max(1, m_size.height()), 0, CopyFromParent, InputOutput, CopyFromParent, CWEventMask, &windowAttributes); XMapWindow(m_display, m_window); XFreeColormap(m_display, colormap); xDamageNotifier().add(m_window, WTF::move(damageNotify)); while (1) { XEvent event; XWindowEvent(m_display, m_window, StructureNotifyMask, &event); if (event.type == MapNotify && event.xmap.window == m_window) break; } XSelectInput(m_display, m_window, NoEventMask); XCompositeRedirectWindow(m_display, m_window, CompositeRedirectManual); m_damage = XDamageCreate(m_display, m_window, XDamageReportNonEmpty); }
int xcomposite_get_widow_contents() { int ret = 0; int ver, rev, eventB, baseB; int x, y; Pixmap pxm = 0; window_struct params; if(create_window(¶ms, "Test Window")) { ret = -1; goto cleanup; } if(!XCompositeQueryExtension(params.display, &eventB, &baseB)) { BLTS_ERROR("XCompositeQueryExtension failed\n"); ret = -1; goto cleanup; } if(!XCompositeQueryVersion(params.display, &ver, &rev)) { BLTS_ERROR("XCompositeQueryVersion failed\n"); ret = -1; goto cleanup; } BLTS_DEBUG("XComposite Extension version %i.%i\n", ver, rev); /* Redirect window to off-screen storage (the window might be already redirected when using composite window manager) */ XCompositeRedirectWindow(params.display, params.window, 0); /* Draw rectangle pattern */ for(x = 0; x < params.window_attributes.width; x+=20) { for(y = 0; y < params.window_attributes.height; y+=20) { XFillRectangle(params.display, params.window, params.gc, x, y, 10, 10); } } XFlush(params.display); sleep(1); /* Get pixmap of window contents */ pxm = XCompositeNameWindowPixmap(params.display, params.window); XCompositeUnredirectWindow(params.display, params.window, 0); /* Copy the pixmap over the window (you should see white/black stripes * after this) */ for(y = 0; y < params.window_attributes.height; y++) { XCopyArea(params.display, pxm, params.window, params.gc, 0, 0, params.window_attributes.width, params.window_attributes.height, 0, y ); } XFlush(params.display); sleep(1); cleanup: if(params.display && pxm) { XFreePixmap(params.display, pxm); } close_window(¶ms); return ret; }
void XCompcapMain::updateSettings(obs_data_t *settings) { PLock lock(&p->lock); XErrorLock xlock; ObsGsContextHolder obsctx; blog(LOG_DEBUG, "Settings updating"); Window prevWin = p->win; xcc_cleanup(p); if (settings) { const char *windowName = obs_data_get_string(settings, "capture_window"); p->windowName = windowName; p->win = getWindowFromString(windowName); p->cut_top = obs_data_get_int(settings, "cut_top"); p->cut_left = obs_data_get_int(settings, "cut_left"); p->cut_right = obs_data_get_int(settings, "cut_right"); p->cut_bot = obs_data_get_int(settings, "cut_bot"); p->lockX = obs_data_get_bool(settings, "lock_x"); p->swapRedBlue = obs_data_get_bool(settings, "swap_redblue"); p->show_cursor = obs_data_get_bool(settings, "show_cursor"); p->include_border = obs_data_get_bool(settings, "include_border"); p->exclude_alpha = obs_data_get_bool(settings, "exclude_alpha"); } else { p->win = prevWin; } xlock.resetError(); if (p->win) XCompositeRedirectWindow(xdisp, p->win, CompositeRedirectAutomatic); if (xlock.gotError()) { blog(LOG_ERROR, "XCompositeRedirectWindow failed: %s", xlock.getErrorText().c_str()); return; } if (p->win) XSelectInput(xdisp, p->win, StructureNotifyMask | ExposureMask); XSync(xdisp, 0); XWindowAttributes attr; if (!p->win || !XGetWindowAttributes(xdisp, p->win, &attr)) { p->win = 0; p->width = 0; p->height = 0; return; } if (p->win && p->cursor && p->show_cursor) { Window child; int x, y; XTranslateCoordinates(xdisp, p->win, attr.root, 0, 0, &x, &y, &child); xcursor_offset(p->cursor, x, y); } gs_color_format cf = GS_RGBA; if (p->exclude_alpha) { cf = GS_BGRX; } p->border = attr.border_width; if (p->include_border) { p->width = attr.width + p->border * 2; p->height = attr.height + p->border * 2; } else { p->width = attr.width; p->height = attr.height; } if (p->cut_top + p->cut_bot < (int)p->height) { p->cur_cut_top = p->cut_top; p->cur_cut_bot = p->cut_bot; } else { p->cur_cut_top = 0; p->cur_cut_bot = 0; } if (p->cut_left + p->cut_right < (int)p->width) { p->cur_cut_left = p->cut_left; p->cur_cut_right = p->cut_right; } else { p->cur_cut_left = 0; p->cur_cut_right = 0; } if (p->tex) gs_texture_destroy(p->tex); uint8_t *texData = new uint8_t[width() * height() * 4]; memset(texData, 0, width() * height() * 4); const uint8_t* texDataArr[] = { texData, 0 }; p->tex = gs_texture_create(width(), height(), cf, 1, texDataArr, 0); delete[] texData; if (p->swapRedBlue) { GLuint tex = *(GLuint*)gs_texture_get_obj(p->tex); glBindTexture(GL_TEXTURE_2D, tex); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_SWIZZLE_B, GL_RED); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_SWIZZLE_R, GL_BLUE); glBindTexture(GL_TEXTURE_2D, 0); } const int attrs[] = { GLX_BIND_TO_TEXTURE_RGBA_EXT, GL_TRUE, GLX_DRAWABLE_TYPE, GLX_PIXMAP_BIT, GLX_BIND_TO_TEXTURE_TARGETS_EXT, GLX_TEXTURE_2D_BIT_EXT, GLX_DOUBLEBUFFER, GL_FALSE, None }; int nelem = 0; GLXFBConfig* configs = glXChooseFBConfig(xdisp, XCompcap::getRootWindowScreen(attr.root), attrs, &nelem); if (nelem <= 0) { blog(LOG_ERROR, "no matching fb config found"); p->win = 0; p->height = 0; p->width = 0; return; } glXGetFBConfigAttrib(xdisp, configs[0], GLX_Y_INVERTED_EXT, &nelem); p->inverted = nelem != 0; xlock.resetError(); p->pixmap = XCompositeNameWindowPixmap(xdisp, p->win); if (xlock.gotError()) { blog(LOG_ERROR, "XCompositeNameWindowPixmap failed: %s", xlock.getErrorText().c_str()); p->pixmap = 0; XFree(configs); return; } const int attribs[] = { GLX_TEXTURE_TARGET_EXT, GLX_TEXTURE_2D_EXT, GLX_TEXTURE_FORMAT_EXT, GLX_TEXTURE_FORMAT_RGBA_EXT, None }; p->glxpixmap = glXCreatePixmap(xdisp, configs[0], p->pixmap, attribs); if (xlock.gotError()) { blog(LOG_ERROR, "glXCreatePixmap failed: %s", xlock.getErrorText().c_str()); XFreePixmap(xdisp, p->pixmap); XFree(configs); p->pixmap = 0; p->glxpixmap = 0; return; } XFree(configs); p->gltex = gs_texture_create(p->width, p->height, cf, 1, 0, GS_GL_DUMMYTEX); GLuint gltex = *(GLuint*)gs_texture_get_obj(p->gltex); glBindTexture(GL_TEXTURE_2D, gltex); glXBindTexImageEXT(xdisp, p->glxpixmap, GLX_FRONT_LEFT_EXT, NULL); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR); glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR); }
void X11Support::redirectWindow(unsigned long window) { XCompositeRedirectWindow(QX11Info::display(), window, CompositeRedirectManual); }
RedirectedXCompositeWindow::RedirectedXCompositeWindow(WebPageProxy& webPage, const IntSize& initialSize, std::function<void()>&& damageNotify) : m_webPage(webPage) , m_display(GDK_DISPLAY_XDISPLAY(gdk_window_get_display(gtk_widget_get_parent_window(webPage.viewWidget())))) , m_size(initialSize) { m_size.scale(m_webPage.deviceScaleFactor()); ASSERT(downcast<PlatformDisplayX11>(PlatformDisplay::sharedDisplay()).native() == m_display); Screen* screen = DefaultScreenOfDisplay(m_display); GdkVisual* visual = gdk_window_get_visual(gtk_widget_get_parent_window(webPage.viewWidget())); XUniqueColormap colormap(XCreateColormap(m_display, RootWindowOfScreen(screen), GDK_VISUAL_XVISUAL(visual), AllocNone)); // This is based on code from Chromium: src/content/common/gpu/image_transport_surface_linux.cc XSetWindowAttributes windowAttributes; windowAttributes.override_redirect = True; windowAttributes.colormap = colormap.get(); // CWBorderPixel must be present when the depth doesn't match the parent's one. // See http://cgit.freedesktop.org/xorg/xserver/tree/dix/window.c?id=xorg-server-1.16.0#n703. windowAttributes.border_pixel = 0; m_parentWindow = XCreateWindow(m_display, RootWindowOfScreen(screen), WidthOfScreen(screen) + 1, 0, 1, 1, 0, gdk_visual_get_depth(visual), InputOutput, GDK_VISUAL_XVISUAL(visual), CWOverrideRedirect | CWColormap | CWBorderPixel, &windowAttributes); XMapWindow(m_display, m_parentWindow.get()); windowAttributes.event_mask = StructureNotifyMask; windowAttributes.override_redirect = False; // Create the window of at last 1x1 since X doesn't allow to create empty windows. m_window = XCreateWindow(m_display, m_parentWindow.get(), 0, 0, std::max(1, m_size.width()), std::max(1, m_size.height()), 0, CopyFromParent, InputOutput, CopyFromParent, CWEventMask, &windowAttributes); XMapWindow(m_display, m_window.get()); xDamageNotifier().add(m_window.get(), WTFMove(damageNotify)); while (1) { XEvent event; XWindowEvent(m_display, m_window.get(), StructureNotifyMask, &event); if (event.type == MapNotify && event.xmap.window == m_window.get()) break; } XSelectInput(m_display, m_window.get(), NoEventMask); XCompositeRedirectWindow(m_display, m_window.get(), CompositeRedirectManual); if (!m_size.isEmpty()) createNewPixampAndPixampSurface(); m_damage = XDamageCreate(m_display, m_window.get(), XDamageReportNonEmpty); }
nsresult nsPluginNativeWindowGtk2::CreateXCompositedWindow() { NS_ASSERTION(!mSocketWidget,"Already created a socket widget!"); mParentWindow = gtk_window_new(GTK_WINDOW_POPUP); mSocketWidget = gtk_socket_new(); GdkWindow *parent_win = mParentWindow->window; //attach the socket to the container widget gtk_widget_set_parent_window(mSocketWidget, parent_win); // Make sure to handle the plug_removed signal. If we don't the // socket will automatically be destroyed when the plug is // removed, which means we're destroying it more than once. // SYNTAX ERROR. g_signal_connect(mSocketWidget, "plug_removed", G_CALLBACK(plug_removed_cb), NULL); g_signal_connect(mSocketWidget, "destroy", G_CALLBACK(gtk_widget_destroyed), &mSocketWidget); /*gpointer user_data = NULL; gdk_window_get_user_data(parent_win, &user_data); */ GtkContainer *container = GTK_CONTAINER(mParentWindow); gtk_container_add(container, mSocketWidget); gtk_widget_realize(mSocketWidget); // Resize before we show SetAllocation(); gtk_widget_set_size_request (mSocketWidget, width, height); /* move offscreen */ gtk_window_move (GTK_WINDOW(mParentWindow), width+1000, height+1000); gtk_widget_show(mSocketWidget); gtk_widget_show_all(mParentWindow); /* store away a reference to the socketwidget */ mPlugWindow = (mSocketWidget); gdk_flush(); window = (nsPluginPort *)gtk_socket_get_id(GTK_SOCKET(mSocketWidget)); /* This is useful if we still have the plugin window inline * i.e. firefox vs. fennec */ // gdk_window_set_composited(mSocketWidget->window, TRUE); if (!mDamage) { /* we install a general handler instead of one specific to a particular window * because we don't have a GdkWindow for the plugin window */ gdk_window_add_filter (parent_win, plugin_composite_filter_func, this); int junk; if (!XDamageQueryExtension (GDK_DISPLAY (), &xdamage_event_base, &junk)) printf ("This requires the XDamage extension"); mDamage = XDamageCreate(GDK_DISPLAY(), (Drawable)window, XDamageReportNonEmpty); XCompositeRedirectWindow (GDK_DISPLAY(), (Drawable)window, CompositeRedirectManual); /* this is a hack to avoid having flash causing a crash when it is unloaded. * libplayback sets up dbus_connection_filters. When flash is unloaded it takes * libplayback with it, however the connection filters are not removed * which causes a crash when dbus tries to execute them. dlopening libplayback * ensures that those functions stay around even after flash is gone. */ static void *libplayback_handle; if (!libplayback_handle) { libplayback_handle = dlopen("libplayback-1.so.0", RTLD_NOW); } } // Fill out the ws_info structure. // (The windowless case is done in nsObjectFrame.cpp.) GdkWindow *gdkWindow = gdk_window_lookup((XID)window); mWsInfo.display = GDK_WINDOW_XDISPLAY(gdkWindow); mWsInfo.colormap = GDK_COLORMAP_XCOLORMAP(gdk_drawable_get_colormap(gdkWindow)); GdkVisual* gdkVisual = gdk_drawable_get_visual(gdkWindow); mWsInfo.visual = GDK_VISUAL_XVISUAL(gdkVisual); mWsInfo.depth = gdkVisual->depth; return NS_OK; }
static DFBResult x11AllocateKey( CoreSurfacePool *pool, void *pool_data, void *pool_local, CoreSurfaceBuffer *buffer, const char *key, u64 handle, CoreSurfaceAllocation *allocation, void *alloc_data ) { CoreSurface *surface; x11AllocationData *alloc = alloc_data; x11PoolLocalData *local = pool_local; DFBX11 *x11 = local->x11; D_DEBUG_AT( X11_Surfaces, "%s( %s, 0x%08llx )\n", __FUNCTION__, key, (unsigned long long) handle ); D_DEBUG_AT( X11_Surfaces, " -> allocation: %s\n", ToString_CoreSurfaceAllocation( allocation ) ); D_MAGIC_ASSERT( pool, CoreSurfacePool ); D_MAGIC_ASSERT( buffer, CoreSurfaceBuffer ); surface = buffer->surface; D_MAGIC_ASSERT( surface, CoreSurface ); if (!strcmp( key, "Pixmap/X11" )) { D_DEBUG_AT( X11_Surfaces, " -> Pixmap/X11\n" ); alloc->type = X11_ALLOC_PIXMAP; } else if (!strcmp( key, "Window/X11" )) { D_DEBUG_AT( X11_Surfaces, " -> Window/X11\n" ); alloc->type = X11_ALLOC_WINDOW; } else { D_BUG( "unexpected key '%s'", key ); return DFB_BUG; } dfb_surface_calc_buffer_size( surface, 8, 8, &alloc->pitch, &allocation->size ); // alloc->depth = DefaultDepthOfScreen( x11->screenptr ); // alloc->visual = DefaultVisualOfScreen( x11->screenptr ); alloc->visual = x11->visuals[DFB_PIXELFORMAT_INDEX(buffer->format)]; alloc->depth = DFB_COLOR_BITS_PER_PIXEL( buffer->format ) + DFB_ALPHA_BITS_PER_PIXEL( buffer->format ); if (alloc->depth == DefaultDepthOfScreen( x11->screenptr )) alloc->visual = DefaultVisualOfScreen( x11->screenptr ); D_DEBUG_AT( X11_Surfaces, " -> visual %p (id %lu), depth %d\n", alloc->visual, alloc->visual->visualid, alloc->depth ); if (handle) { switch (alloc->type) { case X11_ALLOC_PIXMAP: XLockDisplay( x11->display ); alloc->xid = (unsigned long) handle; x11->Sync( x11 ); D_DEBUG_AT( X11_Surfaces, " -> pixmap 0x%08lx\n", (long) alloc->xid ); XUnlockDisplay( x11->display ); D_INFO( "X11/Windows: Import Pixmap 0x%08lx\n", alloc->xid ); break; case X11_ALLOC_WINDOW: { XLockDisplay( x11->display ); alloc->window = (unsigned long) handle; x11->Sync( x11 ); D_DEBUG_AT( X11_Surfaces, " -> window 0x%08lx\n", (long) alloc->window ); XCompositeRedirectWindow( x11->display, alloc->window, CompositeRedirectManual ); x11->Sync( x11 ); D_DEBUG_AT( X11_Surfaces, " -> redirected\n" ); alloc->xid = XCompositeNameWindowPixmap( x11->display, alloc->window ); // alloc->xid = alloc->window; x11->Sync( x11 ); D_DEBUG_AT( X11_Surfaces, " -> pixmap 0x%08lx\n", (long) alloc->xid ); XUnmapWindow( x11->display, alloc->window ); x11->Sync( x11 ); D_DEBUG_AT( X11_Surfaces, " -> unmapped\n" ); XUnlockDisplay( x11->display ); D_INFO( "X11/Windows: Import Window 0x%08lx with Pixmap handle 0x%08lx\n", alloc->window, alloc->xid ); break; } default: D_BUG( "unexpected allocation type %d\n", alloc->type ); return DFB_BUG; } } else { // alloc->type = X11_ALLOC_PIXMAP; switch (alloc->type) { case X11_ALLOC_PIXMAP: XLockDisplay( x11->display ); x11->Sync( x11 ); D_DEBUG_AT( X11_Surfaces, " -> creating pixmap...\n" ); alloc->xid = XCreatePixmap( x11->display, DefaultRootWindow(x11->display), allocation->config.size.w, allocation->config.size.h, alloc->depth ); x11->Sync( x11 ); XSync( x11->display, False ); D_DEBUG_AT( X11_Surfaces, " -> pixmap 0x%08lx\n", (long) alloc->xid ); XUnlockDisplay( x11->display ); D_INFO( "X11/Windows: New Pixmap 0x%08lx\n", alloc->xid ); alloc->created = true; break; case X11_ALLOC_WINDOW: { Window w = (Window) (long) buffer->surface->data; XSetWindowAttributes attr; attr.event_mask = ButtonPressMask | ButtonReleaseMask | PointerMotionMask | KeyPressMask | KeyReleaseMask | ExposureMask | StructureNotifyMask; attr.background_pixmap = 0; XLockDisplay( x11->display ); x11->Sync( x11 ); D_DEBUG_AT( X11_Surfaces, " -> creating window...\n" ); alloc->window = w?:XCreateWindow( x11->display, DefaultRootWindow(x11->display), 600, 200, allocation->config.size.w, allocation->config.size.h, 0, alloc->depth, InputOutput, alloc->visual, CWEventMask, &attr ); x11->Sync( x11 ); D_DEBUG_AT( X11_Surfaces, " -> window 0x%08lx\n", (long) alloc->window ); buffer->surface->data = (void*) (long) alloc->window; XMapRaised( x11->display, alloc->window ); x11->Sync( x11 ); D_DEBUG_AT( X11_Surfaces, " -> raised\n" ); XCompositeRedirectWindow( x11->display, alloc->window, CompositeRedirectManual ); x11->Sync( x11 ); D_DEBUG_AT( X11_Surfaces, " -> redirected\n" ); alloc->xid = XCompositeNameWindowPixmap( x11->display, alloc->window ); // alloc->xid = alloc->window; x11->Sync( x11 ); D_DEBUG_AT( X11_Surfaces, " -> pixmap 0x%08lx\n", (long) alloc->xid ); XUnmapWindow( x11->display, alloc->window ); x11->Sync( x11 ); D_DEBUG_AT( X11_Surfaces, " -> unmapped\n" ); XUnlockDisplay( x11->display ); D_INFO( "X11/Windows: New Window 0x%08lx with Pixmap handle 0x%08lx\n", alloc->window, alloc->xid ); alloc->created = !w; break; } default: D_BUG( "unexpected allocation type %d\n", alloc->type ); return DFB_BUG; } } alloc->gc = XCreateGC( x11->display, alloc->xid, 0, NULL ); allocation->offset = alloc->type; return DFB_OK; }
gboolean embed_icon(TrayWindow *traywin) { if (systray_profile) fprintf(stderr, "[%f] %s:%d win = %lu (%s)\n", profiling_get_time(), __FUNCTION__, __LINE__, traywin->win, traywin->name); if (traywin->embedded) return TRUE; Panel *panel = systray.area.panel; XSync(server.display, False); error = FALSE; XErrorHandler old = XSetErrorHandler(window_error_handler); if (0) { Atom acttype; int actfmt; unsigned long nbitem, bytes; unsigned long *data = 0; int ret; if (systray_profile) fprintf(stderr, "XGetWindowProperty(server.display, traywin->win, server.atom._XEMBED_INFO, 0, 2, False, " "server.atom._XEMBED_INFO, &acttype, &actfmt, &nbitem, &bytes, &data)\n"); ret = XGetWindowProperty(server.display, traywin->win, server.atom._XEMBED_INFO, 0, 2, False, server.atom._XEMBED_INFO, &acttype, &actfmt, &nbitem, &bytes, (unsigned char **)&data); if (ret == Success) { if (data) { if (nbitem >= 2) { int hide = ((data[1] & XEMBED_MAPPED) == 0); if (hide) { // In theory we have to check the embedding with this and remove icons that refuse embedding. // In practice we have no idea when the other application processes the event and accepts the // embed so we cannot check now without a race. // Race can be triggered with PyGtk(2) apps. // We could defer this for later (if we set PropertyChangeMask in XSelectInput we get notified) // but for some reason it breaks transparency for Qt icons. So we don't. // fprintf(stderr, RED "tint2: window refused embedding" RESET "\n"); // remove_icon(traywin); // XFree(data); // return FALSE; } } XFree(data); } } else { fprintf(stderr, RED "tint2 : xembed error" RESET "\n"); remove_icon(traywin); return FALSE; } } // Redirect rendering when using compositing if (systray_composited) { if (systray_profile) fprintf(stderr, "XDamageCreate(server.display, traywin->parent, XDamageReportRawRectangles)\n"); traywin->damage = XDamageCreate(server.display, traywin->parent, XDamageReportRawRectangles); if (systray_profile) fprintf(stderr, "XCompositeRedirectWindow(server.display, traywin->parent, CompositeRedirectManual)\n"); XCompositeRedirectWindow(server.display, traywin->parent, CompositeRedirectManual); } XRaiseWindow(server.display, traywin->win); // Make the icon visible if (systray_profile) fprintf(stderr, "XMapWindow(server.display, traywin->win)\n"); XMapWindow(server.display, traywin->win); if (!panel->is_hidden) { if (systray_profile) fprintf(stderr, "XMapRaised(server.display, traywin->parent)\n"); XMapRaised(server.display, traywin->parent); } if (systray_profile) fprintf(stderr, "XSync(server.display, False)\n"); XSync(server.display, False); XSetErrorHandler(old); if (error != FALSE) { fprintf(stderr, RED "systray %d: cannot embed icon for window %lu (%s) parent %lu pid %d" RESET "\n", __LINE__, traywin->win, traywin->name, traywin->parent, traywin->pid); remove_icon(traywin); return FALSE; } traywin->embedded = TRUE; if (systray_profile) fprintf(stderr, "[%f] %s:%d win = %lu (%s)\n", profiling_get_time(), __FUNCTION__, __LINE__, traywin->win, traywin->name); return TRUE; }
ClientWin * clientwin_create(MainWin *mw, Window client) { session_t *ps = mw->ps; ClientWin *cw = allocchk(malloc(sizeof(ClientWin))); { static const ClientWin CLIENTWT_DEF = CLIENTWT_INIT; memcpy(cw, &CLIENTWT_DEF, sizeof(ClientWin)); } XWindowAttributes attr; cw->mainwin = mw; cw->wid_client = client; if (ps->o.includeFrame) cw->src.window = wm_find_frame(ps, client); if (!cw->src.window) cw->src.window = client; cw->mini.format = mw->format; { XSetWindowAttributes sattr = { .border_pixel = 0, .background_pixel = 0, .colormap = mw->colormap, .event_mask = ButtonPressMask | ButtonReleaseMask | KeyPressMask | KeyReleaseMask | EnterWindowMask | LeaveWindowMask | PointerMotionMask | ExposureMask | FocusChangeMask, .override_redirect = ps->o.lazyTrans, }; cw->mini.window = XCreateWindow(ps->dpy, (ps->o.lazyTrans ? ps->root : mw->window), 0, 0, 1, 1, 0, mw->depth, InputOutput, mw->visual, CWColormap | CWBackPixel | CWBorderPixel | CWEventMask | CWOverrideRedirect, &sattr); } if (!cw->mini.window) goto clientwin_create_err; { static const char *PREFIX = "mini window of "; const int len = strlen(PREFIX) + 20; char *str = allocchk(malloc(len)); snprintf(str, len, "%s%#010lx", PREFIX, cw->src.window); wm_wid_set_info(cw->mainwin->ps, cw->mini.window, str, None); free(str); } // Listen to events on the window. We don't want to miss any changes so // this is to be done as early as possible XSelectInput(cw->mainwin->ps->dpy, cw->src.window, SubstructureNotifyMask | StructureNotifyMask); XGetWindowAttributes(ps->dpy, client, &attr); if (IsViewable != attr.map_state) goto clientwin_create_err; clientwin_update(cw); // Get window pixmap if (ps->o.useNameWindowPixmap) { XCompositeRedirectWindow(ps->dpy, cw->src.window, CompositeRedirectAutomatic); cw->redirected = true; cw->cpixmap = XCompositeNameWindowPixmap(ps->dpy, cw->src.window); } // Create window picture { Drawable draw = cw->cpixmap; if (!draw) draw = cw->src.window; XRenderPictureAttributes pa = { .subwindow_mode = IncludeInferiors }; cw->origin = XRenderCreatePicture(cw->mainwin->ps->dpy, draw, cw->src.format, CPSubwindowMode, &pa); } if (!cw->origin) goto clientwin_create_err; XRenderSetPictureFilter(cw->mainwin->ps->dpy, cw->origin, FilterBest, 0, 0); return cw; clientwin_create_err: if (cw) clientwin_destroy(cw, False); return NULL; } void clientwin_update(ClientWin *cw) { Window tmpwin; XWindowAttributes wattr; XGetWindowAttributes(cw->mainwin->ps->dpy, cw->src.window, &wattr); XTranslateCoordinates(cw->mainwin->ps->dpy, cw->src.window, wattr.root, -wattr.border_width, -wattr.border_width, &cw->src.x, &cw->src.y, &tmpwin); cw->src.width = wattr.width; cw->src.height = wattr.height; cw->src.format = XRenderFindVisualFormat(cw->mainwin->ps->dpy, wattr.visual); cw->mini.x = cw->mini.y = 0; cw->mini.width = cw->mini.height = 1; }
bool TrayIcon::init() { Display* dsp = QX11Info::display(); XWindowAttributes attr; if (! XGetWindowAttributes(dsp, mIconId, &attr)) return false; // qDebug() << "New tray icon ***********************************"; // qDebug() << " * window id: " << hex << mIconId; // qDebug() << " * window name:" << xfitMan().getName(mIconId); // qDebug() << " * size (WxH): " << attr.width << "x" << attr.height; // qDebug() << " * color depth:" << attr.depth; unsigned long mask = 0; XSetWindowAttributes set_attr; Visual* visual = attr.visual; set_attr.colormap = attr.colormap; set_attr.background_pixel = 0; set_attr.border_pixel = 0; mask = CWColormap|CWBackPixel|CWBorderPixel; mWindowId = XCreateWindow(dsp, this->winId(), 0, 0, mIconSize.width(), mIconSize.height(), 0, attr.depth, InputOutput, visual, mask, &set_attr); xError = false; XErrorHandler old; old = XSetErrorHandler(windowErrorHandler); XReparentWindow(dsp, mIconId, mWindowId, 0, 0); XSync(dsp, false); XSetErrorHandler(old); if (xError) { qWarning() << "****************************************"; qWarning() << "* Not icon_swallow *"; qWarning() << "****************************************"; XDestroyWindow(dsp, mWindowId); return false; } { Atom acttype; int actfmt; unsigned long nbitem, bytes; unsigned char *data = 0; int ret; ret = XGetWindowProperty(dsp, mIconId, xfitMan().atom("_XEMBED_INFO"), 0, 2, false, xfitMan().atom("_XEMBED_INFO"), &acttype, &actfmt, &nbitem, &bytes, &data); if (ret == Success) { if (data) XFree(data); } else { qWarning() << "TrayIcon: xembed error"; XDestroyWindow(dsp, mWindowId); return false; } } { XEvent e; e.xclient.type = ClientMessage; e.xclient.serial = 0; e.xclient.send_event = True; e.xclient.message_type = xfitMan().atom("_XEMBED"); e.xclient.window = mIconId; e.xclient.format = 32; e.xclient.data.l[0] = CurrentTime; e.xclient.data.l[1] = XEMBED_EMBEDDED_NOTIFY; e.xclient.data.l[2] = 0; e.xclient.data.l[3] = mWindowId; e.xclient.data.l[4] = 0; XSendEvent(dsp, mIconId, false, 0xFFFFFF, &e); } XSelectInput(dsp, mIconId, StructureNotifyMask); mDamage = XDamageCreate(dsp, mIconId, XDamageReportRawRectangles); XCompositeRedirectWindow(dsp, mWindowId, CompositeRedirectManual); XMapWindow(dsp, mIconId); XMapRaised(dsp, mWindowId); xfitMan().resizeWindow(mWindowId, mIconSize.width(), mIconSize.height()); xfitMan().resizeWindow(mIconId, mIconSize.width(), mIconSize.height()); return true; }
void QWaylandXCompositeEGLContext::geometryChanged() { QSize size(mWindow->geometry().size()); if (size.isEmpty()) { //QGLWidget wants a context for a window without geometry size = QSize(1,1); } delete mBuffer; //XFreePixmap deletes the glxPixmap as well if (mXWindow) { XDestroyWindow(mEglIntegration->xDisplay(),mXWindow); } VisualID visualId = QXlibEglIntegration::getCompatibleVisualId(mEglIntegration->xDisplay(),mEglIntegration->eglDisplay(),mConfig); XVisualInfo visualInfoTemplate; memset(&visualInfoTemplate, 0, sizeof(XVisualInfo)); visualInfoTemplate.visualid = visualId; int matchingCount = 0; XVisualInfo *visualInfo = XGetVisualInfo(mEglIntegration->xDisplay(), VisualIDMask, &visualInfoTemplate, &matchingCount); Colormap cmap = XCreateColormap(mEglIntegration->xDisplay(),mEglIntegration->rootWindow(),visualInfo->visual,AllocNone); XSetWindowAttributes a; a.colormap = cmap; mXWindow = XCreateWindow(mEglIntegration->xDisplay(), mEglIntegration->rootWindow(),0, 0, size.width(), size.height(), 0, visualInfo->depth, InputOutput, visualInfo->visual, CWColormap, &a); XCompositeRedirectWindow(mEglIntegration->xDisplay(), mXWindow, CompositeRedirectManual); XMapWindow(mEglIntegration->xDisplay(), mXWindow); mEglWindowSurface = eglCreateWindowSurface(mEglIntegration->eglDisplay(),mConfig,mXWindow,0); if (mEglWindowSurface == EGL_NO_SURFACE) { qFatal("Could not make eglsurface"); } XSync(mEglIntegration->xDisplay(),False); mBuffer = new QWaylandXCompositeBuffer(mEglIntegration->waylandXComposite(), (uint32_t)mXWindow, size, mEglIntegration->waylandDisplay()->argbVisual()); mWindow->attach(mBuffer); wl_display_sync_callback(mEglIntegration->waylandDisplay()->wl_display(), QWaylandXCompositeEGLContext::sync_function, this); mWaitingForSync = true; wl_display_sync(mEglIntegration->waylandDisplay()->wl_display(),0); mEglIntegration->waylandDisplay()->flushRequests(); while (mWaitingForSync) { mEglIntegration->waylandDisplay()->readEvents(); } }