【问题标题】:c# Xamarin Android return response bool from AlertDialogc# Xamarin Android 从 AlertDialog 返回响应 bool
【发布时间】:2018-06-19 12:50:47
【问题描述】:

如果用户从 AlertDialog 中选择“是”,我将尝试返回布尔值 true,反之亦然。

目前它总是返回 false。似乎从未设置布尔“结果”。

public bool AskForConfirmation(string messege, Context context)
{
    bool result;

    Android.Support.V7.App.AlertDialog.Builder dialog = new Android.Support.V7.App.AlertDialog.Builder(context);

    dialog.SetPositiveButton("Yes", (sender, args) =>
    {
        result = true;
    });

    dialog.SetNegativeButton("No", (sender, args) =>
    {
        result = false;
    }).SetMessage(messege).SetTitle("System Message");


    dialog.Show();

    return result;
}

然后我调用方法

this.RunOnUiThread(() =>
{

    bool response = ioManager.AskForConfirmation("Message", this);

    Console.WriteLine("Response is " + response);

});

【问题讨论】:

  • 你调试过你的代码吗?到目前为止你尝试过什么?
  • 是的,我有,似乎正在发生的事情是它在询问用户之前设置了值。
  • 这不是问题,一旦用户单击按钮,它应该替换该值。您是否尝试将其初始化为 true 或 false ?

标签: c# android xamarin xamarin.android android-alertdialog


【解决方案1】:

您可以通过ManualResetEventTaskCompletionSource 创建一个基于Task 的对话框,这样您就可以这样称呼它:

通过 TaskCompletionSource 使用示例:

try
{
    var result = await DialogAsync.Show(this, "StackOverflow", "Does it rock?");
    Log.Debug("SO", $"Dialog result: {result}");
}
catch (TaskCanceledException ex)
{
    Log.Debug("SO", $"Dialog cancelled; backbutton, click outside dialog, system-initiated, .... ");
}

DialogAsync 通过 TaskCompletionSource 示例:

public class DialogAsync : Java.Lang.Object, IDialogInterfaceOnClickListener, IDialogInterfaceOnCancelListener
{
    readonly TaskCompletionSource<bool?> taskCompletionSource = new TaskCompletionSource<bool?>();

    public DialogAsync(IntPtr handle, Android.Runtime.JniHandleOwnership transfer) : base(handle, transfer) { }
    public DialogAsync() { }

    public void OnClick(IDialogInterface dialog, int which)
    {
        switch (which)
        {
            case -1:
                SetResult(true);
                break;
            default:
                SetResult(false);
                break;
        }
    }

    public void OnCancel(IDialogInterface dialog)
    {
        taskCompletionSource.SetCanceled();
    }

    void SetResult(bool? selection)
    {
        taskCompletionSource.SetResult(selection);
    }

    public async static Task<bool?> Show(Activity context, string title, string message)
    {
        using (var listener = new DialogAsync())
        using (var dialog = new AlertDialog.Builder(context)
                                                            .SetPositiveButton("Yes", listener)
                                                            .SetNegativeButton("No", listener)
                                                            .SetOnCancelListener(listener)
                                                            .SetTitle(title)
                                                            .SetMessage(message))
        {
            dialog.Show();
            return await listener.taskCompletionSource.Task;
        }
    }
}

通过 ManualResetEvent 使用示例:

using (var cancellationTokenSource = new CancellationTokenSource())
{
    var result = await DialogAsync.Show(this, "StackOverflow", "Does it rock?", cancellationTokenSource);
    if (!cancellationTokenSource.Token.IsCancellationRequested)
    {
        Log.Debug("SO", $"Dialog result: {result}");
    }
    else
    {
        Log.Debug("SO", $"Dialog cancelled; backbutton, click outside dialog, system-initiated, .... ");
    }
}

DialogAsync 通过 ManualResetEvent 示例:

public class DialogAsync : Java.Lang.Object, IDialogInterfaceOnClickListener, IDialogInterfaceOnCancelListener
{
    readonly ManualResetEvent resetEvent = new ManualResetEvent(false);
    CancellationTokenSource cancellationTokenSource;
    bool? result;

    public DialogAsync(IntPtr handle, Android.Runtime.JniHandleOwnership transfer) : base(handle, transfer) { }
    public DialogAsync() { }

    public void OnClick(IDialogInterface dialog, int which)
    {
        switch (which)
        {
            case -1:
                SetResult(true);
                break;
            default:
                SetResult(false);
                break;
        }
    }

    public void OnCancel(IDialogInterface dialog)
    {
        cancellationTokenSource.Cancel();
        SetResult(null);
    }

    void SetResult(bool? selection)
    {
        result = selection;
        resetEvent.Set();
    }

    public async static Task<bool?> Show(Activity context, string title, string message, CancellationTokenSource source)
    {
        using (var listener = new DialogAsync())
        using (var dialog = new AlertDialog.Builder(context)
                                                            .SetPositiveButton("Yes", listener)
                                                            .SetNegativeButton("No", listener)
                                                            .SetOnCancelListener(listener)
                                                            .SetTitle(title)
                                                            .SetMessage(message))
        {
            listener.cancellationTokenSource = source;
            context.RunOnUiThread(() => { dialog.Show(); });
            await Task.Run(() => { listener.resetEvent.WaitOne(); }, source.Token);
            return listener.result;
        }
    }
}

【讨论】:

    猜你喜欢
    • 2017-02-22
    • 2011-10-10
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多