forked from aniani/vim
patch 9.0.0850: MS-Windows Terminal has unstable color control
Problem: MS-Windows Terminal has unstable color control. Solution: Do not try to read the old command prompt colortable, use modern VT sequences. (Christopher Plewright, closes #11450, closes #11373)
This commit is contained in:
committed by
Bram Moolenaar
parent
157241e879
commit
38804d6457
187
src/os_win32.c
187
src/os_win32.c
@@ -204,21 +204,17 @@ static void vtp_sgr_bulks(int argc, int *argv);
|
||||
static int wt_working = 0;
|
||||
static void wt_init();
|
||||
|
||||
static guicolor_T save_console_bg_rgb;
|
||||
static guicolor_T save_console_fg_rgb;
|
||||
static guicolor_T store_console_bg_rgb;
|
||||
static guicolor_T store_console_fg_rgb;
|
||||
|
||||
static int g_color_index_bg = 0;
|
||||
static int g_color_index_fg = 7;
|
||||
|
||||
# ifdef FEAT_TERMGUICOLORS
|
||||
static guicolor_T save_console_bg_rgb;
|
||||
static guicolor_T save_console_fg_rgb;
|
||||
static guicolor_T store_console_bg_rgb;
|
||||
static guicolor_T store_console_fg_rgb;
|
||||
static int default_console_color_bg = 0x000000; // black
|
||||
static int default_console_color_fg = 0xc0c0c0; // white
|
||||
# endif
|
||||
|
||||
# ifdef FEAT_TERMGUICOLORS
|
||||
# define USE_VTP (vtp_working && is_term_win32() && (p_tgc || (!p_tgc && t_colors >= 256)))
|
||||
# define USE_VTP (vtp_working && is_term_win32())
|
||||
# define USE_WT (wt_working)
|
||||
# else
|
||||
# define USE_VTP 0
|
||||
@@ -334,7 +330,7 @@ read_console_input(
|
||||
|
||||
if (s_dwMax == 0)
|
||||
{
|
||||
if (!USE_WT && nLength == -1)
|
||||
if (!vtp_working && nLength == -1)
|
||||
return PeekConsoleInputW(hInput, lpBuffer, 1, lpEvents);
|
||||
GetNumberOfConsoleInputEvents(hInput, &dwEvents);
|
||||
if (dwEvents == 0 && nLength == -1)
|
||||
@@ -1255,7 +1251,6 @@ mch_bevalterm_changed(void)
|
||||
static void
|
||||
decode_mouse_wheel(MOUSE_EVENT_RECORD *pmer)
|
||||
{
|
||||
win_T *wp;
|
||||
int horizontal = (pmer->dwEventFlags == MOUSE_HWHEELED);
|
||||
int zDelta = pmer->dwButtonState;
|
||||
|
||||
@@ -1265,7 +1260,7 @@ decode_mouse_wheel(MOUSE_EVENT_RECORD *pmer)
|
||||
#ifdef FEAT_PROP_POPUP
|
||||
int lcol = g_xMouse;
|
||||
int lrow = g_yMouse;
|
||||
wp = mouse_find_win(&lrow, &lcol, FIND_POPUP);
|
||||
win_T *wp = mouse_find_win(&lrow, &lcol, FIND_POPUP);
|
||||
if (wp != NULL && popup_is_popup(wp))
|
||||
{
|
||||
g_nMouseClick = -1;
|
||||
@@ -1605,7 +1600,7 @@ decode_mouse_event(
|
||||
static void
|
||||
mch_set_cursor_shape(int thickness)
|
||||
{
|
||||
if (USE_VTP || USE_WT)
|
||||
if (vtp_working)
|
||||
{
|
||||
if (*T_CSI == NUL)
|
||||
{
|
||||
@@ -2977,6 +2972,9 @@ mch_init_c(void)
|
||||
create_conin();
|
||||
g_hConOut = GetStdHandle(STD_OUTPUT_HANDLE);
|
||||
|
||||
wt_init();
|
||||
vtp_flag_init();
|
||||
vtp_init();
|
||||
# ifdef FEAT_RESTORE_ORIG_SCREEN
|
||||
// Save the initial console buffer for later restoration
|
||||
SaveConsoleBuffer(&g_cbOrig);
|
||||
@@ -3033,10 +3031,6 @@ mch_init_c(void)
|
||||
# ifdef FEAT_CLIPBOARD
|
||||
win_clip_init();
|
||||
# endif
|
||||
|
||||
vtp_flag_init();
|
||||
vtp_init();
|
||||
wt_init();
|
||||
}
|
||||
|
||||
/*
|
||||
@@ -5854,7 +5848,7 @@ termcap_mode_end(void)
|
||||
|
||||
g_fTermcapMode = FALSE;
|
||||
}
|
||||
#endif // FEAT_GUI_MSWIN
|
||||
#endif // !FEAT_GUI_MSWIN || VIMDLL
|
||||
|
||||
|
||||
#if defined(FEAT_GUI_MSWIN) && !defined(VIMDLL)
|
||||
@@ -5876,7 +5870,7 @@ clear_chars(
|
||||
COORD coord,
|
||||
DWORD n)
|
||||
{
|
||||
if (!USE_VTP)
|
||||
if (!vtp_working)
|
||||
{
|
||||
DWORD dwDummy;
|
||||
|
||||
@@ -5901,7 +5895,7 @@ clear_screen(void)
|
||||
{
|
||||
g_coord.X = g_coord.Y = 0;
|
||||
|
||||
if (!USE_VTP)
|
||||
if (!vtp_working)
|
||||
clear_chars(g_coord, Rows * Columns);
|
||||
else
|
||||
{
|
||||
@@ -5920,7 +5914,7 @@ clear_to_end_of_display(void)
|
||||
{
|
||||
COORD save = g_coord;
|
||||
|
||||
if (!USE_VTP)
|
||||
if (!vtp_working)
|
||||
clear_chars(g_coord, (Rows - g_coord.Y - 1)
|
||||
* Columns + (Columns - g_coord.X));
|
||||
else
|
||||
@@ -5943,7 +5937,7 @@ clear_to_end_of_line(void)
|
||||
{
|
||||
COORD save = g_coord;
|
||||
|
||||
if (!USE_VTP)
|
||||
if (!vtp_working)
|
||||
clear_chars(g_coord, Columns - g_coord.X);
|
||||
else
|
||||
{
|
||||
@@ -6045,7 +6039,11 @@ insert_lines(unsigned cLines)
|
||||
clip.Bottom = g_srScrollRegion.Bottom;
|
||||
|
||||
fill.Char.AsciiChar = ' ';
|
||||
if (!USE_VTP)
|
||||
if (!(vtp_working
|
||||
#ifdef FEAT_TERMGUICOLORS
|
||||
&& (p_tgc || t_colors >= 256)
|
||||
#endif
|
||||
))
|
||||
fill.Attributes = g_attrCurrent;
|
||||
else
|
||||
fill.Attributes = g_attrDefault;
|
||||
@@ -6074,7 +6072,7 @@ insert_lines(unsigned cLines)
|
||||
}
|
||||
}
|
||||
|
||||
if (USE_WT)
|
||||
if (vtp_working)
|
||||
{
|
||||
COORD coord;
|
||||
int i;
|
||||
@@ -6116,7 +6114,7 @@ delete_lines(unsigned cLines)
|
||||
clip.Bottom = g_srScrollRegion.Bottom;
|
||||
|
||||
fill.Char.AsciiChar = ' ';
|
||||
if (!USE_VTP)
|
||||
if (!vtp_working)
|
||||
fill.Attributes = g_attrCurrent;
|
||||
else
|
||||
fill.Attributes = g_attrDefault;
|
||||
@@ -6143,7 +6141,7 @@ delete_lines(unsigned cLines)
|
||||
}
|
||||
}
|
||||
|
||||
if (USE_WT)
|
||||
if (vtp_working)
|
||||
{
|
||||
COORD coord;
|
||||
int i;
|
||||
@@ -6169,7 +6167,11 @@ gotoxy(
|
||||
if (x < 1 || x > (unsigned)Columns || y < 1 || y > (unsigned)Rows)
|
||||
return;
|
||||
|
||||
if (!USE_VTP)
|
||||
if (!(vtp_working
|
||||
#ifdef FEAT_TERMGUICOLORS
|
||||
&& (p_tgc || t_colors >= 256)
|
||||
#endif
|
||||
))
|
||||
{
|
||||
// There are reports of double-width characters not displayed
|
||||
// correctly. This workaround should fix it, similar to how it's done
|
||||
@@ -6215,7 +6217,7 @@ textcolor(WORD wAttr)
|
||||
{
|
||||
g_attrCurrent = (g_attrCurrent & 0xf0) + (wAttr & 0x0f);
|
||||
|
||||
if (!USE_VTP)
|
||||
if (!vtp_working)
|
||||
SetConsoleTextAttribute(g_hConOut, g_attrCurrent);
|
||||
else
|
||||
vtp_sgr_bulk(wAttr);
|
||||
@@ -6227,7 +6229,7 @@ textbackground(WORD wAttr)
|
||||
{
|
||||
g_attrCurrent = (g_attrCurrent & 0x0f) + ((wAttr & 0x0f) << 4);
|
||||
|
||||
if (!USE_VTP)
|
||||
if (!vtp_working)
|
||||
SetConsoleTextAttribute(g_hConOut, g_attrCurrent);
|
||||
else
|
||||
vtp_sgr_bulk(wAttr);
|
||||
@@ -6240,7 +6242,7 @@ textbackground(WORD wAttr)
|
||||
static void
|
||||
normvideo(void)
|
||||
{
|
||||
if (!USE_VTP)
|
||||
if (!vtp_working)
|
||||
textattr(g_attrDefault);
|
||||
else
|
||||
vtp_sgr_bulk(0);
|
||||
@@ -6326,7 +6328,7 @@ visual_bell(void)
|
||||
coordOrigin, &dwDummy);
|
||||
|
||||
Sleep(15); // wait for 15 msec
|
||||
if (!USE_VTP)
|
||||
if (!vtp_working)
|
||||
WriteConsoleOutputAttribute(g_hConOut, oldattrs, Rows * Columns,
|
||||
coordOrigin, &dwDummy);
|
||||
vim_free(oldattrs);
|
||||
@@ -6341,7 +6343,7 @@ cursor_visible(BOOL fVisible)
|
||||
{
|
||||
s_cursor_visible = fVisible;
|
||||
|
||||
if (USE_VTP)
|
||||
if (vtp_working)
|
||||
vtp_printf("\033[?25%c", fVisible ? 'h' : 'l');
|
||||
|
||||
# ifdef MCH_CURSOR_SHAPE
|
||||
@@ -6413,7 +6415,11 @@ write_chars(
|
||||
}
|
||||
}
|
||||
|
||||
if (!USE_VTP)
|
||||
if (!(vtp_working
|
||||
#ifdef FEAT_TERMGUICOLORS
|
||||
&& (p_tgc || t_colors >= 256)
|
||||
#endif
|
||||
))
|
||||
{
|
||||
FillConsoleOutputAttribute(g_hConOut, g_attrCurrent, cells,
|
||||
coord, &written);
|
||||
@@ -6453,7 +6459,11 @@ write_chars(
|
||||
}
|
||||
|
||||
// Cursor under VTP is always in the correct position, no need to reset.
|
||||
if (!USE_VTP)
|
||||
if (!(vtp_working
|
||||
#ifdef FEAT_TERMGUICOLORS
|
||||
&& (p_tgc || t_colors >= 256)
|
||||
#endif
|
||||
))
|
||||
gotoxy(g_coord.X + 1, g_coord.Y + 1);
|
||||
|
||||
return written;
|
||||
@@ -6749,12 +6759,16 @@ notsgr:
|
||||
normvideo();
|
||||
else if (argc == 1)
|
||||
{
|
||||
if (USE_VTP)
|
||||
textcolor((WORD) arg1);
|
||||
if (vtp_working
|
||||
# ifdef FEAT_TERMGUICOLORS
|
||||
&& (p_tgc || t_colors >= 256)
|
||||
# endif
|
||||
)
|
||||
textcolor((WORD)arg1);
|
||||
else
|
||||
textattr((WORD) arg1);
|
||||
textattr((WORD)arg1);
|
||||
}
|
||||
else if (USE_VTP)
|
||||
else if (vtp_working)
|
||||
vtp_sgr_bulks(argc, args);
|
||||
}
|
||||
else if (argc == 2 && *p == 'H')
|
||||
@@ -6893,7 +6907,7 @@ notsgr:
|
||||
if (s[l] == ' ' && s[l + 1] == 'q')
|
||||
{
|
||||
// DECSCUSR (cursor style) sequences
|
||||
if (USE_VTP || USE_WT)
|
||||
if (vtp_working)
|
||||
vtp_printf("%.*s", l + 2, s); // Pass through
|
||||
s += l + 2;
|
||||
len -= l + 1;
|
||||
@@ -7932,6 +7946,8 @@ mch_setenv(char *var, char *value, int x UNUSED)
|
||||
* Not stable now.
|
||||
*/
|
||||
#define CONPTY_STABLE_BUILD MAKE_VER(10, 0, 32767) // T.B.D.
|
||||
// Note: Windows 11 (build >= 22000 means Windows 11, even though the major
|
||||
// version says 10!)
|
||||
|
||||
static void
|
||||
vtp_flag_init(void)
|
||||
@@ -7978,29 +7994,27 @@ vtp_flag_init(void)
|
||||
static void
|
||||
vtp_init(void)
|
||||
{
|
||||
CONSOLE_SCREEN_BUFFER_INFOEX csbi;
|
||||
# ifdef FEAT_TERMGUICOLORS
|
||||
COLORREF fg;
|
||||
# endif
|
||||
|
||||
csbi.cbSize = sizeof(csbi);
|
||||
GetConsoleScreenBufferInfoEx(g_hConOut, &csbi);
|
||||
save_console_bg_rgb = (guicolor_T)csbi.ColorTable[g_color_index_bg];
|
||||
save_console_fg_rgb = (guicolor_T)csbi.ColorTable[g_color_index_fg];
|
||||
store_console_bg_rgb = save_console_bg_rgb;
|
||||
store_console_fg_rgb = save_console_fg_rgb;
|
||||
|
||||
# ifdef FEAT_TERMGUICOLORS
|
||||
if (!USE_WT)
|
||||
if (!vtp_working)
|
||||
{
|
||||
CONSOLE_SCREEN_BUFFER_INFOEX csbi;
|
||||
csbi.cbSize = sizeof(csbi);
|
||||
GetConsoleScreenBufferInfoEx(g_hConOut, &csbi);
|
||||
save_console_bg_rgb = (guicolor_T)csbi.ColorTable[g_color_index_bg];
|
||||
save_console_fg_rgb = (guicolor_T)csbi.ColorTable[g_color_index_fg];
|
||||
store_console_bg_rgb = save_console_bg_rgb;
|
||||
store_console_fg_rgb = save_console_fg_rgb;
|
||||
|
||||
COLORREF bg;
|
||||
bg = (COLORREF)csbi.ColorTable[g_color_index_bg];
|
||||
bg = (GetRValue(bg) << 16) | (GetGValue(bg) << 8) | GetBValue(bg);
|
||||
default_console_color_bg = bg;
|
||||
|
||||
COLORREF fg;
|
||||
fg = (COLORREF)csbi.ColorTable[g_color_index_fg];
|
||||
fg = (GetRValue(fg) << 16) | (GetGValue(fg) << 8) | GetBValue(fg);
|
||||
default_console_color_fg = fg;
|
||||
}
|
||||
fg = (COLORREF)csbi.ColorTable[g_color_index_fg];
|
||||
fg = (GetRValue(fg) << 16) | (GetGValue(fg) << 8) | GetBValue(fg);
|
||||
default_console_color_fg = fg;
|
||||
# endif
|
||||
|
||||
set_console_color_rgb();
|
||||
@@ -8217,32 +8231,35 @@ set_console_color_rgb(void)
|
||||
guicolor_T fg, bg;
|
||||
int ctermfg, ctermbg;
|
||||
|
||||
if (!USE_VTP)
|
||||
if (!vtp_working)
|
||||
return;
|
||||
|
||||
get_default_console_color(&ctermfg, &ctermbg, &fg, &bg);
|
||||
|
||||
if (USE_WT)
|
||||
if (p_tgc || t_colors >= 256)
|
||||
{
|
||||
term_fg_rgb_color(fg);
|
||||
term_bg_rgb_color(bg);
|
||||
return;
|
||||
}
|
||||
|
||||
fg = (GetRValue(fg) << 16) | (GetGValue(fg) << 8) | GetBValue(fg);
|
||||
bg = (GetRValue(bg) << 16) | (GetGValue(bg) << 8) | GetBValue(bg);
|
||||
if (!conpty_working)
|
||||
{
|
||||
fg = (GetRValue(fg) << 16) | (GetGValue(fg) << 8) | GetBValue(fg);
|
||||
bg = (GetRValue(bg) << 16) | (GetGValue(bg) << 8) | GetBValue(bg);
|
||||
|
||||
csbi.cbSize = sizeof(csbi);
|
||||
GetConsoleScreenBufferInfoEx(g_hConOut, &csbi);
|
||||
csbi.cbSize = sizeof(csbi);
|
||||
GetConsoleScreenBufferInfoEx(g_hConOut, &csbi);
|
||||
|
||||
csbi.cbSize = sizeof(csbi);
|
||||
csbi.srWindow.Right += 1;
|
||||
csbi.srWindow.Bottom += 1;
|
||||
store_console_bg_rgb = csbi.ColorTable[g_color_index_bg];
|
||||
store_console_fg_rgb = csbi.ColorTable[g_color_index_fg];
|
||||
csbi.ColorTable[g_color_index_bg] = (COLORREF)bg;
|
||||
csbi.ColorTable[g_color_index_fg] = (COLORREF)fg;
|
||||
SetConsoleScreenBufferInfoEx(g_hConOut, &csbi);
|
||||
csbi.cbSize = sizeof(csbi);
|
||||
csbi.srWindow.Right += 1;
|
||||
csbi.srWindow.Bottom += 1;
|
||||
store_console_bg_rgb = csbi.ColorTable[g_color_index_bg];
|
||||
store_console_fg_rgb = csbi.ColorTable[g_color_index_fg];
|
||||
csbi.ColorTable[g_color_index_bg] = (COLORREF)bg;
|
||||
csbi.ColorTable[g_color_index_fg] = (COLORREF)fg;
|
||||
SetConsoleScreenBufferInfoEx(g_hConOut, &csbi);
|
||||
}
|
||||
# endif
|
||||
}
|
||||
|
||||
@@ -8259,6 +8276,7 @@ get_default_console_color(
|
||||
guicolor_T guibg = INVALCOLOR;
|
||||
int ctermfg = 0;
|
||||
int ctermbg = 0;
|
||||
int dummynull = 0;
|
||||
|
||||
id = syn_name2id((char_u *)"Normal");
|
||||
if (id > 0 && p_tgc)
|
||||
@@ -8267,18 +8285,27 @@ get_default_console_color(
|
||||
{
|
||||
ctermfg = -1;
|
||||
if (id > 0)
|
||||
syn_id2cterm_bg(id, &ctermfg, &ctermbg);
|
||||
guifg = ctermfg != -1 ? ctermtoxterm(ctermfg)
|
||||
syn_id2cterm_bg(id, &ctermfg, &dummynull);
|
||||
if (vtp_working)
|
||||
{
|
||||
cterm_normal_fg_gui_color = guifg =
|
||||
ctermfg != -1 ? ctermtoxterm(ctermfg) : INVALCOLOR;
|
||||
ctermfg = ctermfg < 0 ? 0 : ctermfg;
|
||||
}
|
||||
else
|
||||
{
|
||||
guifg = ctermfg != -1 ? ctermtoxterm(ctermfg)
|
||||
: default_console_color_fg;
|
||||
cterm_normal_fg_gui_color = guifg;
|
||||
ctermfg = ctermfg < 0 ? 0 : ctermfg;
|
||||
cterm_normal_fg_gui_color = guifg;
|
||||
ctermfg = ctermfg < 0 ? 0 : ctermfg;
|
||||
}
|
||||
}
|
||||
if (guibg == INVALCOLOR)
|
||||
{
|
||||
ctermbg = -1;
|
||||
if (id > 0)
|
||||
syn_id2cterm_bg(id, &ctermfg, &ctermbg);
|
||||
if (USE_WT)
|
||||
syn_id2cterm_bg(id, &dummynull, &ctermbg);
|
||||
if (vtp_working)
|
||||
{
|
||||
cterm_normal_bg_gui_color = guibg =
|
||||
ctermbg != -1 ? ctermtoxterm(ctermbg) : INVALCOLOR;
|
||||
@@ -8308,11 +8335,12 @@ get_default_console_color(
|
||||
reset_console_color_rgb(void)
|
||||
{
|
||||
# ifdef FEAT_TERMGUICOLORS
|
||||
CONSOLE_SCREEN_BUFFER_INFOEX csbi;
|
||||
|
||||
if (USE_WT)
|
||||
if (vtp_working)
|
||||
return;
|
||||
|
||||
CONSOLE_SCREEN_BUFFER_INFOEX csbi;
|
||||
|
||||
csbi.cbSize = sizeof(csbi);
|
||||
GetConsoleScreenBufferInfoEx(g_hConOut, &csbi);
|
||||
|
||||
@@ -8332,6 +8360,9 @@ reset_console_color_rgb(void)
|
||||
restore_console_color_rgb(void)
|
||||
{
|
||||
# ifdef FEAT_TERMGUICOLORS
|
||||
if (vtp_working)
|
||||
return;
|
||||
|
||||
CONSOLE_SCREEN_BUFFER_INFOEX csbi;
|
||||
|
||||
csbi.cbSize = sizeof(csbi);
|
||||
@@ -8349,7 +8380,7 @@ restore_console_color_rgb(void)
|
||||
void
|
||||
control_console_color_rgb(void)
|
||||
{
|
||||
if (USE_VTP)
|
||||
if (vtp_working)
|
||||
set_console_color_rgb();
|
||||
else
|
||||
reset_console_color_rgb();
|
||||
|
Reference in New Issue
Block a user