comparison src/term.c @ 6874:a89cff862dda v7.4.757

patch 7.4.757 Problem: Cannot detect the background color of a terminal. Solution: Add T_RBG to request the background color if possible. (Lubomir Rintel)
author Bram Moolenaar <bram@vim.org>
date Thu, 25 Jun 2015 17:03:36 +0200
parents 7c5a0c69e1ac
children 7bd926109eea
comparison
equal deleted inserted replaced
6873:48ad20643c92 6874:a89cff862dda
122 /* Request Cursor position report: */ 122 /* Request Cursor position report: */
123 # define U7_GET 1 /* send T_U7 when switched to RAW mode */ 123 # define U7_GET 1 /* send T_U7 when switched to RAW mode */
124 # define U7_SENT 2 /* did send T_U7, waiting for answer */ 124 # define U7_SENT 2 /* did send T_U7, waiting for answer */
125 # define U7_GOT 3 /* received T_U7 response */ 125 # define U7_GOT 3 /* received T_U7 response */
126 static int u7_status = U7_GET; 126 static int u7_status = U7_GET;
127 /* Request background color report: */
128 # define RBG_GET 1 /* send T_RBG when switched to RAW mode */
129 # define RBG_SENT 2 /* did send T_RBG, waiting for answer */
130 # define RBG_GOT 3 /* received T_RBG response */
131 static int rbg_status = RBG_GET;
127 # endif 132 # endif
128 133
129 /* 134 /*
130 * Don't declare these variables if termcap.h contains them. 135 * Don't declare these variables if termcap.h contains them.
131 * Autoconf checks if these variables should be declared extern (not all 136 * Autoconf checks if these variables should be declared extern (not all
947 # else 952 # else
948 {(int)KS_CWS, IF_EB("\033[8;%d;%dt", ESC_STR "[8;%d;%dt")}, 953 {(int)KS_CWS, IF_EB("\033[8;%d;%dt", ESC_STR "[8;%d;%dt")},
949 {(int)KS_CWP, IF_EB("\033[3;%d;%dt", ESC_STR "[3;%d;%dt")}, 954 {(int)KS_CWP, IF_EB("\033[3;%d;%dt", ESC_STR "[3;%d;%dt")},
950 # endif 955 # endif
951 {(int)KS_CRV, IF_EB("\033[>c", ESC_STR "[>c")}, 956 {(int)KS_CRV, IF_EB("\033[>c", ESC_STR "[>c")},
957 {(int)KS_RBG, IF_EB("\033]11;?\007", ESC_STR "]11;?\007")},
952 {(int)KS_U7, IF_EB("\033[6n", ESC_STR "[6n")}, 958 {(int)KS_U7, IF_EB("\033[6n", ESC_STR "[6n")},
953 959
954 {K_UP, IF_EB("\033O*A", ESC_STR "O*A")}, 960 {K_UP, IF_EB("\033O*A", ESC_STR "O*A")},
955 {K_DOWN, IF_EB("\033O*B", ESC_STR "O*B")}, 961 {K_DOWN, IF_EB("\033O*B", ESC_STR "O*B")},
956 {K_RIGHT, IF_EB("\033O*C", ESC_STR "O*C")}, 962 {K_RIGHT, IF_EB("\033O*C", ESC_STR "O*C")},
1238 {(int)KS_CWS, "[%dCWS%d]"}, 1244 {(int)KS_CWS, "[%dCWS%d]"},
1239 {(int)KS_CWP, "[%dCWP%d]"}, 1245 {(int)KS_CWP, "[%dCWP%d]"},
1240 # endif 1246 # endif
1241 {(int)KS_CRV, "[CRV]"}, 1247 {(int)KS_CRV, "[CRV]"},
1242 {(int)KS_U7, "[U7]"}, 1248 {(int)KS_U7, "[U7]"},
1249 {(int)KS_RBG, "[RBG]"},
1243 {K_UP, "[KU]"}, 1250 {K_UP, "[KU]"},
1244 {K_DOWN, "[KD]"}, 1251 {K_DOWN, "[KD]"},
1245 {K_LEFT, "[KL]"}, 1252 {K_LEFT, "[KL]"},
1246 {K_RIGHT, "[KR]"}, 1253 {K_RIGHT, "[KR]"},
1247 {K_XUP, "[xKU]"}, 1254 {K_XUP, "[xKU]"},
3222 { 3229 {
3223 /* May need to check for T_CRV response and termcodes, it 3230 /* May need to check for T_CRV response and termcodes, it
3224 * doesn't work in Cooked mode, an external program may get 3231 * doesn't work in Cooked mode, an external program may get
3225 * them. */ 3232 * them. */
3226 if (tmode != TMODE_RAW && (crv_status == CRV_SENT 3233 if (tmode != TMODE_RAW && (crv_status == CRV_SENT
3227 || u7_status == U7_SENT)) 3234 || u7_status == U7_SENT
3235 || rbg_status == RBG_SENT))
3228 (void)vpeekc_nomap(); 3236 (void)vpeekc_nomap();
3229 check_for_codes_from_term(); 3237 check_for_codes_from_term();
3230 } 3238 }
3231 #endif 3239 #endif
3232 #ifdef FEAT_MOUSE_TTY 3240 #ifdef FEAT_MOUSE_TTY
3283 #ifdef FEAT_TERMRESPONSE 3291 #ifdef FEAT_TERMRESPONSE
3284 # ifdef FEAT_GUI 3292 # ifdef FEAT_GUI
3285 if (!gui.in_use && !gui.starting) 3293 if (!gui.in_use && !gui.starting)
3286 # endif 3294 # endif
3287 { 3295 {
3288 /* May need to discard T_CRV or T_U7 response. */ 3296 /* May need to discard T_CRV, T_U7 or T_RBG response. */
3289 if (crv_status == CRV_SENT || u7_status == U7_SENT) 3297 if (crv_status == CRV_SENT || u7_status == U7_SENT
3298 || rbg_status == RBG_SENT)
3290 { 3299 {
3291 # ifdef UNIX 3300 # ifdef UNIX
3292 /* Give the terminal a chance to respond. */ 3301 /* Give the terminal a chance to respond. */
3293 mch_delay(100L, FALSE); 3302 mch_delay(100L, FALSE);
3294 # endif 3303 # endif
3392 term_windgoto(0, 0); 3401 term_windgoto(0, 0);
3393 /* check for the characters now, otherwise they might be eaten by 3402 /* check for the characters now, otherwise they might be eaten by
3394 * get_keystroke() */ 3403 * get_keystroke() */
3395 out_flush(); 3404 out_flush();
3396 (void)vpeekc_nomap(); 3405 (void)vpeekc_nomap();
3406 }
3407 }
3408 # endif
3409
3410 #if defined(FEAT_TERMRESPONSE) || defined(PROTO)
3411 /*
3412 * Check how the terminal treats ambiguous character width (UAX #11).
3413 * First, we move the cursor to (1, 0) and print a test ambiguous character
3414 * \u25bd (WHITE DOWN-POINTING TRIANGLE) and query current cursor position.
3415 * If the terminal treats \u25bd as single width, the position is (1, 1),
3416 * or if it is treated as double width, that will be (1, 2).
3417 * This function has the side effect that changes cursor position, so
3418 * it must be called immediately after entering termcap mode.
3419 */
3420 void
3421 may_req_bg_color()
3422 {
3423 if (rbg_status == RBG_GET
3424 && cur_tmode == TMODE_RAW
3425 && termcap_active
3426 && p_ek
3427 # ifdef UNIX
3428 && isatty(1)
3429 && isatty(read_cmd_fd)
3430 # endif
3431 && *T_RBG != NUL
3432 && !option_was_set((char_u *)"bg"))
3433 {
3434 LOG_TR("Sending BG request");
3435 out_str(T_RBG);
3436 rbg_status = RBG_SENT;
3437 /* check for the characters now, otherwise they might be eaten by
3438 * get_keystroke() */
3439 out_flush();
3440 (void)vpeekc_nomap();
3397 } 3441 }
3398 } 3442 }
3399 # endif 3443 # endif
3400 3444
3401 # ifdef DEBUG_TERMRESPONSE 3445 # ifdef DEBUG_TERMRESPONSE
4220 * the escape sequence ends with a letter or one of "{|}~". 4264 * the escape sequence ends with a letter or one of "{|}~".
4221 * 4265 *
4222 * - Cursor position report: <Esc>[{row};{col}R 4266 * - Cursor position report: <Esc>[{row};{col}R
4223 * The final byte must be 'R'. It is used for checking the 4267 * The final byte must be 'R'. It is used for checking the
4224 * ambiguous-width character state. 4268 * ambiguous-width character state.
4269 *
4270 * - Background color response:
4271 * <Esc>]11;rgb:{rrrr}/{gggg}/{bbbb}\007
4272 * The final byte must be '\007'.
4225 */ 4273 */
4226 p = tp[0] == CSI ? tp + 1 : tp + 2; 4274 char_u *argp = tp[0] == CSI ? tp + 1 : tp + 2;
4227 if ((*T_CRV != NUL || *T_U7 != NUL) 4275
4276 if ((*T_CRV != NUL || *T_U7 != NUL || *T_RBG != NUL)
4228 && ((tp[0] == ESC && tp[1] == '[' && len >= 3) 4277 && ((tp[0] == ESC && tp[1] == '[' && len >= 3)
4278 || (tp[0] == ESC && tp[1] == ']' && len >= 24)
4229 || (tp[0] == CSI && len >= 2)) 4279 || (tp[0] == CSI && len >= 2))
4230 && (VIM_ISDIGIT(*p) || *p == '>' || *p == '?')) 4280 && (VIM_ISDIGIT(*argp) || *argp == '>' || *argp == '?'))
4231 { 4281 {
4232 #ifdef FEAT_MBYTE 4282 #ifdef FEAT_MBYTE
4233 int col; 4283 int col;
4234 int row_char = NUL; 4284 int row_char = NUL;
4235 #endif 4285 #endif
4360 NULL, NULL, FALSE, curbuf); 4410 NULL, NULL, FALSE, curbuf);
4361 # endif 4411 # endif
4362 key_name[0] = (int)KS_EXTRA; 4412 key_name[0] = (int)KS_EXTRA;
4363 key_name[1] = (int)KE_IGNORE; 4413 key_name[1] = (int)KE_IGNORE;
4364 slen = i + 1; 4414 slen = i + 1;
4415 }
4416 else if (*T_RBG != NUL && len >= 24 - (tp[0] == CSI)
4417 && argp[0] == '1' && argp[1] == '1'
4418 && argp[2] == ';' && argp[3] == 'r' && argp[4] == 'g'
4419 && argp[5] == 'b' && argp[6] == ':'
4420 && argp[11] == '/' && argp[16] == '/'
4421 && argp[21] == '\007')
4422 {
4423 LOG_TR("Received RBG");
4424 rbg_status = RBG_GOT;
4425 if (!option_was_set((char_u *)"bg"))
4426 {
4427 set_option_value((char_u *)"bg", 0L, (char_u *)(
4428 (3 * '6' < argp[7] + argp[12] + argp[17])
4429 ? "light" : "dark"), 0);
4430 reset_option_was_set((char_u *)"bg");
4431 redraw_asap(CLEAR);
4432 }
4433 key_name[0] = (int)KS_EXTRA;
4434 key_name[1] = (int)KE_IGNORE;
4435 slen = 24;
4365 } 4436 }
4366 } 4437 }
4367 4438
4368 /* Check for '<Esc>P1+r<hex bytes><Esc>\'. A "0" instead of the 4439 /* Check for '<Esc>P1+r<hex bytes><Esc>\'. A "0" instead of the
4369 * "1" means an invalid request. */ 4440 * "1" means an invalid request. */