2011-11-14 2 views
6

È possibile cablare View e ViewModel utilizzando sia un DataContext dichiarativo che un modello dati?Cablaggio di MVVM View e ViewModel mediante dichiarativo DataContext per Design-Time e Data Template per Runtime?

Obiettivo: Voglio collegare Views con un ViewModel per la progettazione e un altro in fase di esecuzione. Attualmente, l'utilizzo di un DataContext dichiarativo per una VM in fase di progettazione e una VM specificata per il runtime in Data-Template non si comporta come previsto.

Background - Ci sono una varietà di modi per cablare una vista e ViewModel tra cui i seguenti:

A.) dichiarativo specificare il ViewModel DataContext all'interno della visualizzazione XAML. Questa tecnica è utile in fase di progettazione utilizzando il costruttore parametrico per passare i dati fittizi.

<UserControl.DataContext> 
    <my: BrowseAssetsViewModel /> 
</UserControl.DataContext> 

B.) specificare a livello di codice ViewModel, Vista e DataContext.

// …Setup code 
BrowseAssetsViewModel viewModel = new BrowseAssetsViewModel(assetRegistry, domains); 
BrowseAssetsView view = new BrowseAssetsView(); 
view.DataContext = viewModel; 

Quando Approach B viene utilizzato in combinazione con Approach A, in fase di esecuzione WPF sovrascrive la DataContext predefiniti specificati nel metodo A utilizzando la versione del ViewModel con il costruttore parametrizzato specificato Approach B.

C.) definire un modello di dati per l'associazione View-ViewModel associando una vista e ViewModel in App.xaml Application.Resources, WPF può cablare la corretta visione in base al tipo di un ViewModel.

<DataTemplate DataType="{x:Type vm: BrowseAssetsViewModel }"> 
    <vw: BrowseAssetsView /> 
</DataTemplate> 

Se una proprietà ViewModel fosse associato a un controllo ContentPresenter, WPF sarebbe cablare-up corrispondente View (in base al tipo del ViewModel) e posizionarlo all'interno ContentPresenter. Ciò è utile nello scenario "ViewModel-first" in cui viene presentato ViewModel e WPF risolve e collega la vista corretta controllando il tipo di ViewModel presentato.

Problema - Quando si utilizza questo metodo C in combinazione con Approach A, WPF risolve la corretta visione ma sembra poi ri-interrogare la vista, chiamando il ViewModel dichiarativo specificato tramite il costruttore senza parametri (Approach A) , quindi sovrascrivendo la proprietà ViewModel esistente!

Domanda: esiste un modo per utilizzare insieme queste tecniche (C e A) senza sovrascrivere inavvertitamente la proprietà C ViewModel?

+0

Perché specificare dichiaratamente un DataContext di ViewModel all'interno di XAML della vista se non si desidera che quella dichiarazione abbia luogo? –

+0

L'obiettivo è trovare una tecnica che supporti ViewModels fittizi in fase di progettazione (A) e risoluzione DataTemplate (C) in fase di esecuzione. –

risposta

8

È possibile specificare che il DataContext è nel caso in cui Un insieme solo solo in fase di progettazione , in questo modo:

<UserControl ... 
    d:DataContext="{d:DesignInstance my:BrowseAssetsViewModel}" 
> 

Per i dettagli, vedere Using a DesignInstance... su MSDN.

+3

Inoltre, aggiungere "IsDesignTimeCreatable = True" in modo che venga visualizzato in VS. Ad esempio, d: DataContext = "{d: DesignInstance Tipo = locale: BrowseAssetsViewModel, IsDesignTimeCreatable = True}" –

+0

Questa risposta, combinata con IsDesignTimeCreatable = True menzionata nel commento, ha risolto il problema. Grazie, entrambi. -Larry –