управление для обмена UIElements в WPF - PullRequest
1 голос
/ 18 марта 2009

Каков самый минимальный способ динамического обмена UIElement s в определенном «слоте» в интерфейсе пользователя? У меня есть число UIElement с, и на основе некоторой внешней привязки данных (например, выбор из выпадающего списка) я хочу, чтобы один из них был показан, а тот, который был виден в данный момент, скрыт. Таким образом, поведение похоже на TabControl, но без вкладок, экземпляров Chrome и Tabitem. Так что я мог бы использовать TabControl и переопределить шаблон управления. Но действительно ли это самый минимальный подход?

Ответы [ 6 ]

2 голосов
/ 18 марта 2009
<ContentControl Content="{Binding SomePropertyThatYieldsTheContent}"/>
1 голос
/ 18 марта 2009

У вас есть несколько вариантов. Как уже упоминал Брайан, селектор шаблонов данных определенно может работать, хотя я решил, что они часто бывают лишними. Возьмем, к примеру, ваш пример - если вы хотите связать видимость элемента с выделением в ComboBox, я бы предпочел вместо него ValueConverter. Передайте ComboBox.SelectedItem в Converter и верните значение Visibility:

public class MyObjectToVisibleOrCollapsed : IValueConverter
{
    #region IValueConverter Members
    public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
    {
        if (value is MyObject)
        {
            var myObject = (MyObject)value;
            if (myObject.SomeState)
            {
                return Visibility.Visible;
            }
        }

        return Visibility.Collapsed;
    }

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

    #endregion
}

Теперь в ваших Window.Resources создайте экземпляр ValueConverter и привяжите элемент к ComboBox.SelectedItem, используя экземпляр ValueConverter:

<local:MyObjectToVisibleOrCollapsed x:Key="myObjectToVisibleOrCollapsed"/>
<DataTemplate x:Key="MyTemplate">
    <TextBlock Text="{Binding Path=myText}" 
               x:Name="MyText" 
               Visibility="{Binding ElementName=MyComboBox, Path=SelectedItem, Converter={StaticResource myObjectToVisibleOrCollapsed}, Mode=Default}" />
</DataTemplate>

И, конечно, вы можете повторно использовать ValueConverter для всех элементов в DataTemplate (и, если их много, подход выбора шаблонов данных становится более желательным).

[Отказ от ответственности: приведенный выше код был хеширован из памяти и не проверен - возможно, потребуется небольшая настройка]

1 голос
/ 18 марта 2009

Я не знаю, является ли это наиболее лаконичным способом, но если вы используете DataTemplate, вы можете использовать DataTrigger s (здесь предполагается, что начальная видимость равна Collapsed):

<DataTemplate.Triggers>
    <DataTrigger Binding="{Binding Path=SourceProperty.ValueType}">
        <DataTrigger.Value>
            <pm:ValueType>Text</pm:ValueType>
        </DataTrigger.Value>
        <Setter TargetName="TextEditor" Property="Visibility" Value="Visible" />
    </DataTrigger>
    <DataTrigger Binding="{Binding Path=SourceProperty.ValueType}">
        <DataTrigger.Value>
            <pm:ValueType>Logical</pm:ValueType>
        </DataTrigger.Value>
        <Setter TargetName="LogicalEditor" Property="Visibility" Value="Visible" />
    </DataTrigger>
    <DataTrigger Binding="{Binding Path=SourceProperty.ValueType}">
        <DataTrigger.Value>
            <pm:ValueType>DateTime</pm:ValueType>
        </DataTrigger.Value>
        <Setter TargetName="DateEditor" Property="Visibility" Value="Visible" />
    </DataTrigger>
...
0 голосов
/ 22 июля 2009

Я создаю пользовательские элементы управления для каждого возможного «представления».

Их видимость меняется с помощью c #, тыс. Небольшое кодирование необходимо.

Основной причиной такого подхода является простота разработки - дизайнер фокусируется на конкретном представлении, а не на наборе всех возможных элементов управления, которые будут там.

0 голосов
/ 18 марта 2009

Посмотрите на Селекторы шаблонов данных , у Bea Stollnitz есть хороший пост здесь . В основном вы будете использовать ContentPresenter в каждом из ваших «слотов» пользовательского интерфейса, а затем использовать свойство ContentTemplateSelector, чтобы определить, какой селектор шаблонов вы будете использовать.

0 голосов
/ 18 марта 2009

То, как я это делаю, состоит в том, чтобы наложить элементы друг на друга и программно изменить их свойство Visibility с Visible на Collapsed и обратно при необходимости.

...