How to navigate from detail Page to Master Detail Page? [closed] - visual-studio

Closed. This question needs details or clarity. It is not currently accepting answers.
Want to improve this question? Add details and clarify the problem by editing this post.
Closed 6 years ago.
Improve this question
The button from detail page cannot go to a master detail page. It keeps displaying error "break exception". Maybe I am not implementing this right. Please help :(

Master detail page does not work like that. You do not navigate from master to detail and back. Master is always available but on Phone it slides out like a drawer and on tablet it is present along with the detail page if not intentionally hidden.
public class App : Application
{
MasterDetailPage masterdetail;
Page detailpage;
Page masterpage;
protected override void OnStart()
{
masterdetail= new MasterDetailPage();
detailpage = new MyDetailPage();
masterpage = new Page();
masterdetail.Master = masterpage;
masterdetail.Detail = detailpage;
MainPage = masterdetail;
}
}
On Phone
With the above example you would see the detailpage only unless you slide out left to right or change the masterdetail.IsPresented to true in code.
On Tablet
If masterdetail.IsPresent is true the masterpage would show to the left and the detail to the right without any other code modifying this.
IsPresented
What you may be looking for is accessing the IsPresented field from a button click.
public partial class MyDetailPage : ContentPage
{
Button abutton;
MyDetailPage()
{
abutton = new Button();
abutton.click += (o,s) => {App.masterdetail.IsPresented == true ? false : true}
}
}
General Usage
The general intention of this layout design being that that master page leads to sub navigation detail pages in something like a Contacts List -> Specific Contact Details type relationship.
https://developer.xamarin.com/guides/xamarin-forms/user-interface/navigation/master-detail-page/
Navigation To MasterDetail From Other Page
button.click += (o,s) =>
{
var detailpage = new Page();
var masterpage = new Page();
var masterdetailpage = new MasterDetailPage();
masterdetailpage.Master = masterpage;
masterdetailpage.Detail = detailpage;
App.Current.MainPage = masterdetailpage;
}
Doing the Same Thing From Xaml with Commands
The below example creates a command in the page's.cs code and binds it to to a button on the xaml for the page.
public partial class CurrentPage : ContentPage
{
private ICommand goToMasterDetailCommand;
public ICommand goToMasterDetail
{
return goToMasterDetailCommand ?? (goToMasterDetailCommand = new Command(async () => await ExecuteGoToMasterDetail()));
}
private async Task ExecuteGoToMasterDetail()
{
var detailpage = new Page();
var masterpage = new Page();
var masterdetailpage = new MasterDetailPage();
masterdetailpage.Master = masterpage;
masterdetailpage.Detail = detailpage;
App.Current.MainPage = masterdetailpage;
}
}
<Button
x:Name="GoToButton"
Text="Go To Master Detail"
HorizontalOptions="FillAndExpand"
Command="{Binding goToMasterDetail}"
IsVisible="true">

Please try
Application.Current.MainPage = new MasterDetailsPage();
Upon button click

Related

How do I close all pages after changing an item's data?

I have a doubt in Xamarin forms, I have an application that I would like after finishing the training, it closes all the training screens and only the main screen remains, today I got a cod that does this, but when I restart the app and I login,
when he closes the screens instead of going back to the main screen he goes back to the login, I'm not using masterpage, could that be it?
source:
private async void BtnVoltar_Clicked(object sender, EventArgs e)
{
int numModals = Application.Current.MainPage.Navigation.ModalStack.Count;
// Pop each modal in the stack
for (int currModal = 0; currModal < numModals; currModal++)
{
await Application.Current.MainPage.Navigation.PopModalAsync();
}
await Navigation.PushModalAsync(new TabbedPageMenu());
}
Image Link
https://imgur.com/pOVVYBu
Another doubt would be after updating the data of an item, if it is possible to close the two screens and update it on the main screen
image link2
https://imgur.com/ZpevVNg
You can use the method to navigate to the different pages instead of close the pages.
The code in xaml you can add the command to do the navigation.
Command="{Binding NavigateCommand}"
CommandParameter="{x:Type views:targetpagename}"
The code in xaml.cs or viewmodel
public ICommand NavigateCommand { get; private set; }
public MainPage()
{
InitializeComponent();
NavigateCommand = new Command<Type>(
async (Type pageType) =>
{
Page page = (Page)Activator.CreateInstance(pageType);
await Navigation.PushAsync(page);
});
BindingContext = this;
}

Do I create a new Navigation Page or Content Page when making a tabbed application?

I want to create an application with tabs. I don't need the functionality of a Navigation page that allows me to go back to the last screen. I just want the tab bar to allow me to select one of five pages.
Here's the code I have so far:
public partial class MainPage : TabbedPage
{
public MainPage()
{
InitializeComponent();
My question is which of the following should I use. Note that HomePage inherits from ContentPage.
// this is the one the app uses now. Do I really need to NavigationPage and then inside that another page HomePage?
var homePage = new NavigationPage(new HomePage())
{
Title = "Home",
Icon = "ionicons_2_0_1_home_outline_25.png"
};
// I thought this would be better but ContentPage constructor cannot take an argument
var homePage = new ContentPage(new HomePage())
{
Title = "Home",
Icon = "ionicons_2_0_1_home_outline_25.png"
};
// this is my latest thought but would like to hear from others
var homePage = new HomePage()
{
Title = "Home",
Icon = "ionicons_2_0_1_home_outline_25.png"
};
Children.Add(homePage);
It's recommended that a TabbedPage should be populated with
NavigationPage and ContentPage instances only. This will help to ensure
a consistent user experience across all platforms.
The quote above is from the official TabbedPage documentation.
You don't have to wrap a ContentPage by NavigationPage if it is not needed.
If HomePage is inheriting from a ContentPage then you can just create an instance of it and add to children the next way:
var homePage = new HomePage
{
Title = "Home",
Icon = "ionicons_2_0_1_home_outline_25.png"
};
Children.Add(homePage);
P.S.: Official documentation has covered navigation topics quite nicely. Please get familiar with it.

How to hide navigation Toolbar icon in xamarin?

I want to hide navigation bar button in xamarin. how can i do that using binding. Toolbar item doesn't have "IsVisible" property.
Following is my xaml code
please help me to sort out this issue.
I would suggest to build a bindable ToolBoxItem. That way you can control the visibility through a view model property.
An implementation could look like that:
public class BindableToolbarItem : ToolbarItem
{
public static readonly BindableProperty IsVisibleProperty = BindableProperty.Create(nameof(IsVisible), typeof(bool), typeof(BindableToolbarItem), true, BindingMode.TwoWay, propertyChanged: OnIsVisibleChanged);
public bool IsVisible
{
get => (bool)GetValue(IsVisibleProperty);
set => SetValue(IsVisibleProperty, value);
}
private static void OnIsVisibleChanged(BindableObject bindable, object oldvalue, object newvalue)
{
var item = bindable as BindableToolbarItem;
if (item == null || item.Parent == null)
return;
var toolbarItems = ((ContentPage)item.Parent).ToolbarItems;
if ((bool)newvalue && !toolbarItems.Contains(item))
{
Device.BeginInvokeOnMainThread(() => { toolbarItems.Add(item); });
}
else if (!(bool)newvalue && toolbarItems.Contains(item))
{
Device.BeginInvokeOnMainThread(() => { toolbarItems.Remove(item); });
}
}
}
As you have discovered yourself there is not IsVisible. So you will have to implement functionality like that yourself if you still want it.
Another way would be to handle it in the pages' code-behind and remove or add the toolbar item whenever needed.
Adding and removing is simple, just add and remove items to the ToolbarItems collection: ToolbarItems.RemoveAt(0); for instance will remove the first toolbar item.
Putting #Gerald answer in action, it would be done this way:
void Done_Clicked(System.Object sender, System.EventArgs e)
{
//Do somthing and hide the done item
ShowDoneToolbarItem(false, (ToolbarItem)sender);
}
void Entry_Focused(System.Object sender, Xamarin.Forms.FocusEventArgs e)
{
//Show the done item
ShowDoneToolbarItem(true);
}
void ShowDoneToolbarItem(bool show, ToolbarItem item = null)
{
if(show)
{
ToolbarItem done = new ToolbarItem();
done.Text = "Done";
done.Clicked += Done_Clicked;
ToolbarItems.Add(done);
}
else if(item != null)
{
ToolbarItems.Remove(item);
}
}
This is cleaner and works from the code behind.
Well we need the IsVisible property for the front end, as xamarin doesn't have it, you can use Device.RuntimePlatform to check in real time which device the application is running. Since my code is in .cs of the XAML file, we can use xaml .cs to insert items into the screen.I put if () to do the logic and check if my device is on which platform, because I don't want it to display in UWP a toolbar.
The code is in .cs of the XAML file:
public kingTest()
{
InitializeComponent();
if((Device.RuntimePlatform == "Android")||(Device.RuntimePlatform == "iOS"))
{
ToolbarItem toolbar = new ToolbarItem();
toolbar.IconImageSource = "ic_ToolBar.png";
this.ToolbarItems.Add(toolbar);
}
};
I've achieved this easily using overloaded constructors. Here's an example:
View (add the name property):
<ContentPage x:Name="ContentPage"
<!-- rest of the tag -->
/>
Code-behind (add the toolbar items):
public partial class ExamplePage : ContentPage
{
public ExamplePage()
{
InitializeComponent();
BindingContext = this;
var saveToolbarItem = new ToolbarItem { Text = "Save" };
saveToolbarItem.Clicked += YourMethodToBeRan;
ContentPage.ToolbarItems.Add(saveToolbarItem);
}
public ExamplePage(Object object)
{
InitializeComponent();
BindingContext = this;
var updateToolbarItem = new ToolbarItem { Text = "Update" };
updateToolbarItem.Clicked += YourMethodToBeRan;
var deleteToolbarItem = new ToolbarItem { Text = "Delete" };
deleteToolbarItem.Clicked += YourMethodToBeRan;
ContentPage.ToolbarItems.Add(updateToolbarItem);
ContentPage.ToolbarItems.Add(deleteToolbarItem);
}
// rest of the class
}
The above pseudocode will add the "Save" toolbar item when the class is instantiated with no parameter, or the "Update" and "Delete" when a parameter is provided.
This isn't as elegant as IsEnabled / IsVisible booleans but it's a step in the right direction. Following this train of thought, you could modify the children of your toolbar during runtime to "show" and "hide" by adding and removing them as children.
Good luck!
I don't know if #tequila slammer's solution fully worked on Xamarin, but for us it only kind of works in .Net Maui (the evolution of Xamarin) and binding the IsVisible property to a variable.
Once the BindableToolbarItem is removed from the ContentPage's list of ToolbarItems, it is disconnected from the object that IsVisible is bound to forever.
For example: We want to use this control to hide or show a ToolbarItem that navigates to the admin screen, if I log in as the administrator on app launch, the item is there...great. If I then log out and log in as a non-admin, the item is not there...perfect. If I then log out and log in as an admin, the item is not there (the propertyChanged: OnIsVisibleChanged never fired)...:-(.
Not a big deal for us, if you want admin access then stopping the app and starting the app to log in as the admin is not a big ask.
In the newest release with .Net 7 the workaround works never more !
The reason is because the toolbar item which revomed will destoyed !

Xamarin.Forms Pages are merging together

When I navigate to a new page, adding it to the stack, if it is not full height of the page, it shows part of that page and part of the previous page (like a modal). I have a Xamarin.Forms app which uses a master detail page. I have upgraded to Xamarin.Forms Nuget 2.3.3.168 and am on the latest Xamarin version for Visual Studio.
I also checked the Navigation stack when going to a new page and everything looks correct. I have 1 master page which is the menu and the detail page has a navigation page with more pages in the stack, they just display partially on top of each other.
The only other thing I have changed is when I needed to initialize my App() constructor by setting the MainPage to a new MasterDetail page because it was failing if I did not do that in the constructor for Android. Any ideas?
Here is my App.cs:
public App()
{
InitializeComponent();
var masterDetailPage = new MasterDetailPage
{
Master = new Page() { Title = "Title" },
Detail = new Page(),
IsPresented = false
};
App.Current.MainPage = masterDetailPage;
}
Then, when I figure out if the user is logged in or not, I reset the master detail page with this function:
public static void SetMainPage(Page newPage)
{
var rootPage = new NavigationPage(newPage) { BarBackgroundColor = Color.White};
_nav.Initialize(rootPage);
_dialogService.Initialize(rootPage);
App.Current.MainPage = new MasterDetailPage
{
Master = new Menu(),
Detail = rootPage,
BindingContext = new MowMagicMobileViewModelBase(),
IsPresented = false
};
}
Then from there I call Navigation PushAsync() to pop a page onto the stack.
Wow it was actually that I just did not set a background color at all. I guess if you do not explicitly set it for the page it is transparent, unless that gets inherited from somewhere?
I dont know if its the solution but i have masterdetail page too..
But my page is like this
Master = new MenuPage();// it is a content page
Detail = new NavigationPage(new HomePage());
try it to see
If you want to change background i did sth like that
public class NavigationPageBase:NavigationPage
{
public NavigationPageBase (ContentPage c):base(c)
{
/*if (c.GetType().Equals(typeof(LoginPage)))
SetHasNavigationBar(c, false);
else
SetHasNavigationBar(c, true);*/
SetHasNavigationBar(c, true);
BarBackgroundColor = Styles.toolbarColor;
BackgroundColor = Styles.bgPageColor;
}
}
and for detailpage you can use it for example like
Detail = new NavigationPageBase (new HomePage ());
And from your App() constructor you can do simply
MainPage = new MyMasterDetailPage();
Hope it helps

How do you switch between two different Xamarin Form pages?

I'm trying to figure out how to switch between two different pages in Xamarin Forms.
I do not wish to use a NavigationPage (which has that little back arrow that is auto displayed.
I have a Login page (which is a ContentPage) and once the person has authenticated, I then need to navigate to my Dashboard page (which is a TabbedPage).
eg.
Next, one of the Tab's in the TabbedPage is the profile of the logged in user. As such, I need to log them out. So i'll have a button to log them out, which means I will need to navigate them back to the Login page (which was that ContentPage).
I feel like I have two modes the user might be in.
UnAuthorized. (ContentPage)
Authorized. (TabbedPage).
It's like I need to change the App's MainPage to be either one of those two?
To change MainPage to another just do:
App.Current.MainPage = new NavigationPage(new MyContentPage());
or
App.Current.MainPage = new MyContentPage();
BTW: You can use a NavigationPage and then HIDE the toolbar with:
NavigationPage.SetHasNavigationBar(this, false);
You can do navigation as usual by setting MainPage in your Application instance. Small sample.
namespace TestNavigation
{
public class App : Application
{
public App ()
{
// The root page of your application
MainPage = new MyPage1 ();
}
}
}
namespace TestNavigation
{
public class MyPage1 : ContentPage
{
public MyPage1 ()
{
var button = new Button () {
Text = "Click me"
};
button.Clicked += (object sender, EventArgs e) => {
Application.Current.MainPage = new MyPage2 ();
};
Content = new StackLayout {
Children = {
button
}
};
}
}
}
namespace TestNavigation
{
public class MyPage2 : ContentPage
{
public MyPage2 ()
{
Content = new StackLayout {
Children = {
new Label { Text = "Hello ContentPage" }
}
};
}
}
}
EDIT1
I submitted this answer but then I realised that I probably don't understand your problem.
EDIT2
Updated sample.
If you like to switch between the pages then you can simply do
Application.Current.MainPage=new YourPage();
How to Change MainPage in xamarin forms at runtime?
this is what i have done to get result
For a login page, the best practice is to use
await Navigation.PushModalAsync (new LoginPage());
Once you are on the LoginPage, you can use popModelAsync after the validation is passed:
await Navigation.PopModalAsync ();

Resources