Prism 5 - Using the ViewModelLocator on a UserControl?...

Topics: Prism v4 - WPF 4
Jun 2, 2014 at 6:32 PM
Edited Jun 2, 2014 at 6:50 PM
Unity 3.x

Hi,

I can use the ViewModelLocator in the Shell Window, but how do you get it to work on a UserControl that's inside a Project Library that will be injected into the Shell Window?
<Fluent:RibbonWindow 
    x:Class="NathsarTS.Master.Views.Shell"
    x:Name="NatsarTurahStudyMaster" 
    xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
    xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
    xmlns:prism="http://www.codeplex.com/prism" 
    xmlns:common="clr-namespace:NathsarTS.Common.Shared;assembly=NathsarTS.Common"
    xmlns:Fluent="clr-namespace:Fluent;assembly=Fluent"
    xmlns:Mvvm="clr-namespace:Microsoft.Practices.Prism.Mvvm;assembly=Microsoft.Practices.Prism.Mvvm.Desktop"
    Mvvm:ViewModelLocator.AutoWireViewModel="True"
    Title="Natsar Turah Study Master" Height="768" Width="1024" WindowStartupLocation="CenterScreen" WindowState="Maximized"
    ScrollViewer.HorizontalScrollBarVisibility="Auto" ScrollViewer.VerticalScrollBarVisibility="Auto">
    <DockPanel LastChildFill="True" x:Name="ShellContentGrid">
        <ContentControl 
            DockPanel.Dock="Top"
            x:Name="ShellContent" 
            prism:RegionManager.RegionName="{x:Static common:RegionNames.ActionRegion}">

        </ContentControl>

        <ItemsControl prism:RegionManager.RegionName="{x:Static common:RegionNames.MainRegion}" DockPanel.Dock="Top"/>
    </DockPanel>
</Fluent:RibbonWindow>
I'm injecting UserControl:FluentRibbonView into the ActionRegion. Is it best to use the ShellViewModel for all the actions for the UserControl:FluentRibbonView instead of trying to locate another ViewModel?

But, I would like to use the ViewModelLocator in other parts of the Application when I inject views from a Project Library without using Code-Behind or UserControl Resource.

Because, most of the time I use parameterized constructors.

Thanks!...
Jun 3, 2014 at 3:46 PM
Hi,

It would be helpful if you could provide us the issues you are facing when using the ViewModelLocator in your user control?

Thanks,
Ez.
http://blogs.southworks.net
Jun 4, 2014 at 2:00 AM
Edited Jun 4, 2014 at 2:01 AM
Hi,

Thanks for the response. Sure!

I have a project library with a FluentRibbonView : UserControl, IView:
<UserControl 
    x:Class="NathsarTS.FluentRibbon.Views.FluentRibbonView"
    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:Fluent="clr-namespace:Fluent;assembly=Fluent"
    xmlns:Mvvm="clr-namespace:Microsoft.Practices.Prism.Mvvm;assembly=Microsoft.Practices.Prism.Mvvm.Desktop"
    Mvvm:ViewModelLocator.AutoWireViewModel="True"
    xmlns:d="http://schemas.microsoft.com/expression/blend/2008" 
    mc:Ignorable="d" d:DesignHeight="768" d:DesignWidth="1064">
    <Fluent:Ribbon >
        <!--Backstage-->
        <Fluent:Ribbon.Menu>
            <Fluent:Backstage>
            </Fluent:Backstage>
        </Fluent:Ribbon.Menu>
        <!--Tabs-->
        <Fluent:RibbonTabItem Header="Tab">
            <Fluent:RibbonGroupBox Header="Group">
                <Fluent:Button Name="buttonGreen" Header="Green" Icon="Images\Green.png" LargeIcon="Images\GreenLarge.png" />
                <Fluent:Button Name="buttonGray" Header="Grey" Icon="Images\Gray.png" LargeIcon="Images\GrayLarge.png" />
            </Fluent:RibbonGroupBox>
        </Fluent:RibbonTabItem>
    </Fluent:Ribbon>
</UserControl>
I will be injecting into the Shell : RibbonWindow, IView (Above). The FluentRibbonView has a FluentRibbonViewModel : BindableBase, but its not finding the ViewModel. The file structure is named properly as the Shell's.

To check to see if its working I placed a Debug.WriteLine("FluentRibbonViewModel instantiation"); in the ViewModel's constructor.
Step into: Stepping over non-user code 'NathsarTS.Master.App..ctor'
Step into: Stepping over non-user code 'NathsarTS.Master.App.Main'
Step into: Stepping over non-user code 'NathsarTS.Master.App.InitializeComponent'
ShellViewModel instantiation
CommonModule Constructor instantiation
CommonModule instantiation
CommonModule LoadModuleCompleted
FluentRibbonModule Constructor instantiation
FluentRibbonModule instantiation
CommonModule LoadModuleCompleted
FluentRibbonModule LoadModuleCompleted
TurahStudyUIModule Constructor instantiation
TurahStudyUIModule instantiation
CommonModule LoadModuleCompleted
FluentRibbonModule LoadModuleCompleted
TurahStudyUIModule LoadModuleCompleted
Everything works fine except the UserControl is not finding its ViewModel.
Jun 4, 2014 at 4:50 PM
Edited Jun 4, 2014 at 4:52 PM
Hi,

Thanks for sharing this.

Prism’s ViewModelLocator class has an attached property, AutoWireViewModel that when set to true (as in your scenario) will try to locate the view model of the view, and then set the view’s data context to an instance of the view model. To locate the corresponding view model, the ViewModelLocationProvider first attempts to resolve the view model from any mappings that may have been registered by the Register method of the ViewModelLocationProvider class. If the view model cannot be resolved using this approach, for instance if the mapping wasn't created, the ViewModelLocationProvider falls back to a convention-based approach to resolve the correct view model type. This convention assumes that view models are in the same assembly as the view types, that view models are in a .ViewModels child namespace, that views are in a .Views child namespace, and that view model names correspond with view names and end with "ViewModel."

If you don't have any mapping registered, it might be possible that this is failing because your ViewModel is not following the default naming convention (It should be named FluentRibbonViewViewModel instead of FluentRibbonViewModel)

If your View Models are in different assembly, then you will have to override the logic of the ViewModelLocator.SetDefaultViewTypeToViewModelTypeResolve.

I hope you find this helpful.
Thanks,
Ez
http://blogs.southworks.net
Jun 5, 2014 at 12:03 AM
Thanks! My models were not name properly after their views and now everything is fine now! :)