Files
img-proxy-url-generator/interactive/update.go
Ron Rise d94c9bf4e6
All checks were successful
🧪 ✨ Unit Tests Workflow / 🔍 🐹 Go Tests (push) Successful in 3m13s
novalagung is going to love this.
2025-05-22 20:28:01 -04:00

109 lines
2.7 KiB
Go

package interactive
import (
tea "github.com/charmbracelet/bubbletea"
"github.com/charmbracelet/huh"
)
// Helper: find index of current focusField in a given field slice.
//
//goland:noinspection GoMixedReceiverTypes
func (m *Model) findCurrentFieldIndex(fields []huh.Field) int {
for i, field := range fields {
if field == m.focusField {
return i
}
}
return -1
}
// Helper: blur current, focus next (wraps to 0)
//
//goland:noinspection GoMixedReceiverTypes
func (m *Model) focusNextField(fields []huh.Field) {
index := m.findCurrentFieldIndex(fields)
next := (index + 1) % len(fields)
m.focusField.Blur()
m.focusField = fields[next]
m.focusField.Focus()
}
// Helper: focus a specific field by index
//
//goland:noinspection GoMixedReceiverTypes
func (m *Model) focusFieldByIndex(fields []huh.Field, index int) {
if index >= 0 && index < len(fields) {
m.focusField.Blur()
m.focusField = fields[index]
m.focusField.Focus()
}
}
// Helper: get all selected param fields as a flat slice
//
//goland:noinspection GoMixedReceiverTypes
func (m *Model) selectedParamFields() []huh.Field {
var fields []huh.Field
for _, param := range *m.selectedParams {
fields = append(fields, param.Input()...)
}
return fields
}
//goland:noinspection GoMixedReceiverTypes
func (m Model) Update(msg tea.Msg) (tea.Model, tea.Cmd) {
model := m // copy, since Bubble Tea prefers value receivers, but we'll operate on &model internally
if model.focusField == nil && len(model.Fields) > 0 {
model.Fields[0].Focus()
model.focusField = model.Fields[0]
}
if keyMsg, ok := msg.(tea.KeyMsg); ok {
switch keyMsg.String() {
case "tab":
mainFields := model.Fields
paramFields := model.selectedParamFields()
if model.inParamsFields && len(paramFields) > 0 {
index := model.findCurrentFieldIndex(paramFields)
if index == -1 {
break
}
if index == len(paramFields)-1 {
// Last param field: cycle to main fields
model.inParamsFields = false
model.focusFieldByIndex(mainFields, 0)
} else {
model.focusNextField(paramFields)
}
} else {
index := model.findCurrentFieldIndex(mainFields)
if index == -1 {
break
}
if index == len(mainFields)-1 && len(paramFields) > 0 {
// Last main field & params exist: go to params
model.inParamsFields = true
model.focusFieldByIndex(paramFields, 0)
} else {
model.focusNextField(mainFields)
}
}
case "ctrl+c", "esc":
return model, tea.Quit
case "enter":
return model, nil
default:
if model.focusField != nil {
md, cmd := model.focusField.(huh.Field).Update(msg)
if md != nil {
model.focusField = md.(huh.Field)
}
return model, cmd
}
}
}
return model, nil
}