void map_client(client_t *c) { XWindowAttributes attr; strut_t s = { 0, 0, 0, 0 }; XWMHints *hints; int btn, want_raise = 1; XGrabServer(dpy); XGetWindowAttributes(dpy, c->win, &attr); collect_struts(c, &s); if (attr.map_state == IsViewable) { c->ignore_unmap++; reparent(c, &s); if (get_wm_state(c->win) == IconicState) { c->ignore_unmap++; XUnmapWindow(dpy, c->win); } else { set_wm_state(c, NormalState); do_map(c, want_raise); } } else { if ((hints = XGetWMHints(dpy, c->win))) { if (hints->flags & StateHint) set_wm_state(c, hints->initial_state); XFree(hints); } else { set_wm_state(c, NormalState); } if (!init_geom(c, &s) && opt_imap) { btn = sweep(c, map_curs, recalc_map, SWEEP_DOWN, &s); if (btn == Button2) btn = sweep(c, resize_curs, recalc_resize, SWEEP_UP, &s); if (btn == Button3) want_raise = 0; } #ifdef DEBUG dump_geom(c, "set to"); dump_info(c); #endif reparent(c, &s); if (get_wm_state(c->win) == NormalState) do_map(c, want_raise); } XSync(dpy, False); c->name = get_wm_name(c->win); // horrible kludge XUngrabServer(dpy); }
void snprint_wm_name(char *buf, size_t len, Window w) { char *n; if ((n = get_wm_name(w))) { if (get_wm_state(w) == NormalState) { if (snprintf(buf, len, "%s", n) > len) strcpy(buf+len-4, "..."); } else { if (snprintf(buf, len, "[%s]", n) > len) strcpy(buf+len-5, "...]"); } XFree(n); } else { snprintf(buf, len, "%#lx", w); } }
client_t *new_client(Window w) { client_t *c; XWindowAttributes attr; XColor exact; long supplied; Atom win_type; c = malloc(sizeof *c); c->next = head; head = c; c->name = get_wm_name(w); c->win = w; c->frame = None; c->size.flags = 0; c->ignore_unmap = 0; #ifdef SHAPE c->shaped = 0; #endif c->shaded = 0; c->zoomed = 0; c->decor = 1; XGetWMNormalHints(dpy, c->win, &c->size, &supplied); XGetTransientForHint(dpy, c->win, &c->trans); XGetWindowAttributes(dpy, c->win, &attr); c->geom.x = attr.x; c->geom.y = attr.y; c->geom.w = attr.width; c->geom.h = attr.height; c->cmap = attr.colormap; c->old_bw = attr.border_width; #ifdef DEBUG dump_name(c, "creating", 'w'); dump_geom(c, "initial"); #endif XAllocNamedColor(dpy, c->cmap, opt_fg, &fg, &exact); XAllocNamedColor(dpy, c->cmap, opt_bg, &bg, &exact); XAllocNamedColor(dpy, c->cmap, opt_bd, &bd, &exact); if (get_atoms(c->win, net_wm_wintype, XA_ATOM, 0, &win_type, 1, NULL)) c->decor = HAS_DECOR(win_type); if (get_atoms(c->win, net_wm_desk, XA_CARDINAL, 0, &c->desk, 1, NULL)) { if (c->desk == -1) c->desk = DESK_ALL; /* FIXME */ if (c->desk >= ndesks && c->desk != DESK_ALL) c->desk = cur_desk; } else { set_atoms(c->win, net_wm_desk, XA_CARDINAL, &cur_desk, 1); c->desk = cur_desk; } #ifdef DEBUG dump_info(c); #endif check_states(c); /* We are not actually keeping the stack one in order. However, every * fancy panel uses it and nothing else, no matter what the spec says. * (I'm not sure why, as rearranging the list every time the stacking * changes would be distracting. GNOME's window list applet doesn't.) */ append_atoms(root, net_client_list, XA_WINDOW, &c->win, 1); append_atoms(root, net_client_stack, XA_WINDOW, &c->win, 1); return c; }
void Frame::init() { maximized = false; set_state(1); state = "WithdrawnState"; shaped = false; XSelectInput(QX11Info::display(), winId(), KeyPressMask | KeyReleaseMask | ButtonPressMask | ButtonReleaseMask | KeymapStateMask | ButtonMotionMask | PointerMotionMask | EnterWindowMask | LeaveWindowMask | FocusChangeMask | VisibilityChangeMask | ExposureMask | StructureNotifyMask | SubstructureRedirectMask | SubstructureNotifyMask); XSetWindowAttributes at; at.event_mask = ColormapChangeMask|PropertyChangeMask; XChangeWindowAttributes(QX11Info::display(), c_win, CWEventMask, &at); XGrabServer(QX11Info::display()); // get the client geometry get_client_geometry(); // get the client hints get_wm_hints(); // get the client normal hints get_wm_normal_hints(); // get the client prot get_wm_protocols(); // get the client icon to show on header get_icon(); // get the client name get_wm_name(); // set the frame geometry set_frame_geometry(); // set the window modality set_window_modality(); shaped = query_shape(); if (shaped) reshape(); XSetWindowBorderWidth(QX11Info::display(), c_win, 0); //client XSetWindowBorderWidth(QX11Info::display(), winId(), 0); //frame // *** THE MOST IMPORTANT FUNCTION *** // reparent client with frame XReparentWindow(QX11Info::display(), c_win, winId(), lateral_bdr_width, top_bdr_height); qDebug() << "+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++"; qDebug() << "Reparent Client:" << c_win << "with Frame:" << winId() << "- Name:" << cl_name(); qDebug() << "+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++"; XAddToSaveSet(QX11Info::display(), c_win); // move and resize client XMoveResizeWindow(QX11Info::display(), c_win, lateral_bdr_width, top_bdr_height+3, client_w, client_h); //if the frame is too large, maximize it if (frame_w >= QApplication::desktop()->width()-20 || frame_h >= QApplication::desktop()->height()-40) { maximize_it(); } else // normal size { // move the frame in desktop center and resize move((QApplication::desktop()->width()/2)-(frame_w/2), (QApplication::desktop()->height()/2)-(frame_h/2)); resize(frame_w, frame_h); } qDebug() << "+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++"; qDebug() << "Frame_x:" << frame_x << "Frame_y:" << frame_y << "Frame_w:" << frame_w << "Frame_h:" << frame_h; qDebug() << "+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++" << "\n"; if (frame_type != "Splash") // Splash frame have no header and no border { // create frame borders/header create_borders(); // set the header pixmap set_inactive(); splash = false; } else { qDebug() << "Frame:" << winId() << "Name:" << wm_name << "is Splash type"; splash = true; } // send _NET_ACTIVE_WINDOW property Atom _net_active_window = XInternAtom(QX11Info::display(), "_NET_ACTIVE_WINDOW", False); XClientMessageEvent xev; xev.type = ClientMessage; xev.window = c_win; xev.message_type = _net_active_window; xev.format = 32; xev.data.l[0] = 1; // from application xev.data.l[1] = CurrentTime; xev.data.l[2] = 0; XSendEvent(QX11Info::display(), QApplication::desktop()->winId(), False, StructureNotifyMask, (XEvent *)&xev); // map client XMapWindow(QX11Info::display(), c_win); XSync(QX11Info::display(), false); XUngrabServer(QX11Info::display()); // show frame show(); }