Reputation: 333
I am trying to programmatically add an ActivityIndicator to my Xamarin ContentPages that do data access. I have all of the code working great below on my Android device (a Samsung Galaxy Tab A). When I went to test it on my iOS (iPhone 7), it does not render any of the pages that are wrapped in the AbsoluteLayout. I simplified the repo down to this project that demonstrates the issue.
The full project is here: https://github.com/wadebaird/absoluteLayoutIssue
Here are the basics, I have the ContentPage below, of which I programmatically add buttons to the "MainPageStackLayout" during OnAppearing.
<?xml version="1.0" encoding="utf-8" ?>
<absolutelayoutissue:CommonContentPage
xmlns:absolutelayoutissue="clr-namespace:AbsoluteLayoutIssue"
xmlns="http://xamarin.com/schemas/2014/forms"
xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
x:Class="AbsoluteLayoutIssue.AbsoluteLayoutProgrammatic">
<absolutelayoutissue:CommonContentPage.Content>
<ScrollView>
<StackLayout x:Name="MainPageStackLayout" VerticalOptions="Start" Margin="20, 20" Spacing="25">
<Label FontSize="Large" FontAttributes="Bold" Margin="20" TextColor="Red" HorizontalTextAlignment="Center"
Text="No network connection detected, please enable a connection to use this application."
IsVisible="False" />
</StackLayout>
</ScrollView>
</absolutelayoutissue:CommonContentPage.Content>
</absolutelayoutissue:CommonContentPage>
During the constructor I call this method to programmatically add an AbsoluteLayout that wraps the ActivityIndicator and a Label:
public void AddActivityIndicator()
{
var content = this.Content;
var overlay = new AbsoluteLayout
{
HorizontalOptions = LayoutOptions.FillAndExpand,
VerticalOptions = LayoutOptions.FillAndExpand,
};
var activityIndicator = new ActivityIndicator
{
IsEnabled = true,
HorizontalOptions = LayoutOptions.FillAndExpand,
//Use the same color as the school text color as it should contrast the background the same.
Color = Color.Black,
};
var activityMessage = new Label
{
IsEnabled = true,
HorizontalOptions = LayoutOptions.FillAndExpand,
TextColor = Color.Black,
Text = "Loading...",
};
var stackLayout = new StackLayout();
stackLayout.Children.Add(activityIndicator);
stackLayout.Children.Add(activityMessage);
activityIndicator.SetBinding(ActivityIndicator.IsVisibleProperty, nameof(ViewModel.IsBusy));
activityIndicator.SetBinding(ActivityIndicator.IsRunningProperty, nameof(ViewModel.IsBusy));
activityMessage.SetBinding(Label.IsVisibleProperty, nameof(ViewModel.IsBusy));
AbsoluteLayout.SetLayoutFlags(content, AbsoluteLayoutFlags.All);
AbsoluteLayout.SetLayoutBounds(content, new Rectangle(0f, 0f, 1, 1));
AbsoluteLayout.SetLayoutFlags(stackLayout, AbsoluteLayoutFlags.PositionProportional);
AbsoluteLayout.SetLayoutBounds(stackLayout, new Rectangle(0.5, 0.5, AbsoluteLayout.AutoSize, AbsoluteLayout.AutoSize));
overlay.Children.Add(content);
overlay.Children.Add(stackLayout);
this.Content = overlay;
}
When this is done the page loads as completely blank. When I model the page vs programmatically adding the AbsoluteLayout, it all works perfect:
<?xml version="1.0" encoding="utf-8" ?>
<absolutelayoutissue:CommonContentPage
xmlns:absolutelayoutissue="clr-namespace:AbsoluteLayoutIssue"
xmlns="http://xamarin.com/schemas/2014/forms"
xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
x:Class="AbsoluteLayoutIssue.AbsoluteLayoutModeled">
<absolutelayoutissue:CommonContentPage.Content>
<AbsoluteLayout HorizontalOptions="FillAndExpand" VerticalOptions="FillAndExpand">
<ScrollView AbsoluteLayout.LayoutFlags="All" AbsoluteLayout.LayoutBounds="0,0,1,1">
<StackLayout x:Name="MainPageStackLayout" VerticalOptions="Start" Margin="20, 20" Spacing="25">
<Label FontSize="Large" FontAttributes="Bold" Margin="20" TextColor="Red" HorizontalTextAlignment="Center"
Text="No network connection detected, please enable a connection to use this application."
IsVisible="False" />
</StackLayout>
</ScrollView>
<StackLayout AbsoluteLayout.LayoutFlags="PositionProportional" AbsoluteLayout.LayoutBounds="0.5,0.5,-1,-1">
<ActivityIndicator IsEnabled="True" HorizontalOptions="FillAndExpand" Color="Black" IsVisible="{Binding IsBusy}" IsRunning="{Binding IsBusy}" />
<Label IsEnabled="True" HorizontalOptions="FillAndExpand" TextColor="Black" Text="Loading..." IsVisible="{Binding IsBusy}"/>
</StackLayout>
</AbsoluteLayout>
</absolutelayoutissue:CommonContentPage.Content>
</absolutelayoutissue:CommonContentPage>
However I don't want to model it as I want to be able to add this code to the fly on any page in my app.
So the question is can anyone see the difference between my modeled page and my programmatically built one? If not, has anyone seen this issue before? I can't seem to find any settings on the AbsoluteLayout to get around it.
Thank you in advance.
Upvotes: 2
Views: 1932
Reputation: 333
After a day of continuing to try and figure this out I discovered that switching around the order of setting the AbsoluteLayout on the Page.Content and then adding it's children fixed the rendering / layout issue:
overlay.Children.Add(content);
overlay.Children.Add(stackLayout);
this.Content = overlay;
needs to be like this:
this.Content = overlay;
overlay.Children.Add(content);
overlay.Children.Add(stackLayout);
Upvotes: 3