mirror of
https://github.com/tmux/tmux.git
synced 2024-11-17 18:08:51 +00:00
Merge branch 'master' into sixel
This commit is contained in:
commit
742c063473
40
CHANGES
40
CHANGES
@ -1,5 +1,45 @@
|
||||
CHANGES FROM 3.2a TO 3.3
|
||||
|
||||
* Add an option (pane-border-indicators) to select how the active pane is shown
|
||||
on the pane border (colour, arrows or both).
|
||||
|
||||
* Support underscore styles with capture-pane -e.
|
||||
|
||||
* Make pane-border-format a pane option rather than window.
|
||||
|
||||
* Respond to OSC 4 queries
|
||||
|
||||
* Fix g/G keys in modes to do the same thing as copy mode (and vi).
|
||||
|
||||
* Bump the time terminals have to respond to device attributes queries to three
|
||||
seconds.
|
||||
|
||||
* If automatic-rename is off, allow the rename escape sequence to set an empty
|
||||
name.
|
||||
|
||||
* Trim menu item text more intelligently.
|
||||
|
||||
* Add cursor-style and cursor-colour options to set the default cursor style
|
||||
and colour.
|
||||
|
||||
* Accept some useful and non-conflicting emacs keys in vi normal mode at the
|
||||
command prompt.
|
||||
|
||||
* Add a format modifier (c) to force a colour to RGB.
|
||||
|
||||
* Add -s and -S to display-popup to set styles, -b to set lines and -T to set
|
||||
popup title. New popup-border-lines, popup-border-style and popup-style
|
||||
options set the defaults.
|
||||
|
||||
* Add -e flag to set an environment variable for a popup.
|
||||
|
||||
* Make send-keys without arguments send the key it is bound to (if bound to a
|
||||
key).
|
||||
|
||||
* Try to leave terminal cursor at the right position even when tmux is drawing
|
||||
its own cursor or selection (such as at the command prompt and in choose
|
||||
mode) for people using screen readers and similar which can make use of it.
|
||||
|
||||
* Change so that {} is converted to tmux commands immediately when parsed. This
|
||||
means it must contain valid tmux commands. For commands which expand %% and
|
||||
%%%, this now only happens within string arguments. Use of nested aliases
|
||||
|
@ -206,6 +206,11 @@ if NEED_FORKPTY
|
||||
nodist_tmux_SOURCES += compat/forkpty-@PLATFORM@.c
|
||||
endif
|
||||
|
||||
# Add compat file for systemd.
|
||||
if HAVE_SYSTEMD
|
||||
nodist_tmux_SOURCES += compat/systemd.c
|
||||
endif
|
||||
|
||||
# Add compat file for utf8proc.
|
||||
if HAVE_UTF8PROC
|
||||
nodist_tmux_SOURCES += compat/utf8proc.c
|
||||
|
16
arguments.c
16
arguments.c
@ -131,8 +131,9 @@ args_parse(const struct args_parse *parse, struct args_value *values,
|
||||
u_int i;
|
||||
enum args_parse_type type;
|
||||
struct args_value *value, *new;
|
||||
u_char flag, argument;
|
||||
u_char flag;
|
||||
const char *found, *string, *s;
|
||||
int optional_argument;
|
||||
|
||||
if (count == 0)
|
||||
return (args_create());
|
||||
@ -169,18 +170,27 @@ args_parse(const struct args_parse *parse, struct args_value *values,
|
||||
args_free(args);
|
||||
return (NULL);
|
||||
}
|
||||
argument = *++found;
|
||||
if (argument != ':') {
|
||||
if (*++found != ':') {
|
||||
log_debug("%s: -%c", __func__, flag);
|
||||
args_set(args, flag, NULL);
|
||||
continue;
|
||||
}
|
||||
if (*found == ':') {
|
||||
optional_argument = 1;
|
||||
found++;
|
||||
}
|
||||
new = xcalloc(1, sizeof *new);
|
||||
if (*string != '\0') {
|
||||
new->type = ARGS_STRING;
|
||||
new->string = xstrdup(string);
|
||||
} else {
|
||||
if (i == count) {
|
||||
if (optional_argument) {
|
||||
log_debug("%s: -%c", __func__,
|
||||
flag);
|
||||
args_set(args, flag, NULL);
|
||||
continue;
|
||||
}
|
||||
xasprintf(cause,
|
||||
"-%c expects an argument",
|
||||
flag);
|
||||
|
2
client.c
2
client.c
@ -531,7 +531,7 @@ client_signal(int sig)
|
||||
if (sig == SIGCHLD)
|
||||
waitpid(WAIT_ANY, &status, WNOHANG);
|
||||
else if (!client_attached) {
|
||||
if (sig == SIGTERM)
|
||||
if (sig == SIGTERM || sig == SIGHUP)
|
||||
proc_exit(client_proc);
|
||||
} else {
|
||||
switch (sig) {
|
||||
|
@ -31,6 +31,8 @@
|
||||
#define LIST_CLIENTS_TEMPLATE \
|
||||
"#{client_name}: #{session_name} " \
|
||||
"[#{client_width}x#{client_height} #{client_termname}] " \
|
||||
"#{?#{!=:#{client_uid},#{uid}}," \
|
||||
"[user #{?client_user,#{client_user},#{client_uid},}] ,}" \
|
||||
"#{?client_flags,(,}#{client_flags}#{?client_flags,),}"
|
||||
|
||||
static enum cmd_retval cmd_list_clients_exec(struct cmd *, struct cmdq_item *);
|
||||
|
@ -34,7 +34,7 @@ const struct cmd_entry cmd_refresh_client_entry = {
|
||||
.name = "refresh-client",
|
||||
.alias = "refresh",
|
||||
|
||||
.args = { "A:B:cC:Df:F:lLRSt:U", 0, 1, NULL },
|
||||
.args = { "A:B:cC:Df:F:l::LRSt:U", 0, 1, NULL },
|
||||
.usage = "[-cDlLRSU] [-A pane:state] [-B name:what:format] "
|
||||
"[-C XxY] [-f flags] " CMD_TARGET_CLIENT_USAGE " [adjustment]",
|
||||
|
||||
@ -162,6 +162,37 @@ out:
|
||||
free(copy);
|
||||
}
|
||||
|
||||
static enum cmd_retval
|
||||
cmd_refresh_client_clipboard(struct cmd *self, struct cmdq_item *item)
|
||||
{
|
||||
struct args *args = cmd_get_args(self);
|
||||
struct client *tc = cmdq_get_target_client(item);
|
||||
const char *p;
|
||||
u_int i;
|
||||
struct cmd_find_state fs;
|
||||
|
||||
p = args_get(args, 'l');
|
||||
if (p == NULL) {
|
||||
if (tc->flags & CLIENT_CLIPBOARDBUFFER)
|
||||
return (CMD_RETURN_NORMAL);
|
||||
tc->flags |= CLIENT_CLIPBOARDBUFFER;
|
||||
} else {
|
||||
if (cmd_find_target(&fs, item, p, CMD_FIND_PANE, 0) != 0)
|
||||
return (CMD_RETURN_ERROR);
|
||||
for (i = 0; i < tc->clipboard_npanes; i++) {
|
||||
if (tc->clipboard_panes[i] == fs.wp->id)
|
||||
break;
|
||||
}
|
||||
if (i != tc->clipboard_npanes)
|
||||
return (CMD_RETURN_NORMAL);
|
||||
tc->clipboard_panes = xreallocarray (tc->clipboard_panes,
|
||||
tc->clipboard_npanes + 1, sizeof *tc->clipboard_panes);
|
||||
tc->clipboard_panes[tc->clipboard_npanes++] = fs.wp->id;
|
||||
}
|
||||
tty_clipboard_query(&tc->tty);
|
||||
return (CMD_RETURN_NORMAL);
|
||||
}
|
||||
|
||||
static enum cmd_retval
|
||||
cmd_refresh_client_exec(struct cmd *self, struct cmdq_item *item)
|
||||
{
|
||||
@ -224,10 +255,8 @@ cmd_refresh_client_exec(struct cmd *self, struct cmdq_item *item)
|
||||
return (CMD_RETURN_NORMAL);
|
||||
}
|
||||
|
||||
if (args_has(args, 'l')) {
|
||||
tty_putcode_ptr2(&tc->tty, TTYC_MS, "", "?");
|
||||
return (CMD_RETURN_NORMAL);
|
||||
}
|
||||
if (args_has(args, 'l'))
|
||||
return (cmd_refresh_client_clipboard(self, item));
|
||||
|
||||
if (args_has(args, 'F')) /* -F is an alias for -f */
|
||||
server_client_set_flags(tc, args_get(args, 'F'));
|
||||
|
@ -60,7 +60,7 @@ cmd_resize_pane_exec(struct cmd *self, struct cmdq_item *item)
|
||||
const char *errstr;
|
||||
char *cause;
|
||||
u_int adjust;
|
||||
int x, y;
|
||||
int x, y, status;
|
||||
struct grid *gd = wp->base.grid;
|
||||
|
||||
if (args_has(args, 'T')) {
|
||||
@ -121,6 +121,17 @@ cmd_resize_pane_exec(struct cmd *self, struct cmdq_item *item)
|
||||
free(cause);
|
||||
return (CMD_RETURN_ERROR);
|
||||
}
|
||||
status = options_get_number(w->options, "pane-border-status");
|
||||
switch (status) {
|
||||
case PANE_STATUS_TOP:
|
||||
if (y != INT_MAX && wp->yoff == 1)
|
||||
y++;
|
||||
break;
|
||||
case PANE_STATUS_BOTTOM:
|
||||
if (y != INT_MAX && wp->yoff + wp->sy == w->sy - 1)
|
||||
y++;
|
||||
break;
|
||||
}
|
||||
layout_resize_pane_to(wp, LAYOUT_TOPBOTTOM, y);
|
||||
}
|
||||
|
||||
|
@ -102,7 +102,7 @@ cmd_show_options_exec(struct cmd *self, struct cmdq_item *item)
|
||||
name = options_match(argument, &idx, &ambiguous);
|
||||
if (name == NULL) {
|
||||
if (args_has(args, 'q'))
|
||||
goto fail;
|
||||
goto out;
|
||||
if (ambiguous)
|
||||
cmdq_error(item, "ambiguous option: %s", argument);
|
||||
else
|
||||
@ -113,7 +113,7 @@ cmd_show_options_exec(struct cmd *self, struct cmdq_item *item)
|
||||
&cause);
|
||||
if (scope == OPTIONS_TABLE_NONE) {
|
||||
if (args_has(args, 'q'))
|
||||
goto fail;
|
||||
goto out;
|
||||
cmdq_error(item, "%s", cause);
|
||||
free(cause);
|
||||
goto fail;
|
||||
@ -128,11 +128,12 @@ cmd_show_options_exec(struct cmd *self, struct cmdq_item *item)
|
||||
cmd_show_options_print(self, item, o, idx, parent);
|
||||
else if (*name == '@') {
|
||||
if (args_has(args, 'q'))
|
||||
goto fail;
|
||||
goto out;
|
||||
cmdq_error(item, "invalid option: %s", argument);
|
||||
goto fail;
|
||||
}
|
||||
|
||||
out:
|
||||
free(name);
|
||||
free(argument);
|
||||
return (CMD_RETURN_NORMAL);
|
||||
|
@ -60,6 +60,7 @@ cmd_split_window_exec(struct cmd *self, struct cmdq_item *item)
|
||||
struct client *tc = cmdq_get_target_client(item);
|
||||
struct session *s = target->s;
|
||||
struct winlink *wl = target->wl;
|
||||
struct window *w = wl->window;
|
||||
struct window_pane *wp = target->wp, *new_wp;
|
||||
enum layout_type type;
|
||||
struct layout_cell *lc;
|
||||
@ -86,10 +87,17 @@ cmd_split_window_exec(struct cmd *self, struct cmdq_item *item)
|
||||
cmdq_error(item, "percentage %s", errstr);
|
||||
return (CMD_RETURN_ERROR);
|
||||
}
|
||||
if (type == LAYOUT_TOPBOTTOM)
|
||||
size = (wp->sy * percentage) / 100;
|
||||
else
|
||||
size = (wp->sx * percentage) / 100;
|
||||
if (args_has(args, 'f')) {
|
||||
if (type == LAYOUT_TOPBOTTOM)
|
||||
size = (w->sy * percentage) / 100;
|
||||
else
|
||||
size = (w->sx * percentage) / 100;
|
||||
} else {
|
||||
if (type == LAYOUT_TOPBOTTOM)
|
||||
size = (wp->sy * percentage) / 100;
|
||||
else
|
||||
size = (wp->sx * percentage) / 100;
|
||||
}
|
||||
} else {
|
||||
size = args_strtonum(args, 'l', 0, INT_MAX, &cause);
|
||||
if (cause != NULL) {
|
||||
@ -105,10 +113,17 @@ cmd_split_window_exec(struct cmd *self, struct cmdq_item *item)
|
||||
free(cause);
|
||||
return (CMD_RETURN_ERROR);
|
||||
}
|
||||
if (type == LAYOUT_TOPBOTTOM)
|
||||
size = (wp->sy * percentage) / 100;
|
||||
else
|
||||
size = (wp->sx * percentage) / 100;
|
||||
if (args_has(args, 'f')) {
|
||||
if (type == LAYOUT_TOPBOTTOM)
|
||||
size = (w->sy * percentage) / 100;
|
||||
else
|
||||
size = (w->sx * percentage) / 100;
|
||||
} else {
|
||||
if (type == LAYOUT_TOPBOTTOM)
|
||||
size = (wp->sy * percentage) / 100;
|
||||
else
|
||||
size = (wp->sx * percentage) / 100;
|
||||
}
|
||||
} else
|
||||
size = -1;
|
||||
|
||||
|
2
colour.c
2
colour.c
@ -128,7 +128,7 @@ colour_tostring(int c)
|
||||
u_char r, g, b;
|
||||
|
||||
if (c == -1)
|
||||
return ("invalid");
|
||||
return ("none");
|
||||
|
||||
if (c & COLOUR_FLAG_RGB) {
|
||||
colour_split_rgb(c, &r, &g, &b);
|
||||
|
10
compat.h
10
compat.h
@ -334,6 +334,11 @@ char *strndup(const char *, size_t);
|
||||
void *memmem(const void *, size_t, const void *, size_t);
|
||||
#endif
|
||||
|
||||
#ifndef HAVE_GETPEEREID
|
||||
/* getpeereid.c */
|
||||
int getpeereid(int, uid_t *, gid_t *);
|
||||
#endif
|
||||
|
||||
#ifndef HAVE_DAEMON
|
||||
/* daemon.c */
|
||||
int daemon(int, int);
|
||||
@ -416,6 +421,11 @@ void *reallocarray(void *, size_t, size_t);
|
||||
void *recallocarray(void *, size_t, size_t, size_t);
|
||||
#endif
|
||||
|
||||
#ifdef HAVE_SYSTEMD
|
||||
/* systemd.c */
|
||||
int systemd_create_socket(int, char **);
|
||||
#endif
|
||||
|
||||
#ifdef HAVE_UTF8PROC
|
||||
/* utf8proc.c */
|
||||
int utf8proc_wcwidth(wchar_t);
|
||||
|
59
compat/getpeereid.c
Normal file
59
compat/getpeereid.c
Normal file
@ -0,0 +1,59 @@
|
||||
/*
|
||||
* Copyright (c) 2022 Nicholas Marriott <nicholas.marriott@gmail.com>
|
||||
*
|
||||
* Permission to use, copy, modify, and distribute this software for any
|
||||
* purpose with or without fee is hereby granted, provided that the above
|
||||
* copyright notice and this permission notice appear in all copies.
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
|
||||
* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
|
||||
* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
|
||||
* ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
|
||||
* WHATSOEVER RESULTING FROM LOSS OF MIND, USE, DATA OR PROFITS, WHETHER
|
||||
* IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING
|
||||
* OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
|
||||
*/
|
||||
|
||||
#include <sys/types.h>
|
||||
#include <sys/socket.h>
|
||||
|
||||
#include <stdio.h>
|
||||
|
||||
#ifdef HAVE_UCRED_H
|
||||
#include <ucred.h>
|
||||
#endif
|
||||
|
||||
#include "compat.h"
|
||||
|
||||
int
|
||||
getpeereid(int s, uid_t *uid, gid_t *gid)
|
||||
{
|
||||
#ifdef HAVE_SO_PEERCRED
|
||||
struct ucred uc;
|
||||
int len = sizeof uc;
|
||||
|
||||
if (getsockopt(s, SOL_SOCKET, SO_PEERCRED, &uc, &len) == -1)
|
||||
return (-1);
|
||||
*uid = uc.uid;
|
||||
*gid = uc.gid;
|
||||
return (0);
|
||||
#elif defined(HAVE_GETPEERUCRED)
|
||||
int
|
||||
getpeereid(int s, uid_t *uid, gid_t *gid)
|
||||
{
|
||||
ucred_t *ucred = NULL;
|
||||
|
||||
if (getpeerucred(s, &ucred) == -1)
|
||||
return (-1);
|
||||
if ((*uid = ucred_geteuid(ucred)) == -1)
|
||||
return (-1);
|
||||
if ((*gid = ucred_getrgid(ucred)) == -1)
|
||||
return (-1);
|
||||
ucred_free(ucred);
|
||||
return (0);
|
||||
}
|
||||
#else
|
||||
errno = EOPNOTSUPP;
|
||||
return (-1);
|
||||
#endif
|
||||
}
|
58
compat/systemd.c
Normal file
58
compat/systemd.c
Normal file
@ -0,0 +1,58 @@
|
||||
/* $OpenBSD$ */
|
||||
|
||||
/*
|
||||
* Copyright (c) 2022 Nicholas Marriott <nicholas.marriott@gmail.com>
|
||||
*
|
||||
* Permission to use, copy, modify, and distribute this software for any
|
||||
* purpose with or without fee is hereby granted, provided that the above
|
||||
* copyright notice and this permission notice appear in all copies.
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
|
||||
* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
|
||||
* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
|
||||
* ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
|
||||
* WHATSOEVER RESULTING FROM LOSS OF MIND, USE, DATA OR PROFITS, WHETHER
|
||||
* IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING
|
||||
* OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
|
||||
*/
|
||||
|
||||
#include <sys/types.h>
|
||||
#include <sys/un.h>
|
||||
|
||||
#include <systemd/sd-daemon.h>
|
||||
|
||||
#include "tmux.h"
|
||||
|
||||
int
|
||||
systemd_create_socket(int flags, char **cause)
|
||||
{
|
||||
int fds;
|
||||
int fd;
|
||||
struct sockaddr_un sa;
|
||||
int addrlen = sizeof sa;
|
||||
|
||||
fds = sd_listen_fds(0);
|
||||
if (fds > 1) { /* too many file descriptors */
|
||||
errno = E2BIG;
|
||||
goto fail;
|
||||
}
|
||||
|
||||
if (fds == 1) { /* socket-activated */
|
||||
fd = SD_LISTEN_FDS_START;
|
||||
if (!sd_is_socket_unix(fd, SOCK_STREAM, 1, NULL, 0)) {
|
||||
errno = EPFNOSUPPORT;
|
||||
goto fail;
|
||||
}
|
||||
if (getsockname(fd, (struct sockaddr *)&sa, &addrlen) == -1)
|
||||
goto fail;
|
||||
socket_path = xstrdup(sa.sun_path);
|
||||
return (fd);
|
||||
}
|
||||
|
||||
return (server_create_socket(flags, cause));
|
||||
|
||||
fail:
|
||||
if (cause != NULL)
|
||||
xasprintf(cause, "systemd socket error (%s)", strerror(errno));
|
||||
return (-1);
|
||||
}
|
43
configure.ac
43
configure.ac
@ -69,6 +69,11 @@ AC_ARG_ENABLE(
|
||||
AS_HELP_STRING(--enable-static, create a static build)
|
||||
)
|
||||
if test "x$enable_static" = xyes; then
|
||||
case "$host_os" in
|
||||
*darwin*)
|
||||
AC_MSG_ERROR([static linking is not supported on macOS])
|
||||
;;
|
||||
esac
|
||||
test "x$PKG_CONFIG" != x && PKG_CONFIG="$PKG_CONFIG --static"
|
||||
AM_LDFLAGS="-static $AM_LDFLAGS"
|
||||
LDFLAGS="$AM_LDFLAGS $SAVED_LDFLAGS"
|
||||
@ -123,6 +128,7 @@ AC_CHECK_HEADERS([ \
|
||||
sys/dir.h \
|
||||
sys/ndir.h \
|
||||
sys/tree.h \
|
||||
ucred.h \
|
||||
util.h \
|
||||
])
|
||||
|
||||
@ -141,7 +147,8 @@ AC_CHECK_FUNCS([ \
|
||||
flock \
|
||||
prctl \
|
||||
proc_pidinfo \
|
||||
sysconf
|
||||
getpeerucred \
|
||||
sysconf \
|
||||
])
|
||||
|
||||
# Check for functions with a compatibility implementation.
|
||||
@ -155,6 +162,7 @@ AC_REPLACE_FUNCS([ \
|
||||
freezero \
|
||||
getdtablecount \
|
||||
getdtablesize \
|
||||
getpeereid \
|
||||
getline \
|
||||
getprogname \
|
||||
memmem \
|
||||
@ -382,6 +390,31 @@ if test "x$enable_utf8proc" = xyes; then
|
||||
fi
|
||||
AM_CONDITIONAL(HAVE_UTF8PROC, [test "x$enable_utf8proc" = xyes])
|
||||
|
||||
# Check for systemd support.
|
||||
AC_ARG_ENABLE(
|
||||
systemd,
|
||||
AS_HELP_STRING(--enable-systemd, enable systemd integration)
|
||||
)
|
||||
if test x"$enable_systemd" = xyes; then
|
||||
PKG_CHECK_MODULES(
|
||||
SYSTEMD,
|
||||
libsystemd,
|
||||
[
|
||||
AM_CPPFLAGS="$SYSTEMD_CFLAGS $AM_CPPFLAGS"
|
||||
CPPFLAGS="$AM_CPPFLAGS $SAVED_CPPFLAGS"
|
||||
LIBS="$SYSTEMD_LIBS $LIBS"
|
||||
found_systemd=yes
|
||||
],
|
||||
found_systemd=no
|
||||
)
|
||||
if test "x$found_systemd" = xyes; then
|
||||
AC_DEFINE(HAVE_SYSTEMD)
|
||||
else
|
||||
AC_MSG_ERROR("systemd not found")
|
||||
fi
|
||||
fi
|
||||
AM_CONDITIONAL(HAVE_SYSTEMD, [test "x$found_systemd" = xyes])
|
||||
|
||||
# Check for b64_ntop. If we have b64_ntop, we assume b64_pton as well.
|
||||
AC_MSG_CHECKING(for b64_ntop)
|
||||
AC_LINK_IFELSE([AC_LANG_PROGRAM(
|
||||
@ -679,6 +712,14 @@ AC_CHECK_DECL(
|
||||
[#include <sys/prctl.h>]
|
||||
)
|
||||
|
||||
# Look for setsockopt(SO_PEERCRED).
|
||||
AC_CHECK_DECL(
|
||||
SO_PEERCRED,
|
||||
AC_DEFINE(HAVE_SO_PEERCRED),
|
||||
,
|
||||
[#include <sys/socket.h>]
|
||||
)
|
||||
|
||||
# Look for fcntl(F_CLOSEM).
|
||||
AC_CHECK_DECL(
|
||||
F_CLOSEM,
|
||||
|
@ -1154,13 +1154,13 @@ format_trim_right(const char *expanded, u_int limit)
|
||||
while (*cp != '\0') {
|
||||
if (*cp == '#') {
|
||||
end = format_leading_hashes(cp, &n, &leading_width);
|
||||
copy_width = leading_width;
|
||||
if (width <= skip) {
|
||||
if (skip - width >= leading_width)
|
||||
if (skip - width >= copy_width)
|
||||
copy_width = 0;
|
||||
else
|
||||
copy_width -= (skip - width);
|
||||
} else
|
||||
copy_width = leading_width;
|
||||
}
|
||||
if (copy_width != 0) {
|
||||
if (n == 1)
|
||||
*out++ = '#';
|
||||
|
107
format.c
107
format.c
@ -24,6 +24,7 @@
|
||||
#include <fnmatch.h>
|
||||
#include <libgen.h>
|
||||
#include <math.h>
|
||||
#include <pwd.h>
|
||||
#include <regex.h>
|
||||
#include <stdarg.h>
|
||||
#include <stdlib.h>
|
||||
@ -1387,6 +1388,35 @@ format_cb_client_tty(struct format_tree *ft)
|
||||
return (NULL);
|
||||
}
|
||||
|
||||
/* Callback for client_uid. */
|
||||
static void *
|
||||
format_cb_client_uid(struct format_tree *ft)
|
||||
{
|
||||
uid_t uid;
|
||||
|
||||
if (ft->c != NULL) {
|
||||
uid = proc_get_peer_uid(ft->c->peer);
|
||||
if (uid != (uid_t)-1)
|
||||
return (format_printf("%ld", (long)uid));
|
||||
}
|
||||
return (NULL);
|
||||
}
|
||||
|
||||
/* Callback for client_user. */
|
||||
static void *
|
||||
format_cb_client_user(struct format_tree *ft)
|
||||
{
|
||||
uid_t uid;
|
||||
struct passwd *pw;
|
||||
|
||||
if (ft->c != NULL) {
|
||||
uid = proc_get_peer_uid(ft->c->peer);
|
||||
if (uid != (uid_t)-1 && (pw = getpwuid(uid)) != NULL)
|
||||
return (xstrdup(pw->pw_name));
|
||||
}
|
||||
return (NULL);
|
||||
}
|
||||
|
||||
/* Callback for client_utf8. */
|
||||
static void *
|
||||
format_cb_client_utf8(struct format_tree *ft)
|
||||
@ -1650,6 +1680,13 @@ format_cb_mouse_y(struct format_tree *ft)
|
||||
return (NULL);
|
||||
}
|
||||
|
||||
/* Callback for next_session_id. */
|
||||
static void *
|
||||
format_cb_next_session_id(__unused struct format_tree *ft)
|
||||
{
|
||||
return (format_printf("$%u", next_session_id));
|
||||
}
|
||||
|
||||
/* Callback for origin_flag. */
|
||||
static void *
|
||||
format_cb_origin_flag(struct format_tree *ft)
|
||||
@ -1719,6 +1756,23 @@ format_cb_pane_dead(struct format_tree *ft)
|
||||
return (NULL);
|
||||
}
|
||||
|
||||
/* Callback for pane_dead_signal. */
|
||||
static void *
|
||||
format_cb_pane_dead_signal(struct format_tree *ft)
|
||||
{
|
||||
struct window_pane *wp = ft->wp;
|
||||
const char *name;
|
||||
|
||||
if (wp != NULL) {
|
||||
if ((wp->flags & PANE_STATUSREADY) && WIFSIGNALED(wp->status)) {
|
||||
name = sig2name(WTERMSIG(wp->status));
|
||||
return (format_printf("%s", name));
|
||||
}
|
||||
return (NULL);
|
||||
}
|
||||
return (NULL);
|
||||
}
|
||||
|
||||
/* Callback for pane_dead_status. */
|
||||
static void *
|
||||
format_cb_pane_dead_status(struct format_tree *ft)
|
||||
@ -1733,6 +1787,20 @@ format_cb_pane_dead_status(struct format_tree *ft)
|
||||
return (NULL);
|
||||
}
|
||||
|
||||
/* Callback for pane_dead_time. */
|
||||
static void *
|
||||
format_cb_pane_dead_time(struct format_tree *ft)
|
||||
{
|
||||
struct window_pane *wp = ft->wp;
|
||||
|
||||
if (wp != NULL) {
|
||||
if (wp->flags & PANE_STATUSDRAWN)
|
||||
return (&wp->dead_time);
|
||||
return (NULL);
|
||||
}
|
||||
return (NULL);
|
||||
}
|
||||
|
||||
/* Callback for pane_format. */
|
||||
static void *
|
||||
format_cb_pane_format(struct format_tree *ft)
|
||||
@ -2514,6 +2582,24 @@ format_cb_tree_mode_format(__unused struct format_tree *ft)
|
||||
return (xstrdup(window_tree_mode.default_format));
|
||||
}
|
||||
|
||||
/* Callback for uid. */
|
||||
static void *
|
||||
format_cb_uid(__unused struct format_tree *ft)
|
||||
{
|
||||
return (format_printf("%ld", (long)getuid()));
|
||||
}
|
||||
|
||||
/* Callback for user. */
|
||||
static void *
|
||||
format_cb_user(__unused struct format_tree *ft)
|
||||
{
|
||||
struct passwd *pw;
|
||||
|
||||
if ((pw = getpwuid(getuid())) != NULL)
|
||||
return (xstrdup(pw->pw_name));
|
||||
return NULL;
|
||||
}
|
||||
|
||||
/* Format table type. */
|
||||
enum format_table_type {
|
||||
FORMAT_TABLE_STRING,
|
||||
@ -2620,6 +2706,12 @@ static const struct format_table_entry format_table[] = {
|
||||
{ "client_tty", FORMAT_TABLE_STRING,
|
||||
format_cb_client_tty
|
||||
},
|
||||
{ "client_uid", FORMAT_TABLE_STRING,
|
||||
format_cb_client_uid
|
||||
},
|
||||
{ "client_user", FORMAT_TABLE_STRING,
|
||||
format_cb_client_user
|
||||
},
|
||||
{ "client_utf8", FORMAT_TABLE_STRING,
|
||||
format_cb_client_utf8
|
||||
},
|
||||
@ -2707,6 +2799,9 @@ static const struct format_table_entry format_table[] = {
|
||||
{ "mouse_y", FORMAT_TABLE_STRING,
|
||||
format_cb_mouse_y
|
||||
},
|
||||
{ "next_session_id", FORMAT_TABLE_STRING,
|
||||
format_cb_next_session_id
|
||||
},
|
||||
{ "origin_flag", FORMAT_TABLE_STRING,
|
||||
format_cb_origin_flag
|
||||
},
|
||||
@ -2740,9 +2835,15 @@ static const struct format_table_entry format_table[] = {
|
||||
{ "pane_dead", FORMAT_TABLE_STRING,
|
||||
format_cb_pane_dead
|
||||
},
|
||||
{ "pane_dead_signal", FORMAT_TABLE_STRING,
|
||||
format_cb_pane_dead_signal
|
||||
},
|
||||
{ "pane_dead_status", FORMAT_TABLE_STRING,
|
||||
format_cb_pane_dead_status
|
||||
},
|
||||
{ "pane_dead_time", FORMAT_TABLE_TIME,
|
||||
format_cb_pane_dead_time
|
||||
},
|
||||
{ "pane_fg", FORMAT_TABLE_STRING,
|
||||
format_cb_pane_fg
|
||||
},
|
||||
@ -2896,6 +2997,12 @@ static const struct format_table_entry format_table[] = {
|
||||
{ "tree_mode_format", FORMAT_TABLE_STRING,
|
||||
format_cb_tree_mode_format
|
||||
},
|
||||
{ "uid", FORMAT_TABLE_STRING,
|
||||
format_cb_uid
|
||||
},
|
||||
{ "user", FORMAT_TABLE_STRING,
|
||||
format_cb_user
|
||||
},
|
||||
{ "version", FORMAT_TABLE_STRING,
|
||||
format_cb_version
|
||||
},
|
||||
|
98
grid.c
98
grid.c
@ -826,6 +826,56 @@ grid_string_cells_bg(const struct grid_cell *gc, int *values)
|
||||
return (n);
|
||||
}
|
||||
|
||||
/* Get underscore colour sequence. */
|
||||
static size_t
|
||||
grid_string_cells_us(const struct grid_cell *gc, int *values)
|
||||
{
|
||||
size_t n;
|
||||
u_char r, g, b;
|
||||
|
||||
n = 0;
|
||||
if (gc->us & COLOUR_FLAG_256) {
|
||||
values[n++] = 58;
|
||||
values[n++] = 5;
|
||||
values[n++] = gc->us & 0xff;
|
||||
} else if (gc->us & COLOUR_FLAG_RGB) {
|
||||
values[n++] = 58;
|
||||
values[n++] = 2;
|
||||
colour_split_rgb(gc->us, &r, &g, &b);
|
||||
values[n++] = r;
|
||||
values[n++] = g;
|
||||
values[n++] = b;
|
||||
}
|
||||
return (n);
|
||||
}
|
||||
|
||||
/* Add on SGR code. */
|
||||
static void
|
||||
grid_string_cells_add_code(char *buf, size_t len, u_int n, int *s, int *newc,
|
||||
int *oldc, size_t nnewc, size_t noldc, int escape_c0)
|
||||
{
|
||||
u_int i;
|
||||
char tmp[64];
|
||||
|
||||
if (nnewc != 0 &&
|
||||
(nnewc != noldc ||
|
||||
memcmp(newc, oldc, nnewc * sizeof newc[0]) != 0 ||
|
||||
(n != 0 && s[0] == 0))) {
|
||||
if (escape_c0)
|
||||
strlcat(buf, "\\033[", len);
|
||||
else
|
||||
strlcat(buf, "\033[", len);
|
||||
for (i = 0; i < nnewc; i++) {
|
||||
if (i + 1 < nnewc)
|
||||
xsnprintf(tmp, sizeof tmp, "%d;", newc[i]);
|
||||
else
|
||||
xsnprintf(tmp, sizeof tmp, "%d", newc[i]);
|
||||
strlcat(buf, tmp, len);
|
||||
}
|
||||
strlcat(buf, "m", len);
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* Returns ANSI code to set particular attributes (colour, bold and so on)
|
||||
* given a current state.
|
||||
@ -861,7 +911,9 @@ grid_string_cells_code(const struct grid_cell *lastgc,
|
||||
|
||||
/* If any attribute is removed, begin with 0. */
|
||||
for (i = 0; i < nitems(attrs); i++) {
|
||||
if (!(attr & attrs[i].mask) && (lastattr & attrs[i].mask)) {
|
||||
if (((~attr & attrs[i].mask) &&
|
||||
(lastattr & attrs[i].mask)) ||
|
||||
(lastgc->us != 0 && gc->us == 0)) {
|
||||
s[n++] = 0;
|
||||
lastattr &= GRID_ATTR_CHARSET;
|
||||
break;
|
||||
@ -897,42 +949,20 @@ grid_string_cells_code(const struct grid_cell *lastgc,
|
||||
/* If the foreground colour changed, write its parameters. */
|
||||
nnewc = grid_string_cells_fg(gc, newc);
|
||||
noldc = grid_string_cells_fg(lastgc, oldc);
|
||||
if (nnewc != noldc ||
|
||||
memcmp(newc, oldc, nnewc * sizeof newc[0]) != 0 ||
|
||||
(n != 0 && s[0] == 0)) {
|
||||
if (escape_c0)
|
||||
strlcat(buf, "\\033[", len);
|
||||
else
|
||||
strlcat(buf, "\033[", len);
|
||||
for (i = 0; i < nnewc; i++) {
|
||||
if (i + 1 < nnewc)
|
||||
xsnprintf(tmp, sizeof tmp, "%d;", newc[i]);
|
||||
else
|
||||
xsnprintf(tmp, sizeof tmp, "%d", newc[i]);
|
||||
strlcat(buf, tmp, len);
|
||||
}
|
||||
strlcat(buf, "m", len);
|
||||
}
|
||||
grid_string_cells_add_code(buf, len, n, s, newc, oldc, nnewc, noldc,
|
||||
escape_c0);
|
||||
|
||||
/* If the background colour changed, append its parameters. */
|
||||
nnewc = grid_string_cells_bg(gc, newc);
|
||||
noldc = grid_string_cells_bg(lastgc, oldc);
|
||||
if (nnewc != noldc ||
|
||||
memcmp(newc, oldc, nnewc * sizeof newc[0]) != 0 ||
|
||||
(n != 0 && s[0] == 0)) {
|
||||
if (escape_c0)
|
||||
strlcat(buf, "\\033[", len);
|
||||
else
|
||||
strlcat(buf, "\033[", len);
|
||||
for (i = 0; i < nnewc; i++) {
|
||||
if (i + 1 < nnewc)
|
||||
xsnprintf(tmp, sizeof tmp, "%d;", newc[i]);
|
||||
else
|
||||
xsnprintf(tmp, sizeof tmp, "%d", newc[i]);
|
||||
strlcat(buf, tmp, len);
|
||||
}
|
||||
strlcat(buf, "m", len);
|
||||
}
|
||||
grid_string_cells_add_code(buf, len, n, s, newc, oldc, nnewc, noldc,
|
||||
escape_c0);
|
||||
|
||||
/* If the underscore colour changed, append its parameters. */
|
||||
nnewc = grid_string_cells_us(gc, newc);
|
||||
noldc = grid_string_cells_us(lastgc, oldc);
|
||||
grid_string_cells_add_code(buf, len, n, s, newc, oldc, nnewc, noldc,
|
||||
escape_c0);
|
||||
|
||||
/* Append shift in/shift out if needed. */
|
||||
if ((attr & GRID_ATTR_CHARSET) && !(lastattr & GRID_ATTR_CHARSET)) {
|
||||
@ -973,7 +1003,7 @@ grid_string_cells(struct grid *gd, u_int px, u_int py, u_int nx,
|
||||
|
||||
gl = grid_peek_line(gd, py);
|
||||
for (xx = px; xx < px + nx; xx++) {
|
||||
if (gl == NULL || xx >= gl->cellsize)
|
||||
if (gl == NULL || xx >= gl->cellused)
|
||||
break;
|
||||
grid_get_cell(gd, xx, py, &gc);
|
||||
if (gc.flags & GRID_FLAG_PADDING)
|
||||
|
15
input-keys.c
15
input-keys.c
@ -417,7 +417,7 @@ int
|
||||
input_key(struct screen *s, struct bufferevent *bev, key_code key)
|
||||
{
|
||||
struct input_key_entry *ike;
|
||||
key_code justkey, newkey, outkey;
|
||||
key_code justkey, newkey, outkey, modifiers;
|
||||
struct utf8_data ud;
|
||||
char tmp[64], modifier;
|
||||
|
||||
@ -518,7 +518,12 @@ input_key(struct screen *s, struct bufferevent *bev, key_code key)
|
||||
return (input_key(s, bev, key & ~KEYC_CTRL));
|
||||
}
|
||||
outkey = (key & KEYC_MASK_KEY);
|
||||
switch (key & KEYC_MASK_MODIFIERS) {
|
||||
modifiers = (key & KEYC_MASK_MODIFIERS);
|
||||
if (outkey < 32 && outkey != 9 && outkey != 13 && outkey != 27) {
|
||||
outkey = 64 + outkey;
|
||||
modifiers |= KEYC_CTRL;
|
||||
}
|
||||
switch (modifiers) {
|
||||
case KEYC_SHIFT:
|
||||
modifier = '2';
|
||||
break;
|
||||
@ -577,13 +582,13 @@ input_key_get_mouse(struct screen *s, struct mouse_event *m, u_int x, u_int y,
|
||||
*/
|
||||
if (m->sgr_type != ' ') {
|
||||
if (MOUSE_DRAG(m->sgr_b) &&
|
||||
MOUSE_BUTTONS(m->sgr_b) == 3 &&
|
||||
MOUSE_RELEASE(m->sgr_b) &&
|
||||
(~s->mode & MODE_MOUSE_ALL))
|
||||
return (0);
|
||||
} else {
|
||||
if (MOUSE_DRAG(m->b) &&
|
||||
MOUSE_BUTTONS(m->b) == 3 &&
|
||||
MOUSE_BUTTONS(m->lb) == 3 &&
|
||||
MOUSE_RELEASE(m->b) &&
|
||||
MOUSE_RELEASE(m->lb) &&
|
||||
(~s->mode & MODE_MOUSE_ALL))
|
||||
return (0);
|
||||
}
|
||||
|
55
input.c
55
input.c
@ -2244,11 +2244,13 @@ input_dcs_dispatch(struct input_ctx *ictx)
|
||||
const u_int prefixlen = (sizeof prefix) - 1;
|
||||
struct sixel_image *si;
|
||||
|
||||
if (wp == NULL)
|
||||
return (0);
|
||||
if (ictx->flags & INPUT_DISCARD)
|
||||
return (0);
|
||||
|
||||
log_debug("%s: \"%s\" \"%s\" \"%s\"", __func__, buf, ictx->interm_buf,
|
||||
ictx->param_buf);
|
||||
if (!options_get_number(ictx->wp->options, "allow-passthrough"))
|
||||
return (0);
|
||||
log_debug("%s: \"%s\"", __func__, buf);
|
||||
|
||||
if (len >= prefixlen && strncmp(buf, prefix, prefixlen) == 0)
|
||||
screen_write_rawstring(sctx, buf + prefixlen, len - prefixlen);
|
||||
@ -2690,8 +2692,8 @@ input_osc_52(struct input_ctx *ictx, const char *p)
|
||||
{
|
||||
struct window_pane *wp = ictx->wp;
|
||||
char *end;
|
||||
const char *buf;
|
||||
size_t len;
|
||||
const char *buf = NULL;
|
||||
size_t len = 0;
|
||||
u_char *out;
|
||||
int outlen, state;
|
||||
struct screen_write_ctx ctx;
|
||||
@ -2711,26 +2713,12 @@ input_osc_52(struct input_ctx *ictx, const char *p)
|
||||
log_debug("%s: %s", __func__, end);
|
||||
|
||||
if (strcmp(end, "?") == 0) {
|
||||
if ((pb = paste_get_top(NULL)) != NULL) {
|
||||
if ((pb = paste_get_top(NULL)) != NULL)
|
||||
buf = paste_buffer_data(pb, &len);
|
||||
outlen = 4 * ((len + 2) / 3) + 1;
|
||||
out = xmalloc(outlen);
|
||||
if ((outlen = b64_ntop(buf, len, out, outlen)) == -1) {
|
||||
free(out);
|
||||
return;
|
||||
}
|
||||
} else {
|
||||
outlen = 0;
|
||||
out = NULL;
|
||||
}
|
||||
bufferevent_write(ictx->event, "\033]52;;", 6);
|
||||
if (outlen != 0)
|
||||
bufferevent_write(ictx->event, out, outlen);
|
||||
if (ictx->input_end == INPUT_END_BEL)
|
||||
bufferevent_write(ictx->event, "\007", 1);
|
||||
input_reply_clipboard(ictx->event, buf, len, "\007");
|
||||
else
|
||||
bufferevent_write(ictx->event, "\033\\", 2);
|
||||
free(out);
|
||||
input_reply_clipboard(ictx->event, buf, len, "\033\\");
|
||||
return;
|
||||
}
|
||||
|
||||
@ -2788,3 +2776,26 @@ input_osc_104(struct input_ctx *ictx, const char *p)
|
||||
screen_write_fullredraw(&ictx->ctx);
|
||||
free(copy);
|
||||
}
|
||||
|
||||
void
|
||||
input_reply_clipboard(struct bufferevent *bev, const char *buf, size_t len,
|
||||
const char *end)
|
||||
{
|
||||
char *out = NULL;
|
||||
size_t outlen = 0;
|
||||
|
||||
if (buf != NULL && len != 0) {
|
||||
outlen = 4 * ((len + 2) / 3) + 1;
|
||||
out = xmalloc(outlen);
|
||||
if ((outlen = b64_ntop(buf, len, out, outlen)) == -1) {
|
||||
free(out);
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
bufferevent_write(bev, "\033]52;;", 6);
|
||||
if (outlen != 0)
|
||||
bufferevent_write(bev, out, outlen);
|
||||
bufferevent_write(bev, end, strlen(end));
|
||||
free(out);
|
||||
}
|
||||
|
3
job.c
3
job.c
@ -87,9 +87,8 @@ job_run(const char *cmd, int argc, char **argv, struct environ *e, struct sessio
|
||||
* if-shell to decide on default-terminal based on outside TERM.
|
||||
*/
|
||||
env = environ_for_session(s, !cfg_finished);
|
||||
if (e != NULL) {
|
||||
if (e != NULL)
|
||||
environ_copy(e, env);
|
||||
}
|
||||
|
||||
sigfillset(&set);
|
||||
sigprocmask(SIG_BLOCK, &set, &oldset);
|
||||
|
@ -492,6 +492,7 @@ key_bindings_init(void)
|
||||
"bind -Tcopy-mode \\; { send -X jump-again }",
|
||||
"bind -Tcopy-mode F { command-prompt -1p'(jump backward)' { send -X jump-backward '%%' } }",
|
||||
"bind -Tcopy-mode N { send -X search-reverse }",
|
||||
"bind -Tcopy-mode P { send -X toggle-position }",
|
||||
"bind -Tcopy-mode R { send -X rectangle-toggle }",
|
||||
"bind -Tcopy-mode T { command-prompt -1p'(jump to backward)' { send -X jump-to-backward '%%' } }",
|
||||
"bind -Tcopy-mode X { send -X set-mark }",
|
||||
@ -588,6 +589,7 @@ key_bindings_init(void)
|
||||
"bind -Tcopy-mode-vi L { send -X bottom-line }",
|
||||
"bind -Tcopy-mode-vi M { send -X middle-line }",
|
||||
"bind -Tcopy-mode-vi N { send -X search-reverse }",
|
||||
"bind -Tcopy-mode-vi P { send -X toggle-position }",
|
||||
"bind -Tcopy-mode-vi T { command-prompt -1p'(jump to backward)' { send -X jump-to-backward '%%' } }",
|
||||
"bind -Tcopy-mode-vi V { send -X select-line }",
|
||||
"bind -Tcopy-mode-vi W { send -X next-space }",
|
||||
|
42
key-string.c
42
key-string.c
@ -91,26 +91,68 @@ static const struct {
|
||||
KEYC_MOUSE_STRING(MOUSEDOWN1, MouseDown1),
|
||||
KEYC_MOUSE_STRING(MOUSEDOWN2, MouseDown2),
|
||||
KEYC_MOUSE_STRING(MOUSEDOWN3, MouseDown3),
|
||||
KEYC_MOUSE_STRING(MOUSEDOWN6, MouseDown6),
|
||||
KEYC_MOUSE_STRING(MOUSEDOWN7, MouseDown7),
|
||||
KEYC_MOUSE_STRING(MOUSEDOWN8, MouseDown8),
|
||||
KEYC_MOUSE_STRING(MOUSEDOWN9, MouseDown9),
|
||||
KEYC_MOUSE_STRING(MOUSEDOWN10, MouseDown10),
|
||||
KEYC_MOUSE_STRING(MOUSEDOWN11, MouseDown11),
|
||||
KEYC_MOUSE_STRING(MOUSEUP1, MouseUp1),
|
||||
KEYC_MOUSE_STRING(MOUSEUP2, MouseUp2),
|
||||
KEYC_MOUSE_STRING(MOUSEUP3, MouseUp3),
|
||||
KEYC_MOUSE_STRING(MOUSEUP6, MouseUp6),
|
||||
KEYC_MOUSE_STRING(MOUSEUP7, MouseUp7),
|
||||
KEYC_MOUSE_STRING(MOUSEUP8, MouseUp8),
|
||||
KEYC_MOUSE_STRING(MOUSEUP9, MouseUp9),
|
||||
KEYC_MOUSE_STRING(MOUSEUP10, MouseUp10),
|
||||
KEYC_MOUSE_STRING(MOUSEUP11, MouseUp11),
|
||||
KEYC_MOUSE_STRING(MOUSEDRAG1, MouseDrag1),
|
||||
KEYC_MOUSE_STRING(MOUSEDRAG2, MouseDrag2),
|
||||
KEYC_MOUSE_STRING(MOUSEDRAG3, MouseDrag3),
|
||||
KEYC_MOUSE_STRING(MOUSEDRAG6, MouseDrag6),
|
||||
KEYC_MOUSE_STRING(MOUSEDRAG7, MouseDrag7),
|
||||
KEYC_MOUSE_STRING(MOUSEDRAG8, MouseDrag8),
|
||||
KEYC_MOUSE_STRING(MOUSEDRAG9, MouseDrag9),
|
||||
KEYC_MOUSE_STRING(MOUSEDRAG10, MouseDrag10),
|
||||
KEYC_MOUSE_STRING(MOUSEDRAG11, MouseDrag11),
|
||||
KEYC_MOUSE_STRING(MOUSEDRAGEND1, MouseDragEnd1),
|
||||
KEYC_MOUSE_STRING(MOUSEDRAGEND2, MouseDragEnd2),
|
||||
KEYC_MOUSE_STRING(MOUSEDRAGEND3, MouseDragEnd3),
|
||||
KEYC_MOUSE_STRING(MOUSEDRAGEND6, MouseDragEnd6),
|
||||
KEYC_MOUSE_STRING(MOUSEDRAGEND7, MouseDragEnd7),
|
||||
KEYC_MOUSE_STRING(MOUSEDRAGEND8, MouseDragEnd8),
|
||||
KEYC_MOUSE_STRING(MOUSEDRAGEND9, MouseDragEnd9),
|
||||
KEYC_MOUSE_STRING(MOUSEDRAGEND10, MouseDragEnd10),
|
||||
KEYC_MOUSE_STRING(MOUSEDRAGEND11, MouseDragEnd11),
|
||||
KEYC_MOUSE_STRING(WHEELUP, WheelUp),
|
||||
KEYC_MOUSE_STRING(WHEELDOWN, WheelDown),
|
||||
KEYC_MOUSE_STRING(SECONDCLICK1, SecondClick1),
|
||||
KEYC_MOUSE_STRING(SECONDCLICK2, SecondClick2),
|
||||
KEYC_MOUSE_STRING(SECONDCLICK3, SecondClick3),
|
||||
KEYC_MOUSE_STRING(SECONDCLICK6, SecondClick6),
|
||||
KEYC_MOUSE_STRING(SECONDCLICK7, SecondClick7),
|
||||
KEYC_MOUSE_STRING(SECONDCLICK8, SecondClick8),
|
||||
KEYC_MOUSE_STRING(SECONDCLICK9, SecondClick9),
|
||||
KEYC_MOUSE_STRING(SECONDCLICK10, SecondClick10),
|
||||
KEYC_MOUSE_STRING(SECONDCLICK11, SecondClick11),
|
||||
KEYC_MOUSE_STRING(DOUBLECLICK1, DoubleClick1),
|
||||
KEYC_MOUSE_STRING(DOUBLECLICK2, DoubleClick2),
|
||||
KEYC_MOUSE_STRING(DOUBLECLICK3, DoubleClick3),
|
||||
KEYC_MOUSE_STRING(DOUBLECLICK6, DoubleClick6),
|
||||
KEYC_MOUSE_STRING(DOUBLECLICK7, DoubleClick7),
|
||||
KEYC_MOUSE_STRING(DOUBLECLICK8, DoubleClick8),
|
||||
KEYC_MOUSE_STRING(DOUBLECLICK9, DoubleClick9),
|
||||
KEYC_MOUSE_STRING(DOUBLECLICK10, DoubleClick10),
|
||||
KEYC_MOUSE_STRING(DOUBLECLICK11, DoubleClick11),
|
||||
KEYC_MOUSE_STRING(TRIPLECLICK1, TripleClick1),
|
||||
KEYC_MOUSE_STRING(TRIPLECLICK2, TripleClick2),
|
||||
KEYC_MOUSE_STRING(TRIPLECLICK3, TripleClick3),
|
||||
KEYC_MOUSE_STRING(TRIPLECLICK6, TripleClick6),
|
||||
KEYC_MOUSE_STRING(TRIPLECLICK7, TripleClick7),
|
||||
KEYC_MOUSE_STRING(TRIPLECLICK8, TripleClick8),
|
||||
KEYC_MOUSE_STRING(TRIPLECLICK9, TripleClick9),
|
||||
KEYC_MOUSE_STRING(TRIPLECLICK10, TripleClick10),
|
||||
KEYC_MOUSE_STRING(TRIPLECLICK11, TripleClick11)
|
||||
};
|
||||
|
||||
/* Find key string in table. */
|
||||
|
6
menu.c
6
menu.c
@ -235,7 +235,7 @@ menu_key_cb(struct client *c, void *data, struct key_event *event)
|
||||
|
||||
if (KEYC_IS_MOUSE(event->key)) {
|
||||
if (md->flags & MENU_NOMOUSE) {
|
||||
if (MOUSE_BUTTONS(m->b) != 0)
|
||||
if (MOUSE_BUTTONS(m->b) != MOUSE_BUTTON_1)
|
||||
return (1);
|
||||
return (0);
|
||||
}
|
||||
@ -248,7 +248,7 @@ menu_key_cb(struct client *c, void *data, struct key_event *event)
|
||||
return (1);
|
||||
} else {
|
||||
if (!MOUSE_RELEASE(m->b) &&
|
||||
MOUSE_WHEEL(m->b) == 0 &&
|
||||
!MOUSE_WHEEL(m->b) &&
|
||||
!MOUSE_DRAG(m->b))
|
||||
return (1);
|
||||
}
|
||||
@ -262,7 +262,7 @@ menu_key_cb(struct client *c, void *data, struct key_event *event)
|
||||
if (MOUSE_RELEASE(m->b))
|
||||
goto chosen;
|
||||
} else {
|
||||
if (MOUSE_WHEEL(m->b) == 0 && !MOUSE_DRAG(m->b))
|
||||
if (!MOUSE_WHEEL(m->b) && !MOUSE_DRAG(m->b))
|
||||
goto chosen;
|
||||
}
|
||||
md->choice = m->y - (md->py + 1);
|
||||
|
12
mode-tree.c
12
mode-tree.c
@ -104,7 +104,6 @@ struct mode_tree_menu {
|
||||
struct mode_tree_data *data;
|
||||
struct client *c;
|
||||
u_int line;
|
||||
void *itemdata;
|
||||
};
|
||||
|
||||
static void mode_tree_free_items(struct mode_tree_list *);
|
||||
@ -909,18 +908,14 @@ static void
|
||||
mode_tree_menu_callback(__unused struct menu *menu, __unused u_int idx,
|
||||
key_code key, void *data)
|
||||
{
|
||||
struct mode_tree_menu *mtm = data;
|
||||
struct mode_tree_data *mtd = mtm->data;
|
||||
struct mode_tree_item *mti;
|
||||
struct mode_tree_menu *mtm = data;
|
||||
struct mode_tree_data *mtd = mtm->data;
|
||||
|
||||
if (mtd->dead || key == KEYC_NONE)
|
||||
goto out;
|
||||
|
||||
if (mtm->line >= mtd->line_size)
|
||||
goto out;
|
||||
mti = mtd->line_list[mtm->line].item;
|
||||
if (mti->itemdata != mtm->itemdata)
|
||||
goto out;
|
||||
mtd->current = mtm->line;
|
||||
mtd->menucb(mtd->modedata, mtm->c, key);
|
||||
|
||||
@ -954,14 +949,13 @@ mode_tree_display_menu(struct mode_tree_data *mtd, struct client *c, u_int x,
|
||||
title = xstrdup("");
|
||||
}
|
||||
menu = menu_create(title);
|
||||
menu_add_items(menu, items, NULL, NULL, NULL);
|
||||
menu_add_items(menu, items, NULL, c, NULL);
|
||||
free(title);
|
||||
|
||||
mtm = xmalloc(sizeof *mtm);
|
||||
mtm->data = mtd;
|
||||
mtm->c = c;
|
||||
mtm->line = line;
|
||||
mtm->itemdata = mti->itemdata;
|
||||
mtd->references++;
|
||||
|
||||
if (x >= (menu->width + 4) / 2)
|
||||
|
67
notify.c
67
notify.c
@ -34,18 +34,37 @@ struct notify_entry {
|
||||
int pane;
|
||||
};
|
||||
|
||||
static struct cmdq_item *
|
||||
notify_insert_one_hook(struct cmdq_item *item, struct notify_entry *ne,
|
||||
struct cmd_list *cmdlist, struct cmdq_state *state)
|
||||
{
|
||||
struct cmdq_item *new_item;
|
||||
char *s;
|
||||
|
||||
if (cmdlist == NULL)
|
||||
return (item);
|
||||
if (log_get_level() != 0) {
|
||||
s = cmd_list_print(cmdlist, 0);
|
||||
log_debug("%s: hook %s is: %s", __func__, ne->name, s);
|
||||
free (s);
|
||||
}
|
||||
new_item = cmdq_get_command(cmdlist, state);
|
||||
return (cmdq_insert_after(item, new_item));
|
||||
}
|
||||
|
||||
static void
|
||||
notify_insert_hook(struct cmdq_item *item, struct notify_entry *ne)
|
||||
{
|
||||
struct cmd_find_state fs;
|
||||
struct options *oo;
|
||||
struct cmdq_item *new_item;
|
||||
struct cmdq_state *new_state;
|
||||
struct cmdq_state *state;
|
||||
struct options_entry *o;
|
||||
struct options_array_item *a;
|
||||
struct cmd_list *cmdlist;
|
||||
const char *value;
|
||||
struct cmd_parse_result *pr;
|
||||
|
||||
log_debug("%s: %s", __func__, ne->name);
|
||||
log_debug("%s: inserting hook %s", __func__, ne->name);
|
||||
|
||||
cmd_find_clear_state(&fs, 0);
|
||||
if (cmd_find_empty_state(&ne->fs) || !cmd_find_valid_state(&ne->fs))
|
||||
@ -66,23 +85,37 @@ notify_insert_hook(struct cmdq_item *item, struct notify_entry *ne)
|
||||
oo = fs.wl->window->options;
|
||||
o = options_get(oo, ne->name);
|
||||
}
|
||||
if (o == NULL)
|
||||
if (o == NULL) {
|
||||
log_debug("%s: hook %s not found", __func__, ne->name);
|
||||
return;
|
||||
|
||||
new_state = cmdq_new_state(&fs, NULL, CMDQ_STATE_NOHOOKS);
|
||||
cmdq_add_formats(new_state, ne->formats);
|
||||
|
||||
a = options_array_first(o);
|
||||
while (a != NULL) {
|
||||
cmdlist = options_array_item_value(a)->cmdlist;
|
||||
if (cmdlist != NULL) {
|
||||
new_item = cmdq_get_command(cmdlist, new_state);
|
||||
item = cmdq_insert_after(item, new_item);
|
||||
}
|
||||
a = options_array_next(a);
|
||||
}
|
||||
|
||||
cmdq_free_state(new_state);
|
||||
state = cmdq_new_state(&fs, NULL, CMDQ_STATE_NOHOOKS);
|
||||
cmdq_add_formats(state, ne->formats);
|
||||
|
||||
if (*ne->name == '@') {
|
||||
value = options_get_string(oo, ne->name);
|
||||
pr = cmd_parse_from_string(value, NULL);
|
||||
switch (pr->status) {
|
||||
case CMD_PARSE_ERROR:
|
||||
log_debug("%s: can't parse hook %s: %s", __func__,
|
||||
ne->name, pr->error);
|
||||
free(pr->error);
|
||||
break;
|
||||
case CMD_PARSE_SUCCESS:
|
||||
notify_insert_one_hook(item, ne, pr->cmdlist, state);
|
||||
break;
|
||||
}
|
||||
} else {
|
||||
a = options_array_first(o);
|
||||
while (a != NULL) {
|
||||
cmdlist = options_array_item_value(a)->cmdlist;
|
||||
item = notify_insert_one_hook(item, ne, cmdlist, state);
|
||||
a = options_array_next(a);
|
||||
}
|
||||
}
|
||||
|
||||
cmdq_free_state(state);
|
||||
}
|
||||
|
||||
static enum cmd_retval
|
||||
|
@ -63,6 +63,9 @@ static const char *options_table_cursor_style_list[] = {
|
||||
static const char *options_table_pane_status_list[] = {
|
||||
"off", "top", "bottom", NULL
|
||||
};
|
||||
static const char *options_table_pane_border_indicators_list[] = {
|
||||
"off", "colour", "arrows", "both", NULL
|
||||
};
|
||||
static const char *options_table_pane_border_lines_list[] = {
|
||||
"single", "double", "heavy", "simple", "number", NULL
|
||||
};
|
||||
@ -274,6 +277,7 @@ const struct options_table_entry options_table[] = {
|
||||
.minimum = 0,
|
||||
.maximum = INT_MAX,
|
||||
.default_num = 500,
|
||||
.unit = "milliseconds",
|
||||
.text = "Time to wait before assuming a key is Escape."
|
||||
},
|
||||
|
||||
@ -298,7 +302,7 @@ const struct options_table_entry options_table[] = {
|
||||
.choices = options_table_extended_keys_list,
|
||||
.default_num = 0,
|
||||
.text = "Whether to request extended key sequences from terminals "
|
||||
"that support it."
|
||||
"that support it."
|
||||
},
|
||||
|
||||
{ .name = "focus-events",
|
||||
@ -797,6 +801,14 @@ const struct options_table_entry options_table[] = {
|
||||
"linked to ('off')."
|
||||
},
|
||||
|
||||
{ .name = "allow-passthrough",
|
||||
.type = OPTIONS_TABLE_FLAG,
|
||||
.scope = OPTIONS_TABLE_WINDOW|OPTIONS_TABLE_PANE,
|
||||
.default_num = 0,
|
||||
.text = "Whether applications are allowed to use the escape sequence "
|
||||
"to bypass tmux."
|
||||
},
|
||||
|
||||
{ .name = "allow-rename",
|
||||
.type = OPTIONS_TABLE_FLAG,
|
||||
.scope = OPTIONS_TABLE_WINDOW|OPTIONS_TABLE_PANE,
|
||||
@ -870,6 +882,13 @@ const struct options_table_entry options_table[] = {
|
||||
.text = "Style of the marked line in copy mode."
|
||||
},
|
||||
|
||||
{ .name = "fill-character",
|
||||
.type = OPTIONS_TABLE_STRING,
|
||||
.scope = OPTIONS_TABLE_WINDOW,
|
||||
.default_str = "",
|
||||
.text = "Character used to fill unused parts of window."
|
||||
},
|
||||
|
||||
{ .name = "main-pane-height",
|
||||
.type = OPTIONS_TABLE_STRING,
|
||||
.scope = OPTIONS_TABLE_WINDOW,
|
||||
@ -964,19 +983,28 @@ const struct options_table_entry options_table[] = {
|
||||
|
||||
{ .name = "pane-border-format",
|
||||
.type = OPTIONS_TABLE_STRING,
|
||||
.scope = OPTIONS_TABLE_WINDOW,
|
||||
.scope = OPTIONS_TABLE_WINDOW|OPTIONS_TABLE_PANE,
|
||||
.default_str = "#{?pane_active,#[reverse],}#{pane_index}#[default] "
|
||||
"\"#{pane_title}\"",
|
||||
.text = "Format of text in the pane status lines."
|
||||
},
|
||||
|
||||
{ .name = "pane-border-indicators",
|
||||
.type = OPTIONS_TABLE_CHOICE,
|
||||
.scope = OPTIONS_TABLE_WINDOW,
|
||||
.choices = options_table_pane_border_indicators_list,
|
||||
.default_num = PANE_BORDER_COLOUR,
|
||||
.text = "Whether to indicate the active pane by colouring border or "
|
||||
"displaying arrow markers."
|
||||
},
|
||||
|
||||
{ .name = "pane-border-lines",
|
||||
.type = OPTIONS_TABLE_CHOICE,
|
||||
.scope = OPTIONS_TABLE_WINDOW,
|
||||
.choices = options_table_pane_border_lines_list,
|
||||
.default_num = PANE_LINES_SINGLE,
|
||||
.text = "Type of characters used to draw pane border lines. Some of "
|
||||
"these are only supported on terminals with UTF-8 support."
|
||||
"these are only supported on terminals with UTF-8 support."
|
||||
},
|
||||
|
||||
{ .name = "pane-border-status",
|
||||
@ -1028,7 +1056,7 @@ const struct options_table_entry options_table[] = {
|
||||
.choices = options_table_popup_border_lines_list,
|
||||
.default_num = BOX_LINES_SINGLE,
|
||||
.text = "Type of characters used to draw popup border lines. Some of "
|
||||
"these are only supported on terminals with UTF-8 support."
|
||||
"these are only supported on terminals with UTF-8 support."
|
||||
},
|
||||
|
||||
{ .name = "remain-on-exit",
|
||||
@ -1040,6 +1068,27 @@ const struct options_table_entry options_table[] = {
|
||||
"killed ('off' or 'failed') when the program inside exits."
|
||||
},
|
||||
|
||||
{ .name = "remain-on-exit-format",
|
||||
.type = OPTIONS_TABLE_STRING,
|
||||
.scope = OPTIONS_TABLE_WINDOW|OPTIONS_TABLE_PANE,
|
||||
.default_str = "Pane is dead ("
|
||||
"#{?#{!=:#{pane_dead_status},},"
|
||||
"status #{pane_dead_status},}"
|
||||
"#{?#{!=:#{pane_dead_signal},},"
|
||||
"signal #{pane_dead_signal},}, "
|
||||
"#{t:pane_dead_time})",
|
||||
.text = "Message shown after the program in a pane has exited, if "
|
||||
"remain-on-exit is enabled."
|
||||
},
|
||||
|
||||
{ .name = "scroll-on-clear",
|
||||
.type = OPTIONS_TABLE_FLAG,
|
||||
.scope = OPTIONS_TABLE_WINDOW|OPTIONS_TABLE_PANE,
|
||||
.default_num = 1,
|
||||
.text = "Whether the contents of the screen should be scrolled into"
|
||||
"history when clearing the whole screen."
|
||||
},
|
||||
|
||||
{ .name = "synchronize-panes",
|
||||
.type = OPTIONS_TABLE_FLAG,
|
||||
.scope = OPTIONS_TABLE_WINDOW|OPTIONS_TABLE_PANE,
|
||||
@ -1158,7 +1207,7 @@ const struct options_table_entry options_table[] = {
|
||||
.scope = OPTIONS_TABLE_WINDOW,
|
||||
.default_num = 1,
|
||||
.text = "Whether xterm-style function key sequences should be sent. "
|
||||
"This option is no longer used."
|
||||
"This option is no longer used."
|
||||
},
|
||||
|
||||
/* Hook options. */
|
||||
@ -1206,8 +1255,8 @@ const struct options_table_entry options_table[] = {
|
||||
OPTIONS_TABLE_HOOK("client-active", ""),
|
||||
OPTIONS_TABLE_HOOK("client-attached", ""),
|
||||
OPTIONS_TABLE_HOOK("client-detached", ""),
|
||||
OPTIONS_TABLE_HOOK("client-focus-in", ""),
|
||||
OPTIONS_TABLE_HOOK("client-focus-out", ""),
|
||||
OPTIONS_TABLE_HOOK("client-focus-in", ""),
|
||||
OPTIONS_TABLE_HOOK("client-focus-out", ""),
|
||||
OPTIONS_TABLE_HOOK("client-resized", ""),
|
||||
OPTIONS_TABLE_HOOK("client-session-changed", ""),
|
||||
OPTIONS_TABLE_PANE_HOOK("pane-died", ""),
|
||||
@ -1225,6 +1274,7 @@ const struct options_table_entry options_table[] = {
|
||||
OPTIONS_TABLE_HOOK("window-linked", ""),
|
||||
OPTIONS_TABLE_WINDOW_HOOK("window-pane-changed", ""),
|
||||
OPTIONS_TABLE_WINDOW_HOOK("window-renamed", ""),
|
||||
OPTIONS_TABLE_WINDOW_HOOK("window-resized", ""),
|
||||
OPTIONS_TABLE_HOOK("window-unlinked", ""),
|
||||
|
||||
{ .name = NULL }
|
||||
|
@ -1108,6 +1108,8 @@ options_push_changes(const char *name)
|
||||
struct window_pane *wp;
|
||||
int c;
|
||||
|
||||
log_debug("%s: %s", __func__, name);
|
||||
|
||||
if (strcmp(name, "automatic-rename") == 0) {
|
||||
RB_FOREACH(w, windows, &windows) {
|
||||
if (w->active == NULL)
|
||||
@ -1130,6 +1132,10 @@ options_push_changes(const char *name)
|
||||
&wp->screen->default_mode);
|
||||
}
|
||||
}
|
||||
if (strcmp(name, "fill-character") == 0) {
|
||||
RB_FOREACH(w, windows, &windows)
|
||||
window_set_fill_character(w);
|
||||
}
|
||||
if (strcmp(name, "key-table") == 0) {
|
||||
TAILQ_FOREACH(loop, &clients, entry)
|
||||
server_client_set_key_table(loop, NULL);
|
||||
|
@ -35,9 +35,6 @@
|
||||
((p)->p_stat == SSTOP || (p)->p_stat == SZOMB)
|
||||
|
||||
struct kinfo_proc2 *cmp_procs(struct kinfo_proc2 *, struct kinfo_proc2 *);
|
||||
char *osdep_get_name(int, char *);
|
||||
char *osdep_get_cwd(int);
|
||||
struct event_base *osdep_event_init(void);
|
||||
|
||||
struct kinfo_proc2 *
|
||||
cmp_procs(struct kinfo_proc2 *p1, struct kinfo_proc2 *p2)
|
||||
|
@ -16,7 +16,6 @@
|
||||
* OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
|
||||
*/
|
||||
|
||||
#include <sys/param.h> /* MAXCOMLEN */
|
||||
#include <sys/types.h>
|
||||
#include <sys/signal.h>
|
||||
#include <sys/proc.h>
|
||||
@ -142,7 +141,7 @@ char *
|
||||
osdep_get_cwd(int fd)
|
||||
{
|
||||
int name[] = { CTL_KERN, KERN_PROC_CWD, 0 };
|
||||
static char path[MAXPATHLEN];
|
||||
static char path[PATH_MAX];
|
||||
size_t pathlen = sizeof path;
|
||||
|
||||
if ((name[2] = tcgetpgrp(fd)) == -1)
|
||||
|
17
popup.c
17
popup.c
@ -508,7 +508,7 @@ popup_key_cb(struct client *c, void *data, struct key_event *event)
|
||||
m->x > pd->px + pd->sx - 1 ||
|
||||
m->y < pd->py ||
|
||||
m->y > pd->py + pd->sy - 1) {
|
||||
if (MOUSE_BUTTONS(m->b) == 2)
|
||||
if (MOUSE_BUTTONS(m->b) == MOUSE_BUTTON_3)
|
||||
goto menu;
|
||||
return (0);
|
||||
}
|
||||
@ -523,16 +523,16 @@ popup_key_cb(struct client *c, void *data, struct key_event *event)
|
||||
border = BOTTOM;
|
||||
}
|
||||
if ((m->b & MOUSE_MASK_MODIFIERS) == 0 &&
|
||||
MOUSE_BUTTONS(m->b) == 2 &&
|
||||
MOUSE_BUTTONS(m->b) == MOUSE_BUTTON_3 &&
|
||||
(border == LEFT || border == TOP))
|
||||
goto menu;
|
||||
if (((m->b & MOUSE_MASK_MODIFIERS) == MOUSE_MASK_META) ||
|
||||
border != NONE) {
|
||||
if (!MOUSE_DRAG(m->b))
|
||||
goto out;
|
||||
if (MOUSE_BUTTONS(m->lb) == 0)
|
||||
if (MOUSE_BUTTONS(m->lb) == MOUSE_BUTTON_1)
|
||||
pd->dragging = MOVE;
|
||||
else if (MOUSE_BUTTONS(m->lb) == 2)
|
||||
else if (MOUSE_BUTTONS(m->lb) == MOUSE_BUTTON_3)
|
||||
pd->dragging = SIZE;
|
||||
pd->dx = m->lx - pd->px;
|
||||
pd->dy = m->ly - pd->py;
|
||||
@ -565,10 +565,10 @@ popup_key_cb(struct client *c, void *data, struct key_event *event)
|
||||
menu:
|
||||
pd->menu = menu_create("");
|
||||
if (pd->flags & POPUP_INTERNAL) {
|
||||
menu_add_items(pd->menu, popup_internal_menu_items, NULL, NULL,
|
||||
menu_add_items(pd->menu, popup_internal_menu_items, NULL, c,
|
||||
NULL);
|
||||
} else
|
||||
menu_add_items(pd->menu, popup_menu_items, NULL, NULL, NULL);
|
||||
menu_add_items(pd->menu, popup_menu_items, NULL, c, NULL);
|
||||
if (m->x >= (pd->menu->width + 4) / 2)
|
||||
x = m->x - (pd->menu->width + 4) / 2;
|
||||
else
|
||||
@ -667,7 +667,8 @@ popup_display(int flags, enum box_lines lines, struct cmdq_item *item, u_int px,
|
||||
pd = xcalloc(1, sizeof *pd);
|
||||
pd->item = item;
|
||||
pd->flags = flags;
|
||||
pd->title = xstrdup(title);
|
||||
if (title != NULL)
|
||||
pd->title = xstrdup(title);
|
||||
|
||||
pd->c = c;
|
||||
pd->c->references++;
|
||||
@ -688,7 +689,7 @@ popup_display(int flags, enum box_lines lines, struct cmdq_item *item, u_int px,
|
||||
}
|
||||
pd->border_cell.attr = 0;
|
||||
|
||||
screen_init(&pd->s, sx - 2, sy - 2, 0);
|
||||
screen_init(&pd->s, jx, jy, 0);
|
||||
colour_palette_init(&pd->palette);
|
||||
colour_palette_from_option(&pd->palette, global_w_options);
|
||||
|
||||
|
11
proc.c
11
proc.c
@ -56,6 +56,7 @@ struct tmuxpeer {
|
||||
|
||||
struct imsgbuf ibuf;
|
||||
struct event event;
|
||||
uid_t uid;
|
||||
|
||||
int flags;
|
||||
#define PEER_BAD 0x1
|
||||
@ -308,6 +309,7 @@ proc_add_peer(struct tmuxproc *tp, int fd,
|
||||
void (*dispatchcb)(struct imsg *, void *), void *arg)
|
||||
{
|
||||
struct tmuxpeer *peer;
|
||||
gid_t gid;
|
||||
|
||||
peer = xcalloc(1, sizeof *peer);
|
||||
peer->parent = tp;
|
||||
@ -318,6 +320,9 @@ proc_add_peer(struct tmuxproc *tp, int fd,
|
||||
imsg_init(&peer->ibuf, fd);
|
||||
event_set(&peer->event, fd, EV_READ, proc_event_cb, peer);
|
||||
|
||||
if (getpeereid(fd, &peer->uid, &gid) != 0)
|
||||
peer->uid = (uid_t)-1;
|
||||
|
||||
log_debug("add peer %p: %d (%p)", peer, fd, arg);
|
||||
TAILQ_INSERT_TAIL(&tp->peers, peer, entry);
|
||||
|
||||
@ -373,3 +378,9 @@ proc_fork_and_daemon(int *fd)
|
||||
return (pid);
|
||||
}
|
||||
}
|
||||
|
||||
uid_t
|
||||
proc_get_peer_uid(struct tmuxpeer *peer)
|
||||
{
|
||||
return (peer->uid);
|
||||
}
|
||||
|
3
resize.c
3
resize.c
@ -61,6 +61,7 @@ resize_window(struct window *w, u_int sx, u_int sy, int xpixel, int ypixel)
|
||||
tty_update_window_offset(w);
|
||||
server_redraw_window(w);
|
||||
notify_window("window-layout-changed", w);
|
||||
notify_window("window-resized", w);
|
||||
w->flags &= ~WINDOW_RESIZE;
|
||||
}
|
||||
|
||||
@ -178,7 +179,7 @@ clients_calculate_size(int type, int current, struct client *c,
|
||||
cw = NULL;
|
||||
|
||||
/* Work out this client's size. */
|
||||
if (cw != NULL) {
|
||||
if (cw != NULL && cw->sx != 0 && cw->sy != 0) {
|
||||
cx = cw->sx;
|
||||
cy = cw->sy;
|
||||
} else {
|
||||
|
@ -34,19 +34,29 @@ static void screen_redraw_set_context(struct client *,
|
||||
#define START_ISOLATE "\342\201\246"
|
||||
#define END_ISOLATE "\342\201\251"
|
||||
|
||||
/* Border in relation to a pane. */
|
||||
enum screen_redraw_border_type {
|
||||
SCREEN_REDRAW_OUTSIDE,
|
||||
SCREEN_REDRAW_INSIDE,
|
||||
SCREEN_REDRAW_BORDER
|
||||
SCREEN_REDRAW_BORDER_LEFT,
|
||||
SCREEN_REDRAW_BORDER_RIGHT,
|
||||
SCREEN_REDRAW_BORDER_TOP,
|
||||
SCREEN_REDRAW_BORDER_BOTTOM
|
||||
};
|
||||
#define BORDER_MARKERS " +,.-"
|
||||
|
||||
/* Get cell border character. */
|
||||
static void
|
||||
screen_redraw_border_set(struct window_pane *wp, enum pane_lines pane_lines,
|
||||
int cell_type, struct grid_cell *gc)
|
||||
screen_redraw_border_set(struct window *w, struct window_pane *wp,
|
||||
enum pane_lines pane_lines, int cell_type, struct grid_cell *gc)
|
||||
{
|
||||
u_int idx;
|
||||
|
||||
if (cell_type == CELL_OUTSIDE && w->fill_character != NULL) {
|
||||
utf8_copy(&gc->data, &w->fill_character[0]);
|
||||
return;
|
||||
}
|
||||
|
||||
switch (pane_lines) {
|
||||
case PANE_LINES_NUMBER:
|
||||
if (cell_type == CELL_OUTSIDE) {
|
||||
@ -102,64 +112,74 @@ static enum screen_redraw_border_type
|
||||
screen_redraw_pane_border(struct window_pane *wp, u_int px, u_int py,
|
||||
int pane_status)
|
||||
{
|
||||
u_int ex = wp->xoff + wp->sx, ey = wp->yoff + wp->sy;
|
||||
struct options *oo = wp->window->options;
|
||||
int split = 0;
|
||||
u_int ex = wp->xoff + wp->sx, ey = wp->yoff + wp->sy;
|
||||
|
||||
/* Inside pane. */
|
||||
if (px >= wp->xoff && px < ex && py >= wp->yoff && py < ey)
|
||||
return (SCREEN_REDRAW_INSIDE);
|
||||
|
||||
/* Get pane indicator. */
|
||||
switch (options_get_number(oo, "pane-border-indicators")) {
|
||||
case PANE_BORDER_COLOUR:
|
||||
case PANE_BORDER_BOTH:
|
||||
split = 1;
|
||||
break;
|
||||
}
|
||||
|
||||
/* Left/right borders. */
|
||||
if (pane_status == PANE_STATUS_OFF) {
|
||||
if (screen_redraw_two_panes(wp->window, 0)) {
|
||||
if (screen_redraw_two_panes(wp->window, 0) && split) {
|
||||
if (wp->xoff == 0 && px == wp->sx && py <= wp->sy / 2)
|
||||
return (SCREEN_REDRAW_BORDER);
|
||||
return (SCREEN_REDRAW_BORDER_RIGHT);
|
||||
if (wp->xoff != 0 &&
|
||||
px == wp->xoff - 1 &&
|
||||
py > wp->sy / 2)
|
||||
return (SCREEN_REDRAW_BORDER);
|
||||
return (SCREEN_REDRAW_BORDER_LEFT);
|
||||
} else {
|
||||
if ((wp->yoff == 0 || py >= wp->yoff - 1) && py <= ey) {
|
||||
if (wp->xoff != 0 && px == wp->xoff - 1)
|
||||
return (SCREEN_REDRAW_BORDER);
|
||||
return (SCREEN_REDRAW_BORDER_LEFT);
|
||||
if (px == ex)
|
||||
return (SCREEN_REDRAW_BORDER);
|
||||
return (SCREEN_REDRAW_BORDER_RIGHT);
|
||||
}
|
||||
}
|
||||
} else {
|
||||
if ((wp->yoff == 0 || py >= wp->yoff - 1) && py <= ey) {
|
||||
if (wp->xoff != 0 && px == wp->xoff - 1)
|
||||
return (SCREEN_REDRAW_BORDER);
|
||||
return (SCREEN_REDRAW_BORDER_LEFT);
|
||||
if (px == ex)
|
||||
return (SCREEN_REDRAW_BORDER);
|
||||
return (SCREEN_REDRAW_BORDER_RIGHT);
|
||||
}
|
||||
}
|
||||
|
||||
/* Top/bottom borders. */
|
||||
if (pane_status == PANE_STATUS_OFF) {
|
||||
if (screen_redraw_two_panes(wp->window, 1)) {
|
||||
if (screen_redraw_two_panes(wp->window, 1) && split) {
|
||||
if (wp->yoff == 0 && py == wp->sy && px <= wp->sx / 2)
|
||||
return (SCREEN_REDRAW_BORDER);
|
||||
return (SCREEN_REDRAW_BORDER_BOTTOM);
|
||||
if (wp->yoff != 0 &&
|
||||
py == wp->yoff - 1 &&
|
||||
px > wp->sx / 2)
|
||||
return (SCREEN_REDRAW_BORDER);
|
||||
return (SCREEN_REDRAW_BORDER_TOP);
|
||||
} else {
|
||||
if ((wp->xoff == 0 || px >= wp->xoff - 1) && px <= ex) {
|
||||
if (wp->yoff != 0 && py == wp->yoff - 1)
|
||||
return (SCREEN_REDRAW_BORDER);
|
||||
return (SCREEN_REDRAW_BORDER_TOP);
|
||||
if (py == ey)
|
||||
return (SCREEN_REDRAW_BORDER);
|
||||
return (SCREEN_REDRAW_BORDER_BOTTOM);
|
||||
}
|
||||
}
|
||||
} else if (pane_status == PANE_STATUS_TOP) {
|
||||
if ((wp->xoff == 0 || px >= wp->xoff - 1) && px <= ex) {
|
||||
if (wp->yoff != 0 && py == wp->yoff - 1)
|
||||
return (SCREEN_REDRAW_BORDER);
|
||||
return (SCREEN_REDRAW_BORDER_TOP);
|
||||
}
|
||||
} else {
|
||||
if ((wp->xoff == 0 || px >= wp->xoff - 1) && px <= ex) {
|
||||
if (py == ey)
|
||||
return (SCREEN_REDRAW_BORDER);
|
||||
return (SCREEN_REDRAW_BORDER_BOTTOM);
|
||||
}
|
||||
}
|
||||
|
||||
@ -189,10 +209,10 @@ screen_redraw_cell_border(struct client *c, u_int px, u_int py, int pane_status)
|
||||
switch (screen_redraw_pane_border(wp, px, py, pane_status)) {
|
||||
case SCREEN_REDRAW_INSIDE:
|
||||
return (0);
|
||||
case SCREEN_REDRAW_BORDER:
|
||||
return (1);
|
||||
case SCREEN_REDRAW_OUTSIDE:
|
||||
break;
|
||||
default:
|
||||
return (1);
|
||||
}
|
||||
}
|
||||
|
||||
@ -346,7 +366,7 @@ screen_redraw_check_is(u_int px, u_int py, int pane_status,
|
||||
enum screen_redraw_border_type border;
|
||||
|
||||
border = screen_redraw_pane_border(wp, px, py, pane_status);
|
||||
if (border == SCREEN_REDRAW_BORDER)
|
||||
if (border != SCREEN_REDRAW_INSIDE && border != SCREEN_REDRAW_OUTSIDE)
|
||||
return (1);
|
||||
return (0);
|
||||
}
|
||||
@ -373,7 +393,7 @@ screen_redraw_make_pane_status(struct client *c, struct window_pane *wp,
|
||||
style_apply(&gc, w->options, "pane-active-border-style", ft);
|
||||
else
|
||||
style_apply(&gc, w->options, "pane-border-style", ft);
|
||||
fmt = options_get_string(w->options, "pane-border-format");
|
||||
fmt = options_get_string(wp->options, "pane-border-format");
|
||||
|
||||
expanded = format_expand_time(ft, fmt);
|
||||
if (wp->sx < 4)
|
||||
@ -394,7 +414,7 @@ screen_redraw_make_pane_status(struct client *c, struct window_pane *wp,
|
||||
else
|
||||
py = wp->yoff + wp->sy;
|
||||
cell_type = screen_redraw_type_of_cell(c, px, py, pane_status);
|
||||
screen_redraw_border_set(wp, pane_lines, cell_type, &gc);
|
||||
screen_redraw_border_set(w, wp, pane_lines, cell_type, &gc);
|
||||
screen_write_cell(&ctx, &gc);
|
||||
}
|
||||
gc.attr &= ~GRID_ATTR_CHARSET;
|
||||
@ -637,11 +657,12 @@ screen_redraw_draw_borders_cell(struct screen_redraw_ctx *ctx, u_int i, u_int j)
|
||||
struct options *oo = w->options;
|
||||
struct tty *tty = &c->tty;
|
||||
struct format_tree *ft;
|
||||
struct window_pane *wp;
|
||||
struct window_pane *wp, *active = server_client_get_pane(c);
|
||||
struct grid_cell gc;
|
||||
const struct grid_cell *tmp;
|
||||
struct overlay_ranges r;
|
||||
u_int cell_type, x = ctx->ox + i, y = ctx->oy + j;
|
||||
int arrows = 0, border;
|
||||
int pane_status = ctx->pane_status, isolates;
|
||||
|
||||
if (c->overlay_check != NULL) {
|
||||
@ -674,7 +695,7 @@ screen_redraw_draw_borders_cell(struct screen_redraw_ctx *ctx, u_int i, u_int j)
|
||||
screen_redraw_check_is(x, y, pane_status, marked_pane.wp))
|
||||
gc.attr ^= GRID_ATTR_REVERSE;
|
||||
}
|
||||
screen_redraw_border_set(wp, ctx->pane_lines, cell_type, &gc);
|
||||
screen_redraw_border_set(w, wp, ctx->pane_lines, cell_type, &gc);
|
||||
|
||||
if (cell_type == CELL_TOPBOTTOM &&
|
||||
(c->flags & CLIENT_UTF8) &&
|
||||
@ -689,6 +710,34 @@ screen_redraw_draw_borders_cell(struct screen_redraw_ctx *ctx, u_int i, u_int j)
|
||||
tty_cursor(tty, i, j);
|
||||
if (isolates)
|
||||
tty_puts(tty, END_ISOLATE);
|
||||
|
||||
switch (options_get_number(oo, "pane-border-indicators")) {
|
||||
case PANE_BORDER_ARROWS:
|
||||
case PANE_BORDER_BOTH:
|
||||
arrows = 1;
|
||||
break;
|
||||
}
|
||||
|
||||
if (wp != NULL && arrows) {
|
||||
border = screen_redraw_pane_border(active, x, y, pane_status);
|
||||
if (((i == wp->xoff + 1 &&
|
||||
(cell_type == CELL_LEFTRIGHT ||
|
||||
(cell_type == CELL_TOPJOIN &&
|
||||
border == SCREEN_REDRAW_BORDER_BOTTOM) ||
|
||||
(cell_type == CELL_BOTTOMJOIN &&
|
||||
border == SCREEN_REDRAW_BORDER_TOP))) ||
|
||||
(j == wp->yoff + 1 &&
|
||||
(cell_type == CELL_TOPBOTTOM ||
|
||||
(cell_type == CELL_LEFTJOIN &&
|
||||
border == SCREEN_REDRAW_BORDER_RIGHT) ||
|
||||
(cell_type == CELL_RIGHTJOIN &&
|
||||
border == SCREEN_REDRAW_BORDER_LEFT)))) &&
|
||||
screen_redraw_check_is(x, y, pane_status, active)) {
|
||||
gc.attr |= GRID_ATTR_CHARSET;
|
||||
utf8_set(&gc.data, BORDER_MARKERS[border]);
|
||||
}
|
||||
}
|
||||
|
||||
tty_cell(tty, &gc, &grid_default_cell, NULL);
|
||||
if (isolates)
|
||||
tty_puts(tty, START_ISOLATE);
|
||||
|
@ -1476,7 +1476,11 @@ screen_write_clearendofscreen(struct screen_write_ctx *ctx, u_int bg)
|
||||
ttyctx.bg = bg;
|
||||
|
||||
/* Scroll into history if it is enabled and clearing entire screen. */
|
||||
if (s->cx == 0 && s->cy == 0 && (gd->flags & GRID_HISTORY))
|
||||
if (s->cx == 0 &&
|
||||
s->cy == 0 &&
|
||||
(gd->flags & GRID_HISTORY) &&
|
||||
ctx->wp != NULL &&
|
||||
options_get_number(ctx->wp->options, "scroll-on-clear"))
|
||||
grid_view_clear_history(gd, bg);
|
||||
else {
|
||||
if (s->cx <= sx - 1)
|
||||
@ -1530,7 +1534,9 @@ screen_write_clearscreen(struct screen_write_ctx *ctx, u_int bg)
|
||||
ttyctx.bg = bg;
|
||||
|
||||
/* Scroll into history if it is enabled. */
|
||||
if (s->grid->flags & GRID_HISTORY)
|
||||
if ((s->grid->flags & GRID_HISTORY) &&
|
||||
ctx->wp != NULL &&
|
||||
options_get_number(ctx->wp->options, "scroll-on-clear"))
|
||||
grid_view_clear_history(s->grid, bg);
|
||||
else
|
||||
grid_view_clear(s->grid, 0, 0, sx, sy, bg);
|
||||
|
666
server-client.c
666
server-client.c
@ -40,6 +40,7 @@ static void server_client_check_exit(struct client *);
|
||||
static void server_client_check_redraw(struct client *);
|
||||
static void server_client_check_modes(struct client *);
|
||||
static void server_client_set_title(struct client *);
|
||||
static void server_client_set_path(struct client *);
|
||||
static void server_client_reset_state(struct client *);
|
||||
static int server_client_assume_paste(struct session *);
|
||||
static void server_client_update_latest(struct client *);
|
||||
@ -422,6 +423,7 @@ server_client_lost(struct client *c)
|
||||
if (c->flags & CLIENT_TERMINAL)
|
||||
tty_free(&c->tty);
|
||||
free(c->ttyname);
|
||||
free(c->clipboard_panes);
|
||||
|
||||
free(c->term_name);
|
||||
free(c->term_type);
|
||||
@ -593,11 +595,11 @@ server_client_check_mouse(struct client *c, struct key_event *event)
|
||||
log_debug("double-click at %u,%u", x, y);
|
||||
} else if ((m->sgr_type != ' ' &&
|
||||
MOUSE_DRAG(m->sgr_b) &&
|
||||
MOUSE_BUTTONS(m->sgr_b) == 3) ||
|
||||
MOUSE_RELEASE(m->sgr_b)) ||
|
||||
(m->sgr_type == ' ' &&
|
||||
MOUSE_DRAG(m->b) &&
|
||||
MOUSE_BUTTONS(m->b) == 3 &&
|
||||
MOUSE_BUTTONS(m->lb) == 3)) {
|
||||
MOUSE_RELEASE(m->b) &&
|
||||
MOUSE_RELEASE(m->lb))) {
|
||||
type = MOVE;
|
||||
x = m->x, y = m->y, b = 0;
|
||||
log_debug("move at %u,%u", x, y);
|
||||
@ -750,7 +752,7 @@ have_event:
|
||||
m->wp = -1;
|
||||
|
||||
/* Stop dragging if needed. */
|
||||
if (type != DRAG && type != WHEEL && c->tty.mouse_drag_flag) {
|
||||
if (type != DRAG && type != WHEEL && c->tty.mouse_drag_flag != 0) {
|
||||
if (c->tty.mouse_drag_release != NULL)
|
||||
c->tty.mouse_drag_release(c, m);
|
||||
|
||||
@ -761,8 +763,8 @@ have_event:
|
||||
* End a mouse drag by passing a MouseDragEnd key corresponding
|
||||
* to the button that started the drag.
|
||||
*/
|
||||
switch (c->tty.mouse_drag_flag) {
|
||||
case 1:
|
||||
switch (c->tty.mouse_drag_flag - 1) {
|
||||
case MOUSE_BUTTON_1:
|
||||
if (where == PANE)
|
||||
key = KEYC_MOUSEDRAGEND1_PANE;
|
||||
if (where == STATUS)
|
||||
@ -776,7 +778,7 @@ have_event:
|
||||
if (where == BORDER)
|
||||
key = KEYC_MOUSEDRAGEND1_BORDER;
|
||||
break;
|
||||
case 2:
|
||||
case MOUSE_BUTTON_2:
|
||||
if (where == PANE)
|
||||
key = KEYC_MOUSEDRAGEND2_PANE;
|
||||
if (where == STATUS)
|
||||
@ -790,7 +792,7 @@ have_event:
|
||||
if (where == BORDER)
|
||||
key = KEYC_MOUSEDRAGEND2_BORDER;
|
||||
break;
|
||||
case 3:
|
||||
case MOUSE_BUTTON_3:
|
||||
if (where == PANE)
|
||||
key = KEYC_MOUSEDRAGEND3_PANE;
|
||||
if (where == STATUS)
|
||||
@ -804,6 +806,90 @@ have_event:
|
||||
if (where == BORDER)
|
||||
key = KEYC_MOUSEDRAGEND3_BORDER;
|
||||
break;
|
||||
case MOUSE_BUTTON_6:
|
||||
if (where == PANE)
|
||||
key = KEYC_MOUSEDRAGEND6_PANE;
|
||||
if (where == STATUS)
|
||||
key = KEYC_MOUSEDRAGEND6_STATUS;
|
||||
if (where == STATUS_LEFT)
|
||||
key = KEYC_MOUSEDRAGEND6_STATUS_LEFT;
|
||||
if (where == STATUS_RIGHT)
|
||||
key = KEYC_MOUSEDRAGEND6_STATUS_RIGHT;
|
||||
if (where == STATUS_DEFAULT)
|
||||
key = KEYC_MOUSEDRAGEND6_STATUS_DEFAULT;
|
||||
if (where == BORDER)
|
||||
key = KEYC_MOUSEDRAGEND6_BORDER;
|
||||
break;
|
||||
case MOUSE_BUTTON_7:
|
||||
if (where == PANE)
|
||||
key = KEYC_MOUSEDRAGEND7_PANE;
|
||||
if (where == STATUS)
|
||||
key = KEYC_MOUSEDRAGEND7_STATUS;
|
||||
if (where == STATUS_LEFT)
|
||||
key = KEYC_MOUSEDRAGEND7_STATUS_LEFT;
|
||||
if (where == STATUS_RIGHT)
|
||||
key = KEYC_MOUSEDRAGEND7_STATUS_RIGHT;
|
||||
if (where == STATUS_DEFAULT)
|
||||
key = KEYC_MOUSEDRAGEND7_STATUS_DEFAULT;
|
||||
if (where == BORDER)
|
||||
key = KEYC_MOUSEDRAGEND7_BORDER;
|
||||
break;
|
||||
case MOUSE_BUTTON_8:
|
||||
if (where == PANE)
|
||||
key = KEYC_MOUSEDRAGEND8_PANE;
|
||||
if (where == STATUS)
|
||||
key = KEYC_MOUSEDRAGEND8_STATUS;
|
||||
if (where == STATUS_LEFT)
|
||||
key = KEYC_MOUSEDRAGEND8_STATUS_LEFT;
|
||||
if (where == STATUS_RIGHT)
|
||||
key = KEYC_MOUSEDRAGEND8_STATUS_RIGHT;
|
||||
if (where == STATUS_DEFAULT)
|
||||
key = KEYC_MOUSEDRAGEND8_STATUS_DEFAULT;
|
||||
if (where == BORDER)
|
||||
key = KEYC_MOUSEDRAGEND8_BORDER;
|
||||
break;
|
||||
case MOUSE_BUTTON_9:
|
||||
if (where == PANE)
|
||||
key = KEYC_MOUSEDRAGEND9_PANE;
|
||||
if (where == STATUS)
|
||||
key = KEYC_MOUSEDRAGEND9_STATUS;
|
||||
if (where == STATUS_LEFT)
|
||||
key = KEYC_MOUSEDRAGEND9_STATUS_LEFT;
|
||||
if (where == STATUS_RIGHT)
|
||||
key = KEYC_MOUSEDRAGEND9_STATUS_RIGHT;
|
||||
if (where == STATUS_DEFAULT)
|
||||
key = KEYC_MOUSEDRAGEND9_STATUS_DEFAULT;
|
||||
if (where == BORDER)
|
||||
key = KEYC_MOUSEDRAGEND9_BORDER;
|
||||
break;
|
||||
case MOUSE_BUTTON_10:
|
||||
if (where == PANE)
|
||||
key = KEYC_MOUSEDRAGEND10_PANE;
|
||||
if (where == STATUS)
|
||||
key = KEYC_MOUSEDRAGEND10_STATUS;
|
||||
if (where == STATUS_LEFT)
|
||||
key = KEYC_MOUSEDRAGEND10_STATUS_LEFT;
|
||||
if (where == STATUS_RIGHT)
|
||||
key = KEYC_MOUSEDRAGEND10_STATUS_RIGHT;
|
||||
if (where == STATUS_DEFAULT)
|
||||
key = KEYC_MOUSEDRAGEND10_STATUS_DEFAULT;
|
||||
if (where == BORDER)
|
||||
key = KEYC_MOUSEDRAGEND10_BORDER;
|
||||
break;
|
||||
case MOUSE_BUTTON_11:
|
||||
if (where == PANE)
|
||||
key = KEYC_MOUSEDRAGEND11_PANE;
|
||||
if (where == STATUS)
|
||||
key = KEYC_MOUSEDRAGEND11_STATUS;
|
||||
if (where == STATUS_LEFT)
|
||||
key = KEYC_MOUSEDRAGEND11_STATUS_LEFT;
|
||||
if (where == STATUS_RIGHT)
|
||||
key = KEYC_MOUSEDRAGEND11_STATUS_RIGHT;
|
||||
if (where == STATUS_DEFAULT)
|
||||
key = KEYC_MOUSEDRAGEND11_STATUS_DEFAULT;
|
||||
if (where == BORDER)
|
||||
key = KEYC_MOUSEDRAGEND11_BORDER;
|
||||
break;
|
||||
default:
|
||||
key = KEYC_MOUSE;
|
||||
break;
|
||||
@ -836,7 +922,7 @@ have_event:
|
||||
key = KEYC_DRAGGING;
|
||||
else {
|
||||
switch (MOUSE_BUTTONS(b)) {
|
||||
case 0:
|
||||
case MOUSE_BUTTON_1:
|
||||
if (where == PANE)
|
||||
key = KEYC_MOUSEDRAG1_PANE;
|
||||
if (where == STATUS)
|
||||
@ -850,7 +936,7 @@ have_event:
|
||||
if (where == BORDER)
|
||||
key = KEYC_MOUSEDRAG1_BORDER;
|
||||
break;
|
||||
case 1:
|
||||
case MOUSE_BUTTON_2:
|
||||
if (where == PANE)
|
||||
key = KEYC_MOUSEDRAG2_PANE;
|
||||
if (where == STATUS)
|
||||
@ -864,7 +950,7 @@ have_event:
|
||||
if (where == BORDER)
|
||||
key = KEYC_MOUSEDRAG2_BORDER;
|
||||
break;
|
||||
case 2:
|
||||
case MOUSE_BUTTON_3:
|
||||
if (where == PANE)
|
||||
key = KEYC_MOUSEDRAG3_PANE;
|
||||
if (where == STATUS)
|
||||
@ -878,6 +964,90 @@ have_event:
|
||||
if (where == BORDER)
|
||||
key = KEYC_MOUSEDRAG3_BORDER;
|
||||
break;
|
||||
case MOUSE_BUTTON_6:
|
||||
if (where == PANE)
|
||||
key = KEYC_MOUSEDRAG6_PANE;
|
||||
if (where == STATUS)
|
||||
key = KEYC_MOUSEDRAG6_STATUS;
|
||||
if (where == STATUS_LEFT)
|
||||
key = KEYC_MOUSEDRAG6_STATUS_LEFT;
|
||||
if (where == STATUS_RIGHT)
|
||||
key = KEYC_MOUSEDRAG6_STATUS_RIGHT;
|
||||
if (where == STATUS_DEFAULT)
|
||||
key = KEYC_MOUSEDRAG6_STATUS_DEFAULT;
|
||||
if (where == BORDER)
|
||||
key = KEYC_MOUSEDRAG6_BORDER;
|
||||
break;
|
||||
case MOUSE_BUTTON_7:
|
||||
if (where == PANE)
|
||||
key = KEYC_MOUSEDRAG7_PANE;
|
||||
if (where == STATUS)
|
||||
key = KEYC_MOUSEDRAG7_STATUS;
|
||||
if (where == STATUS_LEFT)
|
||||
key = KEYC_MOUSEDRAG7_STATUS_LEFT;
|
||||
if (where == STATUS_RIGHT)
|
||||
key = KEYC_MOUSEDRAG7_STATUS_RIGHT;
|
||||
if (where == STATUS_DEFAULT)
|
||||
key = KEYC_MOUSEDRAG7_STATUS_DEFAULT;
|
||||
if (where == BORDER)
|
||||
key = KEYC_MOUSEDRAG7_BORDER;
|
||||
break;
|
||||
case MOUSE_BUTTON_8:
|
||||
if (where == PANE)
|
||||
key = KEYC_MOUSEDRAG8_PANE;
|
||||
if (where == STATUS)
|
||||
key = KEYC_MOUSEDRAG8_STATUS;
|
||||
if (where == STATUS_LEFT)
|
||||
key = KEYC_MOUSEDRAG8_STATUS_LEFT;
|
||||
if (where == STATUS_RIGHT)
|
||||
key = KEYC_MOUSEDRAG8_STATUS_RIGHT;
|
||||
if (where == STATUS_DEFAULT)
|
||||
key = KEYC_MOUSEDRAG8_STATUS_DEFAULT;
|
||||
if (where == BORDER)
|
||||
key = KEYC_MOUSEDRAG8_BORDER;
|
||||
break;
|
||||
case MOUSE_BUTTON_9:
|
||||
if (where == PANE)
|
||||
key = KEYC_MOUSEDRAG9_PANE;
|
||||
if (where == STATUS)
|
||||
key = KEYC_MOUSEDRAG9_STATUS;
|
||||
if (where == STATUS_LEFT)
|
||||
key = KEYC_MOUSEDRAG9_STATUS_LEFT;
|
||||
if (where == STATUS_RIGHT)
|
||||
key = KEYC_MOUSEDRAG9_STATUS_RIGHT;
|
||||
if (where == STATUS_DEFAULT)
|
||||
key = KEYC_MOUSEDRAG9_STATUS_DEFAULT;
|
||||
if (where == BORDER)
|
||||
key = KEYC_MOUSEDRAG9_BORDER;
|
||||
break;
|
||||
case MOUSE_BUTTON_10:
|
||||
if (where == PANE)
|
||||
key = KEYC_MOUSEDRAG10_PANE;
|
||||
if (where == STATUS)
|
||||
key = KEYC_MOUSEDRAG10_STATUS;
|
||||
if (where == STATUS_LEFT)
|
||||
key = KEYC_MOUSEDRAG10_STATUS_LEFT;
|
||||
if (where == STATUS_RIGHT)
|
||||
key = KEYC_MOUSEDRAG10_STATUS_RIGHT;
|
||||
if (where == STATUS_DEFAULT)
|
||||
key = KEYC_MOUSEDRAG10_STATUS_DEFAULT;
|
||||
if (where == BORDER)
|
||||
key = KEYC_MOUSEDRAG10_BORDER;
|
||||
break;
|
||||
case MOUSE_BUTTON_11:
|
||||
if (where == PANE)
|
||||
key = KEYC_MOUSEDRAG11_PANE;
|
||||
if (where == STATUS)
|
||||
key = KEYC_MOUSEDRAG11_STATUS;
|
||||
if (where == STATUS_LEFT)
|
||||
key = KEYC_MOUSEDRAG11_STATUS_LEFT;
|
||||
if (where == STATUS_RIGHT)
|
||||
key = KEYC_MOUSEDRAG11_STATUS_RIGHT;
|
||||
if (where == STATUS_DEFAULT)
|
||||
key = KEYC_MOUSEDRAG11_STATUS_DEFAULT;
|
||||
if (where == BORDER)
|
||||
key = KEYC_MOUSEDRAG11_BORDER;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
@ -918,7 +1088,7 @@ have_event:
|
||||
break;
|
||||
case UP:
|
||||
switch (MOUSE_BUTTONS(b)) {
|
||||
case 0:
|
||||
case MOUSE_BUTTON_1:
|
||||
if (where == PANE)
|
||||
key = KEYC_MOUSEUP1_PANE;
|
||||
if (where == STATUS)
|
||||
@ -932,7 +1102,7 @@ have_event:
|
||||
if (where == BORDER)
|
||||
key = KEYC_MOUSEUP1_BORDER;
|
||||
break;
|
||||
case 1:
|
||||
case MOUSE_BUTTON_2:
|
||||
if (where == PANE)
|
||||
key = KEYC_MOUSEUP2_PANE;
|
||||
if (where == STATUS)
|
||||
@ -946,7 +1116,7 @@ have_event:
|
||||
if (where == BORDER)
|
||||
key = KEYC_MOUSEUP2_BORDER;
|
||||
break;
|
||||
case 2:
|
||||
case MOUSE_BUTTON_3:
|
||||
if (where == PANE)
|
||||
key = KEYC_MOUSEUP3_PANE;
|
||||
if (where == STATUS)
|
||||
@ -960,11 +1130,95 @@ have_event:
|
||||
if (where == BORDER)
|
||||
key = KEYC_MOUSEUP3_BORDER;
|
||||
break;
|
||||
case MOUSE_BUTTON_6:
|
||||
if (where == PANE)
|
||||
key = KEYC_MOUSEUP6_PANE;
|
||||
if (where == STATUS)
|
||||
key = KEYC_MOUSEUP6_STATUS;
|
||||
if (where == STATUS_LEFT)
|
||||
key = KEYC_MOUSEUP6_STATUS_LEFT;
|
||||
if (where == STATUS_RIGHT)
|
||||
key = KEYC_MOUSEUP6_STATUS_RIGHT;
|
||||
if (where == STATUS_DEFAULT)
|
||||
key = KEYC_MOUSEUP6_STATUS_DEFAULT;
|
||||
if (where == BORDER)
|
||||
key = KEYC_MOUSEUP6_BORDER;
|
||||
break;
|
||||
case MOUSE_BUTTON_7:
|
||||
if (where == PANE)
|
||||
key = KEYC_MOUSEUP7_PANE;
|
||||
if (where == STATUS)
|
||||
key = KEYC_MOUSEUP7_STATUS;
|
||||
if (where == STATUS_LEFT)
|
||||
key = KEYC_MOUSEUP7_STATUS_LEFT;
|
||||
if (where == STATUS_RIGHT)
|
||||
key = KEYC_MOUSEUP7_STATUS_RIGHT;
|
||||
if (where == STATUS_DEFAULT)
|
||||
key = KEYC_MOUSEUP7_STATUS_DEFAULT;
|
||||
if (where == BORDER)
|
||||
key = KEYC_MOUSEUP7_BORDER;
|
||||
break;
|
||||
case MOUSE_BUTTON_8:
|
||||
if (where == PANE)
|
||||
key = KEYC_MOUSEUP8_PANE;
|
||||
if (where == STATUS)
|
||||
key = KEYC_MOUSEUP8_STATUS;
|
||||
if (where == STATUS_LEFT)
|
||||
key = KEYC_MOUSEUP8_STATUS_LEFT;
|
||||
if (where == STATUS_RIGHT)
|
||||
key = KEYC_MOUSEUP8_STATUS_RIGHT;
|
||||
if (where == STATUS_DEFAULT)
|
||||
key = KEYC_MOUSEUP8_STATUS_DEFAULT;
|
||||
if (where == BORDER)
|
||||
key = KEYC_MOUSEUP8_BORDER;
|
||||
break;
|
||||
case MOUSE_BUTTON_9:
|
||||
if (where == PANE)
|
||||
key = KEYC_MOUSEUP9_PANE;
|
||||
if (where == STATUS)
|
||||
key = KEYC_MOUSEUP9_STATUS;
|
||||
if (where == STATUS_LEFT)
|
||||
key = KEYC_MOUSEUP9_STATUS_LEFT;
|
||||
if (where == STATUS_RIGHT)
|
||||
key = KEYC_MOUSEUP9_STATUS_RIGHT;
|
||||
if (where == STATUS_DEFAULT)
|
||||
key = KEYC_MOUSEUP9_STATUS_DEFAULT;
|
||||
if (where == BORDER)
|
||||
key = KEYC_MOUSEUP9_BORDER;
|
||||
break;
|
||||
case MOUSE_BUTTON_10:
|
||||
if (where == PANE)
|
||||
key = KEYC_MOUSEUP1_PANE;
|
||||
if (where == STATUS)
|
||||
key = KEYC_MOUSEUP1_STATUS;
|
||||
if (where == STATUS_LEFT)
|
||||
key = KEYC_MOUSEUP1_STATUS_LEFT;
|
||||
if (where == STATUS_RIGHT)
|
||||
key = KEYC_MOUSEUP1_STATUS_RIGHT;
|
||||
if (where == STATUS_DEFAULT)
|
||||
key = KEYC_MOUSEUP1_STATUS_DEFAULT;
|
||||
if (where == BORDER)
|
||||
key = KEYC_MOUSEUP1_BORDER;
|
||||
break;
|
||||
case MOUSE_BUTTON_11:
|
||||
if (where == PANE)
|
||||
key = KEYC_MOUSEUP11_PANE;
|
||||
if (where == STATUS)
|
||||
key = KEYC_MOUSEUP11_STATUS;
|
||||
if (where == STATUS_LEFT)
|
||||
key = KEYC_MOUSEUP11_STATUS_LEFT;
|
||||
if (where == STATUS_RIGHT)
|
||||
key = KEYC_MOUSEUP11_STATUS_RIGHT;
|
||||
if (where == STATUS_DEFAULT)
|
||||
key = KEYC_MOUSEUP11_STATUS_DEFAULT;
|
||||
if (where == BORDER)
|
||||
key = KEYC_MOUSEUP11_BORDER;
|
||||
break;
|
||||
}
|
||||
break;
|
||||
case DOWN:
|
||||
switch (MOUSE_BUTTONS(b)) {
|
||||
case 0:
|
||||
case MOUSE_BUTTON_1:
|
||||
if (where == PANE)
|
||||
key = KEYC_MOUSEDOWN1_PANE;
|
||||
if (where == STATUS)
|
||||
@ -978,7 +1232,7 @@ have_event:
|
||||
if (where == BORDER)
|
||||
key = KEYC_MOUSEDOWN1_BORDER;
|
||||
break;
|
||||
case 1:
|
||||
case MOUSE_BUTTON_2:
|
||||
if (where == PANE)
|
||||
key = KEYC_MOUSEDOWN2_PANE;
|
||||
if (where == STATUS)
|
||||
@ -992,7 +1246,7 @@ have_event:
|
||||
if (where == BORDER)
|
||||
key = KEYC_MOUSEDOWN2_BORDER;
|
||||
break;
|
||||
case 2:
|
||||
case MOUSE_BUTTON_3:
|
||||
if (where == PANE)
|
||||
key = KEYC_MOUSEDOWN3_PANE;
|
||||
if (where == STATUS)
|
||||
@ -1006,11 +1260,95 @@ have_event:
|
||||
if (where == BORDER)
|
||||
key = KEYC_MOUSEDOWN3_BORDER;
|
||||
break;
|
||||
case MOUSE_BUTTON_6:
|
||||
if (where == PANE)
|
||||
key = KEYC_MOUSEDOWN6_PANE;
|
||||
if (where == STATUS)
|
||||
key = KEYC_MOUSEDOWN6_STATUS;
|
||||
if (where == STATUS_LEFT)
|
||||
key = KEYC_MOUSEDOWN6_STATUS_LEFT;
|
||||
if (where == STATUS_RIGHT)
|
||||
key = KEYC_MOUSEDOWN6_STATUS_RIGHT;
|
||||
if (where == STATUS_DEFAULT)
|
||||
key = KEYC_MOUSEDOWN6_STATUS_DEFAULT;
|
||||
if (where == BORDER)
|
||||
key = KEYC_MOUSEDOWN6_BORDER;
|
||||
break;
|
||||
case MOUSE_BUTTON_7:
|
||||
if (where == PANE)
|
||||
key = KEYC_MOUSEDOWN7_PANE;
|
||||
if (where == STATUS)
|
||||
key = KEYC_MOUSEDOWN7_STATUS;
|
||||
if (where == STATUS_LEFT)
|
||||
key = KEYC_MOUSEDOWN7_STATUS_LEFT;
|
||||
if (where == STATUS_RIGHT)
|
||||
key = KEYC_MOUSEDOWN7_STATUS_RIGHT;
|
||||
if (where == STATUS_DEFAULT)
|
||||
key = KEYC_MOUSEDOWN7_STATUS_DEFAULT;
|
||||
if (where == BORDER)
|
||||
key = KEYC_MOUSEDOWN7_BORDER;
|
||||
break;
|
||||
case MOUSE_BUTTON_8:
|
||||
if (where == PANE)
|
||||
key = KEYC_MOUSEDOWN8_PANE;
|
||||
if (where == STATUS)
|
||||
key = KEYC_MOUSEDOWN8_STATUS;
|
||||
if (where == STATUS_LEFT)
|
||||
key = KEYC_MOUSEDOWN8_STATUS_LEFT;
|
||||
if (where == STATUS_RIGHT)
|
||||
key = KEYC_MOUSEDOWN8_STATUS_RIGHT;
|
||||
if (where == STATUS_DEFAULT)
|
||||
key = KEYC_MOUSEDOWN8_STATUS_DEFAULT;
|
||||
if (where == BORDER)
|
||||
key = KEYC_MOUSEDOWN8_BORDER;
|
||||
break;
|
||||
case MOUSE_BUTTON_9:
|
||||
if (where == PANE)
|
||||
key = KEYC_MOUSEDOWN9_PANE;
|
||||
if (where == STATUS)
|
||||
key = KEYC_MOUSEDOWN9_STATUS;
|
||||
if (where == STATUS_LEFT)
|
||||
key = KEYC_MOUSEDOWN9_STATUS_LEFT;
|
||||
if (where == STATUS_RIGHT)
|
||||
key = KEYC_MOUSEDOWN9_STATUS_RIGHT;
|
||||
if (where == STATUS_DEFAULT)
|
||||
key = KEYC_MOUSEDOWN9_STATUS_DEFAULT;
|
||||
if (where == BORDER)
|
||||
key = KEYC_MOUSEDOWN9_BORDER;
|
||||
break;
|
||||
case MOUSE_BUTTON_10:
|
||||
if (where == PANE)
|
||||
key = KEYC_MOUSEDOWN10_PANE;
|
||||
if (where == STATUS)
|
||||
key = KEYC_MOUSEDOWN10_STATUS;
|
||||
if (where == STATUS_LEFT)
|
||||
key = KEYC_MOUSEDOWN10_STATUS_LEFT;
|
||||
if (where == STATUS_RIGHT)
|
||||
key = KEYC_MOUSEDOWN10_STATUS_RIGHT;
|
||||
if (where == STATUS_DEFAULT)
|
||||
key = KEYC_MOUSEDOWN10_STATUS_DEFAULT;
|
||||
if (where == BORDER)
|
||||
key = KEYC_MOUSEDOWN10_BORDER;
|
||||
break;
|
||||
case MOUSE_BUTTON_11:
|
||||
if (where == PANE)
|
||||
key = KEYC_MOUSEDOWN11_PANE;
|
||||
if (where == STATUS)
|
||||
key = KEYC_MOUSEDOWN11_STATUS;
|
||||
if (where == STATUS_LEFT)
|
||||
key = KEYC_MOUSEDOWN11_STATUS_LEFT;
|
||||
if (where == STATUS_RIGHT)
|
||||
key = KEYC_MOUSEDOWN11_STATUS_RIGHT;
|
||||
if (where == STATUS_DEFAULT)
|
||||
key = KEYC_MOUSEDOWN11_STATUS_DEFAULT;
|
||||
if (where == BORDER)
|
||||
key = KEYC_MOUSEDOWN11_BORDER;
|
||||
break;
|
||||
}
|
||||
break;
|
||||
case SECOND:
|
||||
switch (MOUSE_BUTTONS(b)) {
|
||||
case 0:
|
||||
case MOUSE_BUTTON_1:
|
||||
if (where == PANE)
|
||||
key = KEYC_SECONDCLICK1_PANE;
|
||||
if (where == STATUS)
|
||||
@ -1024,7 +1362,7 @@ have_event:
|
||||
if (where == BORDER)
|
||||
key = KEYC_SECONDCLICK1_BORDER;
|
||||
break;
|
||||
case 1:
|
||||
case MOUSE_BUTTON_2:
|
||||
if (where == PANE)
|
||||
key = KEYC_SECONDCLICK2_PANE;
|
||||
if (where == STATUS)
|
||||
@ -1038,7 +1376,7 @@ have_event:
|
||||
if (where == BORDER)
|
||||
key = KEYC_SECONDCLICK2_BORDER;
|
||||
break;
|
||||
case 2:
|
||||
case MOUSE_BUTTON_3:
|
||||
if (where == PANE)
|
||||
key = KEYC_SECONDCLICK3_PANE;
|
||||
if (where == STATUS)
|
||||
@ -1052,11 +1390,95 @@ have_event:
|
||||
if (where == BORDER)
|
||||
key = KEYC_SECONDCLICK3_BORDER;
|
||||
break;
|
||||
case MOUSE_BUTTON_6:
|
||||
if (where == PANE)
|
||||
key = KEYC_SECONDCLICK6_PANE;
|
||||
if (where == STATUS)
|
||||
key = KEYC_SECONDCLICK6_STATUS;
|
||||
if (where == STATUS_LEFT)
|
||||
key = KEYC_SECONDCLICK6_STATUS_LEFT;
|
||||
if (where == STATUS_RIGHT)
|
||||
key = KEYC_SECONDCLICK6_STATUS_RIGHT;
|
||||
if (where == STATUS_DEFAULT)
|
||||
key = KEYC_SECONDCLICK6_STATUS_DEFAULT;
|
||||
if (where == BORDER)
|
||||
key = KEYC_SECONDCLICK6_BORDER;
|
||||
break;
|
||||
case MOUSE_BUTTON_7:
|
||||
if (where == PANE)
|
||||
key = KEYC_SECONDCLICK7_PANE;
|
||||
if (where == STATUS)
|
||||
key = KEYC_SECONDCLICK7_STATUS;
|
||||
if (where == STATUS_LEFT)
|
||||
key = KEYC_SECONDCLICK7_STATUS_LEFT;
|
||||
if (where == STATUS_RIGHT)
|
||||
key = KEYC_SECONDCLICK7_STATUS_RIGHT;
|
||||
if (where == STATUS_DEFAULT)
|
||||
key = KEYC_SECONDCLICK7_STATUS_DEFAULT;
|
||||
if (where == BORDER)
|
||||
key = KEYC_SECONDCLICK7_BORDER;
|
||||
break;
|
||||
case MOUSE_BUTTON_8:
|
||||
if (where == PANE)
|
||||
key = KEYC_SECONDCLICK8_PANE;
|
||||
if (where == STATUS)
|
||||
key = KEYC_SECONDCLICK8_STATUS;
|
||||
if (where == STATUS_LEFT)
|
||||
key = KEYC_SECONDCLICK8_STATUS_LEFT;
|
||||
if (where == STATUS_RIGHT)
|
||||
key = KEYC_SECONDCLICK8_STATUS_RIGHT;
|
||||
if (where == STATUS_DEFAULT)
|
||||
key = KEYC_SECONDCLICK8_STATUS_DEFAULT;
|
||||
if (where == BORDER)
|
||||
key = KEYC_SECONDCLICK8_BORDER;
|
||||
break;
|
||||
case MOUSE_BUTTON_9:
|
||||
if (where == PANE)
|
||||
key = KEYC_SECONDCLICK9_PANE;
|
||||
if (where == STATUS)
|
||||
key = KEYC_SECONDCLICK9_STATUS;
|
||||
if (where == STATUS_LEFT)
|
||||
key = KEYC_SECONDCLICK9_STATUS_LEFT;
|
||||
if (where == STATUS_RIGHT)
|
||||
key = KEYC_SECONDCLICK9_STATUS_RIGHT;
|
||||
if (where == STATUS_DEFAULT)
|
||||
key = KEYC_SECONDCLICK9_STATUS_DEFAULT;
|
||||
if (where == BORDER)
|
||||
key = KEYC_SECONDCLICK9_BORDER;
|
||||
break;
|
||||
case MOUSE_BUTTON_10:
|
||||
if (where == PANE)
|
||||
key = KEYC_SECONDCLICK10_PANE;
|
||||
if (where == STATUS)
|
||||
key = KEYC_SECONDCLICK10_STATUS;
|
||||
if (where == STATUS_LEFT)
|
||||
key = KEYC_SECONDCLICK10_STATUS_LEFT;
|
||||
if (where == STATUS_RIGHT)
|
||||
key = KEYC_SECONDCLICK10_STATUS_RIGHT;
|
||||
if (where == STATUS_DEFAULT)
|
||||
key = KEYC_SECONDCLICK10_STATUS_DEFAULT;
|
||||
if (where == BORDER)
|
||||
key = KEYC_SECONDCLICK10_BORDER;
|
||||
break;
|
||||
case MOUSE_BUTTON_11:
|
||||
if (where == PANE)
|
||||
key = KEYC_SECONDCLICK11_PANE;
|
||||
if (where == STATUS)
|
||||
key = KEYC_SECONDCLICK11_STATUS;
|
||||
if (where == STATUS_LEFT)
|
||||
key = KEYC_SECONDCLICK11_STATUS_LEFT;
|
||||
if (where == STATUS_RIGHT)
|
||||
key = KEYC_SECONDCLICK11_STATUS_RIGHT;
|
||||
if (where == STATUS_DEFAULT)
|
||||
key = KEYC_SECONDCLICK11_STATUS_DEFAULT;
|
||||
if (where == BORDER)
|
||||
key = KEYC_SECONDCLICK11_BORDER;
|
||||
break;
|
||||
}
|
||||
break;
|
||||
case DOUBLE:
|
||||
switch (MOUSE_BUTTONS(b)) {
|
||||
case 0:
|
||||
case MOUSE_BUTTON_1:
|
||||
if (where == PANE)
|
||||
key = KEYC_DOUBLECLICK1_PANE;
|
||||
if (where == STATUS)
|
||||
@ -1070,7 +1492,7 @@ have_event:
|
||||
if (where == BORDER)
|
||||
key = KEYC_DOUBLECLICK1_BORDER;
|
||||
break;
|
||||
case 1:
|
||||
case MOUSE_BUTTON_2:
|
||||
if (where == PANE)
|
||||
key = KEYC_DOUBLECLICK2_PANE;
|
||||
if (where == STATUS)
|
||||
@ -1084,7 +1506,7 @@ have_event:
|
||||
if (where == BORDER)
|
||||
key = KEYC_DOUBLECLICK2_BORDER;
|
||||
break;
|
||||
case 2:
|
||||
case MOUSE_BUTTON_3:
|
||||
if (where == PANE)
|
||||
key = KEYC_DOUBLECLICK3_PANE;
|
||||
if (where == STATUS)
|
||||
@ -1098,11 +1520,95 @@ have_event:
|
||||
if (where == BORDER)
|
||||
key = KEYC_DOUBLECLICK3_BORDER;
|
||||
break;
|
||||
case MOUSE_BUTTON_6:
|
||||
if (where == PANE)
|
||||
key = KEYC_DOUBLECLICK6_PANE;
|
||||
if (where == STATUS)
|
||||
key = KEYC_DOUBLECLICK6_STATUS;
|
||||
if (where == STATUS_LEFT)
|
||||
key = KEYC_DOUBLECLICK6_STATUS_LEFT;
|
||||
if (where == STATUS_RIGHT)
|
||||
key = KEYC_DOUBLECLICK6_STATUS_RIGHT;
|
||||
if (where == STATUS_DEFAULT)
|
||||
key = KEYC_DOUBLECLICK6_STATUS_DEFAULT;
|
||||
if (where == BORDER)
|
||||
key = KEYC_DOUBLECLICK6_BORDER;
|
||||
break;
|
||||
case MOUSE_BUTTON_7:
|
||||
if (where == PANE)
|
||||
key = KEYC_DOUBLECLICK7_PANE;
|
||||
if (where == STATUS)
|
||||
key = KEYC_DOUBLECLICK7_STATUS;
|
||||
if (where == STATUS_LEFT)
|
||||
key = KEYC_DOUBLECLICK7_STATUS_LEFT;
|
||||
if (where == STATUS_RIGHT)
|
||||
key = KEYC_DOUBLECLICK7_STATUS_RIGHT;
|
||||
if (where == STATUS_DEFAULT)
|
||||
key = KEYC_DOUBLECLICK7_STATUS_DEFAULT;
|
||||
if (where == BORDER)
|
||||
key = KEYC_DOUBLECLICK7_BORDER;
|
||||
break;
|
||||
case MOUSE_BUTTON_8:
|
||||
if (where == PANE)
|
||||
key = KEYC_DOUBLECLICK8_PANE;
|
||||
if (where == STATUS)
|
||||
key = KEYC_DOUBLECLICK8_STATUS;
|
||||
if (where == STATUS_LEFT)
|
||||
key = KEYC_DOUBLECLICK8_STATUS_LEFT;
|
||||
if (where == STATUS_RIGHT)
|
||||
key = KEYC_DOUBLECLICK8_STATUS_RIGHT;
|
||||
if (where == STATUS_DEFAULT)
|
||||
key = KEYC_DOUBLECLICK8_STATUS_DEFAULT;
|
||||
if (where == BORDER)
|
||||
key = KEYC_DOUBLECLICK8_BORDER;
|
||||
break;
|
||||
case MOUSE_BUTTON_9:
|
||||
if (where == PANE)
|
||||
key = KEYC_DOUBLECLICK9_PANE;
|
||||
if (where == STATUS)
|
||||
key = KEYC_DOUBLECLICK9_STATUS;
|
||||
if (where == STATUS_LEFT)
|
||||
key = KEYC_DOUBLECLICK9_STATUS_LEFT;
|
||||
if (where == STATUS_RIGHT)
|
||||
key = KEYC_DOUBLECLICK9_STATUS_RIGHT;
|
||||
if (where == STATUS_DEFAULT)
|
||||
key = KEYC_DOUBLECLICK9_STATUS_DEFAULT;
|
||||
if (where == BORDER)
|
||||
key = KEYC_DOUBLECLICK9_BORDER;
|
||||
break;
|
||||
case MOUSE_BUTTON_10:
|
||||
if (where == PANE)
|
||||
key = KEYC_DOUBLECLICK10_PANE;
|
||||
if (where == STATUS)
|
||||
key = KEYC_DOUBLECLICK10_STATUS;
|
||||
if (where == STATUS_LEFT)
|
||||
key = KEYC_DOUBLECLICK10_STATUS_LEFT;
|
||||
if (where == STATUS_RIGHT)
|
||||
key = KEYC_DOUBLECLICK10_STATUS_RIGHT;
|
||||
if (where == STATUS_DEFAULT)
|
||||
key = KEYC_DOUBLECLICK10_STATUS_DEFAULT;
|
||||
if (where == BORDER)
|
||||
key = KEYC_DOUBLECLICK10_BORDER;
|
||||
break;
|
||||
case MOUSE_BUTTON_11:
|
||||
if (where == PANE)
|
||||
key = KEYC_DOUBLECLICK11_PANE;
|
||||
if (where == STATUS)
|
||||
key = KEYC_DOUBLECLICK11_STATUS;
|
||||
if (where == STATUS_LEFT)
|
||||
key = KEYC_DOUBLECLICK11_STATUS_LEFT;
|
||||
if (where == STATUS_RIGHT)
|
||||
key = KEYC_DOUBLECLICK11_STATUS_RIGHT;
|
||||
if (where == STATUS_DEFAULT)
|
||||
key = KEYC_DOUBLECLICK11_STATUS_DEFAULT;
|
||||
if (where == BORDER)
|
||||
key = KEYC_DOUBLECLICK11_BORDER;
|
||||
break;
|
||||
}
|
||||
break;
|
||||
case TRIPLE:
|
||||
switch (MOUSE_BUTTONS(b)) {
|
||||
case 0:
|
||||
case MOUSE_BUTTON_1:
|
||||
if (where == PANE)
|
||||
key = KEYC_TRIPLECLICK1_PANE;
|
||||
if (where == STATUS)
|
||||
@ -1116,7 +1622,7 @@ have_event:
|
||||
if (where == BORDER)
|
||||
key = KEYC_TRIPLECLICK1_BORDER;
|
||||
break;
|
||||
case 1:
|
||||
case MOUSE_BUTTON_2:
|
||||
if (where == PANE)
|
||||
key = KEYC_TRIPLECLICK2_PANE;
|
||||
if (where == STATUS)
|
||||
@ -1130,7 +1636,7 @@ have_event:
|
||||
if (where == BORDER)
|
||||
key = KEYC_TRIPLECLICK2_BORDER;
|
||||
break;
|
||||
case 2:
|
||||
case MOUSE_BUTTON_3:
|
||||
if (where == PANE)
|
||||
key = KEYC_TRIPLECLICK3_PANE;
|
||||
if (where == STATUS)
|
||||
@ -1144,6 +1650,90 @@ have_event:
|
||||
if (where == BORDER)
|
||||
key = KEYC_TRIPLECLICK3_BORDER;
|
||||
break;
|
||||
case MOUSE_BUTTON_6:
|
||||
if (where == PANE)
|
||||
key = KEYC_TRIPLECLICK6_PANE;
|
||||
if (where == STATUS)
|
||||
key = KEYC_TRIPLECLICK6_STATUS;
|
||||
if (where == STATUS_LEFT)
|
||||
key = KEYC_TRIPLECLICK6_STATUS_LEFT;
|
||||
if (where == STATUS_RIGHT)
|
||||
key = KEYC_TRIPLECLICK6_STATUS_RIGHT;
|
||||
if (where == STATUS_DEFAULT)
|
||||
key = KEYC_TRIPLECLICK6_STATUS_DEFAULT;
|
||||
if (where == BORDER)
|
||||
key = KEYC_TRIPLECLICK6_BORDER;
|
||||
break;
|
||||
case MOUSE_BUTTON_7:
|
||||
if (where == PANE)
|
||||
key = KEYC_TRIPLECLICK7_PANE;
|
||||
if (where == STATUS)
|
||||
key = KEYC_TRIPLECLICK7_STATUS;
|
||||
if (where == STATUS_LEFT)
|
||||
key = KEYC_TRIPLECLICK7_STATUS_LEFT;
|
||||
if (where == STATUS_RIGHT)
|
||||
key = KEYC_TRIPLECLICK7_STATUS_RIGHT;
|
||||
if (where == STATUS_DEFAULT)
|
||||
key = KEYC_TRIPLECLICK7_STATUS_DEFAULT;
|
||||
if (where == BORDER)
|
||||
key = KEYC_TRIPLECLICK7_BORDER;
|
||||
break;
|
||||
case MOUSE_BUTTON_8:
|
||||
if (where == PANE)
|
||||
key = KEYC_TRIPLECLICK8_PANE;
|
||||
if (where == STATUS)
|
||||
key = KEYC_TRIPLECLICK8_STATUS;
|
||||
if (where == STATUS_LEFT)
|
||||
key = KEYC_TRIPLECLICK8_STATUS_LEFT;
|
||||
if (where == STATUS_RIGHT)
|
||||
key = KEYC_TRIPLECLICK8_STATUS_RIGHT;
|
||||
if (where == STATUS_DEFAULT)
|
||||
key = KEYC_TRIPLECLICK8_STATUS_DEFAULT;
|
||||
if (where == BORDER)
|
||||
key = KEYC_TRIPLECLICK8_BORDER;
|
||||
break;
|
||||
case MOUSE_BUTTON_9:
|
||||
if (where == PANE)
|
||||
key = KEYC_TRIPLECLICK9_PANE;
|
||||
if (where == STATUS)
|
||||
key = KEYC_TRIPLECLICK9_STATUS;
|
||||
if (where == STATUS_LEFT)
|
||||
key = KEYC_TRIPLECLICK9_STATUS_LEFT;
|
||||
if (where == STATUS_RIGHT)
|
||||
key = KEYC_TRIPLECLICK9_STATUS_RIGHT;
|
||||
if (where == STATUS_DEFAULT)
|
||||
key = KEYC_TRIPLECLICK9_STATUS_DEFAULT;
|
||||
if (where == BORDER)
|
||||
key = KEYC_TRIPLECLICK9_BORDER;
|
||||
break;
|
||||
case MOUSE_BUTTON_10:
|
||||
if (where == PANE)
|
||||
key = KEYC_TRIPLECLICK10_PANE;
|
||||
if (where == STATUS)
|
||||
key = KEYC_TRIPLECLICK10_STATUS;
|
||||
if (where == STATUS_LEFT)
|
||||
key = KEYC_TRIPLECLICK10_STATUS_LEFT;
|
||||
if (where == STATUS_RIGHT)
|
||||
key = KEYC_TRIPLECLICK10_STATUS_RIGHT;
|
||||
if (where == STATUS_DEFAULT)
|
||||
key = KEYC_TRIPLECLICK10_STATUS_DEFAULT;
|
||||
if (where == BORDER)
|
||||
key = KEYC_TRIPLECLICK10_BORDER;
|
||||
break;
|
||||
case MOUSE_BUTTON_11:
|
||||
if (where == PANE)
|
||||
key = KEYC_TRIPLECLICK11_PANE;
|
||||
if (where == STATUS)
|
||||
key = KEYC_TRIPLECLICK11_STATUS;
|
||||
if (where == STATUS_LEFT)
|
||||
key = KEYC_TRIPLECLICK11_STATUS_LEFT;
|
||||
if (where == STATUS_RIGHT)
|
||||
key = KEYC_TRIPLECLICK11_STATUS_RIGHT;
|
||||
if (where == STATUS_DEFAULT)
|
||||
key = KEYC_TRIPLECLICK11_STATUS_DEFAULT;
|
||||
if (where == BORDER)
|
||||
key = KEYC_TRIPLECLICK11_BORDER;
|
||||
break;
|
||||
}
|
||||
break;
|
||||
}
|
||||
@ -2011,8 +2601,10 @@ server_client_check_redraw(struct client *c)
|
||||
}
|
||||
|
||||
if (c->flags & CLIENT_ALLREDRAWFLAGS) {
|
||||
if (options_get_number(s->options, "set-titles"))
|
||||
if (options_get_number(s->options, "set-titles")) {
|
||||
server_client_set_title(c);
|
||||
server_client_set_path(c);
|
||||
}
|
||||
screen_redraw_screen(c);
|
||||
}
|
||||
|
||||
@ -2058,6 +2650,26 @@ server_client_set_title(struct client *c)
|
||||
format_free(ft);
|
||||
}
|
||||
|
||||
/* Set client path. */
|
||||
static void
|
||||
server_client_set_path(struct client *c)
|
||||
{
|
||||
struct session *s = c->session;
|
||||
const char *path;
|
||||
|
||||
if (s->curw == NULL)
|
||||
return;
|
||||
if (s->curw->window->active->base.path == NULL)
|
||||
path = "";
|
||||
else
|
||||
path = s->curw->window->active->base.path;
|
||||
if (c->path == NULL || strcmp(path, c->path) != 0) {
|
||||
free(c->path);
|
||||
c->path = xstrdup(path);
|
||||
tty_set_path(&c->tty, c->path);
|
||||
}
|
||||
}
|
||||
|
||||
/* Dispatch message from client. */
|
||||
static void
|
||||
server_client_dispatch(struct imsg *imsg, void *arg)
|
||||
|
38
server-fn.c
38
server-fn.c
@ -310,9 +310,11 @@ server_destroy_pane(struct window_pane *wp, int notify)
|
||||
struct window *w = wp->window;
|
||||
struct screen_write_ctx ctx;
|
||||
struct grid_cell gc;
|
||||
time_t t;
|
||||
char tim[26];
|
||||
int remain_on_exit;
|
||||
const char *s;
|
||||
char *expanded;
|
||||
u_int sx = screen_size_x(&wp->base);
|
||||
u_int sy = screen_size_y(&wp->base);
|
||||
|
||||
if (wp->fd != -1) {
|
||||
#ifdef HAVE_UTEMPTER
|
||||
@ -339,32 +341,26 @@ server_destroy_pane(struct window_pane *wp, int notify)
|
||||
return;
|
||||
wp->flags |= PANE_STATUSDRAWN;
|
||||
|
||||
gettimeofday(&wp->dead_time, NULL);
|
||||
if (notify)
|
||||
notify_pane("pane-died", wp);
|
||||
|
||||
screen_write_start_pane(&ctx, wp, &wp->base);
|
||||
screen_write_scrollregion(&ctx, 0, screen_size_y(ctx.s) - 1);
|
||||
screen_write_cursormove(&ctx, 0, screen_size_y(ctx.s) - 1, 0);
|
||||
screen_write_linefeed(&ctx, 1, 8);
|
||||
memcpy(&gc, &grid_default_cell, sizeof gc);
|
||||
s = options_get_string(wp->options, "remain-on-exit-format");
|
||||
if (*s != '\0') {
|
||||
screen_write_start_pane(&ctx, wp, &wp->base);
|
||||
screen_write_scrollregion(&ctx, 0, sy - 1);
|
||||
screen_write_cursormove(&ctx, 0, sy - 1, 0);
|
||||
screen_write_linefeed(&ctx, 1, 8);
|
||||
memcpy(&gc, &grid_default_cell, sizeof gc);
|
||||
|
||||
time(&t);
|
||||
ctime_r(&t, tim);
|
||||
tim[strcspn(tim, "\n")] = '\0';
|
||||
expanded = format_single(NULL, s, NULL, NULL, NULL, wp);
|
||||
format_draw(&ctx, &gc, sx, expanded, NULL, 0);
|
||||
free(expanded);
|
||||
|
||||
if (WIFEXITED(wp->status)) {
|
||||
screen_write_nputs(&ctx, -1, &gc,
|
||||
"Pane is dead (status %d, %s)",
|
||||
WEXITSTATUS(wp->status),
|
||||
tim);
|
||||
} else if (WIFSIGNALED(wp->status)) {
|
||||
screen_write_nputs(&ctx, -1, &gc,
|
||||
"Pane is dead (signal %s, %s)",
|
||||
sig2name(WTERMSIG(wp->status)),
|
||||
tim);
|
||||
screen_write_stop(&ctx);
|
||||
}
|
||||
wp->base.mode &= ~MODE_CURSOR;
|
||||
|
||||
screen_write_stop(&ctx);
|
||||
wp->flags |= PANE_REDRAW;
|
||||
return;
|
||||
}
|
||||
|
12
server.c
12
server.c
@ -100,7 +100,7 @@ server_check_marked(void)
|
||||
}
|
||||
|
||||
/* Create server socket. */
|
||||
static int
|
||||
int
|
||||
server_create_socket(int flags, char **cause)
|
||||
{
|
||||
struct sockaddr_un sa;
|
||||
@ -214,7 +214,11 @@ server_start(struct tmuxproc *client, int flags, struct event_base *base,
|
||||
|
||||
gettimeofday(&start_time, NULL);
|
||||
|
||||
#ifdef HAVE_SYSTEMD
|
||||
server_fd = systemd_create_socket(flags, &cause);
|
||||
#else
|
||||
server_fd = server_create_socket(flags, &cause);
|
||||
#endif
|
||||
if (server_fd != -1)
|
||||
server_update_socket();
|
||||
if (~flags & CLIENT_NOFORK)
|
||||
@ -230,10 +234,12 @@ server_start(struct tmuxproc *client, int flags, struct event_base *base,
|
||||
|
||||
if (cause != NULL) {
|
||||
if (c != NULL) {
|
||||
cmdq_append(c, cmdq_get_error(cause));
|
||||
c->exit_message = cause;
|
||||
c->flags |= CLIENT_EXIT;
|
||||
} else {
|
||||
fprintf(stderr, "%s\n", cause);
|
||||
exit(1);
|
||||
}
|
||||
free(cause);
|
||||
}
|
||||
|
||||
evtimer_set(&server_ev_tidy, server_tidy_event, NULL);
|
||||
|
@ -27,7 +27,7 @@
|
||||
#include "tmux.h"
|
||||
|
||||
struct sessions sessions;
|
||||
static u_int next_session_id;
|
||||
u_int next_session_id;
|
||||
struct session_groups session_groups = RB_INITIALIZER(&session_groups);
|
||||
|
||||
static void session_free(int, short, void *);
|
||||
@ -501,7 +501,8 @@ session_set_current(struct session *s, struct winlink *wl)
|
||||
winlink_stack_push(&s->lastw, s->curw);
|
||||
s->curw = wl;
|
||||
if (options_get_number(global_options, "focus-events")) {
|
||||
window_update_focus(old->window);
|
||||
if (old != NULL)
|
||||
window_update_focus(old->window);
|
||||
window_update_focus(wl->window);
|
||||
}
|
||||
winlink_clear_flags(wl);
|
||||
|
2
sixel.c
2
sixel.c
@ -554,7 +554,7 @@ sixel_to_screen(struct sixel_image *si)
|
||||
grid_view_set_cell(s->grid, x, y, &gc);
|
||||
}
|
||||
} else {
|
||||
screen_write_box(&ctx, sx, sy);
|
||||
screen_write_box(&ctx, sx, sy, BOX_LINES_DEFAULT, NULL, NULL);
|
||||
for (y = 1; y < sy - 1; y++) {
|
||||
for (x = 1; x < sx - 1; x++)
|
||||
grid_view_set_cell(s->grid, x, y, &gc);
|
||||
|
6
status.c
6
status.c
@ -718,7 +718,7 @@ status_prompt_redraw(struct client *c)
|
||||
memcpy(&cursorgc, &gc, sizeof cursorgc);
|
||||
cursorgc.attr ^= GRID_ATTR_REVERSE;
|
||||
|
||||
start = screen_write_strlen("%s", c->prompt_string);
|
||||
start = format_width(c->prompt_string);
|
||||
if (start > c->tty.sx)
|
||||
start = c->tty.sx;
|
||||
|
||||
@ -728,7 +728,7 @@ status_prompt_redraw(struct client *c)
|
||||
for (offset = 0; offset < c->tty.sx; offset++)
|
||||
screen_write_putc(&ctx, &gc, ' ');
|
||||
screen_write_cursormove(&ctx, 0, lines - 1, 0);
|
||||
screen_write_nputs(&ctx, start, &gc, "%s", c->prompt_string);
|
||||
format_draw(&ctx, &gc, start, c->prompt_string, NULL, 0);
|
||||
screen_write_cursormove(&ctx, start, lines - 1, 0);
|
||||
|
||||
left = c->tty.sx - start;
|
||||
@ -1798,7 +1798,7 @@ status_prompt_complete_window_menu(struct client *c, struct session *s,
|
||||
item.name = tmp;
|
||||
item.key = '0' + size - 1;
|
||||
item.command = NULL;
|
||||
menu_add_item(menu, &item, NULL, NULL, NULL);
|
||||
menu_add_item(menu, &item, NULL, c, NULL);
|
||||
free(tmp);
|
||||
|
||||
if (size == height)
|
||||
|
92
tmux.1
92
tmux.1
@ -43,7 +43,7 @@ then later reattached.
|
||||
.Pp
|
||||
When
|
||||
.Nm
|
||||
is started it creates a new
|
||||
is started, it creates a new
|
||||
.Em session
|
||||
with a single
|
||||
.Em window
|
||||
@ -140,7 +140,10 @@ By default,
|
||||
loads the system configuration file from
|
||||
.Pa @SYSCONFDIR@/tmux.conf ,
|
||||
if present, then looks for a user configuration file at
|
||||
.Pa ~/.tmux.conf .
|
||||
.Pa ~/.tmux.conf,
|
||||
.Pa $XDG_CONFIG_HOME/tmux/tmux.conf
|
||||
or
|
||||
.Pa ~/.config/tmux/tmux.conf .
|
||||
.Pp
|
||||
The configuration file is a set of
|
||||
.Nm
|
||||
@ -1338,11 +1341,12 @@ and sets an environment variable for the newly created session; it may be
|
||||
specified multiple times.
|
||||
.Tg refresh
|
||||
.It Xo Ic refresh-client
|
||||
.Op Fl cDlLRSU
|
||||
.Op Fl cDLRSU
|
||||
.Op Fl A Ar pane:state
|
||||
.Op Fl B Ar name:what:format
|
||||
.Op Fl C Ar size
|
||||
.Op Fl f Ar flags
|
||||
.Op Fl l Op Ar target-pane
|
||||
.Op Fl t Ar target-client
|
||||
.Op Ar adjustment
|
||||
.Xc
|
||||
@ -1456,7 +1460,11 @@ sets a comma-separated list of client flags, see
|
||||
.Fl l
|
||||
requests the clipboard from the client using the
|
||||
.Xr xterm 1
|
||||
escape sequence and stores it in a new paste buffer.
|
||||
escape sequence.
|
||||
If
|
||||
Ar target-pane
|
||||
is given, the clipboard is sent (in encoded form), otherwise it is stored in a
|
||||
new paste buffer.
|
||||
.Pp
|
||||
.Fl L ,
|
||||
.Fl R ,
|
||||
@ -1773,6 +1781,7 @@ The following commands are supported in copy mode:
|
||||
.It Li "set-mark" Ta "X" Ta "X"
|
||||
.It Li "start-of-line" Ta "0" Ta "C-a"
|
||||
.It Li "stop-selection" Ta "" Ta ""
|
||||
.It Li "toggle-position" Ta "P" Ta "P"
|
||||
.It Li "top-line" Ta "H" Ta "M-R"
|
||||
.El
|
||||
.Pp
|
||||
@ -3618,6 +3627,8 @@ Supports DECSLRM margins.
|
||||
Supports
|
||||
.Xr xterm 1
|
||||
mouse sequences.
|
||||
.It osc7
|
||||
Supports the OSC 7 working directory extension.
|
||||
.It overline
|
||||
Supports the overline SGR attribute.
|
||||
.It rectfill
|
||||
@ -4108,6 +4119,9 @@ Set clock colour.
|
||||
.Xc
|
||||
Set clock hour format.
|
||||
.Pp
|
||||
.It Ic fill-character Ar character
|
||||
Set the character used to fill areas of the terminal unused by a window.
|
||||
.Pp
|
||||
.It Ic main-pane-height Ar height
|
||||
.It Ic main-pane-width Ar width
|
||||
Set the width or height of the main (left or top) pane in the
|
||||
@ -4223,6 +4237,12 @@ but set the starting index for pane numbers.
|
||||
.It Ic pane-border-format Ar format
|
||||
Set the text shown in pane border status lines.
|
||||
.Pp
|
||||
.It Xo Ic pane-border-indicators
|
||||
.Op Ic off | colour | arrows | both
|
||||
.Xc
|
||||
Indicate active pane by colouring only half of the border in windows with
|
||||
exactly two panes, by displaying arrow markers, by drawing both or neither.
|
||||
.Pp
|
||||
.It Ic pane-border-lines Ar type
|
||||
Set the type of characters used for drawing pane borders.
|
||||
.Ar type
|
||||
@ -4396,6 +4416,13 @@ The default is on.
|
||||
Available pane options are:
|
||||
.Pp
|
||||
.Bl -tag -width Ds -compact
|
||||
.It Xo Ic allow-passthrough
|
||||
.Op Ic on | off
|
||||
.Xc
|
||||
Allow programs in the pane to bypass
|
||||
.Nm
|
||||
using a terminal escape sequence (\eePtmux;...\ee\e\e).
|
||||
.Pp
|
||||
.It Xo Ic allow-rename
|
||||
.Op Ic on | off
|
||||
.Xc
|
||||
@ -4449,6 +4476,17 @@ The pane may be reactivated with the
|
||||
.Ic respawn-pane
|
||||
command.
|
||||
.Pp
|
||||
.It Ic remain-on-exit-format Ar string
|
||||
Set the text shown at the bottom of exited panes when
|
||||
.Ic remain-on-exit
|
||||
is enabled.
|
||||
.Pp
|
||||
.It Xo Ic scroll-on-clear
|
||||
.Op Ic on | off
|
||||
.Xc
|
||||
When the entire screen is cleared and this option is on, scroll the contents of
|
||||
the screen into history before clearing it.
|
||||
.Pp
|
||||
.It Xo Ic synchronize-panes
|
||||
.Op Ic on | off
|
||||
.Xc
|
||||
@ -4575,6 +4613,11 @@ Run when a session is renamed.
|
||||
Run when a window is linked into a session.
|
||||
.It window-renamed
|
||||
Run when a window is renamed.
|
||||
.It window-resized
|
||||
Run when a window is resized.
|
||||
This may be after the
|
||||
.Ar client-resized
|
||||
hook is run.
|
||||
.It window-unlinked
|
||||
Run when a window is unlinked from a session.
|
||||
.El
|
||||
@ -4989,7 +5032,9 @@ commands to finish; instead, the previous result from running the same command i
|
||||
or a placeholder if the command has not been run before.
|
||||
If the command hasn't exited, the most recent line of output will be used, but the status
|
||||
line will not be updated more than once a second.
|
||||
Commands are executed with the
|
||||
Commands are executed using
|
||||
.Pa /bin/sh
|
||||
and with the
|
||||
.Nm
|
||||
global environment set (see the
|
||||
.Sx GLOBAL AND SESSION ENVIRONMENT
|
||||
@ -5033,6 +5078,8 @@ The following variables are available, where appropriate:
|
||||
.It Li "client_termname" Ta "" Ta "Terminal name of client"
|
||||
.It Li "client_termtype" Ta "" Ta "Terminal type of client, if available"
|
||||
.It Li "client_tty" Ta "" Ta "Pseudo terminal of client"
|
||||
.It Li "client_uid" Ta "" Ta "UID of client process"
|
||||
.It Li "client_user" Ta "" Ta "User of client process"
|
||||
.It Li "client_utf8" Ta "" Ta "1 if client supports UTF-8"
|
||||
.It Li "client_width" Ta "" Ta "Width of client"
|
||||
.It Li "client_written" Ta "" Ta "Bytes written to client"
|
||||
@ -5077,6 +5124,7 @@ The following variables are available, where appropriate:
|
||||
.It Li "mouse_word" Ta "" Ta "Word under mouse, if any"
|
||||
.It Li "mouse_x" Ta "" Ta "Mouse X position, if any"
|
||||
.It Li "mouse_y" Ta "" Ta "Mouse Y position, if any"
|
||||
.It Li "next_session_id" Ta "" Ta "Unique session ID for next new session"
|
||||
.It Li "origin_flag" Ta "" Ta "Pane origin flag"
|
||||
.It Li "pane_active" Ta "" Ta "1 if active pane"
|
||||
.It Li "pane_at_bottom" Ta "" Ta "1 if pane is at the bottom of window"
|
||||
@ -5088,7 +5136,9 @@ The following variables are available, where appropriate:
|
||||
.It Li "pane_current_command" Ta "" Ta "Current command if available"
|
||||
.It Li "pane_current_path" Ta "" Ta "Current path if available"
|
||||
.It Li "pane_dead" Ta "" Ta "1 if pane is dead"
|
||||
.It Li "pane_dead_signal" Ta "" Ta "Exit signal of process in dead pane"
|
||||
.It Li "pane_dead_status" Ta "" Ta "Exit status of process in dead pane"
|
||||
.It Li "pane_dead_time" Ta "" Ta "Exit time of process in dead pane"
|
||||
.It Li "pane_fg" Ta "" Ta "Pane foreground colour"
|
||||
.It Li "pane_format" Ta "" Ta "1 if format is for a pane"
|
||||
.It Li "pane_height" Ta "" Ta "Height of pane"
|
||||
@ -5149,6 +5199,8 @@ The following variables are available, where appropriate:
|
||||
.It Li "session_windows" Ta "" Ta "Number of windows in session"
|
||||
.It Li "socket_path" Ta "" Ta "Server socket path"
|
||||
.It Li "start_time" Ta "" Ta "Server start time"
|
||||
.It Li "uid" Ta "" Ta "Server UID"
|
||||
.It Li "user" Ta "" Ta "Server user"
|
||||
.It Li "version" Ta "" Ta "Server version"
|
||||
.It Li "window_active" Ta "" Ta "1 if window active"
|
||||
.It Li "window_active_clients" Ta "" Ta "Number of clients viewing this window"
|
||||
@ -5163,7 +5215,6 @@ The following variables are available, where appropriate:
|
||||
.It Li "window_cell_width" Ta "" Ta "Width of each cell in pixels"
|
||||
.It Li "window_end_flag" Ta "" Ta "1 if window has the highest index"
|
||||
.It Li "window_flags" Ta "#F" Ta "Window flags with # escaped as ##"
|
||||
.It Li "window_raw_flags" Ta "" Ta "Window flags with nothing escaped"
|
||||
.It Li "window_format" Ta "" Ta "1 if format is for a window"
|
||||
.It Li "window_height" Ta "" Ta "Height of window"
|
||||
.It Li "window_id" Ta "" Ta "Unique window ID"
|
||||
@ -5178,6 +5229,7 @@ The following variables are available, where appropriate:
|
||||
.It Li "window_offset_x" Ta "" Ta "X offset into window if larger than client"
|
||||
.It Li "window_offset_y" Ta "" Ta "Y offset into window if larger than client"
|
||||
.It Li "window_panes" Ta "" Ta "Number of panes in window"
|
||||
.It Li "window_raw_flags" Ta "" Ta "Window flags with nothing escaped"
|
||||
.It Li "window_silence_flag" Ta "" Ta "1 if window has silence alert"
|
||||
.It Li "window_stack_index" Ta "" Ta "Index in session most recent stack"
|
||||
.It Li "window_start_flag" Ta "" Ta "1 if window has the lowest index"
|
||||
@ -5866,7 +5918,7 @@ does not surround the popup by a border.
|
||||
sets the type of border line for the popup.
|
||||
When
|
||||
.Fl B
|
||||
is specified the
|
||||
is specified, the
|
||||
.Fl b
|
||||
option is ignored.
|
||||
See
|
||||
@ -6155,6 +6207,8 @@ Execute the first
|
||||
.Ar command
|
||||
if
|
||||
.Ar shell-command
|
||||
(run with
|
||||
.Pa /bin/sh )
|
||||
returns success or the second
|
||||
.Ar command
|
||||
otherwise.
|
||||
@ -6191,6 +6245,8 @@ option.
|
||||
.D1 Pq alias: Ic run
|
||||
Execute
|
||||
.Ar shell-command
|
||||
using
|
||||
.Pa /bin/sh
|
||||
or (with
|
||||
.Fl C )
|
||||
a
|
||||
@ -6292,6 +6348,11 @@ to change the cursor colour from inside
|
||||
.Bd -literal -offset indent
|
||||
$ printf '\e033]12;red\e033\e\e'
|
||||
.Ed
|
||||
.Pp
|
||||
The colour is an
|
||||
.Xr X 7
|
||||
colour, see
|
||||
.Xr XParseColor 3 .
|
||||
.It Em \&Cmg, \&Clmg, \&Dsmg , \&Enmg
|
||||
Set, clear, disable or enable DECSLRM margins.
|
||||
These are set automatically if the terminal reports it is
|
||||
@ -6335,6 +6396,11 @@ $ printf '\e033[4 q'
|
||||
If
|
||||
.Em Se
|
||||
is not set, \&Ss with argument 0 will be used to reset the cursor style instead.
|
||||
.It Em \&Swd
|
||||
Set the opening sequence for the working directory notification.
|
||||
The sequence is terminated using the standard
|
||||
.Em fsl
|
||||
capability.
|
||||
.It Em \&Sxl
|
||||
Indicates that the terminal supports SIXEL.
|
||||
.It Em \&Sync
|
||||
@ -6509,6 +6575,14 @@ are for future use and should be ignored.
|
||||
The window with ID
|
||||
.Ar window-id
|
||||
was created but is not linked to the current session.
|
||||
.It Ic %unlinked-window-close Ar window-id
|
||||
The window with ID
|
||||
.Ar window-id ,
|
||||
which is not linked to the current session, was closed.
|
||||
.It Ic %unlinked-window-renamed Ar window-id
|
||||
The window with ID
|
||||
.Ar window-id ,
|
||||
which is not linked to the current session, was renamed.
|
||||
.It Ic %window-add Ar window-id
|
||||
The window with ID
|
||||
.Ar window-id
|
||||
@ -6567,7 +6641,7 @@ are replaced with underscores
|
||||
For input,
|
||||
.Nm
|
||||
always runs with a UTF-8 locale.
|
||||
If en_US.UTF-8 is provided by the operating system it is used and
|
||||
If en_US.UTF-8 is provided by the operating system, it is used and
|
||||
.Ev LC_CTYPE
|
||||
is ignored for input.
|
||||
Otherwise,
|
||||
@ -6616,6 +6690,8 @@ options.
|
||||
.Sh FILES
|
||||
.Bl -tag -width "@SYSCONFDIR@/tmux.confXXX" -compact
|
||||
.It Pa ~/.tmux.conf
|
||||
.It Pa $XDG_CONFIG_HOME/tmux/tmux.conf
|
||||
.It Pa ~/.config/tmux/tmux.conf
|
||||
Default
|
||||
.Nm
|
||||
configuration file.
|
||||
|
312
tmux.h
312
tmux.h
@ -203,26 +203,68 @@ enum {
|
||||
KEYC_MOUSE_KEY(MOUSEDOWN1),
|
||||
KEYC_MOUSE_KEY(MOUSEDOWN2),
|
||||
KEYC_MOUSE_KEY(MOUSEDOWN3),
|
||||
KEYC_MOUSE_KEY(MOUSEDOWN6),
|
||||
KEYC_MOUSE_KEY(MOUSEDOWN7),
|
||||
KEYC_MOUSE_KEY(MOUSEDOWN8),
|
||||
KEYC_MOUSE_KEY(MOUSEDOWN9),
|
||||
KEYC_MOUSE_KEY(MOUSEDOWN10),
|
||||
KEYC_MOUSE_KEY(MOUSEDOWN11),
|
||||
KEYC_MOUSE_KEY(MOUSEUP1),
|
||||
KEYC_MOUSE_KEY(MOUSEUP2),
|
||||
KEYC_MOUSE_KEY(MOUSEUP3),
|
||||
KEYC_MOUSE_KEY(MOUSEUP6),
|
||||
KEYC_MOUSE_KEY(MOUSEUP7),
|
||||
KEYC_MOUSE_KEY(MOUSEUP8),
|
||||
KEYC_MOUSE_KEY(MOUSEUP9),
|
||||
KEYC_MOUSE_KEY(MOUSEUP10),
|
||||
KEYC_MOUSE_KEY(MOUSEUP11),
|
||||
KEYC_MOUSE_KEY(MOUSEDRAG1),
|
||||
KEYC_MOUSE_KEY(MOUSEDRAG2),
|
||||
KEYC_MOUSE_KEY(MOUSEDRAG3),
|
||||
KEYC_MOUSE_KEY(MOUSEDRAG6),
|
||||
KEYC_MOUSE_KEY(MOUSEDRAG7),
|
||||
KEYC_MOUSE_KEY(MOUSEDRAG8),
|
||||
KEYC_MOUSE_KEY(MOUSEDRAG9),
|
||||
KEYC_MOUSE_KEY(MOUSEDRAG10),
|
||||
KEYC_MOUSE_KEY(MOUSEDRAG11),
|
||||
KEYC_MOUSE_KEY(MOUSEDRAGEND1),
|
||||
KEYC_MOUSE_KEY(MOUSEDRAGEND2),
|
||||
KEYC_MOUSE_KEY(MOUSEDRAGEND3),
|
||||
KEYC_MOUSE_KEY(MOUSEDRAGEND6),
|
||||
KEYC_MOUSE_KEY(MOUSEDRAGEND7),
|
||||
KEYC_MOUSE_KEY(MOUSEDRAGEND8),
|
||||
KEYC_MOUSE_KEY(MOUSEDRAGEND9),
|
||||
KEYC_MOUSE_KEY(MOUSEDRAGEND10),
|
||||
KEYC_MOUSE_KEY(MOUSEDRAGEND11),
|
||||
KEYC_MOUSE_KEY(WHEELUP),
|
||||
KEYC_MOUSE_KEY(WHEELDOWN),
|
||||
KEYC_MOUSE_KEY(SECONDCLICK1),
|
||||
KEYC_MOUSE_KEY(SECONDCLICK2),
|
||||
KEYC_MOUSE_KEY(SECONDCLICK3),
|
||||
KEYC_MOUSE_KEY(SECONDCLICK6),
|
||||
KEYC_MOUSE_KEY(SECONDCLICK7),
|
||||
KEYC_MOUSE_KEY(SECONDCLICK8),
|
||||
KEYC_MOUSE_KEY(SECONDCLICK9),
|
||||
KEYC_MOUSE_KEY(SECONDCLICK10),
|
||||
KEYC_MOUSE_KEY(SECONDCLICK11),
|
||||
KEYC_MOUSE_KEY(DOUBLECLICK1),
|
||||
KEYC_MOUSE_KEY(DOUBLECLICK2),
|
||||
KEYC_MOUSE_KEY(DOUBLECLICK3),
|
||||
KEYC_MOUSE_KEY(DOUBLECLICK6),
|
||||
KEYC_MOUSE_KEY(DOUBLECLICK7),
|
||||
KEYC_MOUSE_KEY(DOUBLECLICK8),
|
||||
KEYC_MOUSE_KEY(DOUBLECLICK9),
|
||||
KEYC_MOUSE_KEY(DOUBLECLICK10),
|
||||
KEYC_MOUSE_KEY(DOUBLECLICK11),
|
||||
KEYC_MOUSE_KEY(TRIPLECLICK1),
|
||||
KEYC_MOUSE_KEY(TRIPLECLICK2),
|
||||
KEYC_MOUSE_KEY(TRIPLECLICK3),
|
||||
KEYC_MOUSE_KEY(TRIPLECLICK6),
|
||||
KEYC_MOUSE_KEY(TRIPLECLICK7),
|
||||
KEYC_MOUSE_KEY(TRIPLECLICK8),
|
||||
KEYC_MOUSE_KEY(TRIPLECLICK9),
|
||||
KEYC_MOUSE_KEY(TRIPLECLICK10),
|
||||
KEYC_MOUSE_KEY(TRIPLECLICK11),
|
||||
|
||||
/* Backspace key. */
|
||||
KEYC_BSPACE,
|
||||
@ -500,6 +542,7 @@ enum tty_code_code {
|
||||
TTYC_SMXX,
|
||||
TTYC_SXL,
|
||||
TTYC_SS,
|
||||
TTYC_SWD,
|
||||
TTYC_SYNC,
|
||||
TTYC_TC,
|
||||
TTYC_TSL,
|
||||
@ -671,15 +714,15 @@ struct grid_cell_entry {
|
||||
|
||||
/* Grid line. */
|
||||
struct grid_line {
|
||||
struct grid_cell_entry *celldata;
|
||||
u_int cellused;
|
||||
u_int cellsize;
|
||||
struct grid_cell_entry *celldata;
|
||||
|
||||
u_int extdsize;
|
||||
struct grid_extd_entry *extddata;
|
||||
u_int extdsize;
|
||||
|
||||
int flags;
|
||||
} __packed;
|
||||
};
|
||||
|
||||
/* Entire grid of cells. */
|
||||
struct grid {
|
||||
@ -814,7 +857,6 @@ struct screen {
|
||||
struct grid_cell saved_cell;
|
||||
int saved_flags;
|
||||
|
||||
int mode;
|
||||
bitstr_t *tabs;
|
||||
struct screen_sel *sel;
|
||||
struct images images;
|
||||
@ -862,6 +904,12 @@ enum pane_lines {
|
||||
PANE_LINES_NUMBER
|
||||
};
|
||||
|
||||
/* Pane border indicator option. */
|
||||
#define PANE_BORDER_OFF 0
|
||||
#define PANE_BORDER_COLOUR 1
|
||||
#define PANE_BORDER_ARROWS 2
|
||||
#define PANE_BORDER_BOTH 3
|
||||
|
||||
/* Screen redraw context. */
|
||||
struct screen_redraw_ctx {
|
||||
struct client *c;
|
||||
@ -998,6 +1046,7 @@ struct window_pane {
|
||||
pid_t pid;
|
||||
char tty[TTY_NAME_MAX];
|
||||
int status;
|
||||
struct timeval dead_time;
|
||||
|
||||
int fd;
|
||||
struct bufferevent *event;
|
||||
@ -1040,40 +1089,41 @@ RB_HEAD(window_pane_tree, window_pane);
|
||||
|
||||
/* Window structure. */
|
||||
struct window {
|
||||
u_int id;
|
||||
void *latest;
|
||||
u_int id;
|
||||
void *latest;
|
||||
|
||||
char *name;
|
||||
struct event name_event;
|
||||
struct timeval name_time;
|
||||
char *name;
|
||||
struct event name_event;
|
||||
struct timeval name_time;
|
||||
|
||||
struct event alerts_timer;
|
||||
struct event offset_timer;
|
||||
struct event alerts_timer;
|
||||
struct event offset_timer;
|
||||
|
||||
struct timeval activity_time;
|
||||
struct timeval activity_time;
|
||||
|
||||
struct window_pane *active;
|
||||
struct window_pane *last;
|
||||
struct window_panes panes;
|
||||
struct window_pane *active;
|
||||
struct window_pane *last;
|
||||
struct window_panes panes;
|
||||
|
||||
int lastlayout;
|
||||
struct layout_cell *layout_root;
|
||||
struct layout_cell *saved_layout_root;
|
||||
char *old_layout;
|
||||
int lastlayout;
|
||||
struct layout_cell *layout_root;
|
||||
struct layout_cell *saved_layout_root;
|
||||
char *old_layout;
|
||||
|
||||
u_int sx;
|
||||
u_int sy;
|
||||
u_int manual_sx;
|
||||
u_int manual_sy;
|
||||
u_int xpixel;
|
||||
u_int ypixel;
|
||||
u_int sx;
|
||||
u_int sy;
|
||||
u_int manual_sx;
|
||||
u_int manual_sy;
|
||||
u_int xpixel;
|
||||
u_int ypixel;
|
||||
|
||||
u_int new_sx;
|
||||
u_int new_sy;
|
||||
u_int new_xpixel;
|
||||
u_int new_ypixel;
|
||||
u_int new_sx;
|
||||
u_int new_sy;
|
||||
u_int new_xpixel;
|
||||
u_int new_ypixel;
|
||||
|
||||
int flags;
|
||||
struct utf8_data *fill_character;
|
||||
int flags;
|
||||
#define WINDOW_BELL 0x1
|
||||
#define WINDOW_ACTIVITY 0x2
|
||||
#define WINDOW_SILENCE 0x4
|
||||
@ -1082,15 +1132,15 @@ struct window {
|
||||
#define WINDOW_RESIZE 0x20
|
||||
#define WINDOW_ALERTFLAGS (WINDOW_BELL|WINDOW_ACTIVITY|WINDOW_SILENCE)
|
||||
|
||||
int alerts_queued;
|
||||
TAILQ_ENTRY(window) alerts_entry;
|
||||
int alerts_queued;
|
||||
TAILQ_ENTRY(window) alerts_entry;
|
||||
|
||||
struct options *options;
|
||||
struct options *options;
|
||||
|
||||
u_int references;
|
||||
TAILQ_HEAD(, winlink) winlinks;
|
||||
u_int references;
|
||||
TAILQ_HEAD(, winlink) winlinks;
|
||||
|
||||
RB_ENTRY(window) entry;
|
||||
RB_ENTRY(window) entry;
|
||||
};
|
||||
RB_HEAD(windows, window);
|
||||
|
||||
@ -1212,21 +1262,33 @@ struct session {
|
||||
RB_HEAD(sessions, session);
|
||||
|
||||
/* Mouse button masks. */
|
||||
#define MOUSE_MASK_BUTTONS 3
|
||||
#define MOUSE_MASK_BUTTONS 195
|
||||
#define MOUSE_MASK_SHIFT 4
|
||||
#define MOUSE_MASK_META 8
|
||||
#define MOUSE_MASK_CTRL 16
|
||||
#define MOUSE_MASK_DRAG 32
|
||||
#define MOUSE_MASK_WHEEL 64
|
||||
#define MOUSE_MASK_MODIFIERS (MOUSE_MASK_SHIFT|MOUSE_MASK_META|MOUSE_MASK_CTRL)
|
||||
|
||||
/* Mouse wheel states. */
|
||||
#define MOUSE_WHEEL_UP 0
|
||||
#define MOUSE_WHEEL_DOWN 1
|
||||
/* Mouse wheel type. */
|
||||
#define MOUSE_WHEEL_UP 64
|
||||
#define MOUSE_WHEEL_DOWN 65
|
||||
|
||||
/* Mouse button type. */
|
||||
#define MOUSE_BUTTON_1 0
|
||||
#define MOUSE_BUTTON_2 1
|
||||
#define MOUSE_BUTTON_3 2
|
||||
#define MOUSE_BUTTON_6 66
|
||||
#define MOUSE_BUTTON_7 67
|
||||
#define MOUSE_BUTTON_8 128
|
||||
#define MOUSE_BUTTON_9 129
|
||||
#define MOUSE_BUTTON_10 130
|
||||
#define MOUSE_BUTTON_11 131
|
||||
|
||||
/* Mouse helpers. */
|
||||
#define MOUSE_BUTTONS(b) ((b) & MOUSE_MASK_BUTTONS)
|
||||
#define MOUSE_WHEEL(b) ((b) & MOUSE_MASK_WHEEL)
|
||||
#define MOUSE_WHEEL(b) \
|
||||
(((b) & MOUSE_MASK_BUTTONS) == MOUSE_WHEEL_UP || \
|
||||
((b) & MOUSE_MASK_BUTTONS) == MOUSE_WHEEL_DOWN)
|
||||
#define MOUSE_DRAG(b) ((b) & MOUSE_MASK_DRAG)
|
||||
#define MOUSE_RELEASE(b) (((b) & MOUSE_MASK_BUTTONS) == 3)
|
||||
|
||||
@ -1292,6 +1354,7 @@ LIST_HEAD(tty_terms, tty_term);
|
||||
struct tty {
|
||||
struct client *client;
|
||||
struct event start_timer;
|
||||
struct event clipboard_timer;
|
||||
|
||||
u_int sx;
|
||||
u_int sy;
|
||||
@ -1332,15 +1395,14 @@ struct tty {
|
||||
#define TTY_NOCURSOR 0x1
|
||||
#define TTY_FREEZE 0x2
|
||||
#define TTY_TIMER 0x4
|
||||
/* 0x8 unused */
|
||||
#define TTY_NOBLOCK 0x8
|
||||
#define TTY_STARTED 0x10
|
||||
#define TTY_OPENED 0x20
|
||||
/* 0x40 unused */
|
||||
#define TTY_OSC52QUERY 0x40
|
||||
#define TTY_BLOCK 0x80
|
||||
#define TTY_HAVEDA 0x100
|
||||
#define TTY_HAVEXDA 0x200
|
||||
#define TTY_SYNCING 0x400
|
||||
#define TTY_NOBLOCK 0x800
|
||||
int flags;
|
||||
|
||||
struct tty_term *term;
|
||||
@ -1646,50 +1708,51 @@ typedef int (*overlay_key_cb)(struct client *, void *, struct key_event *);
|
||||
typedef void (*overlay_free_cb)(struct client *, void *);
|
||||
typedef void (*overlay_resize_cb)(struct client *, void *);
|
||||
struct client {
|
||||
const char *name;
|
||||
struct tmuxpeer *peer;
|
||||
struct cmdq_list *queue;
|
||||
const char *name;
|
||||
struct tmuxpeer *peer;
|
||||
struct cmdq_list *queue;
|
||||
|
||||
struct client_windows windows;
|
||||
struct client_windows windows;
|
||||
|
||||
struct control_state *control_state;
|
||||
u_int pause_age;
|
||||
struct control_state *control_state;
|
||||
u_int pause_age;
|
||||
|
||||
pid_t pid;
|
||||
int fd;
|
||||
int out_fd;
|
||||
struct event event;
|
||||
int retval;
|
||||
pid_t pid;
|
||||
int fd;
|
||||
int out_fd;
|
||||
struct event event;
|
||||
int retval;
|
||||
|
||||
struct timeval creation_time;
|
||||
struct timeval activity_time;
|
||||
struct timeval creation_time;
|
||||
struct timeval activity_time;
|
||||
|
||||
struct environ *environ;
|
||||
struct environ *environ;
|
||||
struct format_job_tree *jobs;
|
||||
|
||||
char *title;
|
||||
const char *cwd;
|
||||
char *title;
|
||||
char *path;
|
||||
const char *cwd;
|
||||
|
||||
char *term_name;
|
||||
int term_features;
|
||||
char *term_type;
|
||||
char **term_caps;
|
||||
u_int term_ncaps;
|
||||
char *term_name;
|
||||
int term_features;
|
||||
char *term_type;
|
||||
char **term_caps;
|
||||
u_int term_ncaps;
|
||||
|
||||
char *ttyname;
|
||||
struct tty tty;
|
||||
char *ttyname;
|
||||
struct tty tty;
|
||||
|
||||
size_t written;
|
||||
size_t discarded;
|
||||
size_t redraw;
|
||||
size_t written;
|
||||
size_t discarded;
|
||||
size_t redraw;
|
||||
|
||||
struct event repeat_timer;
|
||||
struct event repeat_timer;
|
||||
|
||||
struct event click_timer;
|
||||
u_int click_button;
|
||||
struct mouse_event click_event;
|
||||
struct event click_timer;
|
||||
u_int click_button;
|
||||
struct mouse_event click_event;
|
||||
|
||||
struct status_line status;
|
||||
struct status_line status;
|
||||
|
||||
#define CLIENT_TERMINAL 0x1
|
||||
#define CLIENT_LOGIN 0x2
|
||||
@ -1726,6 +1789,7 @@ struct client {
|
||||
#define CLIENT_CONTROL_PAUSEAFTER 0x100000000ULL
|
||||
#define CLIENT_CONTROL_WAITEXIT 0x200000000ULL
|
||||
#define CLIENT_WINDOWSIZECHANGED 0x400000000ULL
|
||||
#define CLIENT_CLIPBOARDBUFFER 0x800000000ULL
|
||||
#define CLIENT_ALLREDRAWFLAGS \
|
||||
(CLIENT_REDRAWWINDOW| \
|
||||
CLIENT_REDRAWSTATUS| \
|
||||
@ -1737,73 +1801,79 @@ struct client {
|
||||
(CLIENT_DEAD| \
|
||||
CLIENT_SUSPENDED| \
|
||||
CLIENT_EXIT)
|
||||
#define CLIENT_NODETACHFLAGS \
|
||||
#define CLIENT_NODETACHFLAGS \
|
||||
(CLIENT_DEAD| \
|
||||
CLIENT_EXIT)
|
||||
#define CLIENT_NOSIZEFLAGS \
|
||||
(CLIENT_DEAD| \
|
||||
CLIENT_SUSPENDED| \
|
||||
CLIENT_EXIT)
|
||||
uint64_t flags;
|
||||
uint64_t flags;
|
||||
|
||||
enum {
|
||||
CLIENT_EXIT_RETURN,
|
||||
CLIENT_EXIT_SHUTDOWN,
|
||||
CLIENT_EXIT_DETACH
|
||||
} exit_type;
|
||||
enum msgtype exit_msgtype;
|
||||
char *exit_session;
|
||||
char *exit_message;
|
||||
} exit_type;
|
||||
enum msgtype exit_msgtype;
|
||||
char *exit_session;
|
||||
char *exit_message;
|
||||
|
||||
struct key_table *keytable;
|
||||
struct key_table *keytable;
|
||||
|
||||
uint64_t redraw_panes;
|
||||
uint64_t redraw_panes;
|
||||
|
||||
int message_ignore_keys;
|
||||
int message_ignore_styles;
|
||||
char *message_string;
|
||||
struct event message_timer;
|
||||
int message_ignore_keys;
|
||||
int message_ignore_styles;
|
||||
char *message_string;
|
||||
struct event message_timer;
|
||||
|
||||
char *prompt_string;
|
||||
struct utf8_data *prompt_buffer;
|
||||
char *prompt_last;
|
||||
size_t prompt_index;
|
||||
prompt_input_cb prompt_inputcb;
|
||||
prompt_free_cb prompt_freecb;
|
||||
void *prompt_data;
|
||||
u_int prompt_hindex[PROMPT_NTYPES];
|
||||
enum { PROMPT_ENTRY, PROMPT_COMMAND } prompt_mode;
|
||||
struct utf8_data *prompt_saved;
|
||||
char *prompt_string;
|
||||
struct utf8_data *prompt_buffer;
|
||||
char *prompt_last;
|
||||
size_t prompt_index;
|
||||
prompt_input_cb prompt_inputcb;
|
||||
prompt_free_cb prompt_freecb;
|
||||
void *prompt_data;
|
||||
u_int prompt_hindex[PROMPT_NTYPES];
|
||||
enum {
|
||||
PROMPT_ENTRY,
|
||||
PROMPT_COMMAND
|
||||
} prompt_mode;
|
||||
struct utf8_data *prompt_saved;
|
||||
#define PROMPT_SINGLE 0x1
|
||||
#define PROMPT_NUMERIC 0x2
|
||||
#define PROMPT_INCREMENTAL 0x4
|
||||
#define PROMPT_NOFORMAT 0x8
|
||||
#define PROMPT_KEY 0x10
|
||||
int prompt_flags;
|
||||
enum prompt_type prompt_type;
|
||||
int prompt_cursor;
|
||||
int prompt_flags;
|
||||
enum prompt_type prompt_type;
|
||||
int prompt_cursor;
|
||||
|
||||
struct session *session;
|
||||
struct session *last_session;
|
||||
struct session *session;
|
||||
struct session *last_session;
|
||||
|
||||
int references;
|
||||
int references;
|
||||
|
||||
void *pan_window;
|
||||
u_int pan_ox;
|
||||
u_int pan_oy;
|
||||
void *pan_window;
|
||||
u_int pan_ox;
|
||||
u_int pan_oy;
|
||||
|
||||
overlay_check_cb overlay_check;
|
||||
overlay_mode_cb overlay_mode;
|
||||
overlay_draw_cb overlay_draw;
|
||||
overlay_key_cb overlay_key;
|
||||
overlay_free_cb overlay_free;
|
||||
overlay_resize_cb overlay_resize;
|
||||
void *overlay_data;
|
||||
struct event overlay_timer;
|
||||
overlay_check_cb overlay_check;
|
||||
overlay_mode_cb overlay_mode;
|
||||
overlay_draw_cb overlay_draw;
|
||||
overlay_key_cb overlay_key;
|
||||
overlay_free_cb overlay_free;
|
||||
overlay_resize_cb overlay_resize;
|
||||
void *overlay_data;
|
||||
struct event overlay_timer;
|
||||
|
||||
struct client_files files;
|
||||
struct client_files files;
|
||||
|
||||
TAILQ_ENTRY(client) entry;
|
||||
u_int *clipboard_panes;
|
||||
u_int clipboard_npanes;
|
||||
|
||||
TAILQ_ENTRY(client) entry;
|
||||
};
|
||||
TAILQ_HEAD(clients, client);
|
||||
|
||||
@ -1977,6 +2047,7 @@ void proc_remove_peer(struct tmuxpeer *);
|
||||
void proc_kill_peer(struct tmuxpeer *);
|
||||
void proc_toggle_log(struct tmuxproc *);
|
||||
pid_t proc_fork_and_daemon(int *);
|
||||
uid_t proc_get_peer_uid(struct tmuxpeer *);
|
||||
|
||||
/* cfg.c */
|
||||
extern int cfg_finished;
|
||||
@ -2190,6 +2261,7 @@ void tty_reset(struct tty *);
|
||||
void tty_region_off(struct tty *);
|
||||
void tty_margin_off(struct tty *);
|
||||
void tty_cursor(struct tty *, u_int, u_int);
|
||||
void tty_clipboard_query(struct tty *);
|
||||
void tty_putcode(struct tty *, enum tty_code_code);
|
||||
void tty_putcode1(struct tty *, enum tty_code_code, int);
|
||||
void tty_putcode2(struct tty *, enum tty_code_code, int, int);
|
||||
@ -2209,6 +2281,7 @@ void tty_start_tty(struct tty *);
|
||||
void tty_send_requests(struct tty *);
|
||||
void tty_stop_tty(struct tty *);
|
||||
void tty_set_title(struct tty *, const char *);
|
||||
void tty_set_path(struct tty *, const char *);
|
||||
void tty_update_mode(struct tty *, int, struct screen *);
|
||||
void tty_draw_line(struct tty *, struct screen *, u_int, u_int, u_int,
|
||||
u_int, u_int, const struct grid_cell *, struct colour_palette *);
|
||||
@ -2532,6 +2605,7 @@ int server_start(struct tmuxproc *, int, struct event_base *, int, char *);
|
||||
void server_update_socket(void);
|
||||
void server_add_accept(int);
|
||||
void printflike(1, 2) server_add_message(const char *, ...);
|
||||
int server_create_socket(int, char **);
|
||||
|
||||
/* server-client.c */
|
||||
RB_PROTOTYPE(client_windows, client_window, entry, server_client_window_cmp);
|
||||
@ -2637,6 +2711,8 @@ void input_parse_pane(struct window_pane *);
|
||||
void input_parse_buffer(struct window_pane *, u_char *, size_t);
|
||||
void input_parse_screen(struct input_ctx *, struct screen *,
|
||||
screen_write_init_ctx_cb, void *, u_char *, size_t);
|
||||
void input_reply_clipboard(struct bufferevent *, const char *, size_t,
|
||||
const char *);
|
||||
|
||||
/* input-key.c */
|
||||
void input_key_build(void);
|
||||
@ -2930,6 +3006,7 @@ void *window_pane_get_new_data(struct window_pane *,
|
||||
struct window_pane_offset *, size_t *);
|
||||
void window_pane_update_used_data(struct window_pane *,
|
||||
struct window_pane_offset *, size_t);
|
||||
void window_set_fill_character(struct window *);
|
||||
|
||||
/* layout.c */
|
||||
u_int layout_count_cells(struct layout_cell *);
|
||||
@ -3083,6 +3160,7 @@ void control_notify_session_window_changed(struct session *);
|
||||
|
||||
/* session.c */
|
||||
extern struct sessions sessions;
|
||||
extern u_int next_session_id;
|
||||
int session_cmp(struct session *, struct session *);
|
||||
RB_PROTOTYPE(sessions, session, entry, session_cmp);
|
||||
int session_alive(struct session *);
|
||||
|
@ -53,6 +53,18 @@ static const struct tty_feature tty_feature_title = {
|
||||
0
|
||||
};
|
||||
|
||||
/* Terminal has OSC 7 working directory. */
|
||||
static const char *tty_feature_osc7_capabilities[] = {
|
||||
"Swd=\\E]7;",
|
||||
"fsl=\\a",
|
||||
NULL
|
||||
};
|
||||
static const struct tty_feature tty_feature_osc7 = {
|
||||
"osc7",
|
||||
tty_feature_osc7_capabilities,
|
||||
0
|
||||
};
|
||||
|
||||
/* Terminal has mouse support. */
|
||||
static const char *tty_feature_mouse_capabilities[] = {
|
||||
"kmous=\\E[M",
|
||||
@ -249,6 +261,7 @@ static const struct tty_feature *tty_features[] = {
|
||||
&tty_feature_focus,
|
||||
&tty_feature_margins,
|
||||
&tty_feature_mouse,
|
||||
&tty_feature_osc7,
|
||||
&tty_feature_overline,
|
||||
&tty_feature_rectfill,
|
||||
&tty_feature_rgb,
|
||||
@ -363,7 +376,7 @@ tty_default_features(int *feat, const char *name, u_int version)
|
||||
},
|
||||
{ .name = "iTerm2",
|
||||
.features = TTY_FEATURES_BASE_MODERN_XTERM
|
||||
",cstyle,extkeys,margins,sync"
|
||||
",cstyle,extkeys,margins,usstyle,sync"
|
||||
},
|
||||
{ .name = "XTerm",
|
||||
/*
|
||||
|
37
tty-keys.c
37
tty-keys.c
@ -1118,7 +1118,7 @@ tty_keys_mouse(struct tty *tty, const char *buf, size_t len, size_t *size,
|
||||
/* Type is M for press, m for release. */
|
||||
sgr_type = ch;
|
||||
if (sgr_type == 'm')
|
||||
b |= 3;
|
||||
b = 3;
|
||||
|
||||
/*
|
||||
* Some terminals (like PuTTY 0.63) mistakenly send
|
||||
@ -1126,7 +1126,7 @@ tty_keys_mouse(struct tty *tty, const char *buf, size_t len, size_t *size,
|
||||
* Discard it before it reaches any program running inside
|
||||
* tmux.
|
||||
*/
|
||||
if (sgr_type == 'm' && (sgr_b & 64))
|
||||
if (sgr_type == 'm' && MOUSE_WHEEL(sgr_b))
|
||||
return (-2);
|
||||
} else
|
||||
return (-1);
|
||||
@ -1154,12 +1154,14 @@ tty_keys_mouse(struct tty *tty, const char *buf, size_t len, size_t *size,
|
||||
* partial.
|
||||
*/
|
||||
static int
|
||||
tty_keys_clipboard(__unused struct tty *tty, const char *buf, size_t len,
|
||||
size_t *size)
|
||||
tty_keys_clipboard(struct tty *tty, const char *buf, size_t len, size_t *size)
|
||||
{
|
||||
size_t end, terminator, needed;
|
||||
char *copy, *out;
|
||||
int outlen;
|
||||
struct client *c = tty->client;
|
||||
struct window_pane *wp;
|
||||
size_t end, terminator, needed;
|
||||
char *copy, *out;
|
||||
int outlen;
|
||||
u_int i;
|
||||
|
||||
*size = 0;
|
||||
|
||||
@ -1217,6 +1219,12 @@ tty_keys_clipboard(__unused struct tty *tty, const char *buf, size_t len,
|
||||
buf++;
|
||||
end--;
|
||||
|
||||
/* If we did not request this, ignore it. */
|
||||
if (~tty->flags & TTY_OSC52QUERY)
|
||||
return (0);
|
||||
tty->flags &= ~TTY_OSC52QUERY;
|
||||
evtimer_del(&tty->clipboard_timer);
|
||||
|
||||
/* It has to be a string so copy it. */
|
||||
copy = xmalloc(end + 1);
|
||||
memcpy(copy, buf, end);
|
||||
@ -1232,9 +1240,20 @@ tty_keys_clipboard(__unused struct tty *tty, const char *buf, size_t len,
|
||||
}
|
||||
free(copy);
|
||||
|
||||
/* Create a new paste buffer. */
|
||||
/* Create a new paste buffer and forward to panes. */
|
||||
log_debug("%s: %.*s", __func__, outlen, out);
|
||||
paste_add(NULL, out, outlen);
|
||||
if (c->flags & CLIENT_CLIPBOARDBUFFER) {
|
||||
paste_add(NULL, out, outlen);
|
||||
c->flags &= ~CLIENT_CLIPBOARDBUFFER;
|
||||
}
|
||||
for (i = 0; i < c->clipboard_npanes; i++) {
|
||||
wp = window_pane_find_by_id(c->clipboard_panes[i]);
|
||||
if (wp != NULL)
|
||||
input_reply_clipboard(wp->event, out, outlen, "\033\\");
|
||||
}
|
||||
free(c->clipboard_panes);
|
||||
c->clipboard_panes = NULL;
|
||||
c->clipboard_npanes = 0;
|
||||
|
||||
return (0);
|
||||
}
|
||||
|
@ -278,6 +278,7 @@ static const struct tty_term_code_entry tty_term_codes[] = {
|
||||
[TTYC_SMUL] = { TTYCODE_STRING, "smul" },
|
||||
[TTYC_SMXX] = { TTYCODE_STRING, "smxx" },
|
||||
[TTYC_SS] = { TTYCODE_STRING, "Ss" },
|
||||
[TTYC_SWD] = { TTYCODE_STRING, "Swd" },
|
||||
[TTYC_SYNC] = { TTYCODE_STRING, "Sync" },
|
||||
[TTYC_TC] = { TTYCODE_FLAG, "Tc" },
|
||||
[TTYC_TSL] = { TTYCODE_STRING, "tsl" },
|
||||
|
72
tty.c
72
tty.c
@ -83,6 +83,8 @@ static void tty_check_overlay_range(struct tty *, u_int, u_int, u_int,
|
||||
#define TTY_BLOCK_START(tty) (1 + ((tty)->sx * (tty)->sy) * 8)
|
||||
#define TTY_BLOCK_STOP(tty) (1 + ((tty)->sx * (tty)->sy) / 8)
|
||||
|
||||
#define TTY_QUERY_TIMEOUT 5
|
||||
|
||||
void
|
||||
tty_create_log(void)
|
||||
{
|
||||
@ -307,7 +309,7 @@ tty_start_tty(struct tty *tty)
|
||||
{
|
||||
struct client *c = tty->client;
|
||||
struct termios tio;
|
||||
struct timeval tv = { .tv_sec = 3 };
|
||||
struct timeval tv = { .tv_sec = TTY_QUERY_TIMEOUT };
|
||||
|
||||
setblocking(c->fd, 0);
|
||||
event_add(&tty->event_in, NULL);
|
||||
@ -653,6 +655,18 @@ tty_set_title(struct tty *tty, const char *title)
|
||||
tty_putcode(tty, TTYC_FSL);
|
||||
}
|
||||
|
||||
void
|
||||
tty_set_path(struct tty *tty, const char *title)
|
||||
{
|
||||
if (!tty_term_has(tty->term, TTYC_SWD) ||
|
||||
!tty_term_has(tty->term, TTYC_FSL))
|
||||
return;
|
||||
|
||||
tty_putcode(tty, TTYC_SWD);
|
||||
tty_puts(tty, title);
|
||||
tty_putcode(tty, TTYC_FSL);
|
||||
}
|
||||
|
||||
static void
|
||||
tty_force_cursor_colour(struct tty *tty, int c)
|
||||
{
|
||||
@ -791,26 +805,19 @@ tty_update_mode(struct tty *tty, int mode, struct screen *s)
|
||||
|
||||
if ((changed & ALL_MOUSE_MODES) && tty_term_has(term, TTYC_KMOUS)) {
|
||||
/*
|
||||
* If the mouse modes have changed, clear any that are set and
|
||||
* apply again. There are differences in how terminals track
|
||||
* the various bits.
|
||||
* If the mouse modes have changed, clear then all and apply
|
||||
* again. There are differences in how terminals track the
|
||||
* various bits.
|
||||
*/
|
||||
if (tty->mode & MODE_MOUSE_SGR)
|
||||
tty_puts(tty, "\033[?1006l");
|
||||
if (tty->mode & MODE_MOUSE_STANDARD)
|
||||
tty_puts(tty, "\033[?1000l");
|
||||
if (tty->mode & MODE_MOUSE_BUTTON)
|
||||
tty_puts(tty, "\033[?1002l");
|
||||
if (tty->mode & MODE_MOUSE_ALL)
|
||||
tty_puts(tty, "\033[?1003l");
|
||||
tty_puts(tty, "\033[?1006l\033[?1000l\033[?1002l\033[?1003l");
|
||||
if (mode & ALL_MOUSE_MODES)
|
||||
tty_puts(tty, "\033[?1006h");
|
||||
if (mode & MODE_MOUSE_STANDARD)
|
||||
tty_puts(tty, "\033[?1000h");
|
||||
if (mode & MODE_MOUSE_BUTTON)
|
||||
tty_puts(tty, "\033[?1002h");
|
||||
if (mode & MODE_MOUSE_ALL)
|
||||
tty_puts(tty, "\033[?1003h");
|
||||
tty_puts(tty, "\033[?1000h\033[?1002h\033[?1003h");
|
||||
if (mode & MODE_MOUSE_BUTTON)
|
||||
tty_puts(tty, "\033[?1000h\033[?1002h");
|
||||
else if (mode & MODE_MOUSE_STANDARD)
|
||||
tty_puts(tty, "\033[?1000h");
|
||||
}
|
||||
if (changed & MODE_BRACKETPASTE) {
|
||||
if (mode & MODE_BRACKETPASTE)
|
||||
@ -2125,8 +2132,8 @@ tty_set_selection(struct tty *tty, const char *buf, size_t len)
|
||||
encoded = xmalloc(size);
|
||||
|
||||
b64_ntop(buf, len, encoded, size);
|
||||
tty->flags |= TTY_NOBLOCK;
|
||||
tty_putcode_ptr2(tty, TTYC_MS, "", encoded);
|
||||
tty->client->redraw = EVBUFFER_LENGTH(tty->out);
|
||||
|
||||
free(encoded);
|
||||
}
|
||||
@ -2134,6 +2141,7 @@ tty_set_selection(struct tty *tty, const char *buf, size_t len)
|
||||
void
|
||||
tty_cmd_rawstring(struct tty *tty, const struct tty_ctx *ctx)
|
||||
{
|
||||
tty->flags |= TTY_NOBLOCK;
|
||||
tty_add(tty, ctx->ptr, ctx->num);
|
||||
tty_invalidate(tty);
|
||||
}
|
||||
@ -2996,3 +3004,31 @@ tty_default_attributes(struct tty *tty, const struct grid_cell *defaults,
|
||||
gc.bg = bg;
|
||||
tty_attributes(tty, &gc, defaults, palette);
|
||||
}
|
||||
|
||||
static void
|
||||
tty_clipboard_query_callback(__unused int fd, __unused short events, void *data)
|
||||
{
|
||||
struct tty *tty = data;
|
||||
struct client *c = tty->client;
|
||||
|
||||
c->flags &= ~CLIENT_CLIPBOARDBUFFER;
|
||||
free(c->clipboard_panes);
|
||||
c->clipboard_panes = NULL;
|
||||
c->clipboard_npanes = 0;
|
||||
|
||||
tty->flags &= ~TTY_OSC52QUERY;
|
||||
}
|
||||
|
||||
void
|
||||
tty_clipboard_query(struct tty *tty)
|
||||
{
|
||||
struct timeval tv = { .tv_sec = TTY_QUERY_TIMEOUT };
|
||||
|
||||
if ((~tty->flags & TTY_STARTED) || (tty->flags & TTY_OSC52QUERY))
|
||||
return;
|
||||
tty_putcode_ptr2(tty, TTYC_MS, "", "?");
|
||||
|
||||
tty->flags |= TTY_OSC52QUERY;
|
||||
evtimer_set(&tty->clipboard_timer, tty_clipboard_query_callback, tty);
|
||||
evtimer_add(&tty->clipboard_timer, &tv);
|
||||
}
|
||||
|
@ -1272,6 +1272,16 @@ window_copy_cmd_halfpage_up(struct window_copy_cmd_state *cs)
|
||||
return (WINDOW_COPY_CMD_NOTHING);
|
||||
}
|
||||
|
||||
static enum window_copy_cmd_action
|
||||
window_copy_cmd_toggle_position(struct window_copy_cmd_state *cs)
|
||||
{
|
||||
struct window_mode_entry *wme = cs->wme;
|
||||
struct window_copy_mode_data *data = wme->data;
|
||||
|
||||
data->hide_position = !data->hide_position;
|
||||
return (WINDOW_COPY_CMD_REDRAW);
|
||||
}
|
||||
|
||||
static enum window_copy_cmd_action
|
||||
window_copy_cmd_history_bottom(struct window_copy_cmd_state *cs)
|
||||
{
|
||||
@ -2817,6 +2827,12 @@ static const struct {
|
||||
.clear = WINDOW_COPY_CMD_CLEAR_ALWAYS,
|
||||
.f = window_copy_cmd_stop_selection
|
||||
},
|
||||
{ .command = "toggle-position",
|
||||
.minargs = 0,
|
||||
.maxargs = 0,
|
||||
.clear = WINDOW_COPY_CMD_CLEAR_NEVER,
|
||||
.f = window_copy_cmd_toggle_position
|
||||
},
|
||||
{ .command = "top-line",
|
||||
.minargs = 0,
|
||||
.maxargs = 0,
|
||||
@ -3148,6 +3164,11 @@ window_copy_cellstring(const struct grid_line *gl, u_int px, size_t *size,
|
||||
}
|
||||
|
||||
utf8_to_data(gl->extddata[gce->offset].data, &ud);
|
||||
if (ud.size == 0) {
|
||||
*size = 0;
|
||||
*allocated = 0;
|
||||
return (NULL);
|
||||
}
|
||||
*size = ud.size;
|
||||
*allocated = 1;
|
||||
|
||||
|
@ -680,9 +680,7 @@ window_customize_draw_option(struct window_customize_modedata *data,
|
||||
}
|
||||
ft = format_create_from_state(NULL, NULL, &fs);
|
||||
|
||||
if (oe == NULL)
|
||||
text = "This is a user option.";
|
||||
else if (oe->text == NULL)
|
||||
if (oe == NULL || oe->text == NULL)
|
||||
text = "This option doesn't have a description.";
|
||||
else
|
||||
text = oe->text;
|
||||
|
20
window.c
20
window.c
@ -329,6 +329,7 @@ window_create(u_int sx, u_int sy, u_int xpixel, u_int ypixel)
|
||||
w->id = next_window_id++;
|
||||
RB_INSERT(windows, &windows, w);
|
||||
|
||||
window_set_fill_character(w);
|
||||
window_update_activity(w);
|
||||
|
||||
log_debug("%s: @%u create %ux%u (%ux%u)", __func__, w->id, sx, sy,
|
||||
@ -360,6 +361,7 @@ window_destroy(struct window *w)
|
||||
event_del(&w->offset_timer);
|
||||
|
||||
options_free(w->options);
|
||||
free(w->fill_character);
|
||||
|
||||
free(w->name);
|
||||
free(w);
|
||||
@ -761,6 +763,7 @@ window_lost_pane(struct window *w, struct window_pane *wp)
|
||||
if (w->active != NULL) {
|
||||
w->active->flags |= PANE_CHANGED;
|
||||
notify_window("window-pane-changed", w);
|
||||
window_update_focus(w);
|
||||
}
|
||||
} else if (wp == w->last)
|
||||
w->last = NULL;
|
||||
@ -1598,3 +1601,20 @@ window_pane_update_used_data(struct window_pane *wp,
|
||||
size = EVBUFFER_LENGTH(wp->event->input) - used;
|
||||
wpo->used += size;
|
||||
}
|
||||
|
||||
void
|
||||
window_set_fill_character(struct window *w)
|
||||
{
|
||||
const char *value;
|
||||
struct utf8_data *ud;
|
||||
|
||||
free(w->fill_character);
|
||||
w->fill_character = NULL;
|
||||
|
||||
value = options_get_string(w->options, "fill-character");
|
||||
if (*value != '\0' && utf8_isvalid(value)) {
|
||||
ud = utf8_fromcstr(value);
|
||||
if (ud != NULL && ud[0].width == 1)
|
||||
w->fill_character = ud;
|
||||
}
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user