init
This commit is contained in:
91
internal/tui/view.go
Normal file
91
internal/tui/view.go
Normal file
@@ -0,0 +1,91 @@
|
||||
package tui
|
||||
|
||||
import (
|
||||
"filepass/internal/styles"
|
||||
|
||||
tea "charm.land/bubbletea/v2"
|
||||
lipgloss "charm.land/lipgloss/v2"
|
||||
)
|
||||
|
||||
func footerHint(key, desc string) string {
|
||||
return styles.FooterKeyStyle.Render(key) +
|
||||
" " +
|
||||
styles.FooterDescStyle.Render(desc)
|
||||
}
|
||||
|
||||
func footerSep() string {
|
||||
return styles.FooterSepStyle.Render(" · ")
|
||||
}
|
||||
|
||||
func (m TUIInterface) View() tea.View {
|
||||
if m.Quitting {
|
||||
return tea.NewView("")
|
||||
}
|
||||
|
||||
w := m.WindowWidth
|
||||
h := m.WindowHeight
|
||||
if w == 0 {
|
||||
w = 80
|
||||
}
|
||||
if h == 0 {
|
||||
h = 24
|
||||
}
|
||||
|
||||
// menu rows
|
||||
var menuRows []string
|
||||
for i, item := range m.MenuItems {
|
||||
menuRows = append(menuRows, styles.MenuItemStyle(i == m.Selected).Render(item.Label))
|
||||
}
|
||||
menu := lipgloss.JoinVertical(lipgloss.Left, menuRows...)
|
||||
|
||||
// status line — error takes priority over no-servers hint
|
||||
var statusLine string
|
||||
switch {
|
||||
case m.InitErr != nil:
|
||||
statusLine = styles.StatusErrStyle.Render("✗ " + m.InitErr.Error())
|
||||
case m.NoServers:
|
||||
statusLine = styles.StatusWarnStyle.Render("⚠ No servers configured. Select Config to add one.")
|
||||
}
|
||||
|
||||
// top content
|
||||
innerRows := []string{
|
||||
styles.CardTitleStyle.Render("✦ filepass"),
|
||||
styles.CardSubtitleStyle.Render("Secure file transfer"),
|
||||
menu,
|
||||
}
|
||||
if statusLine != "" {
|
||||
innerRows = append(innerRows, statusLine)
|
||||
}
|
||||
topContent := styles.CardInnerStyle.Render(
|
||||
lipgloss.JoinVertical(lipgloss.Left, innerRows...),
|
||||
)
|
||||
|
||||
// footer
|
||||
hints := footerHint("↑↓", "navigate") +
|
||||
footerSep() +
|
||||
footerHint("enter", "select") +
|
||||
footerSep() +
|
||||
footerHint("esc", "quit")
|
||||
footer := styles.FooterStyle.Render(hints)
|
||||
|
||||
// card
|
||||
card := styles.CardStyle.Render(
|
||||
lipgloss.JoinVertical(lipgloss.Left,
|
||||
topContent,
|
||||
footer,
|
||||
),
|
||||
)
|
||||
|
||||
cardHeight := lipgloss.Height(card)
|
||||
topPad := max((h-cardHeight)/2, 0)
|
||||
|
||||
centeredCard := lipgloss.NewStyle().
|
||||
Width(w).
|
||||
Align(lipgloss.Center).
|
||||
PaddingTop(topPad).
|
||||
Render(card)
|
||||
|
||||
v := tea.NewView(centeredCard)
|
||||
v.AltScreen = true
|
||||
return v
|
||||
}
|
||||
Reference in New Issue
Block a user