void may_req_termresponse(void);
void check_terminal_behavior(void);
void may_req_bg_color(void);
+void may_req_decrqm(void);
int swapping_screen(void);
void scroll_start(void);
void cursor_on_force(void);
void ansi_color2rgb(int nr, char_u *r, char_u *g, char_u *b, char_u *ansi_idx);
void cterm_color2rgb(int nr, char_u *r, char_u *g, char_u *b, char_u *ansi_idx);
int term_replace_keycodes(char_u *ta_buf, int ta_len, int len_arg);
-void send_decrqm_modes(void);
void term_disable_dec(void);
void term_set_win_resize(bool state);
void term_set_sync_output(int flags);
// Request window's position report:
static termrequest_T winpos_status = TERMREQUEST_INIT;
+// Request DECRQM (DEC mode) report:
+static termrequest_T decrqm_status = TERMREQUEST_INIT;
+
static termrequest_T *all_termrequests[] = {
&crv_status,
&u7_status,
&rbm_status,
&rcs_status,
&winpos_status,
+ &decrqm_status,
NULL
};
#define TPR_MOUSE 3
// term response indicates kitty
#define TPR_KITTY 4
+// can send DECRQM requests to terminal
+#define TPR_DECRQM 5
// table size
-#define TPR_COUNT 5
+#define TPR_COUNT 6
static termprop_T term_props[TPR_COUNT];
term_props[TPR_MOUSE].tpr_set_by_termresponse = TRUE;
term_props[TPR_KITTY].tpr_name = "kitty";
term_props[TPR_KITTY].tpr_set_by_termresponse = FALSE;
+ term_props[TPR_DECRQM].tpr_name = "decrqm";
+ term_props[TPR_DECRQM].tpr_set_by_termresponse = TRUE;
for (i = 0; i < TPR_COUNT; ++i)
if (all || term_props[i].tpr_set_by_termresponse)
}
}
+/*
+ * Query the settings for the DEC modes we support via DECRQM.
+ * Only sent once, and only when the terminal is known not to dislike it
+ * (i.e. TPR_DECRQM is TPR_YES, or still TPR_UNKNOWN when the version response
+ * has not yet been received).
+ * The DECRPM responses are caught in handle_csi().
+ */
+ void
+may_req_decrqm(void)
+{
+ if (decrqm_status.tr_progress == STATUS_GET
+ && term_props[TPR_DECRQM].tpr_status != TPR_NO
+ && can_get_termresponse()
+ && starting == 0)
+ {
+ MAY_WANT_TO_LOG_THIS;
+ LOG_TR1("Sending DECRQM requests");
+ for (int i = 0; i < (int)ARRAY_LENGTH(dec_modes); i++)
+ {
+ vim_snprintf((char *)IObuff, IOSIZE, "\033[?%d$p", dec_modes[i]);
+ out_str(IObuff);
+ }
+ termrequest_sent(&decrqm_status);
+ // check for the characters now, otherwise they might be eaten by
+ // get_keystroke()
+ out_flush();
+ (void)vpeekc_nomap();
+ }
+}
+
#endif
/*
may_adjust_color_count(256);
// Libvterm can handle SGR mouse reporting.
term_props[TPR_MOUSE].tpr_status = TPR_MOUSE_SGR;
+ term_props[TPR_DECRQM].tpr_status = TPR_YES;
}
if (version == 95)
{
// Mac Terminal.app sends 1;95;0
+ //
+ // Terminal.app doesn't seem to handle DECRQM sequences
+ // properly, see issue #19852.
if (arg[0] == 1 && arg[2] == 0)
{
term_props[TPR_UNDERLINE_RGB].tpr_status = TPR_YES;
term_props[TPR_MOUSE].tpr_status = TPR_MOUSE_SGR;
+ term_props[TPR_DECRQM].tpr_status = TPR_NO;
}
// iTerm2 sends 0;95;0
else if (arg[0] == 0 && arg[2] == 0)
{
// iTerm2 can do SGR mouse reporting
term_props[TPR_MOUSE].tpr_status = TPR_MOUSE_SGR;
+ term_props[TPR_DECRQM].tpr_status = TPR_YES;
}
// old iTerm2 sends 0;95;
else if (arg[0] == 0 && arg[2] == -1)
term_props[TPR_MOUSE].tpr_status = TPR_MOUSE_SGR;
else if (version >= 95)
term_props[TPR_MOUSE].tpr_status = TPR_MOUSE_XTERM2;
+ term_props[TPR_DECRQM].tpr_status = TPR_YES;
}
// Detect terminals that set $TERM to something like
// Assuming any version number over 2500 is not an
// xterm (without the limit for rxvt and screen).
if (arg[1] >= 2500)
+ {
term_props[TPR_UNDERLINE_RGB].tpr_status = TPR_YES;
+ term_props[TPR_DECRQM].tpr_status = TPR_YES;
+ }
else if (version == 136 && arg[2] == 0)
{
term_props[TPR_UNDERLINE_RGB].tpr_status = TPR_YES;
+ term_props[TPR_DECRQM].tpr_status = TPR_YES;
// PuTTY sends 0;136;0
if (arg[0] == 0)
// Kitty can handle SGR mouse reporting.
term_props[TPR_MOUSE].tpr_status = TPR_MOUSE_SGR;
+ term_props[TPR_DECRQM].tpr_status = TPR_YES;
}
// GNU screen sends 83;30600;0, 83;40500;0, etc.
{
term_props[TPR_CURSOR_STYLE].tpr_status = TPR_NO;
term_props[TPR_CURSOR_BLINK].tpr_status = TPR_NO;
+ term_props[TPR_DECRQM].tpr_status = TPR_NO; // screen doesn't seem
+ // to handle DECRQM
+ // sequences
}
// Xterm first responded to this request at patch level
key_name[0] = (int)KS_EXTRA;
key_name[1] = (int)KE_IGNORE;
+#ifdef FEAT_TERMRESPONSE
+ // Mark the DECRQM request as answered so it is not sent again and
+ // stoptermcap() does not wait for it.
+ if (decrqm_status.tr_progress == STATUS_SENT)
+ decrqm_status.tr_progress = STATUS_GOT;
+#endif
+
if (setting >= 0 && setting <= 4)
{
LOG_TRN("Received DECRPM mode %d: %s", arg[0], tp);
return len;
}
-/*
- * Query the settings for the DEC modes we support
- */
- void
-send_decrqm_modes(void)
-{
- if (termcap_active && cur_tmode == TMODE_RAW)
- {
- // Request setting of relevant DEC modes via DECRQM
- for (int i = 0; i < (int)ARRAY_LENGTH(dec_modes); i++)
- {
- vim_snprintf((char *)IObuff, IOSIZE, "\033[?%d$p", dec_modes[i]);
- out_str(IObuff);
- }
- out_flush();
- }
-}
-
/*
* Should be called when cleaning up terminal state.
*/
let &term = save_term
let &ttymouse = save_ttymouse
call test_override('no_query_mouse', 0)
- close!
+ bw!
endfunc
" Test for switching window using mouse in insert mode
\ underline_rgb: 'u',
\ mouse: 's',
\ kitty: 'u',
+ \ decrqm: 'y'
\ }, terminalprops())
set t_RV=
\ underline_rgb: 'u',
\ mouse: 's',
\ kitty: 'u',
+ \ decrqm: 'y'
\ }, terminalprops())
set t_RV=
\ underline_rgb: 'u',
\ mouse: 's',
\ kitty: 'u',
+ \ decrqm: 'y'
\ }, terminalprops())
endfunc
\ underline_rgb: 'y',
\ mouse: 's',
\ kitty: 'u',
+ \ decrqm: 'n'
\ }, terminalprops())
call assert_equal("\<Esc>[58;2;%lu;%lu;%lum", &t_8u)
\ underline_rgb: 'y',
\ mouse: 's',
\ kitty: 'u',
+ \ decrqm: 'y'
\ }, terminalprops())
set t_RV=
\ underline_rgb: 'y',
\ mouse: 's',
\ kitty: 'u',
+ \ decrqm: 'n'
\ }, terminalprops())
set t_RV=
\ underline_rgb: 'u',
\ mouse: 's',
\ kitty: 'u',
+ \ decrqm: 'y'
\ }, terminalprops())
call assert_equal(a:set_by_user ? default_value : '', &t_8u)
endfunc
\ underline_rgb: 'y',
\ mouse: 'u',
\ kitty: 'u',
+ \ decrqm: 'y'
\ }, terminalprops())
" xterm >= 95 < 277 "xterm2"
\ underline_rgb: 'u',
\ mouse: '2',
\ kitty: 'u',
+ \ decrqm: 'y'
\ }, terminalprops())
" xterm >= 277: "sgr"
\ underline_rgb: 'u',
\ mouse: 's',
\ kitty: 'u',
+ \ decrqm: 'y'
\ }, terminalprops())
" xterm >= 279: "sgr" and cursor_style not reset; also check t_8u reset,
\ underline_rgb: 'y',
\ mouse: 's',
\ kitty: 'y',
+ \ decrqm: 'y'
\ }, terminalprops())
call feedkeys("\<Esc>[?1u") " simulate the kitty keyboard protocol is enabled
let buf = RunVimInTerminal('-S XTestWinResize', #{rows: 15, cols: 20})
+ " Must add a delay, since status report is sent internally by vim only when
+ " version response is received, which may come after we send the status report
+ " here.
+ sleep 100m
+
" Send status report
call term_sendkeys(buf, "\<Esc>[?2048;1$y")
call TermWait(buf)