mirror of
https://github.com/JanDeDobbeleer/oh-my-posh.git
synced 2025-01-13 04:07:25 -08:00
refactor(terminal): make truecolor logic internal
This commit is contained in:
parent
0c8b8021b8
commit
dbc0a370b2
|
@ -70,7 +70,6 @@ Exports the config to an image file using customized output options.`,
|
|||
terminal.Init(shell.GENERIC)
|
||||
terminal.BackgroundColor = shell.ConsoleBackgroundColor(env, cfg.TerminalBackground)
|
||||
terminal.AnsiColors = cfg.MakeColors()
|
||||
terminal.TrueColor = env.CmdFlags.TrueColor
|
||||
|
||||
eng := &engine.Engine{
|
||||
Config: cfg,
|
||||
|
|
|
@ -44,7 +44,6 @@ var debugCmd = &cobra.Command{
|
|||
terminal.BackgroundColor = shell.ConsoleBackgroundColor(env, cfg.TerminalBackground)
|
||||
terminal.AnsiColors = cfg.MakeColors()
|
||||
terminal.Plain = plain
|
||||
terminal.TrueColor = env.CmdFlags.TrueColor
|
||||
|
||||
eng := &engine.Engine{
|
||||
Config: cfg,
|
||||
|
|
|
@ -69,7 +69,6 @@ func (b *Block) InitPlain(env platform.Environment, config *Config) {
|
|||
terminal.Init(shell.GENERIC)
|
||||
terminal.BackgroundColor = shell.ConsoleBackgroundColor(env, config.TerminalBackground)
|
||||
terminal.AnsiColors = config.MakeColors()
|
||||
terminal.TrueColor = env.Flags().TrueColor
|
||||
|
||||
b.env = env
|
||||
b.executeSegmentLogic()
|
||||
|
|
|
@ -136,11 +136,11 @@ func (e *Engine) newline() {
|
|||
}
|
||||
|
||||
func (e *Engine) isWarp() bool {
|
||||
return e.Env.Getenv("TERM_PROGRAM") == "WarpTerminal"
|
||||
return terminal.Program == terminal.Warp
|
||||
}
|
||||
|
||||
func (e *Engine) isIterm() bool {
|
||||
return e.Env.Getenv("TERM_PROGRAM") == "iTerm.app"
|
||||
return terminal.Program == terminal.ITerm
|
||||
}
|
||||
|
||||
func (e *Engine) shouldFill(filler string, remaining, blockLength int) (string, bool) {
|
||||
|
|
|
@ -118,7 +118,6 @@ func engineRender() {
|
|||
terminal.Init(shell.GENERIC)
|
||||
terminal.BackgroundColor = shell.ConsoleBackgroundColor(env, cfg.TerminalBackground)
|
||||
terminal.AnsiColors = cfg.MakeColors()
|
||||
terminal.TrueColor = env.CmdFlags.TrueColor
|
||||
|
||||
engine := &Engine{
|
||||
Config: cfg,
|
||||
|
|
|
@ -28,7 +28,6 @@ func New(flags *platform.Flags) *Engine {
|
|||
terminal.BackgroundColor = shell.ConsoleBackgroundColor(env, cfg.TerminalBackground)
|
||||
terminal.AnsiColors = cfg.MakeColors()
|
||||
terminal.Plain = flags.Plain
|
||||
terminal.TrueColor = env.CmdFlags.TrueColor
|
||||
|
||||
eng := &Engine{
|
||||
Config: cfg,
|
||||
|
|
|
@ -106,7 +106,6 @@ func (e *Engine) Primary() string {
|
|||
// see https://github.com/jandedobbeleer/oh-my-posh/pull/2398
|
||||
|
||||
terminal.Init(shell.GENERIC)
|
||||
terminal.TrueColor = e.Env.Flags().TrueColor
|
||||
|
||||
prompt := terminal.SaveCursorPosition()
|
||||
prompt += strings.Repeat(" ", space)
|
||||
|
|
|
@ -58,7 +58,6 @@ type Flags struct {
|
|||
HasTransient bool
|
||||
PromptCount int
|
||||
Cleared bool
|
||||
TrueColor bool
|
||||
NoExitCode bool
|
||||
Column int
|
||||
}
|
||||
|
@ -216,24 +215,24 @@ func (env *Shell) Init() {
|
|||
if env.CmdFlags == nil {
|
||||
env.CmdFlags = &Flags{}
|
||||
}
|
||||
|
||||
if env.CmdFlags.Debug {
|
||||
log.Enable()
|
||||
}
|
||||
|
||||
if env.CmdFlags.Plain {
|
||||
log.Plain()
|
||||
}
|
||||
trueColor := true
|
||||
if env.Getenv("TERM_PROGRAM") == "Apple_Terminal" {
|
||||
trueColor = false
|
||||
}
|
||||
env.CmdFlags.TrueColor = trueColor
|
||||
|
||||
env.fileCache = &fileCache{}
|
||||
env.fileCache.Init(env.CachePath())
|
||||
env.resolveConfigPath()
|
||||
env.cmdCache = &commandCache{
|
||||
commands: NewConcurrentMap(),
|
||||
}
|
||||
|
||||
env.tmplCache = &TemplateCache{}
|
||||
|
||||
env.SetPromptCount()
|
||||
}
|
||||
|
||||
|
|
|
@ -16,7 +16,7 @@ import (
|
|||
// This can include a valid hex color in the format `#FFFFFF`,
|
||||
// but also a name of one of the first 16 ANSI colors like `lightBlue`.
|
||||
type ColorString interface {
|
||||
ToColor(colorString string, isBackground bool, trueColor bool) Color
|
||||
ToColor(colorString string, isBackground bool) Color
|
||||
}
|
||||
|
||||
type ColorSet struct {
|
||||
|
@ -153,45 +153,57 @@ const (
|
|||
backgroundIndex = 1
|
||||
)
|
||||
|
||||
func (d *DefaultColors) ToColor(colorString string, isBackground, trueColor bool) Color {
|
||||
func (d *DefaultColors) ToColor(colorString string, isBackground bool) Color {
|
||||
if len(colorString) == 0 {
|
||||
return emptyColor
|
||||
}
|
||||
|
||||
if colorString == Transparent {
|
||||
return transparentColor
|
||||
}
|
||||
|
||||
if colorString == Accent {
|
||||
if d.accent == nil {
|
||||
return emptyColor
|
||||
}
|
||||
|
||||
if isBackground {
|
||||
return Color(d.accent.Background)
|
||||
}
|
||||
|
||||
return Color(d.accent.Foreground)
|
||||
}
|
||||
|
||||
colorFromName, err := getAnsiColorFromName(colorString, isBackground)
|
||||
if err == nil {
|
||||
return colorFromName
|
||||
}
|
||||
|
||||
if !strings.HasPrefix(colorString, "#") {
|
||||
val, err := strconv.ParseUint(colorString, 10, 64)
|
||||
if err != nil || val > 255 {
|
||||
return emptyColor
|
||||
}
|
||||
|
||||
c256 := color.C256(uint8(val), isBackground)
|
||||
return Color(c256.String())
|
||||
}
|
||||
|
||||
style := color.HEX(colorString, isBackground)
|
||||
if !style.IsEmpty() {
|
||||
if trueColor {
|
||||
return Color(style.String())
|
||||
}
|
||||
|
||||
return Color(style.C256().String())
|
||||
}
|
||||
|
||||
if colorInt, err := strconv.ParseInt(colorString, 10, 8); err == nil {
|
||||
c := color.C256(uint8(colorInt), isBackground)
|
||||
|
||||
return Color(c.String())
|
||||
}
|
||||
|
||||
return emptyColor
|
||||
}
|
||||
|
||||
|
@ -202,8 +214,10 @@ func getAnsiColorFromName(colorName string, isBackground bool) (Color, error) {
|
|||
if isBackground {
|
||||
return colorCodes[backgroundIndex], nil
|
||||
}
|
||||
|
||||
return colorCodes[foregroundIndex], nil
|
||||
}
|
||||
|
||||
return "", fmt.Errorf("color name %s does not exist", colorName)
|
||||
}
|
||||
|
||||
|
@ -219,12 +233,14 @@ type PaletteColors struct {
|
|||
palette Palette
|
||||
}
|
||||
|
||||
func (p *PaletteColors) ToColor(colorString string, isBackground, trueColor bool) Color {
|
||||
func (p *PaletteColors) ToColor(colorString string, isBackground bool) Color {
|
||||
paletteColor, err := p.palette.ResolveColor(colorString)
|
||||
if err != nil {
|
||||
return emptyColor
|
||||
}
|
||||
ansiColor := p.ansiColors.ToColor(paletteColor, isBackground, trueColor)
|
||||
|
||||
ansiColor := p.ansiColors.ToColor(paletteColor, isBackground)
|
||||
|
||||
return ansiColor
|
||||
}
|
||||
|
||||
|
@ -241,7 +257,7 @@ type cachedColorKey struct {
|
|||
isBackground bool
|
||||
}
|
||||
|
||||
func (c *CachedColors) ToColor(colorString string, isBackground, trueColor bool) Color {
|
||||
func (c *CachedColors) ToColor(colorString string, isBackground bool) Color {
|
||||
if c.colorCache == nil {
|
||||
c.colorCache = make(map[cachedColorKey]Color)
|
||||
}
|
||||
|
@ -249,7 +265,7 @@ func (c *CachedColors) ToColor(colorString string, isBackground, trueColor bool)
|
|||
if ansiColor, hit := c.colorCache[key]; hit {
|
||||
return ansiColor
|
||||
}
|
||||
ansiColor := c.ansiColors.ToColor(colorString, isBackground, trueColor)
|
||||
ansiColor := c.ansiColors.ToColor(colorString, isBackground)
|
||||
c.colorCache[key] = ansiColor
|
||||
return ansiColor
|
||||
}
|
||||
|
|
|
@ -31,16 +31,15 @@ func TestGetAnsiFromColorString(t *testing.T) {
|
|||
}
|
||||
for _, tc := range cases {
|
||||
ansiColors := &DefaultColors{}
|
||||
ansiColor := ansiColors.ToColor(tc.Color, tc.Background, !tc.Color256)
|
||||
trueColor = !tc.Color256
|
||||
ansiColor := ansiColors.ToColor(tc.Color, tc.Background)
|
||||
assert.Equal(t, tc.Expected, ansiColor, tc.Case)
|
||||
}
|
||||
}
|
||||
|
||||
func TestMakeColors(t *testing.T) {
|
||||
env := &mock.MockedEnvironment{}
|
||||
env.On("Flags").Return(&platform.Flags{
|
||||
TrueColor: true,
|
||||
})
|
||||
|
||||
env.On("WindowsRegistryKeyValue", `HKEY_CURRENT_USER\Software\Microsoft\Windows\DWM\ColorizationColor`).Return(&platform.WindowsRegistryValue{}, errors.New("err"))
|
||||
colors := MakeColors(nil, false, "", env)
|
||||
assert.IsType(t, &DefaultColors{}, colors)
|
||||
|
|
|
@ -12,8 +12,9 @@ func (d *DefaultColors) SetAccentColor(_ platform.Environment, defaultColor stri
|
|||
if len(defaultColor) == 0 {
|
||||
return
|
||||
}
|
||||
|
||||
d.accent = &Colors{
|
||||
Foreground: string(d.ToColor(defaultColor, false, env.Flags().TrueColor)),
|
||||
Background: string(d.ToColor(defaultColor, true, env.Flags().TrueColor)),
|
||||
Foreground: string(d.ToColor(defaultColor, false)),
|
||||
Background: string(d.ToColor(defaultColor, true)),
|
||||
}
|
||||
}
|
||||
|
|
|
@ -12,11 +12,13 @@ func GetAccentColor(env platform.Environment) (*RGB, error) {
|
|||
if env == nil {
|
||||
return nil, errors.New("unable to get color without environment")
|
||||
}
|
||||
|
||||
// see https://stackoverflow.com/questions/3560890/vista-7-how-to-get-glass-color
|
||||
value, err := env.WindowsRegistryKeyValue(`HKEY_CURRENT_USER\Software\Microsoft\Windows\DWM\ColorizationColor`)
|
||||
if err != nil || value.ValueType != platform.DWORD {
|
||||
return nil, err
|
||||
}
|
||||
|
||||
return &RGB{
|
||||
R: byte(value.DWord >> 16),
|
||||
G: byte(value.DWord >> 8),
|
||||
|
@ -28,13 +30,16 @@ func (d *DefaultColors) SetAccentColor(env platform.Environment, defaultColor st
|
|||
rgb, err := GetAccentColor(env)
|
||||
if err != nil {
|
||||
d.accent = &Colors{
|
||||
Foreground: string(d.ToColor(defaultColor, false, env.Flags().TrueColor)),
|
||||
Background: string(d.ToColor(defaultColor, true, env.Flags().TrueColor)),
|
||||
Foreground: string(d.ToColor(defaultColor, false)),
|
||||
Background: string(d.ToColor(defaultColor, true)),
|
||||
}
|
||||
|
||||
return
|
||||
}
|
||||
|
||||
foreground := color.RGB(rgb.R, rgb.G, rgb.B, false)
|
||||
background := color.RGB(rgb.R, rgb.G, rgb.B, true)
|
||||
|
||||
d.accent = &Colors{
|
||||
Foreground: foreground.String(),
|
||||
Background: background.String(),
|
||||
|
|
|
@ -2,8 +2,10 @@ package terminal
|
|||
|
||||
import (
|
||||
"fmt"
|
||||
"os"
|
||||
"strings"
|
||||
|
||||
"github.com/jandedobbeleer/oh-my-posh/src/log"
|
||||
"github.com/jandedobbeleer/oh-my-posh/src/regex"
|
||||
"github.com/jandedobbeleer/oh-my-posh/src/shell"
|
||||
"github.com/mattn/go-runewidth"
|
||||
|
@ -46,9 +48,10 @@ var (
|
|||
AnsiColors ColorString
|
||||
|
||||
Plain bool
|
||||
TrueColor bool
|
||||
Interactive bool
|
||||
|
||||
trueColor bool
|
||||
|
||||
builder strings.Builder
|
||||
length int
|
||||
|
||||
|
@ -63,7 +66,8 @@ var (
|
|||
|
||||
lastRune rune
|
||||
|
||||
shellName string
|
||||
Shell string
|
||||
Program string
|
||||
|
||||
formats *shellFormats
|
||||
)
|
||||
|
@ -129,12 +133,24 @@ const (
|
|||
hyperLinkEnd = "</LINK>"
|
||||
hyperLinkText = "<TEXT>"
|
||||
hyperLinkTextEnd = "</TEXT>"
|
||||
|
||||
WindowsTerminal = "Windows Terminal"
|
||||
Warp = "WarpTerminal"
|
||||
ITerm = "iTerm.app"
|
||||
AppleTerminal = "Apple_Terminal"
|
||||
Unknown = "Unknown"
|
||||
)
|
||||
|
||||
func Init(sh string) {
|
||||
shellName = sh
|
||||
Shell = sh
|
||||
Program = getTerminalName()
|
||||
|
||||
switch shellName {
|
||||
log.Debug("Terminal shell: %s", Shell)
|
||||
log.Debug("Terminal program: %s", Program)
|
||||
|
||||
trueColor = Program != AppleTerminal
|
||||
|
||||
switch Shell {
|
||||
case shell.BASH:
|
||||
formats = &shellFormats{
|
||||
escape: "\\[%s\\]",
|
||||
|
@ -203,7 +219,7 @@ func Init(sh string) {
|
|||
}
|
||||
}
|
||||
|
||||
if shellName == shell.ZSH {
|
||||
if Shell == shell.ZSH {
|
||||
formats.escapeSequences = map[rune]rune{
|
||||
96: 92, // backtick
|
||||
37: 37, // %
|
||||
|
@ -211,6 +227,20 @@ func Init(sh string) {
|
|||
}
|
||||
}
|
||||
|
||||
func getTerminalName() string {
|
||||
Program = os.Getenv("TERM_PROGRAM")
|
||||
if len(Program) != 0 {
|
||||
return Program
|
||||
}
|
||||
|
||||
wtSession := os.Getenv("WT_SESSION")
|
||||
if len(wtSession) != 0 {
|
||||
return WindowsTerminal
|
||||
}
|
||||
|
||||
return Unknown
|
||||
}
|
||||
|
||||
func SetColors(background, foreground string) {
|
||||
CurrentColors = &Colors{
|
||||
Background: background,
|
||||
|
@ -281,7 +311,7 @@ func FormatTitle(title string) string {
|
|||
}
|
||||
|
||||
// we have to do this to prevent bash/zsh from misidentifying escape sequences
|
||||
switch shellName {
|
||||
switch Shell {
|
||||
case shell.BASH:
|
||||
title = strings.NewReplacer("`", "\\`", `\`, `\\`).Replace(title)
|
||||
case shell.ZSH:
|
||||
|
@ -339,7 +369,7 @@ func Write(background, foreground, text string) {
|
|||
|
||||
// default to white foreground
|
||||
if foregroundColor.IsEmpty() {
|
||||
foregroundColor = AnsiColors.ToColor("white", false, TrueColor)
|
||||
foregroundColor = AnsiColors.ToColor("white", false)
|
||||
}
|
||||
|
||||
// validate if we start with a color override
|
||||
|
@ -451,7 +481,7 @@ func writeEscapedAnsiString(text string) {
|
|||
}
|
||||
|
||||
func getAnsiFromColorString(colorString string, isBackground bool) Color {
|
||||
return AnsiColors.ToColor(colorString, isBackground, TrueColor)
|
||||
return AnsiColors.ToColor(colorString, isBackground)
|
||||
}
|
||||
|
||||
func write(s rune) {
|
||||
|
|
|
@ -226,7 +226,7 @@ func TestWriteANSIColors(t *testing.T) {
|
|||
CurrentColors = tc.Colors
|
||||
BackgroundColor = tc.TerminalBackground
|
||||
AnsiColors = &DefaultColors{}
|
||||
TrueColor = true
|
||||
trueColor = true
|
||||
|
||||
Write(tc.Colors.Background, tc.Colors.Foreground, tc.Input)
|
||||
|
||||
|
|
Loading…
Reference in a new issue