summaryrefslogtreecommitdiff
path: root/pkg/gui
diff options
context:
space:
mode:
Diffstat (limited to 'pkg/gui')
-rw-r--r--pkg/gui/branchview.go33
-rw-r--r--pkg/gui/commitsview.go4
-rw-r--r--pkg/gui/diffview.go4
-rw-r--r--pkg/gui/errorview.go10
-rw-r--r--pkg/gui/gui-navigate.go54
-rw-r--r--pkg/gui/gui.go4
-rw-r--r--pkg/gui/keybindings.go322
-rw-r--r--pkg/gui/remotebranchview.go21
-rw-r--r--pkg/gui/remotesview.go25
9 files changed, 375 insertions, 102 deletions
diff --git a/pkg/gui/branchview.go b/pkg/gui/branchview.go
index a64c3c3..b6a2b43 100644
--- a/pkg/gui/branchview.go
+++ b/pkg/gui/branchview.go
@@ -10,7 +10,7 @@ import (
// updates the branchview for given entity
func (gui *Gui) updateBranch(g *gocui.Gui, entity *git.RepoEntity) error {
var err error
- out, err := g.View("branch")
+ out, err := g.View(branchViewFeature.Name)
if err != nil {
return err
}
@@ -38,11 +38,38 @@ func (gui *Gui) nextBranch(g *gocui.Gui, v *gocui.View) error {
entity := gui.getSelectedRepository()
if err = entity.Checkout(entity.NextBranch()); err != nil {
if err = gui.openErrorView(g, err.Error(),
- "You should manually resolve this issue"); err != nil {
+ "You should manually resolve this issue",
+ branchViewFeature.Name); err != nil {
return err
}
return nil
}
+ if err = gui.checkoutFollowUp(g, entity); err != nil {
+ return err
+ }
+ return nil
+}
+
+// iteration handler for the branchview
+func (gui *Gui) previousBranch(g *gocui.Gui, v *gocui.View) error {
+ var err error
+ entity := gui.getSelectedRepository()
+ if err = entity.Checkout(entity.PreviousBranch()); err != nil {
+ if err = gui.openErrorView(g, err.Error(),
+ "You should manually resolve this issue",
+ branchViewFeature.Name); err != nil {
+ return err
+ }
+ return nil
+ }
+ if err = gui.checkoutFollowUp(g, entity); err != nil {
+ return err
+ }
+ return nil
+}
+
+// after checkout a branch some refreshments needed
+func (gui *Gui) checkoutFollowUp(g *gocui.Gui, entity *git.RepoEntity) (err error) {
if err = gui.updateBranch(g, entity); err != nil {
return err
}
@@ -56,4 +83,4 @@ func (gui *Gui) nextBranch(g *gocui.Gui, v *gocui.View) error {
return err
}
return nil
-}
+} \ No newline at end of file
diff --git a/pkg/gui/commitsview.go b/pkg/gui/commitsview.go
index 91cb795..6d1325c 100644
--- a/pkg/gui/commitsview.go
+++ b/pkg/gui/commitsview.go
@@ -20,8 +20,10 @@ func (gui *Gui) updateCommits(g *gocui.Gui, entity *git.RepoEntity) error {
totalcommits := len(entity.Commits)
for i, c := range entity.Commits {
var body string
- if c.CommitType == git.LocalCommit {
+ if c.CommitType == git.EvenCommit {
body = cyan.Sprint(c.Hash[:hashLength]) + " " + c.Message
+ } else if c.CommitType == git.LocalCommit {
+ body = blue.Sprint(c.Hash[:hashLength]) + " " + c.Message
} else {
body = yellow.Sprint(c.Hash[:hashLength]) + " " + c.Message
}
diff --git a/pkg/gui/diffview.go b/pkg/gui/diffview.go
index 6f512ce..b775f95 100644
--- a/pkg/gui/diffview.go
+++ b/pkg/gui/diffview.go
@@ -47,10 +47,10 @@ func (gui *Gui) closeCommitDiffView(g *gocui.Gui, v *gocui.View) error {
if err := g.DeleteView(v.Name()); err != nil {
return nil
}
- if _, err := g.SetCurrentView(mainViewFeature.Name); err != nil {
+ if _, err := g.SetCurrentView(commitViewFeature.Name); err != nil {
return err
}
- gui.updateKeyBindingsView(g, mainViewFeature.Name)
+ gui.updateKeyBindingsView(g, commitViewFeature.Name)
return nil
}
diff --git a/pkg/gui/errorview.go b/pkg/gui/errorview.go
index 362a656..b4be162 100644
--- a/pkg/gui/errorview.go
+++ b/pkg/gui/errorview.go
@@ -6,10 +6,12 @@ import (
"github.com/jroimartin/gocui"
)
+var errorReturnView string
+
// open an error view to inform user with a message and a useful note
-func (gui *Gui) openErrorView(g *gocui.Gui, message string, note string) error {
+func (gui *Gui) openErrorView(g *gocui.Gui, message, note, returnViewName string) error {
maxX, maxY := g.Size()
-
+ errorReturnView = returnViewName
v, err := g.SetView(errorViewFeature.Name, maxX/2-30, maxY/2-3, maxX/2+30, maxY/2+3)
if err != nil {
if err != gocui.ErrUnknownView {
@@ -34,9 +36,9 @@ func (gui *Gui) closeErrorView(g *gocui.Gui, v *gocui.View) error {
if err := g.DeleteView(v.Name()); err != nil {
return nil
}
- if _, err := g.SetCurrentView(mainViewFeature.Name); err != nil {
+ if _, err := g.SetCurrentView(errorReturnView); err != nil {
return err
}
- gui.updateKeyBindingsView(g, mainViewFeature.Name)
+ gui.updateKeyBindingsView(g, errorReturnView)
return nil
}
diff --git a/pkg/gui/gui-navigate.go b/pkg/gui/gui-navigate.go
new file mode 100644
index 0000000..56d96de
--- /dev/null
+++ b/pkg/gui/gui-navigate.go
@@ -0,0 +1,54 @@
+package gui
+
+import (
+ log "github.com/sirupsen/logrus"
+ "github.com/jroimartin/gocui"
+)
+
+// focus to next view
+func (gui *Gui) nextView(g *gocui.Gui, v *gocui.View) error {
+ var focusedViewName string
+ if v == nil || v.Name() == mainViews[len(mainViews)-1].Name {
+ focusedViewName = mainViews[0].Name
+ } else {
+ for i := range mainViews {
+ if v.Name() == mainViews[i].Name {
+ focusedViewName = mainViews[i+1].Name
+ break
+ }
+ if i == len(mainViews)-1 {
+ return nil
+ }
+ }
+ }
+ if _, err := g.SetCurrentView(focusedViewName); err != nil {
+ log.Warn("Loading view cannot be focused.")
+ return nil
+ }
+ gui.updateKeyBindingsView(g, focusedViewName)
+ return nil
+}
+
+// focus to previous view
+func (gui *Gui) previousView(g *gocui.Gui, v *gocui.View) error {
+ var focusedViewName string
+ if v == nil || v.Name() == mainViews[0].Name {
+ focusedViewName = mainViews[len(mainViews)-1].Name
+ } else {
+ for i := range mainViews {
+ if v.Name() == mainViews[i].Name {
+ focusedViewName = mainViews[i-1].Name
+ break
+ }
+ if i == len(mainViews)-1 {
+ return nil
+ }
+ }
+ }
+ if _, err := g.SetCurrentView(focusedViewName); err != nil {
+ log.Warn("Loading view cannot be focused.")
+ return nil
+ }
+ gui.updateKeyBindingsView(g, focusedViewName)
+ return nil
+}
diff --git a/pkg/gui/gui.go b/pkg/gui/gui.go
index c6950fb..b781ba5 100644
--- a/pkg/gui/gui.go
+++ b/pkg/gui/gui.go
@@ -68,6 +68,8 @@ var (
fetchMode = mode{ModeID: FetchMode, DisplayString: "Fetch", CommandString: "fetch"}
pullMode = mode{ModeID: PullMode, DisplayString: "Pull", CommandString: "pull"}
mergeMode = mode{ModeID: MergeMode, DisplayString: "Merge", CommandString: "merge"}
+
+ mainViews = []viewFeature{mainViewFeature, remoteViewFeature, remoteBranchViewFeature, branchViewFeature, commitViewFeature}
)
// NewGui creates a Gui opject and fill it's state related entites
@@ -117,6 +119,8 @@ func (gui *Gui) Run() error {
defer g.Close()
gui.g = g
+ g.Highlight = true
+ g.SelFgColor = gocui.ColorGreen
g.SetManagerFunc(gui.layout)
if err := gui.generateKeybindings(); err != nil {
diff --git a/pkg/gui/keybindings.go b/pkg/gui/keybindings.go
index a388b51..b2622bc 100644
--- a/pkg/gui/keybindings.go
+++ b/pkg/gui/keybindings.go
@@ -20,32 +20,65 @@ type KeyBinding struct {
// generate the gui's controls a.k.a. keybindings
func (gui *Gui) generateKeybindings() error {
- gui.KeyBindings = []*KeyBinding{
+ // Mainviews common keybindings
+ for _, view := range mainViews {
+ mainKeybindings := []*KeyBinding{
+ {
+ View: view.Name,
+ Key: 'q',
+ Modifier: gocui.ModNone,
+ Handler: gui.quit,
+ Display: "q",
+ Description: "Quit",
+ Vital: true,
+ }, {
+ View: view.Name,
+ Key: gocui.KeyTab,
+ Modifier: gocui.ModNone,
+ Handler: gui.switchMode,
+ Display: "tab",
+ Description: "Switch mode",
+ Vital: true,
+ }, {
+ View: view.Name,
+ Key: gocui.KeyArrowLeft,
+ Modifier: gocui.ModNone,
+ Handler: gui.previousView,
+ Display: "←",
+ Description: "Previous Panel",
+ Vital: false,
+ }, {
+ View: view.Name,
+ Key: gocui.KeyArrowRight,
+ Modifier: gocui.ModNone,
+ Handler: gui.nextView,
+ Display: "→",
+ Description: "Next Panel",
+ Vital: false,
+ }, {
+ View: view.Name,
+ Key: 'l',
+ Modifier: gocui.ModNone,
+ Handler: gui.nextView,
+ Display: "l",
+ Description: "Previous Panel",
+ Vital: false,
+ }, {
+ View: view.Name,
+ Key: 'h',
+ Modifier: gocui.ModNone,
+ Handler: gui.previousView,
+ Display: "h",
+ Description: "Next Panel",
+ Vital: false,
+ },
+ }
+ for _, binding := range mainKeybindings {
+ gui.KeyBindings = append(gui.KeyBindings, binding)
+ }
+ }
+ individualKeybindings := []*KeyBinding{
{
- View: "",
- Key: gocui.KeyCtrlC,
- Modifier: gocui.ModNone,
- Handler: gui.quit,
- Display: "ctrl + c",
- Description: "Force application to quit",
- Vital: false,
- }, {
- View: mainViewFeature.Name,
- Key: 'q',
- Modifier: gocui.ModNone,
- Handler: gui.quit,
- Display: "q",
- Description: "Quit",
- Vital: true,
- }, {
- View: mainViewFeature.Name,
- Key: gocui.KeyTab,
- Modifier: gocui.ModNone,
- Handler: gui.switchMode,
- Display: "tab",
- Description: "Switch mode",
- Vital: true,
- }, {
View: mainViewFeature.Name,
Key: gocui.KeyArrowUp,
Modifier: gocui.ModNone,
@@ -79,59 +112,11 @@ func (gui *Gui) generateKeybindings() error {
Vital: false,
}, {
View: mainViewFeature.Name,
- Key: 'b',
- Modifier: gocui.ModNone,
- Handler: gui.nextBranch,
- Display: "b",
- Description: "Iterate over branches",
- Vital: false,
- }, {
- View: mainViewFeature.Name,
- Key: 'r',
- Modifier: gocui.ModNone,
- Handler: gui.nextRemote,
- Display: "r",
- Description: "Iterate over remotes",
- Vital: false,
- }, {
- View: mainViewFeature.Name,
- Key: 'e',
- Modifier: gocui.ModNone,
- Handler: gui.nextRemoteBranch,
- Display: "e",
- Description: "Iterate over remote branches",
- Vital: false,
- }, {
- View: mainViewFeature.Name,
- Key: 's',
- Modifier: gocui.ModNone,
- Handler: gui.nextCommit,
- Display: "s",
- Description: "Iterate over commits",
- Vital: false,
- },{
- View: mainViewFeature.Name,
- Key: 's',
- Modifier: gocui.ModAlt,
- Handler: gui.prevCommit,
- Display: "alt + s",
- Description: "Iterate over commits",
- Vital: false,
- }, {
- View: mainViewFeature.Name,
- Key: 'd',
- Modifier: gocui.ModNone,
- Handler: gui.openCommitDiffView,
- Display: "d",
- Description: "Show commit diff",
- Vital: false,
- }, {
- View: mainViewFeature.Name,
- Key: 'c',
+ Key: gocui.KeySpace,
Modifier: gocui.ModNone,
- Handler: gui.openCheatSheetView,
- Display: "c",
- Description: "Controls",
+ Handler: gui.markRepository,
+ Display: "space",
+ Description: "Add to queue",
Vital: true,
}, {
View: mainViewFeature.Name,
@@ -143,14 +128,6 @@ func (gui *Gui) generateKeybindings() error {
Vital: true,
}, {
View: mainViewFeature.Name,
- Key: gocui.KeySpace,
- Modifier: gocui.ModNone,
- Handler: gui.markRepository,
- Display: "space",
- Description: "Add to queue",
- Vital: true,
- }, {
- View: mainViewFeature.Name,
Key: gocui.KeyCtrlSpace,
Modifier: gocui.ModNone,
Handler: gui.markAllRepositories,
@@ -167,6 +144,14 @@ func (gui *Gui) generateKeybindings() error {
Vital: false,
}, {
View: mainViewFeature.Name,
+ Key: 'c',
+ Modifier: gocui.ModNone,
+ Handler: gui.openCheatSheetView,
+ Display: "c",
+ Description: "Controls",
+ Vital: true,
+ }, {
+ View: mainViewFeature.Name,
Key: 'n',
Modifier: gocui.ModNone,
Handler: gui.sortByName,
@@ -182,6 +167,160 @@ func (gui *Gui) generateKeybindings() error {
Description: "Sort repositories by Modification date",
Vital: false,
}, {
+ View: "",
+ Key: gocui.KeyCtrlC,
+ Modifier: gocui.ModNone,
+ Handler: gui.quit,
+ Display: "ctrl + c",
+ Description: "Force application to quit",
+ Vital: false,
+ },
+ // Branch View Controls
+ {
+ View: branchViewFeature.Name,
+ Key: gocui.KeyArrowDown,
+ Modifier: gocui.ModNone,
+ Handler: gui.nextBranch,
+ Display: "↓",
+ Description: "Iterate over branches",
+ Vital: false,
+ }, {
+ View: branchViewFeature.Name,
+ Key: gocui.KeyArrowUp,
+ Modifier: gocui.ModNone,
+ Handler: gui.previousBranch,
+ Display: "↑",
+ Description: "Iterate over branches",
+ Vital: false,
+ }, {
+ View: branchViewFeature.Name,
+ Key: 'j',
+ Modifier: gocui.ModNone,
+ Handler: gui.nextBranch,
+ Display: "j",
+ Description: "Down",
+ Vital: false,
+ }, {
+ View: branchViewFeature.Name,
+ Key: 'k',
+ Modifier: gocui.ModNone,
+ Handler: gui.previousBranch,
+ Display: "k",
+ Description: "Up",
+ Vital: false,
+ },
+ // Remote View Controls
+ {
+ View: remoteViewFeature.Name,
+ Key: gocui.KeyArrowDown,
+ Modifier: gocui.ModNone,
+ Handler: gui.nextRemote,
+ Display: "↓",
+ Description: "Iterate over remotes",
+ Vital: false,
+ }, {
+ View: remoteViewFeature.Name,
+ Key: gocui.KeyArrowUp,
+ Modifier: gocui.ModNone,
+ Handler: gui.previousRemote,
+ Display: "↑",
+ Description: "Iterate over remotes",
+ Vital: false,
+ }, {
+ View: remoteViewFeature.Name,
+ Key: 'j',
+ Modifier: gocui.ModNone,
+ Handler: gui.nextRemote,
+ Display: "j",
+ Description: "Down",
+ Vital: false,
+ }, {
+ View: remoteViewFeature.Name,
+ Key: 'k',
+ Modifier: gocui.ModNone,
+ Handler: gui.previousRemote,
+ Display: "k",
+ Description: "Up",
+ Vital: false,
+ },
+ // Remote Branch View Controls
+ {
+ View: remoteBranchViewFeature.Name,
+ Key: gocui.KeyArrowDown,
+ Modifier: gocui.ModNone,
+ Handler: gui.nextRemoteBranch,
+ Display: "↓",
+ Description: "Iterate over remote branches",
+ Vital: false,
+ }, {
+ View: remoteBranchViewFeature.Name,
+ Key: gocui.KeyArrowUp,
+ Modifier: gocui.ModNone,
+ Handler: gui.previousRemoteBranch,
+ Display: "↑",
+ Description: "Iterate over remote branches",
+ Vital: false,
+ }, {
+ View: remoteBranchViewFeature.Name,
+ Key: 'j',
+ Modifier: gocui.ModNone,
+ Handler: gui.nextRemoteBranch,
+ Display: "j",
+ Description: "Down",
+ Vital: false,
+ }, {
+ View: remoteBranchViewFeature.Name,
+ Key: 'k',
+ Modifier: gocui.ModNone,
+ Handler: gui.previousRemoteBranch,
+ Display: "k",
+ Description: "Up",
+ Vital: false,
+ },
+ // Commit View Controls
+ {
+ View: commitViewFeature.Name,
+ Key: gocui.KeyArrowDown,
+ Modifier: gocui.ModNone,
+ Handler: gui.nextCommit,
+ Display: "↓",
+ Description: "Iterate over commits",
+ Vital: false,
+ },{
+ View: commitViewFeature.Name,
+ Key: gocui.KeyArrowUp,
+ Modifier: gocui.ModNone,
+ Handler: gui.prevCommit,
+ Display: "↑",
+ Description: "Iterate over commits",
+ Vital: false,
+ }, {
+ View: commitViewFeature.Name,
+ Key: 'j',
+ Modifier: gocui.ModNone,
+ Handler: gui.nextCommit,
+ Display: "j",
+ Description: "Down",
+ Vital: false,
+ }, {
+ View: commitViewFeature.Name,
+ Key: 'k',
+ Modifier: gocui.ModNone,
+ Handler: gui.prevCommit,
+ Display: "k",
+ Description: "Up",
+ Vital: false,
+ },{
+ View: commitViewFeature.Name,
+ Key: 'd',
+ Modifier: gocui.ModNone,
+ Handler: gui.openCommitDiffView,
+ Display: "d",
+ Description: "Show commit diff",
+ Vital: true,
+ },
+ // Diff View Controls
+ {
View: commitDiffViewFeature.Name,
Key: 'c',
Modifier: gocui.ModNone,
@@ -221,7 +360,9 @@ func (gui *Gui) generateKeybindings() error {
Display: "j",
Description: "Page down",
Vital: false,
- }, {
+ },
+ // Application Controls
+ {
View: cheatSheetViewFeature.Name,
Key: 'c',
Modifier: gocui.ModNone,
@@ -261,7 +402,9 @@ func (gui *Gui) generateKeybindings() error {
Display: "j",
Description: "Down",
Vital: false,
- }, {
+ },
+ // Error View
+ {
View: errorViewFeature.Name,
Key: 'c',
Modifier: gocui.ModNone,
@@ -269,7 +412,10 @@ func (gui *Gui) generateKeybindings() error {
Display: "c",
Description: "close/cancel",
Vital: true,
- },
+ },
+ }
+ for _, binding := range individualKeybindings {
+ gui.KeyBindings = append(gui.KeyBindings, binding)
}
return nil
}
diff --git a/pkg/gui/remotebranchview.go b/pkg/gui/remotebranchview.go
index f720830..eb65d55 100644
--- a/pkg/gui/remotebranchview.go
+++ b/pkg/gui/remotebranchview.go
@@ -19,12 +19,16 @@ func (gui *Gui) updateRemoteBranches(g *gocui.Gui, entity *git.RepoEntity) error
trb := len(entity.Remote.Branches)
if trb > 0 {
for i, r := range entity.Remote.Branches {
+ rName := r.Name
+ if r.Deleted {
+ rName = rName + ws + dirty
+ }
if r.Name == entity.Remote.Branch.Name {
currentindex = i
- fmt.Fprintln(out, selectionIndicator+r.Name)
+ fmt.Fprintln(out, selectionIndicator+rName)
continue
}
- fmt.Fprintln(out, tab+r.Name)
+ fmt.Fprintln(out, tab+rName)
}
if err = gui.smartAnchorRelativeToLine(out, currentindex, trb); err != nil {
return err
@@ -45,3 +49,16 @@ func (gui *Gui) nextRemoteBranch(g *gocui.Gui, v *gocui.View) error {
}
return nil
}
+
+// iteration handler for the remotebranchview
+func (gui *Gui) previousRemoteBranch(g *gocui.Gui, v *gocui.View) error {
+ var err error
+ entity := gui.getSelectedRepository()
+ if err = entity.Remote.PreviousRemoteBranch(); err != nil {
+ return err
+ }
+ if err = gui.updateRemoteBranches(g, entity); err != nil {
+ return err
+ }
+ return nil
+}
diff --git a/pkg/gui/remotesview.go b/pkg/gui/remotesview.go
index a7cbc43..6f31265 100644
--- a/pkg/gui/remotesview.go
+++ b/pkg/gui/remotesview.go
@@ -44,11 +44,32 @@ func (gui *Gui) nextRemote(g *gocui.Gui, v *gocui.View) error {
if err = entity.NextRemote(); err != nil {
return err
}
- if err = gui.updateRemotes(g, entity); err != nil {
+ if err = gui.remoteChangeFollowUp(g, entity); err != nil {
return err
}
- if err = gui.updateRemoteBranches(g, entity); err != nil {
+ return err
+}
+
+// iteration handler for the remotesview
+func (gui *Gui) previousRemote(g *gocui.Gui, v *gocui.View) error {
+ var err error
+ entity := gui.getSelectedRepository()
+ if err = entity.PreviousRemote(); err != nil {
+ return err
+ }
+ if err = gui.remoteChangeFollowUp(g, entity); err != nil {
return err
}
return err
}
+
+// after checkout a remote some refreshments needed
+func (gui *Gui) remoteChangeFollowUp(g *gocui.Gui, entity *git.RepoEntity) (err error) {
+ if err = gui.updateRemotes(g, entity); err != nil {
+ return err
+ }
+ if err = gui.updateRemoteBranches(g, entity); err != nil {
+ return err
+ }
+ return nil
+} \ No newline at end of file