feature: supports to disable GitHub style default avatar (#1814)

Signed-off-by: leo <longshuang@msn.cn>
This commit is contained in:
leo
2025-09-17 21:18:23 +08:00
parent 0ab4926ffe
commit 2047631582
6 changed files with 91 additions and 1 deletions

View File

@@ -575,6 +575,7 @@
<x:String x:Key="Text.Preferences.General.ShowChildren" xml:space="preserve">Show children in the commit details</x:String>
<x:String x:Key="Text.Preferences.General.ShowTagsInGraph" xml:space="preserve">Show tags in commit graph</x:String>
<x:String x:Key="Text.Preferences.General.SubjectGuideLength" xml:space="preserve">Subject Guide Length</x:String>
<x:String x:Key="Text.Preferences.General.UseGitHubStyleAvatar" xml:space="preserve">Generate Github style default avatar</x:String>
<x:String x:Key="Text.Preferences.Git" xml:space="preserve">GIT</x:String>
<x:String x:Key="Text.Preferences.Git.CRLF" xml:space="preserve">Enable Auto CRLF</x:String>
<x:String x:Key="Text.Preferences.Git.DefaultCloneDir" xml:space="preserve">Default Clone Dir</x:String>

View File

@@ -579,6 +579,7 @@
<x:String x:Key="Text.Preferences.General.ShowChildren" xml:space="preserve">在提交详情页中显示子提交列表</x:String>
<x:String x:Key="Text.Preferences.General.ShowTagsInGraph" xml:space="preserve">在提交路线图中显示标签</x:String>
<x:String x:Key="Text.Preferences.General.SubjectGuideLength" xml:space="preserve">SUBJECT字数检测</x:String>
<x:String x:Key="Text.Preferences.General.UseGitHubStyleAvatar" xml:space="preserve">生成GitHub风格的默认头像</x:String>
<x:String x:Key="Text.Preferences.Git" xml:space="preserve">GIT配置</x:String>
<x:String x:Key="Text.Preferences.Git.CRLF" xml:space="preserve">自动换行转换</x:String>
<x:String x:Key="Text.Preferences.Git.DefaultCloneDir" xml:space="preserve">默认克隆路径</x:String>

View File

@@ -579,6 +579,7 @@
<x:String x:Key="Text.Preferences.General.ShowChildren" xml:space="preserve">在提交詳細資訊中顯示後續提交</x:String>
<x:String x:Key="Text.Preferences.General.ShowTagsInGraph" xml:space="preserve">在路線圖中顯示標籤</x:String>
<x:String x:Key="Text.Preferences.General.SubjectGuideLength" xml:space="preserve">提交標題字數偵測</x:String>
<x:String x:Key="Text.Preferences.General.UseGitHubStyleAvatar" xml:space="preserve">生成 GitHub 風格的預設頭像</x:String>
<x:String x:Key="Text.Preferences.Git" xml:space="preserve">Git 設定</x:String>
<x:String x:Key="Text.Preferences.Git.CRLF" xml:space="preserve">自動換行轉換</x:String>
<x:String x:Key="Text.Preferences.Git.DefaultCloneDir" xml:space="preserve">預設複製 (clone) 路徑</x:String>

View File

@@ -170,6 +170,12 @@ namespace SourceGit.ViewModels
set => SetProperty(ref _useAutoHideScrollBars, value);
}
public bool UseGitHubStyleAvatar
{
get => _useGitHubStyleAvatar;
set => SetProperty(ref _useGitHubStyleAvatar, value);
}
public bool Check4UpdatesOnStartup
{
get => _check4UpdatesOnStartup;
@@ -725,6 +731,7 @@ namespace SourceGit.ViewModels
private int _subjectGuideLength = 50;
private bool _useFixedTabWidth = true;
private bool _useAutoHideScrollBars = true;
private bool _useGitHubStyleAvatar = true;
private bool _showAuthorTimeInGraph = false;
private bool _showChildren = false;

View File

@@ -1,4 +1,5 @@
using System;
using System.Collections.Generic;
using System.Globalization;
using System.IO;
using System.Security.Cryptography;
@@ -6,6 +7,7 @@ using System.Text;
using Avalonia;
using Avalonia.Controls;
using Avalonia.Data;
using Avalonia.Interactivity;
using Avalonia.Media;
using Avalonia.Media.Imaging;
@@ -24,9 +26,25 @@ namespace SourceGit.Views
set => SetValue(UserProperty, value);
}
public static readonly StyledProperty<bool> UseGitHubStyleAvatarProperty =
AvaloniaProperty.Register<Avatar, bool>(nameof(UseGitHubStyleAvatar));
public bool UseGitHubStyleAvatar
{
get => GetValue(UseGitHubStyleAvatarProperty);
set => SetValue(UseGitHubStyleAvatarProperty, value);
}
public Avatar()
{
RenderOptions.SetBitmapInterpolationMode(this, BitmapInterpolationMode.HighQuality);
this.Bind(UseGitHubStyleAvatarProperty, new Binding()
{
Mode = BindingMode.OneWay,
Source = ViewModels.Preferences.Instance,
Path = "UseGitHubStyleAvatar"
});
}
public override void Render(DrawingContext context)
@@ -42,6 +60,34 @@ namespace SourceGit.Views
{
context.DrawImage(_img, rect);
}
else if (!UseGitHubStyleAvatar)
{
var fallback = GetFallbackString(User.Name);
var typeface = new Typeface("fonts:SourceGit#JetBrains Mono");
var label = new FormattedText(
fallback,
CultureInfo.CurrentCulture,
FlowDirection.LeftToRight,
typeface,
Bounds.Width * 0.65,
Brushes.White);
var chars = fallback.ToCharArray();
var sum = 0;
foreach (var c in chars)
sum += Math.Abs(c);
var bg = new LinearGradientBrush()
{
GradientStops = FALLBACK_GRADIENTS[sum % FALLBACK_GRADIENTS.Length],
StartPoint = new RelativePoint(0, 0, RelativeUnit.Relative),
EndPoint = new RelativePoint(0, 1, RelativeUnit.Relative),
};
Point textOrigin = new Point((Bounds.Width - label.Width) * 0.5, (Bounds.Height - label.Height) * 0.5);
context.DrawRectangle(bg, null, new Rect(0, 0, Bounds.Width, Bounds.Height), corner, corner);
context.DrawText(label, textOrigin);
}
else
{
context.DrawRectangle(Brushes.White, new Pen(new SolidColorBrush(Colors.Black, 0.3f), 0.65f), rect, corner, corner);
@@ -130,6 +176,11 @@ namespace SourceGit.Views
_img = Models.AvatarManager.Instance.Request(User.Email, false);
InvalidateVisual();
}
else if (change.Property == UseGitHubStyleAvatarProperty)
{
if (_img == null)
InvalidateVisual();
}
}
private void OnContextRequested(object sender, ContextRequestedEventArgs e)
@@ -220,6 +271,30 @@ namespace SourceGit.Views
menu.Open(this);
}
private string GetFallbackString(string name)
{
if (string.IsNullOrWhiteSpace(name))
return "?";
var parts = name.Split(' ', StringSplitOptions.RemoveEmptyEntries);
var chars = new List<char>();
foreach (var part in parts)
chars.Add(part[0]);
if (chars.Count >= 2 && char.IsAsciiLetterOrDigit(chars[0]) && char.IsAsciiLetterOrDigit(chars[^1]))
return string.Format("{0}{1}", chars[0], chars[^1]);
return name.Substring(0, 1);
}
private static readonly GradientStops[] FALLBACK_GRADIENTS = [
new GradientStops() { new GradientStop(Colors.Orange, 0), new GradientStop(Color.FromRgb(255, 213, 134), 1) },
new GradientStops() { new GradientStop(Colors.DodgerBlue, 0), new GradientStop(Colors.LightSkyBlue, 1) },
new GradientStops() { new GradientStop(Colors.LimeGreen, 0), new GradientStop(Color.FromRgb(124, 241, 124), 1) },
new GradientStops() { new GradientStop(Colors.Orchid, 0), new GradientStop(Color.FromRgb(248, 161, 245), 1) },
new GradientStops() { new GradientStop(Colors.Tomato, 0), new GradientStop(Color.FromRgb(252, 165, 150), 1) },
];
private Bitmap _img = null;
}
}

View File

@@ -46,7 +46,7 @@
<TabItem.Header>
<TextBlock Classes="tab_header" Text="{DynamicResource Text.Preferences.General}"/>
</TabItem.Header>
<Grid Margin="8" RowDefinitions="32,32,32,32,32,32,32,32,32,32,32,Auto" ColumnDefinitions="Auto,*">
<Grid Margin="8" RowDefinitions="32,32,32,32,32,32,32,32,32,32,32,32,Auto" ColumnDefinitions="Auto,*">
<TextBlock Grid.Row="0" Grid.Column="0"
Text="{DynamicResource Text.Preferences.General.Locale}"
HorizontalAlignment="Right"
@@ -163,6 +163,11 @@
IsChecked="{Binding EnableCompactFoldersInChangesTree, Mode=TwoWay}"/>
<CheckBox Grid.Row="11" Grid.Column="1"
Height="32"
Content="{DynamicResource Text.Preferences.General.UseGitHubStyleAvatar}"
IsChecked="{Binding UseGitHubStyleAvatar, Mode=TwoWay}"/>
<CheckBox Grid.Row="12" Grid.Column="1"
Height="32"
Content="{DynamicResource Text.Preferences.General.Check4UpdatesOnStartup}"
IsVisible="{x:Static s:App.IsCheckForUpdateCommandVisible}"