ant-design-blazor/components/alert/Alert.razor.cs
Patrick 3da9e703fa feat(module: alert): add message template and loop banner demo (#1250)
* feat(Alert): added alert loop component

* fix: move cmp into main

* feat: add parameters for looping text

* feat: add new messages loop

* fix: create new internal looptext cmp

* doc: add demo

* doc: add demo markdown

* doc: update alert api

* doc: update cn docs

* fix: add missing dependency

* fix: update param name

* impleement loop text with css

* fix the document

Co-authored-by: James Yeung <shunjiey@hotmail.com>
2021-04-04 19:03:18 +08:00

195 lines
5.5 KiB
C#

using System.Threading.Tasks;
using AntDesign.JsInterop;
using Microsoft.AspNetCore.Components;
using Microsoft.AspNetCore.Components.Web;
using System.Collections.Generic;
namespace AntDesign
{
/// <summary>
/// Alert component for feedback.
/// </summary>
public partial class Alert : AntDomComponentBase
{
/// <summary>
/// Called when close animation is finished
/// </summary>
[Parameter]
public EventCallback<MouseEventArgs> AfterClose { get; set; }
/// <summary>
/// Whether to show as banner
/// </summary>
[Parameter]
public bool Banner { get; set; } = false;
/// <summary>
/// Whether Alert can be closed
/// </summary>
[Parameter]
public bool Closable { get; set; } = false;
/// <summary>
/// Close text to show
/// </summary>
[Parameter]
public string CloseText { get; set; }
/// <summary>
/// Additional content of Alert
/// </summary>
[Parameter]
public string Description { get; set; }
/// <summary>
/// Custom icon, effective when showIcon is true
/// </summary>
[Parameter]
public RenderFragment Icon { get; set; }
/// <summary>
/// Content of Alert
/// </summary>
[Parameter]
public string Message { get; set; }
[Parameter]
public RenderFragment MessageTemplate { get; set; }
/// <summary>
/// Whether to show icon.
/// </summary>
[Parameter]
public bool? ShowIcon { get; set; }
/// <summary>
/// Type of Alert styles, options: success, info, warning, error
/// </summary>
[Parameter]
public string Type { get; set; }
/// <summary>
/// Callback when Alert is closed.
/// </summary>
[Parameter]
public EventCallback<MouseEventArgs> OnClose { get; set; }
/// <summary>
/// Additional Content
/// </summary>
[Parameter]
public RenderFragment ChildContent { get; set; }
/// <summary>
/// Icon to show.
/// </summary>
protected string IconType => CalcType switch
{
AlertType.Success => "check-circle",
AlertType.Info => "info-circle",
AlertType.Warning => "exclamation-circle",
AlertType.Error => "close-circle",
_ => "exclamation-circle",
};
/// <summary>
/// Indicator if the component is closed or not.
/// </summary>
private bool _isClosed;
/// <summary>
/// Just before we close the component we set this indicator to show a closing animation.
/// </summary>
private bool _isClosing;
private int _motionStage;
private int _height;
private string _innerStyle = string.Empty;
private bool IsShowIcon => (Banner && ShowIcon == null) ? true : ShowIcon == true;
private string CalcType => Type ?? (Banner ? AlertType.Warning : AlertType.Info);
/// <summary>
/// Sets the default classes.
/// </summary>
private void SetClassMap()
{
string prefixName = "ant-alert";
ClassMapper
.Add("ant-alert")
.GetIf(() => $"{prefixName}-{CalcType}", () => !string.IsNullOrEmpty(CalcType))
.If($"{prefixName}-no-icon", () => !IsShowIcon)
.If($"{prefixName}-closable", () => Closable)
.If($"{prefixName}-banner", () => Banner)
.If($"{prefixName}-with-description", () => !string.IsNullOrEmpty(Description) || ChildContent != null)
.If($"{prefixName}-motion", () => _isClosing)
.If($"{prefixName}-motion-leave", () => _isClosing)
.If($"{prefixName}-motion-leave-active", () => _isClosing && _motionStage == 1)
.If($"{prefixName}-rtl", () => RTL)
;
}
/// <summary>
/// Start-up code.
/// </summary>
protected override void OnInitialized()
{
base.OnInitialized();
SetClassMap();
}
protected override async Task OnAfterRenderAsync(bool firstRender)
{
await base.OnAfterRenderAsync(firstRender);
if (firstRender)
{
Element element = await JsInvokeAsync<Element>(JSInteropConstants.GetDomInfo, Ref);
_height = element.clientHeight;
}
}
/// <summary>
/// Handles the close callback.
/// </summary>
/// <param name="args"></param>
/// <returns></returns>
protected async Task OnCloseHandler(MouseEventArgs args)
{
if (OnClose.HasDelegate)
{
await OnClose.InvokeAsync(args);
}
await PlayMotion();
if (AfterClose.HasDelegate)
{
await AfterClose.InvokeAsync(args);
}
}
private async Task PlayMotion()
{
_isClosing = true;
_innerStyle = $"max-height:{_height}px;";
await InvokeAsync(StateHasChanged);
_motionStage = 1;
await InvokeAsync(StateHasChanged);
await Task.Delay(50);
_innerStyle = string.Empty;
await InvokeAsync(StateHasChanged);
await Task.Delay(300);
_isClosed = true;
}
}
}