WPF绑定列表<string>到ComboBox

时间:2018-01-17 19:06:30

标签: c# wpf

我的问题是EMPTY Combobox列表。我已经浏览了很多网站(3天内),但无法弄明白。
我已经编写了一个显示学生列表的程序,点击我可以更改属性。因此,除了Faculty(ComboBox)之外,我可以更改succsefuly所有属性 Click to see View my programm
我用过MVVM .... 我有班级学生(模特)。在这里,General是enum StudentFaculty ....

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace _15._01._2018.Model
{
    public enum StudentFaculty { Programmer, SysAdministration, Designer};
    class Student : INotifyPropertyChanged
    {
        private string _name;
        private string _lastname;
        private StudentFaculty _faculty;
        private double _averageMark;

        public string Name
        {
            get { return _name; }
            set
            {
                if(_name == value) return;
                _name = value;
                OnPropertyChanged("Name");
            }
        }
        public string Lastname
        {
            get { return _lastname; }
            set
            {
                if (_lastname == value) return;
                _lastname = value;
                OnPropertyChanged("Lastname");
            }
        }
        public StudentFaculty Faculty
        {
            get { return _faculty; }
            set
            {
                if (_faculty == value) return;
                _faculty = value;
                OnPropertyChanged("Faculty");
            }
        }
        public double AverageMark
        {
            get { return _averageMark; }
            set
            {
                if (_averageMark == value) return;
                _averageMark = value;
                OnPropertyChanged("AverageMark");
            }
        }
        public Student() { }
        public Student(string name, string lastname, StudentFaculty faculty, double averageMark)
        {
            Name = name;
            Lastname = lastname;
            Faculty = faculty;
            AverageMark = averageMark;
        }
        public event PropertyChangedEventHandler PropertyChanged;
        public void OnPropertyChanged(string property)
        {
            if (PropertyChanged != null)
                PropertyChanged(this, new PropertyChangedEventArgs(property));
        }
    }
}

类ApplicationViewModel。在这里,我从构造函数中的枚举创建列表(Faculties),也是SelectedFaculty ...

using _15._01._2018.Model;
using System;
using System.Collections.Generic;
using System.Collections.ObjectModel;
using System.ComponentModel;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace _15._01._2018.ViewModel
{
    class ApplicationViewModel : INotifyPropertyChanged
    {
        private Student _selectedStudent;
        private string _selectedFaculty;
        public ObservableCollection<Student> Students { get; set; }
        public List<string> Faculties { get; set; }
        public Student SelectedStudent
        {
            get { return _selectedStudent; }
            set
            {
                if (_selectedStudent == value) return;
                _selectedStudent = value;
                OnChangedProperty("SelectedStudent");
            }
        }
        public string SelectedFaculty
        {
            get { return _selectedFaculty; }
            set
            {
                if (_selectedFaculty == value) return;
                _selectedFaculty = value;
                OnChangedProperty("SelectedFaculty");
            }
        }
        public ApplicationViewModel()
        {
            Students = new ObservableCollection<Student>
            {
                new Student("Vova", "Zyabkin", StudentFaculty.Programmer, 9.4),
                new Student("Vadym", "Lazariev", StudentFaculty.Programmer, 9),
                new Student("SvEta", "Belyaeva", StudentFaculty.Designer, 9.8),
                new Student("Vova", "Skachkov", StudentFaculty.SysAdministration, 8.7)
            };
            Faculties = new List<string>(Enum.GetNames(typeof(StudentFaculty)));
        }
        public event PropertyChangedEventHandler PropertyChanged;
        public void OnChangedProperty(string property)
        {
            if (PropertyChanged != null)
                PropertyChanged(this, new PropertyChangedEventArgs(property));
        }
    }
} 

XAML

<Window x:Class="_15._01._2018.MainWindow"
        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"
        xmlns:local="clr-namespace:_15._01._2018"
        mc:Ignorable="d"
        Title="MainWindow" Height="350" Width="525">
    <Window.Resources>
        <Style TargetType="TextBlock">
            <Setter Property="FontSize" Value="14" />
        </Style>
        <Style TargetType="TextBox">
            <Setter Property="FontSize" Value="14" />
        </Style>
    </Window.Resources>
    <Grid>
        <Grid.ColumnDefinitions>
            <ColumnDefinition></ColumnDefinition>
            <ColumnDefinition></ColumnDefinition>
        </Grid.ColumnDefinitions>
        <ListBox ItemsSource="{Binding Students}" SelectedItem="{Binding SelectedStudent}">
            <ListBox.ItemTemplate>
                <DataTemplate>
                    <StackPanel Orientation="Vertical">
                        <TextBlock Text="{Binding Path=Name}"></TextBlock>
                        <TextBlock Text="{Binding Path=Lastname}"></TextBlock>
                        <!--<TextBlock Text="{Binding Path=Faculty}"></TextBlock>-->
                        <TextBlock Text="{Binding Path=AverageMark}"></TextBlock>
                    </StackPanel>
                </DataTemplate>
            </ListBox.ItemTemplate>
        </ListBox>
        <Grid Grid.Column="1">
            <StackPanel DataContext="{Binding SelectedStudent}">
                <TextBlock Text="D A T A"></TextBlock>
                <TextBlock Text="Name:"></TextBlock>
                <TextBox Text="{Binding Name, UpdateSourceTrigger=PropertyChanged}"></TextBox>
                <TextBlock Text="Lastname:"></TextBlock>
                <TextBox Text="{Binding Lastname, UpdateSourceTrigger=PropertyChanged}"></TextBox>
                <TextBlock Text="Faculty:"></TextBlock>
                <ComboBox ItemsSource="{Binding Faculties}" SelectedItem="{Binding SelectedFaculty}">

                </ComboBox>
                <TextBlock Text="Average Mark:"></TextBlock>
                <TextBox Text="{Binding AverageMark, UpdateSourceTrigger=PropertyChanged}"></TextBox>
            </StackPanel>
        </Grid>
    </Grid>
</Window>

我想创建一个具有String属性Faculty的类,但它与ListBox和Student一样。

1 个答案:

答案 0 :(得分:1)

首先,将ComboBox的DataContext设置为SelectedStudent,而不是ApplicationViewModel(请参阅父StackPanel)。其次,你有Faculties属性返回一个String列表,但Student类有一个StudentFaculty属性(绑定了SelectedValue赢了工作)。

尝试以下方法:

<强>型号/的ViewModels:

class ApplicationViewModel : INotifyPropertyChanged
{
    private Student _selectedStudent;
    private StudentFaculty _selectedFaculty;
    public ObservableCollection<Student> Students { get; set; }
    public ObservableCollection<StudentFaculty> Faculties { get; set; }
    public Student SelectedStudent
    {
        get => _selectedStudent;
        set
        {
            if (_selectedStudent == value) return;
            _selectedStudent = value;
            OnChangedProperty("SelectedStudent");
        }
    }
    public StudentFaculty SelectedFaculty
    {
        get => _selectedFaculty;
        set
        {
            if (_selectedFaculty == value) return;
            _selectedFaculty = value;
            OnChangedProperty("SelectedFaculty");
        }
    }
    public ApplicationViewModel()
    {
        Students = new ObservableCollection<Student>
        {
            new Student("Vova", "Zyabkin", StudentFaculty.Programmer, 9.4),
            new Student("Vadym", "Lazariev", StudentFaculty.Programmer, 9),
            new Student("SvEta", "Belyaeva", StudentFaculty.Designer, 9.8),
            new Student("Vova", "Skachkov", StudentFaculty.SysAdministration, 8.7)
        };
        Faculties = new ObservableCollection<StudentFaculty>(Enum.GetValues(typeof(StudentFaculty)).OfType<StudentFaculty>());
    }
    public event PropertyChangedEventHandler PropertyChanged;

    public void OnChangedProperty(string property) => PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(property));
}

public enum StudentFaculty { Programmer, SysAdministration, Designer };
class Student : INotifyPropertyChanged
{
    private string _name;
    private string _lastname;
    private StudentFaculty _faculty;
    private double _averageMark;

    public string Name
    {
        get => _name;
        set
        {
            if (_name == value) return;
            _name = value;
            OnPropertyChanged("Name");
        }
    }
    public string Lastname
    {
        get => _lastname;
        set
        {
            if (_lastname == value) return;
            _lastname = value;
            OnPropertyChanged("Lastname");
        }
    }
    public StudentFaculty Faculty
    {
        get => _faculty;
        set
        {
            if (_faculty == value) return;
            _faculty = value;
            OnPropertyChanged("Faculty");
        }
    }
    public double AverageMark
    {
        get => _averageMark;
        set
        {
            if (_averageMark == value) return;
            _averageMark = value;
            OnPropertyChanged("AverageMark");
        }
    }
    public Student() { }
    public Student(string name, string lastname, StudentFaculty faculty, double averageMark)
    {
        Name = name;
        Lastname = lastname;
        Faculty = faculty;
        AverageMark = averageMark;
    }

    public event PropertyChangedEventHandler PropertyChanged;

    public void OnPropertyChanged(string property) => PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(property));
}

<强> XAML

<Window x:Class="WpfApp4.MainWindow"
    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"
    xmlns:converters="clr-namespace:WpfApp4.Views.Converters"
    xmlns:i="http://schemas.microsoft.com/expression/2010/interactivity"
    xmlns:ei="http://schemas.microsoft.com/expression/2010/interactions"
    xmlns:viewModels="clr-namespace:WpfApp4.ViewModels"
    mc:Ignorable="d"
    Title="MainWindow" Height="350" Width="525">
<Window.DataContext>
    <viewModels:ApplicationViewModel />
</Window.DataContext>
<Window.Resources>
    <Style TargetType="TextBlock">
        <Setter Property="FontSize" Value="14" />
    </Style>
    <Style TargetType="TextBox">
        <Setter Property="FontSize" Value="14" />
    </Style>
    <CollectionViewSource x:Key="Faculties" Source="{Binding Faculties}"></CollectionViewSource>
</Window.Resources>
<Grid>
    <Grid.ColumnDefinitions>
        <ColumnDefinition></ColumnDefinition>
        <ColumnDefinition></ColumnDefinition>
    </Grid.ColumnDefinitions>
    <ListBox ItemsSource="{Binding Students}" SelectedItem="{Binding SelectedStudent}">
        <ListBox.ItemTemplate>
            <DataTemplate>
                <StackPanel Orientation="Vertical">
                    <TextBlock Text="{Binding Path=Name}"></TextBlock>
                    <TextBlock Text="{Binding Path=Lastname}"></TextBlock>
                    <!--<TextBlock Text="{Binding Path=Faculty}"></TextBlock>-->
                    <TextBlock Text="{Binding Path=AverageMark}"></TextBlock>
                </StackPanel>
            </DataTemplate>
        </ListBox.ItemTemplate>
    </ListBox>
    <Grid Grid.Column="1">
        <StackPanel DataContext="{Binding SelectedStudent}">
            <TextBlock Text="D A T A"></TextBlock>
            <TextBlock Text="Name:"></TextBlock>
            <TextBox Text="{Binding Name, UpdateSourceTrigger=PropertyChanged}"></TextBox>
            <TextBlock Text="Lastname:"></TextBlock>
            <TextBox Text="{Binding Lastname, UpdateSourceTrigger=PropertyChanged}"></TextBox>
            <TextBlock Text="Faculty:"></TextBlock>
            <ComboBox ItemsSource="{Binding Source={StaticResource Faculties}}" SelectedValue="{Binding Faculty, Mode=TwoWay}">

            </ComboBox>
            <TextBlock Text="Average Mark:"></TextBlock>
            <TextBox Text="{Binding AverageMark, UpdateSourceTrigger=PropertyChanged}"></TextBox>
        </StackPanel>
    </Grid>
</Grid>