2023-01-02 13:24:22 -05:00
|
|
|
package windowmanager
|
|
|
|
|
|
|
|
import (
|
|
|
|
tea "github.com/charmbracelet/bubbletea"
|
|
|
|
"github.com/mrusme/gobbs/ui/cmd"
|
2023-01-02 16:45:42 -05:00
|
|
|
"github.com/mrusme/gobbs/ui/ctx"
|
2023-01-02 13:24:22 -05:00
|
|
|
"github.com/mrusme/gobbs/ui/helpers"
|
|
|
|
"github.com/mrusme/gobbs/ui/windows"
|
|
|
|
)
|
|
|
|
|
|
|
|
type StackItem struct {
|
|
|
|
ID string
|
|
|
|
Win windows.Window
|
|
|
|
XYWH [4]int
|
|
|
|
}
|
|
|
|
|
|
|
|
type WM struct {
|
2023-01-02 16:45:42 -05:00
|
|
|
ctx *ctx.Ctx
|
2023-01-02 13:24:22 -05:00
|
|
|
stack []StackItem
|
|
|
|
}
|
|
|
|
|
2023-01-02 16:45:42 -05:00
|
|
|
func New(c *ctx.Ctx) *WM {
|
2023-01-02 13:24:22 -05:00
|
|
|
wm := new(WM)
|
2023-01-02 16:45:42 -05:00
|
|
|
wm.ctx = c
|
2023-01-02 13:24:22 -05:00
|
|
|
|
|
|
|
return wm
|
|
|
|
}
|
|
|
|
|
2023-01-02 15:29:29 -05:00
|
|
|
func (wm *WM) Open(id string, win windows.Window, xywh [4]int, command *cmd.Command) []tea.Cmd {
|
2023-01-02 13:24:22 -05:00
|
|
|
var tcmds []tea.Cmd
|
|
|
|
|
|
|
|
if wm.IsOpen(id) {
|
|
|
|
if wm.IsFocused(id) {
|
|
|
|
return tcmds
|
|
|
|
}
|
|
|
|
return wm.Focus(id)
|
|
|
|
}
|
|
|
|
|
|
|
|
item := new(StackItem)
|
|
|
|
item.ID = id
|
|
|
|
item.Win = win
|
|
|
|
item.XYWH = xywh
|
|
|
|
|
|
|
|
wm.stack = append(wm.stack, *item)
|
|
|
|
|
2023-01-02 19:45:49 -05:00
|
|
|
command.AddArg("xywh", item.XYWH)
|
2023-01-02 16:45:42 -05:00
|
|
|
tcmds = append(tcmds, wm.Update(id, *command))
|
|
|
|
tcmds = append(tcmds, wm.Resize(id, wm.ctx.Content[0], wm.ctx.Content[1])...)
|
2023-01-02 15:29:29 -05:00
|
|
|
// tcmds = append(tcmds, wm.Update(id, *cmd.New(
|
|
|
|
// cmd.WinRefreshData,
|
|
|
|
// id,
|
|
|
|
// )))
|
|
|
|
|
2023-01-02 16:45:42 -05:00
|
|
|
fcmds := wm.Focus(id)
|
|
|
|
tcmds = append(tcmds, fcmds...)
|
2023-01-02 13:24:22 -05:00
|
|
|
|
|
|
|
return tcmds
|
|
|
|
}
|
|
|
|
|
2023-01-02 16:45:42 -05:00
|
|
|
func (wm *WM) CloseFocused() (bool, []tea.Cmd) {
|
2023-01-02 13:24:22 -05:00
|
|
|
return wm.Close(wm.Focused())
|
|
|
|
}
|
|
|
|
|
2023-01-04 21:42:35 -05:00
|
|
|
func (wm *WM) Close(id string, args ...cmd.Arg) (bool, []tea.Cmd) {
|
2023-01-02 16:45:42 -05:00
|
|
|
var tcmds []tea.Cmd
|
2023-01-02 13:24:22 -05:00
|
|
|
for i := len(wm.stack) - 1; i >= 0; i-- {
|
|
|
|
if wm.stack[i].ID == id {
|
|
|
|
wm.stack = append(wm.stack[:i], wm.stack[i+1:]...)
|
2023-01-04 21:42:35 -05:00
|
|
|
tcmds = append(tcmds, cmd.New(cmd.WinClose, id, args...).Tea())
|
2023-01-02 16:45:42 -05:00
|
|
|
wm.ctx.Loading = false
|
|
|
|
|
2023-01-02 18:46:26 -05:00
|
|
|
nrOpen := wm.GetNumberOpen()
|
|
|
|
if nrOpen == 0 {
|
2023-01-02 16:45:42 -05:00
|
|
|
tcmds = append(tcmds, cmd.New(cmd.ViewFocus, "*").Tea())
|
2023-01-02 18:46:26 -05:00
|
|
|
} else {
|
|
|
|
tcmds = append(tcmds, wm.Focus(wm.stack[(nrOpen-1)].ID)...)
|
2023-01-02 16:45:42 -05:00
|
|
|
}
|
|
|
|
return true, tcmds
|
2023-01-02 13:24:22 -05:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2023-01-02 16:45:42 -05:00
|
|
|
return false, tcmds
|
2023-01-02 13:24:22 -05:00
|
|
|
}
|
|
|
|
|
|
|
|
func (wm *WM) Focus(id string) []tea.Cmd {
|
|
|
|
var tcmds []tea.Cmd
|
|
|
|
|
|
|
|
for i := 0; i < len(wm.stack); i++ {
|
|
|
|
var tcmd tea.Cmd
|
|
|
|
if wm.stack[i].ID == id {
|
|
|
|
wm.stack[i].Win, tcmd = wm.stack[i].Win.Update(*cmd.New(cmd.WinFocus, wm.stack[i].ID))
|
|
|
|
} else {
|
|
|
|
wm.stack[i].Win, tcmd = wm.stack[i].Win.Update(*cmd.New(cmd.WinBlur, wm.stack[i].ID))
|
|
|
|
}
|
|
|
|
tcmds = append(tcmds, tcmd)
|
|
|
|
}
|
|
|
|
|
|
|
|
tcmds = append(tcmds, cmd.New(cmd.ViewBlur, "*").Tea())
|
|
|
|
return tcmds
|
|
|
|
}
|
|
|
|
|
|
|
|
func (wm *WM) Focused() string {
|
|
|
|
l := len(wm.stack) - 1
|
|
|
|
if l < 0 {
|
|
|
|
return ""
|
|
|
|
}
|
|
|
|
|
|
|
|
return wm.stack[l].ID
|
|
|
|
}
|
|
|
|
|
|
|
|
func (wm *WM) IsOpen(id string) bool {
|
|
|
|
for _, win := range wm.stack {
|
|
|
|
if win.ID == id {
|
|
|
|
return true
|
|
|
|
}
|
|
|
|
}
|
|
|
|
return false
|
|
|
|
}
|
|
|
|
|
|
|
|
func (wm *WM) IsFocused(id string) bool {
|
|
|
|
return id == wm.Focused()
|
|
|
|
}
|
|
|
|
|
|
|
|
func (wm *WM) GetNumberOpen() int {
|
|
|
|
return len(wm.stack)
|
|
|
|
}
|
|
|
|
|
|
|
|
func (wm *WM) Update(id string, msg tea.Msg) tea.Cmd {
|
|
|
|
var teaCmd tea.Cmd
|
|
|
|
|
|
|
|
for i := 0; i < len(wm.stack); i++ {
|
|
|
|
if wm.stack[i].ID == id {
|
|
|
|
wm.stack[i].Win, teaCmd = wm.stack[i].Win.Update(msg)
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
return teaCmd
|
|
|
|
}
|
|
|
|
|
|
|
|
func (wm *WM) UpdateAll(msg tea.Msg) []tea.Cmd {
|
|
|
|
var tcmd tea.Cmd
|
|
|
|
var tcmds []tea.Cmd
|
|
|
|
|
|
|
|
for i := 0; i < len(wm.stack); i++ {
|
|
|
|
wm.stack[i].Win, tcmd = wm.stack[i].Win.Update(msg)
|
|
|
|
tcmds = append(tcmds, tcmd)
|
|
|
|
}
|
|
|
|
|
|
|
|
return tcmds
|
|
|
|
}
|
|
|
|
|
2023-01-02 18:46:26 -05:00
|
|
|
func (wm *WM) UpdateFocused(msg tea.Msg) []tea.Cmd {
|
|
|
|
var tcmd tea.Cmd
|
|
|
|
var tcmds []tea.Cmd
|
|
|
|
|
|
|
|
i := len(wm.stack) - 1
|
|
|
|
if i < 0 {
|
|
|
|
return tcmds
|
|
|
|
}
|
|
|
|
|
|
|
|
wm.stack[i].Win, tcmd = wm.stack[i].Win.Update(msg)
|
|
|
|
tcmds = append(tcmds, tcmd)
|
|
|
|
|
|
|
|
return tcmds
|
|
|
|
}
|
|
|
|
|
2023-01-02 16:45:42 -05:00
|
|
|
func (wm *WM) Resize(id string, w int, h int) []tea.Cmd {
|
|
|
|
var tcmd tea.Cmd
|
|
|
|
var tcmds []tea.Cmd
|
|
|
|
|
|
|
|
for i := 0; i < len(wm.stack); i++ {
|
|
|
|
if wm.stack[i].ID == id {
|
|
|
|
wm.stack[i].Win, tcmd = wm.stack[i].Win.Update(tea.WindowSizeMsg{
|
2023-01-02 17:43:12 -05:00
|
|
|
Width: w - wm.stack[i].XYWH[0] - wm.stack[i].XYWH[2],
|
|
|
|
Height: h - wm.stack[i].XYWH[1] - wm.stack[i].XYWH[3],
|
2023-01-02 16:45:42 -05:00
|
|
|
})
|
|
|
|
tcmds = append(tcmds, tcmd)
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
return tcmds
|
|
|
|
}
|
|
|
|
|
|
|
|
func (wm *WM) ResizeAll(w int, h int) []tea.Cmd {
|
|
|
|
var tcmd tea.Cmd
|
|
|
|
var tcmds []tea.Cmd
|
|
|
|
|
|
|
|
for i := 0; i < len(wm.stack); i++ {
|
|
|
|
wm.stack[i].Win, tcmd = wm.stack[i].Win.Update(tea.WindowSizeMsg{
|
2023-01-02 17:43:12 -05:00
|
|
|
Width: w - wm.stack[i].XYWH[0] - wm.stack[i].XYWH[2],
|
|
|
|
Height: h - wm.stack[i].XYWH[1] - wm.stack[i].XYWH[3],
|
2023-01-02 16:45:42 -05:00
|
|
|
})
|
|
|
|
tcmds = append(tcmds, tcmd)
|
|
|
|
}
|
|
|
|
|
|
|
|
return tcmds
|
|
|
|
}
|
|
|
|
|
2023-01-02 19:27:23 -05:00
|
|
|
func (wm *WM) View(view string, onlyFocused bool) string {
|
2023-01-02 13:24:22 -05:00
|
|
|
var v string = view
|
2023-01-02 19:27:23 -05:00
|
|
|
var j int = 0
|
2023-01-02 13:24:22 -05:00
|
|
|
|
2023-01-02 19:27:23 -05:00
|
|
|
if onlyFocused {
|
|
|
|
j = len(wm.stack) - 1
|
|
|
|
if j < 0 {
|
|
|
|
j = 0
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
for i := j; i < len(wm.stack); i++ {
|
2023-01-02 17:43:12 -05:00
|
|
|
v = helpers.PlaceOverlay(
|
|
|
|
wm.stack[i].XYWH[0],
|
|
|
|
wm.stack[i].XYWH[1]+(wm.ctx.Screen[1]-wm.ctx.Content[1]),
|
2023-01-02 13:24:22 -05:00
|
|
|
wm.stack[i].Win.View(),
|
2023-01-02 17:43:12 -05:00
|
|
|
v,
|
|
|
|
true,
|
|
|
|
)
|
2023-01-02 13:24:22 -05:00
|
|
|
}
|
|
|
|
|
|
|
|
return v
|
|
|
|
}
|