2

我已经查看了我能找到的所有 Caliburn Micro 的东西,我想我只是让自己感到困惑。我整理了一个简单的样本作为测试。

模型 = Person.cs

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;

namespace WpfTestApp
{
    public class Person
    {
        public string FirstName { get; set; }
        public string LastName { get; set; }
    }
}

PersonView.xaml

<UserControl x:Class="WpfTestApp.PersonView"
             xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
             xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
             xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" 
             xmlns:d="http://schemas.microsoft.com/expression/blend/2008" 
             mc:Ignorable="d" 
             d:DesignHeight="300" d:DesignWidth="300">
    <Grid>
        <StackPanel Orientation="Horizontal">
            <TextBlock Text="{Binding FirstName}" />
            <TextBlock Text="{Binding LastName}" />
        </StackPanel>
    </Grid>
</UserControl>

ShellViewModel.cs

using Caliburn.Micro;
using System.ComponentModel.Composition;
namespace WpfTestApp {
    [Export(typeof(IShell))]
    public class ShellViewModel : PropertyChangedBase, IShell 
    {
        public BindableCollection<PersonViewModel> Items { get; set; }

        public ShellViewModel()
        {
            Items = new BindableCollection<PersonViewModel> {
                new PersonViewModel(new Person { FirstName="Bart", LastName="Simpson" }),
                new PersonViewModel(new Person { FirstName="Lisa", LastName="Simpson" }),
                new PersonViewModel(new Person { FirstName="Homer", LastName="Simpson" }),
                new PersonViewModel(new Person { FirstName="Marge", LastName="Simpson" }),
                new PersonViewModel(new Person { FirstName="Maggie", LastName="Simpson" })
            };
        }
    }
}

ShellView.xaml

<Window x:Class="WpfTestApp.ShellView"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:cal="http://www.caliburnproject.org">
    <Grid>
        <Grid.RowDefinitions>
            <RowDefinition Height="Auto" />
            <RowDefinition Height="*" />
        </Grid.RowDefinitions>

        <StackPanel>
            <ListBox x:Name="Items"/>
        </StackPanel>
        <ContentControl cal:View.Model="{Binding SelectedItem, Mode=TwoWay}" Grid.Row="1" />
    </Grid>
</Window>

根据 Caliburn Micro 文档,我正在使用 MEFBootstrapper。

1) 为什么当我在 ListBox 中选择一个项目时,ContentControl 中什么也没有出现。我显然遗漏了一些东西,但我认为 SelectedItem 被约定所吸引。我试过使用 x:Name="ActiveItem" 也没有用?

2) 如果我的 ShellViewModel.cs 包含 Person 的 BindableCollection 而不是 PersonViewModel,这将如何工作?

3)我可以将 BindableCollection 命名为 Items 以外的名称(是的 - 我知道 Items 是 Caliburn Micro 的约定)?

问候艾伦

4

2 回答 2

1

使您在 ShellView 中的 ContentControl 为

<ContentControl Name="ActiveItem"/>

他们从 Conductor.Collection.OneActive 继承你的 ShellViewModel

public class ShellViewModel : Conductor<IScreen>.Collection.OneActive, IShell
{
}

由于 Conductor 已经有用于绑定 ChildView 的 Items 属性,请从 ShellViewModel 中删除您的 Items 属性。

我们还必须编写代码来激活 ShellView 中的视图

将列表框更改为

<ListBox x:Name="Items" cal:Message.Attach="[Event SelectionChanged]=[Action ActivateChildView($this.SelectedItem)]"/>

在 ShellViewModel 内部有一个新方法

public void ActiveChildView(object view)
{
    ActiveItem(view);
}

我还没有测试过,但希望这会奏效。

于 2013-08-28T12:41:08.207 回答
0
  1. 您实际上需要一个名为SelectedItemPersonViewModel在本例中为类型)的视图模型上的公共属性,否则将无法绑定任何内容,并且您将无法从视图模型访问绑定的数据项。

  2. 您可以直接绑定到一个集合Person。您可以说这违反了Demeter 定律,但如果您PersonViewModel没有Person使用任何其他数据来扩充模型,那么在这种情况下您可能会考虑视图模型盈余。

  3. 是的,您可以将其命名为任何名称,并且约定仍然有效,例如Users将按照约定映射到SelectedUser(或ActiveUserCurrentUser)。People不会按照约定映射到,但如果您想要此功能SelectedPerson,您可以更改ConventionManager委托。 Singularize

于 2013-08-14T09:14:12.633 回答