I'm currently using MVVM in a WPF project, all works very well.
I have one Master view and many Detail views that I manage using a currentView property in my MasterViewModel. By using a datatemplate, I bind a view to a viewmodel.
In fact, my master view has a contentcontrol whose content property is binded to my CurrentView property. When I set this currentview property to a viewmodel or another, it calls the corresponding template.
My problem is that using this, my detail views doesn't have explicit datacontext because it is placed by my datatemplate. So in blend, when I open my view to edit its design, I have no datas to bind to my view. If I set a datacontext to my detailview, in blend I can see all datas I can bind but in runtime, the datacontext set by datatemplate is overrided by the datacontext set in my detailview, so I have no datas during runtime.
Does anyone knows how I can create a good MVVM project, with views managed by datatemplates and with datacontext that we can see with Blend ?
Thanks,
I've got a blog post on this issue: http://www.robfe.com/2009/08/design-time-data-in-expression-blend-3/
My post is all about showing data in blend without having to have that data displayed or even created at runtime.
I solved a similar issue in this post:
How can I use Expression Blend to edit a DataTemplate created in Visual Studio?
Related
I am playing around with Xamarin.Forms (mvvm) with Prism and have noticed that some tutorials show navigating to another Page while others show navigating to a View.
At a high level, I understand the literal difference... however I do not understand when I should use one over the other? I have an inclination that some of the reasoning is around dependencies, for example:
A Page has the instance of User > navigate to a view = User is still present when the back operation is used... meanwhile if you want this same behavior in navigating to and from a page, you'll need to pass the instance around via parameters... Is this correct/the reasoning behind navigating to and from views instead of pages?
In X.Forms View's are only visual objects, they do not support any navigation or any kind of infrastructure. They can only be showed when you navigate to a Page that hosts them, it doest not make sense the phrasing navigate to a View. So you should only use Page's.. In your example project they also only navigate to Page's. In the one you say they are navigating to "Views" it is only in the name, because ViewA is a ContentPage
Technically, in pure MVVM, the ViewModel should know completely nothing about the View and vice versa. When you use Page First Navigation approach you violate the first sentence. Here is an example:
class MyViewModel
{
}
class MyView
{
public MyView()
{
InitializeComponent();
// Alternatively you can do the same thing in XAML
this.BindingContext = new MyViewModel();
}
}
As you see the View is aware of the ViewModel.
When you use a ViewModel First Navigation approach, the decision of which
View should have witch ViewModel is delegated to a dedicated class. This class then is used in a custom NavigationService to match a ViewModel to a View. So it will be possible to navigate from a ViewModel to a ViewModel. This way both ViewModel and the View know nothing about each other. The disadvantage of this approach is complexity.
This is a very short answer, however, I hope you will get the key point. There are many examples of both approaches:
ViewModel First Navigation
Page First Navigation
P.S.: Prism has very nice mechanism that handle navigation. What I wrote above and the examples that I provided are just for low level understanding of this approach. If you want to use Prism you definitely have to be familiar with it.
I have a view, I have bind this view to a view Model having list items.
When I make any changes to view Model corresponding changes I could see in view.
But when I remove an item from view it is not getting updated in viewModel.
I am using KendoUi for above.
Can any one please let me know what is the issue here
I assume ViewModel collection is of type ObservableCollection. Use a two-way binding to accomplish what you need.
ItemsSource = {Binding Path=MyCollection, Mode=TwoWay}
I'm using WPF and trying to program the MVVM way.
I understand how every view has its own view model and this works quite well. I am struggling to manage the interaction between views though.
Say I have two views, View1 and View2, each with its own ViewModel, ViewModel1 and ViewModel2. If I have a combobox on View1 and a button, what is the correct way to close the first view, notify the second view of the selection and show the second view once the button is pressed? It doesn't seem like it should go in the model because it's a UI thing. The ViewModel shouldn't know how to open and close WPF forms (or should it?) And the views shouldn't know about any other ViewModels (or should they?)
So how are these problems solved? In a nutshell:
1) How is data passed between views?
2) What manages the lifetime/visibility of views?
It will depend on whether you are doing view model or view first, and the exact implementation details will depend on if you are using an MVVM framework. If you aren't using a framework, then I would strongly recommend you start using one.
In your example, when the button is pressed, a method on ViewModel1 will be invoked. If doing view model first (which I would recommend), you would instantiate an instance of ViewModel2, and at this point you could pass in the combobox selection to the constructor of ViewModel2.
Depending on your framework, there will be different ways of then displaying the view associated with ViewModel2.
For 1) you can sychronize data through the DataModel. Provided each view shares the same instance of the DataModel and it implements INotifyPropertyChanged multiple views can be updated simulateneously.
Your sesond question is a matter of design, as #devdigital states it can depend on whether it is View first or ViewModel first. I would consider the introduction of a Controller class in much as the same way ASP.Net MVC works which controls which view is displayed. You can expose a ViewClosed event on the ViewModel which the controller can listen to and based on your workflow open another view.
You might consider introducing Controllers which are responsible for the lifetime management of the ViewModels. Furthermore, they mediate between the ViewModels.
The sample applications of the WPF Application Framework (WAF) show how these Controllers can be implemented.
I've got a prism/mvvm view and want to notify the ViewModel if the View has got or lost the focus.
I'd guess I'd need to bind GotFocus of the View to an action in the ViewModel, but I got no idea how to get started on this.
Sure this is a standard problem which has been solved somewhere, and it's just me not finding the solution?
You could use InvokeCommandAction behavior. This behavior is defined in the assembly System.Windows.Interactivity which is part of Expression Blend. With this behavior you could bind to the GotFocus event of your view and execute a command in your viewModel.
The same approach can you use for LostFocus. Here´s an example how to use InvokeCommandAction.
One thing about GotFocus of UserControl. You should know that the GotFocus event of the View is raised when a control, such as TextBox, gets the focus. You can´t focus the UserControl by its self.
[Update]
GotFocus of the UserControl is raised when IsTabStop is set to true
Can´t you use the IActiveAware interface of the prism framework. The IsActive property gets set when the view gets navigated in the region.
The interface can be implemented on the View and the ViewModel (requires that the viewmodel instance is set as DataContext of the view) to be notified when the view is activated in the region.
I am trying to create a usercontrol that is an extremely simple form. This usercontrol will appear in a number of different views in my app. I am thoroughly confused on how this can be accomplished.
I have created a controller, and then created a usercontrol that uses that controller.
I then created another controller and created a view for an index of that controller. Inside this view i added my usercontrol reference:
<% Html.RenderPartial("~/Views/UserControlController/Create.ascx"); %>
When i attempt to navigate to the view i can see that the actionresult method for the usercontrol in UserControlController is never called.. What am i missing?? thanks for any help.
Ok, I see your problem. Dont Render partial, you want render action. Whats the difference? Render Partial should read RenderPartialView, not RenderPartialAction. If you want to execute the action, you need Html.RenderAction.