Saltar al contenido

Cómo manejar / cancelar la navegación hacia atrás en Xamarin Forms

Solución:

Muy bien, después de muchas horas descubrí este. Tiene tres partes.

# 1 Manejo del botón de retroceso del hardware en Android. Este es fácil, anule OnBackButtonPressed. Recuerde, esto es solo para un botón de retroceso de hardware y Android. No manejará el botón de retroceso de la barra de navegación. Como puede ver, estaba tratando de retroceder a través de un navegador antes de salir de la página, pero puede poner la lógica que necesite.

  protected override bool OnBackButtonPressed()
    {
        if (_browser.CanGoBack)
        {
            _browser.GoBack();
            return true;
        }
        else
        {
            //await Navigation.PopAsync(true);
            base.OnBackButtonPressed();
            return true;
        }
    }

# 2 Botón de navegación hacia atrás de iOS. Este fue realmente complicado, si miras en la web, encontrarás un par de ejemplos de cómo reemplazar el botón Atrás con un nuevo botón personalizado, pero es casi imposible lograr que se parezca a tus otras páginas. En este caso, hice un botón transparente que se encuentra encima del botón normal.

[assembly: ExportRenderer(typeof(MyAdvantagePage), typeof

(MyAdvantagePageRenderer))]
namespace Advantage.MyAdvantage.MobileApp.iOS.Renderers
{
    public class MyAdvantagePageRenderer : Xamarin.Forms.Platform.iOS.PageRenderer
    {
        public override void ViewWillAppear(bool animated)
        {
            base.ViewWillAppear(animated);

            if (((MyAdvantagePage)Element).EnableBackButtonOverride)
            {
                SetCustomBackButton();
            }
        }
        private void SetCustomBackButton()
        {
            UIButton btn = new UIButton();
            btn.Frame = new CGRect(0, 0, 50, 40);
            btn.BackgroundColor = UIColor.Clear;

            btn.TouchDown += (sender, e) =>
            {
                // Whatever your custom back button click handling
                if (((MyAdvantagePage)Element)?.
                CustomBackButtonAction != null)
                {
                    ((MyAdvantagePage)Element)?.
                       CustomBackButtonAction.Invoke();
                }
            };
            NavigationController.NavigationBar.AddSubview(btn);
        }
    }
}

Android es complicado. En versiones anteriores y versiones futuras de Formularios, una vez corregidos, simplemente puede anular el OnOptionsItemselected así

       public override bool OnOptionsItemSelected(IMenuItem item)
    {
        // check if the current item id 
        // is equals to the back button id
        if (item.ItemId == 16908332)
        {
            // retrieve the current xamarin forms page instance
            var currentpage = (MyAdvantagePage)
            Xamarin.Forms.Application.
            Current.MainPage.Navigation.
            NavigationStack.LastOrDefault();

            // check if the page has subscribed to 
            // the custom back button event
            if (currentpage?.CustomBackButtonAction != null)
            {
                // invoke the Custom back button action
                currentpage?.CustomBackButtonAction.Invoke();
                // and disable the default back button action
                return false;
            }

            // if its not subscribed then go ahead 
            // with the default back button action
            return base.OnOptionsItemSelected(item);
        }
        else
        {
            // since its not the back button 
            //click, pass the event to the base
            return base.OnOptionsItemSelected(item);
        }
    }

Sin embargo, si está utilizando FormsAppCompatActivity, debe agregar a su OnCreate en MainActivity esto para configurar su barra de herramientas:

Android.Support.V7.Widget.Toolbar toolbar = this.FindViewById<Android.Support.V7.Widget.Toolbar>(Resource.Id.toolbar);
            SetSupportActionBar(toolbar);

¡Pero espera! Si tiene una versión demasiado antigua de .Forms o una versión demasiado nueva, aparecerá un error cuando la barra de herramientas sea nula. Si esto sucede, la forma en que lo hice funcionar para hacer una fecha límite es así. En OnCreate en MainActivity:

        MobileApp.Pages.Articles.ArticleDetail.androdAction = () =>
        {
            Android.Support.V7.Widget.Toolbar toolbar = this.FindViewById<Android.Support.V7.Widget.Toolbar>(Resource.Id.toolbar);
            SetSupportActionBar(toolbar);
        };

ArticleDetail es una página y androidAction es una Action que ejecuto en OnAppearing si la plataforma es Android en mi página. En este punto de su aplicación, la barra de herramientas ya no será nula.

Un par de pasos más, el renderizado de iOS que hicimos anteriormente usa propiedades que necesita agregar a cualquier página para la que esté creando el renderizador. Lo estaba haciendo para mi MyAdvantagePage clase que hice, que implementa ContentPage. Entonces en mi MyAdvantagePage clase que agregué

public Action CustomBackButtonAction { get; set; }

        public static readonly BindableProperty EnableBackButtonOverrideProperty =
               BindableProperty.Create(
               nameof(EnableBackButtonOverride),
               typeof(bool),
               typeof(MyAdvantagePage),
               false);

        /// <summary>
        /// Gets or Sets Custom Back button overriding state
        /// </summary>
        public bool EnableBackButtonOverride
        {
            get
            {
                return (bool)GetValue(EnableBackButtonOverrideProperty);
            }
            set
            {
                SetValue(EnableBackButtonOverrideProperty, value);
            }
        }

Ahora que todo está hecho, en cualquiera de mis MyAdvantagePage Puedo agregar esto

:


 this.EnableBackButtonOverride = true;
            this.CustomBackButtonAction = async () =>
            {
                if (_browser.CanGoBack)
                {
                    _browser.GoBack();
                }
                else
                {
                    await Navigation.PopAsync(true);
                }
            };

Eso debería ser todo para que funcione en el hardware de Android y la navegación de regreso tanto para Android como para iOS.

Tiene razón, en su clase de página anular OnBackButtonPressed y volver true si desea evitar la navegación. Me funciona bien y tengo la misma versión.

protected override bool OnBackButtonPressed()
{
    if (Condition)
        return true;
    return base.OnBackButtonPressed();
}

Dependiendo de lo que esté buscando exactamente (no recomendaría usar esto si simplemente desea cancelar la navegación del botón de retroceso), OnDisappearing puede ser otra opción:

protected override void OnDisappearing()
{
       //back button logic here
}
¡Haz clic para puntuar esta entrada!
(Votos: 0 Promedio: 0)



Utiliza Nuestro Buscador

Deja una respuesta

Tu dirección de correo electrónico no será publicada. Los campos obligatorios están marcados con *