diff --git a/README.md b/README.md index c932ec8a..d63886ed 100644 --- a/README.md +++ b/README.md @@ -18,8 +18,8 @@ * Supports SSH access with each remote * GIT commands with GUI * Clone/Fetch/Pull/Push... - * Merge/Rebase/Reset/Revert/Amend/Cherry-pick... - * Amend/Reword + * Merge/Rebase/Reset/Revert/Cherry-pick... + * Amend/Reword/Squash * Interactive rebase * Branches * Remotes @@ -40,6 +40,7 @@ * Git LFS * Issue Link * Workspace +* Custom Action * Using AI to generate commit message (C# port of [anjerodev/commitollama](https://github.com/anjerodev/commitollama)) > [!WARNING] @@ -47,10 +48,7 @@ ## Translation Status -[![en_US](https://img.shields.io/badge/en__US-%E2%88%9A-brightgreen)](TRANSLATION.md) [![de__DE](https://img.shields.io/badge/de__DE-99.07%25-yellow)](TRANSLATION.md) [![es__ES](https://img.shields.io/badge/es__ES-%E2%88%9A-brightgreen)](TRANSLATION.md) [![fr__FR](https://img.shields.io/badge/fr__FR-91.66%25-yellow)](TRANSLATION.md) [![it__IT](https://img.shields.io/badge/it__IT-99.87%25-yellow)](TRANSLATION.md) [![pt__BR](https://img.shields.io/badge/pt__BR-91.39%25-yellow)](TRANSLATION.md) [![ru__RU](https://img.shields.io/badge/ru__RU-%E2%88%9A-brightgreen)](TRANSLATION.md) [![zh__CN](https://img.shields.io/badge/zh__CN-%E2%88%9A-brightgreen)](TRANSLATION.md) [![zh__TW](https://img.shields.io/badge/zh__TW-%E2%88%9A-brightgreen)](TRANSLATION.md) - -> [!NOTE] -> You can find the missing keys in [TRANSLATION.md](TRANSLATION.md) +You can find the current translation status in [TRANSLATION.md](TRANSLATION.md) ## How to Use @@ -201,3 +199,7 @@ dotnet run --project src/SourceGit.csproj Thanks to all the people who contribute. [![Contributors](https://contrib.rocks/image?repo=sourcegit-scm/sourcegit&columns=20)](https://github.com/sourcegit-scm/sourcegit/graphs/contributors) + +## Third-Party Components + +For detailed license information, see [THIRD-PARTY-LICENSES.md](THIRD-PARTY-LICENSES.md). diff --git a/THIRD-PARTY-LICENSES.md b/THIRD-PARTY-LICENSES.md new file mode 100644 index 00000000..2338263c --- /dev/null +++ b/THIRD-PARTY-LICENSES.md @@ -0,0 +1,86 @@ +# Third-Party Licenses + +This project incorporates components from the following third parties: + +## Packages + +### AvaloniaUI + +- **Source**: https://github.com/AvaloniaUI/Avalonia +- **Version**: 11.2.5 +- **License**: MIT License +- **License Link**: https://github.com/AvaloniaUI/Avalonia/blob/master/licence.md + +### AvaloniaEdit + +- **Source**: https://github.com/AvaloniaUI/AvaloniaEdit +- **Version**: 11.2.0 +- **License**: MIT License +- **License Link**: https://github.com/AvaloniaUI/AvaloniaEdit/blob/master/LICENSE + +### LiveChartsCore.SkiaSharpView.Avalonia + +- **Source**: https://github.com/beto-rodriguez/LiveCharts2 +- **Version**: 2.0.0-rc5.4 +- **License**: MIT License +- **License Link**: https://github.com/beto-rodriguez/LiveCharts2/blob/master/LICENSE + +### TextMateSharp + +- **Source**: https://github.com/danipen/TextMateSharp +- **Version**: 1.0.66 +- **License**: MIT License +- **License Link**: https://github.com/danipen/TextMateSharp/blob/master/LICENSE.md + +### OpenAI .NET SDK + +- **Source**: https://github.com/openai/openai-dotnet +- **Version**: 2.2.0-beta2 +- **License**: MIT License +- **License Link**: https://github.com/openai/openai-dotnet/blob/main/LICENSE + +### Azure.AI.OpenAI + +- **Source**: https://github.com/Azure/azure-sdk-for-net +- **Version**: 2.2.0-beta2 +- **License**: MIT License +- **License Link**: https://github.com/Azure/azure-sdk-for-net/blob/main/LICENSE.txt + +## Fonts + +### JetBrainsMono + +- **Source**: https://github.com/JetBrains/JetBrainsMono +- **Commit**: v2.304 +- **License**: SIL Open Font License, Version 1.1 +- **License Link**: https://github.com/JetBrains/JetBrainsMono/blob/v2.304/OFL.txt + +## Grammar Files + +### haxe-TmLanguage + +- **Source**: https://github.com/vshaxe/haxe-TmLanguage +- **Commit**: ddad8b4c6d0781ac20be0481174ec1be772c5da5 +- **License**: MIT License +- **License Link**: https://github.com/vshaxe/haxe-TmLanguage/blob/ddad8b4c6d0781ac20be0481174ec1be772c5da5/LICENSE.md + +### coc-toml + +- **Source**: https://github.com/kkiyama117/coc-toml +- **Commit**: aac3e0c65955c03314b2733041b19f903b7cc447 +- **License**: MIT License +- **License Link**: https://github.com/kkiyama117/coc-toml/blob/aac3e0c65955c03314b2733041b19f903b7cc447/LICENSE + +### eclipse-buildship + +- **Source**: https://github.com/eclipse/buildship +- **Commit**: 6bb773e7692f913dec27105129ebe388de34e68b +- **License**: Eclipse Public License 1.0 +- **License Link**: https://github.com/eclipse-buildship/buildship/blob/6bb773e7692f913dec27105129ebe388de34e68b/README.md + +### vscode-jsp-lang + +- **Source**: https://github.com/samuel-weinhardt/vscode-jsp-lang +- **Commit**: 0e89ecdb13650dbbe5a1e85b47b2e1530bf2f355 +- **License**: MIT License +- **License Link**: https://github.com/samuel-weinhardt/vscode-jsp-lang/blob/0e89ecdb13650dbbe5a1e85b47b2e1530bf2f355/LICENSE diff --git a/TRANSLATION.md b/TRANSLATION.md index e3f9d2a1..a96f0fc6 100644 --- a/TRANSLATION.md +++ b/TRANSLATION.md @@ -1,8 +1,15 @@ -### de_DE.axaml: 99.07% +# Translation Status +This document shows the translation status of each locale file in the repository. + +## Details + +### ![en_US](https://img.shields.io/badge/en__US-%E2%88%9A-brightgreen) + +### ![de__DE](https://img.shields.io/badge/de__DE-98.92%25-yellow)
-Missing Keys +Missing keys in de_DE.axaml - Text.BranchUpstreamInvalid - Text.Configure.CustomAction.WaitForExit @@ -10,107 +17,35 @@ - Text.Diff.Last - Text.Preferences.AI.Streaming - Text.Preferences.Appearance.EditorTabWidth +- Text.Preferences.General.ShowTagsInGraph - Text.StashCM.SaveAsPatch
-### es_ES.axaml: 100.00% - +### ![es__ES](https://img.shields.io/badge/es__ES-99.87%25-yellow)
-Missing Keys - +Missing keys in es_ES.axaml +- Text.Preferences.General.ShowTagsInGraph
-### fr_FR.axaml: 91.66% +### ![fr__FR](https://img.shields.io/badge/fr__FR-%E2%88%9A-brightgreen) +### ![it__IT](https://img.shields.io/badge/it__IT-99.87%25-yellow)
-Missing Keys +Missing keys in it_IT.axaml -- Text.AIAssistant.Regen -- Text.AIAssistant.Use -- Text.ApplyStash -- Text.ApplyStash.DropAfterApply -- Text.ApplyStash.RestoreIndex -- Text.ApplyStash.Stash -- Text.BranchCM.CustomAction -- Text.BranchUpstreamInvalid -- Text.Clone.RecurseSubmodules -- Text.Configure.CustomAction.Scope.Branch -- Text.Configure.CustomAction.WaitForExit -- Text.CreateBranch.Name.WarnSpace -- Text.DeleteRepositoryNode.Path -- Text.DeleteRepositoryNode.TipForGroup -- Text.DeleteRepositoryNode.TipForRepository -- Text.Diff.First -- Text.Diff.Last -- Text.InProgress.CherryPick.Head -- Text.InProgress.Merge.Operating -- Text.InProgress.Rebase.StoppedAt -- Text.InProgress.Revert.Head -- Text.Merge.Source -- Text.MergeMultiple -- Text.MergeMultiple.CommitChanges -- Text.MergeMultiple.Strategy -- Text.MergeMultiple.Targets -- Text.Preferences.AI.Streaming -- Text.Preferences.Appearance.EditorTabWidth -- Text.Preferences.Appearance.FontSize -- Text.Preferences.Appearance.FontSize.Default -- Text.Preferences.Appearance.FontSize.Editor -- Text.Preferences.General.DateFormat -- Text.Preferences.General.ShowChildren -- Text.Preferences.Git.SSLVerify -- Text.Repository.CustomActions -- Text.Repository.FilterCommits -- Text.Repository.FilterCommits.Default -- Text.Repository.FilterCommits.Exclude -- Text.Repository.FilterCommits.Include -- Text.Repository.HistoriesLayout -- Text.Repository.HistoriesLayout.Horizontal -- Text.Repository.HistoriesLayout.Vertical -- Text.Repository.HistoriesOrder -- Text.Repository.HistoriesOrder.ByDate -- Text.Repository.HistoriesOrder.Topo -- Text.Repository.Notifications.Clear -- Text.Repository.Skip -- Text.Repository.Tags.OrderByCreatorDate -- Text.Repository.Tags.OrderByNameAsc -- Text.Repository.Tags.OrderByNameDes -- Text.Repository.Tags.Sort -- Text.Repository.UseRelativeTimeInHistories -- Text.ScanRepositories -- Text.SetUpstream -- Text.SetUpstream.Local -- Text.SetUpstream.Unset -- Text.SetUpstream.Upstream -- Text.SHALinkCM.NavigateTo -- Text.Stash.AutoRestore -- Text.Stash.AutoRestore.Tip -- Text.StashCM.SaveAsPatch -- Text.WorkingCopy.CommitToEdit -- Text.WorkingCopy.SignOff +- Text.Preferences.General.ShowTagsInGraph
-### it_IT.axaml: 99.87% - +### ![pt__BR](https://img.shields.io/badge/pt__BR-91.12%25-yellow)
-Missing Keys - -- Text.Preferences.Appearance.EditorTabWidth - -
- -### pt_BR.axaml: 91.39% - - -
-Missing Keys +Missing keys in pt_BR.axaml - Text.AIAssistant.Regen - Text.AIAssistant.Use @@ -153,6 +88,7 @@ - Text.Preferences.Appearance.EditorTabWidth - Text.Preferences.General.DateFormat - Text.Preferences.General.ShowChildren +- Text.Preferences.General.ShowTagsInGraph - Text.Preferences.Git.SSLVerify - Text.Repository.FilterCommits - Text.Repository.HistoriesLayout @@ -180,32 +116,8 @@
-### ru_RU.axaml: 100.00% +### ![ru__RU](https://img.shields.io/badge/ru__RU-%E2%88%9A-brightgreen) +### ![zh__CN](https://img.shields.io/badge/zh__CN-%E2%88%9A-brightgreen) -
-Missing Keys - - - -
- -### zh_CN.axaml: 100.00% - - -
-Missing Keys - - - -
- -### zh_TW.axaml: 100.00% - - -
-Missing Keys - - - -
+### ![zh__TW](https://img.shields.io/badge/zh__TW-%E2%88%9A-brightgreen) \ No newline at end of file diff --git a/VERSION b/VERSION index 23993bfb..e78345d1 100644 --- a/VERSION +++ b/VERSION @@ -1 +1 @@ -2025.09 \ No newline at end of file +2025.10 \ No newline at end of file diff --git a/build/scripts/localization-check.js b/build/scripts/localization-check.js index ed89a5e8..1e8f1f0d 100644 --- a/build/scripts/localization-check.js +++ b/build/scripts/localization-check.js @@ -6,7 +6,6 @@ const repoRoot = path.join(__dirname, '../../'); const localesDir = path.join(repoRoot, 'src/Resources/Locales'); const enUSFile = path.join(localesDir, 'en_US.axaml'); const outputFile = path.join(repoRoot, 'TRANSLATION.md'); -const readmeFile = path.join(repoRoot, 'README.md'); const parser = new xml2js.Parser(); @@ -18,46 +17,36 @@ async function parseXml(filePath) { async function calculateTranslationRate() { const enUSData = await parseXml(enUSFile); const enUSKeys = new Set(enUSData.ResourceDictionary['x:String'].map(item => item.$['x:Key'])); - - const translationRates = []; - const badges = []; - const files = (await fs.readdir(localesDir)).filter(file => file !== 'en_US.axaml' && file.endsWith('.axaml')); - // Add en_US badge first - badges.push(`[![en_US](https://img.shields.io/badge/en__US-%E2%88%9A-brightgreen)](TRANSLATION.md)`); + const lines = []; + + lines.push('# Translation Status'); + lines.push('This document shows the translation status of each locale file in the repository.'); + lines.push(`## Details`); + lines.push(`### ![en_US](https://img.shields.io/badge/en__US-%E2%88%9A-brightgreen)`); for (const file of files) { + const locale = file.replace('.axaml', '').replace('_', '__'); const filePath = path.join(localesDir, file); const localeData = await parseXml(filePath); const localeKeys = new Set(localeData.ResourceDictionary['x:String'].map(item => item.$['x:Key'])); - const missingKeys = [...enUSKeys].filter(key => !localeKeys.has(key)); - const translationRate = ((enUSKeys.size - missingKeys.length) / enUSKeys.size) * 100; - translationRates.push(`### ${file}: ${translationRate.toFixed(2)}%\n`); - translationRates.push(`
\nMissing Keys\n\n${missingKeys.map(key => `- ${key}`).join('\n')}\n\n
`); + if (missingKeys.length > 0) { + const progress = ((enUSKeys.size - missingKeys.length) / enUSKeys.size) * 100; + const badgeColor = progress >= 75 ? 'yellow' : 'red'; - // Add badges - const locale = file.replace('.axaml', '').replace('_', '__'); - if (translationRate === 100) { - badges.push(`[![${locale}](https://img.shields.io/badge/${locale}-%E2%88%9A-brightgreen)](TRANSLATION.md)`); + lines.push(`### ![${locale}](https://img.shields.io/badge/${locale}-${progress.toFixed(2)}%25-${badgeColor})`); + lines.push(`
\nMissing keys in ${file}\n\n${missingKeys.map(key => `- ${key}`).join('\n')}\n\n
`) } else { - const badgeColor = translationRate >= 75 ? 'yellow' : 'red'; - badges.push(`[![${locale}](https://img.shields.io/badge/${locale}-${translationRate.toFixed(2)}%25-${badgeColor})](TRANSLATION.md)`); - } + lines.push(`### ![${locale}](https://img.shields.io/badge/${locale}-%E2%88%9A-brightgreen)`); + } } - console.log(translationRates.join('\n\n')); - - await fs.writeFile(outputFile, translationRates.join('\n\n') + '\n', 'utf8'); - - // Update README.md - let readmeContent = await fs.readFile(readmeFile, 'utf8'); - const badgeSection = `## Translation Status\n\n${badges.join(' ')}`; - console.log(badgeSection); - readmeContent = readmeContent.replace(/## Translation Status\n\n.*\n\n/, badgeSection + '\n\n'); - await fs.writeFile(readmeFile, readmeContent, 'utf8'); + const content = lines.join('\n\n'); + console.log(content); + await fs.writeFile(outputFile, content, 'utf8'); } calculateTranslationRate().catch(err => console.error(err)); diff --git a/src/App.axaml.cs b/src/App.axaml.cs index f59d35db..af5e6177 100644 --- a/src/App.axaml.cs +++ b/src/App.axaml.cs @@ -532,7 +532,7 @@ namespace SourceGit catch (Exception e) { if (manually) - ShowSelfUpdateResult(e); + ShowSelfUpdateResult(new Models.SelfUpdateFailed(e)); } }); } diff --git a/src/Commands/CompareRevisions.cs b/src/Commands/CompareRevisions.cs index 8a6f2832..e311a88e 100644 --- a/src/Commands/CompareRevisions.cs +++ b/src/Commands/CompareRevisions.cs @@ -6,7 +6,7 @@ namespace SourceGit.Commands { public partial class CompareRevisions : Command { - [GeneratedRegex(@"^(\s?[\w\?]{1,4})\s+(.+)$")] + [GeneratedRegex(@"^([MADRC])\s+(.+)$")] private static partial Regex REG_FORMAT(); public CompareRevisions(string repo, string start, string end) diff --git a/src/Commands/Config.cs b/src/Commands/Config.cs index 2fb83325..49e8fcb7 100644 --- a/src/Commands/Config.cs +++ b/src/Commands/Config.cs @@ -29,7 +29,7 @@ namespace SourceGit.Commands var rs = new Dictionary(); if (output.IsSuccess) { - var lines = output.StdOut.Split(new[] { '\r', '\n' }, StringSplitOptions.RemoveEmptyEntries); + var lines = output.StdOut.Split(['\r', '\n'], StringSplitOptions.RemoveEmptyEntries); foreach (var line in lines) { var idx = line.IndexOf('=', StringComparison.Ordinal); diff --git a/src/Commands/CountLocalChangesWithoutUntracked.cs b/src/Commands/CountLocalChangesWithoutUntracked.cs index 7ab9a54a..0ba508f8 100644 --- a/src/Commands/CountLocalChangesWithoutUntracked.cs +++ b/src/Commands/CountLocalChangesWithoutUntracked.cs @@ -16,7 +16,7 @@ namespace SourceGit.Commands var rs = ReadToEnd(); if (rs.IsSuccess) { - var lines = rs.StdOut.Split('\n', StringSplitOptions.RemoveEmptyEntries); + var lines = rs.StdOut.Split(['\r', '\n'], StringSplitOptions.RemoveEmptyEntries); return lines.Length; } diff --git a/src/Commands/LFS.cs b/src/Commands/LFS.cs index 2b7d1de4..f7e56486 100644 --- a/src/Commands/LFS.cs +++ b/src/Commands/LFS.cs @@ -82,7 +82,7 @@ namespace SourceGit.Commands var rs = cmd.ReadToEnd(); if (rs.IsSuccess) { - var lines = rs.StdOut.Split(new[] { '\n', '\r' }, StringSplitOptions.RemoveEmptyEntries); + var lines = rs.StdOut.Split(['\r', '\n'], StringSplitOptions.RemoveEmptyEntries); foreach (var line in lines) { var match = REG_LOCK().Match(line); diff --git a/src/Commands/QueryBranches.cs b/src/Commands/QueryBranches.cs index 44438cef..8dbc4055 100644 --- a/src/Commands/QueryBranches.cs +++ b/src/Commands/QueryBranches.cs @@ -24,7 +24,7 @@ namespace SourceGit.Commands if (!rs.IsSuccess) return branches; - var lines = rs.StdOut.Split('\n', StringSplitOptions.RemoveEmptyEntries); + var lines = rs.StdOut.Split(['\r', '\n'], StringSplitOptions.RemoveEmptyEntries); var remoteBranches = new HashSet(); foreach (var line in lines) { diff --git a/src/Commands/QueryCommitChildren.cs b/src/Commands/QueryCommitChildren.cs index 6a6ed909..31fb34f8 100644 --- a/src/Commands/QueryCommitChildren.cs +++ b/src/Commands/QueryCommitChildren.cs @@ -9,7 +9,7 @@ namespace SourceGit.Commands WorkingDirectory = repo; Context = repo; _commit = commit; - Args = $"rev-list -{max} --parents --branches --remotes --ancestry-path={commit} ^{commit}"; + Args = $"rev-list -{max} --parents --branches --remotes --ancestry-path ^{commit}"; } public List Result() diff --git a/src/Commands/QueryCommitFullMessage.cs b/src/Commands/QueryCommitFullMessage.cs index c8f1867d..36b6d1c7 100644 --- a/src/Commands/QueryCommitFullMessage.cs +++ b/src/Commands/QueryCommitFullMessage.cs @@ -6,7 +6,7 @@ namespace SourceGit.Commands { WorkingDirectory = repo; Context = repo; - Args = $"show --no-show-signature --pretty=format:%B -s {sha}"; + Args = $"show --no-show-signature --format=%B -s {sha}"; } public string Result() diff --git a/src/Commands/QueryCommitSignInfo.cs b/src/Commands/QueryCommitSignInfo.cs index 5c81cf57..133949af 100644 --- a/src/Commands/QueryCommitSignInfo.cs +++ b/src/Commands/QueryCommitSignInfo.cs @@ -7,7 +7,7 @@ WorkingDirectory = repo; Context = repo; - const string baseArgs = "show --no-show-signature --pretty=format:\"%G?%n%GS%n%GK\" -s"; + const string baseArgs = "show --no-show-signature --format=%G?%n%GS%n%GK -s"; const string fakeSignersFileArg = "-c gpg.ssh.allowedSignersFile=/dev/null"; Args = $"{(useFakeSignersFile ? fakeSignersFileArg : string.Empty)} {baseArgs} {sha}"; } @@ -18,7 +18,7 @@ if (!rs.IsSuccess) return null; - var raw = rs.StdOut.Trim(); + var raw = rs.StdOut.Trim().ReplaceLineEndings("\n"); if (raw.Length <= 1) return null; @@ -29,7 +29,6 @@ Signer = lines[1], Key = lines[2] }; - } } } diff --git a/src/Commands/QueryCommits.cs b/src/Commands/QueryCommits.cs index 312c068f..dd3c39b4 100644 --- a/src/Commands/QueryCommits.cs +++ b/src/Commands/QueryCommits.cs @@ -10,7 +10,7 @@ namespace SourceGit.Commands { WorkingDirectory = repo; Context = repo; - Args = $"log --no-show-signature --decorate=full --pretty=format:%H%n%P%n%D%n%aN±%aE%n%at%n%cN±%cE%n%ct%n%s {limits}"; + Args = $"log --no-show-signature --decorate=full --format=%H%n%P%n%D%n%aN±%aE%n%at%n%cN±%cE%n%ct%n%s {limits}"; _findFirstMerged = needFindHead; } @@ -35,7 +35,7 @@ namespace SourceGit.Commands var argsBuilder = new StringBuilder(); argsBuilder.Append(search); - var words = filter.Split(new[] { ' ', '\t', '\r' }, StringSplitOptions.RemoveEmptyEntries); + var words = filter.Split([' ', '\t', '\r'], StringSplitOptions.RemoveEmptyEntries); foreach (var word in words) { var escaped = word.Trim().Replace("\"", "\\\"", StringComparison.Ordinal); @@ -48,7 +48,7 @@ namespace SourceGit.Commands WorkingDirectory = repo; Context = repo; - Args = $"log -1000 --date-order --no-show-signature --decorate=full --pretty=format:%H%n%P%n%D%n%aN±%aE%n%at%n%cN±%cE%n%ct%n%s " + search; + Args = $"log -1000 --date-order --no-show-signature --decorate=full --format=%H%n%P%n%D%n%aN±%aE%n%at%n%cN±%cE%n%ct%n%s " + search; _findFirstMerged = false; } @@ -124,7 +124,7 @@ namespace SourceGit.Commands Args = $"log --since=\"{_commits[^1].CommitterTimeStr}\" --format=\"%H\""; var rs = ReadToEnd(); - var shas = rs.StdOut.Split('\n', StringSplitOptions.RemoveEmptyEntries); + var shas = rs.StdOut.Split(['\r', '\n'], StringSplitOptions.RemoveEmptyEntries); if (shas.Length == 0) return; diff --git a/src/Commands/QueryCommitsForInteractiveRebase.cs b/src/Commands/QueryCommitsForInteractiveRebase.cs index 232d86e5..615060a5 100644 --- a/src/Commands/QueryCommitsForInteractiveRebase.cs +++ b/src/Commands/QueryCommitsForInteractiveRebase.cs @@ -11,7 +11,7 @@ namespace SourceGit.Commands WorkingDirectory = repo; Context = repo; - Args = $"log --date-order --no-show-signature --decorate=full --pretty=format:\"%H%n%P%n%D%n%aN±%aE%n%at%n%cN±%cE%n%ct%n%B%n{_boundary}\" {on}..HEAD"; + Args = $"log --date-order --no-show-signature --decorate=full --format=\"%H%n%P%n%D%n%aN±%aE%n%at%n%cN±%cE%n%ct%n%B%n{_boundary}\" {on}..HEAD"; } public List Result() diff --git a/src/Commands/QueryGitCommonDir.cs b/src/Commands/QueryGitCommonDir.cs new file mode 100644 index 00000000..1076243e --- /dev/null +++ b/src/Commands/QueryGitCommonDir.cs @@ -0,0 +1,26 @@ +using System.IO; + +namespace SourceGit.Commands +{ + public class QueryGitCommonDir : Command + { + public QueryGitCommonDir(string workDir) + { + WorkingDirectory = workDir; + Args = "rev-parse --git-common-dir"; + RaiseError = false; + } + + public string Result() + { + var rs = ReadToEnd().StdOut; + if (string.IsNullOrEmpty(rs)) + return null; + + rs = rs.Trim(); + if (Path.IsPathRooted(rs)) + return rs; + return Path.GetFullPath(Path.Combine(WorkingDirectory, rs)); + } + } +} diff --git a/src/Commands/QueryRefsContainsCommit.cs b/src/Commands/QueryRefsContainsCommit.cs index 82e9b341..cabe1b50 100644 --- a/src/Commands/QueryRefsContainsCommit.cs +++ b/src/Commands/QueryRefsContainsCommit.cs @@ -20,7 +20,7 @@ namespace SourceGit.Commands if (!output.IsSuccess) return rs; - var lines = output.StdOut.Split('\n'); + var lines = output.StdOut.Split(['\r', '\n'], StringSplitOptions.RemoveEmptyEntries); foreach (var line in lines) { if (line.EndsWith("/HEAD", StringComparison.Ordinal)) diff --git a/src/Commands/QuerySingleCommit.cs b/src/Commands/QuerySingleCommit.cs index 1e1c9ea4..35289ec5 100644 --- a/src/Commands/QuerySingleCommit.cs +++ b/src/Commands/QuerySingleCommit.cs @@ -8,7 +8,7 @@ namespace SourceGit.Commands { WorkingDirectory = repo; Context = repo; - Args = $"show --no-show-signature --decorate=full --pretty=format:%H%n%P%n%D%n%aN±%aE%n%at%n%cN±%cE%n%ct%n%s -s {sha}"; + Args = $"show --no-show-signature --decorate=full --format=%H%n%P%n%D%n%aN±%aE%n%at%n%cN±%cE%n%ct%n%s -s {sha}"; } public Models.Commit Result() diff --git a/src/Commands/QueryStagedChangesWithAmend.cs b/src/Commands/QueryStagedChangesWithAmend.cs index f5c9659f..cfea5e35 100644 --- a/src/Commands/QueryStagedChangesWithAmend.cs +++ b/src/Commands/QueryStagedChangesWithAmend.cs @@ -24,7 +24,7 @@ namespace SourceGit.Commands if (rs.IsSuccess) { var changes = new List(); - var lines = rs.StdOut.Split('\n', StringSplitOptions.RemoveEmptyEntries); + var lines = rs.StdOut.Split(['\r', '\n'], StringSplitOptions.RemoveEmptyEntries); foreach (var line in lines) { var match = REG_FORMAT2().Match(line); diff --git a/src/Commands/QueryStashChanges.cs b/src/Commands/QueryStashChanges.cs new file mode 100644 index 00000000..7fc27ea3 --- /dev/null +++ b/src/Commands/QueryStashChanges.cs @@ -0,0 +1,68 @@ +using System; +using System.Collections.Generic; +using System.Text.RegularExpressions; + +namespace SourceGit.Commands +{ + /// + /// Query stash changes. Requires git >= 2.32.0 + /// + public partial class QueryStashChanges : Command + { + [GeneratedRegex(@"^([MADRC])\s+(.+)$")] + private static partial Regex REG_FORMAT(); + + public QueryStashChanges(string repo, string stash) + { + WorkingDirectory = repo; + Context = repo; + Args = $"stash show -u --name-status \"{stash}\""; + } + + public List Result() + { + var rs = ReadToEnd(); + if (!rs.IsSuccess) + return []; + + var lines = rs.StdOut.Split(['\r', '\n'], StringSplitOptions.RemoveEmptyEntries); + var outs = new List(); + foreach (var line in lines) + { + var match = REG_FORMAT().Match(line); + if (!match.Success) + continue; + + var change = new Models.Change() { Path = match.Groups[2].Value }; + var status = match.Groups[1].Value; + + switch (status[0]) + { + case 'M': + change.Set(Models.ChangeState.Modified); + outs.Add(change); + break; + case 'A': + change.Set(Models.ChangeState.Added); + outs.Add(change); + break; + case 'D': + change.Set(Models.ChangeState.Deleted); + outs.Add(change); + break; + case 'R': + change.Set(Models.ChangeState.Renamed); + outs.Add(change); + break; + case 'C': + change.Set(Models.ChangeState.Copied); + outs.Add(change); + break; + } + } + + outs.Sort((l, r) => string.Compare(l.Path, r.Path, StringComparison.Ordinal)); + return outs; + } + } +} diff --git a/src/Commands/QueryStashes.cs b/src/Commands/QueryStashes.cs index ccf601c5..dd5d10cc 100644 --- a/src/Commands/QueryStashes.cs +++ b/src/Commands/QueryStashes.cs @@ -9,7 +9,7 @@ namespace SourceGit.Commands { WorkingDirectory = repo; Context = repo; - Args = "stash list --pretty=format:%H%n%P%n%ct%n%gd%n%s"; + Args = "stash list --format=%H%n%P%n%ct%n%gd%n%s"; } public List Result() diff --git a/src/Commands/QuerySubmodules.cs b/src/Commands/QuerySubmodules.cs index 1ceccf78..6016b0be 100644 --- a/src/Commands/QuerySubmodules.cs +++ b/src/Commands/QuerySubmodules.cs @@ -26,7 +26,7 @@ namespace SourceGit.Commands var rs = ReadToEnd(); var builder = new StringBuilder(); - var lines = rs.StdOut.Split('\n', System.StringSplitOptions.RemoveEmptyEntries); + var lines = rs.StdOut.Split(['\r', '\n'], System.StringSplitOptions.RemoveEmptyEntries); foreach (var line in lines) { var match = REG_FORMAT1().Match(line); @@ -55,7 +55,7 @@ namespace SourceGit.Commands return submodules; var dirty = new HashSet(); - lines = rs.StdOut.Split('\n', System.StringSplitOptions.RemoveEmptyEntries); + lines = rs.StdOut.Split(['\r', '\n'], System.StringSplitOptions.RemoveEmptyEntries); foreach (var line in lines) { var match = REG_FORMAT_STATUS().Match(line); diff --git a/src/Commands/QueryTrackStatus.cs b/src/Commands/QueryTrackStatus.cs index 0bf9746f..e7e1f1c9 100644 --- a/src/Commands/QueryTrackStatus.cs +++ b/src/Commands/QueryTrackStatus.cs @@ -19,7 +19,7 @@ namespace SourceGit.Commands if (!rs.IsSuccess) return status; - var lines = rs.StdOut.Split(new char[] { '\n', '\r' }, StringSplitOptions.RemoveEmptyEntries); + var lines = rs.StdOut.Split(['\r', '\n'], StringSplitOptions.RemoveEmptyEntries); foreach (var line in lines) { if (line[0] == '>') diff --git a/src/Commands/Statistics.cs b/src/Commands/Statistics.cs index 511c43e8..1439cedd 100644 --- a/src/Commands/Statistics.cs +++ b/src/Commands/Statistics.cs @@ -8,7 +8,7 @@ namespace SourceGit.Commands { WorkingDirectory = repo; Context = repo; - Args = $"log --date-order --branches --remotes -{max} --pretty=format:\"%ct$%aN\""; + Args = $"log --date-order --branches --remotes -{max} --format=%ct$%aN"; } public Models.Statistics Result() diff --git a/src/Commands/Worktree.cs b/src/Commands/Worktree.cs index b73b8573..960d5501 100644 --- a/src/Commands/Worktree.cs +++ b/src/Commands/Worktree.cs @@ -21,7 +21,7 @@ namespace SourceGit.Commands var last = null as Models.Worktree; if (rs.IsSuccess) { - var lines = rs.StdOut.Split(new[] { '\r', '\n' }, StringSplitOptions.RemoveEmptyEntries); + var lines = rs.StdOut.Split(['\r', '\n'], StringSplitOptions.RemoveEmptyEntries); foreach (var line in lines) { if (line.StartsWith("worktree ", StringComparison.Ordinal)) diff --git a/src/Models/ApplyWhiteSpaceMode.cs b/src/Models/ApplyWhiteSpaceMode.cs index 6fbce0b2..aad45f57 100644 --- a/src/Models/ApplyWhiteSpaceMode.cs +++ b/src/Models/ApplyWhiteSpaceMode.cs @@ -2,14 +2,22 @@ { public class ApplyWhiteSpaceMode { + public static readonly ApplyWhiteSpaceMode[] Supported = + [ + new ApplyWhiteSpaceMode("No Warn", "Turns off the trailing whitespace warning", "nowarn"), + new ApplyWhiteSpaceMode("Warn", "Outputs warnings for a few such errors, but applies", "warn"), + new ApplyWhiteSpaceMode("Error", "Raise errors and refuses to apply the patch", "error"), + new ApplyWhiteSpaceMode("Error All", "Similar to 'error', but shows more", "error-all"), + ]; + public string Name { get; set; } public string Desc { get; set; } public string Arg { get; set; } public ApplyWhiteSpaceMode(string n, string d, string a) { - Name = App.Text(n); - Desc = App.Text(d); + Name = n; + Desc = d; Arg = a; } } diff --git a/src/Models/GitVersions.cs b/src/Models/GitVersions.cs index 394a9518..92fd8c59 100644 --- a/src/Models/GitVersions.cs +++ b/src/Models/GitVersions.cs @@ -13,13 +13,18 @@ public static readonly System.Version ADD_WITH_PATHSPECFILE = new System.Version(2, 25, 0); /// - /// The minimal version of Git that supports the `stash` command with the `--pathspec-from-file` option. + /// The minimal version of Git that supports the `stash push` command with the `--pathspec-from-file` option. /// - public static readonly System.Version STASH_WITH_PATHSPECFILE = new System.Version(2, 26, 0); + public static readonly System.Version STASH_PUSH_WITH_PATHSPECFILE = new System.Version(2, 26, 0); /// - /// The minimal version of Git that supports the `stash` command with the `--staged` option. + /// The minimal version of Git that supports the `stash push` command with the `--staged` option. /// - public static readonly System.Version STASH_ONLY_STAGED = new System.Version(2, 35, 0); + public static readonly System.Version STASH_PUSH_ONLY_STAGED = new System.Version(2, 35, 0); + + /// + /// The minimal version of Git that supports the `stash show` command with the `-u` option. + /// + public static readonly System.Version STASH_SHOW_WITH_UNTRACKED = new System.Version(2, 32, 0); } } diff --git a/src/Models/IRepository.cs b/src/Models/IRepository.cs index 12b1adba..0224d81f 100644 --- a/src/Models/IRepository.cs +++ b/src/Models/IRepository.cs @@ -2,9 +2,6 @@ { public interface IRepository { - string FullPath { get; set; } - string GitDir { get; set; } - void RefreshBranches(); void RefreshWorktrees(); void RefreshTags(); diff --git a/src/Models/MergeMode.cs b/src/Models/MergeMode.cs index 15e3f7e9..5dc70030 100644 --- a/src/Models/MergeMode.cs +++ b/src/Models/MergeMode.cs @@ -5,8 +5,9 @@ public static readonly MergeMode[] Supported = [ new MergeMode("Default", "Fast-forward if possible", ""), + new MergeMode("Fast-forward", "Refuse to merge when fast-forward is not possible", "--ff-only"), new MergeMode("No Fast-forward", "Always create a merge commit", "--no-ff"), - new MergeMode("Squash", "Use '--squash'", "--squash"), + new MergeMode("Squash", "Squash merge", "--squash"), new MergeMode("Don't commit", "Merge without commit", "--no-ff --no-commit"), ]; diff --git a/src/Models/Version.cs b/src/Models/SelfUpdate.cs similarity index 65% rename from src/Models/Version.cs rename to src/Models/SelfUpdate.cs index 35c21778..e02f80d8 100644 --- a/src/Models/Version.cs +++ b/src/Models/SelfUpdate.cs @@ -1,4 +1,5 @@ -using System.Reflection; +using System; +using System.Reflection; using System.Text.Json.Serialization; namespace SourceGit.Models @@ -32,5 +33,24 @@ namespace SourceGit.Models } } - public class AlreadyUpToDate { } + public class AlreadyUpToDate + { + } + + public class SelfUpdateFailed + { + public string Reason + { + get; + private set; + } + + public SelfUpdateFailed(Exception e) + { + if (e.InnerException is { } inner) + Reason = inner.Message; + else + Reason = e.Message; + } + } } diff --git a/src/Models/Stash.cs b/src/Models/Stash.cs index 8dca3bdb..257b6d33 100644 --- a/src/Models/Stash.cs +++ b/src/Models/Stash.cs @@ -10,7 +10,6 @@ namespace SourceGit.Models public List Parents { get; set; } = []; public ulong Time { get; set; } = 0; public string Message { get; set; } = ""; - public bool HasUntracked => Parents.Count == 3; public string TimeStr => DateTime.UnixEpoch.AddSeconds(Time).ToLocalTime().ToString(DateTimeFormat.Actived.DateTime); } diff --git a/src/Models/TextMateHelper.cs b/src/Models/TextMateHelper.cs index 0eb5e489..b7efae72 100644 --- a/src/Models/TextMateHelper.cs +++ b/src/Models/TextMateHelper.cs @@ -21,10 +21,11 @@ namespace SourceGit.Models { private static readonly ExtraGrammar[] s_extraGrammars = [ - new ExtraGrammar("source.toml", ".toml", "toml.json"), - new ExtraGrammar("source.kotlin", ".kotlin", "kotlin.json"), - new ExtraGrammar("source.hx", ".hx", "haxe.json"), - new ExtraGrammar("source.hxml", ".hxml", "hxml.json"), + new ExtraGrammar("source.toml", [".toml"], "toml.json"), + new ExtraGrammar("source.kotlin", [".kotlin", ".kt", ".kts"], "kotlin.json"), + new ExtraGrammar("source.hx", [".hx"], "haxe.json"), + new ExtraGrammar("source.hxml", [".hxml"], "hxml.json"), + new ExtraGrammar("text.html.jsp", [".jsp", ".jspf", ".tag"], "jsp.json"), ]; public static string GetScope(string file, RegistryOptions reg) @@ -36,13 +37,14 @@ namespace SourceGit.Models extension = ".xml"; else if (extension == ".command") extension = ".sh"; - else if (extension == ".kt" || extension == ".kts") - extension = ".kotlin"; foreach (var grammar in s_extraGrammars) { - if (grammar.Extension.Equals(extension, StringComparison.OrdinalIgnoreCase)) - return grammar.Scope; + foreach (var ext in grammar.Extensions) + { + if (ext.Equals(extension, StringComparison.OrdinalIgnoreCase)) + return grammar.Scope; + } } return reg.GetScopeByExtension(extension); @@ -71,10 +73,10 @@ namespace SourceGit.Models return reg.GetGrammar(scopeName); } - private record ExtraGrammar(string Scope, string Extension, string File) + private record ExtraGrammar(string Scope, List Extensions, string File) { public readonly string Scope = Scope; - public readonly string Extension = Extension; + public readonly List Extensions = Extensions; public readonly string File = File; } } diff --git a/src/Models/Watcher.cs b/src/Models/Watcher.cs index d0ccdea5..3ccecad4 100644 --- a/src/Models/Watcher.cs +++ b/src/Models/Watcher.cs @@ -8,12 +8,12 @@ namespace SourceGit.Models { public class Watcher : IDisposable { - public Watcher(IRepository repo) + public Watcher(IRepository repo, string fullpath, string gitDir) { _repo = repo; _wcWatcher = new FileSystemWatcher(); - _wcWatcher.Path = _repo.FullPath; + _wcWatcher.Path = fullpath; _wcWatcher.Filter = "*"; _wcWatcher.NotifyFilter = NotifyFilters.LastWrite | NotifyFilters.DirectoryName | NotifyFilters.FileName | NotifyFilters.Size | NotifyFilters.CreationTime; _wcWatcher.IncludeSubdirectories = true; @@ -23,15 +23,8 @@ namespace SourceGit.Models _wcWatcher.Deleted += OnWorkingCopyChanged; _wcWatcher.EnableRaisingEvents = true; - // If this repository is a worktree repository, just watch the main repository's gitdir. - var gitDirNormalized = _repo.GitDir.Replace("\\", "/"); - var worktreeIdx = gitDirNormalized.IndexOf(".git/worktrees/", StringComparison.Ordinal); - var repoWatchDir = _repo.GitDir; - if (worktreeIdx > 0) - repoWatchDir = _repo.GitDir.Substring(0, worktreeIdx + 4); - _repoWatcher = new FileSystemWatcher(); - _repoWatcher.Path = repoWatchDir; + _repoWatcher.Path = gitDir; _repoWatcher.Filter = "*"; _repoWatcher.NotifyFilter = NotifyFilters.LastWrite | NotifyFilters.DirectoryName | NotifyFilters.FileName; _repoWatcher.IncludeSubdirectories = true; diff --git a/src/Native/MacOS.cs b/src/Native/MacOS.cs index 123b160b..d7ef4701 100644 --- a/src/Native/MacOS.cs +++ b/src/Native/MacOS.cs @@ -31,7 +31,7 @@ namespace SourceGit.Native var env = File.ReadAllText(customPathFile).Trim(); if (!string.IsNullOrEmpty(env)) path = env; - } + } Environment.SetEnvironmentVariable("PATH", path); } diff --git a/src/Resources/Grammars/haxe.json b/src/Resources/Grammars/haxe.json index 12acc538..3f78154d 100644 --- a/src/Resources/Grammars/haxe.json +++ b/src/Resources/Grammars/haxe.json @@ -1,7 +1,9 @@ { "information_for_contributors": [ "This file has been copied from https://github.com/vshaxe/haxe-TmLanguage/blob/ddad8b4c6d0781ac20be0481174ec1be772c5da5/haxe.tmLanguage", - "and converted to JSON using https://marketplace.visualstudio.com/items?itemName=pedro-w.tmlanguage" + "and converted to JSON using https://marketplace.visualstudio.com/items?itemName=pedro-w.tmlanguage", + "The original file was licensed under the MIT License", + "https://github.com/vshaxe/haxe-TmLanguage/blob/ddad8b4c6d0781ac20be0481174ec1be772c5da5/LICENSE.md" ], "fileTypes": [ "hx", @@ -2485,4 +2487,4 @@ "name": "variable.other.hx" } } -} \ No newline at end of file +} diff --git a/src/Resources/Grammars/hxml.json b/src/Resources/Grammars/hxml.json index 829c403e..3be42577 100644 --- a/src/Resources/Grammars/hxml.json +++ b/src/Resources/Grammars/hxml.json @@ -1,7 +1,9 @@ { "information_for_contributors": [ "This file has been copied from https://github.com/vshaxe/haxe-TmLanguage/blob/ddad8b4c6d0781ac20be0481174ec1be772c5da5/hxml.tmLanguage", - "and converted to JSON using https://marketplace.visualstudio.com/items?itemName=pedro-w.tmlanguage" + "and converted to JSON using https://marketplace.visualstudio.com/items?itemName=pedro-w.tmlanguage", + "The original file was licensed under the MIT License", + "https://github.com/vshaxe/haxe-TmLanguage/blob/ddad8b4c6d0781ac20be0481174ec1be772c5da5/LICENSE.md" ], "fileTypes": [ "hxml" @@ -67,4 +69,4 @@ ], "scopeName": "source.hxml", "uuid": "CB1B853A-C4C8-42C3-BA70-1B1605BE51C1" -} \ No newline at end of file +} diff --git a/src/Resources/Grammars/jsp.json b/src/Resources/Grammars/jsp.json new file mode 100644 index 00000000..2fbfd97c --- /dev/null +++ b/src/Resources/Grammars/jsp.json @@ -0,0 +1,100 @@ +{ + "information_for_contributors": [ + "This file has been copied from https://github.com/samuel-weinhardt/vscode-jsp-lang/blob/0e89ecdb13650dbbe5a1e85b47b2e1530bf2f355/syntaxes/jsp.tmLanguage.json", + "The original file was licensed under the MIT License", + "https://github.com/samuel-weinhardt/vscode-jsp-lang/blob/0e89ecdb13650dbbe5a1e85b47b2e1530bf2f355/LICENSE" + ], + "$schema": "https://raw.githubusercontent.com/martinring/tmlanguage/master/tmlanguage.json", + "name": "Jakarta Server Pages", + "fileTypes": ["jsp", "jspf", "tag"], + "scopeName": "text.html.jsp", + "patterns": [ + { "include": "#comment" }, + { "include": "#directive" }, + { "include": "#expression" }, + { "include": "text.html.derivative" } + ], + "injections": { + "L:text.html.jsp -comment -meta.tag.directive.jsp -meta.tag.scriptlet.jsp": { + "patterns": [ + { "include": "#scriptlet" } + ], + "comment": "allow scriptlets anywhere except comments and nested" + }, + "L:meta.attribute (string.quoted.single.html | string.quoted.double.html) -string.template.expression.jsp": { + "patterns": [ + { "include": "#expression" }, + { "include": "text.html.derivative" } + ], + "comment": "allow expressions and tags within HTML attributes (not nested)" + } + }, + "repository": { + "comment": { + "name": "comment.block.jsp", + "begin": "<%--", + "end": "--%>" + }, + "directive": { + "name": "meta.tag.directive.jsp", + "begin": "(<)(%@)", + "end": "(%)(>)", + "beginCaptures": { + "1": { "name": "punctuation.definition.tag.jsp" }, + "2": { "name": "entity.name.tag.jsp" } + }, + "endCaptures": { + "1": { "name": "entity.name.tag.jsp" }, + "2": { "name": "punctuation.definition.tag.jsp" } + }, + "patterns": [ + { + "match": "\\b(attribute|include|page|tag|taglib|variable)\\b(?!\\s*=)", + "name": "keyword.control.directive.jsp" + }, + { "include": "text.html.basic#attribute" } + ] + }, + "scriptlet": { + "name": "meta.tag.scriptlet.jsp", + "contentName": "meta.embedded.block.java", + "begin": "(<)(%[\\s!=])", + "end": "(%)(>)", + "beginCaptures": { + "1": { "name": "punctuation.definition.tag.jsp" }, + "2": { "name": "entity.name.tag.jsp" } + }, + "endCaptures": { + "1": { "name": "entity.name.tag.jsp" }, + "2": { "name": "punctuation.definition.tag.jsp" } + }, + "patterns": [ + { + "match": "\\{(?=\\s*(%>|$))", + "comment": "consume trailing curly brackets for fragmented scriptlets" + }, + { "include": "source.java" } + ] + }, + "expression": { + "name": "string.template.expression.jsp", + "contentName": "meta.embedded.block.java", + "begin": "[$#]\\{", + "end": "\\}", + "beginCaptures": { + "0": { "name": "punctuation.definition.template-expression.begin.jsp" } + }, + "endCaptures": { + "0": { "name": "punctuation.definition.template-expression.end.jsp" } + }, + "patterns": [ + { "include": "#escape" }, + { "include": "source.java" } + ] + }, + "escape": { + "match": "\\\\.", + "name": "constant.character.escape.jsp" + } + } +} diff --git a/src/Resources/Grammars/kotlin.json b/src/Resources/Grammars/kotlin.json index e8f844d0..2857f717 100644 --- a/src/Resources/Grammars/kotlin.json +++ b/src/Resources/Grammars/kotlin.json @@ -1,6 +1,8 @@ { "information_for_contributors": [ - "This file has been copied from https://github.com/eclipse/buildship/blob/6bb773e7692f913dec27105129ebe388de34e68b/org.eclipse.buildship.kotlindsl.provider/kotlin.tmLanguage.json" + "This file has been copied from https://github.com/eclipse/buildship/blob/6bb773e7692f913dec27105129ebe388de34e68b/org.eclipse.buildship.kotlindsl.provider/kotlin.tmLanguage.json", + "The original file was licensed under the Eclipse Public License, Version 1.0", + "https://github.com/eclipse-buildship/buildship/blob/6bb773e7692f913dec27105129ebe388de34e68b/README.md" ], "$schema": "https://raw.githubusercontent.com/martinring/tmlanguage/master/tmlanguage.json", "name": "Kotlin", @@ -698,4 +700,4 @@ "name": "variable.language.this.kotlin" } } -} \ No newline at end of file +} diff --git a/src/Resources/Grammars/toml.json b/src/Resources/Grammars/toml.json index 86c2ef87..6be4678f 100644 --- a/src/Resources/Grammars/toml.json +++ b/src/Resources/Grammars/toml.json @@ -3,7 +3,10 @@ "scopeName": "source.toml", "uuid": "8b4e5008-c50d-11ea-a91b-54ee75aeeb97", "information_for_contributors": [ - "Originally was maintained by aster (galaster@foxmail.com). This notice is only kept here for the record, please don't send e-mails about bugs and other issues." + "Originally was maintained by aster (galaster@foxmail.com). This notice is only kept here for the record, please don't send e-mails about bugs and other issues.", + "This file has been copied from https://github.com/kkiyama117/coc-toml/blob/main/toml.tmLanguage.json", + "The original file was licensed under the MIT License", + "https://github.com/kkiyama117/coc-toml/blob/main/LICENSE" ], "patterns": [ { diff --git a/src/Resources/Icons.axaml b/src/Resources/Icons.axaml index 9426d20a..66589440 100644 --- a/src/Resources/Icons.axaml +++ b/src/Resources/Icons.axaml @@ -54,6 +54,7 @@ M939 94v710L512 998 85 805V94h-64A21 21 0 010 73v-0C0 61 10 51 21 51h981c12 0 21 10 21 21v0c0 12-10 21-21 21h-64zm-536 588L512 624l109 58c6 3 13 4 20 3a32 32 0 0026-37l-21-122 88-87c5-5 8-11 9-18a32 32 0 00-27-37l-122-18-54-111a32 32 0 00-57 0l-54 111-122 18c-7 1-13 4-18 9a33 33 0 001 46l88 87-21 122c-1 7-0 14 3 20a32 32 0 0043 14z M236 542a32 32 0 109 63l86-12a180 180 0 0022 78l-71 47a32 32 0 1035 53l75-50a176 176 0 00166 40L326 529zM512 16C238 16 16 238 16 512s222 496 496 496 496-222 496-496S786 16 512 16zm0 896c-221 0-400-179-400-400a398 398 0 0186-247l561 561A398 398 0 01512 912zm314-154L690 622a179 179 0 004-29l85 12a32 32 0 109-63l-94-13v-49l94-13a32 32 0 10-9-63l-87 12a180 180 0 00-20-62l71-47A32 32 0 10708 252l-75 50a181 181 0 00-252 10l-115-115A398 398 0 01512 112c221 0 400 179 400 400a398 398 0 01-86 247z M884 159l-18-18a43 43 0 00-38-12l-235 43a166 166 0 00-101 60L400 349a128 128 0 00-148 47l-120 171a21 21 0 005 29l17 12a128 128 0 00178-32l27-38 124 124-38 27a128 128 0 00-32 178l12 17a21 21 0 0029 5l171-120a128 128 0 0047-148l117-92A166 166 0 00853 431l43-235a43 43 0 00-12-38zm-177 249a64 64 0 110-90 64 64 0 010 90zm-373 312a21 21 0 010 30l-139 139a21 21 0 01-30 0l-30-30a21 21 0 010-30l139-139a21 21 0 0130 0z + M525 0C235 0 0 235 0 525c0 232 150 429 359 498 26 5 36-11 36-25 0-12-1-54-1-97-146 31-176-63-176-63-23-61-58-76-58-76-48-32 3-32 3-32 53 3 81 54 81 54 47 80 123 57 153 43 4-34 18-57 33-70-116-12-239-57-239-259 0-57 21-104 54-141-5-13-23-67 5-139 0 0 44-14 144 54 42-11 87-17 131-17s90 6 131 17C756 203 801 217 801 217c29 72 10 126 5 139 34 37 54 83 54 141 0 202-123 246-240 259 19 17 36 48 36 97 0 70-1 127-1 144 0 14 10 30 36 25 209-70 359-266 359-498C1050 235 814 0 525 0z M590 74 859 342V876c0 38-31 68-68 68H233c-38 0-68-31-68-68V142c0-38 31-68 68-68h357zm-12 28H233a40 40 0 00-40 38L193 142v734a40 40 0 0038 40L233 916h558a40 40 0 0040-38L831 876V354L578 102zM855 371h-215c-46 0-83-36-84-82l0-2V74h28v213c0 30 24 54 54 55l2 0h215v28zM57 489m28 0 853 0q28 0 28 28l0 284q0 28-28 28l-853 0q-28 0-28-28l0-284q0-28 28-28ZM157 717c15 0 29-6 37-13v-51h-41v22h17v18c-2 2-6 3-10 3-21 0-30-13-30-34 0-21 12-34 28-34 9 0 15 4 20 9l14-17C184 610 172 603 156 603c-29 0-54 21-54 57 0 37 24 56 54 56zM245 711v-108h-34v108h34zm69 0v-86H341V603H262v22h28V711h24zM393 711v-108h-34v108h34zm66 6c15 0 29-6 37-13v-51h-41v22h17v18c-2 2-6 3-10 3-21 0-30-13-30-34 0-21 12-34 28-34 9 0 15 4 20 9l14-17C485 610 474 603 458 603c-29 0-54 21-54 57 0 37 24 56 54 56zm88-6v-36c0-13-2-28-3-40h1l10 24 25 52H603v-108h-23v36c0 13 2 28 3 40h-1l-10-24L548 603H523v108h23zM677 717c30 0 51-22 51-57 0-36-21-56-51-56-30 0-51 20-51 56 0 36 21 57 51 57zm3-23c-16 0-26-12-26-32 0-19 10-31 26-31 16 0 26 11 26 31S696 694 680 694zm93 17v-38h13l21 38H836l-25-43c12-5 19-15 19-31 0-26-20-34-44-34H745v108h27zm16-51H774v-34h15c16 0 25 4 25 16s-9 18-25 18zM922 711v-22h-43v-23h35v-22h-35V625h41V603H853v108h68z M30 271l241 0 0-241-241 0 0 241zM392 271l241 0 0-241-241 0 0 241zM753 30l0 241 241 0 0-241-241 0zM30 632l241 0 0-241-241 0 0 241zM392 632l241 0 0-241-241 0 0 241zM753 632l241 0 0-241-241 0 0 241zM30 994l241 0 0-241-241 0 0 241zM392 994l241 0 0-241-241 0 0 241zM753 994l241 0 0-241-241 0 0 241z M0 512M1024 512M512 0M512 1024M955 323q0 23-16 39l-414 414-78 78q-16 16-39 16t-39-16l-78-78-207-207q-16-16-16-39t16-39l78-78q16-16 39-16t39 16l168 169 375-375q16-16 39-16t39 16l78 78q16 16 16 39z diff --git a/src/Resources/Locales/de_DE.axaml b/src/Resources/Locales/de_DE.axaml index aff8ffc5..7144ef43 100644 --- a/src/Resources/Locales/de_DE.axaml +++ b/src/Resources/Locales/de_DE.axaml @@ -4,11 +4,6 @@ Info Über SourceGit - • Erstellt mit - • Grafik gerendert durch - • Texteditor von - • Monospace-Schriftarten von - • Quelltext findest du auf Open Source & freier Git GUI Client Worktree hinzufügen Was auschecken: @@ -25,18 +20,10 @@ Verwende OpenAI, um Commit-Nachrichten zu generieren Als Commit-Nachricht verwenden Patch - Fehler - Fehler werfen und anwenden des Patches verweigern - Alle Fehler - Ähnlich wie 'Fehler', zeigt aber mehr an Patch-Datei: Wähle die anzuwendende .patch-Datei Ignoriere Leerzeichenänderungen - Keine Warnungen - Keine Warnung vor Leerzeichen am Zeilenende Patch anwenden - Warnen - Gibt eine Warnung für ein paar solcher Fehler aus, aber wendet es an Leerzeichen: Stash anwenden Nach dem Anwenden löschen @@ -509,7 +496,7 @@ Remote löschen Ziel: Worktrees löschen - Worktree Informationen in `$GIT_DIR/worktrees` löschen + Worktree Informationen in `$GIT_COMMON_DIR/worktrees` löschen Pull Remote-Branch: Alle Branches fetchen diff --git a/src/Resources/Locales/en_US.axaml b/src/Resources/Locales/en_US.axaml index 818bd9bb..f24d6c65 100644 --- a/src/Resources/Locales/en_US.axaml +++ b/src/Resources/Locales/en_US.axaml @@ -1,11 +1,6 @@ About About SourceGit - • Build with - • Chart is rendered by - • TextEditor from - • Monospace fonts come from - • Source code can be found at Opensource & Free Git GUI Client Add Worktree What to Checkout: @@ -22,18 +17,10 @@ Use AI to generate commit message APPLY AS COMMIT MESSAGE Patch - Error - Raise errors and refuses to apply the patch - Error All - Similar to 'error', but shows more Patch File: Select .patch file to apply Ignore whitespace changes - No Warn - Turns off the trailing whitespace warning Apply Patch - Warn - Outputs warnings for a few such errors, but applies Whitespace: Apply Stash Delete after applying @@ -484,6 +471,7 @@ History Commits Show author time instead of commit time in graph Show children in the commit details + Show tags in commit graph Subject Guide Length GIT Enable Auto CRLF @@ -512,7 +500,7 @@ Prune Remote Target: Prune Worktrees - Prune worktree information in `$GIT_DIR/worktrees` + Prune worktree information in `$GIT_COMMON_DIR/worktrees` Pull Remote Branch: Fetch all branches diff --git a/src/Resources/Locales/es_ES.axaml b/src/Resources/Locales/es_ES.axaml index e909a14e..e7e953e5 100644 --- a/src/Resources/Locales/es_ES.axaml +++ b/src/Resources/Locales/es_ES.axaml @@ -4,11 +4,6 @@ Acerca de Acerca de SourceGit - • Construido con - • El gráfico es renderizado por - • Editor de texto de - • Las fuentes monoespaciadas provienen de - • El código fuente se puede encontrar en Cliente Git GUI de código abierto y gratuito Agregar Worktree Qué Checkout: @@ -25,18 +20,10 @@ Usar OpenAI para generar mensaje de commit APLICAR CÓMO MENSAJE DE COMMIT Aplicar Parche - Error - Genera errores y se niega a aplicar el parche - Error Todo - Similar a 'error', pero muestra más Archivo del Parche: Seleccionar archivo .patch para aplicar Ignorar cambios de espacios en blanco - Sin Advertencia - Desactiva la advertencia de espacios en blanco al final Aplicar Parche - Advertencia - Genera advertencias para algunos de estos errores, pero aplica Espacios en Blanco: Aplicar Stash Borrar después de aplicar @@ -516,7 +503,7 @@ Podar Remoto Destino: Podar Worktrees - Podar información de worktree en `$GIT_DIR/worktrees` + Podar información de worktree en `$GIT_COMMON_DIR/worktrees` Pull Rama Remota: Fetch todas las ramas diff --git a/src/Resources/Locales/fr_FR.axaml b/src/Resources/Locales/fr_FR.axaml index aecea9ad..19c0859c 100644 --- a/src/Resources/Locales/fr_FR.axaml +++ b/src/Resources/Locales/fr_FR.axaml @@ -4,11 +4,6 @@ À propos À propos de SourceGit - • Compilé avec - • Le graphique est rendu par - • TextEditor de - • Les polices Monospace proviennent de - • Le code source est disponible sur Client Git Open Source et Gratuit Ajouter un Worktree Que récupérer : @@ -23,18 +18,10 @@ Assistant IA Utiliser l'IA pour générer un message de commit Appliquer - Erreur - Soulever les erreurs et refuser d'appliquer le patch - Toutes les erreurs - Similaire à 'Erreur', mais plus détaillé Fichier de patch : Selectionner le fichier .patch à appliquer Ignorer les changements d'espaces blancs - Pas d'avertissement - Désactiver l'avertissement sur les espaces blancs terminaux Appliquer le patch - Avertissement - Affiche des avertissements pour ce type d'erreurs tout en appliquant le patch Espaces blancs : Archiver... Enregistrer l'archive sous : @@ -484,7 +471,7 @@ Élaguer une branche distant Cible : Élaguer les Worktrees - Élaguer les information de worktree dans `$GIT_DIR/worktrees` + Élaguer les information de worktree dans `$GIT_COMMON_DIR/worktrees` Pull Branche distante : Fetch toutes les branches @@ -697,4 +684,68 @@ Verrouiller Supprimer Déverrouiller + RE-GÉNÉRER + APPLIQUER COMME MESSAGE DE COMMIT + Appliquer le Stash + Supprimer après l'application + Rétablir les modifications de l'index + Stash: + Action personnalisée + Branche en amont invalide! + Initialiser et mettre à jour les sous-modules + Branche + Attendre la fin de l'action + Les espaces seront remplacés par des tirets. + Chemin: + Tous les enfants seront retirés de la liste. + Cela le supprimera uniquement de la liste, pas du disque ! + Première différence + Dernière différence + Traitement du commit + Fusionnement + Arrêté à + Annulation du commit + Source: + Fusionner (Plusieurs) + Commit tous les changement + Stratégie: + Cibles: + Activer le streaming + Largeur de tab dans l'éditeur + Taille de police + Défaut + Éditeur + Format de date + Afficher les enfants dans les détails du commit + Afficher les tags dans le graphique des commits + Activer la vérification HTTP SSL + Actions personnalisées + Visibilité dans le graphique + Réinitialiser + Cacher dans le graphique des commits + Filtrer dans le graphique des commits + DISPOSITION + Horizontal + Vertical + ORDRE DES COMMITS + Date du commit + Topologiquement + EFFACER LES NOTIFICATIONS + PASSER + Par date de créateur + Par nom (Croissant) + Par nom (Décroissant) + Trier + Utiliser le temps relatif dans les historiques + Analyser les repositories + Définir la branche suivie + Branche: + Retirer la branche amont + En amont: + Aller sur + Restauration automatique après le stashing + Vos fichiers de travail restent inchangés, mais une sauvegarde est enregistrée. + Sauvegarder en tant que patch... + Commit (Modifier) + SignOff diff --git a/src/Resources/Locales/it_IT.axaml b/src/Resources/Locales/it_IT.axaml index 4dcc8771..d002dfef 100644 --- a/src/Resources/Locales/it_IT.axaml +++ b/src/Resources/Locales/it_IT.axaml @@ -4,11 +4,6 @@ Informazioni Informazioni su SourceGit - • Creato con - • Il grafico è reso da - • Editor di testo da - • I font monospaziati provengono da - • Il codice sorgente è disponibile su Client GUI Git open source e gratuito Aggiungi Worktree Di cosa fare il checkout: @@ -25,18 +20,10 @@ Usa AI per generare il messaggio di commit APPLICA COME MESSAGGIO DI COMMIT Applica - Errore - Genera errori e si rifiuta di applicare la patch - Tutti gli errori - Simile a 'errore', ma mostra di più File Patch: Seleziona file .patch da applicare Ignora modifiche agli spazi - Nessun avviso - Disattiva l'avviso sugli spazi finali Applica Patch - Avviso - Mostra avvisi per alcuni errori, ma applica comunque Spazi: Applica lo stash Rimuovi dopo aver applicato @@ -467,7 +454,8 @@ Abilita streaming ASPETTO Font Predefinito - Font Size + Larghezza della Tab Editor + Dimensione Font Dimensione Font Predefinita Dimensione Font Editor Font Monospaziato @@ -515,7 +503,7 @@ Potatura Remota Destinazione: Potatura Worktrees - Potatura delle informazioni di worktree in `$GIT_DIR/worktrees` + Potatura delle informazioni di worktree in `$GIT_COMMON_DIR/worktrees` Scarica Branch Remoto: Recupera tutti i branch diff --git a/src/Resources/Locales/pt_BR.axaml b/src/Resources/Locales/pt_BR.axaml index b146bf0e..e811cf3e 100644 --- a/src/Resources/Locales/pt_BR.axaml +++ b/src/Resources/Locales/pt_BR.axaml @@ -29,11 +29,6 @@ Sobre Sobre o SourceGit - • Construído com - • Gráfico desenhado por - • Editor de Texto de - • Fontes monoespaçadas de - • Código-fonte pode ser encontrado em Cliente Git GUI Livre e de Código Aberto Adicionar Worktree O que Checar: @@ -48,18 +43,10 @@ Assietente IA Utilizar IA para gerar mensagem de commit Patch - Erro - Erros levantados e se recusa a aplicar o patch - Erro Total - Semelhante a 'erro', mas mostra mais Arquivo de Patch: Selecione o arquivo .patch para aplicar Ignorar mudanças de espaço em branco - Sem Aviso - Desativa o aviso de espaço em branco no final Aplicar Patch - Aviso - Emite avisos para alguns erros, mas aplica Espaço em Branco: Arquivar... Salvar Arquivo Como: @@ -498,7 +485,7 @@ Prunar Remoto Alvo: Podar Worktrees - Podar informações de worktree em `$GIT_DIR/worktrees` + Podar informações de worktree em `$GIT_COMMON_DIR/worktrees` Puxar Branch Remoto: Buscar todos os branches diff --git a/src/Resources/Locales/ru_RU.axaml b/src/Resources/Locales/ru_RU.axaml index 07fb7c94..707c9ed9 100644 --- a/src/Resources/Locales/ru_RU.axaml +++ b/src/Resources/Locales/ru_RU.axaml @@ -4,11 +4,6 @@ О программе О SourceGit - • Сборка с - • Диаграмма отображается с помощью - • Текстовый редактор от - • Моноширинные шрифты взяты из - • Исходный код можно найти по адресу Бесплатный графический клиент Git с исходным кодом Добавить рабочий каталог Переключиться на: @@ -25,18 +20,10 @@ Использовать OpenAI для создания сообщения о ревизии ПРИМЕНИТЬ КАК СООБЩЕНИЕ РЕВИЗИИ Исправить - Ошибка - Выдает ошибки и отказывается применять заплатку - Все ошибки - Аналогично «ошибке», но показывает больше Файл заплатки: Выберите файл .patch для применения Игнорировать изменения пробелов - Нет предупреждений - Отключить предупреждения о пробелах в конце Применить заплатку - Предупреждать - Выдавать предупреждения о нескольких таких ошибках, но применять Пробел: Отложить Удалить после применения @@ -488,6 +475,7 @@ Максимальная длина истории Показывать время автора вместо времени ревизии на графике Показать наследника в деталях комментария + Показывать метки на графике Длина темы ревизии GIT Включить автозавершение CRLF @@ -516,7 +504,7 @@ Удалить внешний репозиторий Цель: Удалить рабочий каталог - Информация об обрезке рабочего каталога в «$GIT_DIR/worktrees» + Информация об обрезке рабочего каталога в «$GIT_COMMON_DIR/worktrees» Забрать Ветка внешнего репозитория: Извлечь все ветки diff --git a/src/Resources/Locales/zh_CN.axaml b/src/Resources/Locales/zh_CN.axaml index 2d160ad2..93d08bd0 100644 --- a/src/Resources/Locales/zh_CN.axaml +++ b/src/Resources/Locales/zh_CN.axaml @@ -4,11 +4,6 @@ 关于软件 关于本软件 - • 项目依赖于 - • 图表绘制组件来自 - • 文本编辑器使用 - • 等宽字体来自于 - • 项目源代码地址 开源免费的Git客户端 新增工作树 检出分支方式 : @@ -25,18 +20,10 @@ 使用AI助手生成提交信息 应用本次生成 应用补丁(apply) - 错误 - 输出错误,并终止应用补丁 - 更多错误 - 与【错误】级别相似,但输出内容更多 补丁文件 : 选择补丁文件 忽略空白符号 - 忽略 - 关闭所有警告 应用补丁 - 警告 - 应用补丁,输出关于空白符的警告 空白符号处理 : 应用贮藏 在成功应用后丢弃该贮藏 @@ -488,6 +475,7 @@ 最大历史提交数 在提交路线图中显示修改时间而非提交时间 在提交详情页中显示子提交列表 + 在提交路线图中显示标签 SUBJECT字数检测 GIT配置 自动换行转换 @@ -516,7 +504,7 @@ 清理远程已删除分支 目标 : 清理工作树 - 清理在`$GIT_DIR/worktrees`中的无效工作树信息 + 清理在`$GIT_COMMON_DIR/worktrees`中的无效工作树信息 拉回(pull) 拉取分支 : 拉取远程中的所有分支变更 diff --git a/src/Resources/Locales/zh_TW.axaml b/src/Resources/Locales/zh_TW.axaml index e50a600d..d5a7a77c 100644 --- a/src/Resources/Locales/zh_TW.axaml +++ b/src/Resources/Locales/zh_TW.axaml @@ -4,11 +4,6 @@ 關於 關於 SourceGit - • 專案依賴於 - • 圖表繪製元件來自 - • 文字編輯器使用 - • 等寬字型來自於 - • 專案原始碼網址 開源免費的 Git 客戶端 新增工作區 簽出分支方式: @@ -25,18 +20,10 @@ 使用 AI 產生提交訊息 套用為提交訊息 套用修補檔 (apply patch) - 錯誤 - 輸出錯誤,並中止套用修補檔 - 更多錯誤 - 與 [錯誤] 級別相似,但輸出更多內容 修補檔: 選擇修補檔 忽略空白符號 - 忽略 - 關閉所有警告 套用修補檔 - 警告 - 套用修補檔,輸出關於空白字元的警告 空白字元處理: 套用擱置變更 套用擱置變更後刪除 @@ -487,6 +474,7 @@ 最大歷史提交數 在提交路線圖中顯示修改時間而非提交時間 在提交詳細資訊中顯示後續提交 + 在路線圖中顯示標籤 提交標題字數偵測 Git 設定 自動換行轉換 @@ -515,7 +503,7 @@ 清理遠端已刪除分支 目標: 清理工作區 - 清理在 `$GIT_DIR/worktrees` 中的無效工作區資訊 + 清理在 `$GIT_COMMON_DIR/worktrees` 中的無效工作區資訊 拉取 (pull) 拉取分支: 拉取遠端中的所有分支 diff --git a/src/Resources/Themes.axaml b/src/Resources/Themes.axaml index 6326023a..ff4c0374 100644 --- a/src/Resources/Themes.axaml +++ b/src/Resources/Themes.axaml @@ -10,7 +10,6 @@ #FFFAFAFA #FFB0CEE8 #FF1F1F1F - DarkGreen #FF836C2E #FFFFFFFF #FFCFCFCF @@ -37,7 +36,6 @@ #FF1C1C1C #FF8F8F8F #FFDDDDDD - #84c88a #FFFAFAD2 #FF252525 #FF181818 @@ -64,7 +62,6 @@ - diff --git a/src/SourceGit.csproj b/src/SourceGit.csproj index 34e4eab2..3578d59f 100644 --- a/src/SourceGit.csproj +++ b/src/SourceGit.csproj @@ -46,8 +46,8 @@ - - + + diff --git a/src/ViewModels/Apply.cs b/src/ViewModels/Apply.cs index 09567761..60001476 100644 --- a/src/ViewModels/Apply.cs +++ b/src/ViewModels/Apply.cs @@ -1,5 +1,4 @@ -using System.Collections.Generic; -using System.ComponentModel.DataAnnotations; +using System.ComponentModel.DataAnnotations; using System.IO; using System.Threading.Tasks; @@ -21,12 +20,6 @@ namespace SourceGit.ViewModels set => SetProperty(ref _ignoreWhiteSpace, value); } - public List WhiteSpaceModes - { - get; - private set; - } - public Models.ApplyWhiteSpaceMode SelectedWhiteSpaceMode { get; @@ -37,23 +30,14 @@ namespace SourceGit.ViewModels { _repo = repo; - WhiteSpaceModes = new List { - new Models.ApplyWhiteSpaceMode("Apply.NoWarn", "Apply.NoWarn.Desc", "nowarn"), - new Models.ApplyWhiteSpaceMode("Apply.Warn", "Apply.Warn.Desc", "warn"), - new Models.ApplyWhiteSpaceMode("Apply.Error", "Apply.Error.Desc", "error"), - new Models.ApplyWhiteSpaceMode("Apply.ErrorAll", "Apply.ErrorAll.Desc", "error-all") - }; - SelectedWhiteSpaceMode = WhiteSpaceModes[0]; - + SelectedWhiteSpaceMode = Models.ApplyWhiteSpaceMode.Supported[0]; View = new Views.Apply() { DataContext = this }; } public static ValidationResult ValidatePatchFile(string file, ValidationContext _) { if (File.Exists(file)) - { return ValidationResult.Success; - } return new ValidationResult($"File '{file}' can NOT be found!!!"); } diff --git a/src/ViewModels/Histories.cs b/src/ViewModels/Histories.cs index 0e67915c..01114dd3 100644 --- a/src/ViewModels/Histories.cs +++ b/src/ViewModels/Histories.cs @@ -871,7 +871,7 @@ namespace SourceGit.ViewModels return; if (_repo.CanCreatePopup()) - _repo.ShowAndStartPopup(new Merge(_repo, b, current.Name)); + _repo.ShowAndStartPopup(new Merge(_repo, b, current.Name, true)); e.Handled = true; }; @@ -972,7 +972,7 @@ namespace SourceGit.ViewModels merge.Click += (_, e) => { if (_repo.CanCreatePopup()) - _repo.ShowPopup(new Merge(_repo, branch, current.Name)); + _repo.ShowPopup(new Merge(_repo, branch, current.Name, false)); e.Handled = true; }; submenu.Items.Add(merge); @@ -1060,7 +1060,7 @@ namespace SourceGit.ViewModels merge.Click += (_, e) => { if (_repo.CanCreatePopup()) - _repo.ShowPopup(new Merge(_repo, branch, current.Name)); + _repo.ShowPopup(new Merge(_repo, branch, current.Name, false)); e.Handled = true; }; diff --git a/src/ViewModels/Merge.cs b/src/ViewModels/Merge.cs index 174bb1e1..be938867 100644 --- a/src/ViewModels/Merge.cs +++ b/src/ViewModels/Merge.cs @@ -15,20 +15,20 @@ namespace SourceGit.ViewModels get; } - public Models.MergeMode SelectedMode + public Models.MergeMode Mode { get; set; } - public Merge(Repository repo, Models.Branch source, string into) + public Merge(Repository repo, Models.Branch source, string into, bool forceFastForward) { _repo = repo; _sourceName = source.FriendlyName; Source = source; Into = into; - SelectedMode = AutoSelectMergeMode(); + Mode = forceFastForward ? Models.MergeMode.Supported[1] : AutoSelectMergeMode(); View = new Views.Merge() { DataContext = this }; } @@ -39,7 +39,7 @@ namespace SourceGit.ViewModels Source = source; Into = into; - SelectedMode = AutoSelectMergeMode(); + Mode = AutoSelectMergeMode(); View = new Views.Merge() { DataContext = this }; } @@ -50,7 +50,7 @@ namespace SourceGit.ViewModels Source = source; Into = into; - SelectedMode = AutoSelectMergeMode(); + Mode = AutoSelectMergeMode(); View = new Views.Merge() { DataContext = this }; } @@ -61,7 +61,7 @@ namespace SourceGit.ViewModels return Task.Run(() => { - new Commands.Merge(_repo.FullPath, _sourceName, SelectedMode.Arg, SetProgressDescription).Exec(); + new Commands.Merge(_repo.FullPath, _sourceName, Mode.Arg, SetProgressDescription).Exec(); CallUIThread(() => _repo.SetWatcherEnabled(true)); return true; }); @@ -72,12 +72,14 @@ namespace SourceGit.ViewModels var config = new Commands.Config(_repo.FullPath).Get($"branch.{Into}.mergeoptions"); if (string.IsNullOrEmpty(config)) return Models.MergeMode.Supported[0]; - if (config.Equals("--no-ff", StringComparison.Ordinal)) + if (config.Equals("--ff-only", StringComparison.Ordinal)) return Models.MergeMode.Supported[1]; - if (config.Equals("--squash", StringComparison.Ordinal)) + if (config.Equals("--no-ff", StringComparison.Ordinal)) return Models.MergeMode.Supported[2]; - if (config.Equals("--no-commit", StringComparison.Ordinal) || config.Equals("--no-ff --no-commit", StringComparison.Ordinal)) + if (config.Equals("--squash", StringComparison.Ordinal)) return Models.MergeMode.Supported[3]; + if (config.Equals("--no-commit", StringComparison.Ordinal) || config.Equals("--no-ff --no-commit", StringComparison.Ordinal)) + return Models.MergeMode.Supported[4]; return Models.MergeMode.Supported[0]; } diff --git a/src/ViewModels/Preferences.cs b/src/ViewModels/Preferences.cs index 0b1d841e..cad6c224 100644 --- a/src/ViewModels/Preferences.cs +++ b/src/ViewModels/Preferences.cs @@ -183,6 +183,12 @@ namespace SourceGit.ViewModels set => SetProperty(ref _showTagsAsTree, value); } + public bool ShowTagsInGraph + { + get => _showTagsInGraph; + set => SetProperty(ref _showTagsInGraph, value); + } + public bool UseTwoColumnsLayoutInHistories { get => _useTwoColumnsLayoutInHistories; @@ -643,6 +649,7 @@ namespace SourceGit.ViewModels private string _ignoreUpdateTag = string.Empty; private bool _showTagsAsTree = false; + private bool _showTagsInGraph = true; private bool _useTwoColumnsLayoutInHistories = false; private bool _displayTimeAsPeriodInHistories = false; private bool _useSideBySideDiff = false; diff --git a/src/ViewModels/Repository.cs b/src/ViewModels/Repository.cs index 97c52d8e..6ea41e04 100644 --- a/src/ViewModels/Repository.cs +++ b/src/ViewModels/Repository.cs @@ -118,20 +118,6 @@ namespace SourceGit.ViewModels } } - public bool EnableTopoOrderInHistories - { - get => _settings.EnableTopoOrderInHistories; - set - { - if (value != _settings.EnableTopoOrderInHistories) - { - _settings.EnableTopoOrderInHistories = value; - OnPropertyChanged(); - Task.Run(RefreshCommits); - } - } - } - public bool OnlyHighlightCurrentBranchInHistories { get => _settings.OnlyHighlighCurrentBranchInHistories; @@ -145,20 +131,6 @@ namespace SourceGit.ViewModels } } - public Models.TagSortMode TagSortMode - { - get => _settings.TagSortMode; - set - { - if (value != _settings.TagSortMode) - { - _settings.TagSortMode = value; - OnPropertyChanged(); - VisibleTags = BuildVisibleTags(); - } - } - } - public string Filter { get => _filter; @@ -457,7 +429,16 @@ namespace SourceGit.ViewModels try { - _watcher = new Models.Watcher(this); + // For worktrees, we need to watch the $GIT_COMMON_DIR instead of the $GIT_DIR. + var gitDirForWatcher = _gitDir; + if (_gitDir.Replace("\\", "/").IndexOf("/worktrees/", StringComparison.Ordinal) > 0) + { + var commonDir = new Commands.QueryGitCommonDir(_fullpath).Result(); + if (!string.IsNullOrEmpty(commonDir)) + gitDirForWatcher = commonDir; + } + + _watcher = new Models.Watcher(this, _fullpath, gitDirForWatcher); } catch (Exception ex) { @@ -1461,6 +1442,80 @@ namespace SourceGit.ViewModels return menu; } + public ContextMenu CreateContextMenuForHistoriesPage() + { + var layout = new MenuItem(); + layout.Header = App.Text("Repository.HistoriesLayout"); + layout.IsEnabled = false; + + var isHorizontal = Preferences.Instance.UseTwoColumnsLayoutInHistories; + var horizontal = new MenuItem(); + horizontal.Header = App.Text("Repository.HistoriesLayout.Horizontal"); + if (isHorizontal) + horizontal.Icon = App.CreateMenuIcon("Icons.Check"); + horizontal.Click += (_, ev) => + { + Preferences.Instance.UseTwoColumnsLayoutInHistories = true; + ev.Handled = true; + }; + + var vertical = new MenuItem(); + vertical.Header = App.Text("Repository.HistoriesLayout.Vertical"); + if (!isHorizontal) + vertical.Icon = App.CreateMenuIcon("Icons.Check"); + vertical.Click += (_, ev) => + { + Preferences.Instance.UseTwoColumnsLayoutInHistories = false; + ev.Handled = true; + }; + + var order = new MenuItem(); + order.Header = App.Text("Repository.HistoriesOrder"); + order.IsEnabled = false; + + var dateOrder = new MenuItem(); + dateOrder.Header = App.Text("Repository.HistoriesOrder.ByDate"); + dateOrder.SetValue(Views.MenuItemExtension.CommandProperty, "--date-order"); + if (!_settings.EnableTopoOrderInHistories) + dateOrder.Icon = App.CreateMenuIcon("Icons.Check"); + dateOrder.Click += (_, ev) => + { + if (_settings.EnableTopoOrderInHistories) + { + _settings.EnableTopoOrderInHistories = false; + Task.Run(RefreshCommits); + } + + ev.Handled = true; + }; + + var topoOrder = new MenuItem(); + topoOrder.Header = App.Text("Repository.HistoriesOrder.Topo"); + topoOrder.SetValue(Views.MenuItemExtension.CommandProperty, "--top-order"); + if (_settings.EnableTopoOrderInHistories) + topoOrder.Icon = App.CreateMenuIcon("Icons.Check"); + topoOrder.Click += (_, ev) => + { + if (!_settings.EnableTopoOrderInHistories) + { + _settings.EnableTopoOrderInHistories = true; + Task.Run(RefreshCommits); + } + + ev.Handled = true; + }; + + var menu = new ContextMenu(); + menu.Items.Add(layout); + menu.Items.Add(horizontal); + menu.Items.Add(vertical); + menu.Items.Add(new MenuItem() { Header = "-" }); + menu.Items.Add(order); + menu.Items.Add(dateOrder); + menu.Items.Add(topoOrder); + return menu; + } + public ContextMenu CreateContextMenuForLocalBranch(Models.Branch branch) { var menu = new ContextMenu(); @@ -1507,7 +1562,7 @@ namespace SourceGit.ViewModels return; if (CanCreatePopup()) - ShowAndStartPopup(new Merge(this, b, branch.Name)); + ShowAndStartPopup(new Merge(this, b, branch.Name, true)); e.Handled = true; }; @@ -1586,7 +1641,7 @@ namespace SourceGit.ViewModels merge.Click += (_, e) => { if (CanCreatePopup()) - ShowPopup(new Merge(this, branch, _currentBranch.Name)); + ShowPopup(new Merge(this, branch, _currentBranch.Name, false)); e.Handled = true; }; @@ -1867,7 +1922,7 @@ namespace SourceGit.ViewModels merge.Click += (_, e) => { if (CanCreatePopup()) - ShowPopup(new Merge(this, branch, _currentBranch.Name)); + ShowPopup(new Merge(this, branch, _currentBranch.Name, false)); e.Handled = true; }; @@ -2056,6 +2111,55 @@ namespace SourceGit.ViewModels return menu; } + public ContextMenu CreateContextMenuForTagSortMode() + { + var mode = _settings.TagSortMode; + var changeMode = new Action((m) => + { + if (_settings.TagSortMode != m) + { + _settings.TagSortMode = m; + VisibleTags = BuildVisibleTags(); + } + }); + + var byCreatorDate = new MenuItem(); + byCreatorDate.Header = App.Text("Repository.Tags.OrderByCreatorDate"); + if (mode == Models.TagSortMode.CreatorDate) + byCreatorDate.Icon = App.CreateMenuIcon("Icons.Check"); + byCreatorDate.Click += (_, ev) => + { + changeMode(Models.TagSortMode.CreatorDate); + ev.Handled = true; + }; + + var byNameAsc = new MenuItem(); + byNameAsc.Header = App.Text("Repository.Tags.OrderByNameAsc"); + if (mode == Models.TagSortMode.NameInAscending) + byNameAsc.Icon = App.CreateMenuIcon("Icons.Check"); + byNameAsc.Click += (_, ev) => + { + changeMode(Models.TagSortMode.NameInAscending); + ev.Handled = true; + }; + + var byNameDes = new MenuItem(); + byNameDes.Header = App.Text("Repository.Tags.OrderByNameDes"); + if (mode == Models.TagSortMode.NameInDescending) + byNameDes.Icon = App.CreateMenuIcon("Icons.Check"); + byNameDes.Click += (_, ev) => + { + changeMode(Models.TagSortMode.NameInDescending); + ev.Handled = true; + }; + + var menu = new ContextMenu(); + menu.Items.Add(byCreatorDate); + menu.Items.Add(byNameAsc); + menu.Items.Add(byNameDes); + return menu; + } + public ContextMenu CreateContextMenuForSubmodule(string submodule) { var open = new MenuItem(); diff --git a/src/ViewModels/StashChanges.cs b/src/ViewModels/StashChanges.cs index 33ebb1f3..e35aaad0 100644 --- a/src/ViewModels/StashChanges.cs +++ b/src/ViewModels/StashChanges.cs @@ -64,7 +64,7 @@ namespace SourceGit.ViewModels { if (OnlyStaged) { - if (Native.OS.GitVersion >= Models.GitVersions.STASH_ONLY_STAGED) + if (Native.OS.GitVersion >= Models.GitVersions.STASH_PUSH_ONLY_STAGED) { succ = new Commands.Stash(_repo.FullPath).PushOnlyStaged(Message, KeepIndex); } @@ -109,7 +109,7 @@ namespace SourceGit.ViewModels return true; var succ = false; - if (Native.OS.GitVersion >= Models.GitVersions.STASH_WITH_PATHSPECFILE) + if (Native.OS.GitVersion >= Models.GitVersions.STASH_PUSH_WITH_PATHSPECFILE) { var paths = new List(); foreach (var c in changes) diff --git a/src/ViewModels/StashesPage.cs b/src/ViewModels/StashesPage.cs index ec7cc84a..77ed5551 100644 --- a/src/ViewModels/StashesPage.cs +++ b/src/ViewModels/StashesPage.cs @@ -58,25 +58,29 @@ namespace SourceGit.ViewModels { Task.Run(() => { - var changes = new Commands.CompareRevisions(_repo.FullPath, $"{value.SHA}^", value.SHA).Result(); - var untracked = new HashSet(); - if (value.HasUntracked) + var changes = null as List; + + if (Native.OS.GitVersion >= Models.GitVersions.STASH_SHOW_WITH_UNTRACKED) { - var untrackedChanges = new Commands.CompareRevisions(_repo.FullPath, "4b825dc642cb6eb9a060e54bf8d69288fbee4904", value.Parents[2]).Result(); - foreach (var c in untrackedChanges) + changes = new Commands.QueryStashChanges(_repo.FullPath, value.Name).Result(); + } + else + { + changes = new Commands.CompareRevisions(_repo.FullPath, $"{value.SHA}^", value.SHA).Result(); + if (value.Parents.Count == 3) { - untracked.Add(c.Path); - changes.Add(c); + var untracked = new Commands.CompareRevisions(_repo.FullPath, "4b825dc642cb6eb9a060e54bf8d69288fbee4904", value.Parents[2]).Result(); + var needSort = changes.Count > 0; + + foreach (var c in untracked) + changes.Add(c); + + if (needSort) + changes.Sort((l, r) => string.Compare(l.Path, r.Path, StringComparison.Ordinal)); } } - changes.Sort((l, r) => Models.NumericSort.Compare(l.Path, r.Path)); - - Dispatcher.UIThread.Invoke(() => - { - Changes = changes; - _untrackedChanges = untracked; - }); + Dispatcher.UIThread.Invoke(() => Changes = changes); }); } } @@ -102,7 +106,7 @@ namespace SourceGit.ViewModels { if (value == null) DiffContext = null; - else if (_untrackedChanges.Contains(value.Path)) + else if (value.Index == Models.ChangeState.Added && _selectedStash.Parents.Count == 3) DiffContext = new DiffContext(_repo.FullPath, new Models.DiffOption("4b825dc642cb6eb9a060e54bf8d69288fbee4904", _selectedStash.Parents[2], value), _diffContext); else DiffContext = new DiffContext(_repo.FullPath, new Models.DiffOption(_selectedStash.Parents[0], _selectedStash.SHA, value), _diffContext); @@ -178,7 +182,7 @@ namespace SourceGit.ViewModels var opts = new List(); foreach (var c in _changes) { - if (_untrackedChanges.Contains(c.Path)) + if (c.Index == Models.ChangeState.Added && _selectedStash.Parents.Count == 3) opts.Add(new Models.DiffOption("4b825dc642cb6eb9a060e54bf8d69288fbee4904", _selectedStash.Parents[2], c)); else opts.Add(new Models.DiffOption(_selectedStash.Parents[0], _selectedStash.SHA, c)); @@ -303,7 +307,6 @@ namespace SourceGit.ViewModels private List _visibleStashes = new List(); private string _searchFilter = string.Empty; private Models.Stash _selectedStash = null; - private HashSet _untrackedChanges = new HashSet(); private List _changes = null; private Models.Change _selectedChange = null; private DiffContext _diffContext = null; diff --git a/src/Views/About.axaml b/src/Views/About.axaml index ecdf156e..d0dd7b82 100644 --- a/src/Views/About.axaml +++ b/src/Views/About.axaml @@ -3,12 +3,12 @@ xmlns:d="http://schemas.microsoft.com/expression/blend/2008" xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" xmlns:v="using:SourceGit.Views" - mc:Ignorable="d" d:DesignWidth="800" d:DesignHeight="450" + mc:Ignorable="d" d:DesignWidth="520" d:DesignHeight="230" x:Class="SourceGit.Views.About" x:Name="ThisControl" Icon="/App.ico" Title="{DynamicResource Text.About}" - SizeToContent="WidthAndHeight" + Width="520" Height="230" CanResize="False" WindowStartupLocation="CenterScreen"> @@ -28,13 +28,13 @@ Text="{DynamicResource Text.About}" HorizontalAlignment="Center" VerticalAlignment="Center" IsHitTestVisible="False"/> - + - + - - + + - + - + + - - - - - - - - - - - - - - - - - - - - - - + + + + diff --git a/src/Views/About.axaml.cs b/src/Views/About.axaml.cs index 631df0f9..d393f94c 100644 --- a/src/Views/About.axaml.cs +++ b/src/Views/About.axaml.cs @@ -1,5 +1,5 @@ using System.Reflection; -using Avalonia.Input; +using Avalonia.Interactivity; namespace SourceGit.Views { @@ -19,31 +19,13 @@ namespace SourceGit.Views TxtCopyright.Text = copyright.Copyright; } - private void OnVisitAvaloniaUI(object _, PointerPressedEventArgs e) + private void OnVisitWebsite(object _, RoutedEventArgs e) { - Native.OS.OpenBrowser("https://www.avaloniaui.net/"); + Native.OS.OpenBrowser("https://sourcegit-scm.github.io/"); e.Handled = true; } - private void OnVisitAvaloniaEdit(object _, PointerPressedEventArgs e) - { - Native.OS.OpenBrowser("https://github.com/AvaloniaUI/AvaloniaEdit"); - e.Handled = true; - } - - private void OnVisitJetBrainsMonoFont(object _, PointerPressedEventArgs e) - { - Native.OS.OpenBrowser("https://www.jetbrains.com/lp/mono/"); - e.Handled = true; - } - - private void OnVisitLiveCharts2(object _, PointerPressedEventArgs e) - { - Native.OS.OpenBrowser("https://livecharts.dev/"); - e.Handled = true; - } - - private void OnVisitSourceCode(object _, PointerPressedEventArgs e) + private void OnVisitSourceCode(object _, RoutedEventArgs e) { Native.OS.OpenBrowser("https://github.com/sourcegit-scm/sourcegit"); e.Handled = true; diff --git a/src/Views/AddWorktree.axaml b/src/Views/AddWorktree.axaml index d6853aab..1811008c 100644 --- a/src/Views/AddWorktree.axaml +++ b/src/Views/AddWorktree.axaml @@ -27,7 +27,7 @@ - + - + - - + Text="{DynamicResource Text.AddWorktree.Tracking}"/> + + IsEnabled="{Binding !IgnoreWhiteSpace}" + Grid.IsSharedSizeScope="True"> - - - - - + + + + + + + + + + + + + + + + + + + + + - + - + - + - + @@ -62,7 +62,7 @@ - + @@ -73,7 +73,7 @@ ToolTip.Tip="{DynamicResource Text.Diff.Next}"> - + - - + - + @@ -285,10 +285,9 @@ - + diff --git a/src/Views/DiffView.axaml.cs b/src/Views/DiffView.axaml.cs index 889f0df7..9dd27f24 100644 --- a/src/Views/DiffView.axaml.cs +++ b/src/Views/DiffView.axaml.cs @@ -13,30 +13,32 @@ namespace SourceGit.Views private void OnGotoFirstChange(object _, RoutedEventArgs e) { - var textDiff = this.FindDescendantOfType(); - textDiff?.GotoFirstChange(); + this.FindDescendantOfType()?.GotoFirstChange(); e.Handled = true; } private void OnGotoPrevChange(object _, RoutedEventArgs e) { - var textDiff = this.FindDescendantOfType(); - textDiff?.GotoPrevChange(); + this.FindDescendantOfType()?.GotoPrevChange(); e.Handled = true; } private void OnGotoNextChange(object _, RoutedEventArgs e) { - var textDiff = this.FindDescendantOfType(); - textDiff?.GotoNextChange(); + this.FindDescendantOfType()?.GotoNextChange(); e.Handled = true; } private void OnGotoLastChange(object _, RoutedEventArgs e) { - var textDiff = this.FindDescendantOfType(); - textDiff?.GotoLastChange(); + this.FindDescendantOfType()?.GotoLastChange(); e.Handled = true; } + + private void OnBlockNavigationChanged(object sender, RoutedEventArgs e) + { + if (sender is TextDiffView textDiff) + BlockNavigationIndicator.Text = textDiff.BlockNavigation?.Indicator ?? string.Empty; + } } } diff --git a/src/Views/Discard.axaml b/src/Views/Discard.axaml index 23162060..1699b051 100644 --- a/src/Views/Discard.axaml +++ b/src/Views/Discard.axaml @@ -11,16 +11,16 @@ - + - - + @@ -31,13 +31,13 @@ Text="{DynamicResource Text.Discard.Changes}"/> - + - + - + - diff --git a/src/Views/EditRepositoryNode.axaml b/src/Views/EditRepositoryNode.axaml index ac8f50f3..615e3f11 100644 --- a/src/Views/EditRepositoryNode.axaml +++ b/src/Views/EditRepositoryNode.axaml @@ -43,7 +43,7 @@ Fill="{Binding Converter={x:Static c:IntConverters.ToBookmarkBrush}}" HorizontalAlignment="Center" VerticalAlignment="Center" Data="{StaticResource Icons.Bookmark}"/> - + diff --git a/src/Views/FileHistories.axaml b/src/Views/FileHistories.axaml index 124b2e00..e33156fb 100644 --- a/src/Views/FileHistories.axaml +++ b/src/Views/FileHistories.axaml @@ -37,7 +37,7 @@ Text="{DynamicResource Text.FileHistory}" HorizontalAlignment="Center" VerticalAlignment="Center" IsHitTestVisible="False"/> - + @@ -184,7 +184,7 @@ - + @@ -234,7 +234,7 @@ HorizontalAlignment="Center" VerticalAlignment="Center" IsVisible="{Binding IsLoading}"/> - + diff --git a/src/Views/FilterModeSwitchButton.axaml b/src/Views/FilterModeSwitchButton.axaml index 0fbbbf8e..b202c434 100644 --- a/src/Views/FilterModeSwitchButton.axaml +++ b/src/Views/FilterModeSwitchButton.axaml @@ -5,7 +5,7 @@ xmlns:m="using:SourceGit.Models" mc:Ignorable="d" d:DesignWidth="800" d:DesignHeight="450" x:Class="SourceGit.Views.FilterModeSwitchButton" - x:Name="ThisControl"> + x:Name="ThisControl"> @@ -104,7 +104,7 @@ - + diff --git a/src/Views/LFSTrackCustomPattern.axaml b/src/Views/LFSTrackCustomPattern.axaml index 36eaef65..f60304d5 100644 --- a/src/Views/LFSTrackCustomPattern.axaml +++ b/src/Views/LFSTrackCustomPattern.axaml @@ -11,7 +11,7 @@ - + + WindowStartupLocation="CenterScreen"> @@ -80,7 +80,7 @@ - @@ -93,7 +93,7 @@ - + diff --git a/src/Views/LauncherPage.axaml b/src/Views/LauncherPage.axaml index 81f504c1..7ce450de 100644 --- a/src/Views/LauncherPage.axaml +++ b/src/Views/LauncherPage.axaml @@ -17,14 +17,14 @@ - + - + @@ -32,7 +32,7 @@ - + @@ -138,7 +138,7 @@ + diff --git a/src/Views/LauncherTabBar.axaml b/src/Views/LauncherTabBar.axaml index 9b748e91..73b48f58 100644 --- a/src/Views/LauncherTabBar.axaml +++ b/src/Views/LauncherTabBar.axaml @@ -54,7 +54,7 @@ - + + SelectedItem="{Binding Mode, Mode=TwoWay}" + Grid.IsSharedSizeScope="True"> - - - - + + + + + + + + + + + + + + + + + + + + diff --git a/src/Views/MergeMultiple.axaml b/src/Views/MergeMultiple.axaml index bb543e16..332d9fef 100644 --- a/src/Views/MergeMultiple.axaml +++ b/src/Views/MergeMultiple.axaml @@ -12,7 +12,7 @@ - + - + @@ -84,7 +84,7 @@ - + diff --git a/src/Views/PopupRunningStatus.axaml b/src/Views/PopupRunningStatus.axaml index c2d86f51..a8467415 100644 --- a/src/Views/PopupRunningStatus.axaml +++ b/src/Views/PopupRunningStatus.axaml @@ -9,19 +9,19 @@ x:Name="ThisControl"> - + - + - + - + - + + + - - + @@ -635,7 +640,7 @@ - + @@ -646,7 +651,7 @@ - + @@ -725,8 +730,8 @@ - - + + diff --git a/src/Views/Repository.axaml.cs b/src/Views/Repository.axaml.cs index 00218a85..d848c000 100644 --- a/src/Views/Repository.axaml.cs +++ b/src/Views/Repository.axaml.cs @@ -396,66 +396,8 @@ namespace SourceGit.Views { if (sender is Button button && DataContext is ViewModels.Repository repo) { - var layout = new MenuItem(); - layout.Header = App.Text("Repository.HistoriesLayout"); - layout.IsEnabled = false; - - var isHorizontal = ViewModels.Preferences.Instance.UseTwoColumnsLayoutInHistories; - var horizontal = new MenuItem(); - horizontal.Header = App.Text("Repository.HistoriesLayout.Horizontal"); - if (isHorizontal) - horizontal.Icon = App.CreateMenuIcon("Icons.Check"); - horizontal.Click += (_, ev) => - { - ViewModels.Preferences.Instance.UseTwoColumnsLayoutInHistories = true; - ev.Handled = true; - }; - - var vertical = new MenuItem(); - vertical.Header = App.Text("Repository.HistoriesLayout.Vertical"); - if (!isHorizontal) - vertical.Icon = App.CreateMenuIcon("Icons.Check"); - vertical.Click += (_, ev) => - { - ViewModels.Preferences.Instance.UseTwoColumnsLayoutInHistories = false; - ev.Handled = true; - }; - - var order = new MenuItem(); - order.Header = App.Text("Repository.HistoriesOrder"); - order.IsEnabled = false; - - var dateOrder = new MenuItem(); - dateOrder.Header = App.Text("Repository.HistoriesOrder.ByDate"); - dateOrder.SetValue(MenuItemExtension.CommandProperty, "--date-order"); - if (!repo.EnableTopoOrderInHistories) - dateOrder.Icon = App.CreateMenuIcon("Icons.Check"); - dateOrder.Click += (_, ev) => - { - repo.EnableTopoOrderInHistories = false; - ev.Handled = true; - }; - - var topoOrder = new MenuItem(); - topoOrder.Header = App.Text("Repository.HistoriesOrder.Topo"); - topoOrder.SetValue(MenuItemExtension.CommandProperty, "--top-order"); - if (repo.EnableTopoOrderInHistories) - topoOrder.Icon = App.CreateMenuIcon("Icons.Check"); - topoOrder.Click += (_, ev) => - { - repo.EnableTopoOrderInHistories = true; - ev.Handled = true; - }; - - var menu = new ContextMenu(); - menu.Items.Add(layout); - menu.Items.Add(horizontal); - menu.Items.Add(vertical); - menu.Items.Add(new MenuItem() { Header = "-" }); - menu.Items.Add(order); - menu.Items.Add(dateOrder); - menu.Items.Add(topoOrder); - menu.Open(button); + var menu = repo.CreateContextMenuForHistoriesPage(); + menu?.Open(button); } e.Handled = true; @@ -465,41 +407,8 @@ namespace SourceGit.Views { if (sender is Button button && DataContext is ViewModels.Repository repo) { - var byCreatorDate = new MenuItem(); - byCreatorDate.Header = App.Text("Repository.Tags.OrderByCreatorDate"); - if (repo.TagSortMode == Models.TagSortMode.CreatorDate) - byCreatorDate.Icon = App.CreateMenuIcon("Icons.Check"); - byCreatorDate.Click += (_, ev) => - { - repo.TagSortMode = Models.TagSortMode.CreatorDate; - ev.Handled = true; - }; - - var byNameAsc = new MenuItem(); - byNameAsc.Header = App.Text("Repository.Tags.OrderByNameAsc"); - if (repo.TagSortMode == Models.TagSortMode.NameInAscending) - byNameAsc.Icon = App.CreateMenuIcon("Icons.Check"); - byNameAsc.Click += (_, ev) => - { - repo.TagSortMode = Models.TagSortMode.NameInAscending; - ev.Handled = true; - }; - - var byNameDes = new MenuItem(); - byNameDes.Header = App.Text("Repository.Tags.OrderByNameDes"); - if (repo.TagSortMode == Models.TagSortMode.NameInDescending) - byNameDes.Icon = App.CreateMenuIcon("Icons.Check"); - byNameDes.Click += (_, ev) => - { - repo.TagSortMode = Models.TagSortMode.NameInDescending; - ev.Handled = true; - }; - - var menu = new ContextMenu(); - menu.Items.Add(byCreatorDate); - menu.Items.Add(byNameAsc); - menu.Items.Add(byNameDes); - menu.Open(button); + var menu = repo.CreateContextMenuForTagSortMode(); + menu?.Open(button); } e.Handled = true; diff --git a/src/Views/RepositoryConfigure.axaml b/src/Views/RepositoryConfigure.axaml index f6a02c49..de777800 100644 --- a/src/Views/RepositoryConfigure.axaml +++ b/src/Views/RepositoryConfigure.axaml @@ -65,7 +65,7 @@ CornerRadius="3" Watermark="{DynamicResource Text.Configure.Email.Placeholder}" Text="{Binding UserEmail, Mode=TwoWay}"/> - + - @@ -256,7 +256,7 @@ - + @@ -315,7 +315,7 @@ - + @@ -442,7 +442,7 @@ - + diff --git a/src/Views/RepositoryToolbar.axaml b/src/Views/RepositoryToolbar.axaml index a409d8d0..9f7f1801 100644 --- a/src/Views/RepositoryToolbar.axaml +++ b/src/Views/RepositoryToolbar.axaml @@ -8,128 +8,128 @@ x:Class="SourceGit.Views.RepositoryToolbar" x:DataType="vm:Repository"> - - + + - - - + - + - - + - - + + - + + + + - + + + - + + + - + + + - + - - + - - + - - - - - - - - + - - - - - - - - + - - - + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/src/Views/RevisionCompare.axaml b/src/Views/RevisionCompare.axaml index 73703ff1..f0498fbf 100644 --- a/src/Views/RevisionCompare.axaml +++ b/src/Views/RevisionCompare.axaml @@ -15,7 +15,7 @@ - + @@ -32,7 +32,7 @@ - + diff --git a/src/Views/RevisionFileContentViewer.axaml b/src/Views/RevisionFileContentViewer.axaml index a3a168cf..86393316 100644 --- a/src/Views/RevisionFileContentViewer.axaml +++ b/src/Views/RevisionFileContentViewer.axaml @@ -35,12 +35,12 @@ - + - + diff --git a/src/Views/RevisionFiles.axaml b/src/Views/RevisionFiles.axaml index e0c6577d..6575dc66 100644 --- a/src/Views/RevisionFiles.axaml +++ b/src/Views/RevisionFiles.axaml @@ -50,7 +50,7 @@ - + - + - + - + - - - + + + - - - + - + + - + diff --git a/src/Views/WorkingCopy.axaml b/src/Views/WorkingCopy.axaml index c9b94d59..4d79135d 100644 --- a/src/Views/WorkingCopy.axaml +++ b/src/Views/WorkingCopy.axaml @@ -23,7 +23,7 @@ - + @@ -106,7 +106,7 @@ - + - + - + @@ -186,7 +186,7 @@ - + @@ -277,7 +277,7 @@ Width="18" Height="18" HorizontalAlignment="Right" IsVisible="{Binding IsCommitting}"/> - + - +