perf!: move from polling to event-driven model

BREAKING CHANGE: requires wl-clipboard >= 2.0

Closes #1.
This commit is contained in:
yory8 2019-09-10 16:20:27 +02:00
parent 3d62f25c7a
commit b46a2c3907
2 changed files with 51 additions and 47 deletions

View file

@ -7,7 +7,7 @@ A basic clipboard manager for Wayland, with support for persisting copy buffers
Requirements: Requirements:
- a windows manager that uses `wlr-data-control`, like Sway and other wlroots-based WMs. - a windows manager that uses `wlr-data-control`, like Sway and other wlroots-based WMs.
- wl-clipboard from latest master (NOT v1.0) - wl-clipboard >= 2.0
- dmenu or rofi - dmenu or rofi
[Install go](https://golang.org/doc/install), add `$GOPATH/bin` to your path, then run `go get github.com/yory8/clipman` OR run `go install` inside this folder. [Install go](https://golang.org/doc/install), add `$GOPATH/bin` to your path, then run `go get github.com/yory8/clipman` OR run `go install` inside this folder.

View file

@ -4,10 +4,22 @@ import (
"encoding/json" "encoding/json"
"io/ioutil" "io/ioutil"
"log" "log"
"os"
"os/exec" "os/exec"
"time"
) )
type historyBuf struct {
buf []string // field name as required by io.Writer, don't change
histfile string
max int
persist bool
}
func (hb *historyBuf) Write(p []byte) (n int, err error) {
hb.buf = store(string(p), hb.buf, hb.histfile, hb.max, hb.persist)
return len(p), err // signature as required by io.Writer, don't change
}
func write(history []string, histfile string) error { func write(history []string, histfile string) error {
histlog, err := json.Marshal(history) histlog, err := json.Marshal(history)
if err != nil { if err != nil {
@ -41,34 +53,11 @@ func filter(history []string, text string) []string {
return history return history
} }
func listen(history []string, histfile string, persist bool, max int) { func store(text string, history []string, histfile string, max int, persist bool) []string {
for {
t, err := exec.Command("wl-paste", "-n", "-t", "text").CombinedOutput()
if err != nil {
// wl-paste exits 1 if there's no selection (e.g., when running it at OS startup)
if string(t) != "No selection\n" {
log.Printf("Error running wl-paste: %s", t)
}
time.Sleep(1 * time.Second)
continue
}
text := string(t)
if text == "" {
// there's nothing to select, so we sleep.
time.Sleep(1 * time.Second)
continue
}
l := len(history) l := len(history)
if l > 0 { if l > 0 {
// wl-paste will always give back the last copied text
// (as long as the place we copied from is still running)
if history[l-1] == text { if history[l-1] == text {
time.Sleep(1 * time.Second) return history
continue
} }
if l >= max { if l >= max {
@ -94,5 +83,20 @@ func listen(history []string, histfile string, persist bool, max int) {
log.Printf("Error running wl-copy: %s", err) log.Printf("Error running wl-copy: %s", err)
} }
} }
return history
}
func listen(history []string, histfile string, persist bool, max int) {
cmd := exec.Command("wl-paste", "-t", "text", "--watch", "cat")
cmd.Stdout = &historyBuf{history, histfile, max, persist}
cmd.Stderr = os.Stderr
if err := cmd.Start(); err != nil {
log.Fatalf("Error running wl-paste (cmd.Start): %s", err)
}
if err := cmd.Wait(); err != nil {
log.Fatalf("Error running wl-paste (cmd.Wait): %s", err)
} }
} }