diff --git a/docs/Config.md b/docs/Config.md index 11fe29877..0cdc8ff83 100644 --- a/docs/Config.md +++ b/docs/Config.md @@ -319,26 +319,30 @@ gui: # Config relating to git git: + # Array of pagers. Each entry has the following format: + # + # # Value of the --color arg in the git diff command. Some pagers want + # # this to be set to 'always' and some want it set to 'never' + # colorArg: "always" + # + # # e.g. + # # diff-so-fancy + # # delta --dark --paging=never + # # ydiff -p cat -s --wrap --width={{columnWidth}} + # pager: "" + # + # # e.g. 'difft --color=always' + # externalDiffCommand: "" + # + # # If true, Lazygit will use git's `diff.external` config for paging. + # # The advantage over `externalDiffCommand` is that this can be + # # configured per file type in .gitattributes; see + # # https://git-scm.com/docs/gitattributes#_defining_an_external_diff_driver. + # useExternalDiffGitConfig: false + # # See https://github.com/jesseduffield/lazygit/blob/master/docs/Custom_Pagers.md - paging: - # Value of the --color arg in the git diff command. Some pagers want this to be - # set to 'always' and some want it set to 'never' - colorArg: always - - # e.g. - # diff-so-fancy - # delta --dark --paging=never - # ydiff -p cat -s --wrap --width={{columnWidth}} - pager: "" - - # e.g. 'difft --color=always' - externalDiffCommand: "" - - # If true, Lazygit will use git's `diff.external` config for paging. The - # advantage over `externalDiffCommand` is that this can be configured per file - # type in .gitattributes; see - # https://git-scm.com/docs/gitattributes#_defining_an_external_diff_driver. - useExternalDiffGitConfig: false + # for more information. + pagers: [] # Config relating to committing commit: @@ -638,6 +642,7 @@ keybinding: prevTab: '[' nextScreenMode: + prevScreenMode: _ + cyclePagers: '|' undo: z redo: Z filteringMenu: diff --git a/docs/Custom_Pagers.md b/docs/Custom_Pagers.md index 5e5d51372..c6616cecf 100644 --- a/docs/Custom_Pagers.md +++ b/docs/Custom_Pagers.md @@ -4,23 +4,27 @@ Lazygit supports custom pagers, [configured](/docs/Config.md) in the config.yml Support does not extend to Windows users, because we're making use of a package which doesn't have Windows support. However, see [below](#emulating-custom-pagers-on-windows) for a workaround. -## Default: +Multiple pagers are supported; you can cycle through them with the `|` key. This can be useful if you usually prefer a particular pager, but want to use a different one for certain kinds of diffs. + +Pagers are configured with the `pagers` array in the git section; here's an example for a multi-pager setup: ```yaml git: - paging: - colorArg: always + pagers: + - pager: delta --dark --paging=never + - pager: ydiff -p cat -s --wrap --width={{columnWidth}} + colorArg: never + - externalDiffCommand: difft --color=always ``` -the `colorArg` key is for whether you want the `--color=always` arg in your `git diff` command. Some pagers want it set to `always`, others want it set to `never`. +The `colorArg` key is for whether you want the `--color=always` arg in your `git diff` command. Some pagers want it set to `always`, others want it set to `never`. The default is `always`, since that's what most pagers need. ## Delta: ```yaml git: - paging: - colorArg: always - pager: delta --dark --paging=never + pagers: + - pager: delta --dark --paging=never ``` ![](https://i.imgur.com/QJpQkF3.png) @@ -31,9 +35,8 @@ A cool feature of delta is --hyperlinks, which renders clickable links for the l ```yaml git: - paging: - colorArg: always - pager: diff-so-fancy + pagers: + - pager: diff-so-fancy ``` ![](https://i.imgur.com/rjH1TpT.png) @@ -44,9 +47,9 @@ git: gui: sidePanelWidth: 0.2 # gives you more space to show things side-by-side git: - paging: - colorArg: never - pager: ydiff -p cat -s --wrap --width={{columnWidth}} + pagers: + - colorArg: never + pager: ydiff -p cat -s --wrap --width={{columnWidth}} ``` ![](https://i.imgur.com/vaa8z0H.png) @@ -61,8 +64,8 @@ These can be used in lazygit by using the `externalDiffCommand` config; in the c ```yaml git: - paging: - externalDiffCommand: difft --color=always + pagers: + - externalDiffCommand: difft --color=always ``` The `colorArg` and `pager` options are not used in this case. @@ -71,16 +74,16 @@ You can add whatever extra arguments you prefer for your difftool; for instance ```yaml git: - paging: - externalDiffCommand: difft --color=always --display=inline --syntax-highlight=off + pagers: + - externalDiffCommand: difft --color=always --display=inline --syntax-highlight=off ``` Instead of setting this command in lazygit's `externalDiffCommand` config, you can also tell lazygit to use the external diff command that is configured in git itself (`diff.external`), by using ```yaml git: - paging: - useExternalDiffGitConfig: true + pagers: + - useExternalDiffGitConfig: true ``` This can be useful if you also want to use it for diffs on the command line, and it also has the advantage that you can configure it per file type in `.gitattributes`; see https://git-scm.com/docs/gitattributes#_defining_an_external_diff_driver. @@ -106,8 +109,8 @@ In your lazygit config, use ```yml git: - paging: - externalDiffCommand: "C:/wherever/lazygit-pager.ps1" + pagers: + - externalDiffCommand: "C:/wherever/lazygit-pager.ps1" ``` The main limitation of this approach compared to a "real" pager is that renames are not displayed correctly; they are shown as if they were modifications of the old file. (This affects only the hunk headers; the diff itself is always correct.) diff --git a/docs/keybindings/Keybindings_en.md b/docs/keybindings/Keybindings_en.md index e42ebee1c..cf78b8574 100644 --- a/docs/keybindings/Keybindings_en.md +++ b/docs/keybindings/Keybindings_en.md @@ -24,6 +24,7 @@ _Legend: `` means ctrl+b, `` means alt+b, `B` means shift+b_ | `` R `` | Refresh | Refresh the git state (i.e. run `git status`, `git branch`, etc in background to update the contents of panels). This does not run `git fetch`. | | `` + `` | Next screen mode (normal/half/fullscreen) | | | `` _ `` | Prev screen mode | | +| `` | `` | Cycle pagers | Choose the next pager in the list of configured pagers | | `` `` | Cancel | | | `` ? `` | Open keybindings menu | | | `` `` | View filter options | View options for filtering the commit log, so that only commits matching the filter are shown. | diff --git a/docs/keybindings/Keybindings_ja.md b/docs/keybindings/Keybindings_ja.md index 207b0d397..198578d09 100644 --- a/docs/keybindings/Keybindings_ja.md +++ b/docs/keybindings/Keybindings_ja.md @@ -24,6 +24,7 @@ _凡例:`<c-b>` はctrl+b、`<a-b>` はalt+b、`B` はshift+bを意味 | `` R `` | 更新 | Gitの状態を更新します(`git status`、`git branch`などをバックグラウンドで実行してパネルの内容を更新します)。これは`git fetch`を実行しません。 | | `` + `` | 次の画面モード(通常/半分/全画面) | | | `` _ `` | 前の画面モード | | +| `` | `` | Cycle pagers | Choose the next pager in the list of configured pagers | | `` `` | キャンセル | | | `` ? `` | キーバインディングメニューを開く | | | `` `` | フィルターオプションを表示 | コミットログのフィルタリングオプションを表示し、フィルタに一致するコミットのみを表示します。 | diff --git a/docs/keybindings/Keybindings_ko.md b/docs/keybindings/Keybindings_ko.md index e0d83760a..5c4f1ad7b 100644 --- a/docs/keybindings/Keybindings_ko.md +++ b/docs/keybindings/Keybindings_ko.md @@ -24,6 +24,7 @@ _Legend: `` means ctrl+b, `` means alt+b, `B` means shift+b_ | `` R `` | 새로고침 | Refresh the git state (i.e. run `git status`, `git branch`, etc in background to update the contents of panels). This does not run `git fetch`. | | `` + `` | 다음 스크린 모드 (normal/half/fullscreen) | | | `` _ `` | 이전 스크린 모드 | | +| `` | `` | Cycle pagers | Choose the next pager in the list of configured pagers | | `` `` | 취소 | | | `` ? `` | 매뉴 열기 | | | `` `` | View filter-by-path options | View options for filtering the commit log, so that only commits matching the filter are shown. | diff --git a/docs/keybindings/Keybindings_nl.md b/docs/keybindings/Keybindings_nl.md index 9fea316a7..d74247d71 100644 --- a/docs/keybindings/Keybindings_nl.md +++ b/docs/keybindings/Keybindings_nl.md @@ -24,6 +24,7 @@ _Legend: `` means ctrl+b, `` means alt+b, `B` means shift+b_ | `` R `` | Verversen | Refresh the git state (i.e. run `git status`, `git branch`, etc in background to update the contents of panels). This does not run `git fetch`. | | `` + `` | Volgende scherm modus (normaal/half/groot) | | | `` _ `` | Vorige scherm modus | | +| `` | `` | Cycle pagers | Choose the next pager in the list of configured pagers | | `` `` | Annuleren | | | `` ? `` | Open menu | | | `` `` | Bekijk scoping opties | View options for filtering the commit log, so that only commits matching the filter are shown. | diff --git a/docs/keybindings/Keybindings_pl.md b/docs/keybindings/Keybindings_pl.md index 92b9c6388..5d5d53609 100644 --- a/docs/keybindings/Keybindings_pl.md +++ b/docs/keybindings/Keybindings_pl.md @@ -24,6 +24,7 @@ _Legenda: `` oznacza ctrl+b, `` oznacza alt+b, `B` oznacza shift+b_ | `` R `` | Odśwież | Odśwież stan git (tj. uruchom `git status`, `git branch`, itp. w tle, aby zaktualizować zawartość paneli). To nie uruchamia `git fetch`. | | `` + `` | Następny tryb ekranu (normalny/półpełny/pełnoekranowy) | | | `` _ `` | Poprzedni tryb ekranu | | +| `` | `` | Cycle pagers | Choose the next pager in the list of configured pagers | | `` `` | Anuluj | | | `` ? `` | Otwórz menu przypisań klawiszy | | | `` `` | Pokaż opcje filtrowania | Pokaż opcje filtrowania dziennika commitów, tak aby pokazywane były tylko commity pasujące do filtra. | diff --git a/docs/keybindings/Keybindings_pt.md b/docs/keybindings/Keybindings_pt.md index 1ae9178c1..34094ba2b 100644 --- a/docs/keybindings/Keybindings_pt.md +++ b/docs/keybindings/Keybindings_pt.md @@ -24,6 +24,7 @@ _Legend: `` means ctrl+b, `` means alt+b, `B` means shift+b_ | `` R `` | Atualizar | Atualize o estado do git (ou seja, execute `git status`, `git branch`, etc em segundo plano para atualizar o conteúdo de painéis). Isso não executa `git fetch`. | | `` + `` | Next screen mode (normal/half/fullscreen) | | | `` _ `` | Prev screen mode | | +| `` | `` | Cycle pagers | Choose the next pager in the list of configured pagers | | `` `` | Cancelar | | | `` ? `` | Open keybindings menu | | | `` `` | View filter options | View options for filtering the commit log, so that only commits matching the filter are shown. | diff --git a/docs/keybindings/Keybindings_ru.md b/docs/keybindings/Keybindings_ru.md index 4c46c5479..c1cd6f53c 100644 --- a/docs/keybindings/Keybindings_ru.md +++ b/docs/keybindings/Keybindings_ru.md @@ -24,6 +24,7 @@ _Связки клавиш_ | `` R `` | Обновить | Refresh the git state (i.e. run `git status`, `git branch`, etc in background to update the contents of panels). This does not run `git fetch`. | | `` + `` | Следующий режим экрана (нормальный/полуэкранный/полноэкранный) | | | `` _ `` | Предыдущий режим экрана | | +| `` | `` | Cycle pagers | Choose the next pager in the list of configured pagers | | `` `` | Отменить | | | `` ? `` | Открыть меню | | | `` `` | Просмотреть параметры фильтрации по пути | View options for filtering the commit log, so that only commits matching the filter are shown. | diff --git a/docs/keybindings/Keybindings_zh-CN.md b/docs/keybindings/Keybindings_zh-CN.md index ffc50aeda..799d7e511 100644 --- a/docs/keybindings/Keybindings_zh-CN.md +++ b/docs/keybindings/Keybindings_zh-CN.md @@ -24,6 +24,7 @@ _图例:`` 意味着ctrl+b, `意味着Alt+b, `B` 意味着shift+b_ | `` R `` | 刷新 | 刷新git状态(即在后台上运行`git status`,`git branch`等命令以更新面板内容) 不会运行`git fetch` | | `` + `` | 下一屏模式(正常/半屏/全屏) | | | `` _ `` | 上一屏模式 | | +| `` | `` | Cycle pagers | Choose the next pager in the list of configured pagers | | `` `` | 取消 | | | `` ? `` | 打开菜单 | | | `` `` | 查看按路径过滤选项 | 查看用于过滤提交日志的选项,以便仅显示与过滤器匹配的提交。 | diff --git a/docs/keybindings/Keybindings_zh-TW.md b/docs/keybindings/Keybindings_zh-TW.md index 2e7e58e7e..9c9f2e913 100644 --- a/docs/keybindings/Keybindings_zh-TW.md +++ b/docs/keybindings/Keybindings_zh-TW.md @@ -24,6 +24,7 @@ _說明:`` 表示 Ctrl+B、`` 表示 Alt+B,`B`表示 Shift+B | `` R `` | 重新整理 | Refresh the git state (i.e. run `git status`, `git branch`, etc in background to update the contents of panels). This does not run `git fetch`. | | `` + `` | 下一個螢幕模式(常規/半螢幕/全螢幕) | | | `` _ `` | 上一個螢幕模式 | | +| `` | `` | Cycle pagers | Choose the next pager in the list of configured pagers | | `` `` | 取消 | | | `` ? `` | 開啟選單 | | | `` `` | 檢視篩選路徑選項 | View options for filtering the commit log, so that only commits matching the filter are shown. | diff --git a/pkg/commands/git.go b/pkg/commands/git.go index 4aba9a7a8..90514cbd6 100644 --- a/pkg/commands/git.go +++ b/pkg/commands/git.go @@ -12,6 +12,7 @@ import ( "github.com/jesseduffield/lazygit/pkg/commands/oscommands" "github.com/jesseduffield/lazygit/pkg/commands/patch" "github.com/jesseduffield/lazygit/pkg/common" + "github.com/jesseduffield/lazygit/pkg/config" "github.com/jesseduffield/lazygit/pkg/utils" ) @@ -59,6 +60,7 @@ func NewGitCommand( version *git_commands.GitVersion, osCommand *oscommands.OSCommand, gitConfig git_config.IGitConfig, + pagerConfig *config.PagerConfig, ) (*GitCommand, error) { repoPaths, err := git_commands.GetRepoPaths(osCommand.Cmd, version) if err != nil { @@ -88,6 +90,7 @@ func NewGitCommand( gitConfig, repoPaths, repository, + pagerConfig, ), nil } @@ -98,6 +101,7 @@ func NewGitCommandAux( gitConfig git_config.IGitConfig, repoPaths *git_commands.RepoPaths, repo *gogit.Repository, + pagerConfig *config.PagerConfig, ) *GitCommand { cmd := NewGitCmdObjBuilder(cmn.Log, osCommand.Cmd) @@ -108,7 +112,7 @@ func NewGitCommandAux( // common ones are: cmn, osCommand, dotGitDir, configCommands configCommands := git_commands.NewConfigCommands(cmn, gitConfig, repo) - gitCommon := git_commands.NewGitCommon(cmn, version, cmd, osCommand, repoPaths, repo, configCommands) + gitCommon := git_commands.NewGitCommon(cmn, version, cmd, osCommand, repoPaths, repo, configCommands, pagerConfig) fileLoader := git_commands.NewFileLoader(gitCommon, cmd, configCommands) statusCommands := git_commands.NewStatusCommands(gitCommon) diff --git a/pkg/commands/git_commands/commit.go b/pkg/commands/git_commands/commit.go index 084a6c8d4..89063be82 100644 --- a/pkg/commands/git_commands/commit.go +++ b/pkg/commands/git_commands/commit.go @@ -256,14 +256,14 @@ func (self *CommitCommands) AmendHeadCmdObj() *oscommands.CmdObj { func (self *CommitCommands) ShowCmdObj(hash string, filterPaths []string) *oscommands.CmdObj { contextSize := self.UserConfig().Git.DiffContextSize - extDiffCmd := self.UserConfig().Git.Paging.ExternalDiffCommand - useExtDiffGitConfig := self.UserConfig().Git.Paging.UseExternalDiffGitConfig + extDiffCmd := self.pagerConfig.GetExternalDiffCommand() + useExtDiffGitConfig := self.pagerConfig.GetUseExternalDiffGitConfig() cmdArgs := NewGitCmd("show"). Config("diff.noprefix=false"). ConfigIf(extDiffCmd != "", "diff.external="+extDiffCmd). ArgIfElse(extDiffCmd != "" || useExtDiffGitConfig, "--ext-diff", "--no-ext-diff"). Arg("--submodule"). - Arg("--color="+self.UserConfig().Git.Paging.ColorArg). + Arg("--color="+self.pagerConfig.GetColorArg()). Arg(fmt.Sprintf("--unified=%d", contextSize)). Arg("--stat"). Arg("--decorate"). diff --git a/pkg/commands/git_commands/commit_test.go b/pkg/commands/git_commands/commit_test.go index 8460164cc..6ea914c64 100644 --- a/pkg/commands/git_commands/commit_test.go +++ b/pkg/commands/git_commands/commit_test.go @@ -255,8 +255,7 @@ func TestCommitShowCmdObj(t *testing.T) { contextSize uint64 similarityThreshold int ignoreWhitespace bool - extDiffCmd string - useExtDiffGitConfig bool + pagerConfig *config.PagingConfig expected []string } @@ -267,7 +266,7 @@ func TestCommitShowCmdObj(t *testing.T) { contextSize: 3, similarityThreshold: 50, ignoreWhitespace: false, - extDiffCmd: "", + pagerConfig: nil, expected: []string{"-C", "/path/to/worktree", "-c", "diff.noprefix=false", "show", "--no-ext-diff", "--submodule", "--color=always", "--unified=3", "--stat", "--decorate", "-p", "1234567890", "--find-renames=50%", "--"}, }, { @@ -276,7 +275,7 @@ func TestCommitShowCmdObj(t *testing.T) { contextSize: 3, similarityThreshold: 50, ignoreWhitespace: false, - extDiffCmd: "", + pagerConfig: nil, expected: []string{"-C", "/path/to/worktree", "-c", "diff.noprefix=false", "show", "--no-ext-diff", "--submodule", "--color=always", "--unified=3", "--stat", "--decorate", "-p", "1234567890", "--find-renames=50%", "--", "file.txt"}, }, { @@ -285,7 +284,7 @@ func TestCommitShowCmdObj(t *testing.T) { contextSize: 77, similarityThreshold: 50, ignoreWhitespace: false, - extDiffCmd: "", + pagerConfig: nil, expected: []string{"-C", "/path/to/worktree", "-c", "diff.noprefix=false", "show", "--no-ext-diff", "--submodule", "--color=always", "--unified=77", "--stat", "--decorate", "-p", "1234567890", "--find-renames=50%", "--"}, }, { @@ -294,7 +293,7 @@ func TestCommitShowCmdObj(t *testing.T) { contextSize: 3, similarityThreshold: 33, ignoreWhitespace: false, - extDiffCmd: "", + pagerConfig: nil, expected: []string{"-C", "/path/to/worktree", "-c", "diff.noprefix=false", "show", "--no-ext-diff", "--submodule", "--color=always", "--unified=3", "--stat", "--decorate", "-p", "1234567890", "--find-renames=33%", "--"}, }, { @@ -303,7 +302,7 @@ func TestCommitShowCmdObj(t *testing.T) { contextSize: 77, similarityThreshold: 50, ignoreWhitespace: true, - extDiffCmd: "", + pagerConfig: nil, expected: []string{"-C", "/path/to/worktree", "-c", "diff.noprefix=false", "show", "--no-ext-diff", "--submodule", "--color=always", "--unified=77", "--stat", "--decorate", "-p", "1234567890", "--ignore-all-space", "--find-renames=50%", "--"}, }, { @@ -312,7 +311,7 @@ func TestCommitShowCmdObj(t *testing.T) { contextSize: 3, similarityThreshold: 50, ignoreWhitespace: false, - extDiffCmd: "difft --color=always", + pagerConfig: &config.PagingConfig{ExternalDiffCommand: "difft --color=always"}, expected: []string{"-C", "/path/to/worktree", "-c", "diff.external=difft --color=always", "-c", "diff.noprefix=false", "show", "--ext-diff", "--submodule", "--color=always", "--unified=3", "--stat", "--decorate", "-p", "1234567890", "--find-renames=50%", "--"}, }, { @@ -321,7 +320,7 @@ func TestCommitShowCmdObj(t *testing.T) { contextSize: 3, similarityThreshold: 50, ignoreWhitespace: false, - useExtDiffGitConfig: true, + pagerConfig: &config.PagingConfig{UseExternalDiffGitConfig: true}, expected: []string{"-C", "/path/to/worktree", "-c", "diff.noprefix=false", "show", "--ext-diff", "--submodule", "--color=always", "--unified=3", "--stat", "--decorate", "-p", "1234567890", "--find-renames=50%", "--"}, }, } @@ -329,11 +328,12 @@ func TestCommitShowCmdObj(t *testing.T) { for _, s := range scenarios { t.Run(s.testName, func(t *testing.T) { userConfig := config.GetDefaultConfig() - userConfig.Git.Paging.ExternalDiffCommand = s.extDiffCmd + if s.pagerConfig != nil { + userConfig.Git.Pagers = []config.PagingConfig{*s.pagerConfig} + } userConfig.Git.IgnoreWhitespaceInDiffView = s.ignoreWhitespace userConfig.Git.DiffContextSize = s.contextSize userConfig.Git.RenameSimilarityThreshold = s.similarityThreshold - userConfig.Git.Paging.UseExternalDiffGitConfig = s.useExtDiffGitConfig runner := oscommands.NewFakeRunner(t).ExpectGitArgs(s.expected, "", nil) repoPaths := RepoPaths{ diff --git a/pkg/commands/git_commands/common.go b/pkg/commands/git_commands/common.go index b9537165c..28dd78e8b 100644 --- a/pkg/commands/git_commands/common.go +++ b/pkg/commands/git_commands/common.go @@ -4,16 +4,18 @@ import ( gogit "github.com/jesseduffield/go-git/v5" "github.com/jesseduffield/lazygit/pkg/commands/oscommands" "github.com/jesseduffield/lazygit/pkg/common" + "github.com/jesseduffield/lazygit/pkg/config" ) type GitCommon struct { *common.Common - version *GitVersion - cmd oscommands.ICmdObjBuilder - os *oscommands.OSCommand - repoPaths *RepoPaths - repo *gogit.Repository - config *ConfigCommands + version *GitVersion + cmd oscommands.ICmdObjBuilder + os *oscommands.OSCommand + repoPaths *RepoPaths + repo *gogit.Repository + config *ConfigCommands + pagerConfig *config.PagerConfig } func NewGitCommon( @@ -24,14 +26,16 @@ func NewGitCommon( repoPaths *RepoPaths, repo *gogit.Repository, config *ConfigCommands, + pagerConfig *config.PagerConfig, ) *GitCommon { return &GitCommon{ - Common: cmn, - version: version, - cmd: cmd, - os: osCommand, - repoPaths: repoPaths, - repo: repo, - config: config, + Common: cmn, + version: version, + cmd: cmd, + os: osCommand, + repoPaths: repoPaths, + repo: repo, + config: config, + pagerConfig: pagerConfig, } } diff --git a/pkg/commands/git_commands/config.go b/pkg/commands/git_commands/config.go index 1bed98985..fa6570356 100644 --- a/pkg/commands/git_commands/config.go +++ b/pkg/commands/git_commands/config.go @@ -1,15 +1,10 @@ package git_commands import ( - "os" - "strconv" - "strings" - gogit "github.com/jesseduffield/go-git/v5" "github.com/jesseduffield/go-git/v5/config" "github.com/jesseduffield/lazygit/pkg/commands/git_config" "github.com/jesseduffield/lazygit/pkg/common" - "github.com/jesseduffield/lazygit/pkg/utils" ) type ConfigCommands struct { @@ -31,26 +26,6 @@ func NewConfigCommands( } } -func (self *ConfigCommands) ConfiguredPager() string { - if os.Getenv("GIT_PAGER") != "" { - return os.Getenv("GIT_PAGER") - } - if os.Getenv("PAGER") != "" { - return os.Getenv("PAGER") - } - output := self.gitConfig.Get("core.pager") - return strings.Split(output, "\n")[0] -} - -func (self *ConfigCommands) GetPager(width int) string { - templateValues := map[string]string{ - "columnWidth": strconv.Itoa(width/2 - 6), - } - - pagerTemplate := string(self.UserConfig().Git.Paging.Pager) - return utils.ResolvePlaceholderString(pagerTemplate, templateValues) -} - type GpgConfigKey string const ( diff --git a/pkg/commands/git_commands/deps_test.go b/pkg/commands/git_commands/deps_test.go index a8fff5edd..3c4bd5a14 100644 --- a/pkg/commands/git_commands/deps_test.go +++ b/pkg/commands/git_commands/deps_test.go @@ -61,6 +61,10 @@ func buildGitCommon(deps commonDeps) *GitCommon { gitCommon.Common.SetUserConfig(config.GetDefaultConfig()) } + gitCommon.pagerConfig = config.NewPagerConfig(func() *config.UserConfig { + return gitCommon.Common.UserConfig() + }) + gitCommon.version = deps.gitVersion if gitCommon.version == nil { gitCommon.version = &GitVersion{2, 0, 0, ""} diff --git a/pkg/commands/git_commands/diff.go b/pkg/commands/git_commands/diff.go index 76b677884..4feeb4d7f 100644 --- a/pkg/commands/git_commands/diff.go +++ b/pkg/commands/git_commands/diff.go @@ -19,9 +19,9 @@ func NewDiffCommands(gitCommon *GitCommon) *DiffCommands { // This is for generating diffs to be shown in the UI (e.g. rendering a range // diff to the main view). It uses a custom pager if one is configured. func (self *DiffCommands) DiffCmdObj(diffArgs []string) *oscommands.CmdObj { - extDiffCmd := self.UserConfig().Git.Paging.ExternalDiffCommand + extDiffCmd := self.pagerConfig.GetExternalDiffCommand() useExtDiff := extDiffCmd != "" - useExtDiffGitConfig := self.UserConfig().Git.Paging.UseExternalDiffGitConfig + useExtDiffGitConfig := self.pagerConfig.GetUseExternalDiffGitConfig() ignoreWhitespace := self.UserConfig().Git.IgnoreWhitespaceInDiffView return self.cmd.New( @@ -30,7 +30,7 @@ func (self *DiffCommands) DiffCmdObj(diffArgs []string) *oscommands.CmdObj { ConfigIf(useExtDiff, "diff.external="+extDiffCmd). ArgIfElse(useExtDiff || useExtDiffGitConfig, "--ext-diff", "--no-ext-diff"). Arg("--submodule"). - Arg(fmt.Sprintf("--color=%s", self.UserConfig().Git.Paging.ColorArg)). + Arg(fmt.Sprintf("--color=%s", self.pagerConfig.GetColorArg())). ArgIf(ignoreWhitespace, "--ignore-all-space"). Arg(fmt.Sprintf("--unified=%d", self.UserConfig().Git.DiffContextSize)). Arg(diffArgs...). diff --git a/pkg/commands/git_commands/stash.go b/pkg/commands/git_commands/stash.go index f6b69ae7d..0e5eb299d 100644 --- a/pkg/commands/git_commands/stash.go +++ b/pkg/commands/git_commands/stash.go @@ -81,8 +81,8 @@ func (self *StashCommands) Hash(index int) (string, error) { } func (self *StashCommands) ShowStashEntryCmdObj(index int) *oscommands.CmdObj { - extDiffCmd := self.UserConfig().Git.Paging.ExternalDiffCommand - useExtDiffGitConfig := self.UserConfig().Git.Paging.UseExternalDiffGitConfig + extDiffCmd := self.pagerConfig.GetExternalDiffCommand() + useExtDiffGitConfig := self.pagerConfig.GetUseExternalDiffGitConfig() // "-u" is the same as "--include-untracked", but the latter fails in older git versions for some reason cmdArgs := NewGitCmd("stash").Arg("show"). @@ -91,7 +91,7 @@ func (self *StashCommands) ShowStashEntryCmdObj(index int) *oscommands.CmdObj { Arg("-u"). ConfigIf(extDiffCmd != "", "diff.external="+extDiffCmd). ArgIfElse(extDiffCmd != "" || useExtDiffGitConfig, "--ext-diff", "--no-ext-diff"). - Arg(fmt.Sprintf("--color=%s", self.UserConfig().Git.Paging.ColorArg)). + Arg(fmt.Sprintf("--color=%s", self.pagerConfig.GetColorArg())). Arg(fmt.Sprintf("--unified=%d", self.UserConfig().Git.DiffContextSize)). ArgIf(self.UserConfig().Git.IgnoreWhitespaceInDiffView, "--ignore-all-space"). Arg(fmt.Sprintf("--find-renames=%d%%", self.UserConfig().Git.RenameSimilarityThreshold)). diff --git a/pkg/commands/git_commands/stash_test.go b/pkg/commands/git_commands/stash_test.go index 6b21c0b83..a942a4e98 100644 --- a/pkg/commands/git_commands/stash_test.go +++ b/pkg/commands/git_commands/stash_test.go @@ -103,8 +103,7 @@ func TestStashStashEntryCmdObj(t *testing.T) { contextSize uint64 similarityThreshold int ignoreWhitespace bool - extDiffCmd string - useExtDiffGitConfig bool + pagerConfig *config.PagingConfig expected []string } @@ -139,7 +138,7 @@ func TestStashStashEntryCmdObj(t *testing.T) { contextSize: 3, similarityThreshold: 50, ignoreWhitespace: false, - extDiffCmd: "difft --color=always", + pagerConfig: &config.PagingConfig{ExternalDiffCommand: "difft --color=always"}, expected: []string{"git", "-C", "/path/to/worktree", "-c", "diff.external=difft --color=always", "stash", "show", "-p", "--stat", "-u", "--ext-diff", "--color=always", "--unified=3", "--find-renames=50%", "refs/stash@{5}"}, }, { @@ -148,7 +147,7 @@ func TestStashStashEntryCmdObj(t *testing.T) { contextSize: 3, similarityThreshold: 50, ignoreWhitespace: false, - useExtDiffGitConfig: true, + pagerConfig: &config.PagingConfig{UseExternalDiffGitConfig: true}, expected: []string{"git", "-C", "/path/to/worktree", "stash", "show", "-p", "--stat", "-u", "--ext-diff", "--color=always", "--unified=3", "--find-renames=50%", "refs/stash@{5}"}, }, { @@ -167,8 +166,9 @@ func TestStashStashEntryCmdObj(t *testing.T) { userConfig.Git.IgnoreWhitespaceInDiffView = s.ignoreWhitespace userConfig.Git.DiffContextSize = s.contextSize userConfig.Git.RenameSimilarityThreshold = s.similarityThreshold - userConfig.Git.Paging.ExternalDiffCommand = s.extDiffCmd - userConfig.Git.Paging.UseExternalDiffGitConfig = s.useExtDiffGitConfig + if s.pagerConfig != nil { + userConfig.Git.Pagers = []config.PagingConfig{*s.pagerConfig} + } repoPaths := RepoPaths{ worktreePath: "/path/to/worktree", } diff --git a/pkg/commands/git_commands/working_tree.go b/pkg/commands/git_commands/working_tree.go index ffa1d99b6..1cba0d511 100644 --- a/pkg/commands/git_commands/working_tree.go +++ b/pkg/commands/git_commands/working_tree.go @@ -258,7 +258,7 @@ func (self *WorkingTreeCommands) WorktreeFileDiff(file *models.File, plain bool, } func (self *WorkingTreeCommands) WorktreeFileDiffCmdObj(node models.IFile, plain bool, cached bool) *oscommands.CmdObj { - colorArg := self.UserConfig().Git.Paging.ColorArg + colorArg := self.pagerConfig.GetColorArg() if plain { colorArg = "never" } @@ -266,9 +266,9 @@ func (self *WorkingTreeCommands) WorktreeFileDiffCmdObj(node models.IFile, plain contextSize := self.UserConfig().Git.DiffContextSize prevPath := node.GetPreviousPath() noIndex := !node.GetIsTracked() && !node.GetHasStagedChanges() && !cached && node.GetIsFile() - extDiffCmd := self.UserConfig().Git.Paging.ExternalDiffCommand + extDiffCmd := self.pagerConfig.GetExternalDiffCommand() useExtDiff := extDiffCmd != "" && !plain - useExtDiffGitConfig := self.UserConfig().Git.Paging.UseExternalDiffGitConfig && !plain + useExtDiffGitConfig := self.pagerConfig.GetUseExternalDiffGitConfig() && !plain cmdArgs := NewGitCmd("diff"). ConfigIf(useExtDiff, "diff.external="+extDiffCmd). @@ -299,14 +299,14 @@ func (self *WorkingTreeCommands) ShowFileDiff(from string, to string, reverse bo func (self *WorkingTreeCommands) ShowFileDiffCmdObj(from string, to string, reverse bool, fileName string, plain bool) *oscommands.CmdObj { contextSize := self.UserConfig().Git.DiffContextSize - colorArg := self.UserConfig().Git.Paging.ColorArg + colorArg := self.pagerConfig.GetColorArg() if plain { colorArg = "never" } - extDiffCmd := self.UserConfig().Git.Paging.ExternalDiffCommand + extDiffCmd := self.pagerConfig.GetExternalDiffCommand() useExtDiff := extDiffCmd != "" && !plain - useExtDiffGitConfig := self.UserConfig().Git.Paging.UseExternalDiffGitConfig && !plain + useExtDiffGitConfig := self.pagerConfig.GetUseExternalDiffGitConfig() && !plain cmdArgs := NewGitCmd("diff"). Config("diff.noprefix=false"). diff --git a/pkg/config/app_config.go b/pkg/config/app_config.go index dde4b5382..8205f7ef6 100644 --- a/pkg/config/app_config.go +++ b/pkg/config/app_config.go @@ -310,6 +310,11 @@ func computeMigratedConfig(path string, content []byte, changes *ChangesSet) ([] return nil, false, fmt.Errorf("Couldn't migrate config file at `%s`: %w", path, err) } + err = migratePagers(&rootNode, changes) + if err != nil { + return nil, false, fmt.Errorf("Couldn't migrate config file at `%s`: %w", path, err) + } + // Add more migrations here... if reflect.DeepEqual(rootNode, originalCopy) { @@ -469,6 +474,37 @@ func migrateAllBranchesLogCmd(rootNode *yaml.Node, changes *ChangesSet) error { }) } +func migratePagers(rootNode *yaml.Node, changes *ChangesSet) error { + return yaml_utils.TransformNode(rootNode, []string{"git"}, func(gitNode *yaml.Node) error { + pagingKeyNode, pagingValueNode := yaml_utils.LookupKey(gitNode, "paging") + if pagingKeyNode == nil || pagingValueNode.Kind != yaml.MappingNode { + // If there's no "paging" section (or it's not an object), there's nothing to do + return nil + } + + pagersKeyNode, _ := yaml_utils.LookupKey(gitNode, "pagers") + if pagersKeyNode != nil { + // Conversely, if there *is* already a "pagers" array, we also have nothing to do. + // This covers the case where the user keeps both the "paging" section and the "pagers" + // array for the sake of easier testing of old versions. + return nil + } + + pagingKeyNode.Value = "pagers" + pagingContentCopy := pagingValueNode.Content + pagingValueNode.Kind = yaml.SequenceNode + pagingValueNode.Tag = "!!seq" + pagingValueNode.Content = []*yaml.Node{{ + Kind: yaml.MappingNode, + Content: pagingContentCopy, + }} + + changes.Add("Moved git.paging object to git.pagers array") + + return nil + }) +} + func (c *AppConfig) GetDebug() bool { return c.debug } diff --git a/pkg/config/app_config_test.go b/pkg/config/app_config_test.go index cc7ffea79..1109256a9 100644 --- a/pkg/config/app_config_test.go +++ b/pkg/config/app_config_test.go @@ -1089,3 +1089,98 @@ func TestAllBranchesLogCmdMigrations(t *testing.T) { }) } } + +func TestPagerMigration(t *testing.T) { + scenarios := []struct { + name string + input string + expected string + expectedDidChange bool + expectedChanges []string + }{ + { + name: "Incomplete Configuration Passes uneventfully", + input: "git:", + expectedDidChange: false, + expectedChanges: []string{}, + }, + { + name: "No paging section", + input: `git: + autoFetch: true +`, + expected: `git: + autoFetch: true +`, + expectedDidChange: false, + expectedChanges: []string{}, + }, + { + name: "Both paging and pagers exist", + input: `git: + paging: + pager: delta --dark --paging=never + pagers: + - diff: diff-so-fancy +`, + expected: `git: + paging: + pager: delta --dark --paging=never + pagers: + - diff: diff-so-fancy +`, + expectedDidChange: false, + expectedChanges: []string{}, + }, + { + name: "paging is not an object", + input: `git: + paging: 5 +`, + expected: `git: + paging: 5 +`, + expectedDidChange: false, + expectedChanges: []string{}, + }, + { + name: "paging is moved to pagers array (keeping the order)", + input: `git: + paging: + pager: delta --dark --paging=never + autoFetch: true +`, + expected: `git: + pagers: + - pager: delta --dark --paging=never + autoFetch: true +`, + expectedDidChange: true, + expectedChanges: []string{"Moved git.paging object to git.pagers array"}, + }, + { + name: "paging is moved to pagers array even if empty", + input: `git: + paging: {} +`, + expected: `git: + pagers: [{}] +`, + expectedDidChange: true, + expectedChanges: []string{"Moved git.paging object to git.pagers array"}, + }, + } + + for _, s := range scenarios { + t.Run(s.name, func(t *testing.T) { + changes := NewChangesSet() + actual, didChange, err := computeMigratedConfig("path doesn't matter", []byte(s.input), changes) + assert.NoError(t, err) + assert.Equal(t, s.expectedDidChange, didChange) + if didChange { + assert.Equal(t, s.expected, string(actual)) + } + assert.Equal(t, s.expectedChanges, changes.ToSliceFromOldest()) + }) + } +} diff --git a/pkg/config/pager_config.go b/pkg/config/pager_config.go new file mode 100644 index 000000000..e721da0e8 --- /dev/null +++ b/pkg/config/pager_config.go @@ -0,0 +1,82 @@ +package config + +import ( + "strconv" + + "github.com/jesseduffield/lazygit/pkg/utils" +) + +type PagerConfig struct { + getUserConfig func() *UserConfig + pagerIndex int +} + +func NewPagerConfig(getUserConfig func() *UserConfig) *PagerConfig { + return &PagerConfig{getUserConfig: getUserConfig} +} + +func (self *PagerConfig) currentPagerConfig() *PagingConfig { + pagers := self.getUserConfig().Git.Pagers + if len(pagers) == 0 { + return nil + } + + // Guard against the pager index being out of range, which can happen if the user + // has removed pagers from their config file while lazygit is running. + if self.pagerIndex >= len(pagers) { + self.pagerIndex = 0 + } + + return &pagers[self.pagerIndex] +} + +func (self *PagerConfig) GetPagerCommand(width int) string { + currentPagerConfig := self.currentPagerConfig() + if currentPagerConfig == nil { + return "" + } + + templateValues := map[string]string{ + "columnWidth": strconv.Itoa(width/2 - 6), + } + + pagerTemplate := string(currentPagerConfig.Pager) + return utils.ResolvePlaceholderString(pagerTemplate, templateValues) +} + +func (self *PagerConfig) GetColorArg() string { + currentPagerConfig := self.currentPagerConfig() + if currentPagerConfig == nil { + return "always" + } + + colorArg := currentPagerConfig.ColorArg + if colorArg == "" { + return "always" + } + return colorArg +} + +func (self *PagerConfig) GetExternalDiffCommand() string { + currentPagerConfig := self.currentPagerConfig() + if currentPagerConfig == nil { + return "" + } + return currentPagerConfig.ExternalDiffCommand +} + +func (self *PagerConfig) GetUseExternalDiffGitConfig() bool { + currentPagerConfig := self.currentPagerConfig() + if currentPagerConfig == nil { + return false + } + return currentPagerConfig.UseExternalDiffGitConfig +} + +func (self *PagerConfig) CyclePagers() { + self.pagerIndex = (self.pagerIndex + 1) % len(self.getUserConfig().Git.Pagers) +} + +func (self *PagerConfig) CurrentPagerIndex() (int, int) { + return self.pagerIndex, len(self.getUserConfig().Git.Pagers) +} diff --git a/pkg/config/user_config.go b/pkg/config/user_config.go index a951de2e2..6635ff06a 100644 --- a/pkg/config/user_config.go +++ b/pkg/config/user_config.go @@ -233,8 +233,30 @@ type SpinnerConfig struct { } type GitConfig struct { - // See https://github.com/jesseduffield/lazygit/blob/master/docs/Custom_Pagers.md - Paging PagingConfig `yaml:"paging"` + // Array of pagers. Each entry has the following format: + // [dev] The following documentation is duplicated from the PagingConfig struct below. + // + // # Value of the --color arg in the git diff command. Some pagers want + // # this to be set to 'always' and some want it set to 'never' + // colorArg: "always" + // + // # e.g. + // # diff-so-fancy + // # delta --dark --paging=never + // # ydiff -p cat -s --wrap --width={{columnWidth}} + // pager: "" + // + // # e.g. 'difft --color=always' + // externalDiffCommand: "" + // + // # If true, Lazygit will use git's `diff.external` config for paging. + // # The advantage over `externalDiffCommand` is that this can be + // # configured per file type in .gitattributes; see + // # https://git-scm.com/docs/gitattributes#_defining_an_external_diff_driver. + // useExternalDiffGitConfig: false + // + // See https://github.com/jesseduffield/lazygit/blob/master/docs/Custom_Pagers.md for more information. + Pagers []PagingConfig `yaml:"pagers"` // Config relating to committing Commit CommitConfig `yaml:"commit"` // Config relating to merging @@ -301,6 +323,7 @@ func (PagerType) JSONSchemaExtend(schema *jsonschema.Schema) { } } +// [dev] This documentation is duplicated in the GitConfig struct. If you make changes here, make them there too. type PagingConfig struct { // Value of the --color arg in the git diff command. Some pagers want this to be set to 'always' and some want it set to 'never' ColorArg string `yaml:"colorArg" jsonschema:"enum=always,enum=never"` @@ -441,6 +464,7 @@ type KeybindingUniversalConfig struct { PrevTab string `yaml:"prevTab"` NextScreenMode string `yaml:"nextScreenMode"` PrevScreenMode string `yaml:"prevScreenMode"` + CyclePagers string `yaml:"cyclePagers"` Undo string `yaml:"undo"` Redo string `yaml:"redo"` FilteringMenu string `yaml:"filteringMenu"` @@ -784,11 +808,6 @@ func GetDefaultConfig() *UserConfig { SwitchTabsWithPanelJumpKeys: false, }, Git: GitConfig{ - Paging: PagingConfig{ - ColorArg: "always", - Pager: "", - ExternalDiffCommand: "", - }, Commit: CommitConfig{ SignOff: false, AutoWrapCommitMessage: true, @@ -904,6 +923,7 @@ func GetDefaultConfig() *UserConfig { PrevTab: "[", NextScreenMode: "+", PrevScreenMode: "_", + CyclePagers: "|", Undo: "z", Redo: "Z", FilteringMenu: "", diff --git a/pkg/gui/controllers/global_controller.go b/pkg/gui/controllers/global_controller.go index 734e65516..1ae560685 100644 --- a/pkg/gui/controllers/global_controller.go +++ b/pkg/gui/controllers/global_controller.go @@ -1,6 +1,8 @@ package controllers import ( + "fmt" + "github.com/jesseduffield/gocui" "github.com/jesseduffield/lazygit/pkg/gui/types" ) @@ -58,6 +60,13 @@ func (self *GlobalController) GetKeybindings(opts types.KeybindingsOpts) []*type Handler: opts.Guards.NoPopupPanel(self.prevScreenMode), Description: self.c.Tr.PrevScreenMode, }, + { + Key: opts.GetKey(opts.Config.Universal.CyclePagers), + Handler: opts.Guards.NoPopupPanel(self.cyclePagers), + GetDisabledReason: self.canCyclePagers, + Description: self.c.Tr.CyclePagers, + Tooltip: self.c.Tr.CyclePagersTooltip, + }, { Key: opts.GetKey(opts.Config.Universal.Return), Modifier: gocui.ModNone, @@ -171,6 +180,27 @@ func (self *GlobalController) prevScreenMode() error { return (&ScreenModeActions{c: self.c}).Prev() } +func (self *GlobalController) cyclePagers() error { + self.c.State().GetPagerConfig().CyclePagers() + if self.c.Context().CurrentSide().GetKey() == self.c.Context().Current().GetKey() { + self.c.Context().CurrentSide().HandleFocus(types.OnFocusOpts{}) + } + + current, total := self.c.State().GetPagerConfig().CurrentPagerIndex() + self.c.Toast(fmt.Sprintf("Selected pager %d of %d", current+1, total)) + return nil +} + +func (self *GlobalController) canCyclePagers() *types.DisabledReason { + _, total := self.c.State().GetPagerConfig().CurrentPagerIndex() + if total <= 1 { + return &types.DisabledReason{ + Text: self.c.Tr.CyclePagersDisabledReason, + } + } + return nil +} + func (self *GlobalController) createOptionsMenu() error { return (&OptionsMenuAction{c: self.c}).Call() } diff --git a/pkg/gui/gui.go b/pkg/gui/gui.go index c9252e03d..2727df3c4 100644 --- a/pkg/gui/gui.go +++ b/pkg/gui/gui.go @@ -69,6 +69,8 @@ type Gui struct { // this is the state of the GUI for the current repo State *GuiRepoState + pagerConfig *config.PagerConfig + CustomCommandsClient *custom_commands.Client // this is a mapping of repos to gui states, so that we can restore the original @@ -169,6 +171,10 @@ func (self *StateAccessor) GetRepoState() types.IRepoStateAccessor { return self.gui.State } +func (self *StateAccessor) GetPagerConfig() *config.PagerConfig { + return self.gui.pagerConfig +} + func (self *StateAccessor) GetIsRefreshingFiles() bool { return self.gui.IsRefreshingFiles } @@ -307,6 +313,7 @@ func (gui *Gui) onNewRepo(startArgs appTypes.StartArgs, contextKey types.Context gui.gitVersion, gui.os, git_config.NewStdCachedGitConfig(gui.Log), + gui.pagerConfig, ) if err != nil { return err @@ -653,7 +660,7 @@ func (gui *Gui) Contexts() *context.ContextTree { // NewGui builds a new gui handler func NewGui( cmn *common.Common, - config config.AppConfigurer, + configurer config.AppConfigurer, gitVersion *git_commands.GitVersion, updater *updates.Updater, showRecentRepos bool, @@ -663,7 +670,7 @@ func NewGui( gui := &Gui{ Common: cmn, gitVersion: gitVersion, - Config: config, + Config: configurer, Updater: updater, statusManager: status.NewStatusManager(), viewBufferManagerMap: map[string]*tasks.ViewBufferManager{}, @@ -713,7 +720,7 @@ func NewGui( credentialsHelper.PromptUserForCredential, ) - osCommand := oscommands.NewOSCommand(cmn, config, oscommands.GetPlatform(), guiIO) + osCommand := oscommands.NewOSCommand(cmn, configurer, oscommands.GetPlatform(), guiIO) gui.os = osCommand @@ -724,6 +731,8 @@ func NewGui( gui.BackgroundRoutineMgr = &BackgroundRoutineMgr{gui: gui} gui.stateAccessor = &StateAccessor{gui: gui} + gui.pagerConfig = config.NewPagerConfig(func() *config.UserConfig { return gui.UserConfig() }) + return gui, nil } diff --git a/pkg/gui/pty.go b/pkg/gui/pty.go index 4253438bb..688240dff 100644 --- a/pkg/gui/pty.go +++ b/pkg/gui/pty.go @@ -45,8 +45,8 @@ func (gui *Gui) onResize() error { // command. func (gui *Gui) newPtyTask(view *gocui.View, cmd *exec.Cmd, prefix string) error { width := view.InnerWidth() - pager := gui.git.Config.GetPager(width) - externalDiffCommand := gui.Config.GetUserConfig().Git.Paging.ExternalDiffCommand + pager := gui.stateAccessor.GetPagerConfig().GetPagerCommand(width) + externalDiffCommand := gui.stateAccessor.GetPagerConfig().GetExternalDiffCommand() if pager == "" && externalDiffCommand == "" { // if we're not using a custom pager we don't need to use a pty @@ -58,7 +58,7 @@ func (gui *Gui) newPtyTask(view *gocui.View, cmd *exec.Cmd, prefix string) error // Need to get the width and the pager again because the layout might have // changed the size of the view width = view.InnerWidth() - pager = gui.git.Config.GetPager(width) + pager := gui.stateAccessor.GetPagerConfig().GetPagerCommand(width) cmdStr := strings.Join(cmd.Args, " ") diff --git a/pkg/gui/types/common.go b/pkg/gui/types/common.go index 6f7087d8e..905a9b65d 100644 --- a/pkg/gui/types/common.go +++ b/pkg/gui/types/common.go @@ -356,6 +356,7 @@ type HasUrn interface { type IStateAccessor interface { GetRepoPathStack() *utils.StringStack GetRepoState() IRepoStateAccessor + GetPagerConfig() *config.PagerConfig // tells us whether we're currently updating lazygit GetUpdating() bool SetUpdating(bool) diff --git a/pkg/i18n/english.go b/pkg/i18n/english.go index 30123efaa..86ba163aa 100644 --- a/pkg/i18n/english.go +++ b/pkg/i18n/english.go @@ -585,6 +585,9 @@ type TranslationSet struct { ViewResetToUpstreamOptions string NextScreenMode string PrevScreenMode string + CyclePagers string + CyclePagersTooltip string + CyclePagersDisabledReason string StartSearch string StartFilter string Keybindings string @@ -1678,6 +1681,9 @@ func EnglishTranslationSet() *TranslationSet { ViewResetToUpstreamOptions: "View upstream reset options", NextScreenMode: "Next screen mode (normal/half/fullscreen)", PrevScreenMode: "Prev screen mode", + CyclePagers: "Cycle pagers", + CyclePagersTooltip: "Choose the next pager in the list of configured pagers", + CyclePagersDisabledReason: "No other pagers configured", StartSearch: "Search the current view by text", StartFilter: "Filter the current view by text", KeybindingsLegend: "Legend: `` means ctrl+b, `` means alt+b, `B` means shift+b", diff --git a/schema/config.json b/schema/config.json index 19554058b..db86f4f00 100644 --- a/schema/config.json +++ b/schema/config.json @@ -285,9 +285,12 @@ }, "GitConfig": { "properties": { - "paging": { - "$ref": "#/$defs/PagingConfig", - "description": "See https://github.com/jesseduffield/lazygit/blob/master/docs/Custom_Pagers.md" + "pagers": { + "items": { + "$ref": "#/$defs/PagingConfig" + }, + "type": "array", + "description": "Array of pagers. Each entry has the following format:\n\n # Value of the --color arg in the git diff command. Some pagers want\n # this to be set to 'always' and some want it set to 'never'\n colorArg: \"always\"\n\n # e.g.\n # diff-so-fancy\n # delta --dark --paging=never\n # ydiff -p cat -s --wrap --width={{columnWidth}}\n pager: \"\"\n\n # e.g. 'difft --color=always'\n externalDiffCommand: \"\"\n\n # If true, Lazygit will use git's `diff.external` config for paging.\n # The advantage over `externalDiffCommand` is that this can be\n # configured per file type in .gitattributes; see\n # https://git-scm.com/docs/gitattributes#_defining_an_external_diff_driver.\n useExternalDiffGitConfig: false\n\nSee https://github.com/jesseduffield/lazygit/blob/master/docs/Custom_Pagers.md for more information." }, "commit": { "$ref": "#/$defs/CommitConfig", @@ -1464,6 +1467,10 @@ "type": "string", "default": "_" }, + "cyclePagers": { + "type": "string", + "default": "|" + }, "undo": { "type": "string", "default": "z" @@ -1667,13 +1674,11 @@ "always", "never" ], - "description": "Value of the --color arg in the git diff command. Some pagers want this to be set to 'always' and some want it set to 'never'", - "default": "always" + "description": "Value of the --color arg in the git diff command. Some pagers want this to be set to 'always' and some want it set to 'never'" }, "pager": { "type": "string", "description": "e.g.\ndiff-so-fancy\ndelta --dark --paging=never\nydiff -p cat -s --wrap --width={{columnWidth}}", - "default": "", "examples": [ "delta --dark --paging=never", "diff-so-fancy", @@ -1686,13 +1691,11 @@ }, "useExternalDiffGitConfig": { "type": "boolean", - "description": "If true, Lazygit will use git's `diff.external` config for paging. The advantage over `externalDiffCommand` is that this can be configured per file type in .gitattributes; see https://git-scm.com/docs/gitattributes#_defining_an_external_diff_driver.", - "default": false + "description": "If true, Lazygit will use git's `diff.external` config for paging. The advantage over `externalDiffCommand` is that this can be configured per file type in .gitattributes; see https://git-scm.com/docs/gitattributes#_defining_an_external_diff_driver." } }, "additionalProperties": false, - "type": "object", - "description": "See https://github.com/jesseduffield/lazygit/blob/master/docs/Custom_Pagers.md" + "type": "object" }, "RefresherConfig": { "properties": {