Search code examples
c#androidmauipicker

.Net MAUI Capture Cancel action from picker control


So, I'm upgrading a project from Xamarin to MAUI. Most has been ok, overall minor in most parts, but stuck on a picker control.

I am good on all aspects of populating a list, binding that to the picker, getting values to/from. However, the one thing I am severely stuck on is the "Cancel" button. There appears to be no "On" event or otherwise to capture and allow me to do something when the dialog portion of the picker is closed.

Anyone know how to capture? I am running this on an Android application.

Feedback-- Unfocused. I tried the unfocused, but that is not quite enough. When the cancel is done, it remains focused in the picker control with nothing specifically checked, but I get no notification either way. I am looking to get some sort of answer like an OnCancelButton, or OnDoneButton that the modal portion action of the picker is closed out. Appreciate that thought though.


Solution

  • Here is my solution .I'm using handler to solve it.For more information ,please refer to handler.

    Platforms/Android/MyPickerHandler.cs;

    public class MyPickerHandler : PickerHandler
    {
        private AlertDialog _dialog;
       
        public MyPickerHandler()
        {
        }
    
        protected override void ConnectHandler(MauiPicker platformView)
        {
            base.ConnectHandler(platformView);
            platformView.Click += OnControlClick;
        }
    
        protected override void DisconnectHandler(MauiPicker platformView)
        {
            platformView.Click -= OnControlClick;
            base.DisconnectHandler(platformView);
        }
    
        private void OnControlClick(object sender, System.EventArgs e)
        {
           
            PlatformView.ClearFocus();
            var picker = new NumberPicker(Context);
            var model = VirtualView;
    
            if (model.Items != null && model.Items.Any())
            {
                picker.MaxValue = model.Items.Count - 1;
                picker.MinValue = 0;
                picker.SetDisplayedValues(model.Items.ToArray());
                picker.WrapSelectorWheel = false;
                picker.Value = model.SelectedIndex;
            }
    
            var layout = new LinearLayout(Context) { Orientation = Orientation.Vertical };
            layout.AddView(picker);
    
             VirtualView.IsFocused = true;
    
            var builder = new AlertDialog.Builder(Context);
            builder.SetView(layout);
            builder.SetTitle("this is a test for selection");
            //Write a cancel button business
            builder.SetNegativeButton("Cancel", (s, a) =>
            {
                VirtualView.IsFocused = false;
                PlatformView.ClearFocus();
                _dialog.Dismiss();
                PlatformView.ClearAnimation();
                MessagingCenter.Send(this, "PickerCanceled");
    
            });
    
            if (_dialog == null) {
                _dialog = builder.Create();
                _dialog.DismissEvent += (ssender, args) =>
                {
                    VirtualView.IsFocused = false;
                };
            }
            _dialog.Show();            
        }
    }
    

    MauiProgram.cs

    var builder = MauiApp.CreateBuilder();
    builder
        .UseMauiApp<App>()
        .ConfigureFonts(fonts =>
        {
            fonts.AddFont("OpenSans-Regular.ttf", "OpenSansRegular");
            fonts.AddFont("OpenSans-Semibold.ttf", "OpenSansSemibold");
        })
        .ConfigureMauiHandlers(handlers =>
           {
               handlers.AddHandler(typeof(Picker), typeof(MyPickerHandler));
           });
    

    MainPage.xaml

      <Picker  x:Name="picker" Title="select an item"  
               >
          <Picker.Items>
              <x:String>1
              </x:String>
              <x:String>2
              </x:String>
              <x:String>3
              </x:String>
          </Picker.Items>
      </Picker>
    
    

    MainPage.xaml.cs

           public MainPage()
            {
                InitializeComponent();
    
    #if ANDROID
                MessagingCenter.Subscribe<MyPickerHandler>(this, "PickerCanceled", (sender) =>
                {
    
                    picker.Unfocus();
                 
                });
    
    
    #endif    
               
    
            }