# HG changeset patch # User Bram Moolenaar # Date 1673354704 -3600 # Node ID 9dc48932db8e3b265b9514ec56e404624a72b49e # Parent 5ed19049b1e82a7701c4665ae98f70a4eca4425b patch 9.0.1168: code to enable/disable mouse is not from terminfo/termcap Commit: https://github.com/vim/vim/commit/06cd14d0bf990d0002d61a721aa3d5b8a3c44028 Author: Bram Moolenaar Date: Tue Jan 10 12:37:38 2023 +0000 patch 9.0.1168: code to enable/disable mouse is not from terminfo/termcap Problem: Code to enable/disable mouse is not from terminfo/termcap. Solution: Request the "XM" entry and use it to set 'ttymouse' if possible. diff --git a/runtime/doc/options.txt b/runtime/doc/options.txt --- a/runtime/doc/options.txt +++ b/runtime/doc/options.txt @@ -8679,6 +8679,9 @@ A jump table for the options with a shor set to a name that starts with "xterm", "mlterm", "screen", "tmux", "st" (full match only), "st-" or "stterm", and 'ttymouse' is not set already. + If the terminfo/termcap entry "XM" exists and the first number is + "1006" then 'ttymouse' will be set to "sgr". This works for many + modern terminals. Additionally, if vim is compiled with the |+termresponse| feature and |t_RV| is set to the escape sequence to request the xterm version number, more intelligent detection is done. diff --git a/src/optiondefs.h b/src/optiondefs.h --- a/src/optiondefs.h +++ b/src/optiondefs.h @@ -2934,6 +2934,7 @@ static struct vimoption options[] = p_term("t_vs", T_VS) p_term("t_WP", T_CWP) p_term("t_WS", T_CWS) + p_term("t_XM", T_CXM) p_term("t_xn", T_XN) p_term("t_xs", T_XS) p_term("t_ZH", T_CZH) diff --git a/src/os_unix.c b/src/os_unix.c --- a/src/os_unix.c +++ b/src/os_unix.c @@ -3780,7 +3780,11 @@ mch_setmouse(int on) } #endif - if (ttym_flags == TTYM_SGR) + if (T_CXM != NULL && *T_CXM != NUL) + { + term_enable_mouse(on); + } + else if (ttym_flags == TTYM_SGR) { // SGR mode supports columns above 223 out_str_nf((char_u *)(on ? "\033[?1006h" : "\033[?1006l")); diff --git a/src/proto/term.pro b/src/proto/term.pro --- a/src/proto/term.pro +++ b/src/proto/term.pro @@ -25,6 +25,7 @@ void term_windgoto(int row, int col); void term_cursor_right(int i); void term_append_lines(int line_count); void term_delete_lines(int line_count); +void term_enable_mouse(int enable); void term_set_winpos(int x, int y); int term_get_winpos(int *x, int *y, varnumber_T timeout); void term_set_winsize(int height, int width); diff --git a/src/term.c b/src/term.c --- a/src/term.c +++ b/src/term.c @@ -473,6 +473,7 @@ static tcap_entry_T builtin_xterm[] = { {(int)KS_CGP, "\033[13t"}, # endif {(int)KS_CRV, "\033[>c"}, + {(int)KS_CXM, "\033[?1006;1000%?%p1%{1}%=%th%el%;"}, {(int)KS_RFG, "\033]10;?\007"}, {(int)KS_RBG, "\033]11;?\007"}, {(int)KS_U7, "\033[6n"}, @@ -1229,6 +1230,7 @@ static tcap_entry_T builtin_debug[] = { {(int)KS_CWP, "[%dCWP%d]"}, # endif {(int)KS_CRV, "[CRV]"}, + {(int)KS_CXM, "[CXM]"}, {(int)KS_U7, "[U7]"}, {(int)KS_RFG, "[RFG]"}, {(int)KS_RBG, "[RBG]"}, @@ -1721,7 +1723,8 @@ get_term_entries(int *height, int *width {KS_BC, "bc"}, {KS_CSB,"Sb"}, {KS_CSF,"Sf"}, {KS_CAB,"AB"}, {KS_CAF,"AF"}, {KS_CAU,"AU"}, {KS_LE, "le"}, - {KS_ND, "nd"}, {KS_OP, "op"}, {KS_CRV, "RV"}, + {KS_ND, "nd"}, {KS_OP, "op"}, + {KS_CRV, "RV"}, {KS_CXM, "XM"}, {KS_VS, "vs"}, {KS_CVS, "VS"}, {KS_CIS, "IS"}, {KS_CIE, "IE"}, {KS_CSC, "SC"}, {KS_CEC, "EC"}, @@ -2107,8 +2110,8 @@ set_termname(char_u *term) else T_CCS = empty_option; - // Special case: "kitty" does not normally have a "RV" entry in terminfo, - // but we need to request the version for several other things to work. + // Special case: "kitty" may not have a "RV" entry in terminfo, but we need + // to request the version for several other things to work. if (strstr((char *)term, "kitty") != NULL && (T_CRV == NULL || *T_CRV == NUL)) T_CRV = (char_u *)"\033[>c"; @@ -2156,6 +2159,22 @@ set_termname(char_u *term) init_term_props(FALSE); #endif + // If the first number in t_XM is 1006 then the terminal will support SGR + // mouse reporting. + int did_set_ttym = FALSE; + if (T_CXM != NULL && *T_CXM != NUL && !option_was_set((char_u *)"ttym")) + { + char_u *p = T_CXM; + + while (*p != NUL && !VIM_ISDIGIT(*p)) + ++p; + if (getdigits(&p) == 1006) + { + did_set_ttym = TRUE; + set_option_value_give_err((char_u *)"ttym", 0L, (char_u *)"sgr", 0); + } + } + #if defined(UNIX) || defined(VMS) /* * For Unix, set the 'ttymouse' option to the type of mouse to be used. @@ -2173,7 +2192,7 @@ set_termname(char_u *term) p = (char_u *)"xterm"; } # endif - if (p != NULL) + if (p != NULL && !did_set_ttym) { set_option_value_give_err((char_u *)"ttym", 0L, p, 0); // Reset the WAS_SET flag, 'ttymouse' can be set to "sgr" or @@ -2801,8 +2820,8 @@ out_str_nf(char_u *s) if (out_pos > OUT_SIZE - MAX_ESC_SEQ_LEN) out_flush(); - while (*s) - out_char_nf(*s++); + for (char_u *p = s; *p != NUL; ++p) + out_char_nf(*p); // For testing we write one string at a time. if (p_wd) @@ -2942,6 +2961,15 @@ term_delete_lines(int line_count) OUT_STR(tgoto((char *)T_CDL, 0, line_count)); } +#if defined(UNIX) || defined(PROTO) + void +term_enable_mouse(int enable) +{ + int on = enable ? 1 : 0; + OUT_STR(tgoto((char *)T_CXM, 0, on)); +} +#endif + #if defined(HAVE_TGETENT) || defined(PROTO) void term_set_winpos(int x, int y) diff --git a/src/termdefs.h b/src/termdefs.h --- a/src/termdefs.h +++ b/src/termdefs.h @@ -95,6 +95,7 @@ enum SpecialKey KS_CGP, // get window position KS_CWS, // set window size in characters KS_CRV, // request version string + KS_CXM, // enable/disable mouse reporting KS_RFG, // request foreground color KS_RBG, // request background color KS_CSI, // start insert mode (bar cursor) @@ -205,6 +206,7 @@ extern char_u *(term_strings[]); // c #define T_CEI (TERM_STR(KS_CEI)) // end insert mode #define T_CSR (TERM_STR(KS_CSR)) // start replace mode #define T_CRV (TERM_STR(KS_CRV)) // request version string +#define T_CXM (TERM_STR(KS_CXM)) // enable/disable mouse reporting #define T_RFG (TERM_STR(KS_RFG)) // request foreground RGB #define T_RBG (TERM_STR(KS_RBG)) // request background RGB #define T_OP (TERM_STR(KS_OP)) // original color pair diff --git a/src/version.c b/src/version.c --- a/src/version.c +++ b/src/version.c @@ -696,6 +696,8 @@ static char *(features[]) = static int included_patches[] = { /* Add new patch number below this line */ /**/ + 1168, +/**/ 1167, /**/ 1166,