开发者

Change selected tab from ViewModel And send objects between ViewModels

I got a wpf desktop application with 3 ViewModels. I have 1 ViewModel that contains a tabhost and tabs. And I got 2 tabs. Each of those tabs has it's own ViewModel.

The problem I have is that in tab1 I have a listview with searchresults and a button. When I select one item in that list and press the button, I want to change tab and display information about that item I selected in tab2.

I have searched for a solution, but it seems to include creating all ViewModels in the MainViewModel and providing a reference of the MainViewModel to all the subViewModels.

Is there no other way?



EDIT

I just managed to solve my problems with MVVM light that I added to the project.

By binding a method in the MainViewModel and a property in it to the .xaml I can now call it from tab1 with info to tell it to change tab. Also, by binding a method in tab2 I can now send over an item from tab1 in the same manner.

This is how I solved it after importing MVVM light into the project.

In tab1

Messenger.Default.Send<string, tab2ViewModel>(--object to send to tab2--);
Messenger.Default.Send<int, MainViewModel>(--tab index--);

In Main/tab2

Messen开发者_JAVA百科ger.Default.Register<int>(this, ChangeTab);
public void ChangeTab(int i)
{
   SelectedTabIndex = i; //Bound property in .xaml
}

It seems to automagically just work..

P.s. Thanx for reply. I shall look into how Prism work as well, and see if there is any advantages to use that instead of MVVM light(Not right now however).


A good solution to your problem would be to use the EventAggregator of Prism.

This service lets you listen to and publish a particular type of event from anywhere in your application without tying your view-models to each other. This is a really nice solution for MVVM and other losely-coupled designs. It is easy and works like a charm.

You can find the documentation here : EventAggregator More information about Prism here : Prism on Codeplex


Here is a concrete sample. Imagine you want to change the title of the main Window from anywhere in the application. You would create this event:

public class TitleChangedEvent : CompositePresentationEvent<string>{}

Then you would suscribe to this event in your MainWindowViewModel like this:

eventAggregator.GetEvent<TitleChangedEvent.Suscribe(
(newTitle) =>
{
    this.WindowTitle = newTitle;
});

And finally you can update the title from anywhere in your application like this:

eventAggregator.GetEvent<TitleChangedEvent>().Publish("This is a new title!");

Quite easy as you can see.


Smililarly with MVVM Light you would first create a message for notification:

public class TitleChangedMessage : GenericMessage<string>{}

Then you would listen to the message like this in your MainWindowViewModel:

Messenger.Register<TitleChangedMessage>(this, 
(message) =>
{
    this.WindowTitle = message.Content;
}

And you would send an update like this:

Messenger.Send<TitleChangedMessage>(this, new TitleChangedMessage("This is a new title!"));

This is the MVVM Light way to do it :)

You can also have a look at this related question: Messenger class in MVVM Light

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜