0

今天我在尝试做的时候变得疯狂,我认为,很简单的事情。

我希望能够创建我的用户控件,并在我的数据网格的列模板中使用它

我已经搜索并尝试了几种组合,但似乎没有任何效果

谁能帮我?

public class User
{
    public string Name { get; set; }
    public bool IsValid { get; set; }
}

partial class MyControl : UserControl
{
    private string _value;
    public string Value
    {
        get { return _value; }
        set { _value = value;
            txt.Text = value;
        }
    }
    public MyControl()
    {
        InitializeComponent();
    }
}

<Grid x:Name="LayoutRoot" Background="White">
    <TextBlock x:Name="txt" Text="[undefined]"></TextBlock>
</Grid>

public partial class MainPage : UserControl
{
    public MainPage()
    {
        InitializeComponent();

        var items = new List<User>();
        items.Add(new User{Name = "user 1", IsValid = true});
        items.Add(new User { Name = "user 2", IsValid = false });

        myGrid.ItemsSource = items;

    }
}

<Grid x:Name="LayoutRoot" Background="White">

    <sdk:DataGrid x:Name="myGrid" AutoGenerateColumns="False" IsReadOnly="True">
        <sdk:DataGrid.Columns>
            <sdk:DataGridTemplateColumn Header="Name">
                <sdk:DataGridTemplateColumn.CellTemplate>
                    <DataTemplate>
                        <SilverlightApplication1:MyControl Value="{Binding Name}"></SilverlightApplication1:MyControl>
                        <!--<TextBlock Text="{Binding Name}"></TextBlock>-->
                    </DataTemplate>
                </sdk:DataGridTemplateColumn.CellTemplate>
            </sdk:DataGridTemplateColumn>

        </sdk:DataGrid.Columns>
    </sdk:DataGrid>

</Grid>

编辑: 我也尝试了以下方法,但在我的网格上没有得到任何结果:

<Grid x:Name="LayoutRoot" Background="White">
    <TextBlock x:Name="txt" Text="{Binding Value}"></TextBlock>
</Grid>

   public partial class MyControl : UserControl
    {
    public DependencyProperty ValueProperty =
        DependencyProperty.Register("Value",
        typeof(string),
        typeof(MyControl),
         new PropertyMetadata(OnValueChanged));


    public string Value
    {
        get
        {
            return (string)GetValue(ValueProperty);
        }
        set
        {
            SetValue(ValueProperty, value);
            NotifyPropertyChanged("Value");
        }
    }

    private static void OnValueChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
    {
        ((MyControl) d).Value = (String)e.NewValue; //ERROR: here I got always empty string
    }

    public MyControl()
    {
        InitializeComponent();
    }
}
4

2 回答 2

1

您的第一个代码不起作用的原因很简单。为了能够在“MyControl”(Value={Binding Name})上绑定“Value”属性,它必须是一个依赖属性。您在第二段代码中修复了它。

这是我所做的(效果很好):

<UserControl x:Class="BusinessApplication8_SOF_Sandbox.Controls.MyControl"
             xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
             xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
             xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
             xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
             mc:Ignorable="d"
             d:DesignHeight="300" d:DesignWidth="400" Name="myControl">
    <Grid x:Name="LayoutRoot" Background="White">
        <TextBlock Name="textBlock" Text="{Binding Value, ElementName=myControl}"/>
    </Grid>
</UserControl>

其余的,我使用了你的代码。

另一种可能性,如果您只希望数据沿一个方向流动(从源到目标的“一种方式”),这应该没问题,因为使用TextBlock控件时的情况是更新Text“OnValueChanged”中的属性。这是 Value 属性的代码:

public static readonly DependencyProperty ValueProperty =
        DependencyProperty.Register("Value", typeof(string), typeof(MyControl),
            new PropertyMetadata("", OnValueChanged));
public string Value
{
   get { return (string)GetValue(ValueProperty); }
   set { SetValue(ValueProperty, value); }
}
private static void OnValueChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
{
   var target = (MyControl)d;
   var oldValue = (string)e.OldValue;
   var newValue = target.Value;
   target.OnValueChanged(oldValue, newValue);
}
protected virtual void OnValueChanged(string oldValue, string newValue)
{
    textBlock.Text = newValue;
} 

您可以删除 xaml 中的绑定:

<TextBlock Name="textBlock" />

这也对我有用。

希望这可以帮助 ;)

于 2011-05-02T12:48:23.180 回答
0

您需要在 User 类中实现 INotifyPropertyChanged 接口,以便绑定的用户控件知道是否有任何绑定的属性发生更改。有关如何实现它的详细信息,请参见以下页面:http ://www.silverlightshow.net/tips/How-to-implement-INotifyPropertyChanged-interface.aspx

如您所见,您需要实现接口并在设置器中引发事件 OnPropertyChanged

然后它应该与您的绑定一起使用。

最好的,蒂姆

于 2011-05-02T11:31:19.050 回答