Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

AbsoluteLayout Doesn't Fill Screen

I have an issue with absolute layout in Xamarin Forms on android 6.0 Marshmellow

when setting a view to fill the entire screen there is left a 1px gap at the bottom of the screen.

Bizarrely it doesn't occur if you rotate the screen to landscape. Or on 4.4

xaml :

<?xml version="1.0" encoding="utf-8" ?>
<ContentPage xmlns="http://xamarin.com/schemas/2014/forms"
             xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
             x:Class="XamarinTest.Page1">
  <AbsoluteLayout BackgroundColor="White">
    <BoxView BackgroundColor="Red" AbsoluteLayout.LayoutBounds="0,0,1,1" AbsoluteLayout.LayoutFlags="All">

    </BoxView>
  </AbsoluteLayout>
</ContentPage>

screen shots : (these are from the vs emulators but i also get the same behavior on devices, eg samsung galaxy 6)

1px white line on 6.0.0 (you are gona have to zoom)

In this example I use a boxview fillign the screen, but its any sort of placement aligned to the bottom of the screen.

what I'm looking for is some sort of workaround or custom renderer which will ensure that items drawn at 1,1 or stretching the full height of the screen, are placed at, or stretch to the bottom of the screen

like image 907
Ewan Avatar asked Apr 18 '16 11:04

Ewan


1 Answers

That's a confirmed bug in Xamarin.Forms 2.1.0: https://bugzilla.xamarin.com/show_bug.cgi?id=40092.

You can try to fix it by overriding LayoutChildren and sending one height pixel more to the base implementation.

public class MyAbsoluteLayout : AbsoluteLayout
{
    protected override void LayoutChildren(double x, double y, double width, double height)
    {
        base.LayoutChildren(x, y, width, height+1);
    }
}

And then use it in your XAML

<local:MyAbsoluteLayout BackgroundColor="White">
  <BoxView BackgroundColor="Red" AbsoluteLayout.LayoutBounds="0,0,1,1" AbsoluteLayout.LayoutFlags="All">

  </BoxView>
</local:MyAbsoluteLayout>

If this doesn't help, you could try to reimplement the LayoutChildren function and manipulate the outcome like

public class MyAbsoluteLayout : AbsoluteLayout
{
    private readonly MethodInfo _computeLayout;

    public MyAbsoluteLayout()
    {
        _computeLayout = typeof(AbsoluteLayout).GetTypeInfo().GetDeclaredMethod("ComputeLayoutForRegion");
    }

    protected override void LayoutChildren(double x, double y, double width, double height)
    {
        foreach (View logicalChild in Children)
        {
            Size region = new Size(width, height);
            Rectangle layoutForRegion = (Rectangle)_computeLayout.Invoke(null, new object[] { logicalChild, region });
            layoutForRegion.X += x;
            layoutForRegion.Y += y + 1;
            Rectangle bounds = layoutForRegion;
            logicalChild.Layout(bounds);
        }
    }
}
like image 167
Sven-Michael Stübe Avatar answered Sep 22 '22 21:09

Sven-Michael Stübe