mirror of
https://github.com/jesseduffield/lazygit.git
synced 2026-09-29 10:36:45 -04:00
Compare commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
e921ba0910 | ||
|
|
0f5a073d57 | ||
|
|
cb0bdd89c0 | ||
|
|
e89bf5d06b | ||
|
|
e82d2f37a1 | ||
|
|
e73f4c6b7e | ||
|
|
cf5cefb2d6 | ||
|
|
36ac764133 | ||
|
|
003e45d2f5 | ||
|
|
04e93317b8 | ||
|
|
f8dedb710b | ||
|
|
1c259f69f6 | ||
|
|
913f17ee3e | ||
|
|
6291c53966 |
@@ -22,7 +22,7 @@ jobs:
|
||||
env:
|
||||
GITHUB_TOKEN: ${{secrets.GITHUB_API_TOKEN}}
|
||||
- name: Bump Homebrew
|
||||
uses: dawidd6/action-homebrew-bump-formula@v2
|
||||
uses: dawidd6/action-homebrew-bump-formula@v3
|
||||
with:
|
||||
token: ${{secrets.GITHUB_API_TOKEN}}
|
||||
formula: lazygit
|
||||
|
||||
+13
-4
@@ -24,7 +24,9 @@ Default path for the config file:
|
||||
optionsTextColor:
|
||||
- blue
|
||||
selectedLineBgColor:
|
||||
- bold
|
||||
- default
|
||||
selectedRangeBgColor:
|
||||
- blue
|
||||
commitLength:
|
||||
show: true
|
||||
mouseEvents: true
|
||||
@@ -41,6 +43,7 @@ Default path for the config file:
|
||||
args: ""
|
||||
skipHookPrefix: WIP
|
||||
autoFetch: true
|
||||
branchLogCmd: "git log --graph --color=always --abbrev-commit --decorate --date=relative --pretty=medium {{branchName}} --"
|
||||
update:
|
||||
method: prompt # can be: prompt | background | never
|
||||
days: 14 # how often an update is checked for
|
||||
@@ -93,7 +96,7 @@ Default path for the config file:
|
||||
prevScreenMode: '_'
|
||||
undo: 'z'
|
||||
redo: '<c-z>'
|
||||
filteringMenu: <c-s>
|
||||
filteringMenu: '<c-s>'
|
||||
diffingMenu: '<c-e>'
|
||||
copyToClipboard: '<c-o>'
|
||||
status:
|
||||
@@ -216,7 +219,7 @@ If you have issues with a light terminal theme where you can't read / see the te
|
||||
inactiveBorderColor:
|
||||
- black
|
||||
selectedLineBgColor:
|
||||
- bold
|
||||
- default
|
||||
```
|
||||
|
||||
## Struggling to see selected line
|
||||
@@ -228,6 +231,8 @@ If you struggle to see the selected line I recomment using the reverse attribute
|
||||
theme:
|
||||
selectedLineBgColor:
|
||||
- reverse
|
||||
selectedRangeBgColor:
|
||||
- reverse
|
||||
```
|
||||
|
||||
## Example Coloring
|
||||
@@ -256,14 +261,18 @@ For all possible keybinding options, check [Custom_Keybindings.md](https://githu
|
||||
scrollDownMain-alt1: 'E'
|
||||
scrollUpMain-alt2: '<c-u>'
|
||||
scrollDownMain-alt2: '<c-e>'
|
||||
undo: 'l'
|
||||
redo: '<c-r>'
|
||||
diffingMenu: 'M'
|
||||
filteringMenu: '<c-f>'
|
||||
files:
|
||||
ignoreFile: 'I'
|
||||
commits:
|
||||
moveDownCommit: '<c-e>'
|
||||
moveUpCommit: '<c-u>'
|
||||
toggleDiffCommit: 'l'
|
||||
branches:
|
||||
viewGitFlowOptions: 'I'
|
||||
setUpstream: 'U'
|
||||
```
|
||||
|
||||
## Custom pull request URLs
|
||||
|
||||
+8
-1
@@ -131,9 +131,16 @@ func NewApp(config config.AppConfigurer, filterPath string) (*App, error) {
|
||||
func (app *App) setupRepo() error {
|
||||
// if we are not in a git repo, we ask if we want to `git init`
|
||||
if err := app.OSCommand.RunCommand("git status"); err != nil {
|
||||
if !strings.Contains(err.Error(), "Not a git repository") {
|
||||
cwd, err := os.Getwd()
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
info, _ := os.Stat(filepath.Join(cwd, ".git"))
|
||||
if info != nil && info.IsDir() {
|
||||
return err // Current directory appears to be a git repository.
|
||||
}
|
||||
|
||||
// Offer to initialize a new repository in current directory.
|
||||
fmt.Print(app.Tr.SLocalize("CreateRepo"))
|
||||
response, _ := bufio.NewReader(os.Stdin).ReadString('\n')
|
||||
if strings.Trim(response, " \n") != "y" {
|
||||
|
||||
@@ -52,7 +52,7 @@ func (b *BranchListBuilder) obtainBranches() []*Branch {
|
||||
|
||||
split := strings.Split(line, SEPARATION_CHAR)
|
||||
|
||||
name := split[1]
|
||||
name := strings.TrimPrefix(split[1], "heads/")
|
||||
branch := &Branch{
|
||||
Name: name,
|
||||
Pullables: "?",
|
||||
|
||||
@@ -19,6 +19,11 @@ func NewDummyOSCommand() *OSCommand {
|
||||
|
||||
// NewDummyAppConfig creates a new dummy AppConfig for testing
|
||||
func NewDummyAppConfig() *config.AppConfig {
|
||||
userConfig := viper.New()
|
||||
userConfig.SetConfigType("yaml")
|
||||
if err := config.LoadDefaults(userConfig, config.GetDefaultConfig()); err != nil {
|
||||
panic(err)
|
||||
}
|
||||
appConfig := &config.AppConfig{
|
||||
Name: "lazygit",
|
||||
Version: "unversioned",
|
||||
@@ -26,7 +31,7 @@ func NewDummyAppConfig() *config.AppConfig {
|
||||
BuildDate: "",
|
||||
Debug: false,
|
||||
BuildSource: "",
|
||||
UserConfig: viper.New(),
|
||||
UserConfig: userConfig,
|
||||
}
|
||||
_ = yaml.Unmarshal([]byte{}, appConfig.AppState)
|
||||
return appConfig
|
||||
|
||||
+18
-1
@@ -85,6 +85,9 @@ type GitCommand struct {
|
||||
DotGitDir string
|
||||
onSuccessfulContinue func() error
|
||||
PatchManager *PatchManager
|
||||
|
||||
// Push to current determines whether the user has configured to push to the remote branch of the same name as the current or not
|
||||
PushToCurrent bool
|
||||
}
|
||||
|
||||
// NewGitCommand it runs git commands
|
||||
@@ -92,6 +95,15 @@ func NewGitCommand(log *logrus.Entry, osCommand *OSCommand, tr *i18n.Localizer,
|
||||
var worktree *gogit.Worktree
|
||||
var repo *gogit.Repository
|
||||
|
||||
// see what our default push behaviour is
|
||||
output, err := osCommand.RunCommandWithOutput("git config --get push.default")
|
||||
pushToCurrent := false
|
||||
if err != nil {
|
||||
log.Errorf("error reading git config: %v", err)
|
||||
} else {
|
||||
pushToCurrent = strings.TrimSpace(output) == "current"
|
||||
}
|
||||
|
||||
fs := []func() error{
|
||||
func() error {
|
||||
return verifyInGitRepo(osCommand.RunCommand)
|
||||
@@ -128,6 +140,7 @@ func NewGitCommand(log *logrus.Entry, osCommand *OSCommand, tr *i18n.Localizer,
|
||||
getLocalGitConfig: gitconfig.Local,
|
||||
removeFile: os.RemoveAll,
|
||||
DotGitDir: dotGitDir,
|
||||
PushToCurrent: pushToCurrent,
|
||||
}
|
||||
|
||||
gitCommand.PatchManager = NewPatchManager(log, gitCommand.ApplyPatch)
|
||||
@@ -622,7 +635,11 @@ func (c *GitCommand) ShowCmdStr(sha string, filterPath string) string {
|
||||
}
|
||||
|
||||
func (c *GitCommand) GetBranchGraphCmdStr(branchName string) string {
|
||||
return fmt.Sprintf("git log --graph --color=always --abbrev-commit --decorate --date=relative --pretty=medium %s --", branchName)
|
||||
branchLogCmdTemplate := c.Config.GetUserConfig().GetString("git.branchLogCmd")
|
||||
templateValues := map[string]string{
|
||||
"branchName": branchName,
|
||||
}
|
||||
return utils.ResolvePlaceholderString(branchLogCmdTemplate, templateValues)
|
||||
}
|
||||
|
||||
// GetRemoteURL returns current repo remote url
|
||||
|
||||
@@ -1387,10 +1387,8 @@ func TestGitCommandGetBranchGraph(t *testing.T) {
|
||||
gitCmd.OSCommand.command = func(cmd string, args ...string) *exec.Cmd {
|
||||
assert.EqualValues(t, "git", cmd)
|
||||
assert.EqualValues(t, []string{"log", "--graph", "--color=always", "--abbrev-commit", "--decorate", "--date=relative", "--pretty=medium", "test", "--"}, args)
|
||||
|
||||
return exec.Command("echo")
|
||||
}
|
||||
|
||||
_, err := gitCmd.GetBranchGraph("test")
|
||||
assert.NoError(t, err)
|
||||
}
|
||||
@@ -1410,7 +1408,7 @@ func TestGitCommandDiff(t *testing.T) {
|
||||
"Default case",
|
||||
func(cmd string, args ...string) *exec.Cmd {
|
||||
assert.EqualValues(t, "git", cmd)
|
||||
assert.EqualValues(t, []string{"diff", "--color=", "--", "test.txt"}, args)
|
||||
assert.EqualValues(t, []string{"diff", "--color=always", "--", "test.txt"}, args)
|
||||
|
||||
return exec.Command("echo")
|
||||
},
|
||||
@@ -1426,7 +1424,7 @@ func TestGitCommandDiff(t *testing.T) {
|
||||
"cached",
|
||||
func(cmd string, args ...string) *exec.Cmd {
|
||||
assert.EqualValues(t, "git", cmd)
|
||||
assert.EqualValues(t, []string{"diff", "--color=", "--cached", "--", "test.txt"}, args)
|
||||
assert.EqualValues(t, []string{"diff", "--color=always", "--cached", "--", "test.txt"}, args)
|
||||
|
||||
return exec.Command("echo")
|
||||
},
|
||||
@@ -1458,7 +1456,7 @@ func TestGitCommandDiff(t *testing.T) {
|
||||
"File not tracked and file has no staged changes",
|
||||
func(cmd string, args ...string) *exec.Cmd {
|
||||
assert.EqualValues(t, "git", cmd)
|
||||
assert.EqualValues(t, []string{"diff", "--color=", "--no-index", "/dev/null", "test.txt"}, args)
|
||||
assert.EqualValues(t, []string{"diff", "--color=always", "--no-index", "/dev/null", "test.txt"}, args)
|
||||
|
||||
return exec.Command("echo")
|
||||
},
|
||||
|
||||
+4
-3
@@ -132,11 +132,12 @@ func (c *OSCommand) DetectUnamePass(command string, ask func(string) string) err
|
||||
ttyText = ttyText + " " + word
|
||||
|
||||
prompts := map[string]string{
|
||||
"password": `Password\s*for\s*'.+':`,
|
||||
"username": `Username\s*for\s*'.+':`,
|
||||
`.+'s password:`: "password",
|
||||
`Password\s*for\s*'.+':`: "password",
|
||||
`Username\s*for\s*'.+':`: "username",
|
||||
}
|
||||
|
||||
for askFor, pattern := range prompts {
|
||||
for pattern, askFor := range prompts {
|
||||
if match, _ := regexp.MatchString(pattern, ttyText); match {
|
||||
ttyText = ""
|
||||
return ask(askFor)
|
||||
|
||||
@@ -120,7 +120,7 @@ func coloredString(colorAttr color.Attribute, str string, selected bool, include
|
||||
var cl *color.Color
|
||||
attributes := []color.Attribute{colorAttr}
|
||||
if selected {
|
||||
attributes = append(attributes, theme.SelectedLineBgColor)
|
||||
attributes = append(attributes, theme.SelectedRangeBgColor)
|
||||
}
|
||||
cl = color.New(attributes...)
|
||||
var clIncluded *color.Color
|
||||
|
||||
@@ -256,7 +256,9 @@ func GetDefaultConfig() []byte {
|
||||
optionsTextColor:
|
||||
- blue
|
||||
selectedLineBgColor:
|
||||
- bold
|
||||
- default
|
||||
selectedRangeBgColor:
|
||||
- blue
|
||||
commitLength:
|
||||
show: true
|
||||
git:
|
||||
@@ -268,6 +270,7 @@ git:
|
||||
args: ""
|
||||
skipHookPrefix: 'WIP'
|
||||
autoFetch: true
|
||||
branchLogCmd: "git log --graph --color=always --abbrev-commit --decorate --date=relative --pretty=medium {{branchName}} --"
|
||||
update:
|
||||
method: prompt # can be: prompt | background | never
|
||||
days: 14 # how often a update is checked for
|
||||
|
||||
+7
-22
@@ -398,25 +398,6 @@ func (gui *Gui) refreshStateFiles() error {
|
||||
return nil
|
||||
}
|
||||
|
||||
func (gui *Gui) catSelectedFile(g *gocui.Gui) (string, error) {
|
||||
item, err := gui.getSelectedFile()
|
||||
if err != nil {
|
||||
if err != gui.Errors.ErrNoFiles {
|
||||
return "", err
|
||||
}
|
||||
return "", gui.newStringTask("main", gui.Tr.SLocalize("NoFilesDisplay"))
|
||||
}
|
||||
if item.Type != "file" {
|
||||
return "", gui.newStringTask("main", gui.Tr.SLocalize("NotAFile"))
|
||||
}
|
||||
cat, err := gui.GitCommand.CatFile(item.Name)
|
||||
if err != nil {
|
||||
gui.Log.Error(err)
|
||||
return "", gui.newStringTask("main", err.Error())
|
||||
}
|
||||
return cat, nil
|
||||
}
|
||||
|
||||
func (gui *Gui) handlePullFiles(g *gocui.Gui, v *gocui.View) error {
|
||||
// if we have no upstream branch we need to set that first
|
||||
currentBranch := gui.currentBranch()
|
||||
@@ -497,9 +478,13 @@ func (gui *Gui) pushFiles(g *gocui.Gui, v *gocui.View) error {
|
||||
}
|
||||
}
|
||||
|
||||
return gui.createPromptPanel(g, v, gui.Tr.SLocalize("EnterUpstream"), "origin "+currentBranch.Name, func(g *gocui.Gui, v *gocui.View) error {
|
||||
return gui.pushWithForceFlag(g, v, false, gui.trimmedContent(v), "")
|
||||
})
|
||||
if gui.GitCommand.PushToCurrent {
|
||||
return gui.pushWithForceFlag(g, v, false, "", "--set-upstream")
|
||||
} else {
|
||||
return gui.createPromptPanel(g, v, gui.Tr.SLocalize("EnterUpstream"), "origin "+currentBranch.Name, func(g *gocui.Gui, v *gocui.View) error {
|
||||
return gui.pushWithForceFlag(g, v, false, gui.trimmedContent(v), "")
|
||||
})
|
||||
}
|
||||
} else if currentBranch.Pullables == "0" {
|
||||
return gui.pushWithForceFlag(g, v, false, "", "")
|
||||
}
|
||||
|
||||
@@ -65,10 +65,18 @@ func (gui *Gui) scrollDownView(viewName string) error {
|
||||
}
|
||||
|
||||
func (gui *Gui) scrollUpMain(g *gocui.Gui, v *gocui.View) error {
|
||||
if gui.canScrollMergePanel() {
|
||||
gui.State.Panels.Merging.UserScrolling = true
|
||||
}
|
||||
|
||||
return gui.scrollUpView("main")
|
||||
}
|
||||
|
||||
func (gui *Gui) scrollDownMain(g *gocui.Gui, v *gocui.View) error {
|
||||
if gui.canScrollMergePanel() {
|
||||
gui.State.Panels.Merging.UserScrolling = true
|
||||
}
|
||||
|
||||
return gui.scrollDownView("main")
|
||||
}
|
||||
|
||||
|
||||
@@ -112,6 +112,10 @@ type mergingPanelState struct {
|
||||
ConflictTop bool
|
||||
Conflicts []commands.Conflict
|
||||
EditHistory *stack.Stack
|
||||
|
||||
// UserScrolling tells us if the user has started scrolling through the file themselves
|
||||
// in which case we won't auto-scroll to a conflict.
|
||||
UserScrolling bool
|
||||
}
|
||||
|
||||
type filePanelState struct {
|
||||
|
||||
@@ -1287,6 +1287,14 @@ func (gui *Gui) GetInitialKeybindings() []*Binding {
|
||||
Handler: gui.handleCheckoutRemoteBranch,
|
||||
Description: gui.Tr.SLocalize("checkout"),
|
||||
},
|
||||
{
|
||||
ViewName: "branches",
|
||||
Contexts: []string{"remote-branches"},
|
||||
Key: gui.getKey("universal.new"),
|
||||
Handler: gui.handleNewBranchOffRemote,
|
||||
Description: gui.Tr.SLocalize("newBranch"),
|
||||
},
|
||||
|
||||
{
|
||||
ViewName: "branches",
|
||||
Contexts: []string{"remote-branches"},
|
||||
|
||||
+2
-2
@@ -398,7 +398,7 @@ func (gui *Gui) layout(g *gocui.Gui) error {
|
||||
searchPrefixView.BgColor = gocui.ColorDefault
|
||||
searchPrefixView.FgColor = gocui.ColorGreen
|
||||
searchPrefixView.Frame = false
|
||||
gui.setViewContent(gui.g, searchPrefixView, searchPrefix)
|
||||
gui.setViewContent(searchPrefixView, searchPrefix)
|
||||
}
|
||||
|
||||
if searchView, err := g.SetView("search", appStatusOptionsBoundary-1+searchViewOffset+len(searchPrefix), height-2+searchViewOffset, optionsVersionBoundary+searchViewOffset, height+searchViewOffset, 0); err != nil {
|
||||
@@ -440,7 +440,7 @@ func (gui *Gui) layout(g *gocui.Gui) error {
|
||||
}
|
||||
}
|
||||
if gui.State.OldInformation != information {
|
||||
gui.setViewContent(g, informationView, information)
|
||||
gui.setViewContent(informationView, information)
|
||||
gui.State.OldInformation = information
|
||||
}
|
||||
|
||||
|
||||
@@ -88,7 +88,7 @@ func (gui *Gui) refreshLineByLinePanel(diff string, secondaryDiff string, second
|
||||
}
|
||||
|
||||
gui.g.Update(func(*gocui.Gui) error {
|
||||
gui.setViewContent(gui.g, gui.getSecondaryView(), secondaryPatchParser.Render(-1, -1, nil))
|
||||
gui.setViewContent(gui.getSecondaryView(), secondaryPatchParser.Render(-1, -1, nil))
|
||||
return nil
|
||||
})
|
||||
|
||||
@@ -242,7 +242,7 @@ func (gui *Gui) refreshMainView() error {
|
||||
mainView.Wrap = false
|
||||
|
||||
gui.g.Update(func(*gocui.Gui) error {
|
||||
gui.setViewContent(gui.g, gui.getMainView(), colorDiff)
|
||||
gui.setViewContent(gui.getMainView(), colorDiff)
|
||||
return nil
|
||||
})
|
||||
|
||||
|
||||
+59
-5
@@ -59,7 +59,7 @@ func (gui *Gui) coloredConflictFile(content string, conflicts []commands.Conflic
|
||||
colour := color.New(colourAttr)
|
||||
if hasFocus && conflictIndex < len(conflicts) && conflicts[conflictIndex] == conflict && gui.shouldHighlightLine(i, conflict, conflictTop) {
|
||||
colour.Add(color.Bold)
|
||||
colour.Add(theme.SelectedLineBgColor)
|
||||
colour.Add(theme.SelectedRangeBgColor)
|
||||
}
|
||||
if i == conflict.End && len(remainingConflicts) > 0 {
|
||||
conflict, remainingConflicts = gui.shiftConflict(remainingConflicts)
|
||||
@@ -69,17 +69,24 @@ func (gui *Gui) coloredConflictFile(content string, conflicts []commands.Conflic
|
||||
return outputBuffer.String(), nil
|
||||
}
|
||||
|
||||
func (gui *Gui) takeOverScrolling() {
|
||||
gui.State.Panels.Merging.UserScrolling = false
|
||||
}
|
||||
|
||||
func (gui *Gui) handleSelectTop(g *gocui.Gui, v *gocui.View) error {
|
||||
gui.takeOverScrolling()
|
||||
gui.State.Panels.Merging.ConflictTop = true
|
||||
return gui.refreshMergePanel()
|
||||
}
|
||||
|
||||
func (gui *Gui) handleSelectBottom(g *gocui.Gui, v *gocui.View) error {
|
||||
gui.takeOverScrolling()
|
||||
gui.State.Panels.Merging.ConflictTop = false
|
||||
return gui.refreshMergePanel()
|
||||
}
|
||||
|
||||
func (gui *Gui) handleSelectNextConflict(g *gocui.Gui, v *gocui.View) error {
|
||||
gui.takeOverScrolling()
|
||||
if gui.State.Panels.Merging.ConflictIndex >= len(gui.State.Panels.Merging.Conflicts)-1 {
|
||||
return nil
|
||||
}
|
||||
@@ -88,6 +95,7 @@ func (gui *Gui) handleSelectNextConflict(g *gocui.Gui, v *gocui.View) error {
|
||||
}
|
||||
|
||||
func (gui *Gui) handleSelectPrevConflict(g *gocui.Gui, v *gocui.View) error {
|
||||
gui.takeOverScrolling()
|
||||
if gui.State.Panels.Merging.ConflictIndex <= 0 {
|
||||
return nil
|
||||
}
|
||||
@@ -160,6 +168,8 @@ func (gui *Gui) handlePopFileSnapshot(g *gocui.Gui, v *gocui.View) error {
|
||||
}
|
||||
|
||||
func (gui *Gui) handlePickHunk(g *gocui.Gui, v *gocui.View) error {
|
||||
gui.takeOverScrolling()
|
||||
|
||||
conflict := gui.State.Panels.Merging.Conflicts[gui.State.Panels.Merging.ConflictIndex]
|
||||
if err := gui.pushFileSnapshot(g); err != nil {
|
||||
return err
|
||||
@@ -184,6 +194,8 @@ func (gui *Gui) handlePickHunk(g *gocui.Gui, v *gocui.View) error {
|
||||
}
|
||||
|
||||
func (gui *Gui) handlePickBothHunks(g *gocui.Gui, v *gocui.View) error {
|
||||
gui.takeOverScrolling()
|
||||
|
||||
conflict := gui.State.Panels.Merging.Conflicts[gui.State.Panels.Merging.ConflictIndex]
|
||||
if err := gui.pushFileSnapshot(g); err != nil {
|
||||
return err
|
||||
@@ -222,20 +234,44 @@ func (gui *Gui) refreshMergePanel() error {
|
||||
return err
|
||||
}
|
||||
|
||||
mainView := gui.getMainView()
|
||||
mainView.Wrap = false
|
||||
if err := gui.newStringTask("main", content); err != nil {
|
||||
if err := gui.scrollToConflict(gui.g); err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
if err := gui.scrollToConflict(gui.g); err != nil {
|
||||
mainView := gui.getMainView()
|
||||
mainView.Wrap = false
|
||||
|
||||
if err := gui.newStringTaskWithoutScroll("main", content); err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
func (gui *Gui) catSelectedFile(g *gocui.Gui) (string, error) {
|
||||
item, err := gui.getSelectedFile()
|
||||
if err != nil {
|
||||
if err != gui.Errors.ErrNoFiles {
|
||||
return "", err
|
||||
}
|
||||
return "", gui.newStringTask("main", gui.Tr.SLocalize("NoFilesDisplay"))
|
||||
}
|
||||
if item.Type != "file" {
|
||||
return "", gui.newStringTask("main", gui.Tr.SLocalize("NotAFile"))
|
||||
}
|
||||
cat, err := gui.GitCommand.CatFile(item.Name)
|
||||
if err != nil {
|
||||
gui.Log.Error(err)
|
||||
return "", gui.newStringTask("main", err.Error())
|
||||
}
|
||||
return cat, nil
|
||||
}
|
||||
|
||||
func (gui *Gui) scrollToConflict(g *gocui.Gui) error {
|
||||
if gui.State.Panels.Merging.UserScrolling {
|
||||
return nil
|
||||
}
|
||||
|
||||
panelState := gui.State.Panels.Merging
|
||||
if len(panelState.Conflicts) == 0 {
|
||||
return nil
|
||||
@@ -263,6 +299,8 @@ func (gui *Gui) renderMergeOptions() error {
|
||||
}
|
||||
|
||||
func (gui *Gui) handleEscapeMerge(g *gocui.Gui, v *gocui.View) error {
|
||||
gui.takeOverScrolling()
|
||||
|
||||
gui.State.Panels.Merging.EditHistory = stack.New()
|
||||
if err := gui.refreshSidePanels(refreshOptions{scope: []int{FILES}}); err != nil {
|
||||
return err
|
||||
@@ -296,7 +334,23 @@ func (gui *Gui) handleCompleteMerge() error {
|
||||
|
||||
// promptToContinue asks the user if they want to continue the rebase/merge that's in progress
|
||||
func (gui *Gui) promptToContinue() error {
|
||||
gui.takeOverScrolling()
|
||||
|
||||
return gui.createConfirmationPanel(gui.g, gui.getFilesView(), true, "continue", gui.Tr.SLocalize("ConflictsResolved"), func(g *gocui.Gui, v *gocui.View) error {
|
||||
return gui.genericMergeCommand("continue")
|
||||
}, nil)
|
||||
}
|
||||
|
||||
func (gui *Gui) canScrollMergePanel() bool {
|
||||
currentViewName := gui.currentViewName()
|
||||
if currentViewName != "main" {
|
||||
return false
|
||||
}
|
||||
|
||||
file, err := gui.getSelectedFile()
|
||||
if err != nil {
|
||||
return false
|
||||
}
|
||||
|
||||
return file.HasInlineMergeConflicts
|
||||
}
|
||||
|
||||
@@ -94,7 +94,7 @@ func (gui *Gui) refreshSecondaryPatchPanel() error {
|
||||
secondaryView.Wrap = false
|
||||
|
||||
gui.g.Update(func(*gocui.Gui) error {
|
||||
gui.setViewContent(gui.g, gui.getSecondaryView(), gui.GitCommand.PatchManager.RenderAggregatedPatchColored(false))
|
||||
gui.setViewContent(gui.getSecondaryView(), gui.GitCommand.PatchManager.RenderAggregatedPatchColored(false))
|
||||
return nil
|
||||
})
|
||||
} else {
|
||||
|
||||
@@ -139,3 +139,26 @@ func (gui *Gui) handleCreateResetToRemoteBranchMenu(g *gocui.Gui, v *gocui.View)
|
||||
|
||||
return gui.createResetMenu(fmt.Sprintf("%s/%s", selectedBranch.RemoteName, selectedBranch.Name))
|
||||
}
|
||||
|
||||
func (gui *Gui) handleNewBranchOffRemote(g *gocui.Gui, v *gocui.View) error {
|
||||
branch := gui.getSelectedRemoteBranch()
|
||||
if branch == nil {
|
||||
return nil
|
||||
}
|
||||
message := gui.Tr.TemplateLocalize(
|
||||
"NewBranchNameBranchOff",
|
||||
Teml{
|
||||
"branchName": branch.FullName(),
|
||||
},
|
||||
)
|
||||
return gui.createPromptPanel(g, v, message, branch.FullName(), func(g *gocui.Gui, v *gocui.View) error {
|
||||
if err := gui.GitCommand.NewBranch(gui.trimmedContent(v), branch.FullName()); err != nil {
|
||||
return gui.surfaceError(err)
|
||||
}
|
||||
gui.State.Panels.Branches.SelectedLine = 0
|
||||
if err := gui.switchBranchesPanelContext("local-branches"); err != nil {
|
||||
return err
|
||||
}
|
||||
return gui.refreshSidePanels(refreshOptions{mode: ASYNC})
|
||||
})
|
||||
}
|
||||
|
||||
@@ -42,7 +42,7 @@ func (gui *Gui) refreshStatus() {
|
||||
status += fmt.Sprintf("%s → %s ", repoName, name)
|
||||
|
||||
gui.g.Update(func(*gocui.Gui) error {
|
||||
gui.setViewContent(gui.g, gui.getStatusView(), status)
|
||||
gui.setViewContent(gui.getStatusView(), status)
|
||||
return nil
|
||||
})
|
||||
}
|
||||
|
||||
@@ -70,6 +70,26 @@ func (gui *Gui) newStringTask(viewName string, str string) error {
|
||||
return nil
|
||||
}
|
||||
|
||||
func (gui *Gui) newStringTaskWithoutScroll(viewName string, str string) error {
|
||||
view, err := gui.g.View(viewName)
|
||||
if err != nil {
|
||||
return nil // swallowing for now
|
||||
}
|
||||
|
||||
manager := gui.getManager(view)
|
||||
|
||||
f := func(stop chan struct{}) error {
|
||||
gui.setViewContent(view, str)
|
||||
return nil
|
||||
}
|
||||
|
||||
if err := manager.NewTask(f); err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
|
||||
func (gui *Gui) getManager(view *gocui.View) *tasks.ViewBufferManager {
|
||||
manager, ok := gui.viewBufferManagerMap[view.Name()]
|
||||
if !ok {
|
||||
|
||||
@@ -340,7 +340,7 @@ func (gui *Gui) cleanString(s string) string {
|
||||
return utils.NormalizeLinefeeds(output)
|
||||
}
|
||||
|
||||
func (gui *Gui) setViewContent(g *gocui.Gui, v *gocui.View, s string) {
|
||||
func (gui *Gui) setViewContent(v *gocui.View, s string) {
|
||||
v.Clear()
|
||||
fmt.Fprint(v, gui.cleanString(s))
|
||||
}
|
||||
@@ -358,7 +358,7 @@ func (gui *Gui) renderString(g *gocui.Gui, viewName, s string) {
|
||||
if err := v.SetCursor(0, 0); err != nil {
|
||||
return err
|
||||
}
|
||||
gui.setViewContent(gui.g, v, s)
|
||||
gui.setViewContent(v, s)
|
||||
return nil
|
||||
})
|
||||
}
|
||||
|
||||
@@ -24,6 +24,9 @@ var (
|
||||
// SelectedLineBgColor is the background color for the selected line
|
||||
SelectedLineBgColor color.Attribute
|
||||
|
||||
// SelectedRangeBgColor is the background color of the selected range of lines
|
||||
SelectedRangeBgColor color.Attribute
|
||||
|
||||
// GocuiSelectedLineBgColor is the background color for the selected line in gocui
|
||||
GocuiSelectedLineBgColor gocui.Attribute
|
||||
|
||||
@@ -39,6 +42,7 @@ func UpdateTheme(userConfig *viper.Viper) {
|
||||
ActiveBorderColor = GetGocuiColor(userConfig.GetStringSlice("gui.theme.activeBorderColor"))
|
||||
InactiveBorderColor = GetGocuiColor(userConfig.GetStringSlice("gui.theme.inactiveBorderColor"))
|
||||
SelectedLineBgColor = GetBgColor(userConfig.GetStringSlice("gui.theme.selectedLineBgColor"))
|
||||
SelectedRangeBgColor = GetBgColor(userConfig.GetStringSlice("gui.theme.selectedRangeBgColor"))
|
||||
GocuiSelectedLineBgColor = GetGocuiColor(userConfig.GetStringSlice("gui.theme.selectedLineBgColor"))
|
||||
OptionsColor = GetGocuiColor(userConfig.GetStringSlice("gui.theme.optionsTextColor"))
|
||||
OptionsFgColor = GetFgColor(userConfig.GetStringSlice("gui.theme.optionsTextColor"))
|
||||
|
||||
Reference in New Issue
Block a user