Laden...

WPF / MVVM Projektstruktur

Erstellt von Lynix vor 12 Jahren Letzter Beitrag vor 12 Jahren 4.629 Views
L
Lynix Themenstarter:in
667 Beiträge seit 2004
vor 12 Jahren
WPF / MVVM Projektstruktur

Hallo zusammen,

ich bin gerade dabei mich mit WPF zu beschäftigen, und versuche gerade im Hinblick auf das MVVM Muster eine schöne "Blueprint"-Projektstruktur zu erstellen.

Ich gehe dabei von einem simplen (einzelnen) WPFApplication Projekt aus, in dem ich drei Namespaces vorsehe : MyApp.View MyApp.ViewModel und MyApp.Model

Für ein fiktives Window "Window1" welches ich im MyApp.View Namespace ablege, würde ich jetzt gerne eine Klasse Window1_VM anlegen, in dem ich alle Properties, die Window1 per Databinding konsumiert und alle für Window1 relevanten Custom Commands implementieren will.

Frage 1:

Sehe ich es richtig, dass ich im Window1 Codebehind dann eine Instanz von Window1_VM anlegen muss, um über XAML auf die Properties binden zu können ?
Falls ja, ist doch eigentlich die Entkopplung von View und ViewModel gleich schon dahin, oder ?

Als Alternative ist mir noch die Idee gekommen, Window1_VM gleich als statische Klasse zu realisieren, dann kann ich aber das nichtstatische NotifyPropertyChanged Event aus dem INotifyPropertyChanged interface nicht mehr nutzen, und das Binding taugt nicht mehr wirklich.

Es würde sich natürlich noch über eine Realisierung von Window1_VM als Singleton lösen / umgehen lassen, aber das kann doch eigentlich nicht der Standard sein oder ?

Wäre nett, wenn hier jemand etwas Licht ins Dunkel bringen könnte...

Frage 2:

Ich bin bisher davon ausgegangen, ich das MVVM gewinnbringend nutzen kann, um die Ebene View von der Ebene Model möglichst unabhängig zu halten. Wenn ich mir jetzt eine einfache Anwendung vorstelle, die nur aus einer Datenbank eine Liste von Datensätzen auslesen soll und diese Liste darstellen soll, wie würde man hier am Besten vorgehen ?

Wenn ich mir nun ein WPF Window mit einem Datagrid anlege und die Datasource auf ein DataSet im ViewModel binde, dann habe ich doch durch die Entscheidung, auf dem Window ein Datagrid zu benutzen, eigentlich schon die Ebene ViewModel (muss ein Dataset bereitstellen) und die Ebene Model (muss beim Zugriff auf die Datenbank ein Dataset zurückgeben) schon gleich mit festgelegt, oder ?

Wenn ich nun übermorgen entscheide, dass mir eine ListView viel besser gefällt als ein Datagrid, dann wäre es ja notwendig auch das ViewModel anzupassen, damit es mir die Daten in einem für eine Listview angenehmeren Format als ein Dataset zur Verfügung stellt...

Wo liegt mein Denkfehler ?

"It is not wise to be wise" - Sun Tzu

3.430 Beiträge seit 2007
vor 12 Jahren

Hallo Lynix,

an sich sind deine Gedanken schon mal nicht schlecht.
Um dem Hauptfenster sein ViewModel zuzuweisen gibt es mehrere Vorgehensweisen.
Manche machen das im Codebehind und setzen manuell den DataContext (nur im MainWindow).

Oder man verwendet irgend einen Resolver der das ViewModel automatisch lädt.

Für diese ganzen Feinheiten sind die MVVM Frameworks ziemlich praktisch. Die nehmen einen viel Arbeit ab, damit man es nicht selbst machen muss.
Ich verwenden Cinch V2. Es gibt aber auch noch viele andere wie z.B. Caliburn
Mir persönlich gefällt Cinch besser da es "natürlicher" wirkt, weil es den View-First verwendet. Damit kann man perfekt Designtime / Runtime ViewModels getrennt laden lassen.
Dabei findest du auch noch ein umfangreiches Beispielprojekt wo man die meisten Dinge nachschauen kann.

Ein netter Artikel zu MVVM ist der hier: MVVM - Josh Smith

Ich hoffe dass es dir weitergeholfen hat. Auch wenn ich nicht auf jede Frage einzeln eingegangen bin.

Gruß
Michael

6.911 Beiträge seit 2009
vor 12 Jahren

Hallo Lynix,

@Frage 1: statische Klasse und Singleton sind definitiv nicht der Standard. Guck dir mal MVVM Instantiation Approaches an, dort findest du eine nette Übersicht über die Möglichkeiten die anschließend auch kommentiert wurde.

@Frage 2:

Wenn ich mir jetzt eine einfache Anwendung vorstelle, die nur aus einer Datenbank eine Liste von Datensätzen auslesen soll und diese Liste darstellen soll, wie würde man hier am Besten vorgehen ?

Im Model bildest du die Datensätze ab, z.B. durch einen Customer. Dieses Model kannst du dann durch ein CustomerViewModel kapseln und ggf. für die View aufbereiten.
In einem weiteren ViewModel, einem AllCustomerViewModel, hast du eine ObservableCollection<CustomerViewModel> und gegen diese bindest du in der View. Dann ist es egal obs in einem DataGrid od. einem ListView od. sonst was dargestellt wird.

Es gibt auch Abwandlungen von MVVM bzw. MVVM ist so loose definiert, dass es mehrere Ausprägungen davon gibt. Interessant dazu ist auch Thought: MVVM eliminates 99% of the need for ValueConverters und das Bild in MVVM: Beziehung zwischen Model, View und ViewModel (die Beiträge davor sind nicht am produktivsten 😉).

Bitte beachte [Hinweis] Wie poste ich richtig? Punkt 1.2, sonst gibts einen Sammelthread der unübersichtlich wird.

mfG Gü

Stellt fachliche Fragen bitte im Forum, damit von den Antworten alle profitieren. Daher beantworte ich solche Fragen nicht per PM.

"Alle sagten, das geht nicht! Dann kam einer, der wusste das nicht - und hat's gemacht!"

1.002 Beiträge seit 2007
vor 12 Jahren

Hallo zusammen,

was zurzeit eventuell auch interessant ist: Vom 12. – 14. November bietet Pluralsight 3 Stunden kostenloses Training für WPF bzw. Prism an. Mehr Details unter FREE WPF and Silverlight Online Prism Training from PluralSight on Nov 12-Nov 14.

m0rius

Mein Blog: blog.mariusschulz.com
Hochwertige Malerarbeiten in Magdeburg und Umgebung: M'Decor, Ihr Maler für Magdeburg

L
Lynix Themenstarter:in
667 Beiträge seit 2004
vor 12 Jahren

@Frage 1: statische Klasse und Singleton sind definitiv nicht der Standard. Guck dir mal
>
an, dort findest du eine nette Übersicht über die Möglichkeiten die anschließend auch kommentiert wurde.

Hallo gfoidl,

der Link hat mir für Frage 1 schonmal weiter geholfen, danke. Aber eine Nachfrage habe ich noch zum Verständnis. Bei der in dem Artikel beschriebenen Option 4

  
<UserControl ...>  
    <UserControl.DataContext>  
        <local:CalculatorViewModel />  
    </UserControl.DataContext>  
</UserControl>  
  

-> würde das bedeuten, dass CalculatorViewModel eine statische Klasse sein muss ? Oder wird durch diese XAML Deklaration implizit eine Instanz von CalculatorViewModel erzeugt auf die sich dann die weiteren Bindings beziehen ?

"It is not wise to be wise" - Sun Tzu

3.430 Beiträge seit 2007
vor 12 Jahren

Hallo,

nö, das musst keine Statische Klasse sein.
Damit wird eine neue Instanz erstellt und dem DataContext zugewiesen.

Die Bindings in diesem UserControl werden somit direkt auf den DataContext (also die neue Instanz gehen

Oder wird durch diese XAML Deklaration implizit eine Instanz von CalculatorViewModel erzeugt auf die sich dann die weiteren Bindings beziehen

Genau so ist es 😃

Gruß
Michael