Silverlight中的TabControl如何绑定数据?
在 WPF 中,TabControl 可以直接将 ItemsSource 绑定数据源,见
将 TabControl 绑定到数据的示例
http://msdn.microsoft.com/zh-cn/library/aa972130(VS.90).aspx
<Window.Resources>
<ObjectDataProvider x:Key="TabListResource" ObjectType="{x:Type src:TabList}" />
<DataTemplate x:Key="HeaderTemplate">
<TextBlock Text="{Binding Path=Header}" />
</DataTemplate>
<DataTemplate x:Key="ContentTemplate">
<TextBlock Text="{Binding Path=Content}" />
</DataTemplate>
</Window.Resources>
<DockPanel>
<TabControl ItemsSource="{Binding Source={StaticResource TabListResource}}"
ItemTemplate="{StaticResource HeaderTemplate}"
ContentTemplate="{StaticResource ContentTemplate}"/>
</DockPanel>
匪疑所思的是,TabControl.ItemTeplate 居然是用于 Header, ContentTemplate 才是用于 TabItem。
但是在 Silverlight 中貌似无此功能, TabControl.ContentTemplate 属性也不存在。
作为从 ItemsControl 中派生的类,Silverlight 中的 TabControl.ItemsSource 貌似要求为 IEnumerable<TabItem>,
这让人很难接受, 不知是不是真的这样?
作为无奈的解决办法,只能对通过代码动态添加各个 TabItem,并对它们分别进行 Binding。
下面是代码:
namespace TabControl_DataBinding
{
using System;
using System.ComponentModel;
using System.Collections.ObjectModel;
using System.ComponentModel.DataAnnotations;
public class Model
{
public ObservableCollection<Article> Articles { get; private set; }
public Model()
{
this.Articles = new ObservableCollection<Article>();
}
}
public class Article
{
public string LanguageCode { get; set; }
public string LanguageName { get; set; }
[Display(Name="主题")]
public string Subject { get; set; }
[Display(Name = "详细描述")]
public string Description { get; set; }
}
public class Settings
{
public static System.Collections.Generic.Dictionary<string, string>
Languages { get; private set; }
static Settings()
{
Languages = new System.Collections.Generic.Dictionary<string, string>();
Languages.Add("en", "English");
Languages.Add("zh-Hans", "简体");
Languages.Add("zh-Hant", "繁体");
}
}
}
<UserControl.Resources>
<DataTemplate x:Key="languageDataTemplate">
<Grid >
<Grid.ColumnDefinitions>
<ColumnDefinition Width="Auto" />
<ColumnDefinition Width="Auto" />
</Grid.ColumnDefinitions>
<Grid.RowDefinitions>
<RowDefinition Height="Auto" />
<RowDefinition Height="*" />
</Grid.RowDefinitions>
<sdk:Label Grid.Column="0" Grid.Row="0"
Target="{Binding ElementName=txtSubject}" />
<TextBox Grid.Column="1" Grid.Row="0" Name="txtSubject"
Text="{Binding Subject, Mode=TwoWay,
ValidatesOnExceptions=true, NotifyOnValidationError=true}" />
<sdk:Label Grid.Column="0" Grid.Row="1"
Target="{Binding ElementName=txtDetail}" />
<TextBox Grid.Column="1" Grid.Row="1" Name="txtDetail" Width="280"
Text="{Binding Description, Mode=TwoWay,
ValidatesOnExceptions=true, NotifyOnValidationError=true}"
Height="80" AcceptsReturn="True" TextWrapping="Wrap"
VerticalScrollBarVisibility="Auto" />
</Grid>
</DataTemplate>
</UserControl.Resources>
<Grid x:Name="LayoutRoot" Background="White">
<sdk:TabControl Name="tabControl1" Margin="16" >
</sdk:TabControl>
</Grid>
public partial class MainPage : UserControl
{
Model data;
public MainPage()
{
InitializeComponent();
this.Loaded += (sender, e) =>
{
this.GenerateData();
this.BindControls();
};
}
/// <summary>
/// 创建初始数据
/// </summary>
void GenerateData()
{
this.data = new Model();
foreach (var item in Settings.Languages)
{
this.data.Articles.Add(new Article()
{
LanguageCode = item.Key,
LanguageName = item.Value,
Subject = "主题" + item.Value
});
}
}
void BindControls()
{
foreach (var item in Settings.Languages)
{
Article article = this.data.Articles
.Single(art => art.LanguageCode == item.Key);
TabItem ti = new TabItem()
{
Header = article.LanguageName,
Tag = article.LanguageCode,
ContentTemplate = (DataTemplate)this.Resources["languageDataTemplate"]
};
ti.SetBinding(TabItem.ContentProperty, new System.Windows.Data.Binding());
this.tabControl1.Items.Add(ti);
ti.DataContext = article;
}
}
}