0
votes

Hi Xamarin Developers,

So I have one requirement where user go From Page1 -> Page2 -> Page3 -> Page4 and after Page4, He has to return back to Page2 and If he press back button he should navigate it back to Page1.

How to achieve this in Xamarin Forms.?

I tried like this,

 Navigation.RemovePage(Navigation.NavigationStack[Navigation.NavigationStack.Count - 1]);
               _ = Navigation.PopAsync(true);

But it's giving weird animation and not working properly.

Please help me on this.

1

1 Answers

1
votes

First of all: If you are using

Navigation.RemovePage(Navigation.NavigationStack[Navigation.NavigationStack.Count - 1]);

from page4, Navigation.NavigationStack.Count - 1 = 3, which is the index of page4 in the NavigationStack (page1 has index 0!).

I think you should use

Navigation.RemovePage(Navigation.NavigationStack[Navigation.NavigationStack.Count - 2]);

instead...


Further comments:

Using Shell/Xamarin.Forms 4.0

Shell, available from Xamarin.Forms 4.0, is meant to easy the management of Navigation in an Application. XF 4.0 ships in a couple of weeks, so maybe it would be worth to wait for it (X.F 4.0 is at the moment in pre-release, and you can use Shell features now if you want to give it a chance!).

The traditional way

a) In order to go back to the first page (root page) you can use

Navigation.PopToRootAsync();

b) In order to pop from page4 to page2, i also use the technique with Navigation.RemovePage, but with the difference that i perform this removal immediately after i PushAsync to page4, so once you call PopAsync() from page4, it pops directly to page2 without having to remove anything at that time (see code below). Please try it this way and let me know if you succeed :)

private async Task PushMyPage4RemovingCurrentPageFromNavigationStack()
{
    var currentPage = ((NavigationPage)mainPage).CurrentPage as MyPage3;

    await currentPage.Navigation.PushAsync(new MyPage4());

    await Task.Run(() =>
    {
        // At this point MyPage4 is already pushed, so it is now the CurrentPage.
        var newCurrentPage = ((NavigationPage)mainPage).CurrentPage;

        IReadOnlyList<Page> navStack = newCurrentPage.Navigation.NavigationStack;

        // If not moved to main thread in iOS we get:
        //
        // UIKit.UIKitThreadAccessException: UIKit Consistency error: you are 
        // calling a UIKit method that can only be invoked from the UI thread.
        //
        if (Device.RuntimePlatform == Device.iOS)

            Device.BeginInvokeOnMainThread(() => newCurrentPage.Navigation.RemovePage(navStack[navStack.Count - 2]));

        else

            newCurrentPage.Navigation.RemovePage(navStack[navStack.Count - 2]);
    });

}