package x import "image" import "github.com/jezek/xgbutil" // import "github.com/jezek/xgbutil/ewmh" import "github.com/jezek/xgbutil/xevent" import "github.com/jezek/xgbutil/xwindow" import "github.com/jezek/xgbutil/xgraphics" import "git.tebibyte.media/sashakoshka/stone" type Backend struct { application *stone.Application config *stone.Config connection *xgbutil.XUtil window *xwindow.Window canvas *xgraphics.Image channel chan(stone.Event) ping struct { before chan(struct { }) after chan(struct { }) quit chan(struct { }) } metrics struct { cellWidth int cellHeight int padding int paddingX int paddingY int descent int } } func (backend *Backend) Run (channel chan(stone.Event)) { backend.channel = channel for { select { case <- backend.ping.before: <- backend.ping.after case <- backend.ping.quit: backend.shutDown() return } } } func (backend *Backend) SetTitle (title string) { } func (backend *Backend) SetIcon (icons []image.Image) { } func (backend *Backend) shutDown () { backend.channel <- stone.EventQuit { } } // calculateWindowSize calculates window bounds based on the internal buffer // size. func (backend *Backend) calculateWindowSize () (x, y int) { width, height := backend.application.Size() x = width * backend.metrics.cellWidth + backend.metrics.padding * 2 y = height * backend.metrics.cellHeight + backend.metrics.padding * 2 return } // factory instantiates an X backend. func factory (application *stone.Application) (output stone.Backend, err error) { backend := &Backend { application: application, config: application.Config(), } // calculate metrics // TODO: base these off of font metrics backend.metrics.cellWidth = 8 backend.metrics.cellHeight = 16 backend.metrics.padding = backend.config.Padding() * backend.metrics.cellHeight backend.metrics.paddingX = backend.metrics.padding backend.metrics.paddingY = backend.metrics.padding // connect to X backend.connection, err = xgbutil.NewConn() if err != nil { return } backend.window, err = xwindow.Generate(backend.connection) if err != nil { return } // create the window windowWidth, windowHeight := backend.calculateWindowSize() backend.window.Create ( backend.connection.RootWin(), 0, 0, windowWidth, windowHeight, 0) backend.window.Map() // attatch graceful close handler backend.window.WMGracefulClose (func (window *xwindow.Window) { backend.window.Destroy() backend.shutDown() }) // start event loop backend.ping.before, backend.ping.after, backend.ping.quit = xevent.MainPing(backend.connection) output = backend return } // init registers this backend when the program starts. func init () { stone.RegisterBackend(factory) }