2009-04-24 8 views
8

Je prévois une application WPF quiComment créer des formulaires de saisie de données dynamiques dans une application WPF?

  • pouvoir créer forme entrée de données dynamiques (ce qui signifie la forme obtient les champs à afficher, leur ordre, etc. à partir des données dans la base de données, pas de le XAML)
  • utiliser le modèle MVVM si possible

Voici comment je prévois d'aller à ce sujet: dans un client de données d'entrée Voir je fixerait le contexte de données:

<UserControl.DataContext> 
    <vm:DynamicFormViewModel/> 
</UserControl.DataContext> 

et comprennent un élément dans mon XAML comme un espace réservé pour la forme:

<UserControl.Content> 
    <view:DynamicFormView x:Name="CustomerEntry"/> 
</UserControl.Content> 

alors dans mon MODELVIEW je veux pas avoir des propriétés statiques, mais je veux construire le XAML comme un construit contrôle HTML arrière dans ASP.NET, de cette façon:

View view = new View(); 
view.Children.Add(...) 

et ainsi construire la grille basée sur la collecte de données (nom, prénom) et les méta-données (étiquette de champ, nom de domaine, HelpText sur le terrain, l'ordre d'affichage sur le terrain , etc.) que ViewModel obtient du modèle.

  • a quelqu'un construit une application WPF qui pourrait créer des formulaires dynamiques de cette manière?
  • avez-vous utilisé le modèle MVVM?
  • est-il possible d'utiliser le modèle MVVM de cette manière ou le modèle MVVM présuppose-t-il des champs statiques dans le modèle View qui sont directement liés aux éléments statiques de la vue?

Répondre

7

Vous devrez écrire des modèles de données pour vos différents types de données de champ afin que WPF choisisse comment afficher vos données en fonction de leur type. quelque chose de ce format:

NOTE: Ce n'est pas WPF simplement le code pseudo

<DataTemplate DataType="{x:Type DateTime}"> 
    <DatePicker Value="{Binding}"/> 
</DataTemplate> 
<DataTemplate DataType="{x:Type String}"> 
    <TextBox Text="{Binding}"/> 
</DataTemplate> 

Il ne doit pas être un type primitif. Il peut s'agir d'un type de classe Email, DateApproved ou même Url. par exemple.

class Customer 
{ 
    public Email Email{get;set;} 
    public DateTime DateApproved{get;set;} 
    public URI Url{get;set;} 
} 

public class Email 
{ 
    public string Type{get;set;} 
    public string Value{get;set;} 
} 

..etc ...

Mise à jour

Vérifiez cette exemple dynamique WPF interface utilisateur sur MSDN: Dynamic Data Entry with WPF and LINQ

+0

Exactement, mais je souhaite inclure des types personnalisés tels que Email, URL, Durée, Client, chacun devra donc avoir sa propre validation. J'imagine une base appelée "CustomType" qui hérite de tous ces types et chacun construit sa propre méthode appelée par ex. IsValid() et displayAsXaml() etc –

+0

Mettre des choses dans XAML à moi se sent statique. Je me souviens des applications ASP.NET, dans presque tous les projets, vous avez fini par avoir un tout petit Default.aspx avec quelques contrôles qui ont tous été créés dynamiquement. Sinon, vous créez des applications statiques uniques qui ne peuvent pas être modifiées très facilement. Je suppose que pour obtenir cette nature dynamique de WPF, vous aurez juste un petit Window1.xaml et ensuite tout ce qui est créé dynamiquement de la même manière. –

+0

Ce message semble être vieux. Mais je voudrais faire quelque chose de similaire dans WPF 4.0. Le lien vers l'exemple d'interface utilisateur dynamique WPF semble être rompu. Est-ce que quelqu'un connaît un autre exemple? –

1

Vous devez configurer un DataTemplate pour chaque type de champ par exemple Date, Chaîne, Bool. Cela déterminera comment chaque champ apparaîtra.

Vous pouvez ensuite utiliser les colonnes d'une requête de base de données pour générer une liste d'objets et les placer dans ItemsControl.

ObservableCollection<ColumnDef> columns = new ObservableCollection<ColumnDef>(); 

// Add columns from DB 
columns.Add(new StringColumnDef{Object=..., Field=..., Label=..., Value=...}); 
columns.Add(new DateColumnDef{Object=..., Field=..., Label=..., Value=...}); 

items.ItemsSource = columns; // items is an ItemsControl 

Chaque élément du contrôle d'élément s'affichera en fonction de DataTemplate pour ce type.

À l'intérieur de ColumnDef, vous pouviez utiliser Reflection pour mettre à jour l'objet de données avec les modifications des contrôles de l'interface utilisateur. Vous pouvez ensuite appliquer les modifications à la base de données lorsque l'utilisateur enregistre.

Questions connexes