summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--server-fn.c31
-rw-r--r--server.c11
-rw-r--r--status.c130
-rw-r--r--tmux.c4
-rw-r--r--tmux.h15
-rw-r--r--window-copy.c4
6 files changed, 183 insertions, 12 deletions
diff --git a/server-fn.c b/server-fn.c
index 9893d409..526a859d 100644
--- a/server-fn.c
+++ b/server-fn.c
@@ -1,4 +1,4 @@
-/* $Id: server-fn.c,v 1.43 2008-06-19 18:27:55 nicm Exp $ */
+/* $Id: server-fn.c,v 1.44 2008-06-19 19:40:34 nicm Exp $ */
/*
* Copyright (c) 2007 Nicholas Marriott <nicm@users.sourceforge.net>
@@ -49,6 +49,35 @@ server_clear_client_message(struct client *c)
}
void
+server_set_client_prompt(
+ struct client *c, const char *msg, void (*fn)(void *, char *), void *data)
+{
+ c->prompt_string = xstrdup(msg);
+
+ c->prompt_buffer = xstrdup("");
+ c->prompt_index = 0;
+
+ c->prompt_callback = fn;
+ c->prompt_data = data;
+
+ c->flags |= CLIENT_STATUS;
+}
+
+void
+server_clear_client_prompt(struct client *c)
+{
+ if (c->prompt_string == NULL)
+ return;
+
+ xfree(c->prompt_string);
+ c->prompt_string = NULL;
+
+ xfree(c->prompt_buffer);
+
+ c->flags |= CLIENT_STATUS;
+}
+
+void
server_write_client(
struct client *c, enum hdrtype type, const void *buf, size_t len)
{
diff --git a/server.c b/server.c
index b10cf476..a7b94186 100644
--- a/server.c
+++ b/server.c
@@ -1,4 +1,4 @@
-/* $Id: server.c,v 1.69 2008-06-19 18:27:55 nicm Exp $ */
+/* $Id: server.c,v 1.70 2008-06-19 19:40:34 nicm Exp $ */
/*
* Copyright (c) 2007 Nicholas Marriott <nicm@users.sourceforge.net>
@@ -357,6 +357,8 @@ server_check_redraw(struct client *c)
if (c->flags & CLIENT_STATUS) {
if (c->message_string != NULL)
status_message_redraw(c);
+ else if (c->prompt_string != NULL)
+ status_prompt_redraw(c);
else
status_redraw(c);
}
@@ -501,7 +503,7 @@ server_accept_client(int srv_fd)
c->prompt_string = NULL;
c->prompt_buffer = NULL;
- c->prompt_size = 0;
+ c->prompt_index = 0;
for (i = 0; i < ARRAY_LENGTH(&clients); i++) {
if (ARRAY_ITEM(&clients, i) == NULL) {
@@ -523,6 +525,11 @@ server_handle_client(struct client *c)
prefix = options_get_key(&c->session->options, "prefix-key");
while (tty_keys_next(&c->tty, &key) == 0) {
server_clear_client_message(c);
+ if (c->prompt_string != NULL) {
+ status_prompt_key(c, key);
+ continue;
+ }
+
if (c->flags & CLIENT_PREFIX) {
key_bindings_dispatch(key, c);
c->flags &= ~CLIENT_PREFIX;
diff --git a/status.c b/status.c
index 20e3282c..59ca12b0 100644
--- a/status.c
+++ b/status.c
@@ -1,4 +1,4 @@
-/* $Id: status.c,v 1.31 2008-06-19 18:27:55 nicm Exp $ */
+/* $Id: status.c,v 1.32 2008-06-19 19:40:35 nicm Exp $ */
/*
* Copyright (c) 2007 Nicholas Marriott <nicm@users.sourceforge.net>
@@ -311,3 +311,131 @@ status_message_redraw(struct client *c)
/* Force cursor off. */
tty_write_client(c, TTY_CURSOROFF);
}
+
+/* Draw client prompt on status line of present else on last line. */
+void
+status_prompt_redraw(struct client *c)
+{
+ struct screen_redraw_ctx ctx;
+ size_t i, xx, yy, left, size, offset;
+
+ if (c->sx == 0 || c->sy == 0)
+ return;
+ offset = 0;
+
+ xx = strlen(c->prompt_string) + 1;
+ if (xx > c->sx)
+ xx = c->sx;
+ yy = c->sy - 1;
+
+ screen_redraw_start_client(&ctx, c);
+ screen_redraw_set_attributes(&ctx, ATTR_REVERSE, 0x88);
+
+ screen_redraw_move_cursor(&ctx, 0, yy);
+ screen_redraw_write_string(&ctx, "%.*s ", (int) xx, c->prompt_string);
+
+ left = c->sx - xx;
+ if (left != 0) {
+ if (c->prompt_index < left)
+ size = strlen(c->prompt_buffer);
+ else {
+ offset = c->prompt_index - left;
+ if (c->prompt_index == strlen(c->prompt_buffer))
+ left--;
+ size = left;
+ }
+ screen_redraw_write_string(
+ &ctx, "%.*s", (int) left, c->prompt_buffer + offset);
+
+ for (i = xx + size; i < c->sx; i++)
+ ctx.write(ctx.data, TTY_CHARACTER, ' ');
+ }
+
+ screen_redraw_stop(&ctx);
+
+ /* Force cursor on. */
+ tty_write_client(c, TTY_CURSORMOVE, yy, xx + c->prompt_index - offset);
+ tty_write_client(c, TTY_CURSORON);
+}
+
+/* Handle keys in prompt. */
+void
+status_prompt_key(struct client *c, int key)
+{
+ size_t size;
+
+ size = strlen(c->prompt_buffer);
+ switch (key) {
+ case KEYC_LEFT:
+ if (c->prompt_index > 0) {
+ c->prompt_index--;
+ c->flags |= CLIENT_STATUS;
+ }
+ break;
+ case KEYC_RIGHT:
+ if (c->prompt_index < size) {
+ c->prompt_index++;
+ c->flags |= CLIENT_STATUS;
+ }
+ break;
+ case '\001': /* C-a */
+ if (c->prompt_index != 0) {
+ c->prompt_index = 0;
+ c->flags |= CLIENT_STATUS;
+ }
+ break;
+ case '\005': /* C-e */
+ if (c->prompt_index != size) {
+ c->prompt_index = size;
+ c->flags |= CLIENT_STATUS;
+ }
+ break;
+ case '\010':
+ case '\177':
+ if (c->prompt_index != 0) {
+ if (c->prompt_index == size)
+ c->prompt_buffer[--c->prompt_index] = '\0';
+ else {
+ memmove(c->prompt_buffer + c->prompt_index - 1,
+ c->prompt_buffer + c->prompt_index,
+ size + 1 - c->prompt_index);
+ c->prompt_index--;
+ }
+ c->flags |= CLIENT_STATUS;
+ }
+ break;
+ case KEYC_DC:
+ if (c->prompt_index != size) {
+ memmove(c->prompt_buffer + c->prompt_index,
+ c->prompt_buffer + c->prompt_index + 1,
+ size + 1 - c->prompt_index);
+ c->flags |= CLIENT_STATUS;
+ }
+ break;
+ case '\r': /* enter */
+ c->prompt_callback(c->prompt_data, c->prompt_buffer);
+ server_clear_client_prompt(c);
+ break;
+ case '\e': /* escape */
+ c->prompt_callback(c->prompt_data, NULL);
+ server_clear_client_prompt(c);
+ break;
+ default:
+ if (key < 32)
+ break;
+ c->prompt_buffer = xrealloc(c->prompt_buffer, 1, size + 2);
+
+ if (c->prompt_index == size) {
+ c->prompt_buffer[c->prompt_index++] = key;
+ c->prompt_buffer[c->prompt_index] = '\0';
+ } else {
+ memmove(c->prompt_buffer + c->prompt_index + 1,
+ c->prompt_buffer + c->prompt_index,
+ size + 1 - c->prompt_index);
+ c->prompt_buffer[c->prompt_index++] = key;
+ }
+
+ c->flags |= CLIENT_STATUS;
+ break;
+ }
+}
diff --git a/tmux.c b/tmux.c
index 07a150da..eb1cb467 100644
--- a/tmux.c
+++ b/tmux.c
@@ -1,4 +1,4 @@
-/* $Id: tmux.c,v 1.61 2008-06-18 22:21:51 nicm Exp $ */
+/* $Id: tmux.c,v 1.62 2008-06-19 19:40:35 nicm Exp $ */
/*
* Copyright (c) 2007 Nicholas Marriott <nicm@users.sourceforge.net>
@@ -215,7 +215,7 @@ main(int argc, char **argv)
options_set_number(&global_options, "bell-action", BELL_ANY);
options_set_number(&global_options, "history-limit", 2000);
options_set_key(&global_options, "prefix-key", META);
- options_set_string(&global_options, "status-left", "");
+ options_set_string(&global_options, "status-left", "%s", ""); /* ugh */
options_set_string(
&global_options, "status-right", "%%H:%%M %%d-%%b-%%y");
options_set_number(&global_options, "status-interval", 15);
diff --git a/tmux.h b/tmux.h
index 83e0f643..620b02e9 100644
--- a/tmux.h
+++ b/tmux.h
@@ -1,4 +1,4 @@
-/* $Id: tmux.h,v 1.152 2008-06-19 18:27:55 nicm Exp $ */
+/* $Id: tmux.h,v 1.153 2008-06-19 19:40:35 nicm Exp $ */
/*
* Copyright (c) 2007 Nicholas Marriott <nicm@users.sourceforge.net>
@@ -681,7 +681,9 @@ struct client {
char *prompt_string;
char *prompt_buffer;
- size_t prompt_size;
+ size_t prompt_index;
+ void (*prompt_callback)(void *, char *);
+ void *prompt_data;
struct session *session;
};
@@ -957,6 +959,9 @@ int server_msg_dispatch(struct client *);
/* server-fn.c */
void server_set_client_message(struct client *, const char *);
void server_clear_client_message(struct client *);
+void server_set_client_prompt(
+ struct client *, const char *, void (*)(void *, char *), void *);
+void server_clear_client_prompt(struct client *);
struct session *server_extract_session(
struct msg_command_data *, char *, char **);
void server_write_client(
@@ -974,8 +979,10 @@ void server_status_window(struct window *);
void printflike2 server_write_message(struct client *, const char *, ...);
/* status.c */
-void status_redraw(struct client *c);
-void status_message_redraw(struct client *c);
+void status_redraw(struct client *);
+void status_message_redraw(struct client *);
+void status_prompt_redraw(struct client *);
+void status_prompt_key(struct client *, int);
/* resize.c */
void recalculate_sizes(void);
diff --git a/window-copy.c b/window-copy.c
index 8cf3e053..2115f10f 100644
--- a/window-copy.c
+++ b/window-copy.c
@@ -1,4 +1,4 @@
-/* $Id: window-copy.c,v 1.18 2008-06-18 22:21:51 nicm Exp $ */
+/* $Id: window-copy.c,v 1.19 2008-06-19 19:40:35 nicm Exp $ */
/*
* Copyright (c) 2007 Nicholas Marriott <nicm@users.sourceforge.net>
@@ -180,7 +180,7 @@ window_copy_key(struct window *w, int key)
screen_clear_selection(&data->screen);
break;
case '\027': /* C-w */
- case '\r': /* enter */
+ case '\r': /* enter */
window_copy_copy_selection(w);
window_reset_mode(w);
break;