我有:
public class BaseSong
{
public string Artist
{
get; set;
}
public string Title
{
get; set;
}
public class ExtendedSong : BaseSong
{
public string Bitrate { get; set;}
...
}
public class CollectionSong<T> : ObservableCollection<T> where T : BaseSong
{
...
}
public class Playlist
{
CollectionSong _collectionSong;
public CollectionSong<BaseSong> Collection
{
get { return _collectionSong; }
set {...}
}
public Playlist()
{}
...
}
我可以这样
Playlist plist= new Playlist();
plist.Collection = new CollectionSong<BaseSong>();
plist.Collection.Add(new ExtendedSong(){...});
ListView lv = new ListView();
lv.ItemSource = plist.Collection;
但是,我怎么能说ListView关于show listViewItem为ExtendedSong而不是BaseSong?
P.S。集合只有BaseSong项目或只有ExtendedSong
private ListView CreateListView(PlaylistViewModel model)
{
System.Windows.Controls.ListView lv = new System.Windows.Controls.ListView();
lv.SetBinding(ListView.ItemsSourceProperty, new Binding("Collection")
{
Source = model,
UpdateSourceTrigger = UpdateSourceTrigger.PropertyChanged
});
lv.SetBinding(ListView.ViewProperty, new Binding("ColumnConfig")
{
Converter = new VkPlayer.Helpers.ConfigToDynamicGridViewConverter()
});
return lv;
}
DataTemplate songLayout = new DataTemplate();
songLayout.DataType = typeof(ExtendedSong);
FrameworkElementFactory spFactory = new FrameworkElementFactory(typeof(TextBlock));
spFactory.Name = "textBoxFactory";
spFactory.SetBinding(TextBlock.TextProperty, new Binding("Bitrate"));
songLayout.VisualTree = spFactory;
ColumnConfig = new ColumnConfig { Columns = new List<Column> {
new Column { Header = "Title", DataField = "FullName" },
new Column { Header = "Bitrate", Template = songLayout}
}
};
public class ConfigToDynamicGridViewConverter : System.Windows.Data.IValueConverter
{
public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
{
var config = value as ColumnConfig;
if (config != null)
{
var grdiView = new GridView();
foreach (var column in config.Columns)
{
var grwCol = new GridViewColumn { Header = column.Header };
if (column.DataField != null)
{
var binding = new System.Windows.Data.Binding(column.DataField);
if (column.Converter != null)
binding.Converter = column.Converter as System.Windows.Data.IValueConverter;
if (column.ConverterParameter != null)
{
binding.ConverterParameter = column.ConverterParameter;
}
grwCol.DisplayMemberBinding = binding;
}
else
{
grwCol.CellTemplate = column.Template;
}
grdiView.Columns.Add(grwCol);
}
return grdiView;
}
return System.Windows.Data.Binding.DoNothing;
}
不工作,输出: System.Windows.Data错误:40:BindingExpression路径错误:&#39; Bitrate&#39;在&#39; object&#39;上找不到的属性&#39;&#39; BaseSong&#39; (的HashCode = 23764897)&#39;
答案 0 :(得分:3)
在WPF中,我们使用DataTemplate
来定义我们的数据对象在UI中应该是什么样子。有关数据绑定的详细信息,请参阅MSDN上的Data Binding Overview页面。因此,我们只需为您的每种数据类型声明DataTemplate
,并且每个DataTemplate
的内容都可以访问该类型的属性。尝试这样的事情:
<DataTemplate DataType="{x:Type YourPrefix:BaseSong}">
<TextBlock Text="{Binding Title}" />
</DataTemplate>
<DataTemplate DataType="{x:Type YourPrefix:ExtendedSong}">
<TextBlock Text="{Binding Bitrate}" />
</DataTemplate>
...
<ListBox ItemsSource="{Binding CollectionSong" ... />
这就是你所要做的一切。
答案 1 :(得分:0)
public class CollectionSong<T> : ObservableCollection<T> where T : BaseSong
{
public CollectionSong<ExtendedSong> ToExSongs() {...}
}
public CollectionSong<BaseSong> CollectionEx
{
get { return Collection.ToExSongs(); }
set {...}
}