使用MVVM和WPF绑定问题

时间:2016-04-10 15:03:07

标签: c# wpf mvvm view binding

我是C#的新手。 我在绑定方面遇到了麻烦。我将离开这里的代码示例,希望你能帮助我找到麻烦。

FriendsView

<UserControl x:Class="WpfWHERE.View.FriendsView"
         xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
         xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
         xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" 
         xmlns:d="http://schemas.microsoft.com/expression/blend/2008" 
         xmlns:local="clr-namespace:WpfWHERE.View"
         xmlns:ViewModel="clr-namespace:WpfWHERE.ViewModel"
         xmlns:data = "clr-namespace:WpfWHERE.Model"
         mc:Ignorable="d" 
         d:DesignHeight="600" d:DesignWidth="800">
<UserControl.DataContext>
    <ViewModel:FriendsViewModel/>
</UserControl.DataContext>
<UserControl.Resources><DataGrid x:Key="friendsList" AutoGenerateColumns="false" ItemsSource = "{Binding Student}">
        <DataGrid.Columns>
            <DataGridTemplateColumn Header="Name" Width="150">
                <DataGridTemplateColumn.CellTemplate>
                    <DataTemplate>
                        <ComboBox x:Name="cbName" SelectedItem="{Binding Path=FullName, Mode=OneWay}" ItemsSource="{Binding RelativeSource={RelativeSource AncestorType={x:Type UserControl}}}" DisplayMemberPath="Name">
                        </ComboBox>
                    </DataTemplate>
                </DataGridTemplateColumn.CellTemplate>
            </DataGridTemplateColumn>
        </DataGrid.Columns>
    </DataGrid>

FriendsViewModel

public class FriendsViewModel:AViewModel
{
    #region fields
    public DelegateCommand DeleteCommand { get; set; }
    #endregion fields

    #region constructors
    public FriendsViewModel()
    {
        LoadStudents();
        DeleteCommand = new DelegateCommand(OnDelete, CanDelete);
    }
    #endregion constructors
    public ObservableCollection<Student> Students
    {
        get;
        set;
    }

    public void LoadStudents()
    {
        ObservableCollection<Student> students = new ObservableCollection<Student>();

        students.Add(new Student { FirstName = "Mark", LastName = "Allain" ,Place = "Home"});
        students.Add(new Student { FirstName = "Allen", LastName = "Brown", Place = "China" });
        students.Add(new Student { FirstName = "Linda", LastName = "Hamerski", Place = "Je" });

        Students = students;
    }

    private Student _selectedStudent;

    public Student SelectedStudent
    {
        get
        {
            return _selectedStudent;
        }

        set
        {
            _selectedStudent = value;
            DeleteCommand.RaiseCanExecuteChanged();
        }
    }

    private void OnDelete()
    {
        Students.Remove(SelectedStudent);
    }

    private bool CanDelete()
    {
        return SelectedStudent != null;
    }
}

学生

public class StudentModel { }

public class Student : INotifyPropertyChanged
{
    private string firstName;
    private string lastName;
    private string place;

    public string FirstName
    {
        get { return firstName; }

        set
        {
            if (firstName != value)
            {
                firstName = value;
                RaisePropertyChanged("FirstName");
                RaisePropertyChanged("FullName");
            }
        }
    }

    public string LastName
    {
        get { return lastName; }

        set
        {
            if (lastName != value)
            {
                lastName = value;
                RaisePropertyChanged("LastName");
                RaisePropertyChanged("FullName");
            }
        }
    }
    public string Place
    {
        get { return place; }

        set
        {
            if (place != value)
            {
                place = value;
                RaisePropertyChanged("Place");
            }
        }
    }

    public string FullName
    {
        get
        {
            return firstName + " " + lastName;
        }
    }

    public event PropertyChangedEventHandler PropertyChanged;

    private void RaisePropertyChanged(string property)
    {
        if (PropertyChanged != null)
        {
            PropertyChanged(this, new PropertyChangedEventArgs(property));
        }
    }
}

我真的不知道我做错了什么,我谷歌和堆叠了一点,但不能使它工作。我希望你能分享知识并帮助我。

致以最诚挚的问候,

1 个答案:

答案 0 :(得分:2)

注意评论中的2个变化

a)使用ItemsSource = "{Binding Students}代替ItemsSource = "{Binding Student}

b)使用语法为<TextBlock Text = "{Binding Path = FullName, Mode = OneWay}" ></TextBlock>

的TextBlock

以下针对FriendsView的修正代码应提供所需的DataGrid结果。经过测试并在我的最后工作,以显示一个DataGrid,其中一列显示FullName

<UserControl x:Class="WpfWHERE.View.FriendsView"
         xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
         xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
         xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" 
         xmlns:d="http://schemas.microsoft.com/expression/blend/2008" 
         xmlns:local="clr-namespace:WpfWHERE.View"
         xmlns:ViewModel="clr-namespace:WpfWHERE.ViewModel"
         xmlns:data = "clr-namespace:WpfWHERE.Model"
         mc:Ignorable="d" 
         d:DesignHeight="600" d:DesignWidth="800">
    <UserControl.DataContext>
        <ViewModel:FriendsViewModel/>
    </UserControl.DataContext>
    <UserControl.Resources>
        <DataGrid x:Key="friendsList" AutoGenerateColumns="false" ItemsSource = "{Binding Students}">
            <DataGrid.Columns>
                <DataGridTemplateColumn Header="Name" Width="150">
                    <DataGridTemplateColumn.CellTemplate>
                        <DataTemplate>
                            <TextBlock Text = "{Binding Path = FullName, Mode = OneWay}" ></TextBlock>
                        </DataTemplate>
                    </DataGridTemplateColumn.CellTemplate>
                </DataGridTemplateColumn>
            </DataGrid.Columns>
        </DataGrid>
    </UserControl.Resources>
    <ContentControl Content="{StaticResource friendsList}"/>
</UserControl>

请注意:

1)我已在DataGrid中显示ContentControl,因为我不确定您是如何显示它的。

2)我不确定你的AViewModel中有什么,但它不应该影响结果