CarouselView not showing on Android if in a modal page - xamarin

I am trying to handle a login/registration form inside a CarouselView (https://github.com/alexrainman/CarouselView). In my MainPage, I have this:
protected override async void OnAppearing()
{
base.OnAppearing();
// Is user logged in?
if (!(bool)Application.Current.Properties["IsLoggedIn"]) // He is not logged in
{
await this.Navigation.PushModalAsync(new LoginRegistrationPage());
}
}
LoginRegistrationPage contains a CarouselView and its first page is the registration form, while the second page is the login form.
iOS is fine, but on Android I get a blank page. The CarouselView is visible everywhere except that in a modal page. (I have tried to set LoginRegistrationPage as MainPage and to put it inside a simple Navigation rather than a modal one, both work).

It was a bug of CarouselView.
This solved: https://github.com/alexrainman/CarouselView/pull/329

Related

How to create a custom WebView Control Xamarin forms

I am trying to create a custom control for webview, i am trying to get a checkbox inside a webview Reason :- we have a bunch of text to be displayed and unless the user reaches the end of the scroll he cannot move to the next page and at the end of the scroll there is a checkbox where user has to check the the checkbox and then he can process. here i have tried putting the checkbox and webview inside the stacklayout but the issue is webview have its own scroll bar and and stacklayout scroll bar does not work when a user try to scroll as the webview scroller scrolls out also when i try to close the Webview Page with back button the webview gets close and not the page
i am not sure what approach should i apply here.
i am getting my html data from my webapi.
anyone with some solution would be appreciable
here is my custom renderer which i have wrote but the piece missing here is how can i add another xamarin control inside this
public class CustomPdfViewRenderer : WebViewRenderer
{
public CustomPdfViewRenderer(Context context) : base(context)
{
}
protected override void OnElementChanged(ElementChangedEventArgs<WebView> e)
{
base.OnElementChanged(e);
if (Control != null)
{
Control.Settings.BuiltInZoomControls = true;
Control.Settings.DisplayZoomControls = false;
Control.Settings.LoadWithOverviewMode = true;
Control.Settings.UseWideViewPort = true;
}
}
}
You can try the following approach:
Add checkbox to HTML
When the user check checkbox call some JavaScript function
When JavaScript function is called, call C# function (Xamarin) which will enable the user to process to the next page (or some other Xamarin side stuff)
Here is how you can call C# function from JavaScript :HybridWebView

Is it possible to use modal page in Tabbed pages in Xamarin Forms?

As what my title says, is it possible to use modal page when you click a tab in Xamarin Forms?
What I would like to do it when I click one of my 5 tabs it would open a Modal page. If it's possible can someone please show my some example of how it is done or point me to the right way.
Sure, it is possibile but a bit tricky.
Create a blank page (for example FakePage) and add it to the TabbedPage.Children
In the TabbedPage code behind override OnCurrentPageChanged, check when your fakepage is selected, then open a Modal.
When the modal is opened tell your TabbedPage to go back to the previous tab (so when the user closes the modal it doesnt see a blank page)
Your tabbed page childrens
<views:Page1 Title="First tab" />
<views:Page2 Title="Second Tab" />
<views:FakePage Title="Modal tab" />
Tabbed page code behind
private Page _lastPage;
protected override async void OnCurrentPageChanged()
{
if (CurrentPage is FakePage)
{
await Navigation.PushModalAsync(new YourModalPage());
//Wait a bit for the modal to open, then reselect the last tab
//This is useful when a user close the modal: you dont want to show a blank page
await Task.Delay(150);
CurrentPage = _lastPage;
}
else
{
_lastPage = CurrentPage;
}
base.OnCurrentPageChanged();
}
Going off of what Giampaolo said, the following method might be a bit smoother:
protected override async void OnCurrentPageChanged()
{
if (CurrentPage is FakePage)
{
CurrentPage = _lastPage;
await Navigation.PushModalAsync(new YourModalPage());
}
else
{
_lastPage = CurrentPage;
}
base.OnCurrentPageChanged();
}
That way, you won't ever see the blank fake page during the transition.

Menu button not visible on MasterDetailPage after removing previous page

The main page of the app is set to a NavigationPage.
I have a common scenario where I have a login page (ContentPage) and then I navigate to app's main page (MasterDetailPage).
The code I run on login page is something like this:
var mainPage = new MasterDetailTestPage();
await this.Navigation.PushAsync(mainPage);
this.Navigation.RemovePage(this); // remove login page
The issue is the menu button is not visible on the MasterDetailPage.
If instead of this I set the main page to MasterDetailPage on app start like this:
MainPage = new NavigationPage (new MasterDetailTestPage());
in this case the menu button is shown. But this only works if it's set at the beginning. It doesn't work if app starts with login page and then setting MainPage.
It looks like the MasterDetailTestPage doesn't display menu button unless it's the root page of NavigationPage.
I reproduced this on a sample app too.
MasterDetailPage with button will only appear if it sets in root page a NavigationPage. In your case you shoud do something like this.
public partial class App : Application
{
public App()
{
InitializeComponent();
MainPage = new NavigationPage(new MenuPage());
}
The MenuPage Contains the MasterDetailPage with a List, and then when navigates to another page(LoginPage) you can do your logic and then :
public async void login_clicked(object sender ,EventArgs e)
{
//.....your logic
await Navigation.PopToRootAsync();
}
So now you can return and navigate to your MasterDetailPage with a visible button, because it removes all pages that was in stack. I hope it helps you.

Strange NavigationBar behaviour in Xamarin Forms

I have a Login page that is the starting point of my application. This page has navigation bar hidden with the following code:
NavigationPage.SetHasNavigationBar(this, false);
From Login page I start my Dashboard page using the following code:
Navigation.PushAsync(new Dashboard());
I do this on two seperate places inside my Login page. First place is inside constructor of Login page where I check for active user session and the second place is inside method that handles button click for login.
So I call Navigation.PushAsync() like this:
1st way:
public Login()
{
NavigationPage.SetHasNavigationBar(this, false);
InitializeComponent();
var loginSession = App.DataService.CheckUserSession();
if(loginSession != null)
{
Navigation.PushAsync(new Dashboard());
}
}
2nd way:
public void OnLogin(object o, EventArgs e)
{
Navigation.PushAsync(new Dashboard());
}
And this is where things start to go strange. If I open my Dasboard page with button click (using 2nd example) the Dasboard page gets loaded normally and has it's own NavigationBar. However everytime that I open Dasboard page when user session is found (using 1st way), my Dasboard page will have missing NavigationBar. To make things even more strange, if I navigate from Dasboard page to another page (lets say Settings) and then return back to Dasboard, navigation bar will then work normally on Dasboard page. I have tried removing the code that hides navigation bar on Login page NavigationPage.SetHasNavigationBar(this, false);
and what this does is that Login page will have it's navigation bar shown, but upon navigation to Dashboard (using 1st way), navigation bar will remain the same as on Login page.
I was maybe wondering if the problem lies within the fact that all my pages (Login, Dashboard and Settings) are child's of ContentPage and would have to instead inherit from NavigationPage?
I am really confused about what's happening with my NavigationBar at this moment.
It's because the Dashboard page is being pushed from inside the Login constructor. Instead, override OnAppearing() and do it there:
protected override async void OnAppearing()
{
base.OnAppearing();
await Navigation.PushAsync(new Dashboard());
}
Also, your children pages should inherit from ContentPage as nesting NavigationPages could lead to other issues :)

Showing different toolbar buttons on each page with Xamarin Forms

I have 2 pages in my Xamarin Forms app. My first page has 4 icons in the toolbar. My second page is a login page and has a tick and a cross in the toolbar.
I can't get the login page to show any icons unless I make it a navigation page. I also have to clear ToolBarItems on the first page before calling PushAsync() otherwise it complains there are too many toolbar items.
If I call PopAsync() on the login page it does not return to the first page. I'm guessing this is due to their being 2 navigation pages. I also tried PopToRootAsync().The back button works however.
My question is - how do I show different toolbar icons on 2 different pages in a way that allows navigation to work?
I'm testing this on Windows Phone 8.0
Here is the code calling the login page:
private async void ShowLoginPage()
{
ToolbarItems.Clear();
var page = new NavigationPage(new LoginPage());
await Navigation.PushAsync(page);
}
and here is the code to return to the first page:
private void Cancel()
{
Navigation.PopToRootAsync();
}
I'm running Xamarin.Forms v1.2.2.6243
One thing you could try is to keep your Login Page inside of a NavigationPage, and then instead of running PopAsync() within the Login Page after they have logged in successfully, simply replace the MainPage with your old Navigation page:
In your App class:
public NavigationPage AppNavPage = new NavigationPage(new FirstPage());
public App() {
MainPage = AppNavPage;
}
In your FirstPage:
private async void ShowLoginPage() {
ToolbarItems.Clear();
var page = new NavigationPage(new LoginPage());
await Navigation.PushAsync(page);
}
In Login Page:
private async void OnCreateClicked(object sender, EventArgs e) {
bool loginInfoIsGood = CheckLoginInfo(); //Check their login info
if(loginInfoIsGood) {
Application.Current.MainPage = App.AppNavPage;
}
}
Otherwise, I have also done a custom renderer for the NavigationRenderer on iOS to insert toolbar items onto the right side of the Navigation Bar and have overridden some Menu related stuff on Android to change the icon text/colors.
One option that you have, and one that I implemented in my own app, is a custom renderer that removes the navigation header from the app and then you could build your own custom header. With this approach, you do lose some of the native feel of the app, and you have to implement much of the transitional functionality your self. However, it gives you alot more control over the look.
CustomRenderer that removes the navigationBar:
//add using statements
// add all view here that need this custom header, might be able to build a
//base page that others inherit from, so that this will work on all pages.
[assembly: ExportRenderer(typeof(yourView), typeof(HeaderRenderer))]
class HeaderRenderer : PageRenderer
{
public override void ViewWillAppear(bool animated)
{
base.ViewWillAppear(animated);
this.NavigationController.SetNavigationBarHidden(true, true);
}
}
After this you can build a header view that can be placed on the top of every page (I am using xaml) so I don't know if it is relevant in you application.
Edit: You might need to change this renderer for differnt page types.

Resources