【问题标题】:Why won't these constraints in a RelativeLayout work on a Xamarin Forms project?为什么RelativeLayout 中的这些约束不适用于Xamarin Forms 项目?
【发布时间】:2018-06-23 20:16:06
【问题描述】:

布局如下:

<?xml version="1.0" encoding="utf-8"?>
<ContentPage xmlns="http://xamarin.com/schemas/2014/forms" xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml" xmlns:views="clr-namespace:Test.Views" x:Class="Test.Views.MainPage">
    <StackLayout VerticalOptions="FillAndExpand">
        <BoxView Color="Yellow" HeightRequest="25" VerticalOptions="Start"></BoxView>
        <RelativeLayout x:Name="mainView" BackgroundColor="Red" VerticalOptions="StartAndExpand">
            <BoxView x:Name="boxA" Color="Blue" WidthRequest="50" HeightRequest="50"
                RelativeLayout.XConstraint="{Binding BoxAXConstraint}"
                RelativeLayout.YConstraint="{Binding BoxAYConstraint}">
            </BoxView>
            <BoxView x:Name="boxB" Color="Green" WidthRequest="50" HeightRequest="50"
                RelativeLayout.XConstraint="{Binding BoxBXConstraint}"
                RelativeLayout.YConstraint="{Binding BoxBYConstraint}">
            </BoxView>
        </RelativeLayout>
    </StackLayout>
</ContentPage>

我找不到在 XAML 的相对布局中指定右下角的方法,这就是为什么我将这些约束绑定到代码隐藏中的属性,如下所示:

public partial class MainPage : ContentPage
{
    public Constraint BoxAXConstraint { get; set; }
    public Constraint BoxAYConstraint { get; set; }
    public Constraint BoxBXConstraint { get; set; }
    public Constraint BoxBYConstraint { get; set; }

    public MainPage()
    {
        InitializeComponent();

        BoxAXConstraint = Constraint.RelativeToParent(parent => mainView.Width - boxA.WidthRequest);
        BoxAYConstraint = Constraint.RelativeToParent(parent => 0);
        BoxBXConstraint = Constraint.RelativeToParent(parent => mainView.Width - boxB.WidthRequest);
        BoxBYConstraint = Constraint.RelativeToParent(parent => mainView.Height - boxB.HeightRequest);

        BindingContext = this;
    }
}

这是test project,它在 Android 和 iOS 上都重现了该问题。

【问题讨论】:

标签: visual-studio xaml xamarin xamarin.forms


【解决方案1】:

RelativeLayout 对 XAML 中可以表达的内容有限制 - 例如,您不能在同一约束中引用两个不同元素的布局属性。你绝对可以用 C# 表达更多。在这种情况下,您应该能够在 XAML 中执行几乎相同的操作:

        <BoxView x:Name="boxB" Color="Green" WidthRequest="50" HeightRequest="50"
            RelativeLayout.XConstraint="{ConstraintExpression Type=RelativeToParent,
        Property=Width,Factor=1,Constant=-50}"
            RelativeLayout.YConstraint="{ConstraintExpression Type=RelativeToParent,
        Property=Height,Factor=1,Constant=-50}">
        </BoxView>

XAML 方法的缺点是,如果更改 WidthRequest 或 HeightRequest,则还需要更改约束,而在 C# 版本中,由于定义约束的方式,更改会自动考虑在内。

您可以查看AbsoluteLayout,它(与RelativeLayout 不同)试图将元素保留在屏幕上。因此,您可以在 XAML 中相当轻松地将 AbsoluteLayout 的子级定位在右下角:

AbsoluteLayout.LayoutBounds="1,1,-1,-1" AbsoluteLayout.LayoutFlags="PositionProportional"

【讨论】:

  • 我发布的代码是我实际布局的精简版。在我的布局中,我还为两个小盒子添加了一些填充,这取决于它们的尺寸,并且在右上角的小盒子的左侧旁边有第三个盒子,所以它的位置取决于框到右上角。这就是我选择使用 RelativeLayout 的原因。
  • 鉴于此,您可能会遇到在 C# 中定义的 RelativeLayout 和约束。唯一值得考虑的替代方法是通过定义一个布局(StackLayout、RelativeLayout、Grid 等)添加一些嵌套,其中包含“右上角的所有内容”,另一个包含“底部的所有内容” right" 然后使用 AbsoluteLayout 将这两个容器布局放在整个页面上的正确位置。
  • 我试试看。感谢您的建议!
猜你喜欢
  • 1970-01-01
  • 2019-03-23
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2018-07-07
相关资源
最近更新 更多