Caliburn.Micro & Telerik WPF Controls - PullRequest
       15

Caliburn.Micro & Telerik WPF Controls

8 голосов
/ 06 ноября 2010

Надеюсь, у вас все хорошо.

Я использую Caliburn.Micro с элементами управления Telerik WPF для создания интерфейса с вкладками.Используя RadTabControl, у меня есть следующий код:

<telerik:RadTabControl x:Name="Items" Grid.Row="1" TabStripPlacement="Bottom">
    <telerik:RadTabControl.ItemTemplate>
        <DataTemplate>
            <StackPanel Orientation="Horizontal">
                <Image Source="{Binding DisplayIcon}" Width="16" Height="16"/>
                <TextBlock Text="{Binding DisplayName}"/>
            </StackPanel>
        </DataTemplate>
    </telerik:RadTabControl.ItemTemplate>
</telerik:RadTabControl>

Вкладка имеет правильный заголовок, но содержимое показывает «... / MyViewModel» (эллипсы заменяют полный путь) вместо экрана, который должен отображаться.

Если я заменим <telerik:RadTabControl... на <TabControl..., все это будет работать как задумано.

Чего мне не хватает?

Ответы [ 2 ]

12 голосов
/ 06 ноября 2010

Система условных обозначений Caliburn настроена только на готовые элементы управления WPF.Когда он видит RabTabControl, он не распознает его, поэтому он искал иерархию классов в поисках чего-то, что он распознает.В этом случае он, вероятно, совпадает либо с Selector, либо с ItemsControl.Вот почему существует частичное применение соглашений.Чтобы получить именно то, что вы хотите, вам нужно добавить в ConventionManager для RadTabControl соглашение, которое делает именно то, что вы хотите.Вот как определяется соглашение TabControl:

AddElementConvention<TabControl>(TabControl.ItemsSourceProperty, "ItemsSource", "SelectionChanged")
.ApplyBinding = (viewModelType, path, property, element, convention) => {
    if(!SetBinding(viewModelType, path, property, element, convention))
        return;

    var tabControl = (TabControl)element;
    if(tabControl.ContentTemplate == null && tabControl.ContentTemplateSelector == null && property.PropertyType.IsGenericType) {
        var itemType = property.PropertyType.GetGenericArguments().First();
        if(!itemType.IsValueType && !typeof(string).IsAssignableFrom(itemType))
            tabControl.ContentTemplate = DefaultItemTemplate;
    }

    ConfigureSelectedItem(element, Selector.SelectedItemProperty, viewModelType, path);

    if(string.IsNullOrEmpty(tabControl.DisplayMemberPath))
        ApplyHeaderTemplate(tabControl, TabControl.ItemTemplateProperty, viewModelType);
};

Я думаю, что вы сможете взять код и с небольшими изменениями заставить его делать то, что вы хотите.Обратите внимание, что некоторые методы, вызываемые в приведенном выше коде, действительно существуют в ConventionManager, поэтому вам нужно это исправить.Вы должны добавить свое соглашение в переопределение Configure вашего Bootstrapper.Для дополнительного примера этого взгляните на Bootstrapper шаблона WP7, который определяет пользовательские соглашения для Pivot и Panarama.

4 голосов
/ 19 июля 2012

Caliburn.Micro.Telerik содержит соглашения для элементов управления Telerik WPF, а также некоторые другие специфичные для Telerik + WPF вещи, такие как реализация IWindowManager, и два приложения с примерами.

Вы можете проверить исходный код или пакет nuget .

Соглашение для RadTabControl выглядит следующим образом:

ConventionManager.AddElementConvention<RadTabControl>(RadTabControl.ItemsSourceProperty,
                                                  "ItemsSource",
                                                  "SelectionChanged")
.ApplyBinding = (viewModelType, path, property, element, convention) =>
{
    if (!ConventionManager.SetBindingWithoutBindingOrValueOverwrite(viewModelType,
                                                                    path,
                                                                    property,
                                                                    element,
                                                                    convention,
                                                                    RadTabControl.ItemsSourceProperty))
        return false;

    var tabControl = (RadTabControl) element;
    if (tabControl.ContentTemplate == null
        && tabControl.ContentTemplateSelector == null
        && property.PropertyType.IsGenericType)
    {
        var itemType = property.PropertyType.GetGenericArguments().First();
        if (!itemType.IsValueType && !typeof (string).IsAssignableFrom(itemType))
            tabControl.ContentTemplate = ConventionManager.DefaultItemTemplate;
    }
    ConventionManager.ConfigureSelectedItem(element,
                                            RadTabControl.SelectedItemProperty,
                                            viewModelType,
                                            path);

    if (string.IsNullOrEmpty(tabControl.DisplayMemberPath))
        ConventionManager.ApplyHeaderTemplate(tabControl,
                                              RadTabControl.ItemTemplateProperty,
                                              RadTabControl.ItemTemplateSelectorProperty,
                                              viewModelType);
    return true;
};

Надеюсь, это поможет ...

...