From ffe832aa76770c528abdea66dd49945bfb8812da Mon Sep 17 00:00:00 2001 From: Rasmus Lindroth Date: Sun, 28 Jun 2020 15:11:06 +0200 Subject: [PATCH] Add xrdb support --- README.md | 18 ++++++- config.example.ini | 127 +++++++++++++++++++++++++++++++++++++++++++++ config.go | 113 +++++++++++++++++++++++++++------------- main.go | 39 +++++++++++++- ui.go | 12 +++-- xrdb.go | 83 +++++++++++++++++++++++++++++ 6 files changed, 348 insertions(+), 44 deletions(-) create mode 100644 config.example.ini create mode 100644 xrdb.go diff --git a/README.md b/README.md index 0857c8d..2957d4d 100644 --- a/README.md +++ b/README.md @@ -22,6 +22,13 @@ You can find Linux binaries under [releases](https://github.com/RasmusLindroth/t * `:user` followed by a username e.g. `:user rasmus` to narrow a search include the instance like this `:user rasmus@mastodon.acc.sunet.se`. +Keys without description in tut +* `c` = Compose a new toot +* `hjkl` = navigation +* `arrow keys` = navigation +* `q` = go back and quit +* `ESC` = go back + Explanation of the non obvious keys when viewing a toot * `V` = view. In this mode you can scroll throught the text of the toot if it doesn't fit the screen * `O` = open. Gives you a list of all URLs in the toot. Opens them in your default browser, if it's @@ -35,8 +42,11 @@ all the options. You find it in `XDG_CONFIG_HOME/tut/config.ini` which usally equals to `~/.config/tut/config.ini`. +You can find an updated configuration file in this repo named `config.example.ini`. +If there are any new configurations options you can copy them frome that file. + ## Install instructions -### Using Arch? +### Using Arch or Manjaro? You can find it in the Arch User Repository (AUR). @@ -47,6 +57,10 @@ If you don't use the binary that you find under releases you will need Go. Use a newer one that supports modules. ```bash +# Fetches and installs tut. Usally /home/user/go/bin +go get -u github.com/RasmusLindroth/tut + +# You can also clone the repo if you like # First clone this repository git clone https://github.com/RasmusLindroth/tut.git @@ -58,7 +72,7 @@ cd tut # Install (usally /home/user/go/bin) go install -#Build (same directory i.e. ./ ) +# Build (same directory i.e. ./ ) go build ``` diff --git a/config.example.ini b/config.example.ini new file mode 100644 index 0000000..fb21ad4 --- /dev/null +++ b/config.example.ini @@ -0,0 +1,127 @@ +# +# Configuration file for tut + +[general] +# If the program should check for new toots without user interaction. +# If you don't enable this the program will only look for new toots when +# you reach the bottom or top of your feed. With this enabled it will check +# for new toots every x second. +# default=true +auto-load-newer=true + +# How many seconds between each pulling of new toots if you have enabled +# auto-load-newer. +# default=60 +auto-load-seconds=60 + + +# The date format to be used +# See https://godoc.org/time#Time.Format +# default=2006-01-02 15:04 +date-format=2006-01-02 15:04 + +# Format for dates the same day +# default=15:04 +date-today-format=15:04 + +# The timeline that opens up when you start tut +# Valid values: home, direct, local, federated +# default=home +timeline=home + +[media] +# Your image viewer +# default=xdg-open +image-viewer=xdg-open + +# If image should open one by one e.g. "imv image.png" multiple times +# If set to false all images will open at the same time like this +# "imv image1.png image2.png image3.png". +# Not all image viewers support this, so try it first. +# default=true +image-single=true + +# Your video viewer +# default=xdg-open +video-viewer=xdg-open + +# If videos should open one by one. See above comment about image-single +# default=true +video-single=true + +# Your audio viewer +# default=xdg-open +audio-viewer=xdg-open + +# If audio files should open one by one. See above comment about image-single +# default=true +audio-single=true + +# Your web browser +# default=xdg-open +link-viewer=xdg-open + +[style] +# All styles can be represented in their HEX value like #ffffff or +# with their name, so in this case white. +# The only special value is "default" which equals to transparent, +# so it will be the same color as your terminal. But this can lead +# to some artifacts left from a previous paint + +# You can also use xrdb colors like this xrdb:color1 +# The program will use colors prefixed with an * first then look +# for URxvt or XTerm if it can't find any color prefixed with an asterix. +# If you don't want tut to guess the prefix you can set the prefix yourself. +# If the xrdb color can't be found a preset color will be used. + +# The xrdb prefix used for colors in .Xresources +# default=guess +xrdb-prefix=guess + +# The background color used on most elements +# default=xrdb:background +background=xrdb:background + +# The text color used on most of the text +# default=xrdb:foreground +text=xrdb:foreground + +# The color to display sublte elements or subtle text. Like lines and help text +# default=xrdb:color14 +subtle=xrdb:color14 + +# The color for errors or warnings +# default=xrdb:color1 +warning-text=xrdb:color1 + +# This color is used to display username +# default=xrdb:color5 +text-special-one=xrdb:color5 + +# This color is used to display username and keys +# default=xrdb:color2 +text-special-two=xrdb:color2 + +# The color of the bar at the top +# default=xrdb:color5 +top-bar-background=xrdb:color5 + +# The color of the text in the bar at the top +# default=xrdb:background +top-bar-text=xrdb:background + +# The color of the bar at the bottom +# default=xrdb:color0 +status-bar-background=xrdb:color0 + +# The color of the text in the bar at the bottom +# default=xrdb:foreground +status-bar-text=xrdb:foreground + +# Background of selected list items +# default=xrdb:color5 +list-selected-background=xrdb:color5 + +# The text color of selected list items +# default=xrdb:background +list-selected-text=xrdb:background diff --git a/config.go b/config.go index c40bb6f..a20ea09 100644 --- a/config.go +++ b/config.go @@ -57,52 +57,81 @@ type MediaConfig struct { LinkArgs []string } -func parseColor(input string, def string) tcell.Color { +func parseColor(input string, def string, xrdb map[string]string) tcell.Color { if input == "" { return tcell.GetColor(def) } + + if strings.HasPrefix(input, "xrdb:") { + key := strings.TrimPrefix(input, "xrdb:") + if c, ok := xrdb[key]; ok { + return tcell.GetColor(c) + } else { + return tcell.GetColor(def) + } + } return tcell.GetColor(input) } func parseStyle(cfg *ini.File) StyleConfig { + var xrdbColors map[string]string + xrdbMap, _ := GetXrdbColors() + prefix := cfg.Section("style").Key("xrdb-prefix").String() + if prefix == "" { + prefix = "guess" + } + + if prefix == "guess" { + if m, ok := xrdbMap["*"]; ok { + xrdbColors = m + } else if m, ok := xrdbMap["URxvt"]; ok { + xrdbColors = m + } else if m, ok := xrdbMap["XTerm"]; ok { + xrdbColors = m + } + } else { + if m, ok := xrdbMap[prefix]; ok { + xrdbColors = m + } + } style := StyleConfig{} bg := cfg.Section("style").Key("background").String() - style.Background = parseColor(bg, "default") + style.Background = parseColor(bg, "default", xrdbColors) text := cfg.Section("style").Key("text").String() - style.Text = parseColor(text, "white") + style.Text = parseColor(text, "white", xrdbColors) subtle := cfg.Section("style").Key("subtle").String() - style.Subtle = parseColor(subtle, "gray") + style.Subtle = parseColor(subtle, "gray", xrdbColors) warningText := cfg.Section("style").Key("warning-text").String() - style.WarningText = parseColor(warningText, "#f92672") + style.WarningText = parseColor(warningText, "#f92672", xrdbColors) textSpecial1 := cfg.Section("style").Key("text-special-one").String() - style.TextSpecial1 = parseColor(textSpecial1, "#ae81ff") + style.TextSpecial1 = parseColor(textSpecial1, "#ae81ff", xrdbColors) textSpecial2 := cfg.Section("style").Key("text-special-two").String() - style.TextSpecial2 = parseColor(textSpecial2, "#a6e22e") + style.TextSpecial2 = parseColor(textSpecial2, "#a6e22e", xrdbColors) topBarBackround := cfg.Section("style").Key("top-bar-background").String() - style.TopBarBackground = parseColor(topBarBackround, "#f92672") + style.TopBarBackground = parseColor(topBarBackround, "#f92672", xrdbColors) topBarText := cfg.Section("style").Key("top-bar-text").String() - style.TopBarText = parseColor(topBarText, "white") + style.TopBarText = parseColor(topBarText, "white", xrdbColors) statusBarBackround := cfg.Section("style").Key("status-bar-background").String() - style.StatusBarBackground = parseColor(statusBarBackround, "#f92672") + style.StatusBarBackground = parseColor(statusBarBackround, "#f92672", xrdbColors) statusBarText := cfg.Section("style").Key("status-bar-text").String() - style.StatusBarText = parseColor(statusBarText, "white") + style.StatusBarText = parseColor(statusBarText, "white", xrdbColors) listSelectedBackground := cfg.Section("style").Key("list-selected-background").String() - style.ListSelectedBackground = parseColor(listSelectedBackground, "#f92672") + style.ListSelectedBackground = parseColor(listSelectedBackground, "#f92672", xrdbColors) listSelectedText := cfg.Section("style").Key("list-selected-text").String() - style.ListSelectedText = parseColor(listSelectedText, "white") + style.ListSelectedText = parseColor(listSelectedText, "white", xrdbColors) return style } @@ -289,53 +318,63 @@ link-viewer=xdg-open # so it will be the same color as your terminal. But this can lead # to some artifacts left from a previous paint +# You can also use xrdb colors like this xrdb:color1 +# The program will use colors prefixed with an * first then look +# for URxvt or XTerm if it can't find any color prefixed with an asterix. +# If you don't want tut to guess the prefix you can set the prefix yourself. +# If the xrdb color can't be found a preset color will be used. + +# The xrdb prefix used for colors in .Xresources +# default=guess +xrdb-prefix=guess + # The background color used on most elements -# default=default -background=default +# default=xrdb:background +background=xrdb:background # The text color used on most of the text -# default=white -text=white +# default=xrdb:foreground +text=xrdb:foreground # The color to display sublte elements or subtle text. Like lines and help text -# default=gray -subtle=gray +# default=xrdb:color14 +subtle=xrdb:color14 # The color for errors or warnings -# default=#f92672 -warning-text=#f92672 +# default=xrdb:color1 +warning-text=xrdb:color1 # This color is used to display username -# default=#ae81ff -text-special-one=#ae81ff +# default=xrdb:color5 +text-special-one=xrdb:color5 # This color is used to display username and keys -# default=#a6e22e -text-special-two=#a6e22e +# default=xrdb:color2 +text-special-two=xrdb:color2 # The color of the bar at the top -# default=#f92672 -top-bar-background=#f92672 +# default=xrdb:color5 +top-bar-background=xrdb:color5 # The color of the text in the bar at the top -# default=white -top-bar-text=white +# default=xrdb:background +top-bar-text=xrdb:background # The color of the bar at the bottom -# default=#f92672 -status-bar-background=#f92672 +# default=xrdb:color0 +status-bar-background=xrdb:color0 # The color of the text in the bar at the bottom -# default=white -status-bar-text=white +# default=xrdb:foreground +status-bar-text=xrdb:foreground # Background of selected list items -# default=#f92672 -list-selected-background=#f92672 +# default=xrdb:color5 +list-selected-background=xrdb:color5 # The text color of selected list items -# default=white -list-selected-text=white +# default=xrdb:background +list-selected-text=xrdb:background ` f, err := os.Create(filepath) defer f.Close() diff --git a/main.go b/main.go index 23a6983..effbccc 100644 --- a/main.go +++ b/main.go @@ -4,13 +4,50 @@ import ( "context" "fmt" "log" - "strings" "os" + "strings" "github.com/gdamore/tcell" ) +const version string = "0.0.10" + func main() { + + if len(os.Args) > 1 { + switch os.Args[1] { + case "example-config": + CreateDefaultConfig("./config.example.ini") + os.Exit(0) + case "--help": + case "-h": + fmt.Print("tut - a TUI for Mastodon with vim inspired keys.\n\n") + fmt.Print("Usage:\n\n") + fmt.Print("\tTo run the program you just have to write tut\n\n") + + fmt.Print("Commands:\n\n") + fmt.Print("\texample-config - creates the default configuration file in the current directory and names it ./config.example.ini\n\n") + + fmt.Print("Flags:\n\n") + fmt.Print("\t--help -h - prints this message\n") + fmt.Print("\t--version -v - prints the version\n\n") + + fmt.Print("Configuration:\n\n") + fmt.Printf("\tThe config is located in XDG_CONFIG_HOME/tut/config.ini which usally equals to ~/.config/tut/config.ini.\n") + fmt.Printf("\tThe program will generate the file the first time you run tut. The file has comments which exmplains what each configuration option does.\n\n") + + fmt.Print("Contact info for issues or questions:\n\n") + fmt.Printf("\t@rasmus@mastodon.acc.sunet.se\n\trasmus@lindroth.xyz\n") + fmt.Printf("\thttps://github.com/RasmusLindroth/tut\n") + os.Exit(0) + case "--version": + case "-v": + fmt.Printf("tut version %s\n\n", version) + fmt.Printf("https://github.com/RasmusLindroth/tut\n") + os.Exit(0) + } + } + err := CreateConfigDir() if err != nil { log.Fatalln( diff --git a/ui.go b/ui.go index 9d4ee48..29ab43c 100644 --- a/ui.go +++ b/ui.go @@ -44,10 +44,12 @@ func (ui *UI) Init() { ui.Pages.SetBackgroundColor(ui.app.Config.Style.Background) - verticalLine := tview.NewBox().SetBackgroundColor(ui.app.Config.Style.Background) + verticalLine := tview.NewBox() verticalLine.SetDrawFunc(func(screen tcell.Screen, x int, y int, width int, height int) (int, int, int, int) { + var s tcell.Style + s = s.Background(ui.app.Config.Style.Background).Foreground(ui.app.Config.Style.Subtle) for cy := y; cy < y+height; cy++ { - screen.SetContent(x, cy, tview.BoxDrawingsLightVertical, nil, tcell.StyleDefault.Foreground(ui.app.Config.Style.Subtle)) + screen.SetContent(x, cy, tview.BoxDrawingsLightVertical, nil, s) } return 0, 0, 0, 0 }) @@ -235,10 +237,12 @@ func (ui *UI) SetTopText(s string) { func (ui *UI) LoggedIn() { ui.StatusView = NewStatusView(ui.app, ui.Timeline) - verticalLine := tview.NewBox().SetBackgroundColor(ui.app.Config.Style.Background) + verticalLine := tview.NewBox() verticalLine.SetDrawFunc(func(screen tcell.Screen, x int, y int, width int, height int) (int, int, int, int) { + var s tcell.Style + s = s.Background(ui.app.Config.Style.Background).Foreground(ui.app.Config.Style.Subtle) for cy := y; cy < y+height; cy++ { - screen.SetContent(x, cy, tview.BoxDrawingsLightVertical, nil, tcell.StyleDefault.Foreground(ui.app.Config.Style.Subtle)) + screen.SetContent(x, cy, tview.BoxDrawingsLightVertical, nil, s) } return 0, 0, 0, 0 }) diff --git a/xrdb.go b/xrdb.go new file mode 100644 index 0000000..7a99f95 --- /dev/null +++ b/xrdb.go @@ -0,0 +1,83 @@ +package main + +import ( + "os/exec" + "strconv" + "strings" +) + +type xrdbField struct { + Name string + Value string +} + +type XrdbColors map[string]map[string]string + +func getXrdb() ([]xrdbField, error) { + var xf []xrdbField + + out, err := exec.Command("xrdb", "-query").CombinedOutput() + if err != nil { + return xf, err + } + + lines := strings.Split(string(out), "\n") + for _, line := range lines { + parts := strings.Split(line, ":") + if len(parts) < 2 { + continue + } + + xf = append(xf, + xrdbField{ + Name: strings.TrimSpace(parts[0]), + Value: strings.TrimSpace( + strings.Join(parts[1:], ":"), + ), + }, + ) + } + + return xf, nil +} + +func GetXrdbColors() (XrdbColors, error) { + colors := make(XrdbColors) + + xf, err := getXrdb() + if err != nil { + return colors, err + } + + for _, field := range xf { + parts := strings.Split(field.Name, ".") + if len(parts) == 1 && strings.HasPrefix(parts[0], "*") { + parts = append(parts, parts[0][1:]) + parts[0] = "*" + } + if len(parts) != 2 { + continue + } + + c := parts[1] + if c != "background" && c != "foreground" && !strings.HasPrefix(c, "color") { + continue + } + + if strings.HasPrefix(c, "color") { + num := strings.TrimPrefix(c, "color") + i, err := strconv.Atoi(num) + + if err != nil || i < 0 || i > 15 { + continue + } + } + + if _, ok := colors[parts[0]]; !ok { + colors[parts[0]] = make(map[string]string) + } + colors[parts[0]][c] = field.Value + } + + return colors, nil +}