68 lines
1.9 KiB
C#
68 lines
1.9 KiB
C#
|
using System;
|
|||
|
using Avalonia;
|
|||
|
using Avalonia.Controls;
|
|||
|
using Avalonia.Interactivity;
|
|||
|
using ReactiveUI;
|
|||
|
|
|||
|
namespace DispenserUI.Views.Controls;
|
|||
|
|
|||
|
/// <summary>
|
|||
|
/// 按钮 with 加载中动画
|
|||
|
/// </summary>
|
|||
|
public class LoadingButton : Button
|
|||
|
{
|
|||
|
public static readonly StyledProperty<bool> IsLoadingProperty =
|
|||
|
AvaloniaProperty.Register<LoadingButton, bool>(nameof(IsLoading));
|
|||
|
|
|||
|
private bool _isCommandExecuting;
|
|||
|
|
|||
|
static LoadingButton()
|
|||
|
{
|
|||
|
// Register the IsLoading property to trigger a pseudo-class when it changes
|
|||
|
IsLoadingProperty.Changed.AddClassHandler<LoadingButton>((x, e) => x.UpdatePseudoClasses());
|
|||
|
}
|
|||
|
|
|||
|
public LoadingButton()
|
|||
|
{
|
|||
|
// Assign the default style of the button from 'LoadingButton.xaml'
|
|||
|
this.GetObservable(ContentProperty).Subscribe(_ => UpdatePseudoClasses());
|
|||
|
ClickEvent.AddClassHandler<LoadingButton>((x, e) => x.OnDebounceClick(e), RoutingStrategies.Bubble);
|
|||
|
}
|
|||
|
|
|||
|
public bool IsLoading
|
|||
|
{
|
|||
|
get => GetValue(IsLoadingProperty);
|
|||
|
set => SetValue(IsLoadingProperty, value);
|
|||
|
}
|
|||
|
|
|||
|
private void UpdatePseudoClasses()
|
|||
|
{
|
|||
|
PseudoClasses.Set(":loading", IsLoading);
|
|||
|
}
|
|||
|
|
|||
|
private void OnDebounceClick(RoutedEventArgs e)
|
|||
|
{
|
|||
|
if (Command is not IReactiveCommand command) return;
|
|||
|
|
|||
|
if (_isCommandExecuting || Command == null) return;
|
|||
|
|
|||
|
command.IsExecuting.Subscribe(x =>
|
|||
|
{
|
|||
|
if (x) return;
|
|||
|
_isCommandExecuting = false;
|
|||
|
SetCurrentValue(IsLoadingProperty, false);
|
|||
|
e.Handled = true;
|
|||
|
},
|
|||
|
ex => { },
|
|||
|
() => { });
|
|||
|
|
|||
|
var commandParameter = CommandParameter;
|
|||
|
// 检查命令是否可以执行
|
|||
|
if (!Command.CanExecute(commandParameter)) return;
|
|||
|
|
|||
|
_isCommandExecuting = true;
|
|||
|
SetCurrentValue(IsLoadingProperty, true);
|
|||
|
// 执行命令
|
|||
|
Command.Execute(commandParameter);
|
|||
|
}
|
|||
|
}
|