From 1e1367ce709feca3aa20d0154a997009048476c9 Mon Sep 17 00:00:00 2001 From: Sasha Koshka Date: Wed, 7 Jun 2023 00:54:57 -0400 Subject: [PATCH] Added paste example --- examples/paste/main.go | 74 ++++++++++++++++++++++++++++++++++++++++++ selection.go | 4 +-- 2 files changed, 75 insertions(+), 3 deletions(-) create mode 100644 examples/paste/main.go diff --git a/examples/paste/main.go b/examples/paste/main.go new file mode 100644 index 0000000..d88cc09 --- /dev/null +++ b/examples/paste/main.go @@ -0,0 +1,74 @@ +// Example paste shows how to read text data from the CLIPBOARD selection. +package main + +import "os" +import "io" +import "log" +import "github.com/jezek/xgbutil" +import "github.com/jezek/xgb/xproto" +import "github.com/jezek/xgbutil/xprop" +import "github.com/jezek/xgbutil/xevent" +import "github.com/jezek/xgbutil/xwindow" +import "git.tebibyte.media/sashakoshka/xgbsel" + +type requestor struct { + window *xwindow.Window +} + +func (requestor requestor) Window () *xwindow.Window { + return requestor.window +} + +func (requestor requestor) Success (target xgbsel.Target, data io.ReadCloser) { + defer data.Close() + text, _ := io.ReadAll(data) + log.Println("Clipboard text:", string(text)) + os.Exit(0) +} + +func (requestor requestor) Failure (err error) { + log.Fatalln("could not get clipboard:", err) + os.Exit(1) +} + +func (requestor requestor) Choose (from []xgbsel.Target) (xgbsel.Target, bool) { + for _, target := range from { + if target == "TEXT" { + return target, true + } + } + + return "", false +} + +func main () { + X, err := xgbutil.NewConn() + if err != nil { + log.Fatal(err) + } + + // create window + window, err := xwindow.Generate(X) + if err != nil { + log.Fatalln("could not generate a new window X id:", err) + } + window.Create(X.RootWin(), 0, 0, 500, 500, xproto.CwBackPixel, 0xffffffff) + + // get the atom for the clipboard, and the name of the property we want + // to recieve the selection contents on (which can be anything) + log.Println("creating request") + clipboard, _ := xprop.Atm(X, "CLIPBOARD") + property, _ := xprop.Atm(X, "DESTINATION") + request := xgbsel.NewRequest ( + requestor { window: window }, + clipboard, + property) + + // listen for events + window.Listen(xproto.EventMaskPropertyChange) + xevent.PropertyNotifyFun(request.HandlePropertyNotify).Connect(X, window.Id) + xevent.SelectionNotifyFun(request.HandleSelectionNotify).Connect(X, window.Id) + + log.Println("running main event loop") + xevent.Main(X) +} diff --git a/selection.go b/selection.go index f51d863..8c507e5 100644 --- a/selection.go +++ b/selection.go @@ -84,9 +84,7 @@ func (request *Request) convertSelection (target xproto.Atom, switchTo selReqSta request.destination, // TODO: *possibly replace this zero with an actual timestamp // received from the server. this is non-trivial as we cannot - // rely on the timestamp of the last received event, because - // there is a possibility that this method is invoked - // asynchronously from within tomo.Do(). + // rely on the timestamp of the last received event. 0).Check() if err != nil { request.die(err); return }