为什么数据绑定不起作用?

时间:2010-12-14 18:07:53

标签: c# wpf data-binding

我有这样的汽车级:

public class car
{
    public String Name {get; private set;}

    public car(string name)
    {
      this.Name = name;
    }
}

我还有一个userControl:

public partial class CarListItem : UserControl
{
    private Car car;

    public CarListItem (Car car)
    {
        InitializeComponent();
        this.car= car;
    }

}

使用xaml:

<Grid>
     <Label Content="{Binding Path=car.Name}" Name="lblCarName"/>
</Grid>

但数据绑定不起作用。我做错了什么?

我想在userControl上显示汽车的名称。

4 个答案:

答案 0 :(得分:2)

你不需要在汽车......前面加上绑定表达式。

<Grid>
     <Label Content="{Binding Name}" Name="lblCarName"/>
</Grid>

...此外,您需要设置DataContext

UserControl
public partial class CarListItem : UserControl
{
    public CarListItem (Car car)
    {
        InitializeComponent();

        this.DataContext = car;
    }
}

另外我的假设是你将一个名字传递给汽车的ctor,然后是一个空字符串或null。

答案 1 :(得分:1)

要使绑定生效,您需要在Control的DataContext属性中包含值。它也可以继承。因此,子控件也可以访问父级DataContext,如果他们没有。{/ p>

除非与Self Binding一起使用,否则属性(甚至不公开)对绑定没有帮助。

要使代码正常工作,

替换

this.car = car;

使用

this.DataContext = car;

并替换

<Label Content="{Binding Path=car.Name}" Name="lblCarName"/>

使用

<Label Content="{Binding Path=Name}" Name="lblCarName"/>

答案 2 :(得分:0)

您的绑定绑定到datacontext的car.Name。在您的情况下,DataContext为NULL。

您有几种选择:

  1. 将数据上下文设置为CarListItem实例
  2. 指定绑定源。
  3. 第一种选择通常更好。

    更好的想法是为DataTemplate定义Car,并使用Car列表而不是明确的CarListItem

    <DataTemplate DataType="{x:Type local:Car}">
        <Grid>
            <Label Content="{Binding Path=Name}"/>
        </Grid>
    </DataTemplate>
    

    现在,您可以在列表中将此模板用作ItemTemplate

答案 3 :(得分:-1)

使用this.DataContext工作,但它既脆弱又可怕,并不是设计应用程序的好方法。如果我要使用你的用户控件并写下这个xaml:

<CarListItem DataContext="{Binding MyThing}" />

...无论Car属性是否正确设置,您的控件都会中断。那不是很漂亮。

更强大的方法是使用UserControl在Xaml中标记x:Name元素,并在绑定中使用ElementName。所以,你的控件看起来像这样:

<UserControl x:Name="control" ....... (namespaces/etc here)>
  <Grid>
    <Label Content="{Binding Car.Name, ElementName=control}" Name="lblCarName"/>
  </Grid>

现在,如果您想在DataContext上设置Grid(使用DataContext="{Binding Car, ElementName=control}"),您可以更加健壮地获得datacontext的好处。

但是,要使其中任何一个工作,您需要将car字段作为属性公开,而不是仅仅作为字段。您还需要实现INotifyPropertyChanged,以便在更改属性值时实现UI,但您可以通过在之前设置car 来临时解决此问题,并调用{{ 1}}在你的构造函数中。