mirror of
https://github.com/fish-shell/fish-shell
synced 2024-11-10 23:24:39 +00:00
Merge floam/colorfix #3260
This commit is contained in:
commit
f7c6426b21
10 changed files with 225 additions and 244 deletions
|
@ -2,36 +2,35 @@
|
|||
|
||||
\subsection set_color-synopsis Synopsis
|
||||
\fish{synopsis}
|
||||
set_color [OPTIONS] [COLOR]
|
||||
set_color [OPTIONS] VALUE
|
||||
\endfish
|
||||
|
||||
\subsection set_color-description Description
|
||||
|
||||
`set_color` changes the foreground and/or background color of the terminal. `COLOR` is one of `black`, `red`, `green`, `brown`, `yellow`, `blue`, `magenta`, `purple`, `cyan`, `brred`, `brgreen`, `brbrown`, `bryellow`, `brblue`, `brmagenta`, `brpurple`, `brcyan`, `white`. The `br`, bright, forms are most useful as background colors. The special color `normal` resets the background and foreground to whatever is normal for your terminal.
|
||||
`set_color` is used to control the color and styling of text in the terminal. `VALUE` corresponds to a reserved color name such as *red* or a RGB color value given as 3 or 6 hexadecimal digits. The *br*-, as in 'bright', forms are full-brightness variants of the 8 standard-brightness colors on many terminals. *brblack* has higher brightness than *black* - towards gray. A special keyword *normal* resets text formatting to terminal defaults.
|
||||
|
||||
You can also specify an RGB value with three or six hex digits, such as A0FF33 or f2f. `fish` will choose the closest supported color. A three digit value is equivalent to specifying each digit twice; e.g., `#2BC` is the same as `#22BBCC`. Hex RGB values can be in lower or uppercase, optionally prefixed with the pound-sign character. Depending on the capabilities of your terminal the actual color may be approximated by the closest known matching color in the [ANSI X3.64](https://en.wikipedia.org/wiki/ANSI_escape_code#Colors) color palette.
|
||||
Valid colors include:
|
||||
|
||||
- *black*, *red*, *green*, *yellow*, *blue*, *magenta*, *cyan*, *white*
|
||||
- *brblack*, *brred*, *brgreen*, *bryellow*, *brblue*, *brmagenta*, *brcyan*, *brwhite*
|
||||
|
||||
An RGB value with three or six hex digits, such as A0FF33 or f2f can be used. `fish` will choose the closest supported color. A three digit value is equivalent to specifying each digit twice; e.g., `set_color 2BC` is the same as `set_color 22BBCC`. Hexadecimal RGB values can be in lower or uppercase. Depending on the capabilities of your terminal (and the level of support `set_color` has for it) the actual color may be approximated by a nearby matching reserved color name or `set_color` may not have an effect on color. A second color may be given as a desired fallback color. e.g. `set_color 124212` *brblue* will instruct set_color to use *brblue* if a terminal is not capable of the exact shade of grey desired. This is very useful when an 8 or 16 color terminal might otherwise not use a color.
|
||||
|
||||
The following options are available:
|
||||
|
||||
- `-b`, `--background` `COLOR` sets the background color.
|
||||
|
||||
- `-c`, `--print-colors` prints a list of all valid color names.
|
||||
|
||||
- `-o`, `--bold` sets bold or extra bright mode.
|
||||
|
||||
- `-b`, `--background` *COLOR* sets the background color.
|
||||
- `-c`, `--print-colors` prints a list of the 16 named colors.
|
||||
- `-o`, `--bold` sets bold mode.
|
||||
- `-u`, `--underline` sets underlined mode.
|
||||
|
||||
Calling `set_color normal` will set the terminal background and foreground colors to the defaults for the terminal.
|
||||
Using the *normal* keyword will reset foreground, background, and all formatting back to default.
|
||||
|
||||
Some terminals use the `--bold` escape sequence to switch to a brighter color set rather than bolding the characters. This only applies to the foreground color. You should probably use the `br` color name variants listed above for both the foreground and background "bright" colors rather than use this option. The only use for this option is on a black&white terminal (e.g., a DEC VT220) to select foreground black text that is bolder than the normal text.
|
||||
\subsection set_color-notes Notes
|
||||
|
||||
Not all terminal emulators support all these features.
|
||||
|
||||
Note 1: Setting either color to "normal" will reset both background and foreground colors to whatever is the default for the terminal.
|
||||
|
||||
Note 2: Setting the background color only affects subsequently written characters. Fish provides no way to set the background color for the entire terminal window. Configuring the window background color (and other attributes such as its opacity) has to be done using whatever mechanisms the terminal provides.
|
||||
|
||||
Note 3: `set_color` works by printing sequences of characters to its stdout. If you use it in a command substitution or pipe, these characters will also be captured (and can then later be printed to the terminal). To avoid printing these sequences (and hence not add color) if not connected to a terminal, use `isatty stdout`.
|
||||
1. Using the *normal* keyword will reset both background and foreground colors to whatever is the default for the terminal.
|
||||
2. Setting the background color only affects subsequently written characters. Fish provides no way to set the background color for the entire terminal window. Configuring the window background color (and other attributes such as its opacity) has to be done using whatever mechanisms the terminal provides.
|
||||
3. Some terminals use the `--bold` escape sequence to switch to a brighter color set rather than increasing the weight of text.
|
||||
4. `set_color` works by printing sequences of characters to *stdout*. If used in command substitution or a pipe, these characters will also be captured. This may or may not be desirable. Checking the exit code of `isatty stdout` before using `set_color` can be useful to decide not to colorize output in a script.
|
||||
|
||||
\subsection set_color-example Examples
|
||||
|
||||
|
@ -44,8 +43,10 @@ set_color normal; echo "Normal is nice" # Resets the background too
|
|||
|
||||
\subsection set_color-detection Terminal Capability Detection
|
||||
|
||||
Fish uses a heuristic to decide if your terminal supports the 256 color palette (as opposed to the more limited 16 color palette of older terminals). If you've done the equivalent of `set fish_term256 1` that will be true. If the $TERM value contains "256color" (e.g., "xterm-256color") that will be true. If your $TERM value is "xterm" and $TERM_PROGRAM is not set to "Apple_Terminal" that will be true. If your terminal supports the full 256 color palette (which is pretty much every color terminal emulator written in the past decade) you should ensure one of the aforementioned conditions is true.
|
||||
Fish uses a heuristic to decide if a terminal supports the 256-color palette as opposed to the more limited 16 color palette of older terminals. Support can be forced on by setting `fish_term256` to *1*. If `$TERM` contains "256color" (e.g., *xterm-256color*), 256-color support is enabled. If `$TERM` contains *xterm*, 256 color support is enabled (except for MacOS: `$TERM_PROGRAM` and `$TERM_PROGRAM_VERSION` are used to detect Terminal.app from MacOS 10.6; support is disabled here it because it is known that it reports `xterm` and only supports 16 colors.
|
||||
|
||||
Many terminals support 24-bit (i.e., true-color) color escape sequences. This includes modern xterms, Gnome Terminal, KDE Konsole, and iTerm2. Fish currently does some limited attempts to detect whether a given `$TERM` supports 24-bit colors. You can explicitly enable that support via `set fish_term24bit 1`. If you do so fish will not map your RGB color values to the closest known matching color in the ANSI X3.64 color palette.
|
||||
If terminfo reports 256 color support for a terminal, support will always be enabled. To debug color palette problems, `tput colors` may be useful to see the number of colors in terminfo for a terminal. Fish launched as `fish -d2` will include diagnostic messages that indicate the color support mode in use.
|
||||
|
||||
The `set_color` command uses the terminfo database to look up how to change terminal colors on whatever terminal is in use. Some systems have old and incomplete terminfo databases, and may lack color information for terminals that support it. Fish will use the [ANSI X3.64](https://en.wikipedia.org/wiki/ANSI_escape_code) escape sequences if the terminfo definition says less than 256 colors are supported; otherwise it will use the terminfo definition.
|
||||
Many terminals support 24-bit (i.e., true-color) color escape sequences. This includes modern xterm, Gnome Terminal, Konsole, and iTerm2. Fish attempts to detect such terminals through various means in `config.fish` You can explicitly force that support via `set fish_term24bit 1`.
|
||||
|
||||
The `set_color` command uses the terminfo database to look up how to change terminal colors on whatever terminal is in use. Some systems have old and incomplete terminfo databases, and may lack color information for terminals that support it. Fish will assume that all terminals can use the [ANSI X3.64](https://en.wikipedia.org/wiki/ANSI_escape_code) escape sequences if the terminfo definition indicates a color below 16 is not supported.
|
||||
|
|
|
@ -1,8 +1,6 @@
|
|||
# Main file for fish command completions. This file contains various
|
||||
# common helper functions for the command completions. All actual
|
||||
# completions are located in the completions subdirectory.
|
||||
#
|
||||
|
||||
#
|
||||
# Set default field separators
|
||||
#
|
||||
|
@ -15,6 +13,8 @@ function __fish_default_command_not_found_handler
|
|||
echo "fish: Unknown command '$argv'" >&2
|
||||
end
|
||||
|
||||
set -g version $FISH_VERSION
|
||||
|
||||
if status --is-interactive
|
||||
# The user has seemingly explicitly launched an old fish with too-new scripts installed.
|
||||
if not contains "string" (builtin -n)
|
||||
|
|
|
@ -22,42 +22,54 @@ function __fish_config_interactive -d "Initializations that should be performed
|
|||
set userdatadir $XDG_DATA_HOME
|
||||
end
|
||||
|
||||
if not set -q fish_greeting
|
||||
set -l line1 (printf (_ 'Welcome to fish, the friendly interactive shell' ))
|
||||
if not set -q __fish_init_2_3_0
|
||||
set -l line2 \n(printf (_ 'Type %shelp%s for instructions on how to use fish %s') (set_color green) (set_color normal))
|
||||
else
|
||||
set -l line2 ''
|
||||
end
|
||||
set -U fish_greeting $line1$line2
|
||||
end
|
||||
|
||||
#
|
||||
# If we are starting up for the first time, set various defaults
|
||||
#
|
||||
if not set -q __fish_init_1_50_0
|
||||
if not set -q fish_greeting
|
||||
set -l line1 (printf (_ 'Welcome to fish, the friendly interactive shell') )
|
||||
set -l line2 (printf (_ 'Type %shelp%s for instructions on how to use fish') (set_color green) (set_color normal))
|
||||
set -U fish_greeting $line1\n$line2
|
||||
if not set -q __fish_init_2_39_8 # bump this to 2_4_0 when rolling release if anything changes after 9/10/2016
|
||||
set -g colors_backup "$HOME/fish_previous_colors-(date).txt"
|
||||
|
||||
echo Backing up uvars to:\n (set_color --underline)$colors_backup(set_color normal)
|
||||
set -U >>$colors_backup
|
||||
for option in (set -Un | string match "fish*color_*")
|
||||
set -eU $option
|
||||
end
|
||||
set -U __fish_init_1_50_0
|
||||
echo \"Normalized\" colors on upgrade.
|
||||
|
||||
# Regular syntax highlighting colors
|
||||
set -q fish_color_normal
|
||||
or set -U fish_color_normal normal
|
||||
set -q fish_color_command
|
||||
or set -U fish_color_command brblue
|
||||
or set -U fish_color_command --bold
|
||||
set -q fish_color_param
|
||||
or set -U fish_color_param cyan
|
||||
set -q fish_color_redirection
|
||||
or set -U fish_color_redirection normal
|
||||
or set -U fish_color_redirection brblue
|
||||
set -q fish_color_comment
|
||||
or set -U fish_color_comment red
|
||||
set -q fish_color_error
|
||||
or set -U fish_color_error red --bold
|
||||
or set -U fish_color_error brred
|
||||
set -q fish_color_escape
|
||||
or set -U fish_color_escape cyan
|
||||
or set -U fish_color_escape bryellow
|
||||
set -q fish_color_operator
|
||||
or set -U fish_color_operator cyan
|
||||
or set -U fish_color_operator bryellow
|
||||
set -q fish_color_end
|
||||
or set -U fish_color_end green
|
||||
or set -U fish_color_end brmagenta
|
||||
set -q fish_color_quote
|
||||
or set -U fish_color_quote brown
|
||||
or set -U fish_color_quote yellow
|
||||
set -q fish_color_autosuggestion
|
||||
or set -U fish_color_autosuggestion brgrey
|
||||
or set -U fish_color_autosuggestion 555 brblack
|
||||
set -q fish_color_user
|
||||
or set -U fish_color_user green
|
||||
or set -U fish_color_user brgreen
|
||||
|
||||
set -q fish_color_host
|
||||
or set -U fish_color_host normal
|
||||
|
@ -71,31 +83,34 @@ function __fish_config_interactive -d "Initializations that should be performed
|
|||
|
||||
# Background color for matching quotes and parenthesis
|
||||
set -q fish_color_match
|
||||
or set -U fish_color_match cyan
|
||||
or set -U fish_color_match --background=blue
|
||||
|
||||
# Background color for search matches
|
||||
set -q fish_color_search_match
|
||||
or set -U fish_color_search_match --background=purple
|
||||
or set -U fish_color_search_match bryellow --background=brgrey
|
||||
|
||||
# Background color for selections
|
||||
set -q fish_color_selection
|
||||
or set -U fish_color_selection --background=purple
|
||||
or set -U fish_color_selection white --bold --background=brgrey
|
||||
|
||||
# Pager colors
|
||||
set -q fish_pager_color_prefix
|
||||
or set -U fish_pager_color_prefix cyan
|
||||
set -q fish_pager_color_completion
|
||||
or set -U fish_pager_color_completion normal
|
||||
or set -U fish_pager_color_prefix white --bold --underline
|
||||
#set -q fish_pager_color_completion
|
||||
#or set -U fish_pager_color_completion
|
||||
set -q fish_pager_color_description
|
||||
or set -U fish_pager_color_description brgrey
|
||||
or set -U fish_pager_color_description B3A06D yellow
|
||||
set -q fish_pager_color_progress
|
||||
or set -U fish_pager_color_progress cyan
|
||||
or set -U fish_pager_color_progress brwhite --background=cyan
|
||||
|
||||
#
|
||||
# Directory history colors
|
||||
#
|
||||
set -q fish_color_history_current
|
||||
or set -U fish_color_history_current cyan
|
||||
or set -U fish_color_history_current --bold
|
||||
|
||||
|
||||
set -U __fish_init_2_39_8
|
||||
end
|
||||
|
||||
#
|
||||
|
@ -144,11 +159,13 @@ function __fish_config_interactive -d "Initializations that should be performed
|
|||
# Completions for SysV startup scripts. These aren't bound to any
|
||||
# specific command, so they can't be autoloaded.
|
||||
#
|
||||
if test -d /etc/init.d
|
||||
complete -x -p "/etc/init.d/*" -a start --description 'Start service'
|
||||
complete -x -p "/etc/init.d/*" -a stop --description 'Stop service'
|
||||
complete -x -p "/etc/init.d/*" -a status --description 'Print service status'
|
||||
complete -x -p "/etc/init.d/*" -a restart --description 'Stop and then start service'
|
||||
complete -x -p "/etc/init.d/*" -a reload --description 'Reload service configuration'
|
||||
end
|
||||
|
||||
# Make sure some key bindings are set
|
||||
if not set -q fish_key_bindings
|
||||
|
@ -208,15 +225,14 @@ function __fish_config_interactive -d "Initializations that should be performed
|
|||
commandline -f repaint
|
||||
end
|
||||
|
||||
|
||||
# Notify vte-based terminals when $PWD changes (issue #906)
|
||||
# Notify terminals when $PWD changes (issue #906)
|
||||
if test "$VTE_VERSION" -ge 3405 -o "$TERM_PROGRAM" = "Apple_Terminal"
|
||||
function __update_vte_cwd --on-variable PWD --description 'Notify VTE of change to $PWD'
|
||||
function __update_cwd_osc --on-variable PWD --description 'Notify VTE of change to $PWD'
|
||||
status --is-command-substitution
|
||||
and return
|
||||
printf '\033]7;file://%s%s\a' (hostname) (pwd | __fish_urlencode)
|
||||
printf \e\]7\;file://\%s\%s\a (hostname) (pwd | __fish_urlencode)
|
||||
end
|
||||
__update_vte_cwd # Run once because we might have already inherited a PWD from an old tab
|
||||
__update_cwd_osc # Run once because we might have already inherited a PWD from an old tab
|
||||
end
|
||||
|
||||
### Command-not-found handlers
|
||||
|
@ -269,69 +285,4 @@ function __fish_config_interactive -d "Initializations that should be performed
|
|||
end
|
||||
end
|
||||
end
|
||||
|
||||
if test $TERM = "linux" # A linux in-kernel VT with 8 colors and 256/512 glyphs
|
||||
# In a VT we have
|
||||
# black (invisible)
|
||||
# red
|
||||
# green
|
||||
# yellow
|
||||
# blue
|
||||
# magenta
|
||||
# cyan
|
||||
# white
|
||||
|
||||
# Pretty much just set at random
|
||||
set -g fish_color_normal normal
|
||||
set -g fish_color_command yellow
|
||||
set -g fish_color_param cyan
|
||||
set -g fish_color_redirection normal
|
||||
set -g fish_color_comment red
|
||||
set -g fish_color_error red
|
||||
set -g fish_color_escape cyan
|
||||
set -g fish_color_operator cyan
|
||||
set -g fish_color_quote blue
|
||||
set -g fish_color_autosuggestion yellow
|
||||
set -g fish_color_valid_path
|
||||
set -g fish_color_cwd green
|
||||
set -g fish_color_cwd_root red
|
||||
set -g fish_color_match cyan
|
||||
set -g fish_color_history_current cyan
|
||||
set -g fish_color_search_match cyan
|
||||
set -g fish_color_selection blue
|
||||
set -g fish_color_end yellow
|
||||
set -g fish_color_host normal
|
||||
set -g fish_color_status red
|
||||
set -g fish_color_user green
|
||||
set -g fish_pager_color_prefix cyan
|
||||
set -g fish_pager_color_completion normal
|
||||
set -g fish_pager_color_description yellow
|
||||
set -g fish_pager_color_progress cyan
|
||||
|
||||
# Don't allow setting color other than what linux offers (see #2001)
|
||||
functions -e set_color
|
||||
function set_color
|
||||
set -l term_colors black red green yellow blue magenta cyan white normal
|
||||
for a in $argv
|
||||
if not contains -- $a $term_colors
|
||||
switch $a
|
||||
# Also allow options
|
||||
case "-*"
|
||||
continue
|
||||
case "*"
|
||||
echo "Color not valid in TERM = linux: $a"
|
||||
return 1
|
||||
end
|
||||
end
|
||||
end
|
||||
builtin set_color $argv
|
||||
return $status
|
||||
end
|
||||
|
||||
# Set fish_prompt to a VT-friendly version
|
||||
# without color or unicode
|
||||
function fish_prompt
|
||||
fish_fallback_prompt
|
||||
end
|
||||
end
|
||||
end
|
||||
|
|
|
@ -65,23 +65,27 @@ def escape_fish_cmd(text):
|
|||
|
||||
named_colors = {
|
||||
'black' : '000000',
|
||||
'red' : 'FF0000',
|
||||
'green' : '00FF00',
|
||||
'red' : '800000',
|
||||
'green' : '008000',
|
||||
'brown' : '725000',
|
||||
'yellow' : 'FFFF00',
|
||||
'blue' : '0000FF',
|
||||
'magenta' : 'FF00FF',
|
||||
'purple' : 'FF00FF',
|
||||
'cyan' : '00FFFF',
|
||||
'grey' : 'E5E5E5',
|
||||
'yellow' : '808000',
|
||||
'blue' : '000080',
|
||||
'magenta' : '800080',
|
||||
'purple' : '800080',
|
||||
'cyan' : '008080',
|
||||
'grey' : 'e5e5e5',
|
||||
'brgrey' : '555555',
|
||||
'brbrown' : 'FFFF55',
|
||||
'bryellow' : 'FFFF55',
|
||||
'brblue' : '5555FF',
|
||||
'brmagenta' : 'FF55FF',
|
||||
'brpurple' : 'FF55FF',
|
||||
'brcyan' : '55FFFF',
|
||||
'white' : 'FFFFFF'
|
||||
'white' : 'c0c0c0',
|
||||
'brblack' : '808080',
|
||||
'brred' : 'ff0000',
|
||||
'brgreen' : '00ff00',
|
||||
'brbrown' : 'ffff00',
|
||||
'bryellow' : 'ffff00',
|
||||
'brblue' : '0000ff',
|
||||
'brmagenta' : 'ff00ff',
|
||||
'brpurple' : 'ff00ff',
|
||||
'brcyan' : '00ffff',
|
||||
'brwhite' : 'ffffff'
|
||||
}
|
||||
|
||||
bindings_blacklist = set(["self-insert", "'begin;end'"])
|
||||
|
|
|
@ -179,7 +179,12 @@ int builtin_set_color(parser_t &parser, io_streams_t &streams, wchar_t **argv) {
|
|||
write_color(rgb_color_t::black(), true /* is_fg */);
|
||||
writembs(tparm(exit_attribute_mode));
|
||||
} else {
|
||||
write_color(fg, true /* is_fg */);
|
||||
if (!write_color(fg, true /* is_fg */)) {
|
||||
// We need to do *something* or the lack of any output messes up
|
||||
// when the cartesian product here would make "foo" disappear:
|
||||
// $ echo (set_color foo)bar
|
||||
set_color(rgb_color_t::reset(), rgb_color_t::none());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -149,29 +149,32 @@ struct named_color_t {
|
|||
const wchar_t *name;
|
||||
unsigned char idx;
|
||||
unsigned char rgb[3];
|
||||
bool hidden;
|
||||
};
|
||||
|
||||
static const named_color_t named_colors[] = {
|
||||
{L"black", 0, {0, 0, 0}},
|
||||
{L"red", 1, {0xFF, 0, 0}},
|
||||
{L"green", 2, {0, 0xFF, 0}},
|
||||
{L"brown", 3, {0x72, 0x50, 0}},
|
||||
{L"yellow", 3, {0xFF, 0xFF, 0}},
|
||||
{L"blue", 4, {0, 0, 0xFF}},
|
||||
{L"magenta", 5, {0xFF, 0, 0xFF}},
|
||||
{L"purple", 5, {0xFF, 0, 0xFF}},
|
||||
{L"cyan", 6, {0, 0xFF, 0xFF}},
|
||||
{L"grey", 7, {0xE5, 0xE5, 0xE5}},
|
||||
{L"brgrey", 8, {0x55, 0x55, 0x55}},
|
||||
{L"brred", 9, {0xFF, 0x55, 0x55}},
|
||||
{L"brgreen", 10, {0x55, 0xFF, 0x55}},
|
||||
{L"brbrown", 11, {0xFF, 0xFF, 0x55}},
|
||||
{L"bryellow", 11, {0xFF, 0xFF, 0x55}},
|
||||
{L"brblue", 12, {0x55, 0x55, 0xFF}},
|
||||
{L"brmagenta", 13, {0xFF, 0x55, 0xFF}},
|
||||
{L"brpurple", 13, {0xFF, 0x55, 0xFF}},
|
||||
{L"brcyan", 14, {0x55, 0xFF, 0xFF}},
|
||||
{L"white", 15, {0xFF, 0xFF, 0xFF}},
|
||||
{L"black", 0, {0, 0, 0}, false},
|
||||
{L"red", 1, {0x80, 0, 0}, false},
|
||||
{L"green", 2, {0, 0x80, 0}, false},
|
||||
{L"brown", 3, {0x72, 0x50, 0}, true},
|
||||
{L"yellow", 3, {0x80, 0x80, 0}, false},
|
||||
{L"blue", 4, {0, 0, 0x80}, false},
|
||||
{L"magenta", 5, {0x80, 0, 0x80}, false},
|
||||
{L"purple", 5, {0x80, 0, 0x80}, true},
|
||||
{L"cyan", 6, {0, 0x80, 0x80}, false},
|
||||
{L"white", 7, {0xC0, 0xC0, 0xC0}, false},
|
||||
{L"grey", 7, {0xe5, 0xe5, 0xe5}, true},
|
||||
{L"brblack", 8, {0x80, 0x80, 0x80}, false},
|
||||
{L"brgrey", 8, {0055, 0x55, 0x55}, true},
|
||||
{L"brred", 9, {0xFF, 0x00, 0x00}, false},
|
||||
{L"brgreen", 10, {0x00, 0xFF, 0x00}, false},
|
||||
{L"brbrown", 11, {0xFF, 0xFF, 0x00}, true},
|
||||
{L"bryellow", 11, {0xFF, 0xFF, 0x00}, false},
|
||||
{L"brblue", 12, {0x00, 0, 0xFF}, false},
|
||||
{L"brmagenta", 13, {0xFF, 0, 0xFF}, false},
|
||||
{L"brpurple", 13, {0xFF, 0, 0xFF}, true},
|
||||
{L"brcyan", 14, {0x00, 0xFF, 0xFF}, false},
|
||||
{L"brwhite", 15, {0xFF, 0xFF, 0xFF}, false},
|
||||
};
|
||||
|
||||
wcstring_list_t rgb_color_t::named_color_names(void) {
|
||||
|
@ -179,8 +182,10 @@ wcstring_list_t rgb_color_t::named_color_names(void) {
|
|||
wcstring_list_t result;
|
||||
result.reserve(1 + count);
|
||||
for (size_t i = 0; i < count; i++) {
|
||||
if (named_colors[i].hidden == false) {
|
||||
result.push_back(named_colors[i].name);
|
||||
}
|
||||
}
|
||||
// "normal" isn't really a color and does not have a color palette index or
|
||||
// RGB value. Therefore, it does not appear in the named_colors table.
|
||||
// However, it is a legitimate color name for the "set_color" command so
|
||||
|
@ -227,16 +232,24 @@ rgb_color_t rgb_color_t::white() { return rgb_color_t(type_named, 7); }
|
|||
|
||||
rgb_color_t rgb_color_t::black() { return rgb_color_t(type_named, 0); }
|
||||
|
||||
static unsigned char term8_color_for_rgb(const unsigned char rgb[3]) {
|
||||
static unsigned char term16_color_for_rgb(const unsigned char rgb[3]) {
|
||||
const uint32_t kColors[] = {
|
||||
0x000000, // Black
|
||||
0xFF0000, // Red
|
||||
0x00FF00, // Green
|
||||
0xFFFF00, // Yellow
|
||||
0x0000FF, // Blue
|
||||
0xFF00FF, // Magenta
|
||||
0x00FFFF, // Cyan
|
||||
0xFFFFFF, // White
|
||||
0x800000, // Red
|
||||
0x008000, // Green
|
||||
0x808000, // Yellow
|
||||
0x000080, // Blue
|
||||
0x800080, // Magenta
|
||||
0x008080, // Cyan
|
||||
0xc0c0c0, // White
|
||||
0x808080, // Bright Black
|
||||
0xFF0000, // Bright Red
|
||||
0x00FF00, // Bright Green
|
||||
0xFFFF00, // Bright Yellow
|
||||
0x0000FF, // Bright Blue
|
||||
0xFF00FF, // Bright Magenta
|
||||
0x00FFFF, // Bright Cyan
|
||||
0xFFFFFF // Bright White
|
||||
};
|
||||
return convert_color(rgb, kColors, sizeof kColors / sizeof *kColors);
|
||||
}
|
||||
|
@ -284,9 +297,10 @@ color24_t rgb_color_t::to_color24() const {
|
|||
}
|
||||
|
||||
unsigned char rgb_color_t::to_name_index() const {
|
||||
// XXX this should look for the nearest color
|
||||
assert(type == type_named || type == type_rgb);
|
||||
if (type == type_named) return data.name_idx;
|
||||
if (type == type_rgb) return term8_color_for_rgb(data.color.rgb);
|
||||
if (type == type_rgb) return term16_color_for_rgb(data.color.rgb);
|
||||
return (unsigned char)-1; // this is an error
|
||||
}
|
||||
|
||||
|
|
|
@ -37,15 +37,19 @@ static int (*out)(char c) = writeb_internal;
|
|||
/// Whether term256 and term24bit are supported.
|
||||
static color_support_t color_support = 0;
|
||||
|
||||
/// Set the function used for writing in move_cursor, writespace and set_color and all other output
|
||||
/// functions in this library. By default, the write call is used to give completely unbuffered
|
||||
/// output to stdout.
|
||||
void output_set_writer(int (*writer)(char)) {
|
||||
CHECK(writer, );
|
||||
out = writer;
|
||||
}
|
||||
|
||||
/// Return the current output writer.
|
||||
int (*output_get_writer())(char) { return out; }
|
||||
|
||||
// Returns true if we think the term256 support is "native" as opposed to forced.
|
||||
static bool term256_support_is_native(void) { return max_colors >= 256; }
|
||||
/// Returns true if we think tparm can handle outputting a color index
|
||||
static bool term_supports_color_natively(unsigned int c) { return max_colors >= c; }
|
||||
|
||||
color_support_t output_get_color_support(void) { return color_support; }
|
||||
|
||||
|
@ -59,15 +63,18 @@ unsigned char index_for_color(rgb_color_t c) {
|
|||
}
|
||||
|
||||
static bool write_color_escape(char *todo, unsigned char idx, bool is_fg) {
|
||||
bool result = false;
|
||||
if (idx < 16 || term256_support_is_native()) {
|
||||
if (term_supports_color_natively(idx)) {
|
||||
// Use tparm to emit color escape.
|
||||
writembs(tparm(todo, idx));
|
||||
result = true;
|
||||
return true;
|
||||
} else {
|
||||
// We are attempting to bypass the term here. Generate the ANSI escape sequence ourself.
|
||||
char buff[128] = "";
|
||||
char buff[16] = "";
|
||||
if (idx < 16) {
|
||||
snprintf(buff, sizeof buff, "\x1b[%dm", ((idx > 7) ? 82 : 30) + idx + !is_fg * 10);
|
||||
} else {
|
||||
snprintf(buff, sizeof buff, "\x1b[%d;5;%dm", is_fg ? 38 : 48, idx);
|
||||
}
|
||||
|
||||
int (*writer)(char) = output_get_writer();
|
||||
if (writer) {
|
||||
|
@ -76,9 +83,8 @@ static bool write_color_escape(char *todo, unsigned char idx, bool is_fg) {
|
|||
}
|
||||
}
|
||||
|
||||
result = true;
|
||||
return true;
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
static bool write_foreground_color(unsigned char idx) {
|
||||
|
@ -99,12 +105,13 @@ static bool write_background_color(unsigned char idx) {
|
|||
return false;
|
||||
}
|
||||
|
||||
void write_color(rgb_color_t color, bool is_fg) {
|
||||
// Exported for builtin_set_color's usage only.
|
||||
bool write_color(rgb_color_t color, bool is_fg) {
|
||||
bool supports_term24bit = !!(output_get_color_support() & color_support_term24bit);
|
||||
if (!supports_term24bit || !color.is_rgb()) {
|
||||
// Indexed or non-24 bit color.
|
||||
unsigned char idx = index_for_color(color);
|
||||
(is_fg ? write_foreground_color : write_background_color)(idx);
|
||||
return (is_fg ? write_foreground_color : write_background_color)(idx);
|
||||
} else {
|
||||
// 24 bit! No tparm here, just ANSI escape sequences.
|
||||
// Foreground: ^[38;2;<r>;<g>;<b>m
|
||||
|
@ -120,8 +127,30 @@ void write_color(rgb_color_t color, bool is_fg) {
|
|||
}
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
/// Sets the fg and bg color. May be called as often as you like, since if the new color is the same
|
||||
/// as the previous, nothing will be written. Negative values for set_color will also be ignored.
|
||||
/// Since the terminfo string this function emits can potentially cause the screen to flicker, the
|
||||
/// function takes care to write as little as possible.
|
||||
///
|
||||
/// Possible values for color are any form the FISH_COLOR_* enum and FISH_COLOR_RESET.
|
||||
/// FISH_COLOR_RESET will perform an exit_attribute_mode, even if set_color thinks it is already in
|
||||
/// FISH_COLOR_NORMAL mode.
|
||||
///
|
||||
/// In order to set the color to normal, three terminfo strings may have to be written.
|
||||
///
|
||||
/// - First a string to set the color, such as set_a_foreground. This is needed because otherwise
|
||||
/// the previous strings colors might be removed as well.
|
||||
///
|
||||
/// - After that we write the exit_attribute_mode string to reset all color attributes.
|
||||
///
|
||||
/// - Lastly we may need to write set_a_background or set_a_foreground to set the other half of the
|
||||
/// color pair to what it should be.
|
||||
///
|
||||
/// \param c Foreground color.
|
||||
/// \param c2 Background color.
|
||||
void set_color(rgb_color_t c, rgb_color_t c2) {
|
||||
#if 0
|
||||
wcstring tmp = c.description();
|
||||
|
@ -260,11 +289,15 @@ static int writeb_internal(char c) { // cppcheck
|
|||
return 0;
|
||||
}
|
||||
|
||||
/// This is for writing process notification messages. Has to write to stdout, so clr_eol and such
|
||||
/// functions will work correctly. Not an issue since this function is only used in interactive mode
|
||||
/// anyway.
|
||||
int writeb(tputs_arg_t b) {
|
||||
out(b);
|
||||
return 0;
|
||||
}
|
||||
|
||||
/// Write a wide character using the output method specified using output_set_writer().
|
||||
int writech(wint_t ch) {
|
||||
char buff[MB_LEN_MAX + 1];
|
||||
size_t len;
|
||||
|
@ -294,6 +327,7 @@ int writech(wint_t ch) {
|
|||
return 0;
|
||||
}
|
||||
|
||||
/// Write a wide character string to FD 1.
|
||||
void writestr(const wchar_t *str) {
|
||||
CHECK(str, );
|
||||
|
||||
|
@ -329,6 +363,8 @@ void writestr(const wchar_t *str) {
|
|||
if (buffer != static_buffer) delete[] buffer;
|
||||
}
|
||||
|
||||
/// Given a list of rgb_color_t, pick the "best" one, as determined by the color support. Returns
|
||||
/// rgb_color_t::none() if empty.
|
||||
rgb_color_t best_color(const std::vector<rgb_color_t> &candidates, color_support_t support) {
|
||||
if (candidates.empty()) {
|
||||
return rgb_color_t::none();
|
||||
|
@ -358,7 +394,8 @@ rgb_color_t best_color(const std::vector<rgb_color_t> &candidates, color_support
|
|||
return result;
|
||||
}
|
||||
|
||||
// This code should be refactored to enable sharing with builtin_set_color.
|
||||
/// Return the internal color code representing the specified color.
|
||||
/// XXX This code should be refactored to enable sharing with builtin_set_color.
|
||||
rgb_color_t parse_color(const wcstring &val, bool is_background) {
|
||||
int is_bold = 0;
|
||||
int is_underline = 0;
|
||||
|
@ -408,6 +445,7 @@ rgb_color_t parse_color(const wcstring &val, bool is_background) {
|
|||
return result;
|
||||
}
|
||||
|
||||
/// Write specified multibyte string.
|
||||
void writembs_check(char *mbs, const char *mbs_name, const char *file, long line) {
|
||||
if (mbs != NULL) {
|
||||
tputs(mbs, 1, &writeb);
|
||||
|
|
57
src/output.h
57
src/output.h
|
@ -14,65 +14,33 @@
|
|||
|
||||
/// Constants for various colors as used by the set_color function.
|
||||
enum {
|
||||
FISH_COLOR_BLACK,
|
||||
FISH_COLOR_RED,
|
||||
FISH_COLOR_GREEN,
|
||||
FISH_COLOR_YELLOW,
|
||||
FISH_COLOR_BLUE,
|
||||
FISH_COLOR_MAGENTA,
|
||||
FISH_COLOR_CYAN,
|
||||
FISH_COLOR_WHITE,
|
||||
FISH_COLOR_NORMAL, // the default fg color of the terminal
|
||||
FISH_COLOR_RESET
|
||||
FISH_COLOR_BLACK, // 0
|
||||
FISH_COLOR_RED, // 1
|
||||
FISH_COLOR_GREEN, // 2
|
||||
FISH_COLOR_YELLOW, // 3
|
||||
FISH_COLOR_BLUE, // 4
|
||||
FISH_COLOR_MAGENTA, // 5
|
||||
FISH_COLOR_CYAN, // 6
|
||||
FISH_COLOR_WHITE, // 7
|
||||
FISH_COLOR_NORMAL, // 8 terminal default
|
||||
FISH_COLOR_RESET // 9
|
||||
};
|
||||
|
||||
/// Sets the fg and bg color. May be called as often as you like, since if the new color is the same
|
||||
/// as the previous, nothing will be written. Negative values for set_color will also be ignored.
|
||||
/// Since the terminfo string this function emits can potentially cause the screen to flicker, the
|
||||
/// function takes care to write as little as possible.
|
||||
///
|
||||
/// Possible values for color are any form the FISH_COLOR_* enum and FISH_COLOR_RESET.
|
||||
/// FISH_COLOR_RESET will perform an exit_attribute_mode, even if set_color thinks it is already in
|
||||
/// FISH_COLOR_NORMAL mode.
|
||||
///
|
||||
/// In order to set the color to normal, three terminfo strings may have to be written.
|
||||
///
|
||||
/// - First a string to set the color, such as set_a_foreground. This is needed because otherwise
|
||||
/// the previous strings colors might be removed as well.
|
||||
///
|
||||
/// - After that we write the exit_attribute_mode string to reset all color attributes.
|
||||
///
|
||||
/// - Lastly we may need to write set_a_background or set_a_foreground to set the other half of the
|
||||
/// color pair to what it should be.
|
||||
///
|
||||
/// \param c Foreground color.
|
||||
/// \param c2 Background color.
|
||||
void set_color(rgb_color_t c, rgb_color_t c2);
|
||||
|
||||
/// Write specified multibyte string.
|
||||
void writembs_check(char *mbs, const char *mbs_name, const char *file, long line);
|
||||
#define writembs(mbs) writembs_check((mbs), #mbs, __FILE__, __LINE__)
|
||||
|
||||
/// Write a wide character using the output method specified using output_set_writer().
|
||||
int writech(wint_t ch);
|
||||
|
||||
/// Write a wide character string to FD 1.
|
||||
void writestr(const wchar_t *str);
|
||||
|
||||
/// Return the internal color code representing the specified color.
|
||||
rgb_color_t parse_color(const wcstring &val, bool is_background);
|
||||
|
||||
/// This is for writing process notification messages. Has to write to stdout, so clr_eol and such
|
||||
/// functions will work correctly. Not an issue since this function is only used in interactive mode
|
||||
/// anyway.
|
||||
int writeb(tputs_arg_t b);
|
||||
|
||||
/// Set the function used for writing in move_cursor, writespace and set_color and all other output
|
||||
/// functions in this library. By default, the write call is used to give completely unbuffered
|
||||
/// output to stdout.
|
||||
void output_set_writer(int (*writer)(char));
|
||||
|
||||
/// Return the current output writer.
|
||||
int (*output_get_writer())(char);
|
||||
|
||||
/// Sets what colors are supported.
|
||||
|
@ -81,12 +49,9 @@ typedef unsigned int color_support_t;
|
|||
color_support_t output_get_color_support();
|
||||
void output_set_color_support(color_support_t support);
|
||||
|
||||
/// Given a list of rgb_color_t, pick the "best" one, as determined by the color support. Returns
|
||||
/// rgb_color_t::none() if empty.
|
||||
rgb_color_t best_color(const std::vector<rgb_color_t> &colors, color_support_t support);
|
||||
|
||||
// Exported for builtin_set_color's usage only.
|
||||
void write_color(rgb_color_t color, bool is_fg);
|
||||
bool write_color(rgb_color_t color, bool is_fg);
|
||||
unsigned char index_for_color(rgb_color_t c);
|
||||
|
||||
#endif
|
||||
|
|
|
@ -130,9 +130,10 @@ line_t pager_t::completion_print_item(const wcstring &prefix, const comp_t *c, s
|
|||
{
|
||||
written += print_max(L" ", packed_color, 1, false, &line_data);
|
||||
}
|
||||
print_max(L"(", packed_color, 1, false, &line_data);
|
||||
// hack - this just works around the issue
|
||||
print_max(L"(", highlight_spec_pager_completion | highlight_make_background(bg_color), 1, false, &line_data);
|
||||
print_max(c->desc, packed_color, desc_width, false, &line_data);
|
||||
print_max(L")", packed_color, 1, false, &line_data);
|
||||
print_max(L")", highlight_spec_pager_completion | highlight_make_background(bg_color), 1, false, &line_data);
|
||||
} else {
|
||||
while (written < width) {
|
||||
written += print_max(L" ", 0, 1, false, &line_data);
|
||||
|
|
|
@ -205,7 +205,7 @@ size_t escape_code_length(const wchar_t *code) {
|
|||
bool found = false;
|
||||
|
||||
if (cur_term != NULL) {
|
||||
// Detect these terminfo color escapes with parameter value 0..7, all of which don't move
|
||||
// Detect these terminfo color escapes with parameter value 0..16, all of which don't move
|
||||
// the cursor.
|
||||
char *const esc[] = {
|
||||
set_a_foreground, set_a_background, set_foreground, set_background,
|
||||
|
@ -232,12 +232,15 @@ size_t escape_code_length(const wchar_t *code) {
|
|||
enter_superscript_mode, exit_superscript_mode, enter_blink_mode,
|
||||
enter_italics_mode, exit_italics_mode, enter_reverse_mode,
|
||||
enter_shadow_mode, exit_shadow_mode, enter_standout_mode,
|
||||
exit_standout_mode, enter_secure_mode};
|
||||
exit_standout_mode, enter_secure_mode, enter_dim_mode,
|
||||
enter_blink_mode, enter_protected_mode, enter_alt_charset_mode,
|
||||
exit_alt_charset_mode};
|
||||
|
||||
for (size_t p = 0; p < sizeof esc2 / sizeof *esc2 && !found; p++) {
|
||||
if (!esc2[p]) continue;
|
||||
// Test both padded and unpadded version, just to be safe. Most versions of tparm don't
|
||||
// actually seem to do anything these days.
|
||||
|
||||
size_t len = maxi(try_sequence(tparm(esc2[p]), code), try_sequence(esc2[p], code));
|
||||
if (len) {
|
||||
resulting_length = len;
|
||||
|
@ -601,9 +604,8 @@ static bool perform_any_impending_soft_wrap(screen_t *scr, int x, int y) {
|
|||
/// Make sure we don't soft wrap.
|
||||
static void invalidate_soft_wrap(screen_t *scr) { scr->soft_wrap_location = INVALID_LOCATION; }
|
||||
|
||||
// Various code for testing term behavior.
|
||||
|
||||
#if 0
|
||||
/// Various code for testing term behavior.
|
||||
static bool test_stuff(screen_t *scr)
|
||||
{
|
||||
data_buffer_t output;
|
||||
|
@ -1186,18 +1188,18 @@ void s_reset(screen_t *s, screen_reset_mode_t mode) {
|
|||
// omitted_newline_char in common.cpp.
|
||||
int non_space_width = fish_wcwidth(omitted_newline_char);
|
||||
if (screen_width >= non_space_width) {
|
||||
bool has_256_colors = output_get_color_support() & color_support_term256;
|
||||
if (has_256_colors) {
|
||||
// Draw the string in term256 gray.
|
||||
abandon_line_string.append(L"\x1b[38;5;245m");
|
||||
} else {
|
||||
// Draw in "bright black" (gray).
|
||||
abandon_line_string.append(
|
||||
L"\x1b[0m" // bright
|
||||
L"\x1b[30;1m"); // black
|
||||
if (enter_dim_mode) {
|
||||
// Use dim if they have it, so the color will be based on their actual normal color and the background of the termianl.
|
||||
abandon_line_string.append(str2wcstring(tparm(enter_dim_mode)));
|
||||
}
|
||||
else if (set_a_foreground && max_colors >= 8) {
|
||||
// Draw the string in gray.
|
||||
abandon_line_string.append(str2wcstring(tparm(set_a_foreground, 8)));
|
||||
}
|
||||
|
||||
abandon_line_string.push_back(omitted_newline_char);
|
||||
abandon_line_string.append(L"\x1b[0m"); // normal text ANSI escape sequence
|
||||
if (exit_attribute_mode)
|
||||
abandon_line_string.append(str2wcstring(tparm(exit_attribute_mode))); // normal text ANSI escape sequence
|
||||
abandon_line_string.append(screen_width - non_space_width, L' ');
|
||||
}
|
||||
abandon_line_string.push_back(L'\r');
|
||||
|
|
Loading…
Reference in a new issue