| 1 | package tui |
| 2 | |
| 3 | import ( |
| 4 | "github.com/charmbracelet/bubbles/textinput" |
| 5 | tea "github.com/charmbracelet/bubbletea" |
| 6 | ) |
| 7 | |
| 8 | func (m Model) updateLoadingModels(msg tea.Msg) (tea.Model, tea.Cmd) { |
| 9 | switch msg := msg.(type) { |
| 10 | case tea.KeyMsg: |
| 11 | if msg.String() == "ctrl+c" { |
| 12 | m.quitting = true |
| 13 | return m, tea.Quit |
| 14 | } |
| 15 | case pickerModelsMsg: |
| 16 | if msg.err != nil { |
| 17 | m.modelsErr = msg.err |
| 18 | m.phase = phaseSelect |
| 19 | return m, nil |
| 20 | } |
| 21 | if len(msg.families) == 0 { |
| 22 | m.phase = phaseDone |
| 23 | m.launchAfterConfig = true |
| 24 | return m, tea.Quit |
| 25 | } |
| 26 | // Auto-select if only one model available (for kimi variants). |
| 27 | if m.pickerProvider == "kimi" || m.pickerProvider == "kimi-api-cn" || m.pickerProvider == "kimi-api-intl" { |
| 28 | var singleModel *PickerItem |
| 29 | totalModels := 0 |
| 30 | for _, items := range msg.models { |
| 31 | for i := range items { |
| 32 | singleModel = &items[i] |
| 33 | totalModels++ |
| 34 | if totalModels > 1 { |
| 35 | break |
| 36 | } |
| 37 | } |
| 38 | if totalModels > 1 { |
| 39 | break |
| 40 | } |
| 41 | } |
| 42 | if totalModels == 1 && singleModel != nil { |
| 43 | pc := m.cfg.Providers[m.pickerProvider] |
| 44 | pc.Model = singleModel.ID |
| 45 | m.cfg.Providers[m.pickerProvider] = pc |
| 46 | m.cfg.ActiveProvider = m.pickerProvider |
| 47 | m.phase = phaseDone |
| 48 | m.launchAfterConfig = true |
| 49 | return m, tea.Quit |
| 50 | } |
| 51 | } |
| 52 | m.families = msg.families |
| 53 | m.familyModels = msg.models |
| 54 | m.popularProviders = msg.popularProviders |
| 55 | m.popularProviderModels = msg.popularProviderModels |
| 56 | m.allModelIDs = msg.allModelIDs |
| 57 | m.preSelectModel() |
| 58 | m.phase = phaseSelectModel |
| 59 | if m.pickerProvider == "openrouter" || m.pickerProvider == "nvidia" { |
| 60 | m.initPickerInput() |
| 61 | } |
| 62 | if m.pickerProvider == "deepseek" && len(m.families) == 1 { |
| 63 | m.modelFocus = true |
| 64 | } |
| 65 | return m, nil |
| 66 | } |
| 67 | return m, nil |
| 68 | } |
| 69 | |
| 70 | func (m *Model) initPickerInput() { |
| 71 | pi := textinput.New() |
| 72 | switch m.pickerProvider { |
| 73 | case "nvidia": |
| 74 | pi.Placeholder = "e.g. nvidia/llama-3.1-nemotron-ultra-253b-v1" |
| 75 | default: |
| 76 | pi.Placeholder = "e.g. anthropic/claude-sonnet-4" |
| 77 | } |
| 78 | pi.CharLimit = 256 |
| 79 | pi.Width = 40 |
| 80 | m.pickerInput = pi |
| 81 | } |
| 82 | |