init: pristine aerc 0.20.0 source
This commit is contained in:
+165
@@ -0,0 +1,165 @@
|
||||
package app
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"sync"
|
||||
"time"
|
||||
|
||||
"github.com/mattn/go-runewidth"
|
||||
|
||||
"git.sr.ht/~rjarry/aerc/config"
|
||||
"git.sr.ht/~rjarry/aerc/lib/log"
|
||||
"git.sr.ht/~rjarry/aerc/lib/state"
|
||||
"git.sr.ht/~rjarry/aerc/lib/templates"
|
||||
"git.sr.ht/~rjarry/aerc/lib/ui"
|
||||
"git.sr.ht/~rockorager/vaxis"
|
||||
)
|
||||
|
||||
type StatusLine struct {
|
||||
sync.Mutex
|
||||
stack []*StatusMessage
|
||||
acct *AccountView
|
||||
err string
|
||||
}
|
||||
|
||||
type StatusMessage struct {
|
||||
style vaxis.Style
|
||||
message string
|
||||
}
|
||||
|
||||
func (status *StatusLine) Invalidate() {
|
||||
ui.Invalidate()
|
||||
}
|
||||
|
||||
func (status *StatusLine) Draw(ctx *ui.Context) {
|
||||
status.Lock()
|
||||
defer status.Unlock()
|
||||
style := status.uiConfig().GetStyle(config.STYLE_STATUSLINE_DEFAULT)
|
||||
ctx.Fill(0, 0, ctx.Width(), ctx.Height(), ' ', style)
|
||||
switch {
|
||||
case len(status.stack) != 0:
|
||||
line := status.stack[len(status.stack)-1]
|
||||
msg := runewidth.Truncate(line.message, ctx.Width(), "")
|
||||
msg = runewidth.FillRight(msg, ctx.Width())
|
||||
ctx.Printf(0, 0, line.style, "%s", msg)
|
||||
case status.err != "":
|
||||
msg := runewidth.Truncate(status.err, ctx.Width(), "")
|
||||
msg = runewidth.FillRight(msg, ctx.Width())
|
||||
style := status.uiConfig().GetStyle(config.STYLE_STATUSLINE_ERROR)
|
||||
ctx.Printf(0, 0, style, "%s", msg)
|
||||
case status.acct != nil:
|
||||
data := state.NewDataSetter()
|
||||
data.SetPendingKeys(aerc.pendingKeys)
|
||||
data.SetState(&status.acct.state)
|
||||
data.SetAccount(status.acct.acct)
|
||||
data.SetFolder(status.acct.Directories().SelectedDirectory())
|
||||
msg, _ := status.acct.SelectedMessage()
|
||||
data.SetInfo(msg, 0, false)
|
||||
data.SetRUE(status.acct.dirlist.List(), status.acct.dirlist.GetRUECount)
|
||||
if store := status.acct.Store(); store != nil {
|
||||
data.SetVisual(store.Marker().IsVisualMark())
|
||||
}
|
||||
table := ui.NewTable(
|
||||
ctx.Height(),
|
||||
config.Statusline.StatusColumns,
|
||||
config.Statusline.ColumnSeparator,
|
||||
nil,
|
||||
func(*ui.Table, int) vaxis.Style { return style },
|
||||
)
|
||||
var buf bytes.Buffer
|
||||
cells := make([]string, len(table.Columns))
|
||||
for c, col := range table.Columns {
|
||||
err := templates.Render(col.Def.Template, &buf,
|
||||
data.Data())
|
||||
if err != nil {
|
||||
log.Errorf("%s", err)
|
||||
cells[c] = err.Error()
|
||||
} else {
|
||||
cells[c] = buf.String()
|
||||
}
|
||||
buf.Reset()
|
||||
}
|
||||
table.AddRow(cells, nil)
|
||||
table.Draw(ctx)
|
||||
}
|
||||
}
|
||||
|
||||
func (status *StatusLine) Update(acct *AccountView) {
|
||||
status.acct = acct
|
||||
status.Invalidate()
|
||||
}
|
||||
|
||||
func (status *StatusLine) SetError(err string) {
|
||||
prev := status.err
|
||||
status.err = err
|
||||
if prev != status.err {
|
||||
status.Invalidate()
|
||||
}
|
||||
}
|
||||
|
||||
func (status *StatusLine) Clear() {
|
||||
status.SetError("")
|
||||
status.acct = nil
|
||||
}
|
||||
|
||||
func (status *StatusLine) Push(text string, expiry time.Duration) *StatusMessage {
|
||||
status.Lock()
|
||||
defer status.Unlock()
|
||||
log.Debugf(text)
|
||||
msg := &StatusMessage{
|
||||
style: status.uiConfig().GetStyle(config.STYLE_STATUSLINE_DEFAULT),
|
||||
message: text,
|
||||
}
|
||||
status.stack = append(status.stack, msg)
|
||||
go (func() {
|
||||
defer log.PanicHandler()
|
||||
|
||||
time.Sleep(expiry)
|
||||
status.Lock()
|
||||
defer status.Unlock()
|
||||
for i, m := range status.stack {
|
||||
if m == msg {
|
||||
status.stack = append(status.stack[:i], status.stack[i+1:]...)
|
||||
break
|
||||
}
|
||||
}
|
||||
status.Invalidate()
|
||||
})()
|
||||
status.Invalidate()
|
||||
return msg
|
||||
}
|
||||
|
||||
func (status *StatusLine) PushError(text string) *StatusMessage {
|
||||
log.Errorf(text)
|
||||
msg := status.Push(text, 10*time.Second)
|
||||
msg.Color(status.uiConfig().GetStyle(config.STYLE_STATUSLINE_ERROR))
|
||||
return msg
|
||||
}
|
||||
|
||||
func (status *StatusLine) PushWarning(text string) *StatusMessage {
|
||||
log.Warnf(text)
|
||||
msg := status.Push(text, 10*time.Second)
|
||||
msg.Color(status.uiConfig().GetStyle(config.STYLE_STATUSLINE_WARNING))
|
||||
return msg
|
||||
}
|
||||
|
||||
func (status *StatusLine) PushSuccess(text string) *StatusMessage {
|
||||
log.Tracef(text)
|
||||
msg := status.Push(text, 10*time.Second)
|
||||
msg.Color(status.uiConfig().GetStyle(config.STYLE_STATUSLINE_SUCCESS))
|
||||
return msg
|
||||
}
|
||||
|
||||
func (status *StatusLine) Expire() {
|
||||
status.Lock()
|
||||
defer status.Unlock()
|
||||
status.stack = nil
|
||||
}
|
||||
|
||||
func (status *StatusLine) uiConfig() *config.UIConfig {
|
||||
return SelectedAccountUiConfig()
|
||||
}
|
||||
|
||||
func (msg *StatusMessage) Color(style vaxis.Style) {
|
||||
msg.style = style
|
||||
}
|
||||
Reference in New Issue
Block a user