X-Git-Url: https://git.dogcows.com/gitweb?a=blobdiff_plain;f=openbox%2Fclient.c;h=e58cc753733078743560748dcc0c7399e545aa73;hb=97792a403a52c12c2601a7b2caebdea197f0b5f0;hp=fed902fc0b59548161abc082422e6a360ceea26d;hpb=de2ba8f28b85422e645c94cfdf5791cce3321264;p=chaz%2Fopenbox diff --git a/openbox/client.c b/openbox/client.c index fed902fc..e58cc753 100644 --- a/openbox/client.c +++ b/openbox/client.c @@ -88,7 +88,8 @@ static void client_update_transient_tree(ObClient *self, gboolean oldgtran, gboolean newgtran, ObClient* oldparent, ObClient *newparent); -static void client_present(ObClient *self, gboolean here, gboolean raise); +static void client_present(ObClient *self, gboolean here, gboolean raise, + gboolean unshade); static GSList *client_search_all_top_parents_internal(ObClient *self, gboolean bylayer, ObStackingLayer layer); @@ -394,7 +395,7 @@ void client_manage(Window window) */ if (ob_state() == OB_STATE_RUNNING && (transient || - (!(self->sized & USSize) && + (!(self->sized & USSize || self->positioned & USPosition) && client_normal(self) && !self->session))) { @@ -544,7 +545,7 @@ void client_manage(Window window) if (activate) { gboolean stacked = client_restore_session_stacking(self); - client_present(self, FALSE, !stacked); + client_present(self, FALSE, !stacked, TRUE); } /* add to client list/map */ @@ -932,7 +933,7 @@ gboolean client_find_onscreen(ObClient *self, gint *x, gint *y, gint w, gint h, frame_rect_to_frame(self->frame, &desired); /* get where the frame would be */ - frame_client_gravity(self->frame, x, y, w, h); + frame_client_gravity(self->frame, x, y); /* get the requested size of the window with decorations */ fw = self->frame->size.left + w + self->frame->size.right; @@ -1020,7 +1021,7 @@ gboolean client_find_onscreen(ObClient *self, gint *x, gint *y, gint w, gint h, } /* get where the client should be */ - frame_frame_gravity(self->frame, x, y, w, h); + frame_frame_gravity(self->frame, x, y); return ox != *x || oy != *y; } @@ -2084,8 +2085,11 @@ void client_update_icons(ObClient *self) /* set the default icon onto the window in theory, this could be a race, but if a window doesn't set an icon or removes it entirely, it's not very likely it is going to set one - right away afterwards */ - if (self->nicons == 0) { + right away afterwards + + if it has parents, then one of them will have an icon already + */ + if (self->nicons == 0 && !self->parents) { RrPixel32 *icon = ob_rr_theme->def_win_icon; gulong *data; @@ -2509,7 +2513,6 @@ gboolean client_hide(ObClient *self) frame_hide(self->frame); hide = TRUE; - ob_debug("hiding client %s\n", self->title); /* According to the ICCCM (sec 4.1.3.1) when a window is not visible, it needs to be in IconicState. This includes when it is on another @@ -2610,11 +2613,18 @@ static void client_apply_startup_state(ObClient *self, else if (max_horz) client_maximize(self, TRUE, 1); - /* if the window hasn't been configured yet, then do so now */ - if (!fullscreen && !max_vert && !max_horz) { - self->area = oldarea; - client_configure(self, x, y, w, h, FALSE, TRUE, FALSE); - } + /* if the window hasn't been configured yet, then do so now, in fact the + x,y,w,h may _not_ be the same as the area rect, which can end up + meaning that the client isn't properly moved/resized by the fullscreen + function + pho can cause this because it maps at size of the screen but not 0,0 + so openbox moves it on screen to 0,0 (thus x,y=0,0 and area.x,y don't). + then fullscreen'ing makes it go to 0,0 which it thinks it already is at + cuz thats where the pre-fullscreen will be. however the actual area is + not, so this needs to be called even if we have fullscreened/maxed + */ + self->area = oldarea; + client_configure(self, x, y, w, h, FALSE, TRUE, FALSE); /* set the desktop hint, to make sure that it always exists */ PROP_SET32(self->window, net_wm_desktop, cardinal, self->desktop); @@ -2699,7 +2709,7 @@ void client_try_configure(ObClient *self, gint *x, gint *y, gint *w, gint *h, frame_adjust_area(self->frame, FALSE, TRUE, TRUE); /* gets the frame's position */ - frame_client_gravity(self->frame, x, y, *w, *h); + frame_client_gravity(self->frame, x, y); /* these positions are frame positions, not client positions */ @@ -2746,7 +2756,7 @@ void client_try_configure(ObClient *self, gint *x, gint *y, gint *w, gint *h, } /* gets the client's position */ - frame_frame_gravity(self->frame, x, y, *w, *h); + frame_frame_gravity(self->frame, x, y); /* work within the prefered sizes given by the window */ if (!(*w == self->area.width && *h == self->area.height)) { @@ -3026,6 +3036,9 @@ void client_fullscreen(ObClient *self, gboolean fs) RECT_SET(self->pre_fullscreen_area, 0, 0, 0, 0); } + ob_debug("Window %s going fullscreen (%d)\n", + self->title, self->fullscreen); + client_setup_decor_and_functions(self, FALSE); client_move_resize(self, x, y, w, h); @@ -3261,7 +3274,8 @@ void client_set_desktop_recursive(ObClient *self, frame_adjust_state(self->frame); /* 'move' the window to the new desktop */ if (!donthide) - client_showhide(self); + client_hide(self); + client_show(self); /* raise if it was not already on the desktop */ if (old != DESKTOP_ALL && !dontraise) stacking_raise(CLIENT_AS_WINDOW(self)); @@ -3558,6 +3572,10 @@ gboolean client_focus(ObClient *self) "Focusing client \"%s\" (0x%x) at time %u\n", self->title, self->window, event_curtime); + /* if using focus_delay, stop the timer now so that focus doesn't + go moving on us */ + event_halt_focus_delay(); + /* if there is a grab going on, then we need to cancel it. if we move focus during the grab, applications will get NotifyWhileGrabbed events and ignore them ! @@ -3598,17 +3616,9 @@ gboolean client_focus(ObClient *self) return !xerror_occured; } -/*! Present the client to the user. - @param raise If the client should be raised or not. You should only set - raise to false if you don't care if the window is completely - hidden. -*/ -static void client_present(ObClient *self, gboolean here, gboolean raise) +static void client_present(ObClient *self, gboolean here, gboolean raise, + gboolean unshade) { - /* if using focus_delay, stop the timer now so that focus doesn't - go moving on us */ - event_halt_focus_delay(); - if (client_normal(self) && screen_showing_desktop) screen_show_desktop(FALSE, self); if (self->iconic) @@ -3624,7 +3634,7 @@ static void client_present(ObClient *self, gboolean here, gboolean raise) /* if its not visible for other reasons, then don't mess with it */ return; - if (self->shaded) + if (self->shaded && unshade) client_shade(self, FALSE); if (raise) stacking_raise(CLIENT_AS_WINDOW(self)); @@ -3632,7 +3642,8 @@ static void client_present(ObClient *self, gboolean here, gboolean raise) client_focus(self); } -void client_activate(ObClient *self, gboolean here, gboolean user) +void client_activate(ObClient *self, gboolean here, gboolean raise, + gboolean unshade, gboolean user) { guint32 last_time = focus_client ? focus_client->user_time : CurrentTime; gboolean allow = FALSE; @@ -3658,7 +3669,7 @@ void client_activate(ObClient *self, gboolean here, gboolean user) (user ? "user" : "application"), allow); if (allow) - client_present(self, here, TRUE); + client_present(self, here, raise, unshade); else /* don't focus it but tell the user it wants attention */ client_hilite(self, TRUE); @@ -4080,3 +4091,30 @@ gboolean client_has_group_siblings(ObClient *self) { return self->group && self->group->members->next; } + +ObClientIcon *client_thumbnail(ObClient *self, gint wantw, gint wanth) +{ + ObClientIcon *ret; + RrPixel32 *data; + gint w, h; + + if (!self->frame->pixmap) return NULL; + if (!RrPixmapToRGBA(ob_rr_inst, self->frame->pixmap, None, &w, &h, &data)) + return NULL; + + /* resize the thumbnail (within aspect ratio) to the given sizes */ + + ret = g_new(ObClientIcon, 1); + ret->data = data; + ret->width = w; + ret->height = h; + return ret; +} + +void clienticon_free(ObClientIcon *ci) +{ + if (ci) { + g_free(ci->data); + g_free(ci); + } +}