In my WP8 app, i have situation where i have to navigate from one page to another and afterwards i need to reload the same page for some reasons.
MainPage.xaml --> Page1.xaml --> Page1.xaml --> Page1.xaml
When user press the backkey should go back to "MainPage.xaml" page.
I tried using the NavigationService.navigate() for navigation, some reason i couldn't able to reload the page. If i pass any unique query strings (eg: Guid) with navigation url, i am able to reload the page. But, when i press back button - it never goes back to Mainpage.xaml page.
Is there any best way to achieve this?
Pass in a query string every time you reload the page (such as your random GUID). On your OnNavigatedTo method check if the GUID query string exists. If it does exist, you know that you don't want this page on the Navigation Stack because it's the reloaded version, so you can remove it by calling NavigationService.RemoveBackEntry.
protected override void OnNavigatedTo(NavigationEventArgs e)
{
string guid = string.Empty;
if (NavigationContext.QueryString.TryGetValue("guid", out guid))
{
//guid exists therefore it's a reload, so delete the last entry
//from the navigation stack
if(NavigationService.CanGoBack)
NavigationService.RemoveBackEntry();
}
}
Use NavigationService.RemoveBackEntry method to remove last navigation stack entry.
You can also remove all elements from navigation history:
while(service.CanGoBack)
service.RemoveBackEntry();
and then add the one you're interested in.
NavigationService.Navigate(new Uri("/MainPage.xaml?" + DateTime.Now.Ticks, UriKind.Relative));
You can use it under a control to navigate to same page
Because I couldn't find any Windows 10 (Universal apps UWP UAP) questions about this, and this one seems to be top result on google search to reload a page, here is a solution:
NavigationService.Refresh();
I'm using Template 10 on my app, so I don't know if it matters here. The lib encapsulates NavigationService on its own INavigationService
Related
I am using the latest version of Prism.MVVM in Xamarin.Forms. In this, if I try to navigate to second page from the first page, the first page is initialized once again. i.e., the constructor of the first page is called once again.
For example, I am having Page1.xaml and Page2.xaml pages with their respective view models(those will be created and registered automatically while creating in prism).
I navigating to Page2 from Page1 like below,
NavigationAsync("Navigation/Page1/Page2")
While navigating, Page1.xaml's constructor is called so that the page is created newly which lead I could not able to maintain the Page1.xaml instance. Also, please note that Page1.xaml is a Master-Details page.
Is this a behavior in Prism? If so how can I overcome this?
Thanks in advance.
Navigating away from a XAML page destroys it in UWP. You can preserve a page’s state data (and avoid re-construction) by adding a single line in a XAML page’s tag:
NavigationCacheMode="Required"
Does it work the same in Xamarin?
I need to ask for a passcode every time the app was suspended (and resumed), so I have to show a corresponding page, and after the user enters the pin proceed the app resuming to the page which was shown before suspending. How can I get the page to which I have to proceed? The App.Resume event provides 2 parameters, but both of them are objects. To which type I need to cast these objects to get the proper page's type? Can I get from these parameters the proper page type at all?
I mean
private void OnResuming(object sender, object e)
{
//get the suspended page's type here
}
Thanks :)
I recommend the following:
In OnResuming simply Navigate to the passcode page, but remember the current page before.
OnResuming should look like this:
//...
// the following line returns something like e.g. "MainPage"
var pageTypeName = ((Frame)Window.Current.Content).SourcePageType.Name;
// store pageTypeName in app scope
// Navigate to passcode page ...
When passcode was entered correctly navigate to the previous page.
Second Option:
You can also try to navigate to the passcode page during "OnSuspending". The user will see the passcode page after a resume. After entering the code you can redirect the user to the previous page. Of course you also have to store the type of the current page during OnSuspending accordingly.
The code shown works fine if you have an "easy" interface without e.g. a SplitView. You probably have to tweak it a little if you are working with nested Frames etc.
I'm trying to create an App with a Login Page as the first page.
Once the user logs in, the pages that come after will be in a standard page stack organisation so I can easily use the build in Navigation object and wrap everything in Navigation pages.
e.g.
Login Page -> MainAppPage |-> Category1Page -> Cat1SubPage
|-> Category2Page -> Cat2SubPage
My understanding is that I should wrap MainAppPage with new NavigationPage(), and then I'll have access to the Navigation object allowing me to do things like this:
await this.Navigation.PushAsync(new Category1Page());
And the various platforms will give me automatic back button support to go back to the previous page.
But I don't want a user to navigate from LoginPage -> MainAppPage in this manner, because I don't want the backbutton to take them back to Login, without them explicitly hitting the logout button.
So how should I handle that first Page Transition from LoginPage -> MainApp Page.
Is there an alternative way to have 2 Primary pages and swap between them? Or is there a way to intercept the back button requests on MainAppPage and discard them?
Not finding an awful lot of info in the documentation regarding this, but it seems like a fairly standard requirement so possibly PEBKAC
I just posted a quick sample on Github for this scenario. The idea is that you want to initially navigate to your NavigationPage, then if necessary (meaning the user isn't already logged in), push the LoginPage modally. Then, on successful Login, simply pop the LoginPage from the stack. You can check out the sample here, https://github.com/jamesqquick/Xamarin-Forms-Login-Navigation/blob/master/ReadMe.MD
I can think of at least two solutions.
One way is to create a MainAppPage first and within that page show Login Page as Modal.
Other would be to create a platform specific page, load Login Page and only upon successful login navigate to MainPage using platform specific navigation (LoginPage should be NoHistory or something like that to avoid going back) not Forms navigation (i.e. in Android both pages should be separate activities). This involves a bit more work since you have to deal with the three platforms but it shouldn't be much overhead.
That said there is a better navigation supposedly coming with, hopefully, 1.3.0.
As Miha Markic said, a Modal window is a good option. One other thing you can also consider, especially if you want the login page to have the same Navigation Bar as your other pages, would be the same thing that I already posted about in the question URL below.
Basically, you would keep a reference to your NavigationPage in the App class (lets call it AppNavPage), then, when showing your login page, you put your login page within a separate NavigationPage and do a PushAsync() with your new NavigationPage and login page.
Once the user logs in successfully, you just replace the current MainPage with your old NavigationPage using this code:
Application.Current.MainPage = App.AppNavPage
Check out the link below for better code examples.
https://stackoverflow.com/a/32382852/3850012
This is what I have working on Android:
protected override void OnCreate (Bundle bundle){
base.OnCreate (bundle);
string start = "new";
Bundle extras = Intent.Extras;
if (extras != null) {
start = extras.GetString ("start");
}
if(start == "new"){
SetPage (App.GetLoginPage (OnLoginCompleted));
} else if (start == "login") {
SetPage (App.GetMainPage (OnSignOutCompleted));
}
}
void OnLoginCompleted(){
// ...
var refresh = new Intent (this, typeof(MainActivity));
refresh.PutExtra ("start", "login");
StartActivity (refresh);
Finish ();
}
void OnSignOutCompleted(){/* mirrors OnLoginCompleted */ }
This is effectively an activity with a configurable landing page. In order to change to it we restart with a different setting. It's a tiny bit slower than navigating on my phone but only just noticeable.
I think the best way would be to Remove the LoginPage from the stack once you verify login, then it's not available any longer.
async void OnLoginButtonClicked (object sender, EventArgs e)
{
...
var isValid = AreCredentialsCorrect (user);
if (isValid) {
App.IsUserLoggedIn = true;
Navigation.InsertPageBefore (new MainPage (), this);
await Navigation.PopAsync ();
} else {
// Login failed
}
}
Provided that the user's credentials are correct, the MainPage
instance is inserted into the navigation stack before the current
page. The PopAsync method then removes the current page from the
navigation stack, with the MainPage instance becoming the active page.
See full description here
I'm developing a Windows Phone application and I have three screens:
Main screen
Login selection screen.
Sign in screen.
When user has signed in and push "sign in" button I want to come back from screen 3 to screen 1.
Now I come back to screen 2 and immediately to first one. I don't want to show 2 screen.
Is it possible to do this?
Try this
Assume your pages are named as FirstPage.xaml, SecondPage.xaml, ThirdPage.xaml
//Check for the first page and remove the remaining back stack in your ThirdPage.xaml
while(!NavigationService.BackStack.First().Source.OriginalString.Contains("FirstPage"))
{
NavigationService.RemoveBackEntry();
}
NavigationService.GoBack();
Somewhere in page 3 add
NavigationService.RemoveBackEntry();
This will remove page 2 from the back stack. Now when the user hits the back key, he'll navigate directly backwards to page 1.
But as Amal Dev noted, Microsoft wants you to let the user navigate to the previous page. This rule doesn't seem to be enforced too much, it's probably meant as "never ever confuse the user". If you confuse the certificating tester, your app will fail certification.
You can use the NavigationService.Navigate method for this.
NavigationService.Navigate(new Uri( string.Format("/your page name.xaml?val={0}", ValueTextBox.Text), UriKind.Relative));
Please refer the link given below.
Simple Navigation In Windows Phone 7
As the title says...
If I start my app project with a pivot page(MainPage.xaml) and then choose to click for example the "design two" link in the databinded listbox. Is it possible to bind the "LineThree" text for the "design two" link in to a separate portrait page?
Do I have to make new portrait page for every "LineThree"-link? Or can I just generate the "MainViewModelSampleData.xaml" data to a single portrait page depending on what "LineOne"-link I click in the pivot page in the start?
Hope my question is understandable... :P
If I understand you correctly, you want to have a main page that contains a list of data, and then a details page whose contents are dependent on the item that you clicked in the main page. The answer to your question is then "yes". There are a number of ways to achieve this, some of which include global variables, a custom navigation service, storing a value in isolated storage and so on. My personal preference is to use the context of the NavigationService and to pass an ID or an index in the query string for the target page.
Your call to navigate to the details page then looks like this:
Application.Current.Navigate(string.Format("/Views/DetailsView.xaml?id={0}", id));
In the target page, you override the OnNavigatedTo handler to retrieve the value that you passed and then process it accordingly (i.e. look up the value from your database, or retrieve it from a data collection).
protected override void OnNavigatedTo(NavigationEventArgs e)
{
if (this.NavigationContext.QueryString.ContainsKey("id"))
{
var id = this.NavigationContext.QueryString["id"];
// TODO: Do what you need to with the ID.
}
else
{
// I use this condition to handle creating new items.
}
}
How is what you're trying to do different from what is created by default in a new DataBound Application? That lets you select an item in the list on the main page and then displays another page which includes the text from LineThree.
I suggest you look at the sample code created as part of a new DataBound Application.