]> git.lizzy.rs Git - micro.git/blob - internal/action/infopane.go
Add mkparents option
[micro.git] / internal / action / infopane.go
1 package action
2
3 import (
4         "bytes"
5
6         "github.com/zyedidia/micro/internal/display"
7         "github.com/zyedidia/micro/internal/info"
8         "github.com/zyedidia/micro/internal/util"
9         "github.com/zyedidia/tcell"
10 )
11
12 type InfoKeyAction func(*InfoPane)
13
14 type InfoPane struct {
15         *BufPane
16         *info.InfoBuf
17 }
18
19 func NewInfoPane(ib *info.InfoBuf, w display.BWindow) *InfoPane {
20         ip := new(InfoPane)
21         ip.InfoBuf = ib
22         ip.BufPane = NewBufPane(ib.Buffer, w)
23
24         return ip
25 }
26
27 func NewInfoBar() *InfoPane {
28         ib := info.NewBuffer()
29         w := display.NewInfoWindow(ib)
30         return NewInfoPane(ib, w)
31 }
32
33 func (h *InfoPane) Close() {
34         h.InfoBuf.Close()
35         h.BufPane.Close()
36 }
37
38 func (h *InfoPane) HandleEvent(event tcell.Event) {
39         switch e := event.(type) {
40         case *tcell.EventKey:
41                 ke := KeyEvent{
42                         code: e.Key(),
43                         mod:  e.Modifiers(),
44                         r:    e.Rune(),
45                 }
46
47                 done := h.DoKeyEvent(ke)
48                 hasYN := h.HasYN
49                 if e.Key() == tcell.KeyRune && hasYN {
50                         if e.Rune() == 'y' && hasYN {
51                                 h.YNResp = true
52                                 h.DonePrompt(false)
53                         } else if e.Rune() == 'n' && hasYN {
54                                 h.YNResp = false
55                                 h.DonePrompt(false)
56                         }
57                 }
58                 if e.Key() == tcell.KeyRune && !done && !hasYN {
59                         h.DoRuneInsert(e.Rune())
60                         done = true
61                 }
62                 if done && h.HasPrompt && !hasYN {
63                         resp := string(h.LineBytes(0))
64                         hist := h.History[h.PromptType]
65                         hist[h.HistoryNum] = resp
66                         if h.EventCallback != nil {
67                                 h.EventCallback(resp)
68                         }
69                 }
70         case *tcell.EventMouse:
71                 h.BufPane.HandleEvent(event)
72         }
73 }
74
75 func (h *InfoPane) DoKeyEvent(e KeyEvent) bool {
76         done := false
77         if action, ok := BufKeyBindings[e]; ok {
78                 estr := BufKeyStrings[e]
79                 for _, s := range InfoNones {
80                         if s == estr {
81                                 return false
82                         }
83                 }
84                 for s, a := range InfoOverrides {
85                         if s == estr {
86                                 done = true
87                                 a(h)
88                                 break
89                         }
90                 }
91                 if !done {
92                         done = action(h.BufPane)
93                 }
94         }
95         return done
96 }
97
98 // InfoNones is a list of actions that should have no effect when executed
99 // by an infohandler
100 var InfoNones = []string{
101         "Save",
102         "SaveAll",
103         "SaveAs",
104         "Find",
105         "FindNext",
106         "FindPrevious",
107         "Center",
108         "DuplicateLine",
109         "MoveLinesUp",
110         "MoveLinesDown",
111         "OpenFile",
112         "Start",
113         "End",
114         "PageUp",
115         "PageDown",
116         "SelectPageUp",
117         "SelectPageDown",
118         "HalfPageUp",
119         "HalfPageDown",
120         "ToggleHelp",
121         "ToggleKeyMenu",
122         "ToggleRuler",
123         "JumpLine",
124         "ClearStatus",
125         "ShellMode",
126         "CommandMode",
127         "AddTab",
128         "PreviousTab",
129         "NextTab",
130         "NextSplit",
131         "PreviousSplit",
132         "Unsplit",
133         "VSplit",
134         "HSplit",
135         "ToggleMacro",
136         "PlayMacro",
137         "Suspend",
138         "ScrollUp",
139         "ScrollDown",
140         "SpawnMultiCursor",
141         "SpawnMultiCursorSelect",
142         "RemoveMultiCursor",
143         "RemoveAllMultiCursors",
144         "SkipMultiCursor",
145 }
146
147 // InfoOverrides is the list of actions which have been overriden
148 // by the infohandler
149 var InfoOverrides = map[string]InfoKeyAction{
150         "CursorUp":      (*InfoPane).CursorUp,
151         "CursorDown":    (*InfoPane).CursorDown,
152         "InsertNewline": (*InfoPane).InsertNewline,
153         "InsertTab":     (*InfoPane).InsertTab,
154         "OutdentLine":   (*InfoPane).CycleBack,
155         "Escape":        (*InfoPane).Escape,
156         "Quit":          (*InfoPane).Quit,
157         "QuitAll":       (*InfoPane).QuitAll,
158 }
159
160 // CursorUp cycles history up
161 func (h *InfoPane) CursorUp() {
162         h.UpHistory(h.History[h.PromptType])
163 }
164
165 // CursorDown cycles history down
166 func (h *InfoPane) CursorDown() {
167         h.DownHistory(h.History[h.PromptType])
168 }
169
170 // InsertTab begins autocompletion
171 func (h *InfoPane) InsertTab() {
172         b := h.Buf
173         if b.HasSuggestions {
174                 b.CycleAutocomplete(true)
175                 return
176         }
177
178         c := b.GetActiveCursor()
179         l := b.LineBytes(0)
180         l = util.SliceStart(l, c.X)
181
182         args := bytes.Split(l, []byte{' '})
183         cmd := string(args[0])
184
185         if len(args) == 1 {
186                 b.Autocomplete(CommandComplete)
187         } else {
188                 if action, ok := commands[cmd]; ok {
189                         if action.completer != nil {
190                                 b.Autocomplete(action.completer)
191                         }
192                 }
193         }
194 }
195
196 // CycleBack cycles back in the autocomplete suggestion list
197 func (h *InfoPane) CycleBack() {
198         if h.Buf.HasSuggestions {
199                 h.Buf.CycleAutocomplete(false)
200         }
201 }
202
203 // InsertNewline completes the prompt
204 func (h *InfoPane) InsertNewline() {
205         if !h.HasYN {
206                 h.DonePrompt(false)
207         }
208 }
209
210 // Quit cancels the prompt
211 func (h *InfoPane) Quit() {
212         h.DonePrompt(true)
213 }
214
215 // QuitAll cancels the prompt
216 func (h *InfoPane) QuitAll() {
217         h.DonePrompt(true)
218 }
219
220 // Escape cancels the prompt
221 func (h *InfoPane) Escape() {
222         h.DonePrompt(true)
223 }