2020-08-18 01:03:52 +02:00
|
|
|
package gui
|
|
|
|
|
|
|
|
import "os/exec"
|
|
|
|
|
|
|
|
type viewUpdateOpts struct {
|
|
|
|
title string
|
2020-08-18 14:02:35 +02:00
|
|
|
|
|
|
|
// awkwardly calling this noWrap because of how hard Go makes it to have
|
|
|
|
// a boolean option that defaults to true
|
|
|
|
noWrap bool
|
|
|
|
|
|
|
|
highlight bool
|
|
|
|
|
|
|
|
task updateTask
|
2020-08-18 01:03:52 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
type refreshMainOpts struct {
|
|
|
|
main *viewUpdateOpts
|
|
|
|
secondary *viewUpdateOpts
|
|
|
|
}
|
|
|
|
|
|
|
|
// constants for updateTask's kind field
|
|
|
|
const (
|
|
|
|
RENDER_STRING = iota
|
2020-08-18 14:02:35 +02:00
|
|
|
RENDER_STRING_WITHOUT_SCROLL
|
2020-08-18 01:03:52 +02:00
|
|
|
RUN_FUNCTION
|
|
|
|
RUN_COMMAND
|
2020-08-18 14:02:35 +02:00
|
|
|
RUN_PTY
|
2020-08-18 01:03:52 +02:00
|
|
|
)
|
|
|
|
|
2020-08-18 14:02:35 +02:00
|
|
|
type updateTask interface {
|
|
|
|
GetKind() int
|
|
|
|
}
|
|
|
|
|
|
|
|
type renderStringTask struct {
|
|
|
|
str string
|
|
|
|
}
|
|
|
|
|
|
|
|
func (t *renderStringTask) GetKind() int {
|
|
|
|
return RENDER_STRING
|
|
|
|
}
|
|
|
|
|
|
|
|
func (gui *Gui) createRenderStringTask(str string) *renderStringTask {
|
|
|
|
return &renderStringTask{str: str}
|
|
|
|
}
|
|
|
|
|
|
|
|
type renderStringWithoutScrollTask struct {
|
|
|
|
str string
|
|
|
|
}
|
|
|
|
|
|
|
|
func (t *renderStringWithoutScrollTask) GetKind() int {
|
|
|
|
return RENDER_STRING_WITHOUT_SCROLL
|
|
|
|
}
|
|
|
|
|
|
|
|
func (gui *Gui) createRenderStringWithoutScrollTask(str string) *renderStringWithoutScrollTask {
|
|
|
|
return &renderStringWithoutScrollTask{str: str}
|
|
|
|
}
|
|
|
|
|
|
|
|
type runCommandTask struct {
|
2020-10-01 00:18:16 +02:00
|
|
|
cmd *exec.Cmd
|
|
|
|
prefix string
|
2020-08-18 14:02:35 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
func (t *runCommandTask) GetKind() int {
|
|
|
|
return RUN_COMMAND
|
|
|
|
}
|
|
|
|
|
|
|
|
func (gui *Gui) createRunCommandTask(cmd *exec.Cmd) *runCommandTask {
|
|
|
|
return &runCommandTask{cmd: cmd}
|
|
|
|
}
|
|
|
|
|
2020-10-01 00:18:16 +02:00
|
|
|
func (gui *Gui) createRunCommandTaskWithPrefix(cmd *exec.Cmd, prefix string) *runCommandTask {
|
|
|
|
return &runCommandTask{cmd: cmd, prefix: prefix}
|
|
|
|
}
|
|
|
|
|
2020-08-18 14:02:35 +02:00
|
|
|
type runPtyTask struct {
|
2020-10-01 00:18:16 +02:00
|
|
|
cmd *exec.Cmd
|
|
|
|
prefix string
|
2020-08-18 14:02:35 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
func (t *runPtyTask) GetKind() int {
|
|
|
|
return RUN_PTY
|
|
|
|
}
|
|
|
|
|
|
|
|
func (gui *Gui) createRunPtyTask(cmd *exec.Cmd) *runPtyTask {
|
|
|
|
return &runPtyTask{cmd: cmd}
|
|
|
|
}
|
|
|
|
|
2020-11-16 11:38:26 +02:00
|
|
|
// currently unused
|
|
|
|
// func (gui *Gui) createRunPtyTaskWithPrefix(cmd *exec.Cmd, prefix string) *runPtyTask {
|
|
|
|
// return &runPtyTask{cmd: cmd, prefix: prefix}
|
|
|
|
// }
|
2020-10-01 00:18:16 +02:00
|
|
|
|
2020-08-18 14:02:35 +02:00
|
|
|
type runFunctionTask struct {
|
|
|
|
f func(chan struct{}) error
|
|
|
|
}
|
|
|
|
|
|
|
|
func (t *runFunctionTask) GetKind() int {
|
|
|
|
return RUN_FUNCTION
|
|
|
|
}
|
|
|
|
|
2020-11-16 11:38:26 +02:00
|
|
|
// currently unused
|
|
|
|
// func (gui *Gui) createRunFunctionTask(f func(chan struct{}) error) *runFunctionTask {
|
|
|
|
// return &runFunctionTask{f: f}
|
|
|
|
// }
|
2020-08-18 01:03:52 +02:00
|
|
|
|
2020-08-18 14:02:35 +02:00
|
|
|
func (gui *Gui) runTaskForView(viewName string, task updateTask) error {
|
|
|
|
switch task.GetKind() {
|
|
|
|
case RENDER_STRING:
|
|
|
|
specificTask := task.(*renderStringTask)
|
|
|
|
return gui.newStringTask(viewName, specificTask.str)
|
|
|
|
|
|
|
|
case RENDER_STRING_WITHOUT_SCROLL:
|
|
|
|
specificTask := task.(*renderStringWithoutScrollTask)
|
|
|
|
return gui.newStringTaskWithoutScroll(viewName, specificTask.str)
|
|
|
|
|
|
|
|
case RUN_FUNCTION:
|
|
|
|
specificTask := task.(*runFunctionTask)
|
|
|
|
return gui.newTask(viewName, specificTask.f)
|
2020-08-18 01:03:52 +02:00
|
|
|
|
2020-08-18 14:02:35 +02:00
|
|
|
case RUN_COMMAND:
|
|
|
|
specificTask := task.(*runCommandTask)
|
2020-10-01 00:18:16 +02:00
|
|
|
return gui.newCmdTask(viewName, specificTask.cmd, specificTask.prefix)
|
2020-08-18 14:02:35 +02:00
|
|
|
|
|
|
|
case RUN_PTY:
|
|
|
|
specificTask := task.(*runPtyTask)
|
2020-10-01 00:18:16 +02:00
|
|
|
return gui.newPtyTask(viewName, specificTask.cmd, specificTask.prefix)
|
2020-08-18 14:02:35 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
return nil
|
2020-08-18 01:03:52 +02:00
|
|
|
}
|
|
|
|
|
2020-08-23 01:46:28 +02:00
|
|
|
func (gui *Gui) refreshMainView(opts *viewUpdateOpts, viewName string) error {
|
|
|
|
view, err := gui.g.View(viewName)
|
|
|
|
if err != nil {
|
|
|
|
gui.Log.Error(err)
|
|
|
|
return nil
|
|
|
|
}
|
2020-08-18 01:03:52 +02:00
|
|
|
|
2020-08-23 01:46:28 +02:00
|
|
|
view.Title = opts.title
|
|
|
|
view.Wrap = !opts.noWrap
|
|
|
|
view.Highlight = opts.highlight
|
|
|
|
|
2020-08-23 03:45:43 +02:00
|
|
|
if err := gui.runTaskForView(viewName, opts.task); err != nil {
|
2020-08-23 01:46:28 +02:00
|
|
|
gui.Log.Error(err)
|
|
|
|
return nil
|
|
|
|
}
|
2020-08-18 14:02:35 +02:00
|
|
|
|
2020-08-23 01:46:28 +02:00
|
|
|
return nil
|
|
|
|
}
|
|
|
|
|
|
|
|
func (gui *Gui) refreshMainViews(opts refreshMainOpts) error {
|
|
|
|
if opts.main != nil {
|
|
|
|
if err := gui.refreshMainView(opts.main, "main"); err != nil {
|
|
|
|
return err
|
2020-08-18 01:03:52 +02:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
gui.splitMainPanel(opts.secondary != nil)
|
|
|
|
|
|
|
|
if opts.secondary != nil {
|
2020-08-23 01:46:28 +02:00
|
|
|
if err := gui.refreshMainView(opts.secondary, "secondary"); err != nil {
|
|
|
|
return err
|
2020-08-18 01:03:52 +02:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
return nil
|
|
|
|
}
|
|
|
|
|
|
|
|
func (gui *Gui) splitMainPanel(splitMainPanel bool) {
|
|
|
|
gui.State.SplitMainPanel = splitMainPanel
|
|
|
|
|
|
|
|
// no need to set view on bottom when splitMainPanel is false: it will have zero size anyway thanks to our view arrangement code.
|
|
|
|
if splitMainPanel {
|
|
|
|
_, _ = gui.g.SetViewOnTop("secondary")
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
func (gui *Gui) isMainPanelSplit() bool {
|
|
|
|
return gui.State.SplitMainPanel
|
|
|
|
}
|