0

嗨,我正在尝试通过棱镜中的视图模型实例化视图,但没有成功。显示该窗口,但没有更新任何模块区域。

请看下面的代码片段:

 public class Bootstrapper : UnityBootstrapper
    {
        private ShellViewModel shellViewModel;

        protected override DependencyObject CreateShell()
        {
            // register shell types
            var container = ServiceLocator.Current.GetInstance<IUnityContainer>();
            container.RegisterType<IShellView, ShellWindow>("ShellView");
            container.RegisterType<Object, ShellViewModel>("ShellViewModel");
            shellViewModel = container.Resolve<ShellViewModel>();
            this.Shell = shellViewModel.View as DependencyObject;
            return this.Shell;
            //return new ShellWindow();

        }
...

并且视图模型定义如下

 public class ShellViewModel : ViewModelBase<IShellView>
    {
        public ShellViewModel([Dependency("ShellView")]IShellView view)
            : base(view)
        {
        }
    }

 public interface IShellView : IView
    {
        void ShowMessageInOutputWindow(string message);
    }

 /// <summary>
    /// Abstract base class for a ViewModel implementation.
    /// </summary>
    /// <typeparam name="TView">The type of the view. Do provide an interface as type and not the concrete type itself.</typeparam>
    public abstract class ViewModelBase<TView> : ViewBase where TView : IView
    {
        /// <summary>
        /// The view.
        /// </summary>
        private readonly TView view;

        /// <summary>
        /// Initializes a new instance of the <see cref="ViewModel&lt;TView&gt;"/> class and
        /// attaches itself as <c>DataContext</c> to the view.
        /// </summary>
        /// <param name="view">The view.</param>
        protected ViewModelBase(TView view)
            : base(view)
        {
            this.view = view;
        }

        /// <summary>
        /// Gets the associated view as specified view type.
        /// </summary>
        /// <remarks>
        /// Use this property in a ViewModel class to avoid casting.
        /// </remarks>
        public TView View
        {
            get { return this.view; }
        }
    }

使用系统;使用 System.ComponentModel;使用 System.Threading;使用 System.Windows.Threading;

/// /// 所有视图模型的基类 /// 公共抽象类 ViewBase : INotifyPropertyChanging, INotifyPropertyChanged { /// /// 视图。/// 私有的只读 IView 视图;

/// <summary>
/// Initializes a new instance of the <see cref="ViewModelBase"/> class and
/// attaches itself as <c>DataContext</c> to the view.
/// </summary>
/// <param name="view">The view.</param>
protected ViewBase(IView view)
{
    if (view == null)
    {
        throw new ArgumentNullException("view");
    }

    this.view = view;

    // Check if the code is running within the WPF application model
    if (SynchronizationContext.Current is DispatcherSynchronizationContext)
    {
        // Set DataContext of the view has to be delayed so that the ViewModel can initialize the internal data (e.g. Commands)
        // before the view starts with DataBinding.
        Dispatcher.CurrentDispatcher.BeginInvoke((Action)delegate
        {
            this.view.DataContext = this;
        });
    }
    else
    {
        // When the code runs outside of the WPF application model then we set the DataContext immediately.
        this.view.DataContext = this;
    }
}

#region INotifyPropertyChanging Members

public event PropertyChangingEventHandler PropertyChanging;

#endregion

#region INotifyPropertyChanged Members

public event PropertyChangedEventHandler PropertyChanged;

#endregion

#region Administrative Properties

/// <summary>
/// Whether the view model should ignore property-change events.
/// </summary>
public virtual bool IgnorePropertyChangeEvents { get; set; }

#endregion

#region Public Methods

/// <summary>
/// Raises the PropertyChanged event.
/// </summary>
/// <param name="propertyName">The name of the changed property.</param>
public virtual void RaisePropertyChangedEvent(string propertyName)
{
    // Exit if changes ignored
    if (IgnorePropertyChangeEvents) return;

    // Exit if no subscribers
    if (PropertyChanged == null) return;

    // Raise event
    var e = new PropertyChangedEventArgs(propertyName);
    PropertyChanged(this, e);
}

/// <summary>
/// Raises the PropertyChanging event.
/// </summary>
/// <param name="propertyName">The name of the changing property.</param>
public virtual void RaisePropertyChangingEvent(string propertyName)
{
    // Exit if changes ignored
    if (IgnorePropertyChangeEvents) return;

    // Exit if no subscribers
    if (PropertyChanging == null) return;

    // Raise event
    var e = new PropertyChangingEventArgs(propertyName);
    PropertyChanging(this, e);
}

}

#endregion


/// <summary>
    /// Represents a view
    /// </summary>
    public interface IView
    {
        /// <summary>
        /// Gets or sets the data context of the view.
        /// </summary>
        object DataContext { get; set; }

        /// <summary>
        /// Initializes the view
        /// </summary>
        void Initialize();
    }
4

2 回答 2

0

Doing this works though but i don't see the difference.

ShellWindow view = new ShellWindow();
            ShellViewModel viewModel = new ShellViewModel(view);
            return viewModel.View as DependencyObject;
于 2013-07-19T19:30:11.517 回答
0

当您使用名称在 UnityContainer 中注册类型时,您还必须通过指定该名称来解析它。您还必须使用您注册的类型进行解析。

container.RegisterType<Object, ShellViewModel>("ShellViewModel");
shellViewModel = container.Resolve<Object>("ShellViewModel") as ShellViewModel;

您还应该为 ShellViewModel 类定义一个接口,并使用该接口进行注册/解析。

public interface ShellViewModel
{
}

您的引导程序将如下所示:

public class Bootstrapper : UnityBootstrapper
{
    private IShellViewModel shellViewModel;

    protected override DependencyObject CreateShell()
    {
        // register shell types
        var container = ServiceLocator.Current.GetInstance<IUnityContainer>();
        container.RegisterType<IShellView, ShellWindow>("ShellView");
        container.RegisterType<IShellViewModel, ShellViewModel>("ShellViewModel");
        shellViewModel = container.Resolve<IShellViewModel>("ShellViewModel");
        this.Shell = shellViewModel.View as DependencyObject;
        return this.Shell;

    }
}
于 2013-07-19T21:16:26.347 回答