90f5ad50dd
TopBar.xaml(.cs) takes the Row 0 top controls: logo/About button, REC/ON-AIR pills + status signs, avatar, Sign In/Start/End buttons. The avatar fetch (AvatarHttp/_loadedAvatarUrl/LoadAvatarImage/ShowAvatarFallback) moved into the control with async semantics preserved; the window grabs the control via FindName in its ctor and calls _topBar.RefreshAvatar() when IsConnected or AccountAvatarUrl changes (previously OnViewModelPropertyChanged -> LoadAvatarImage). AccountLight is pure binding (never touched by code-behind) so it moved with the XAML. Zero behavior change; build 0 warnings; 246 pass, only the 2 known failures. Also dropped the now-unused System.IO using from MainWindow.xaml.cs. Docs: ViewModels/index.md Phase 2 tracker updated in the same commit.
72 lines
2.2 KiB
C#
72 lines
2.2 KiB
C#
using System;
|
|
using System.IO;
|
|
using System.Net.Http;
|
|
using System.Windows.Controls;
|
|
using System.Windows.Media.Imaging;
|
|
using ytLive.Helpers;
|
|
using ytLive.ViewModels;
|
|
|
|
namespace ytLive.Controls;
|
|
|
|
public partial class TopBar : UserControl
|
|
{
|
|
private static readonly HttpClient AvatarHttp = new() { Timeout = TimeSpan.FromSeconds(15) };
|
|
private string? _loadedAvatarUrl;
|
|
|
|
public TopBar()
|
|
{
|
|
InitializeComponent();
|
|
AvatarImage.Source = null;
|
|
AvatarInitial.Visibility = System.Windows.Visibility.Collapsed;
|
|
}
|
|
|
|
public void RefreshAvatar()
|
|
{
|
|
_ = LoadAvatarImageAsync();
|
|
}
|
|
|
|
private async System.Threading.Tasks.Task LoadAvatarImageAsync()
|
|
{
|
|
var vm = DataContext as MainViewModel;
|
|
var url = vm?.AccountAvatarUrl;
|
|
if (vm is not { IsConnected: true })
|
|
{
|
|
ShowAvatarFallback(null);
|
|
return;
|
|
}
|
|
if (string.IsNullOrWhiteSpace(url))
|
|
{
|
|
AppLog.Write("Avatar: connected but no profile image URL on the session");
|
|
ShowAvatarFallback(null);
|
|
return;
|
|
}
|
|
if (url == _loadedAvatarUrl && AvatarImage.Source != null) return;
|
|
try
|
|
{
|
|
var bytes = await AvatarHttp.GetByteArrayAsync(url);
|
|
using var ms = new MemoryStream(bytes);
|
|
var bitmap = new BitmapImage();
|
|
bitmap.BeginInit();
|
|
bitmap.CacheOption = BitmapCacheOption.OnLoad;
|
|
bitmap.StreamSource = ms;
|
|
bitmap.EndInit();
|
|
bitmap.Freeze();
|
|
_loadedAvatarUrl = url;
|
|
AvatarImage.Source = bitmap;
|
|
AvatarInitial.Visibility = System.Windows.Visibility.Collapsed;
|
|
}
|
|
catch (Exception ex)
|
|
{
|
|
AppLog.Write($"Avatar load failed ({url}): {ex.Message}");
|
|
ShowAvatarFallback(vm?.AccountDisplayName);
|
|
}
|
|
}
|
|
|
|
private void ShowAvatarFallback(string? name)
|
|
{
|
|
_loadedAvatarUrl = null;
|
|
AvatarImage.Source = null;
|
|
AvatarInitial.Text = string.IsNullOrWhiteSpace(name) ? "?" : name.Substring(0, 1).ToUpperInvariant();
|
|
AvatarInitial.Visibility = System.Windows.Visibility.Visible;
|
|
}
|
|
} |