获取Bootstrapper中OnStartup中创建的View Model实例

时间:2015-04-18 11:51:59

标签: c# wpf mvvm caliburn.micro

我仍然是WPF和Caliburn的新手,但是,鉴于我在我的bootstrapper类中有以下内容:

    protected override void OnStartup(object sender, StartupEventArgs e)
    {
        DisplayRootViewFor<MainWindowViewModel>();
    }

据我所知(或不知道),DisplayRootViewFor创建View和ViewModel类的实例,绑定它们并显示它们。所以我想要的是能够获得ViewModel类的实例。可能我一般都不理解MVVM原则,但实质上,在我的观点中,我希望能够说出一些简单的内容:

    MainWindowViewModel vm = ?;
    vm.Property = "Hi this is a test";

那么'?'会怎样?或者这只是一般的皱眉头?

编辑: 正如下面的回答和评论中所提到的,我希望与Avalon Dock合作,这对于从MVVM部分可访问而言是着名的。我真的只是想找到一种方法来查找在调用OnStartup时创建的ViewModel的正确实例。这可能吗?

2 个答案:

答案 0 :(得分:1)

Caliburn Micro与大多数MVVM框架有点不同,因为它是模型优先的,即模型的名称(例如MainWindowViewModel)决定了在哪个视图中创建(MainWindowView案例),Caliburn Micro负责该对的创建和绑定接线。它使用许多标准(但可覆盖的)约定来实现这一点。

拥有视图模型 - 视图对的想法是,视图绑定并显示视图模型的内容和状态,并且当用户操作视图中的元素时,它会触发视图模型中的命令(例如,按下按钮)。视图模型负责对这些命令作出反应,并相应地更新它的状态或内容。完成后,视图将反映新的状态或内容。

一般情况下,如果您习惯其他MVVM框架,这可能会让您感到困惑,Caliburn Micro需要 0 行代码&#34;代码&#34;对于您的View类,因为所有绑定通常只能在XAML中完成。

为了说明一个允许从可用称呼列表中为用户选择称呼的屏幕的基本示例,显示所选用户称呼的预览,并允许保存它。

public class UserSalutationViewModel : Screen
{
    private readonly string _userName;
    private readonly IDataService _dataService;
    private string _selectedSalutation;

    public UserSalutationViewModel(string userName, IDataService dataService)
    {   
        _userName = userName;
        _dataService = dataService;
        Salutions = new BindableCollection<string>(_dataService.GetAvailableSalutations());
        _selectedSalutation = _dataService.GetUserSalutation(_userName);
    }

    // List with selectable salutations. Bound in the View to a ListBox element.
    public BindableCollection<string> Salutions { get; private set;}

    // Caliburn Micro will automatically bind this to the selected item in the ListBox.
    public string SelectedSalutation 
    {
        get { return _selectedSalutation; }
        set
        {
            _selectedSaluation = value;
            NotifyOfPropertyChange(() => SelectedSalutation);
            // Notify the view to refresh with the new user salutation value
            NotifyOfPropertyChange(() => UserSaluation);
        }
    }

    // This returns a model constructed value. Bound to a Label element in the View
    public string UserSalutation
    {
        get { return _selectedSaluation + " " + _userName; }
    }

    // Saves the selected salutation. Bound to a Button in the View
    public void Save()
    {
        _dataService.SaveUserSalutation(_userName, _selectedSalutation);
    }
}

然后UserSalutationView XAML也可以非常简单,只包括视图中的元素。

<UserControl x:Class="MyProject.UserSalutationView"
         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" 
         xmlns:cal="clr-namespace:Caliburn.Micro;assembly=Caliburn.Micro"
         mc:Ignorable="d" 
         d:DesignHeight="300" d:DesignWidth="300">

    <Grid HorizontalAlignment="Stretch" VerticalAlignment="Stretch">
        <Grid.RowDefinitions>
            <RowDefinition Height="Auto"/>
            <RowDefinition Height="*"/>
            <RowDefinition Height="Auto"/>
        </Grid.RowDefinitions>
        <TextBlock Grid.Row="0" x:Name="UserSalutation"/>  
        <ListBox Grid.Row="1" x:Name="Salutions"/>
        <Button Grid.Row="2" x:Name="Save" Content="Save user salutation"/>
    </Grid>

</UserControl>

XAML中的x:Name部分用于Caliburn的View with ViewModel的连线。

答案 1 :(得分:0)

要从View中后面的代码直接访问Caliburn Micro View模型,您可以访问其DataContext属性并将其转换为视图模型类型。像这样(在UserSalutationView.xaml.cs中):

// Get my UserSalutationViewModel
var viewModelInstance = DataContext as UserSalutationViewModel;