using System;
using System.Diagnostics;
using System.IO;
using AsyncAwaitBestPractices;
using Avalonia;
using Avalonia.Controls;
using Avalonia.Controls.Presenters;
using Avalonia.Logging;
using FluentAvalonia.UI.Controls;
using StabilityMatrix.Core.Processes;
using Symbol = FluentIcons.Common.Symbol;
namespace StabilityMatrix.Avalonia.Controls;
///
/// Like , but with a link icon left of the text content.
///
public class HyperlinkIconButton : Button
{
private Uri? _navigateUri;
///
/// Defines the property
///
public static readonly DirectProperty NavigateUriProperty =
AvaloniaProperty.RegisterDirect(
nameof(NavigateUri),
x => x.NavigateUri,
(x, v) => x.NavigateUri = v
);
///
/// Gets or sets the Uri that the button should navigate to upon clicking. In assembly paths are not supported, (e.g., avares://...)
///
public Uri? NavigateUri
{
get => _navigateUri;
set => SetAndRaise(NavigateUriProperty, ref _navigateUri, value);
}
public static readonly StyledProperty IconProperty = AvaloniaProperty.Register<
HyperlinkIconButton,
Symbol
>("Icon", Symbol.Link);
public Symbol Icon
{
get => GetValue(IconProperty);
set => SetValue(IconProperty, value);
}
protected override Type StyleKeyOverride => typeof(HyperlinkIconButton);
///
protected override void OnPropertyChanged(AvaloniaPropertyChangedEventArgs change)
{
base.OnPropertyChanged(change);
// Update icon
if (change.Property == NavigateUriProperty)
{
var uri = change.GetNewValue();
if (uri is not null && uri.IsFile && Icon == Symbol.Link)
{
Icon = Symbol.Open;
}
}
}
protected override void OnClick()
{
base.OnClick();
if (NavigateUri is null)
return;
// File or Folder URIs
if (NavigateUri.IsFile)
{
var path = NavigateUri.LocalPath;
if (Directory.Exists(path))
{
ProcessRunner
.OpenFolderBrowser(path)
.SafeFireAndForget(ex =>
{
Logger.TryGet(LogEventLevel.Error, $"Unable to open directory Uri {NavigateUri}");
});
}
else if (File.Exists(path))
{
ProcessRunner
.OpenFileBrowser(path)
.SafeFireAndForget(ex =>
{
Logger.TryGet(LogEventLevel.Error, $"Unable to open file Uri {NavigateUri}");
});
}
}
// Web
else
{
try
{
Process.Start(
new ProcessStartInfo(NavigateUri.ToString()) { UseShellExecute = true, Verb = "open" }
);
}
catch
{
Logger.TryGet(LogEventLevel.Error, $"Unable to open Uri {NavigateUri}");
}
}
}
protected override bool RegisterContentPresenter(ContentPresenter presenter)
{
return presenter.Name == "ContentPresenter";
}
}