diff options
Diffstat (limited to 'src')
-rw-r--r-- | src/actions.c | 43 | ||||
-rw-r--r-- | src/bar.c | 35 | ||||
-rw-r--r-- | src/communications.c | 2 | ||||
-rw-r--r-- | src/conf.h | 4 | ||||
-rw-r--r-- | src/events.c | 238 | ||||
-rw-r--r-- | src/list.c | 62 | ||||
-rw-r--r-- | src/list.h | 4 | ||||
-rw-r--r-- | src/manage.c | 32 | ||||
-rw-r--r-- | src/messages.h | 11 | ||||
-rw-r--r-- | src/split.c | 3 |
10 files changed, 203 insertions, 231 deletions
diff --git a/src/actions.c b/src/actions.c index 3cb5e9a..b7ca8c7 100644 --- a/src/actions.c +++ b/src/actions.c @@ -327,10 +327,6 @@ cmd_bind (int interactive, void *data) { rp_action *key_action; - /* char foo[1000]; */ - /* sprintf (foo, " %d %ld : '%s' ", key->state, key->sym, cmd); */ - /* message (foo); */ - if ((key_action = find_keybinding (key->sym, key->state))) replace_keybinding (key_action, cmd); else @@ -640,7 +636,8 @@ cmd_delete (int interactive, void *data) ev.xclient.data.l[1] = CurrentTime; status = XSendEvent(dpy, current_window()->w, False, 0, &ev); - if (status == 0) fprintf(stderr, "ratpoison: delete window failed\n"); + if (status == 0) + PRINT_DEBUG ("Delete window failed\n"); return NULL; } @@ -668,9 +665,7 @@ command (int interactive, char *data) char *result = NULL; char *cmd, *rest; char *input; - user_command *uc; - struct sbuf *buf = NULL; if (data == NULL) return NULL; @@ -697,20 +692,11 @@ command (int interactive, char *data) } } - /* couldnt find the command name */ - buf = sbuf_new (strlen(MESSAGE_UNKNOWN_COMMAND + strlen (cmd) + 4)); - sbuf_copy (buf, MESSAGE_UNKNOWN_COMMAND); - sbuf_concat (buf, "'"); - sbuf_concat (buf, cmd); - sbuf_concat (buf, "' "); - - message (sbuf_get (buf)); - - sbuf_free (buf); + marked_message_printf (0, 0, MESSAGE_UNKNOWN_COMMAND, cmd); done: free (input); - + return result; } @@ -938,19 +924,6 @@ cmd_abort (int interactive, void *data) return NULL; } -/* Send the current window the prefix key event */ -/* void */ -/* cmd_generate_prefix (void *data) */ -/* { */ -/* XEvent ev; */ -/* ev = *rp_current_event; */ - -/* ev.xkey.window = current_window()->w; */ -/* ev.xkey.state = MODIFIER_PREFIX; */ -/* XSendEvent (dpy, current_window()->w, False, KeyPressMask, &ev); */ -/* XSync (dpy, False); */ -/* } */ - /* Maximize the current window. */ char * cmd_maximize (int interactive, void *data) @@ -1020,7 +993,9 @@ cmd_escape (int interactive, void *data) char * cmd_echo (int interactive, void *data) { - if (data) message ((char *)data); + if (data) + marked_message_printf (0, 0, " %s ", (char *)data); + return NULL; } @@ -1198,13 +1173,13 @@ cmd_rudeness (int interactive, void *data) if (data == NULL) { - message ("Rudeness level required"); + message (" Rudeness level required "); return NULL; } if (sscanf ((char *)data, "%d", &num) < 1) { - message ("Bad rudeness level"); + marked_message_printf (0, 0, " Bad rudeness level: %s ", (char *)data); return NULL; } @@ -60,11 +60,12 @@ show_bar (screen_info *s) if (!s->bar_is_raised) { s->bar_is_raised = BAR_IS_WINDOW_LIST; - XMapWindow (dpy, s->bar_window); + XMapRaised (dpy, s->bar_window); update_window_names (s); /* Set an alarm to auto-hide the bar BAR_TIMEOUT seconds later */ alarm (BAR_TIMEOUT); + alarm_signalled = 0; return 1; } @@ -149,11 +150,12 @@ marked_message (char *msg, int mark_start, int mark_end) if (!s->bar_is_raised) { s->bar_is_raised = BAR_IS_MESSAGE; - XMapWindow (dpy, s->bar_window); + XMapRaised (dpy, s->bar_window); } /* Reset the alarm to auto-hide the bar in BAR_TIMEOUT seconds. */ alarm (BAR_TIMEOUT); + alarm_signalled = 0; XMoveResizeWindow (dpy, s->bar_window, bar_x (s, width), bar_y (s), @@ -168,19 +170,36 @@ marked_message (char *msg, int mark_start, int mark_end) BAR_Y_PADDING + s->font->max_bounds.ascent, msg, strlen (msg)); + + /* Crop to boundary conditions. */ + if (mark_start < 0) + mark_start = 0; + + if (mark_end < 0) + mark_end = 0; + + if (mark_start > strlen (msg)) + mark_start = strlen (msg); + + if (mark_end > strlen (msg)) + mark_end = strlen (msg); + + if (mark_start > mark_end) + { + int tmp; + tmp = mark_start; + mark_start = mark_end; + mark_end = tmp; + } + /* xor the string representing the current window */ if (mark_start != mark_end) { int start; int end; - assert (mark_start <= mark_end); /* FIXME: remove these assertions, - make it work in all cases */ - assert (mark_start <= strlen(msg) + 1); - assert (mark_end <= strlen(msg) + 1); - start = XTextWidth (s->font, msg, mark_start) + BAR_X_PADDING; - end = XTextWidth (s->font, msg + mark_start, mark_end - mark_start); + end = XTextWidth (s->font, msg + mark_start, mark_end - mark_start) + BAR_X_PADDING; PRINT_DEBUG ("%d %d strlen(%d)==> %d %d\n", mark_start, mark_end, strlen(msg), start, end); diff --git a/src/communications.c b/src/communications.c index 8b6cd66..a4f97a0 100644 --- a/src/communications.c +++ b/src/communications.c @@ -106,7 +106,7 @@ send_command (unsigned char *cmd) w = XCreateSimpleWindow (dpy, DefaultRootWindow (dpy), 0, 0, 1, 1, 0, 0, 0); - // Select first to avoid race condition + /* Select first to avoid race condition */ XSelectInput (dpy, w, PropertyChangeMask); XChangeProperty (dpy, w, rp_command, XA_STRING, @@ -41,6 +41,10 @@ /* Quit ratpoison when there are no more managed windows. */ /* #define AUTO_CLOSE */ +/* Treat windows with maxsize hints as if they were a transient window + (don't hide the windows underneath, and center them) */ +#define MAXSIZE_WINDOWS_ARE_TRANSIENTS + /* The minimum size of the input window */ #define INPUT_WINDOW_SIZE 200 diff --git a/src/events.c b/src/events.c index 2759ae8..165a45b 100644 --- a/src/events.c +++ b/src/events.c @@ -44,14 +44,18 @@ new_window (XCreateWindowEvent *e) rp_window *win; screen_info *s; - if (e->override_redirect) return; + if (e->override_redirect) + return; s = find_screen (e->parent); - win = find_window (e->window); - if (s && !win && e->window != s->key_window && e->window != s->bar_window - && e->window != s->input_window && e->window != s->frame_window && e->window != s->help_window) + if (s && win == NULL + && e->window != s->key_window + && e->window != s->bar_window + && e->window != s->input_window + && e->window != s->frame_window + && e->window != s->help_window) { win = add_to_window_list (s, e->window); update_window_information (win); @@ -61,179 +65,152 @@ new_window (XCreateWindowEvent *e) static void cleanup_frame (rp_window_frame *frame) { + rp_window *last_win; rp_window *win; win = find_window_other (); - if (win) + if (win == NULL) { - rp_window *last_win; - last_win = set_frames_window (frame, win); + set_frames_window (frame, NULL); + return; + } - maximize (win); -// unhide_transient_for (win); - unhide_window (win); + last_win = set_frames_window (frame, win); - if (!win->transient) - { - hide_others(win); - } + maximize (win); + unhide_window (win); -// if (is_transient_ancestor (last_win, win)) -// { -// hide_transient_for_between (last_win, win); -// } -// else if (last_win->transient && win->transient && -// last_win->transient_for == win->transient_for) -// { -// /* Both last_win and win have the same transient_for so we -// don't need to hide anything more */ -// } -// else -// { -// hide_transient_for (last_win); -// } - } - else - { -// hide_transient_for (frame->win); - set_frames_window (frame, NULL); - } + +#ifdef MAXSIZE_WINDOWS_ARE_TRANSIENTS + if (!win->transient + && !(win->hints->flags & PMaxSize + && win->hints->max_width < win->scr->root_attr.width + && win->hints->max_height < win->scr->root_attr.height)) +#else + if (!win->transient) +#endif + hide_others (win); } static void unmap_notify (XEvent *ev) { - screen_info *s; + rp_window_frame *frame; rp_window *win; /* ignore SubstructureNotify unmaps. */ - if(ev->xunmap.event != ev->xunmap.window - && ev->xunmap.send_event != True) return; - - s = find_screen (ev->xunmap.event); + if(ev->xunmap.event != ev->xunmap.window + && ev->xunmap.send_event != True) + return; /* FIXME: Should we only look in the mapped window list? */ win = find_window_in_list (ev->xunmap.window, rp_mapped_window_sentinel); - if (s && win) - { - rp_window_frame *frame; - - switch (win->state) - { - case IconicState: - PRINT_DEBUG ("Withdrawing iconized window '%s'\n", win->name); - if (ev->xunmap.send_event) withdraw_window (win); - break; - case NormalState: - PRINT_DEBUG ("Withdrawing normal window '%s'\n", win->name); - /* If the window was inside a frame, fill the frame with another - window. */ - frame = find_windows_frame (win); - if (frame) cleanup_frame (frame); - if (frame == rp_current_frame) set_active_frame (frame); + if (win == NULL) + return; - withdraw_window (win); - break; - } + switch (win->state) + { + case IconicState: + PRINT_DEBUG ("Withdrawing iconized window '%s'\n", win->name); + if (ev->xunmap.send_event) withdraw_window (win); + break; + case NormalState: + PRINT_DEBUG ("Withdrawing normal window '%s'\n", win->name); + /* If the window was inside a frame, fill the frame with another + window. */ + frame = find_windows_frame (win); + if (frame) cleanup_frame (frame); + if (frame == rp_current_frame) set_active_frame (frame); - update_window_names (s); + withdraw_window (win); + break; } + + update_window_names (win->scr); } static void map_request (XEvent *ev) { - screen_info *s; rp_window *win; - s = find_screen (ev->xmap.event); win = find_window (ev->xmap.window); - - if (s && win) + if (win == NULL) { - PRINT_DEBUG ("Map from a managable window\n"); + PRINT_DEBUG ("Map request from an unknown window.\n"); + XMapWindow (dpy, ev->xmap.window); + return; + } - switch (win->state) + PRINT_DEBUG ("Map request from a managed window\n"); + + switch (win->state) + { + case WithdrawnState: + if (unmanaged_window (win->w)) { - case WithdrawnState: - PRINT_DEBUG ("Unmapped window\n"); - if (unmanaged_window (win->w)) - { - PRINT_DEBUG ("Unmanaged Window\n"); - XMapWindow (dpy, win->w); - break; - } - else - { - PRINT_DEBUG ("managed Window\n"); - map_window (win); - break; - } - case NormalState: - PRINT_DEBUG ("Mapped Window\n"); - /* Its already mapped, so we don't have to do anything */ - - /* maximize (win); */ - /* XMapRaised (dpy, win->w); */ - /* set_state (win, NormalState); */ - /* set_active_window (win); */ + PRINT_DEBUG ("Mapping Unmanaged Window\n"); + XMapWindow (dpy, win->w); break; - case IconicState: - PRINT_DEBUG ("Mapped iconic window\n"); - if (win->last_access == 0) - { - /* Depending on the rudeness level, actually map the - window. */ - if ((rp_honour_transient_map && win->transient) - || (rp_honour_normal_map && !win->transient)) - set_active_window (win); - } + } + else + { + PRINT_DEBUG ("Mapping Withdrawn Window\n"); + map_window (win); + break; + } + break; + case IconicState: + PRINT_DEBUG ("Mapping Iconic window\n"); + if (win->last_access == 0) + { + /* Depending on the rudeness level, actually map the + window. */ + if ((rp_honour_transient_map && win->transient) + || (rp_honour_normal_map && !win->transient)) + set_active_window (win); + } + else + { + /* Depending on the rudeness level, actually map the + window. */ + if ((rp_honour_transient_raise && win->transient) + || (rp_honour_normal_raise && !win->transient)) + set_active_window (win); else { - /* Depending on the rudeness level, actually map the - window. */ - if ((rp_honour_transient_raise && win->transient) - || (rp_honour_normal_raise && !win->transient)) - set_active_window (win); + if (win->transient) + marked_message_printf (0, 0, MESSAGE_RAISE_TRANSIENT, + win->number, win->name); else - { - if (win->transient) - marked_message_printf (0, 0, "Raise request from transient window %d (%s)", - win->number, win->name); - else - marked_message_printf (0, 0, "Raise request from window %d (%s)", - win->number, win->name); - } + marked_message_printf (0, 0, MESSAGE_RAISE_WINDOW, + win->number, win->name); } - break; } - } - else - { - PRINT_DEBUG ("Not managed.\n"); - XMapWindow (dpy, ev->xmap.window); + break; } } static void destroy_window (XDestroyWindowEvent *ev) { + rp_window_frame *frame; rp_window *win; - ignore_badwindow++; win = find_window (ev->window); + if (win == NULL) return; - if (win) - { - rp_window_frame *frame; + ignore_badwindow++; - frame = find_windows_frame (win); - if (frame) cleanup_frame (frame); - if (frame == rp_current_frame) set_active_frame (frame); + /* A destroyed window should never have a frame, since it should + have been cleaned up with an unmap notify event, but just in + case... */ + frame = find_windows_frame (win); + if (frame) cleanup_frame (frame); + if (frame == rp_current_frame) set_active_frame (frame); - unmanage (win); - } + unmanage (win); ignore_badwindow--; } @@ -291,10 +268,10 @@ configure_request (XConfigureRequestEvent *e) else { if (win->transient) - marked_message_printf (0, 0, "Raise request from transient window %d (%s)", + marked_message_printf (0, 0, MESSAGE_RAISE_TRANSIENT, win->number, win->name); else - marked_message_printf (0, 0, "Raise request from window %d (%s)", + marked_message_printf (0, 0, MESSAGE_RAISE_WINDOW, win->number, win->name); } } @@ -426,6 +403,10 @@ handle_key (screen_info *s) if (BAR_TIMEOUT > 0) hide_bar (s); hide_frame_indicator(); + /* Disable any alarm that was going to go off. */ + alarm (0); + alarm_signalled = 0; + XGetInputFocus (dpy, &fwin, &revert); XSetInputFocus (dpy, s->key_window, RevertToPointerRoot, CurrentTime); @@ -631,6 +612,7 @@ property_notify (XEvent *ev) case XA_WM_TRANSIENT_FOR: PRINT_DEBUG ("Transient for\n"); + win->transient = XGetTransientForHint (dpy, win->w, &win->transient_for); break; default: @@ -400,6 +400,7 @@ give_window_focus (rp_window *win, rp_window *last_win) XSync (dpy, False); } +#if 0 void unhide_transient_for (rp_window *win) { @@ -438,7 +439,9 @@ unhide_transient_for (rp_window *win) unhide_transient_for (transient_for); } } +#endif +#if 0 /* Hide all transient windows for win until we get to last. */ void hide_transient_for_between (rp_window *win, rp_window *last) @@ -466,14 +469,18 @@ hide_transient_for_between (rp_window *win, rp_window *last) hide_transient_for (transient_for); } } +#endif +#if 0 void hide_transient_for (rp_window *win) { /* Hide ALL the transient windows for win. */ hide_transient_for_between (win, NULL); } +#endif +#if 0 /* return 1 if transient_for is a transient window for win or one of win's transient_for ancestors. */ int @@ -496,6 +503,7 @@ is_transient_ancestor (rp_window *win, rp_window *transient_for) return 0; } +#endif void set_active_window (rp_window *win) @@ -510,40 +518,18 @@ set_active_window (rp_window *win) PRINT_DEBUG ("new window: %s\n", win->name); /* Make sure the window comes up full screen */ -// unhide_transient_for (win); maximize (win); unhide_window (win); +#ifdef MAXSIZE_WINDOWS_ARE_TRANSIENTS + if (!win->transient + && !(win->hints->flags & PMaxSize + && win->hints->max_width < win->scr->root_attr.width + && win->hints->max_height < win->scr->root_attr.height)) +#else if (!win->transient) - { - hide_others(win); - } - -// /* Hide the last window and its transients_fors */ -// if (is_transient_ancestor (win, last_win)) -// { -// /* Do nothing if last_win is a transient since it should stay visible */ -// } -// else -// { -// hide_window (last_win); - -// if (last_win && is_transient_ancestor (last_win, win)) -// { -// /* We only need to hide the transients "between" last_win and win */ -// hide_transient_for_between (last_win, win); -// } -// else if (last_win && last_win->transient && win->transient && -// last_win->transient_for == win->transient_for) -// { -// /* Both last_win and win have the same transient_for so we -// don't need to hide anything more */ -// } -// else -// { -// hide_transient_for (last_win); -// } -// } +#endif + hide_others(win); give_window_focus (win, last_win); @@ -574,21 +560,7 @@ goto_window (rp_window *win) void print_window_information (rp_window *win) { - char number[3]; - char *str; - - snprintf (number, 3, "%d", win->number); - - /* There is a bit of extra memory being allocated from the - formatting tags in MESSAGE_WINDOW_INFORMATION, but it is not a - couple bytes. */ - str = xmalloc (strlen (number) + strlen (win->name) + strlen (MESSAGE_WINDOW_INFORMATION) + 1); - - sprintf (str, MESSAGE_WINDOW_INFORMATION, number, win->name); - message (str); - free (str); - - return; + marked_message_printf (0, 0, MESSAGE_WINDOW_INFORMATION, win->number, win->name); } /* get the window list and store it in buffer delimiting each window @@ -37,10 +37,14 @@ void give_window_focus (rp_window *win, rp_window *last_win); void set_active_window (rp_window *win); void goto_window (rp_window *win); void set_current_window (rp_window *win); + +#if 0 void unhide_transient_for (rp_window *win); void hide_transient_for (rp_window *win); void hide_transient_for_between (rp_window *win, rp_window *last); int is_transient_ancestor (rp_window *win, rp_window *transient_for); +#endif + /* int goto_window_name (char *name); */ rp_window *find_window_other (); rp_window *find_window_by_number (int n); diff --git a/src/manage.c b/src/manage.c index cbde3d2..311cf5c 100644 --- a/src/manage.c +++ b/src/manage.c @@ -188,6 +188,9 @@ update_window_information (rp_window *win) win->width = attr.width; win->height = attr.height; win->border = attr.border_width; + + /* Transient status */ + win->transient = XGetTransientForHint (dpy, win->w, &win->transient_for); } void @@ -361,7 +364,6 @@ maximize_normal (rp_window *win) { rp_window_frame *frame; int maxx, maxy; - int off_x = 0; int off_y = 0; @@ -407,8 +409,6 @@ maximize_normal (rp_window *win) amount -= delta; maxx = amount + win->width; - PRINT_DEBUG ("maxy = %d height = %d", maxy, win->height); - amount = maxy - win->height; delta = amount % win->hints->height_inc; if (amount < 0 && delta) amount -= win->hints->height_inc; @@ -417,12 +417,22 @@ maximize_normal (rp_window *win) } PRINT_DEBUG ("maxsize: %d %d\n", maxx, maxy); + +#ifdef MAXSIZE_WINDOWS_ARE_TRANSIENTS + if (win->hints->flags & PMaxSize && frame) + { + off_x = frame->x - win->width / 2 + + (frame->width - win->border * 2) / 2; + off_y = frame->y - win->height / 2 + + (frame->height - win->border * 2) / 2; + } +#endif /* Fit the window inside its frame (if it has one) */ if (frame) { - win->x = frame->x; - win->y = frame->y; + win->x = frame->x + off_x; + win->y = frame->y + off_y; } else { @@ -442,8 +452,8 @@ maximize (rp_window *win) if (!win) win = current_window(); if (!win) return; - /* Handle maximizing transient windows differently */ - if (win->transient) + /* Handle maximizing transient windows differently. */ + if (win->transient) { maximize_transient (win); } @@ -490,6 +500,10 @@ map_window (rp_window *win) remove_from_list (win); insert_into_list (win, rp_mapped_window_sentinel); + /* The window has never been accessed since it was brought back from + the Withdrawn state. */ + win->last_access = 0; + /* It is now considered iconic and set_active_window can handle the rest. */ set_state (win, IconicState); @@ -500,10 +514,10 @@ map_window (rp_window *win) else { if (win->transient) - marked_message_printf (0, 0, "New transient window %d (%s)", + marked_message_printf (0, 0, MESSAGE_MAP_TRANSIENT, win->number, win->name); else - marked_message_printf (0, 0, "New window %d (%s)", + marked_message_printf (0, 0, MESSAGE_MAP_WINDOW, win->number, win->name); } } diff --git a/src/messages.h b/src/messages.h index 23ffe3d..0d08d6d 100644 --- a/src/messages.h +++ b/src/messages.h @@ -26,8 +26,13 @@ #define MESSAGE_NO_OTHER_WINDOW " No other window " #define MESSAGE_NO_MANAGED_WINDOWS " No managed windows " -#define MESSAGE_UNKNOWN_COMMAND ": unknown command " -#define MESSAGE_WINDOW_INFORMATION "This is window %s (%s)." +#define MESSAGE_UNKNOWN_COMMAND ": unknown command '%s' " +#define MESSAGE_WINDOW_INFORMATION " This is window %d (%s) " + +#define MESSAGE_RAISE_TRANSIENT " Raise request from transient window %d (%s) " +#define MESSAGE_RAISE_WINDOW " Raise request from window %d (%s) " +#define MESSAGE_MAP_TRANSIENT " New transient window %d (%s) " +#define MESSAGE_MAP_WINDOW " New window %d (%s) " #define MESSAGE_PROMPT_SWITCH_TO_WINDOW " Switch to window: " #define MESSAGE_PROMPT_NEW_WINDOW_NAME " Set window's title to: " @@ -36,6 +41,6 @@ #define MESSAGE_PROMPT_SWITCH_WM " Switch to wm: " #define MESSAGE_PROMPT_XTERM_COMMAND MESSAGE_PROMPT_SHELL_COMMAND TERM_PROG " -e " -#define MESSAGE_WELCOME "Welcome to ratpoison! Hit C-t ? for help." +#define MESSAGE_WELCOME " Welcome to ratpoison! Hit C-t ? for help. " #endif /* ! _RATPOISON_MESSAGES_H */ diff --git a/src/split.c b/src/split.c index 36b7b91..28e4c5c 100644 --- a/src/split.c +++ b/src/split.c @@ -253,7 +253,6 @@ split_frame (rp_window_frame *frame, int way) maximize (win); unhide_window (win); -/* unhide_transient_for (win); */ XRaiseWindow (dpy, win->w); } else @@ -309,7 +308,6 @@ remove_all_splits () { if (win->frame == frame) hide_window (win); -/* hide_transient_for (cur->win); */ } } free (frame); @@ -545,7 +543,6 @@ blank_frame (rp_window_frame *frame) { if (frame->win == NULL) return; -/* hide_transient_for (frame->win); */ hide_window (frame->win); set_frames_window (frame, NULL); |