将 Silverlight TabControl 绑定到集合

发布于 2024-09-17 23:11:16 字数 2083 浏览 6 评论 0原文

我的 ViewModel 中有一个模型对象集合。我希望能够将 TabControl 绑定到这些控件并使用 DataTemplate 从模型对象中提取信息。当我尝试执行此操作时,出现错误消息:无法将 Model 类型的对象转换为 TabItem 类型的对象。花了一些时间寻找解决方案后,我发现了以下内容:

  1. Silverlight TabControl 是 破碎的。使用ListBox的组合 和 ContentControl 来模仿 TabControl 的行为。 (方法 我必须给 ListBox 换肤 看起来像 TabControl)

  2. TabControl 不会覆盖 PrepareContainerForItemOverride 和 解决方案是制作一个 转换器。 (不太好,因为我 然后需要指定的类型 转换器中的被转换者)

有人知道更好的解决方案吗?

XAML

<sdk:TabControl ItemsSource="{Binding Items, ElementName=MyControl}">
        <sdk:TabControl.ItemTemplate>
            <DataTemplate>
                <TextBlock Text="{Binding Name}" />
            </DataTemplate>
        </sdk:TabControl.ItemTemplate>
    </sdk:TabControl>

C#

public ObservableCollection<Model> Items { get; set; }

public ViewModel()

    Items = new ObservableCollection<Model>{
        new Model { Name = "1"},
        new Model { Name = "2"},
        new Model { Name = "3"},
        new Model { Name = "4"}
    };
}

建议转换器

public class TabConverter : IValueConverter
{
    public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
    {
        List<TabSource> source = value as List<TabSource>;
        if (source != null)
        {
            List<TabItem> result = new List<TabItem>();
            foreach (TabSource tab in source)
            {
                result.Add(new TabItem()
                {
                    Header = tab.Header,
                    Content = tab.Content
                });
            }
            return result;
        }
        return null;
    }

    public object ConvertBack(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
    {
        throw new NotImplementedException();
    }
}

I have a Collection of Model-objects in my ViewModel. I would like to be able to bind a TabControl to these and use a DataTemplate to extract the information from the Model-objects. When I try to do this I get the errormessage: Unable to cast object of type Model to object of type TabItem. After spending some time looking for a solution I found the following:

  1. The Silverlight TabControl is
    broken. Use a combination of ListBox
    and ContentControl to mimic the
    behaviour of a TabControl. (Means
    that I have to skin the ListBox to
    look like a TabControl)

  2. TabControl does not override
    PrepareContainerForItemOverride and
    the solution is to make a
    Converter. (Not so good because I
    then need to specify the type of the
    convertee in the Converter)

Anyone know any better solution?

XAML

<sdk:TabControl ItemsSource="{Binding Items, ElementName=MyControl}">
        <sdk:TabControl.ItemTemplate>
            <DataTemplate>
                <TextBlock Text="{Binding Name}" />
            </DataTemplate>
        </sdk:TabControl.ItemTemplate>
    </sdk:TabControl>

C#

public ObservableCollection<Model> Items { get; set; }

public ViewModel()

    Items = new ObservableCollection<Model>{
        new Model { Name = "1"},
        new Model { Name = "2"},
        new Model { Name = "3"},
        new Model { Name = "4"}
    };
}

Suggested Converter:

public class TabConverter : IValueConverter
{
    public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
    {
        List<TabSource> source = value as List<TabSource>;
        if (source != null)
        {
            List<TabItem> result = new List<TabItem>();
            foreach (TabSource tab in source)
            {
                result.Add(new TabItem()
                {
                    Header = tab.Header,
                    Content = tab.Content
                });
            }
            return result;
        }
        return null;
    }

    public object ConvertBack(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
    {
        throw new NotImplementedException();
    }
}

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

大海や 2024-09-24 23:11:16

创建转换器

public class SourceToTabItemsConverter : IValueConverter
    {
        public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
        {
            try
            {
                var source = (IEnumerable)value;
                if (source != null)
                {
                    var controlTemplate = (ControlTemplate)parameter;

                    var tabItems = new List<TabItem>();

                    foreach (object item in source)
                    {
                        PropertyInfo[] propertyInfos = item.GetType().GetProperties();

                        //тут мы выбираем, то поле которое будет Header. Вы должны сами вводить это значение.
                        var propertyInfo = propertyInfos.First(x => x.Name == "name");

                        string headerText = null;
                        if (propertyInfo != null)
                        {
                            object propValue = propertyInfo.GetValue(item, null);
                            headerText = (propValue ?? string.Empty).ToString();
                        }

                        var tabItem = new TabItem
                                          {
                                              DataContext = item,
                                              Header = headerText,
                                              Content =
                                                  controlTemplate == null
                                                      ? item
                                                      : new ContentControl { Template = controlTemplate }
                                          };

                        tabItems.Add(tabItem);
                    }

                    return tabItems;
                }
                return null;
            }
            catch (Exception)
            {
                return null;
            }
        }

        /// <summary>
        /// ConvertBack method is not supported
        /// </summary>
        public object ConvertBack(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
        {
            throw new NotSupportedException("ConvertBack method is not supported");
        }

创建ControlTemplate:

<ControlTemplate x:Key="MyTabItemContentTemplate">
            <StackPanel>
                <TextBlock Text="{Binding Path=name}" />
            </StackPanel>
        </ControlTemplate>

并绑定convert,controltemplate

<controls:TabControl  x:Name="tabControl"
        ItemsSource="{Binding ElementName=tabControl, 
                              Path=DataContext, 
                              Converter={StaticResource ConverterCollectionToTabItems}, 
                              ConverterParameter={StaticResource MyTabItemContentTemplate}}">
        </controls:TabControl>

取自博客绑定选项卡控件

Create converter

public class SourceToTabItemsConverter : IValueConverter
    {
        public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
        {
            try
            {
                var source = (IEnumerable)value;
                if (source != null)
                {
                    var controlTemplate = (ControlTemplate)parameter;

                    var tabItems = new List<TabItem>();

                    foreach (object item in source)
                    {
                        PropertyInfo[] propertyInfos = item.GetType().GetProperties();

                        //тут мы выбираем, то поле которое будет Header. Вы должны сами вводить это значение.
                        var propertyInfo = propertyInfos.First(x => x.Name == "name");

                        string headerText = null;
                        if (propertyInfo != null)
                        {
                            object propValue = propertyInfo.GetValue(item, null);
                            headerText = (propValue ?? string.Empty).ToString();
                        }

                        var tabItem = new TabItem
                                          {
                                              DataContext = item,
                                              Header = headerText,
                                              Content =
                                                  controlTemplate == null
                                                      ? item
                                                      : new ContentControl { Template = controlTemplate }
                                          };

                        tabItems.Add(tabItem);
                    }

                    return tabItems;
                }
                return null;
            }
            catch (Exception)
            {
                return null;
            }
        }

        /// <summary>
        /// ConvertBack method is not supported
        /// </summary>
        public object ConvertBack(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
        {
            throw new NotSupportedException("ConvertBack method is not supported");
        }

Create ControlTemplate:

<ControlTemplate x:Key="MyTabItemContentTemplate">
            <StackPanel>
                <TextBlock Text="{Binding Path=name}" />
            </StackPanel>
        </ControlTemplate>

And binding convert, controltemplate

<controls:TabControl  x:Name="tabControl"
        ItemsSource="{Binding ElementName=tabControl, 
                              Path=DataContext, 
                              Converter={StaticResource ConverterCollectionToTabItems}, 
                              ConverterParameter={StaticResource MyTabItemContentTemplate}}">
        </controls:TabControl>

taken from the blog binding-tabcontrol

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文