From af4645a4ade086672c43a99f23aa2f2e93223d41 Mon Sep 17 00:00:00 2001 From: leo Date: Tue, 18 Feb 2025 16:27:19 +0800 Subject: [PATCH 01/28] project: upgrade `LiveChartsCore.SkiaSharpView.Avalonia` to `2.0.0-rc5.4` Signed-off-by: leo --- src/SourceGit.csproj | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/SourceGit.csproj b/src/SourceGit.csproj index 7cceee7e..12e914f9 100644 --- a/src/SourceGit.csproj +++ b/src/SourceGit.csproj @@ -50,7 +50,7 @@ - + From 3d4a9b86b46f4ee09a1335532483d958edc5f0db Mon Sep 17 00:00:00 2001 From: leo Date: Tue, 18 Feb 2025 16:54:00 +0800 Subject: [PATCH 02/28] ux: use bold font weight for current branch name (#997) Signed-off-by: leo --- src/Converters/BoolConverters.cs | 4 ++++ src/Views/BranchTree.axaml | 1 + 2 files changed, 5 insertions(+) diff --git a/src/Converters/BoolConverters.cs b/src/Converters/BoolConverters.cs index 2d738700..3563fb37 100644 --- a/src/Converters/BoolConverters.cs +++ b/src/Converters/BoolConverters.cs @@ -1,4 +1,5 @@ using Avalonia.Data.Converters; +using Avalonia.Media; namespace SourceGit.Converters { @@ -6,5 +7,8 @@ namespace SourceGit.Converters { public static readonly FuncValueConverter ToPageTabWidth = new FuncValueConverter(x => x ? 200 : double.NaN); + + public static readonly FuncValueConverter IsBoldToFontWeight = + new FuncValueConverter(x => x ? FontWeight.Bold : FontWeight.Normal); } } diff --git a/src/Views/BranchTree.axaml b/src/Views/BranchTree.axaml index b7ac725b..a01f3502 100644 --- a/src/Views/BranchTree.axaml +++ b/src/Views/BranchTree.axaml @@ -65,6 +65,7 @@ From 5d2cd8b2fa6cf94b972865bd73dae7c2c1eef278 Mon Sep 17 00:00:00 2001 From: leo Date: Tue, 18 Feb 2025 18:19:19 +0800 Subject: [PATCH 03/28] ux: new style for current branch (#998) Signed-off-by: leo --- src/Resources/Icons.axaml | 1 + src/Views/BranchTree.axaml | 17 +++++------------ src/Views/BranchTree.axaml.cs | 19 ++++++++++++------- 3 files changed, 18 insertions(+), 19 deletions(-) diff --git a/src/Resources/Icons.axaml b/src/Resources/Icons.axaml index 8e865660..b7d9c22e 100644 --- a/src/Resources/Icons.axaml +++ b/src/Resources/Icons.axaml @@ -8,6 +8,7 @@ M757 226a143 143 0 00-55 276 96 96 0 01-88 59h-191a187 187 0 00-96 27V312a143 143 0 10-96 0v399a143 143 0 10103 2 96 96 0 0188-59h191a191 191 0 00187-151 143 143 0 00-43-279zM280 130a48 48 0 110 96 48 48 0 010-96zm0 764a48 48 0 110-96 48 48 0 010 96zM757 417a48 48 0 110-96 48 48 0 010 96z M896 128h-64V64c0-35-29-64-64-64s-64 29-64 64v64h-64c-35 0-64 29-64 64s29 64 64 64h64v64c0 35 29 64 64 64s64-29 64-64V256h64c35 0 64-29 64-64s-29-64-64-64zm-204 307C673 481 628 512 576 512H448c-47 0-90 13-128 35V372C394 346 448 275 448 192c0-106-86-192-192-192S64 86 64 192c0 83 54 154 128 180v280c-74 26-128 97-128 180c0 106 86 192 192 192s192-86 192-192c0-67-34-125-84-159c22-20 52-33 84-33h128c122 0 223-85 249-199c-19 4-37 7-57 7c-26 0-51-5-76-13zM256 128c35 0 64 29 64 64s-29 64-64 64s-64-29-64-64s29-64 64-64zm0 768c-35 0-64-29-64-64s29-64 64-64s64 29 64 64s-29 64-64 64z M512 597m-1 0a1 1 0 103 0a1 1 0 10-3 0ZM810 393 732 315 448 600 293 444 214 522l156 156 78 78 362-362z + M512 32C246 32 32 250 32 512s218 480 480 480 480-218 480-480S774 32 512 32zm269 381L496 698c-26 26-61 26-83 0L243 528c-26-26-26-61 0-83s61-26 83 0l128 128 240-240c26-26 61-26 83 0 26 19 26 54 3 80z M747 467c29 0 56 4 82 12v-363c0-47-38-84-84-84H125c-47 0-84 38-84 84v707c0 47 38 84 84 84h375a287 287 0 01-43-152c0-160 129-289 289-289zm-531-250h438c19 0 34 15 34 34s-15 34-34 34H216c-19 0-34-15-34-34s15-34 34-34zm0 179h263c19 0 34 15 34 34s-15 34-34 34H216c-19 0-34-15-34-34s15-34 34-34zm131 247h-131c-19 0-34-15-34-34s15-34 34-34h131c19 0 34 15 34 34s-15 34-34 34zM747 521c-130 0-236 106-236 236S617 992 747 992s236-106 236-236S877 521 747 521zm11 386v-65h-130c-12 0-22-10-22-22s10-22 22-22h260l-130 108zm108-192H606l130-108v65h130c12 0 22 10 22 22s-10 22-22 22z M529 511c115 0 212 79 239 185h224a62 62 0 017 123l-7 0-224 0a247 247 0 01-479 0H65a62 62 0 01-7-123l7-0h224a247 247 0 01239-185zm0 124a124 124 0 100 247 124 124 0 000-247zm0-618c32 0 58 24 61 55l0 7V206c89 11 165 45 225 103a74 74 0 0122 45l0 9v87a62 62 0 01-123 7l-0-7v-65l-6-4c-43-33-97-51-163-53l-17-0c-74 0-133 18-180 54l-6 4v65a62 62 0 01-55 61l-7 0a62 62 0 01-61-55l-0-7V362c0-20 8-39 23-53 60-58 135-92 224-103V79c0-34 28-62 62-62z M512 926c-229 0-414-186-414-414S283 98 512 98s414 186 414 414-186 414-414 414zm0-73c189 0 341-153 341-341S701 171 512 171 171 323 171 512s153 341 341 341zm-6-192L284 439l52-52 171 171 171-171L728 439l-222 222z diff --git a/src/Views/BranchTree.axaml b/src/Views/BranchTree.axaml index a01f3502..6bff4d39 100644 --- a/src/Views/BranchTree.axaml +++ b/src/Views/BranchTree.axaml @@ -57,18 +57,11 @@ IsExpanded="{Binding IsExpanded}"/> - - - - - - - - + Date: Wed, 19 Feb 2025 10:35:34 +0800 Subject: [PATCH 04/28] enhance: tag push behavior while creating and deleting (#999) - Remember the state of `Push to all remotes after created` checkbox while creating tag - Remember the state of `Delete from remote repositories` checkbox while deleting tag - Change default state of `Delete from remote repositories` to `false` Signed-off-by: leo --- src/Models/RepositorySettings.cs | 12 ++++++++++++ src/ViewModels/CreateTag.cs | 13 +++++++------ src/ViewModels/DeleteTag.cs | 9 ++++----- src/Views/CreateTag.axaml | 2 +- src/Views/DeleteTag.axaml | 2 +- 5 files changed, 25 insertions(+), 13 deletions(-) diff --git a/src/Models/RepositorySettings.cs b/src/Models/RepositorySettings.cs index 556c99ea..44742fb8 100644 --- a/src/Models/RepositorySettings.cs +++ b/src/Models/RepositorySettings.cs @@ -104,6 +104,18 @@ namespace SourceGit.Models set; } = false; + public bool PushToRemoteWhenCreateTag + { + get; + set; + } = true; + + public bool PushToRemoteWhenDeleteTag + { + get; + set; + } = false; + public DealWithLocalChanges DealWithLocalChangesOnCreateBranch { get; diff --git a/src/ViewModels/CreateTag.cs b/src/ViewModels/CreateTag.cs index af9dcf99..a6d7255b 100644 --- a/src/ViewModels/CreateTag.cs +++ b/src/ViewModels/CreateTag.cs @@ -39,11 +39,11 @@ namespace SourceGit.ViewModels set; } = false; - public bool PushToAllRemotes + public bool PushToRemotes { - get; - set; - } = true; + get => _repo.Settings.PushToRemoteWhenCreateTag; + set => _repo.Settings.PushToRemoteWhenCreateTag = value; + } public CreateTag(Repository repo, Models.Branch branch) { @@ -82,6 +82,7 @@ namespace SourceGit.ViewModels _repo.SetWatcherEnabled(false); ProgressDescription = "Create tag..."; + var remotes = PushToRemotes ? _repo.Remotes : null; return Task.Run(() => { bool succ; @@ -90,9 +91,9 @@ namespace SourceGit.ViewModels else succ = Commands.Tag.Add(_repo.FullPath, _tagName, _basedOn); - if (succ && PushToAllRemotes) + if (succ && remotes != null) { - foreach (var remote in _repo.Remotes) + foreach (var remote in remotes) { SetProgressDescription($"Pushing tag to remote {remote.Name} ..."); new Commands.Push(_repo.FullPath, remote.Name, _tagName, false).Exec(); diff --git a/src/ViewModels/DeleteTag.cs b/src/ViewModels/DeleteTag.cs index 7b53e798..341eb4a2 100644 --- a/src/ViewModels/DeleteTag.cs +++ b/src/ViewModels/DeleteTag.cs @@ -10,17 +10,16 @@ namespace SourceGit.ViewModels private set; } - public bool ShouldPushToRemote + public bool PushToRemotes { - get; - set; + get => _repo.Settings.PushToRemoteWhenDeleteTag; + set => _repo.Settings.PushToRemoteWhenDeleteTag = value; } public DeleteTag(Repository repo, Models.Tag tag) { _repo = repo; Target = tag; - ShouldPushToRemote = true; View = new Views.DeleteTag() { DataContext = this }; } @@ -29,9 +28,9 @@ namespace SourceGit.ViewModels _repo.SetWatcherEnabled(false); ProgressDescription = $"Deleting tag '{Target.Name}' ..."; + var remotes = PushToRemotes ? _repo.Remotes : null; return Task.Run(() => { - var remotes = ShouldPushToRemote ? _repo.Remotes : null; var succ = Commands.Tag.Delete(_repo.FullPath, Target.Name, remotes); CallUIThread(() => { diff --git a/src/Views/CreateTag.axaml b/src/Views/CreateTag.axaml index 20b6798a..55b6052f 100644 --- a/src/Views/CreateTag.axaml +++ b/src/Views/CreateTag.axaml @@ -84,7 +84,7 @@ + IsChecked="{Binding PushToRemotes, Mode=TwoWay}"/> diff --git a/src/Views/DeleteTag.axaml b/src/Views/DeleteTag.axaml index 702a7f2a..23c19d35 100644 --- a/src/Views/DeleteTag.axaml +++ b/src/Views/DeleteTag.axaml @@ -23,7 +23,7 @@ + IsChecked="{Binding PushToRemotes, Mode=TwoWay}"/> From 69d107430a2473de5a2f4fb92b2c106929882f8f Mon Sep 17 00:00:00 2001 From: leo Date: Wed, 19 Feb 2025 10:44:51 +0800 Subject: [PATCH 05/28] project: upgrade `OpenAI` and `Azure.AI.OpenAI` to `2.2.0-beta.2` Signed-off-by: leo --- src/SourceGit.csproj | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/SourceGit.csproj b/src/SourceGit.csproj index 12e914f9..4183511e 100644 --- a/src/SourceGit.csproj +++ b/src/SourceGit.csproj @@ -48,10 +48,10 @@ - + - + From c3eca0d7fdea2c28084db3732875becac6874c28 Mon Sep 17 00:00:00 2001 From: leo Date: Wed, 19 Feb 2025 18:01:16 +0800 Subject: [PATCH 06/28] refactor: OpenAI integration (#996) - Add `OpenAIResponse` to trim the `...` block - Add an `Enable Streaming` option to fix the issue that some services do not support streaming output Signed-off-by: leo --- src/Commands/GenerateCommitMessage.cs | 81 +++------------ src/Models/OpenAI.cs | 136 +++++++++++++++++++++++--- src/Resources/Locales/en_US.axaml | 1 + src/Resources/Locales/zh_CN.axaml | 1 + src/Resources/Locales/zh_TW.axaml | 7 +- src/Views/Preferences.axaml | 4 + 6 files changed, 145 insertions(+), 85 deletions(-) diff --git a/src/Commands/GenerateCommitMessage.cs b/src/Commands/GenerateCommitMessage.cs index 4b18a561..df61fdd2 100644 --- a/src/Commands/GenerateCommitMessage.cs +++ b/src/Commands/GenerateCommitMessage.cs @@ -1,7 +1,6 @@ using System; using System.Collections.Generic; using System.Text; -using System.Text.RegularExpressions; using System.Threading; using Avalonia.Threading; @@ -36,6 +35,8 @@ namespace SourceGit.Commands { try { + _onResponse?.Invoke("Waiting for pre-file analyzing to completed...\n\n"); + var responseBuilder = new StringBuilder(); var summaryBuilder = new StringBuilder(); foreach (var change in _changes) @@ -49,18 +50,17 @@ namespace SourceGit.Commands var rs = new GetDiffContent(_repo, new Models.DiffOption(change, false)).ReadToEnd(); if (rs.IsSuccess) { - var hasFirstValidChar = false; - var thinkingBuffer = new StringBuilder(); _service.Chat( _service.AnalyzeDiffPrompt, $"Here is the `git diff` output: {rs.StdOut}", _cancelToken, update => - ProcessChatResponse(update, ref hasFirstValidChar, thinkingBuffer, - (responseBuilder, text => - _onResponse?.Invoke( - $"Waiting for pre-file analyzing to completed...\n\n{text}")), - (summaryBuilder, null))); + { + responseBuilder.Append(update); + summaryBuilder.Append(update); + + _onResponse?.Invoke($"Waiting for pre-file analyzing to completed...\n\n{responseBuilder}"); + }); } responseBuilder.Append("\n"); @@ -74,15 +74,15 @@ namespace SourceGit.Commands var responseBody = responseBuilder.ToString(); var subjectBuilder = new StringBuilder(); - var hasSubjectFirstValidChar = false; - var subjectThinkingBuffer = new StringBuilder(); _service.Chat( _service.GenerateSubjectPrompt, $"Here are the summaries changes:\n{summaryBuilder}", _cancelToken, update => - ProcessChatResponse(update, ref hasSubjectFirstValidChar, subjectThinkingBuffer, - (subjectBuilder, text => _onResponse?.Invoke($"{text}\n\n{responseBody}")))); + { + subjectBuilder.Append(update); + _onResponse?.Invoke($"{subjectBuilder}\n\n{responseBody}"); + }); } catch (Exception e) { @@ -90,67 +90,10 @@ namespace SourceGit.Commands } } - private void ProcessChatResponse( - string update, - ref bool hasFirstValidChar, - StringBuilder thinkingBuffer, - params (StringBuilder builder, Action callback)[] outputs) - { - if (!hasFirstValidChar) - { - update = update.TrimStart(); - if (string.IsNullOrEmpty(update)) - return; - if (update.StartsWith("<", StringComparison.Ordinal)) - thinkingBuffer.Append(update); - hasFirstValidChar = true; - } - - if (thinkingBuffer.Length > 0) - thinkingBuffer.Append(update); - - if (thinkingBuffer.Length > 15) - { - var match = REG_COT.Match(thinkingBuffer.ToString()); - if (match.Success) - { - update = REG_COT.Replace(thinkingBuffer.ToString(), "").TrimStart(); - if (update.Length > 0) - { - foreach (var output in outputs) - output.builder.Append(update); - thinkingBuffer.Clear(); - } - return; - } - - match = REG_THINK_START.Match(thinkingBuffer.ToString()); - if (!match.Success) - { - foreach (var output in outputs) - output.builder.Append(thinkingBuffer); - thinkingBuffer.Clear(); - return; - } - } - - if (thinkingBuffer.Length == 0) - { - foreach (var output in outputs) - { - output.builder.Append(update); - output.callback?.Invoke(output.builder.ToString()); - } - } - } - private Models.OpenAIService _service; private string _repo; private List _changes; private CancellationToken _cancelToken; private Action _onResponse; - - private static readonly Regex REG_COT = new(@"^<(think|thought|thinking|thought_chain)>(.*?)", RegexOptions.Singleline); - private static readonly Regex REG_THINK_START = new(@"^<(think|thought|thinking|thought_chain)>", RegexOptions.Singleline); } } diff --git a/src/Models/OpenAI.cs b/src/Models/OpenAI.cs index a6648c11..264230c6 100644 --- a/src/Models/OpenAI.cs +++ b/src/Models/OpenAI.cs @@ -1,5 +1,8 @@ using System; using System.ClientModel; +using System.Collections.Generic; +using System.Text; +using System.Text.RegularExpressions; using System.Threading; using Azure.AI.OpenAI; using CommunityToolkit.Mvvm.ComponentModel; @@ -8,6 +11,91 @@ using OpenAI.Chat; namespace SourceGit.Models { + public partial class OpenAIResponse + { + public OpenAIResponse(Action onUpdate) + { + _onUpdate = onUpdate; + } + + public void Append(string text) + { + var buffer = text; + + if (_thinkTail.Length > 0) + { + _thinkTail.Append(buffer); + buffer = _thinkTail.ToString(); + _thinkTail.Clear(); + } + + buffer = REG_COT().Replace(buffer, ""); + + var startIdx = buffer.IndexOf('<', StringComparison.Ordinal); + if (startIdx >= 0) + { + if (startIdx > 0) + OnReceive(buffer.Substring(0, startIdx)); + + var endIdx = buffer.IndexOf(">", startIdx + 1, StringComparison.Ordinal); + if (endIdx <= startIdx) + { + if (buffer.Length - startIdx <= 15) + _thinkTail.Append(buffer.Substring(startIdx)); + else + OnReceive(buffer.Substring(startIdx)); + } + else if (endIdx < startIdx + 15) + { + var tag = buffer.Substring(startIdx + 1, endIdx - startIdx - 1); + if (_thinkTags.Contains(tag)) + _thinkTail.Append(buffer.Substring(startIdx)); + else + OnReceive(buffer.Substring(startIdx)); + } + else + { + OnReceive(buffer.Substring(startIdx)); + } + } + else + { + OnReceive(buffer); + } + } + + public void End() + { + if (_thinkTail.Length > 0) + { + OnReceive(_thinkTail.ToString()); + _thinkTail.Clear(); + } + } + + private void OnReceive(string text) + { + if (!_hasTrimmedStart) + { + text = text.TrimStart(); + if (string.IsNullOrEmpty(text)) + return; + + _hasTrimmedStart = true; + } + + _onUpdate.Invoke(text); + } + + [GeneratedRegex(@"<(think|thought|thinking|thought_chain)>.*?", RegexOptions.Singleline)] + private static partial Regex REG_COT(); + + private Action _onUpdate = null; + private StringBuilder _thinkTail = new StringBuilder(); + private HashSet _thinkTags = ["think", "thought", "thinking", "thought_chain"]; + private bool _hasTrimmedStart = false; + } + public class OpenAIService : ObservableObject { public string Name @@ -42,6 +130,12 @@ namespace SourceGit.Models set => SetProperty(ref _model, value); } + public bool Streaming + { + get => _streaming; + set => SetProperty(ref _streaming, value); + } + public string AnalyzeDiffPrompt { get => _analyzeDiffPrompt; @@ -89,32 +183,47 @@ namespace SourceGit.Models public void Chat(string prompt, string question, CancellationToken cancellation, Action onUpdate) { - Uri server = new(Server); - ApiKeyCredential key = new(ApiKey); - ChatClient client = null; - if (Server.Contains("openai.azure.com/", StringComparison.Ordinal)) + var server = new Uri(_server); + var key = new ApiKeyCredential(_apiKey); + var client = null as ChatClient; + if (_server.Contains("openai.azure.com/", StringComparison.Ordinal)) { var azure = new AzureOpenAIClient(server, key); - client = azure.GetChatClient(Model); + client = azure.GetChatClient(_model); } else { var openai = new OpenAIClient(key, new() { Endpoint = server }); - client = openai.GetChatClient(Model); + client = openai.GetChatClient(_model); } + var messages = new List(); + messages.Add(_model.Equals("o1-mini", StringComparison.Ordinal) ? new UserChatMessage(prompt) : new SystemChatMessage(prompt)); + messages.Add(new UserChatMessage(question)); + try { - var updates = client.CompleteChatStreaming([ - _model.Equals("o1-mini", StringComparison.Ordinal) ? new UserChatMessage(prompt) : new SystemChatMessage(prompt), - new UserChatMessage(question), - ], null, cancellation); + var rsp = new OpenAIResponse(onUpdate); - foreach (var update in updates) + if (_streaming) { - if (update.ContentUpdate.Count > 0) - onUpdate.Invoke(update.ContentUpdate[0].Text); + var updates = client.CompleteChatStreaming(messages, null, cancellation); + + foreach (var update in updates) + { + if (update.ContentUpdate.Count > 0) + rsp.Append(update.ContentUpdate[0].Text); + } } + else + { + var completion = client.CompleteChat(messages, null, cancellation); + + if (completion.Value.Content.Count > 0) + rsp.Append(completion.Value.Content[0].Text); + } + + rsp.End(); } catch { @@ -127,6 +236,7 @@ namespace SourceGit.Models private string _server; private string _apiKey; private string _model; + private bool _streaming = true; private string _analyzeDiffPrompt; private string _generateSubjectPrompt; } diff --git a/src/Resources/Locales/en_US.axaml b/src/Resources/Locales/en_US.axaml index cd266666..0da8b5ed 100644 --- a/src/Resources/Locales/en_US.axaml +++ b/src/Resources/Locales/en_US.axaml @@ -459,6 +459,7 @@ Model Name Server + Enable Streaming APPEARANCE Default Font Font Size diff --git a/src/Resources/Locales/zh_CN.axaml b/src/Resources/Locales/zh_CN.axaml index 4db909c9..983775e7 100644 --- a/src/Resources/Locales/zh_CN.axaml +++ b/src/Resources/Locales/zh_CN.axaml @@ -462,6 +462,7 @@ 模型 配置名称 服务地址 + 启用流式输出 外观配置 缺省字体 字体大小 diff --git a/src/Resources/Locales/zh_TW.axaml b/src/Resources/Locales/zh_TW.axaml index a3fe5c19..2a5ced45 100644 --- a/src/Resources/Locales/zh_TW.axaml +++ b/src/Resources/Locales/zh_TW.axaml @@ -456,12 +456,13 @@ {0} 年前 偏好設定 AI - 伺服器 + 分析變更差異提示詞 API 金鑰 + 產生提交訊息提示詞 模型 名稱 - 分析變更差異提示詞 - 產生提交訊息提示詞 + 伺服器 + 啟用串流輸出 外觀設定 預設字型 字型大小 diff --git a/src/Views/Preferences.axaml b/src/Views/Preferences.axaml index 1d282ad9..3bdd150a 100644 --- a/src/Views/Preferences.axaml +++ b/src/Views/Preferences.axaml @@ -616,6 +616,10 @@ Text="{Binding GenerateSubjectPrompt, Mode=TwoWay}" AcceptsReturn="true" TextWrapping="Wrap"/> + + From 68946d21400575332c784d8820ae247063865b1b Mon Sep 17 00:00:00 2001 From: "github-actions[bot]" Date: Wed, 19 Feb 2025 10:01:37 +0000 Subject: [PATCH 07/28] doc: Update translation status and missing keys --- README.md | 2 +- TRANSLATION.md | 18 ++++++++++++------ 2 files changed, 13 insertions(+), 7 deletions(-) diff --git a/README.md b/README.md index 3829cf54..aca5a594 100644 --- a/README.md +++ b/README.md @@ -47,7 +47,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.47%25-yellow)](TRANSLATION.md) [![es__ES](https://img.shields.io/badge/es__ES-97.61%25-yellow)](TRANSLATION.md) [![fr__FR](https://img.shields.io/badge/fr__FR-92.42%25-yellow)](TRANSLATION.md) [![it__IT](https://img.shields.io/badge/it__IT-97.87%25-yellow)](TRANSLATION.md) [![pt__BR](https://img.shields.io/badge/pt__BR-92.15%25-yellow)](TRANSLATION.md) [![ru__RU](https://img.shields.io/badge/ru__RU-99.73%25-yellow)](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) +[![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.34%25-yellow)](TRANSLATION.md) [![es__ES](https://img.shields.io/badge/es__ES-97.48%25-yellow)](TRANSLATION.md) [![fr__FR](https://img.shields.io/badge/fr__FR-92.30%25-yellow)](TRANSLATION.md) [![it__IT](https://img.shields.io/badge/it__IT-97.74%25-yellow)](TRANSLATION.md) [![pt__BR](https://img.shields.io/badge/pt__BR-92.03%25-yellow)](TRANSLATION.md) [![ru__RU](https://img.shields.io/badge/ru__RU-99.60%25-yellow)](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) diff --git a/TRANSLATION.md b/TRANSLATION.md index 84411404..08b7c462 100644 --- a/TRANSLATION.md +++ b/TRANSLATION.md @@ -1,4 +1,4 @@ -### de_DE.axaml: 99.47% +### de_DE.axaml: 99.34%
@@ -7,11 +7,12 @@ - Text.BranchCM.CustomAction - Text.Configure.CustomAction.Scope.Branch - Text.Configure.CustomAction.WaitForExit +- Text.Preferences.AI.Streaming - Text.Repository.Notifications.Clear
-### es_ES.axaml: 97.61% +### es_ES.axaml: 97.48%
@@ -31,6 +32,7 @@ - Text.DeleteRepositoryNode.Path - Text.DeleteRepositoryNode.TipForGroup - Text.DeleteRepositoryNode.TipForRepository +- Text.Preferences.AI.Streaming - Text.Repository.Notifications.Clear - Text.Stash.AutoRestore - Text.Stash.AutoRestore.Tip @@ -38,7 +40,7 @@
-### fr_FR.axaml: 92.42% +### fr_FR.axaml: 92.30%
@@ -67,6 +69,7 @@ - Text.MergeMultiple.CommitChanges - Text.MergeMultiple.Strategy - Text.MergeMultiple.Targets +- Text.Preferences.AI.Streaming - Text.Preferences.Appearance.FontSize - Text.Preferences.Appearance.FontSize.Default - Text.Preferences.Appearance.FontSize.Editor @@ -104,7 +107,7 @@
-### it_IT.axaml: 97.87% +### it_IT.axaml: 97.74%
@@ -123,13 +126,14 @@ - Text.DeleteRepositoryNode.Path - Text.DeleteRepositoryNode.TipForGroup - Text.DeleteRepositoryNode.TipForRepository +- Text.Preferences.AI.Streaming - Text.Repository.Notifications.Clear - Text.Stash.AutoRestore - Text.Stash.AutoRestore.Tip
-### pt_BR.axaml: 92.15% +### pt_BR.axaml: 92.03%
@@ -169,6 +173,7 @@ - Text.MergeMultiple.CommitChanges - Text.MergeMultiple.Strategy - Text.MergeMultiple.Targets +- Text.Preferences.AI.Streaming - Text.Preferences.General.DateFormat - Text.Preferences.General.ShowChildren - Text.Preferences.Git.SSLVerify @@ -197,7 +202,7 @@
-### ru_RU.axaml: 99.73% +### ru_RU.axaml: 99.60%
@@ -205,6 +210,7 @@ - Text.BranchCM.CustomAction - Text.Configure.CustomAction.Scope.Branch +- Text.Preferences.AI.Streaming
From ce16ac63eb9ef3308209f42ee94ee974a2b42957 Mon Sep 17 00:00:00 2001 From: leo Date: Wed, 19 Feb 2025 19:22:21 +0800 Subject: [PATCH 08/28] enhance: submodule bookmark inherts from parent repo (#1001) Signed-off-by: leo --- src/ViewModels/Repository.cs | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/src/ViewModels/Repository.cs b/src/ViewModels/Repository.cs index 19e48b13..6e8a5290 100644 --- a/src/ViewModels/Repository.cs +++ b/src/ViewModels/Repository.cs @@ -1161,6 +1161,10 @@ namespace SourceGit.ViewModels public void OpenSubmodule(string submodule) { + var selfPage = GetOwnerPage(); + if (selfPage == null) + return; + var root = Path.GetFullPath(Path.Combine(_fullpath, submodule)); var normalizedPath = root.Replace("\\", "/"); @@ -1171,12 +1175,12 @@ namespace SourceGit.ViewModels { Id = normalizedPath, Name = Path.GetFileName(normalizedPath), - Bookmark = 0, + Bookmark = selfPage.Node.Bookmark, IsRepository = true, }; } - App.GetLauncer()?.OpenRepositoryInTab(node, null); + App.GetLauncer().OpenRepositoryInTab(node, null); } public void AddWorktree() From cbc2e46beb75edf05fb05935d87d8dfce36a539d Mon Sep 17 00:00:00 2001 From: Oleg Kosmakov <1533952+kosmakoff@users.noreply.github.com> Date: Thu, 20 Feb 2025 02:31:07 +0100 Subject: [PATCH 09/28] fix: Update unstaged filed counter when unstaged files change (#1007) * Add missing OnPropertyChanged in Cleanup * Force unstaged count to refresh --- src/ViewModels/WorkingCopy.cs | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/src/ViewModels/WorkingCopy.cs b/src/ViewModels/WorkingCopy.cs index 7ac13dc2..60fa93c3 100644 --- a/src/ViewModels/WorkingCopy.cs +++ b/src/ViewModels/WorkingCopy.cs @@ -214,9 +214,11 @@ namespace SourceGit.ViewModels OnPropertyChanged(nameof(SelectedStaged)); _visibleUnstaged.Clear(); - _unstaged.Clear(); OnPropertyChanged(nameof(VisibleUnstaged)); + _unstaged.Clear(); + OnPropertyChanged(nameof(Unstaged)); + _staged.Clear(); OnPropertyChanged(nameof(Staged)); @@ -305,6 +307,7 @@ namespace SourceGit.ViewModels _isLoadingData = true; HasUnsolvedConflicts = hasConflict; VisibleUnstaged = visibleUnstaged; + OnPropertyChanged(nameof(Unstaged)); Staged = staged; SelectedUnstaged = selectedUnstaged; SelectedStaged = selectedStaged; From 0e1dfba7ef9c94e43f0cf9a9dc8bfad33d3f8df7 Mon Sep 17 00:00:00 2001 From: leo Date: Thu, 20 Feb 2025 09:34:03 +0800 Subject: [PATCH 10/28] code_review: PR #1007 Signed-off-by: leo --- src/ViewModels/WorkingCopy.cs | 14 ++++++-------- 1 file changed, 6 insertions(+), 8 deletions(-) diff --git a/src/ViewModels/WorkingCopy.cs b/src/ViewModels/WorkingCopy.cs index 60fa93c3..d87c54ec 100644 --- a/src/ViewModels/WorkingCopy.cs +++ b/src/ViewModels/WorkingCopy.cs @@ -109,7 +109,7 @@ namespace SourceGit.ViewModels if (_isLoadingData) return; - VisibleUnstaged = GetVisibleUnstagedChanges(); + VisibleUnstaged = GetVisibleUnstagedChanges(_unstaged); SelectedUnstaged = []; } } @@ -284,9 +284,7 @@ namespace SourceGit.ViewModels } } - _unstaged = unstaged; - - var visibleUnstaged = GetVisibleUnstagedChanges(); + var visibleUnstaged = GetVisibleUnstagedChanges(unstaged); var selectedUnstaged = new List(); foreach (var c in visibleUnstaged) { @@ -307,7 +305,7 @@ namespace SourceGit.ViewModels _isLoadingData = true; HasUnsolvedConflicts = hasConflict; VisibleUnstaged = visibleUnstaged; - OnPropertyChanged(nameof(Unstaged)); + Unstaged = unstaged; Staged = staged; SelectedUnstaged = selectedUnstaged; SelectedStaged = selectedStaged; @@ -1459,14 +1457,14 @@ namespace SourceGit.ViewModels } } - private List GetVisibleUnstagedChanges() + private List GetVisibleUnstagedChanges(List unstaged) { if (string.IsNullOrEmpty(_unstagedFilter)) - return _unstaged; + return unstaged; var visible = new List(); - foreach (var c in _unstaged) + foreach (var c in unstaged) { if (c.Path.Contains(_unstagedFilter, StringComparison.OrdinalIgnoreCase)) visible.Add(c); From 53f591bdad68afeb49a4c6d0b0ea8fc42b7a7323 Mon Sep 17 00:00:00 2001 From: leo Date: Thu, 20 Feb 2025 10:12:12 +0800 Subject: [PATCH 11/28] ux: add a warning icon when the tracking upstream of a local branch is gone (#1006) Co-authored-by: Davide Tentori --- src/Commands/QueryBranches.cs | 12 ++++++++++++ src/Models/Branch.cs | 1 + src/Resources/Locales/en_US.axaml | 1 + src/Resources/Locales/zh_CN.axaml | 1 + src/Resources/Locales/zh_TW.axaml | 1 + src/ViewModels/BranchTreeNode.cs | 8 +++++--- src/Views/BranchTree.axaml | 12 +++++++++++- 7 files changed, 32 insertions(+), 4 deletions(-) diff --git a/src/Commands/QueryBranches.cs b/src/Commands/QueryBranches.cs index 95f97214..44438cef 100644 --- a/src/Commands/QueryBranches.cs +++ b/src/Commands/QueryBranches.cs @@ -25,11 +25,22 @@ namespace SourceGit.Commands return branches; var lines = rs.StdOut.Split('\n', StringSplitOptions.RemoveEmptyEntries); + var remoteBranches = new HashSet(); foreach (var line in lines) { var b = ParseLine(line); if (b != null) + { branches.Add(b); + if (!b.IsLocal) + remoteBranches.Add(b.FullName); + } + } + + foreach (var b in branches) + { + if (b.IsLocal && !string.IsNullOrEmpty(b.Upstream)) + b.IsUpsteamGone = !remoteBranches.Contains(b.Upstream); } return branches; @@ -75,6 +86,7 @@ namespace SourceGit.Commands branch.Head = parts[1]; branch.IsCurrent = parts[2] == "*"; branch.Upstream = parts[3]; + branch.IsUpsteamGone = false; if (branch.IsLocal && !string.IsNullOrEmpty(parts[4]) && !parts[4].Equals("=", StringComparison.Ordinal)) branch.TrackStatus = new QueryTrackStatus(WorkingDirectory, branch.Name, branch.Upstream).Result(); diff --git a/src/Models/Branch.cs b/src/Models/Branch.cs index 0ba320c1..2d0ae5b2 100644 --- a/src/Models/Branch.cs +++ b/src/Models/Branch.cs @@ -34,6 +34,7 @@ namespace SourceGit.Models public string Upstream { get; set; } public BranchTrackStatus TrackStatus { get; set; } public string Remote { get; set; } + public bool IsUpsteamGone { get; set; } public string FriendlyName => IsLocal ? Name : $"{Remote}/{Name}"; } diff --git a/src/Resources/Locales/en_US.axaml b/src/Resources/Locales/en_US.axaml index 0da8b5ed..dfc17dee 100644 --- a/src/Resources/Locales/en_US.axaml +++ b/src/Resources/Locales/en_US.axaml @@ -72,6 +72,7 @@ Rename ${0}$... Set Tracking Branch... Branch Compare + Invalid upstream! Bytes CANCEL Reset to This Revision diff --git a/src/Resources/Locales/zh_CN.axaml b/src/Resources/Locales/zh_CN.axaml index 983775e7..115f917e 100644 --- a/src/Resources/Locales/zh_CN.axaml +++ b/src/Resources/Locales/zh_CN.axaml @@ -75,6 +75,7 @@ 重命名 ${0}$... 切换上游分支 ... 分支比较 + 跟踪的上游分支不存在或已删除! 字节 取 消 重置文件到该版本 diff --git a/src/Resources/Locales/zh_TW.axaml b/src/Resources/Locales/zh_TW.axaml index 2a5ced45..00933783 100644 --- a/src/Resources/Locales/zh_TW.axaml +++ b/src/Resources/Locales/zh_TW.axaml @@ -75,6 +75,7 @@ 重新命名 ${0}$... 切換上游分支... 分支比較 + 追蹤上游分支不存在或已刪除! 位元組 取 消 重設檔案為此版本 diff --git a/src/ViewModels/BranchTreeNode.cs b/src/ViewModels/BranchTreeNode.cs index 5c42f729..6c1d2e04 100644 --- a/src/ViewModels/BranchTreeNode.cs +++ b/src/ViewModels/BranchTreeNode.cs @@ -1,9 +1,6 @@ using System; using System.Collections.Generic; - using Avalonia; -using Avalonia.Media; - using CommunityToolkit.Mvvm.ComponentModel; namespace SourceGit.ViewModels @@ -45,6 +42,11 @@ namespace SourceGit.ViewModels get => Backend is Models.Branch { IsCurrent: true }; } + public bool ShowUpstreamGoneTip + { + get => Backend is Models.Branch { IsUpsteamGone: true }; + } + public string Tooltip { get => Backend is Models.Branch b ? b.FriendlyName : null; diff --git a/src/Views/BranchTree.axaml b/src/Views/BranchTree.axaml index 6bff4d39..0ac09e6c 100644 --- a/src/Views/BranchTree.axaml +++ b/src/Views/BranchTree.axaml @@ -61,7 +61,17 @@ Classes="primary" Text="{Binding Name}" FontWeight="{Binding IsCurrent, Converter={x:Static c:BoolConverters.IsBoldToFontWeight}}" - TextTrimming="CharacterEllipsis"/> + TextTrimming="CharacterEllipsis"/> + + + + + Date: Thu, 20 Feb 2025 02:14:51 +0000 Subject: [PATCH 12/28] doc: Update translation status and missing keys --- README.md | 2 +- TRANSLATION.md | 18 ++++++++++++------ 2 files changed, 13 insertions(+), 7 deletions(-) diff --git a/README.md b/README.md index aca5a594..784d0672 100644 --- a/README.md +++ b/README.md @@ -47,7 +47,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.34%25-yellow)](TRANSLATION.md) [![es__ES](https://img.shields.io/badge/es__ES-97.48%25-yellow)](TRANSLATION.md) [![fr__FR](https://img.shields.io/badge/fr__FR-92.30%25-yellow)](TRANSLATION.md) [![it__IT](https://img.shields.io/badge/it__IT-97.74%25-yellow)](TRANSLATION.md) [![pt__BR](https://img.shields.io/badge/pt__BR-92.03%25-yellow)](TRANSLATION.md) [![ru__RU](https://img.shields.io/badge/ru__RU-99.60%25-yellow)](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) +[![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.20%25-yellow)](TRANSLATION.md) [![es__ES](https://img.shields.io/badge/es__ES-97.35%25-yellow)](TRANSLATION.md) [![fr__FR](https://img.shields.io/badge/fr__FR-92.18%25-yellow)](TRANSLATION.md) [![it__IT](https://img.shields.io/badge/it__IT-97.61%25-yellow)](TRANSLATION.md) [![pt__BR](https://img.shields.io/badge/pt__BR-91.91%25-yellow)](TRANSLATION.md) [![ru__RU](https://img.shields.io/badge/ru__RU-99.47%25-yellow)](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) diff --git a/TRANSLATION.md b/TRANSLATION.md index 08b7c462..53631bc1 100644 --- a/TRANSLATION.md +++ b/TRANSLATION.md @@ -1,10 +1,11 @@ -### de_DE.axaml: 99.34% +### de_DE.axaml: 99.20%
Missing Keys - Text.BranchCM.CustomAction +- Text.BranchUpstreamInvalid - Text.Configure.CustomAction.Scope.Branch - Text.Configure.CustomAction.WaitForExit - Text.Preferences.AI.Streaming @@ -12,7 +13,7 @@
-### es_ES.axaml: 97.48% +### es_ES.axaml: 97.35%
@@ -25,6 +26,7 @@ - Text.ApplyStash.RestoreIndex - Text.ApplyStash.Stash - Text.BranchCM.CustomAction +- Text.BranchUpstreamInvalid - Text.Clone.RecurseSubmodules - Text.Configure.CustomAction.Scope.Branch - Text.Configure.CustomAction.WaitForExit @@ -40,7 +42,7 @@
-### fr_FR.axaml: 92.30% +### fr_FR.axaml: 92.18%
@@ -53,6 +55,7 @@ - Text.ApplyStash.RestoreIndex - Text.ApplyStash.Stash - Text.BranchCM.CustomAction +- Text.BranchUpstreamInvalid - Text.Clone.RecurseSubmodules - Text.Configure.CustomAction.Scope.Branch - Text.Configure.CustomAction.WaitForExit @@ -107,7 +110,7 @@
-### it_IT.axaml: 97.74% +### it_IT.axaml: 97.61%
@@ -120,6 +123,7 @@ - Text.ApplyStash.RestoreIndex - Text.ApplyStash.Stash - Text.BranchCM.CustomAction +- Text.BranchUpstreamInvalid - Text.Clone.RecurseSubmodules - Text.Configure.CustomAction.Scope.Branch - Text.Configure.CustomAction.WaitForExit @@ -133,7 +137,7 @@
-### pt_BR.axaml: 92.03% +### pt_BR.axaml: 91.91%
@@ -147,6 +151,7 @@ - Text.ApplyStash.Stash - Text.BranchCM.CustomAction - Text.BranchCM.MergeMultiBranches +- Text.BranchUpstreamInvalid - Text.Clone.RecurseSubmodules - Text.CommitCM.Merge - Text.CommitCM.MergeMultiple @@ -202,13 +207,14 @@
-### ru_RU.axaml: 99.60% +### ru_RU.axaml: 99.47%
Missing Keys - Text.BranchCM.CustomAction +- Text.BranchUpstreamInvalid - Text.Configure.CustomAction.Scope.Branch - Text.Preferences.AI.Streaming From 507e502874a6dc6e3d4aa090519fc8a48e6c3e83 Mon Sep 17 00:00:00 2001 From: leo Date: Thu, 20 Feb 2025 10:18:46 +0800 Subject: [PATCH 13/28] fix: `Custom Action` height is not large enough to display all contents (#1004) Signed-off-by: leo --- src/Views/RepositoryConfigure.axaml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/Views/RepositoryConfigure.axaml b/src/Views/RepositoryConfigure.axaml index 6b7cdc12..61bc14e0 100644 --- a/src/Views/RepositoryConfigure.axaml +++ b/src/Views/RepositoryConfigure.axaml @@ -340,7 +340,7 @@ - + From 731f1055bcdc10da906eccd4345a43ba595896a3 Mon Sep 17 00:00:00 2001 From: leo Date: Thu, 20 Feb 2025 11:04:57 +0800 Subject: [PATCH 14/28] feat!: add `ptyxis` support (#1005) BREAKING CHANGE: Index of `Custom` shell/terminal Signed-off-by: leo --- src/Models/ShellOrTerminal.cs | 1 + src/Resources/Images/ShellIcons/ptyxis.png | Bin 0 -> 6930 bytes 2 files changed, 1 insertion(+) create mode 100644 src/Resources/Images/ShellIcons/ptyxis.png diff --git a/src/Models/ShellOrTerminal.cs b/src/Models/ShellOrTerminal.cs index 4f0222e8..3ada2cf9 100644 --- a/src/Models/ShellOrTerminal.cs +++ b/src/Models/ShellOrTerminal.cs @@ -57,6 +57,7 @@ namespace SourceGit.Models new ShellOrTerminal("mate-terminal", "MATE Terminal", "mate-terminal"), new ShellOrTerminal("foot", "Foot", "foot"), new ShellOrTerminal("wezterm", "WezTerm", "wezterm"), + new ShellOrTerminal("ptyxis", "Ptyxis", "ptyxis"), new ShellOrTerminal("custom", "Custom", ""), }; } diff --git a/src/Resources/Images/ShellIcons/ptyxis.png b/src/Resources/Images/ShellIcons/ptyxis.png new file mode 100644 index 0000000000000000000000000000000000000000..9202f6e115724d234fd1bf015abd705a475405a0 GIT binary patch literal 6930 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 Date: Thu, 20 Feb 2025 11:12:29 +0800 Subject: [PATCH 15/28] enhance: prefer to use `Default Remote` in repository settings while fetching remote changes (#1008) Signed-off-by: leo --- src/ViewModels/Fetch.cs | 19 ++++++++++++++++++- 1 file changed, 18 insertions(+), 1 deletion(-) diff --git a/src/ViewModels/Fetch.cs b/src/ViewModels/Fetch.cs index d816d0b8..1094012e 100644 --- a/src/ViewModels/Fetch.cs +++ b/src/ViewModels/Fetch.cs @@ -38,7 +38,24 @@ namespace SourceGit.ViewModels { _repo = repo; _fetchAllRemotes = preferedRemote == null; - SelectedRemote = preferedRemote != null ? preferedRemote : _repo.Remotes[0]; + + if (preferedRemote != null) + { + SelectedRemote = preferedRemote; + } + else if (!string.IsNullOrEmpty(_repo.Settings.DefaultRemote)) + { + var def = _repo.Remotes.Find(r => r.Name == _repo.Settings.DefaultRemote); + if (def != null) + SelectedRemote = def; + else + SelectedRemote = _repo.Remotes[0]; + } + else + { + SelectedRemote = _repo.Remotes[0]; + } + View = new Views.Fetch() { DataContext = this }; } From b5feabfd37816ced5ecfa6eacb6fd820833e1651 Mon Sep 17 00:00:00 2001 From: leo Date: Thu, 20 Feb 2025 15:42:11 +0800 Subject: [PATCH 16/28] enhance: auto-set commit message while rebasing is inprogress (#1003) Signed-off-by: leo --- src/ViewModels/WorkingCopy.cs | 100 +++++++++++++++++++--------------- 1 file changed, 56 insertions(+), 44 deletions(-) diff --git a/src/ViewModels/WorkingCopy.cs b/src/ViewModels/WorkingCopy.cs index d87c54ec..f1db3f3d 100644 --- a/src/ViewModels/WorkingCopy.cs +++ b/src/ViewModels/WorkingCopy.cs @@ -233,25 +233,10 @@ namespace SourceGit.ViewModels // Just force refresh selected changes. Dispatcher.UIThread.Invoke(() => { - if (_selectedUnstaged.Count == 1) - SetDetail(_selectedUnstaged[0], true); - else if (_selectedStaged.Count == 1) - SetDetail(_selectedStaged[0], false); - else - SetDetail(null, false); - - var inProgress = null as InProgressContext; - if (File.Exists(Path.Combine(_repo.GitDir, "CHERRY_PICK_HEAD"))) - inProgress = new CherryPickInProgress(_repo); - else if (Directory.Exists(Path.Combine(_repo.GitDir, "rebase-merge")) || Directory.Exists(Path.Combine(_repo.GitDir, "rebase-apply"))) - inProgress = new RebaseInProgress(_repo); - else if (File.Exists(Path.Combine(_repo.GitDir, "REVERT_HEAD"))) - inProgress = new RevertInProgress(_repo); - else if (File.Exists(Path.Combine(_repo.GitDir, "MERGE_HEAD"))) - inProgress = new MergeInProgress(_repo); - HasUnsolvedConflicts = _cached.Find(x => x.IsConflit) != null; - InProgressContext = inProgress; + + UpdateDetail(); + UpdateInProgressState(); }); return; @@ -311,32 +296,8 @@ namespace SourceGit.ViewModels SelectedStaged = selectedStaged; _isLoadingData = false; - if (selectedUnstaged.Count == 1) - SetDetail(selectedUnstaged[0], true); - else if (selectedStaged.Count == 1) - SetDetail(selectedStaged[0], false); - else - SetDetail(null, false); - - var inProgress = null as InProgressContext; - if (File.Exists(Path.Combine(_repo.GitDir, "CHERRY_PICK_HEAD"))) - inProgress = new CherryPickInProgress(_repo); - else if (Directory.Exists(Path.Combine(_repo.GitDir, "rebase-merge")) || Directory.Exists(Path.Combine(_repo.GitDir, "rebase-apply"))) - inProgress = new RebaseInProgress(_repo); - else if (File.Exists(Path.Combine(_repo.GitDir, "REVERT_HEAD"))) - inProgress = new RevertInProgress(_repo); - else if (File.Exists(Path.Combine(_repo.GitDir, "MERGE_HEAD"))) - inProgress = new MergeInProgress(_repo); - - InProgressContext = inProgress; - - // Try to load merge message from MERGE_MSG - if (string.IsNullOrEmpty(_commitMessage)) - { - var mergeMsgFile = Path.Combine(_repo.GitDir, "MERGE_MSG"); - if (File.Exists(mergeMsgFile)) - CommitMessage = File.ReadAllText(mergeMsgFile); - } + UpdateDetail(); + UpdateInProgressState(); }); } @@ -1488,6 +1449,57 @@ namespace SourceGit.ViewModels return rs; } + private void UpdateDetail() + { + if (_selectedUnstaged.Count == 1) + SetDetail(_selectedUnstaged[0], true); + else if (_selectedStaged.Count == 1) + SetDetail(_selectedStaged[0], false); + else + SetDetail(null, false); + } + + private void UpdateInProgressState() + { + if (string.IsNullOrEmpty(_commitMessage)) + { + var mergeMsgFile = Path.Combine(_repo.GitDir, "MERGE_MSG"); + if (File.Exists(mergeMsgFile)) + CommitMessage = File.ReadAllText(mergeMsgFile); + } + + if (File.Exists(Path.Combine(_repo.GitDir, "CHERRY_PICK_HEAD"))) + { + InProgressContext = new CherryPickInProgress(_repo); + } + else if (Directory.Exists(Path.Combine(_repo.GitDir, "rebase-merge")) || Directory.Exists(Path.Combine(_repo.GitDir, "rebase-apply"))) + { + var rebasing = new RebaseInProgress(_repo); + InProgressContext = rebasing; + + if (string.IsNullOrEmpty(_commitMessage)) + { + var rebaseMsgFile = Path.Combine(_repo.GitDir, "rebase-merge", "message"); + if (File.Exists(rebaseMsgFile)) + CommitMessage = File.ReadAllText(rebaseMsgFile); + else if (rebasing.StoppedAt != null) + CommitMessage = new Commands.QueryCommitFullMessage(_repo.FullPath, rebasing.StoppedAt.SHA).Result(); + } + } + else if (File.Exists(Path.Combine(_repo.GitDir, "REVERT_HEAD"))) + { + InProgressContext = new RevertInProgress(_repo); + } + else if (File.Exists(Path.Combine(_repo.GitDir, "MERGE_HEAD"))) + { + InProgressContext = new MergeInProgress(_repo); + } + else + { + InProgressContext = null; + } + } + private async void StageChanges(List changes, Models.Change next) { if (changes.Count == 0) From 9da2c787dbf0dbac7cc26ce777672857d40e6066 Mon Sep 17 00:00:00 2001 From: leo Date: Fri, 21 Feb 2025 09:44:51 +0800 Subject: [PATCH 17/28] enhance: supports to configure `fetch.prune` for selected repository (#995) Signed-off-by: leo --- src/ViewModels/RepositoryConfigure.cs | 9 +++++++++ src/Views/RepositoryConfigure.axaml | 8 ++++++-- 2 files changed, 15 insertions(+), 2 deletions(-) diff --git a/src/ViewModels/RepositoryConfigure.cs b/src/ViewModels/RepositoryConfigure.cs index a7c04937..cf23b6d8 100644 --- a/src/ViewModels/RepositoryConfigure.cs +++ b/src/ViewModels/RepositoryConfigure.cs @@ -60,6 +60,12 @@ namespace SourceGit.ViewModels set => SetProperty(ref _httpProxy, value); } + public bool EnablePruneOnFetch + { + get; + set; + } + public bool EnableAutoFetch { get => _repo.Settings.EnableAutoFetch; @@ -153,6 +159,8 @@ namespace SourceGit.ViewModels GPGUserSigningKey = signingKey; if (_cached.TryGetValue("http.proxy", out var proxy)) HttpProxy = proxy; + if (_cached.TryGetValue("fetch.prune", out var prune)) + EnablePruneOnFetch = (prune == "true"); } public void ClearHttpProxy() @@ -286,6 +294,7 @@ namespace SourceGit.ViewModels SetIfChanged("tag.gpgsign", GPGTagSigningEnabled ? "true" : "false", "false"); SetIfChanged("user.signingkey", GPGUserSigningKey, ""); SetIfChanged("http.proxy", HttpProxy, ""); + SetIfChanged("fetch.prune", EnablePruneOnFetch ? "true" : "false", "false"); } private void SetIfChanged(string key, string value, string defValue) diff --git a/src/Views/RepositoryConfigure.axaml b/src/Views/RepositoryConfigure.axaml index 61bc14e0..f6a02c49 100644 --- a/src/Views/RepositoryConfigure.axaml +++ b/src/Views/RepositoryConfigure.axaml @@ -44,7 +44,7 @@ - + - + + + From 2b4fc64c73b126fd0d94b5562be53e25dcf7b24d Mon Sep 17 00:00:00 2001 From: leo Date: Fri, 21 Feb 2025 10:26:14 +0800 Subject: [PATCH 18/28] fix: resolve conflict with deleted files does not work (#1009) Signed-off-by: leo --- src/Commands/Add.cs | 4 +- src/ViewModels/WorkingCopy.cs | 76 ++++++++++++++++++++++++++------- src/Views/TextDiffView.axaml.cs | 2 +- 3 files changed, 64 insertions(+), 18 deletions(-) diff --git a/src/Commands/Add.cs b/src/Commands/Add.cs index e1b55b68..b2aa803d 100644 --- a/src/Commands/Add.cs +++ b/src/Commands/Add.cs @@ -12,7 +12,7 @@ namespace SourceGit.Commands Args = includeUntracked ? "add ." : "add -u ."; } - public Add(string repo, List changes) + public Add(string repo, List changes) { WorkingDirectory = repo; Context = repo; @@ -22,7 +22,7 @@ namespace SourceGit.Commands foreach (var c in changes) { builder.Append(" \""); - builder.Append(c.Path); + builder.Append(c); builder.Append("\""); } Args = builder.ToString(); diff --git a/src/ViewModels/WorkingCopy.cs b/src/ViewModels/WorkingCopy.cs index f1db3f3d..ce2a2ac1 100644 --- a/src/ViewModels/WorkingCopy.cs +++ b/src/ViewModels/WorkingCopy.cs @@ -353,38 +353,80 @@ namespace SourceGit.ViewModels public async void UseTheirs(List changes) { + _repo.SetWatcherEnabled(false); + var files = new List(); + var needStage = new List(); + foreach (var change in changes) { - if (change.IsConflit) + if (!change.IsConflit) + continue; + + if (change.WorkTree == Models.ChangeState.Deleted) + { + var fullpath = Path.Combine(_repo.FullPath, change.Path); + if (File.Exists(fullpath)) + File.Delete(fullpath); + + needStage.Add(change.Path); + } + else + { files.Add(change.Path); + } } - _repo.SetWatcherEnabled(false); - var succ = await Task.Run(() => new Commands.Checkout(_repo.FullPath).UseTheirs(files)); - if (succ) + if (files.Count > 0) { - await Task.Run(() => new Commands.Add(_repo.FullPath, changes).Exec()); + var succ = await Task.Run(() => new Commands.Checkout(_repo.FullPath).UseTheirs(files)); + if (succ) + needStage.AddRange(files); } + + if (needStage.Count > 0) + await Task.Run(() => new Commands.Add(_repo.FullPath, needStage).Exec()); + _repo.MarkWorkingCopyDirtyManually(); _repo.SetWatcherEnabled(true); } public async void UseMine(List changes) { + _repo.SetWatcherEnabled(false); + var files = new List(); + var needStage = new List(); + foreach (var change in changes) { - if (change.IsConflit) + if (!change.IsConflit) + continue; + + if (change.Index == Models.ChangeState.Deleted) + { + var fullpath = Path.Combine(_repo.FullPath, change.Path); + if (File.Exists(fullpath)) + File.Delete(fullpath); + + needStage.Add(change.Path); + } + else + { files.Add(change.Path); + } } - _repo.SetWatcherEnabled(false); - var succ = await Task.Run(() => new Commands.Checkout(_repo.FullPath).UseMine(files)); - if (succ) + if (files.Count > 0) { - await Task.Run(() => new Commands.Add(_repo.FullPath, changes).Exec()); + var succ = await Task.Run(() => new Commands.Checkout(_repo.FullPath).UseMine(files)); + if (succ) + needStage.AddRange(files); } + + if (needStage.Count > 0) + await Task.Run(() => new Commands.Add(_repo.FullPath, needStage).Exec()); + _repo.MarkWorkingCopyDirtyManually(); _repo.SetWatcherEnabled(true); } @@ -1502,7 +1544,8 @@ namespace SourceGit.ViewModels private async void StageChanges(List changes, Models.Change next) { - if (changes.Count == 0) + var count = changes.Count; + if (count == 0) return; // Use `_selectedUnstaged` instead of `SelectedUnstaged` to avoid UI refresh. @@ -1510,7 +1553,7 @@ namespace SourceGit.ViewModels IsStaging = true; _repo.SetWatcherEnabled(false); - if (changes.Count == _unstaged.Count) + if (count == _unstaged.Count) { await Task.Run(() => new Commands.Add(_repo.FullPath, _repo.IncludeUntracked).Exec()); } @@ -1527,10 +1570,13 @@ namespace SourceGit.ViewModels } else { - for (int i = 0; i < changes.Count; i += 10) + var paths = new List(); + foreach (var c in changes) + paths.Add(c.Path); + + for (int i = 0; i < count; i += 10) { - var count = Math.Min(10, changes.Count - i); - var step = changes.GetRange(i, count); + var step = paths.GetRange(i, Math.Min(10, count - i)); await Task.Run(() => new Commands.Add(_repo.FullPath, step).Exec()); } } diff --git a/src/Views/TextDiffView.axaml.cs b/src/Views/TextDiffView.axaml.cs index 28fe81a8..83bc47e3 100644 --- a/src/Views/TextDiffView.axaml.cs +++ b/src/Views/TextDiffView.axaml.cs @@ -1796,7 +1796,7 @@ namespace SourceGit.Views if (!selection.HasLeftChanges) { - new Commands.Add(repo.FullPath, [change]).Exec(); + new Commands.Add(repo.FullPath, [change.Path]).Exec(); } else { From 841276852a29c12f9da642e8d3c5f96b6cb7fce1 Mon Sep 17 00:00:00 2001 From: saxc Date: Fri, 21 Feb 2025 03:34:38 +0100 Subject: [PATCH 19/28] localization: add german translations (#1011) (cherry picked from commit fcc720480c85fe01120e555c22b6aec286ee717b) --- src/Resources/Locales/de_DE.axaml | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/src/Resources/Locales/de_DE.axaml b/src/Resources/Locales/de_DE.axaml index b6458822..c16c90b5 100644 --- a/src/Resources/Locales/de_DE.axaml +++ b/src/Resources/Locales/de_DE.axaml @@ -59,6 +59,7 @@ Mit HEAD vergleichen Mit Worktree vergleichen Branch-Namen kopieren + Benutzerdefinierte Aktion Lösche ${0}$... Lösche alle ausgewählten {0} Branches Alle Änderungen verwerfen @@ -159,6 +160,7 @@ Ausführbare Datei: Name: Geltungsbereich: + Branch Commit Repository Email Adresse @@ -586,6 +588,7 @@ LOKALE BRANCHES Zum HEAD wechseln Erstelle Branch + BENACHRICHTIGUNGEN LÖSCHEN Nur aktuellen Branch im Graphen hervorheben Öffne in {0} Öffne in externen Tools @@ -710,7 +713,7 @@ Öffne alle Repositories Öffne Repository Öffne Terminal - Klon Standardordner erneut nach Repositories durchsuchen + Klon Standardordner erneut nach Repositories durchsuchen Suche Repositories... Sortieren Änderungen From b2ab62825ece1bb0111782f094266d1445c3a110 Mon Sep 17 00:00:00 2001 From: "github-actions[bot]" Date: Fri, 21 Feb 2025 02:48:21 +0000 Subject: [PATCH 20/28] doc: Update translation status and missing keys --- README.md | 2 +- TRANSLATION.md | 5 +---- 2 files changed, 2 insertions(+), 5 deletions(-) diff --git a/README.md b/README.md index 784d0672..60c8543e 100644 --- a/README.md +++ b/README.md @@ -47,7 +47,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.20%25-yellow)](TRANSLATION.md) [![es__ES](https://img.shields.io/badge/es__ES-97.35%25-yellow)](TRANSLATION.md) [![fr__FR](https://img.shields.io/badge/fr__FR-92.18%25-yellow)](TRANSLATION.md) [![it__IT](https://img.shields.io/badge/it__IT-97.61%25-yellow)](TRANSLATION.md) [![pt__BR](https://img.shields.io/badge/pt__BR-91.91%25-yellow)](TRANSLATION.md) [![ru__RU](https://img.shields.io/badge/ru__RU-99.47%25-yellow)](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) +[![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.60%25-yellow)](TRANSLATION.md) [![es__ES](https://img.shields.io/badge/es__ES-97.35%25-yellow)](TRANSLATION.md) [![fr__FR](https://img.shields.io/badge/fr__FR-92.18%25-yellow)](TRANSLATION.md) [![it__IT](https://img.shields.io/badge/it__IT-97.61%25-yellow)](TRANSLATION.md) [![pt__BR](https://img.shields.io/badge/pt__BR-91.91%25-yellow)](TRANSLATION.md) [![ru__RU](https://img.shields.io/badge/ru__RU-99.47%25-yellow)](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) diff --git a/TRANSLATION.md b/TRANSLATION.md index 53631bc1..c235ea6a 100644 --- a/TRANSLATION.md +++ b/TRANSLATION.md @@ -1,15 +1,12 @@ -### de_DE.axaml: 99.20% +### de_DE.axaml: 99.60%
Missing Keys -- Text.BranchCM.CustomAction - Text.BranchUpstreamInvalid -- Text.Configure.CustomAction.Scope.Branch - Text.Configure.CustomAction.WaitForExit - Text.Preferences.AI.Streaming -- Text.Repository.Notifications.Clear
From 9ab602788a7bfeaf05e382d876a145547cc3e73c Mon Sep 17 00:00:00 2001 From: Ikko Eltociear Ashimine Date: Mon, 24 Feb 2025 10:28:00 +0900 Subject: [PATCH 21/28] docs: update README.md (#1014) comaptible -> compatible --- README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/README.md b/README.md index 60c8543e..256070e2 100644 --- a/README.md +++ b/README.md @@ -132,7 +132,7 @@ For **Linux** users: ## OpenAI -This software supports using OpenAI or other AI service that has an OpenAI comaptible HTTP API to generate commit message. You need configurate the service in `Preference` window. +This software supports using OpenAI or other AI service that has an OpenAI compatible HTTP API to generate commit message. You need configurate the service in `Preference` window. For `OpenAI`: From fa4caa218628169d5f34076732ffa9b35ed040fb Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?G=C3=B6ran=20W?= <44604769+goran-w@users.noreply.github.com> Date: Mon, 24 Feb 2025 02:32:19 +0100 Subject: [PATCH 22/28] enhance: add first/last buttons for block-nav, no wrapping (#1015) (#1016) Added 2 new buttons (only visible in block-nav mode), with new icons and new (en_US) strings (First/Last Difference). Implemented these new buttons, and disabled the automatic wrap-around for the prev/next buttons in block-nav mode. --- src/Resources/Icons.axaml | 2 ++ src/Resources/Locales/en_US.axaml | 2 ++ src/ViewModels/BlockNavigation.cs | 28 ++++++++++++++-- src/Views/DiffView.axaml | 28 ++++++++++++++++ src/Views/DiffView.axaml.cs | 14 ++++++++ src/Views/TextDiffView.axaml.cs | 56 +++++++++++++++++++++++++++++++ 6 files changed, 127 insertions(+), 3 deletions(-) diff --git a/src/Resources/Icons.axaml b/src/Resources/Icons.axaml index b7d9c22e..9426d20a 100644 --- a/src/Resources/Icons.axaml +++ b/src/Resources/Icons.axaml @@ -5,6 +5,7 @@ M71 1024V0h661L953 219V1024H71zm808-731-220-219H145V951h735V293zM439 512h-220V219h220V512zm-74-219H292v146h74v-146zm0 512h74v73h-220v-73H292v-146H218V585h147v219zm294-366h74V512H512v-73h74v-146H512V219h147v219zm74 439H512V585h220v293zm-74-219h-74v146h74v-146z M128 256h192a64 64 0 110 128H128a64 64 0 110-128zm576 192h192a64 64 0 010 128h-192a64 64 0 010-128zm-576 192h192a64 64 0 010 128H128a64 64 0 010-128zm576 0h192a64 64 0 010 128h-192a64 64 0 010-128zm0-384h192a64 64 0 010 128h-192a64 64 0 010-128zM128 448h192a64 64 0 110 128H128a64 64 0 110-128zm384-320a64 64 0 0164 64v640a64 64 0 01-128 0V192a64 64 0 0164-64z M832 64H192c-18 0-32 14-32 32v832c0 18 14 32 32 32h640c18 0 32-14 32-32V96c0-18-14-32-32-32zM736 596 624 502 506 596V131h230v318z + M509 546 780 275 871 366 509 728 147 366 238 275zM509 728h-362v128h724v-128z M757 226a143 143 0 00-55 276 96 96 0 01-88 59h-191a187 187 0 00-96 27V312a143 143 0 10-96 0v399a143 143 0 10103 2 96 96 0 0188-59h191a191 191 0 00187-151 143 143 0 00-43-279zM280 130a48 48 0 110 96 48 48 0 010-96zm0 764a48 48 0 110-96 48 48 0 010 96zM757 417a48 48 0 110-96 48 48 0 010 96z M896 128h-64V64c0-35-29-64-64-64s-64 29-64 64v64h-64c-35 0-64 29-64 64s29 64 64 64h64v64c0 35 29 64 64 64s64-29 64-64V256h64c35 0 64-29 64-64s-29-64-64-64zm-204 307C673 481 628 512 576 512H448c-47 0-90 13-128 35V372C394 346 448 275 448 192c0-106-86-192-192-192S64 86 64 192c0 83 54 154 128 180v280c-74 26-128 97-128 180c0 106 86 192 192 192s192-86 192-192c0-67-34-125-84-159c22-20 52-33 84-33h128c122 0 223-85 249-199c-19 4-37 7-57 7c-26 0-51-5-76-13zM256 128c35 0 64 29 64 64s-29 64-64 64s-64-29-64-64s29-64 64-64zm0 768c-35 0-64-29-64-64s29-64 64-64s64 29 64 64s-29 64-64 64z M512 597m-1 0a1 1 0 103 0a1 1 0 10-3 0ZM810 393 732 315 448 600 293 444 214 522l156 156 78 78 362-362z @@ -119,6 +120,7 @@ M996 452 572 28A96 96 0 00504 0H96C43 0 0 43 0 96v408a96 96 0 0028 68l424 424c37 37 98 37 136 0l408-408c37-37 37-98 0-136zM224 320c-53 0-96-43-96-96s43-96 96-96 96 43 96 96-43 96-96 96zm1028 268L844 996c-37 37-98 37-136 0l-1-1L1055 647c34-34 53-79 53-127s-19-93-53-127L663 0h97a96 96 0 0168 28l424 424c37 37 37 98 0 136z M765 118 629 239l-16 137-186 160 54 59 183-168 144 4 136-129 47-43-175-12L827 67zM489 404c-66 0-124 55-124 125s54 121 124 121c66 0 120-55 120-121H489l23-121c-8-4-16-4-23-4zM695 525c0 114-93 207-206 207s-206-94-206-207 93-207 206-207c16 0 27 0 43 4l43-207c-27-4-54-8-85-8-229 0-416 188-416 419s187 419 416 419c225 0 408-180 416-403v-12l-210-4z M144 112h736c18 0 32 14 32 32v736c0 18-14 32-32 32H144c-18 0-32-14-32-32V144c0-18 14-32 32-32zm112 211v72a9 9 0 003 7L386 509 259 615a9 9 0 00-3 7v72a9 9 0 0015 7L493 516a9 9 0 000-14l-222-186a9 9 0 00-15 7zM522 624a10 10 0 00-10 10v60a10 10 0 0010 10h237a10 10 0 0010-10v-60a10 10 0 00-10-10H522z + M170 831 513 489 855 831 960 726 512 278 64 726 170 831zM512 278h448v-128h-896v128h448z M897 673v13c0 51-42 93-93 93h-10c-1 0-2 0-2 0H220c-23 0-42 19-42 42v13c0 23 19 42 42 42h552c14 0 26 12 26 26 0 14-12 26-26 26H220c-51 0-93-42-93-93v-13c0-51 42-93 93-93h20c1-0 2-0 2-0h562c23 0 42-19 42-42v-13c0-11-5-22-13-29-8-7-17-11-28-10H660c-14 0-26-12-26-26 0-14 12-26 26-26h144c24-1 47 7 65 24 18 17 29 42 29 67zM479 98c-112 0-203 91-203 203 0 44 14 85 38 118l132 208c15 24 50 24 66 0l133-209c23-33 37-73 37-117 0-112-91-203-203-203zm0 327c-68 0-122-55-122-122s55-122 122-122 122 55 122 122-55 122-122 122z M912 800a48 48 0 1 1 0 96h-416a48 48 0 1 1 0-96h416z m-704-704A112 112 0 0 1 256 309.184V480h80a48 48 0 0 1 0 96H256v224h81.664a48 48 0 1 1 0 96H256a96 96 0 0 1-96-96V309.248A112 112 0 0 1 208 96z m704 384a48 48 0 1 1 0 96h-416a48 48 0 0 1 0-96h416z m0-320a48 48 0 1 1 0 96h-416a48 48 0 0 1 0-96h416z M30 0 30 30 0 15z diff --git a/src/Resources/Locales/en_US.axaml b/src/Resources/Locales/en_US.axaml index dfc17dee..d2d64d5c 100644 --- a/src/Resources/Locales/en_US.axaml +++ b/src/Resources/Locales/en_US.axaml @@ -252,9 +252,11 @@ File Mode Changed Ignore Whitespace Change LFS OBJECT CHANGE + First Difference Next Difference NO CHANGES OR ONLY EOL CHANGES Previous Difference + Last Difference Save as Patch Show hidden symbols Side-By-Side Diff diff --git a/src/ViewModels/BlockNavigation.cs b/src/ViewModels/BlockNavigation.cs index 709338f8..9a5a926c 100644 --- a/src/ViewModels/BlockNavigation.cs +++ b/src/ViewModels/BlockNavigation.cs @@ -101,12 +101,12 @@ namespace SourceGit.ViewModels return (_current >= 0 && _current < Blocks.Count) ? Blocks[_current] : null; } - public Block GotoNext() + public Block GotoFirst() { if (Blocks.Count == 0) return null; - Current = (_current + 1) % Blocks.Count; + Current = 0; return Blocks[_current]; } @@ -115,7 +115,29 @@ namespace SourceGit.ViewModels if (Blocks.Count == 0) return null; - Current = _current == -1 ? Blocks.Count - 1 : (_current - 1 + Blocks.Count) % Blocks.Count; + if (_current == -1) + Current = 0; + else if (_current > 0) + Current = _current - 1; + return Blocks[_current]; + } + + public Block GotoNext() + { + if (Blocks.Count == 0) + return null; + + if (_current < Blocks.Count - 1) + Current = _current + 1; + return Blocks[_current]; + } + + public Block GotoLast() + { + if (Blocks.Count == 0) + return null; + + Current = Blocks.Count - 1; return Blocks[_current]; } diff --git a/src/Views/DiffView.axaml b/src/Views/DiffView.axaml index aa75c2a0..fccb949d 100644 --- a/src/Views/DiffView.axaml +++ b/src/Views/DiffView.axaml @@ -34,6 +34,20 @@ + + + + (); + textDiff?.GotoFirstChange(); + e.Handled = true; + } + private void OnGotoPrevChange(object _, RoutedEventArgs e) { var textDiff = this.FindDescendantOfType(); @@ -24,5 +31,12 @@ namespace SourceGit.Views textDiff?.GotoNextChange(); e.Handled = true; } + + private void OnGotoLastChange(object _, RoutedEventArgs e) + { + var textDiff = this.FindDescendantOfType(); + textDiff?.GotoLastChange(); + e.Handled = true; + } } } diff --git a/src/Views/TextDiffView.axaml.cs b/src/Views/TextDiffView.axaml.cs index 83bc47e3..323fde03 100644 --- a/src/Views/TextDiffView.axaml.cs +++ b/src/Views/TextDiffView.axaml.cs @@ -543,6 +543,21 @@ namespace SourceGit.Views { } + public void GotoFirstChange() + { + var blockNavigation = BlockNavigation; + if (blockNavigation != null) + { + var prev = blockNavigation.GotoFirst(); + if (prev != null) + { + TextArea.Caret.Line = prev.Start; + ScrollToLine(prev.Start); + } + } + // NOTE: Not implemented (button hidden) for non-block navigation. + } + public void GotoPrevChange() { var blockNavigation = BlockNavigation; @@ -641,6 +656,21 @@ namespace SourceGit.Views } } + public void GotoLastChange() + { + var blockNavigation = BlockNavigation; + if (blockNavigation != null) + { + var next = blockNavigation.GotoLast(); + if (next != null) + { + TextArea.Caret.Line = next.Start; + ScrollToLine(next.Start); + } + } + // NOTE: Not implemented (button hidden) for non-block navigation. + } + public override void Render(DrawingContext context) { base.Render(context); @@ -1682,6 +1712,19 @@ namespace SourceGit.Views InitializeComponent(); } + public void GotoFirstChange() + { + var presenter = this.FindDescendantOfType(); + if (presenter == null) + return; + + presenter.GotoFirstChange(); + if (presenter is SingleSideTextDiffPresenter singleSide) + singleSide.ForceSyncScrollOffset(); + + BlockNavigationIndicator = BlockNavigation?.Indicator ?? string.Empty; + } + public void GotoPrevChange() { var presenter = this.FindDescendantOfType(); @@ -1708,6 +1751,19 @@ namespace SourceGit.Views BlockNavigationIndicator = BlockNavigation?.Indicator ?? string.Empty; } + public void GotoLastChange() + { + var presenter = this.FindDescendantOfType(); + if (presenter == null) + return; + + presenter.GotoLastChange(); + if (presenter is SingleSideTextDiffPresenter singleSide) + singleSide.ForceSyncScrollOffset(); + + BlockNavigationIndicator = BlockNavigation?.Indicator ?? string.Empty; + } + protected override void OnDataContextChanged(EventArgs e) { base.OnDataContextChanged(e); From 52a53cc6976df7ff153209ace0e78bb353e50d94 Mon Sep 17 00:00:00 2001 From: "github-actions[bot]" Date: Mon, 24 Feb 2025 01:32:32 +0000 Subject: [PATCH 23/28] doc: Update translation status and missing keys --- README.md | 2 +- TRANSLATION.md | 34 ++++++++++++++++++++++++---------- 2 files changed, 25 insertions(+), 11 deletions(-) diff --git a/README.md b/README.md index 256070e2..a48af9bd 100644 --- a/README.md +++ b/README.md @@ -47,7 +47,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.60%25-yellow)](TRANSLATION.md) [![es__ES](https://img.shields.io/badge/es__ES-97.35%25-yellow)](TRANSLATION.md) [![fr__FR](https://img.shields.io/badge/fr__FR-92.18%25-yellow)](TRANSLATION.md) [![it__IT](https://img.shields.io/badge/it__IT-97.61%25-yellow)](TRANSLATION.md) [![pt__BR](https://img.shields.io/badge/pt__BR-91.91%25-yellow)](TRANSLATION.md) [![ru__RU](https://img.shields.io/badge/ru__RU-99.47%25-yellow)](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) +[![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.34%25-yellow)](TRANSLATION.md) [![es__ES](https://img.shields.io/badge/es__ES-97.09%25-yellow)](TRANSLATION.md) [![fr__FR](https://img.shields.io/badge/fr__FR-91.93%25-yellow)](TRANSLATION.md) [![it__IT](https://img.shields.io/badge/it__IT-97.35%25-yellow)](TRANSLATION.md) [![pt__BR](https://img.shields.io/badge/pt__BR-91.67%25-yellow)](TRANSLATION.md) [![ru__RU](https://img.shields.io/badge/ru__RU-99.21%25-yellow)](TRANSLATION.md) [![zh__CN](https://img.shields.io/badge/zh__CN-99.74%25-yellow)](TRANSLATION.md) [![zh__TW](https://img.shields.io/badge/zh__TW-99.74%25-yellow)](TRANSLATION.md) > [!NOTE] > You can find the missing keys in [TRANSLATION.md](TRANSLATION.md) diff --git a/TRANSLATION.md b/TRANSLATION.md index c235ea6a..4e96f0ac 100644 --- a/TRANSLATION.md +++ b/TRANSLATION.md @@ -1,4 +1,4 @@ -### de_DE.axaml: 99.60% +### de_DE.axaml: 99.34%
@@ -6,11 +6,13 @@ - Text.BranchUpstreamInvalid - Text.Configure.CustomAction.WaitForExit +- Text.Diff.First +- Text.Diff.Last - Text.Preferences.AI.Streaming
-### es_ES.axaml: 97.35% +### es_ES.axaml: 97.09%
@@ -31,6 +33,8 @@ - Text.DeleteRepositoryNode.Path - Text.DeleteRepositoryNode.TipForGroup - Text.DeleteRepositoryNode.TipForRepository +- Text.Diff.First +- Text.Diff.Last - Text.Preferences.AI.Streaming - Text.Repository.Notifications.Clear - Text.Stash.AutoRestore @@ -39,7 +43,7 @@
-### fr_FR.axaml: 92.18% +### fr_FR.axaml: 91.93%
@@ -60,6 +64,8 @@ - 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 @@ -107,7 +113,7 @@
-### it_IT.axaml: 97.61% +### it_IT.axaml: 97.35%
@@ -127,6 +133,8 @@ - Text.DeleteRepositoryNode.Path - Text.DeleteRepositoryNode.TipForGroup - Text.DeleteRepositoryNode.TipForRepository +- Text.Diff.First +- Text.Diff.Last - Text.Preferences.AI.Streaming - Text.Repository.Notifications.Clear - Text.Stash.AutoRestore @@ -134,7 +142,7 @@
-### pt_BR.axaml: 91.91% +### pt_BR.axaml: 91.67%
@@ -162,6 +170,8 @@ - Text.DeleteRepositoryNode.Path - Text.DeleteRepositoryNode.TipForGroup - Text.DeleteRepositoryNode.TipForRepository +- Text.Diff.First +- Text.Diff.Last - Text.Diff.UseBlockNavigation - Text.Fetch.Force - Text.FileCM.ResolveUsing @@ -204,7 +214,7 @@
-### ru_RU.axaml: 99.47% +### ru_RU.axaml: 99.21%
@@ -213,26 +223,30 @@ - Text.BranchCM.CustomAction - Text.BranchUpstreamInvalid - Text.Configure.CustomAction.Scope.Branch +- Text.Diff.First +- Text.Diff.Last - Text.Preferences.AI.Streaming
-### zh_CN.axaml: 100.00% +### zh_CN.axaml: 99.74%
Missing Keys - +- Text.Diff.First +- Text.Diff.Last
-### zh_TW.axaml: 100.00% +### zh_TW.axaml: 99.74%
Missing Keys - +- Text.Diff.First +- Text.Diff.Last
From 124bdc97f96a30ebcd0572671aed5db26bc6ee81 Mon Sep 17 00:00:00 2001 From: leo Date: Mon, 24 Feb 2025 09:37:34 +0800 Subject: [PATCH 24/28] localization: add missing keys for zh_CN and zh_TW Signed-off-by: leo --- src/Resources/Locales/en_US.axaml | 6 +++--- src/Resources/Locales/zh_CN.axaml | 2 ++ src/Resources/Locales/zh_TW.axaml | 2 ++ 3 files changed, 7 insertions(+), 3 deletions(-) diff --git a/src/Resources/Locales/en_US.axaml b/src/Resources/Locales/en_US.axaml index d2d64d5c..1a83a4da 100644 --- a/src/Resources/Locales/en_US.axaml +++ b/src/Resources/Locales/en_US.axaml @@ -250,13 +250,13 @@ OLD Copy File Mode Changed - Ignore Whitespace Change - LFS OBJECT CHANGE First Difference + Ignore Whitespace Change + Last Difference + LFS OBJECT CHANGE Next Difference NO CHANGES OR ONLY EOL CHANGES Previous Difference - Last Difference Save as Patch Show hidden symbols Side-By-Side Diff diff --git a/src/Resources/Locales/zh_CN.axaml b/src/Resources/Locales/zh_CN.axaml index 115f917e..acfdefd2 100644 --- a/src/Resources/Locales/zh_CN.axaml +++ b/src/Resources/Locales/zh_CN.axaml @@ -253,7 +253,9 @@ 原始大小 复制 文件权限已变化 + 首个差异 忽略空白符号变化 + 最后一个差异 LFS对象变更 下一个差异 没有变更或仅有换行符差异 diff --git a/src/Resources/Locales/zh_TW.axaml b/src/Resources/Locales/zh_TW.axaml index 00933783..dd9092a4 100644 --- a/src/Resources/Locales/zh_TW.axaml +++ b/src/Resources/Locales/zh_TW.axaml @@ -253,7 +253,9 @@ 原始大小 複製 檔案權限已變更 + 第一個差異 忽略空白符號變化 + 最後一個差異 LFS 物件變更 下一個差異 沒有變更或僅有換行字元差異 From 74e5bcb7047d95e38ca116a1fe0ef2ef9c84242e Mon Sep 17 00:00:00 2001 From: "github-actions[bot]" Date: Mon, 24 Feb 2025 01:37:52 +0000 Subject: [PATCH 25/28] doc: Update translation status and missing keys --- README.md | 2 +- TRANSLATION.md | 10 ++++------ 2 files changed, 5 insertions(+), 7 deletions(-) diff --git a/README.md b/README.md index a48af9bd..a82a43b1 100644 --- a/README.md +++ b/README.md @@ -47,7 +47,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.34%25-yellow)](TRANSLATION.md) [![es__ES](https://img.shields.io/badge/es__ES-97.09%25-yellow)](TRANSLATION.md) [![fr__FR](https://img.shields.io/badge/fr__FR-91.93%25-yellow)](TRANSLATION.md) [![it__IT](https://img.shields.io/badge/it__IT-97.35%25-yellow)](TRANSLATION.md) [![pt__BR](https://img.shields.io/badge/pt__BR-91.67%25-yellow)](TRANSLATION.md) [![ru__RU](https://img.shields.io/badge/ru__RU-99.21%25-yellow)](TRANSLATION.md) [![zh__CN](https://img.shields.io/badge/zh__CN-99.74%25-yellow)](TRANSLATION.md) [![zh__TW](https://img.shields.io/badge/zh__TW-99.74%25-yellow)](TRANSLATION.md) +[![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.34%25-yellow)](TRANSLATION.md) [![es__ES](https://img.shields.io/badge/es__ES-97.09%25-yellow)](TRANSLATION.md) [![fr__FR](https://img.shields.io/badge/fr__FR-91.93%25-yellow)](TRANSLATION.md) [![it__IT](https://img.shields.io/badge/it__IT-97.35%25-yellow)](TRANSLATION.md) [![pt__BR](https://img.shields.io/badge/pt__BR-91.67%25-yellow)](TRANSLATION.md) [![ru__RU](https://img.shields.io/badge/ru__RU-99.21%25-yellow)](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) diff --git a/TRANSLATION.md b/TRANSLATION.md index 4e96f0ac..acecf990 100644 --- a/TRANSLATION.md +++ b/TRANSLATION.md @@ -229,24 +229,22 @@
-### zh_CN.axaml: 99.74% +### zh_CN.axaml: 100.00%
Missing Keys -- Text.Diff.First -- Text.Diff.Last +
-### zh_TW.axaml: 99.74% +### zh_TW.axaml: 100.00%
Missing Keys -- Text.Diff.First -- Text.Diff.Last +
From d4341c119554835d4885dd54ba15bd7fe153cf78 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Javier=20J=2E=20Mart=C3=ADnez=20M=2E?= <56406225+jjesus-dev@users.noreply.github.com> Date: Sun, 23 Feb 2025 19:45:39 -0600 Subject: [PATCH 26/28] localization: add missing spanish translations (#1017) --- src/Resources/Locales/es_ES.axaml | 20 ++++++++++++++++++++ 1 file changed, 20 insertions(+) diff --git a/src/Resources/Locales/es_ES.axaml b/src/Resources/Locales/es_ES.axaml index a0f35814..24170683 100644 --- a/src/Resources/Locales/es_ES.axaml +++ b/src/Resources/Locales/es_ES.axaml @@ -22,7 +22,9 @@ Rama de Seguimiento: Seguimiento de rama remota Asistente OpenAI + RE-GENERAR Usar OpenAI para generar mensaje de commit + APLICAR CÓMO MENSAJE DE COMMIT Aplicar Patch Error Genera errores y se niega a aplicar el patch @@ -37,6 +39,10 @@ Advertencia Genera advertencias para algunos de estos errores, pero aplica Espacios en Blanco: + Aplicar Stash + Borrar después de aplicar + Restaurar los cambios del índice + Stash: Archivar... Guardar Archivo en: Seleccionar ruta del archivo @@ -53,6 +59,7 @@ Comparar con HEAD Comparar con Worktree Copiar Nombre de Rama + Acción personalizada Eliminar ${0}$... Eliminar {0} ramas seleccionadas Descartar todos los cambios @@ -68,6 +75,7 @@ Renombrar ${0}$... Establecer Rama de Seguimiento... Comparar Ramas + ¡Upstream inválido! Bytes CANCELAR Resetear a Esta Revisión @@ -100,6 +108,7 @@ Nombre Local: Nombre del repositorio. Opcional. Carpeta Padre: + Inicializar y actualizar submodulos URL del Repositorio: CERRAR Editor @@ -152,8 +161,10 @@ Archivo Ejecutable: Nombre: Alcance: + Rama Commit Repositorio + Esperar la acción de salida Dirección de Email Dirección de email GIT @@ -202,6 +213,7 @@ Stash & Reaplicar Nombre de la Nueva Rama: Introduzca el nombre de la rama. + Los espacios serán reemplazados con guiones. Crear Rama Local Crear Etiqueta... Nueva Etiqueta En: @@ -225,8 +237,11 @@ Estás intentando eliminar múltiples ramas a la vez. ¡Asegúrate de revisar antes de tomar acción! Eliminar Remoto Remoto: + Ruta: Destino: + Todos los hijos serán removidos de la lista. Confirmar Eliminación de Grupo + ¡Esto solo lo removera de la lista, no del disco! Confirmar Eliminación de Repositorio Eliminar Submódulo Ruta del Submódulo: @@ -449,6 +464,7 @@ Modelo Nombre Servidor + Activar Transmisión APARIENCIA Fuente por defecto Tamaño de fuente @@ -576,6 +592,7 @@ RAMAS LOCALES Navegar a HEAD Crear Rama + LIMPIAR NOTIFICACIONES Resaltar solo la rama actual en el gráfico Abrir en {0} Abrir en Herramientas Externas @@ -642,6 +659,8 @@ Ruta de almacenamiento de la clave privada SSH INICIAR Stash + Restaurar automáticamente después del stashing + Tus archivos de trabajo permanecen sin cambios, pero se guarda un stash. Incluir archivos no rastreados Mantener archivos staged Mensaje: @@ -721,6 +740,7 @@ INCLUIR ARCHIVOS NO RASTREADOS NO HAY MENSAJES DE ENTRADA RECIENTES NO HAY PLANTILLAS DE COMMIT + Firmar STAGED UNSTAGE UNSTAGE TODO From 89e09d842d6f632e4c2cda52a6715983b44a2c28 Mon Sep 17 00:00:00 2001 From: "github-actions[bot]" Date: Mon, 24 Feb 2025 01:45:49 +0000 Subject: [PATCH 27/28] doc: Update translation status and missing keys --- README.md | 2 +- TRANSLATION.md | 22 +--------------------- 2 files changed, 2 insertions(+), 22 deletions(-) diff --git a/README.md b/README.md index a82a43b1..0990a39d 100644 --- a/README.md +++ b/README.md @@ -47,7 +47,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.34%25-yellow)](TRANSLATION.md) [![es__ES](https://img.shields.io/badge/es__ES-97.09%25-yellow)](TRANSLATION.md) [![fr__FR](https://img.shields.io/badge/fr__FR-91.93%25-yellow)](TRANSLATION.md) [![it__IT](https://img.shields.io/badge/it__IT-97.35%25-yellow)](TRANSLATION.md) [![pt__BR](https://img.shields.io/badge/pt__BR-91.67%25-yellow)](TRANSLATION.md) [![ru__RU](https://img.shields.io/badge/ru__RU-99.21%25-yellow)](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) +[![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.34%25-yellow)](TRANSLATION.md) [![es__ES](https://img.shields.io/badge/es__ES-99.74%25-yellow)](TRANSLATION.md) [![fr__FR](https://img.shields.io/badge/fr__FR-91.93%25-yellow)](TRANSLATION.md) [![it__IT](https://img.shields.io/badge/it__IT-97.35%25-yellow)](TRANSLATION.md) [![pt__BR](https://img.shields.io/badge/pt__BR-91.67%25-yellow)](TRANSLATION.md) [![ru__RU](https://img.shields.io/badge/ru__RU-99.21%25-yellow)](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) diff --git a/TRANSLATION.md b/TRANSLATION.md index acecf990..04e121fc 100644 --- a/TRANSLATION.md +++ b/TRANSLATION.md @@ -12,34 +12,14 @@ -### es_ES.axaml: 97.09% +### es_ES.axaml: 99.74%
Missing Keys -- 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.Preferences.AI.Streaming -- Text.Repository.Notifications.Clear -- Text.Stash.AutoRestore -- Text.Stash.AutoRestore.Tip -- Text.WorkingCopy.SignOff
From 0b7805b2ee3489de0e4b6a3b62782301fa25012b Mon Sep 17 00:00:00 2001 From: leo Date: Mon, 24 Feb 2025 09:49:30 +0800 Subject: [PATCH 28/28] version: Release 2025.06 Signed-off-by: leo --- VERSION | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/VERSION b/VERSION index 15689348..bb11b3b9 100644 --- a/VERSION +++ b/VERSION @@ -1 +1 @@ -2025.05 \ No newline at end of file +2025.06 \ No newline at end of file