Last active
February 24, 2021 13:12
-
-
Save yinyue200/98c576712155b8fcec629c11d994a8bb to your computer and use it in GitHub Desktop.
ContentDialog for Xamarin 3.0
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
//********************************************************* | |
// | |
// Copyright (c) yinyue200.com. All rights reserved. | |
// This code is licensed under the MIT License (MIT). | |
// THIS CODE IS PROVIDED *AS IS* WITHOUT WARRANTY OF | |
// ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING ANY | |
// IMPLIED WARRANTIES OF FITNESS FOR A PARTICULAR | |
// PURPOSE, MERCHANTABILITY, OR NON-INFRINGEMENT. | |
// | |
//********************************************************* | |
#if ANDROID | |
using Android.Support.V7.App; | |
#elif __IOS__ | |
using Moespirit.Xamarin.iOSControls; | |
#endif | |
using System; | |
using System.Collections.Generic; | |
using System.Threading.Tasks; | |
using Windows.Foundation; | |
using Xamarin.Forms; | |
namespace Windows.UI.Xaml.Controls | |
{ | |
public class ContentDialog : BindableObject | |
{ | |
public View Content | |
{ | |
get { return (View)GetValue(ContentProperty); } | |
set { SetValue(ContentProperty, value); } | |
} | |
// Using a DependencyProperty as the backing store for Content. This enables animation, styling, binding, etc... | |
public static readonly BindableProperty ContentProperty = | |
BindableProperty.Create(nameof(Content), typeof(View), typeof(ContentDialog), propertyChanged: (BindableObject obj, object old, object newobj)=> | |
{ | |
var cd = (ContentDialog)obj; | |
var cp = new ContentPage() { Content = (View)newobj }; | |
cd.NativeView = yfxsApp.Controls.Common.Page2View.ConvertToNativeView(cp); | |
}); | |
#if ANDROID | |
Android.Views.View NativeView; | |
AlertDialog dialog; | |
#elif __IOS__ | |
UIKit.UIView NativeView; | |
CustomIOSAlertView dialog; | |
#endif | |
public string CloseButtonText | |
{ | |
get { return (string)GetValue(CloseButtonTextProperty); } | |
set { SetValue(CloseButtonTextProperty, value); } | |
} | |
// Using a DependencyProperty as the backing store for CloseButtonText. This enables animation, styling, binding, etc... | |
public static readonly BindableProperty CloseButtonTextProperty = | |
BindableProperty.Create(nameof(CloseButtonText), typeof(string), typeof(ContentDialog)); | |
//public ContentDialogButton DefaultButton | |
//{ | |
// get { return (ContentDialogButton)GetValue(DefaultButtonProperty); } | |
// set { SetValue(DefaultButtonProperty, value); } | |
//} | |
//// Using a DependencyProperty as the backing store for DefaultButton. This enables animation, styling, binding, etc... | |
//public static readonly BindableProperty DefaultButtonProperty = | |
// BindableProperty.Create(nameof(DefaultButton), typeof(ContentDialogButton), typeof(ContentDialog)); | |
//public bool FullSizeDesired | |
//{ | |
// get { return (bool)GetValue(FullSizeDesiredProperty); } | |
// set { SetValue(FullSizeDesiredProperty, value); } | |
//} | |
//// Using a DependencyProperty as the backing store for FullSizeDesired. This enables animation, styling, binding, etc... | |
//public static readonly BindableProperty FullSizeDesiredProperty = | |
// BindableProperty.Create(nameof(FullSizeDesired), typeof(bool), typeof(ContentDialog)); | |
//public bool IsPrimaryButtonEnabled | |
//{ | |
// get { return (bool)GetValue(IsPrimaryButtonEnabledProperty); } | |
// set { SetValue(IsPrimaryButtonEnabledProperty, value); } | |
//} | |
//// Using a DependencyProperty as the backing store for IsPrimaryButtonEnabled. This enables animation, styling, binding, etc... | |
//public static readonly BindableProperty IsPrimaryButtonEnabledProperty = | |
// BindableProperty.Create(nameof(IsPrimaryButtonEnabled), typeof(bool), typeof(ContentDialog)); | |
//public bool IsSecondaryButtonEnabled | |
//{ | |
// get { return (bool)GetValue(IsSecondaryButtonEnabledProperty); } | |
// set { SetValue(IsSecondaryButtonEnabledProperty, value); } | |
//} | |
//// Using a DependencyProperty as the backing store for IsSecondaryButtonEnabled. This enables animation, styling, binding, etc... | |
//public static readonly BindableProperty IsSecondaryButtonEnabledProperty = | |
// BindableProperty.Create("IsSecondaryButtonEnabled", typeof(bool), typeof(ContentDialog)); | |
public string PrimaryButtonText | |
{ | |
get { return (string)GetValue(PrimaryButtonTextProperty); } | |
set { SetValue(PrimaryButtonTextProperty, value); } | |
} | |
// Using a DependencyProperty as the backing store for PrimaryButtonText. This enables animation, styling, binding, etc... | |
public static readonly BindableProperty PrimaryButtonTextProperty = | |
BindableProperty.Create(nameof(PrimaryButtonText), typeof(string), typeof(ContentDialog)); | |
public string SecondaryButtonText | |
{ | |
get { return (string)GetValue(SecondaryButtonTextProperty); } | |
set { SetValue(SecondaryButtonTextProperty, value); } | |
} | |
// Using a DependencyProperty as the backing store for SecondaryButtonText. This enables animation, styling, binding, etc... | |
public static readonly BindableProperty SecondaryButtonTextProperty = | |
BindableProperty.Create(nameof(SecondaryButtonText), typeof(string), typeof(ContentDialog)); | |
public string Title | |
{ | |
get { return (string)GetValue(TitleProperty); } | |
set { SetValue(TitleProperty, value); } | |
} | |
// Using a DependencyProperty as the backing store for Title. This enables animation, styling, binding, etc... | |
public static readonly BindableProperty TitleProperty = | |
BindableProperty.Create(nameof(Title), typeof(string), typeof(ContentDialog)); | |
public async void Hide() | |
{ | |
var args = new ContentDialogClosingEventArgs() { Result = result }; | |
Closing?.Invoke(this,args); | |
await args.od.WaitOneAsync(); | |
if (args.Cancel) | |
return; | |
#if ANDROID | |
if(dialog.IsShowing) | |
dialog.Cancel(); | |
#elif __IOS__ | |
dialog.Close(); | |
dialog.Dispose(); | |
dialog = null; | |
#endif | |
Closed?.Invoke(this, new ContentDialogClosedEventArgs() { Result = result }); | |
} | |
ContentDialogResult result; | |
public async Task<ContentDialogResult> ShowAsync() | |
{ | |
var od = new Yinyue200.OperationDeferral.OperationDeferral(); | |
od.Start(); | |
#if ANDROID | |
AlertDialog.Builder builder = new AlertDialog.Builder(Forms.Context); | |
builder.SetView(NativeView); | |
if(Title!=null) | |
{ | |
builder.SetTitle(Title); | |
} | |
if (PrimaryButtonText!=null) | |
{ | |
builder.SetPositiveButton(PrimaryButtonText, (sen,args)=> | |
{ | |
primaryclick(); | |
}); | |
} | |
if(SecondaryButtonText !=null) | |
{ | |
builder.SetNegativeButton(SecondaryButtonText, (sen, args) => | |
{ | |
secondaryclick(); | |
}); | |
} | |
if(CloseButtonText!=null) | |
{ | |
builder.SetNeutralButton(CloseButtonText, (sen, args) => | |
{ | |
closeclick(); | |
}); | |
} | |
dialog = builder.Show(); | |
#else | |
dialog = new CustomIOSAlertView(); | |
dialog.ContainerView = NativeView; | |
yfxsApp.DeveloperDebug.NeedAttention(); | |
//TODO:Settitle | |
string[] ttles = new string[3]; | |
ttles[0] = PrimaryButtonText; | |
ttles[1] = SecondaryButtonText; | |
ttles[2] = CloseButtonText; | |
var buttons = new List<string>(3); | |
foreach (var one in ttles) | |
{ | |
if (one != null) | |
buttons.Add(one); | |
} | |
dialog.CloseOnTouchUpOutside = true; | |
dialog.ButtonTitles = buttons.ToArray(); | |
dialog.ButtonClicked += (sender, e) => | |
{ | |
int newid = e.ButtonId; | |
switch(e.ButtonId) | |
{ | |
case 0: | |
if(PrimaryButtonText!=null) | |
{ | |
primaryclick(); | |
} | |
else if (SecondaryButtonText != null) | |
{ | |
secondaryclick(); | |
} | |
else | |
{ | |
closeclick(); | |
} | |
break; | |
case 1: | |
if (PrimaryButtonText != null && SecondaryButtonText != null) | |
{ | |
secondaryclick(); | |
} | |
else if(PrimaryButtonText!=null|| SecondaryButtonText != null) | |
{ | |
closeclick(); | |
} | |
break; | |
case 2: | |
closeclick(); | |
break; | |
} | |
}; | |
dialog.Show(); | |
#endif | |
Closed += (s, e) => | |
{ | |
od.Complete(); | |
}; | |
await od.WaitOneAsync(); | |
return result; | |
} | |
private void closeclick() | |
{ | |
result = ContentDialogResult.None; | |
NewMethod(CloseButtonClick); | |
} | |
private void secondaryclick() | |
{ | |
result = ContentDialogResult.Secondary; | |
NewMethod(SecondaryButtonClick); | |
} | |
private void primaryclick() | |
{ | |
result = ContentDialogResult.Primary; | |
NewMethod(PrimaryButtonClick); | |
} | |
private async void NewMethod(TypedEventHandler<ContentDialog, ContentDialogButtonClickEventArgs> clevent) | |
{ | |
try | |
{ | |
var aargs = new ContentDialogButtonClickEventArgs(); | |
clevent?.Invoke(this, aargs); | |
await aargs.od.WaitOneAsync(); | |
if (!aargs.Cancel) | |
{ | |
Hide(); | |
} | |
} | |
catch | |
{ | |
throw; | |
} | |
} | |
/// <summary> | |
/// 关闭对话框后发生。 | |
/// </summary> | |
public event TypedEventHandler<ContentDialog, ContentDialogClosedEventArgs> Closed; | |
/// <summary> | |
/// 发生对话框开始关闭之后,但它关闭之前,并在 Windows.UI.Xaml。发生 Controls.ContentDialog.Closed 事件。 | |
/// </summary> | |
public event TypedEventHandler<ContentDialog, ContentDialogClosingEventArgs> Closing; | |
/// <summary> | |
/// 对话框打开后发生。 | |
/// </summary> | |
public event TypedEventHandler<ContentDialog, ContentDialogOpenedEventArgs> Opened; | |
/// <summary> | |
/// 点击主按钮后发生。 | |
/// </summary> | |
public event TypedEventHandler<ContentDialog, ContentDialogButtonClickEventArgs> PrimaryButtonClick; | |
/// <summary> | |
/// 点击次按钮后发生。 | |
/// </summary> | |
public event TypedEventHandler<ContentDialog, ContentDialogButtonClickEventArgs> SecondaryButtonClick; | |
/// <summary> | |
/// 已点击关闭按钮后发生。 | |
/// </summary> | |
public event TypedEventHandler<ContentDialog, ContentDialogButtonClickEventArgs> CloseButtonClick; | |
} | |
//public enum ContentDialogButton | |
//{ | |
// /// <summary> | |
// /// The close button is the default. | |
// /// </summary> | |
// Close, | |
// /// <summary> | |
// /// No button is specified as the defaul | |
// /// </summary> | |
// None, | |
// /// <summary> | |
// /// The primary button is the default. | |
// /// </summary> | |
// Primary, | |
// /// <summary> | |
// /// The secondary button is the default. | |
// /// </summary> | |
// Secondary, | |
//} | |
public enum ContentDialogResult | |
{ | |
/// <summary> | |
/// No button was tapped. | |
/// </summary> | |
None, | |
/// <summary> | |
/// The primary button was tapped by the user. | |
/// </summary> | |
Primary, | |
/// <summary> | |
/// The secondary button was tapped by the user. | |
/// </summary> | |
Secondary, | |
} | |
public sealed class ContentDialogClosedEventArgs : EventArgs | |
{ | |
// | |
// 摘要: | |
// 获取 Windows.UI.Xaml。按钮的 Controls.ContentDialogResult 单击事件。 | |
// | |
// 返回结果: | |
// 按钮单击事件的结果。 | |
public ContentDialogResult Result { get; internal set; } | |
} | |
// | |
// 摘要: | |
// 为关闭事件提供数据。 | |
public sealed class ContentDialogClosingEventArgs : EventArgs | |
{ | |
// | |
// 摘要: | |
// 获取 Windows.UI.Xaml。应用可以使用异步响应结束事件的 Controls.ContentDialogClosingDeferral。 | |
// | |
// 返回结果: | |
// Windows.UI.Xaml。应用可以使用异步响应结束事件的 Controls.ContentDialogClosingDeferral。 | |
public Yinyue200.OperationDeferral.OperationDeferral GetDeferral() | |
{ | |
od.Start(); | |
return od; | |
} | |
internal Yinyue200.OperationDeferral.OperationDeferral od = new Yinyue200.OperationDeferral.OperationDeferral(); | |
// | |
// 摘要: | |
// 获取或设置一个可取消正在关闭的对话框的值。 一个 * * true * * Windows.UI.Xaml 值。Controls.ContentDialogButtonClickEventArgs.Cancel | |
// 取消默认行为。 | |
// | |
// 返回结果: | |
// 取消关闭对话框为 true;否则为 false。 | |
public bool Cancel { get; set; } | |
// | |
// 摘要: | |
// 获取 Windows.UI.Xaml。结束事件的 Controls.ContentDialogResult。 | |
// | |
// 返回结果: | |
// Windows.UI.Xaml。结束事件的 Controls.ContentDialogResult。 | |
public ContentDialogResult Result { get; internal set; } | |
} | |
public sealed class ContentDialogOpenedEventArgs : EventArgs | |
{ | |
} | |
public sealed class ContentDialogButtonClickEventArgs : EventArgs | |
{ | |
// | |
// 摘要: | |
// 获取 Windows.UI.Xaml。应用可以使用异步响应一个按钮的 Controls.ContentDialogButtonClickDeferral | |
// 单击事件。 | |
// | |
// 返回结果: | |
// Windows.UI.Xaml。应用可以使用异步响应一个按钮的 Controls.ContentDialogButtonClickDeferral 单击事件。 | |
public Yinyue200.OperationDeferral.OperationDeferral GetDeferral() | |
{ | |
od.Start(); | |
return od; | |
} | |
internal Yinyue200.OperationDeferral.OperationDeferral od = new Yinyue200.OperationDeferral.OperationDeferral(); | |
// | |
// 摘要: | |
// 获取或设置一个可取消按钮点击的值。 一个 * * true * * Windows.UI.Xaml 值。Controls.ContentDialogButtonClickEventArgs.Cancel | |
// 取消默认行为。 | |
// | |
// 返回结果: | |
// 取消按钮单击为 true;否则为 false。 | |
public bool Cancel { get; set; } | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment