注意这张图片: alt text http://img25.imageshack.us/img25/9743/timetablepo.png
此用户界面的 TimeTableViewModel 是:
public string SchoolclassCodeMonday {get;set;}
public string SchoolclassCodeTuesday {get;set;}
public string SchoolclassCodeWednesday {get;set;}
public string SchoolclassCodeThursday {get;set;}
public string SchoolclassCodeFriday {get;set;}
public string SchoolclassCodeSaturday {get;set;}
public string SchoolclassCodeSunday {get;set;}
当我在文本框中仅显示属性作为字符串时,上述操作将起作用。 但我想要的是将每个 combox绑定到相互ObservableCollection SchoolclassCodes 和ComboBox的SelectedItem aka DisplayMember必须以某种方式 映射到上述7个属性之一,如果检索到SelectedItem,则必须提供一行 在组合框中选出的所有7个学校班级。
或者换句话说我真正想要的是什么; - )
在ComboBox中显示SchoolclassCodes列表,将 的值> SelectedItem.SchoolclassCode“WeekdayName”设置为所选的ComboboxItem.SchoolclassCode
的值我有一些想法,但都缺乏使它们完全发挥作用的经验。
我可以为每个属性添加 TimeTableViewModel a ObservableCollection SchoolclassCodes 但这对我来说似乎非常多余。当每个单元格中包含相同项目的相同列表时,为什么我应该为一行保留7个列表?
欢迎任何有关ViewModels结构和Wpf绑定的建议:)
UPDATE :我的 SchoolclassCodes 列表是动态创建的,所以我不可能在XAML中使用静态绑定或硬编码字符串项...
UPDATE2:
好的我试着让它与MVVM一起工作:
我必须更改 ObservableCollection ClassCodes 到 ObservableCollection SchoolclassCodes作为Schoolclass对象 有一个不可能的字符串引用Pupil类。
Schoolclass.cs:
public string SchoolclassCode {get;set;}
...
TimeTableWeekViewModel.cs:
public ObservableCollection<Schoolclass> SchoolclassCodes
{
get { return _schoolclassCodes; }
set
{
_schoolclassCodes = value;
this.RaisePropertyChanged("SchoolclassCodes");
}
}
XAML:
绑定如何看起来像NOW,因为wpf找不到SchoolclassCodes?
答案 0 :(得分:1)
如果您正在执行任何远程复杂的操作,我建议您查看MVVM(Model-View-ViewModel)模式。此外,在您的模型/ viewmodel中实现INotifyPropertyChanged
非常有用(例如,下面示例中的MyWeek
类)。只要您的某个SchoolclassCode<Day>
属性发生更改,这将通知任何其他绑定。
以下是一些简单的示例代码,可帮助您入门:
using System.Collections.ObjectModel;
using System.Linq;
namespace BindingSample
{
public partial class Window1
{
public Window1()
{
InitializeComponent();
SchoolclassCodes = new ObservableCollection<string>(
Enumerable.Range(1, 10).Select(i => "Code #" + i));
MyWeeks = new ObservableCollection<MyWeek>(
Enumerable.Range(1, 5).Select(i => new MyWeek() {SchoolclassCodeMonday = SchoolclassCodes.First()}));
DataContext = this;
}
public ObservableCollection<string> SchoolclassCodes { get; private set; }
public ObservableCollection<MyWeek> MyWeeks { get; private set; }
}
public class MyWeek
{
public string SchoolclassCodeMonday { get; set; }
public string SchoolclassCodeTuesday { get; set; }
public string SchoolclassCodeWednesday { get; set; }
public string SchoolclassCodeThursday { get; set; }
public string SchoolclassCodeFriday { get; set; }
public string SchoolclassCodeSaturday { get; set; }
public string SchoolclassCodeSunday { get; set; }
}
}
<Window x:Class="BindingSample.Window1"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Title="Window1" Height="300" Width="300">
<Window.Resources>
<CollectionViewSource x:Key="ClassCodes" Source="{Binding SchoolclassCodes}" />
</Window.Resources>
<ListView ItemsSource="{Binding MyWeeks}">
<ListView.View>
<GridView>
<GridView.Columns>
<GridViewColumn Header="Monday">
<GridViewColumn.CellTemplate>
<DataTemplate>
<ComboBox SelectedValue="{Binding SchoolclassCodeMonday}"
ItemsSource="{Binding Source={StaticResource ClassCodes}}"
IsSynchronizedWithCurrentItem="False" />
</DataTemplate>
</GridViewColumn.CellTemplate>
</GridViewColumn>
<!-- Other columns here... -->
</GridView.Columns>
</GridView>
</ListView.View>
</ListView>
</Window>
答案 1 :(得分:0)
由于必须自动生成列,因此将此代码放在适当的位置(Loaded
event?)应该可以执行您想要的操作:
ObservableCollection<String> Collection = GetCollection();
foreach (DataGridComboBoxColumn column in DataGrid1.Columns.OfType<DataGridComboBoxColumn>())
{
column.ItemsSource = Collection;
}
当然,必须进行一些修改!
答案 2 :(得分:0)
您不需要乱用DataGrid,并且您当然不需要创建任何具有七个不同属性的类,您必须为其实现属性更改通知。 Grid控件使日历变得简单。
您的视图模型应包含三个类:Month
,Week
和Day
。 Week
类包含Day
个对象的列表,Month
类包含Week
个对象的列表。每个类都应该引用其父级,即Week
中的Day
和Month
中的Week
。
Week
类的构造函数应将其Days
属性初始化为7 Day
个对象的列表。 Month
类的构造函数必须具有更具体的逻辑来设置其Weeks
属性;我会留给你的。
Day
对象应该公开这些属性:
public DayOfWeek DayNumber { get; private set; }
public ObservableCollection<SchoolclassCode> Codes { get { return Week.Codes; } }
以及执行属性更改通知的读/写字符串Code
属性。
Week
对象应该公开:
public ObservableCollection<SchoolclassCode> Codes { get { return Month.Codes; } }
public IEnumerable<Day> Days { get; private set; }
public IEnumerable<string> Codes
{
get { return Days.Select(x => x.Code); }
}
然后,您可以定义用于呈现日期的数据模板:
<DataTemplate DataType="{x:Type local:Day}">
<Grid>
<Grid.ColumnDefinitions>
<ColumnDefinition SharedSizeGroup="Sunday"/>
<ColumnDefinition SharedSizeGroup="Monday"/>
<ColumnDefinition SharedSizeGroup="Tuesday"/>
<ColumnDefinition SharedSizeGroup="Wednesday"/>
<ColumnDefinition SharedSizeGroup="Thursday"/>
<ColumnDefinition SharedSizeGroup="Friday"/>
<ColumnDefinition SharedSizeGroup="Saturday"/>
</Grid.ColumnDefinitions>
<ComboBox
Grid.Column="{Binding DayNumber}"
ItemsSource="{Binding Codes}"
SelectedValue="{Binding Code, Mode=TwoWay}"/>
</Grid>
</DataTemplate>
和周:
<DataTemplate DataType="{x:Type Week}">
<ItemsControl ItemsSource="{Binding Days}">
<ItemsControl.ItemTemplate>
<ItemsPanelTemplate>
<StackPanel Orientation="Horizontal"/>
</ItemsPanelTemplate>
</ItemsControl.ItemTemplate>
</ItemsControl>
</DataTemplate>
和月:
<DataTemplate DataType="{x:Type Month}">
<ItemsControl ItemsSource="{Binding Weeks}" Grid.IsSharedSizeScope="True">
<ItemsControl.ItemTemplate>
<ItemsPanelTemplate>
<StackPanel Orientation="Vertical"/>
</ItemsPanelTemplate>
</ItemsControl.ItemTemplate>
</ItemsControl>
</DataTemplate>
将上述日期名称和周数添加到上述模板中非常简单。