Combo box driven UI element with Caliburn.Micro
I'm trying to get my head around Caliburn.Micro and MVVM in a small test WPF app.
I've got a custom user control that has a payment combo box (with the Cash, Check, Credit) and next to this combo box I want load the appropriate data entry view based on the selected payment type. For example, if the user selects cash, maybe I only load a view with an amount text field but if the user selects credit I'll load a view with fields for amount, credit card type, credit card number, etc.
Can Caliburn.Micro help with this in any way? I keep wondering if this is a use case for the Screens and Conductors functionality built into Caliburn.Micro but am unsure. If Caliburn can help what should the view model hierarchy be to support that? I could see having a开发者_如何转开发 PaymentViewModel that contains an instance of a PaymentTypeViewModel but I'm not sure how I'd facilitate the switching of the PaymentTypeViewModel instance that would somehow be based on the current selection in the combo box as well as load the associated view for that view model.
Any advice given is much appreciated.
There are a few ways you could do this, but using Caliburn's Conductor
and Screen
types makes the most sense. I suppose one question would be what are you going to do with this data once you retrieve it from the user? Will it be persisted, or temporarily stored as application state whilst you retrieve further information from the user on different screens?
Either way, it would make sense to use a single screen conductor (Conductor<T>
), which will hold references to each of the three types of payment retrieval screens. Create a view model and view for each of the payment screens, instantiate and store a reference to each in your Conductor
(or better still inject these as dependencies into your conductor's constructor, or inject a factory type which instantiates them).
Through conventions, your combobox if called Payment
will automatically bind the selected value to a SelectedPayment
property on your conductor. In this property's setter, you can call the ActivateItem
method on the appropriate payment view model reference based on the value of SelectedPayment
.
Presumably, you'll have an 'OK' or similar button on your conductor, which can retrieve the data from the currently active model (ActiveItem
). Each payment view model could implement an interface for example with a GetPaymentDetails
method, and perhaps this could return a serialized form of the details ready to be persisted.
Should also mention in your conductors view (let's assume it's called ShellView.xaml), you can use a ContentControl
to display the current payment view model (and have Caliburn inject the appropriate view and do the binding) which is referenced as the ActiveItem
:
<ContentControl x:Name="ActiveItem" />
Note that you could be a bit fancier and give your combobox the (slightly ambiguous) name of Items
, and bind its ItemsSource
to a collection of your payment view models, which can be the Items
collection on Conductor<T>.Collection.OneActive
. Caliburn will automatically bind the selected value (a payment view model) to the ActiveItem
property on your conductor, and therefore your current view will automatically switch as you change combobox values.
精彩评论