绑定x:Load,更新绑定值不会加载控件(UWP)

时间:2018-09-22 21:08:32

标签: c# xaml uwp uwp-xaml

我有一个网格元素,其x:Load属性绑定到页面中的变量:

Page.xaml

<Page>
...
    <Grid x:Name="grd" x:Load="{x:Bind LoadGrid, Mode=OneWay}">

Page.xaml.cs

public sealed partial class Page : Page
...
bool LoadGrid;

OnNavigatedTo事件处理程序接收到传递的参数后,我相应地设置LoadGrid的值:

request = (Request) e.Parameter;

if (request == null)
    LoadGrid = false;
else {
    LoadGrid = true;
    InitializeComponent(); // Tried adding this to refresh the controls.
    grd.Loaded += grd_Loaded;
}

执行grd.Loaded += grd_Loaded;行时,将引发ArgumentException:

An exception of type 'System.ArgumentException' occurred ...
Delegate to an instance method cannot have null 'this'.

我检查并且grd的值为null,即使x:Load属性为true且绑定模式为OneWay(控件“检查”绑定值的更新)

编辑

尝试1

调用this.InitializeComponent()重新初始化控件。

@touseefbsb的

ATTEMPT 2 suggested

使用MVVM方法创建用于更新属性值的事件。

ATTEMPT 3

设置加载值后尝试.FindName("grd")无效。

2 个答案:

答案 0 :(得分:2)

  

与以前的XAML平台不同,在加载可视树之前调用OnNavigated方法。

因此,您可以在页面的加载事件处理程序中注册网格的加载事件,如下所示:

protected override void OnNavigatedTo(NavigationEventArgs e)
{
    base.OnNavigatedTo(e);
    var request = e.Parameter;

    if (request == null)
        LoadGrid = false;
    else
    {
        LoadGrid = true;
        InitializeComponent();
        this.Loaded += BlankPage1_Loaded;
    }
 }

private void BlankPage1_Loaded(object sender, RoutedEventArgs e)
{
    grd.Loaded += Grd_Loaded;
}

private void Grd_Loaded(object sender, RoutedEventArgs e)
{
    Debug.WriteLine("Grd loaded.");
}

答案 1 :(得分:0)

OneWay 绑定还要求该属性使用 INotifyPropertyChanged 接口。

首先,您的 LoadGrid 应该是一个属性,而不仅是如下所示的字段

public bool LoadGrid {get; set;}

此后,您需要实现INotifyPropertyChanged,它最好与ViewModel(MVVM pattren)一起使用

通过实现创建一个 ViewModel 类。

public class PageViewModel : INotifyPropertyChanged
{
    private bool loadGrid;

    public event PropertyChangedEventHandler PropertyChanged = delegate { };


    public bool LoadGrid
    {
        get { return this.loadGrid; }
        set
        {
            this.loadGrid = value;
            this.OnPropertyChanged();
        }
    }

    public void OnPropertyChanged([CallerMemberName] string propertyName = null)
    {
        // Raise the PropertyChanged event, passing the name of the property whose value has changed.
        this.PropertyChanged(this, new PropertyChangedEventArgs(propertyName));
    }
}

之后,在您的页面中创建一个类型为 PageViewModel 的属性,例如:

public PageViewModel vm {get; set;} = new PageViewModel();

然后在OnNavigatedTo()方法中,可以根据需要设置属性。而且您无需再次调用InitializeComponent即可刷新任何内容。

if (request == null)
    vm.LoadGrid = false;
else {
    vm.LoadGrid = true;
    grd.Loaded += grd_Loaded;
}

您需要做的最后一个更改是对xaml进行一些更改,只需将其绑定到vm.LoadGrid而不是LoadGrid即可,如下所示:

<Grid x:Name="grd" x:Load="{x:Bind vm.LoadGrid, Mode=OneWay}">
  

有关数据绑定的更多详细信息:https://docs.microsoft.com/en-us/windows/uwp/data-binding/data-binding-in-depth