Model-View-ViewModel (MVVM)

Aus dev.kaibel.net
Zur Navigation springen Zur Suche springen

Model-View-ViewModel (MVVM) Entwurfsmuster

Das Model-View-ViewModel-Muster (kurz: MVVM) ist ein Architekturmuster, das aus dem MVP-Muster hervorgegangen ist. Es wurde ursprünglich von Microsoft für das Framework WPF (Windows Presentation Foundation) entwickelt und wird heute in vielen modernen UI-Frameworks verwendet – etwa in **MAUI**, **Xamarin**, **Angular**, **Vue.js** und **Blazor**.

Das Ziel ist es, **Benutzeroberfläche, Logik und Daten** konsequent zu trennen und gleichzeitig eine **automatische Synchronisierung** zwischen View und Datenmodell durch **Datenbindung (Data Binding)** zu ermöglichen.

Grundidee

MVVM teilt eine Anwendung in drei Schichten:

Komponente Aufgabe
Model Enthält die Daten und Geschäftslogik.

Definiert, wie Daten gespeichert, verarbeitet und validiert werden.

View Stellt die Benutzerschnittstelle dar.

Zeigt die Daten aus dem ViewModel an und sendet Benutzerinteraktionen zurück.

ViewModel Vermittelt zwischen View und Model.

Bereitet Daten auf, stellt Bindungsfelder bereit und reagiert auf Änderungen.

+--------------+         +----------------+         +--------------+
|    View      | <-----> |   ViewModel    | <-----> |    Model     |
| (Anzeige)    |  Binding| (Logik + State)|         | (Daten)      |
+--------------+         +----------------+         +--------------+

Hauptprinzip

Das ViewModel ist das Bindeglied zwischen der Oberfläche (View) und der Logik (Model). Es stellt **Eigenschaften** und **Befehle (Commands)** bereit, an die die View **gebunden (bound)** wird. Wenn sich der Wert im Model ändert, wird die View automatisch aktualisiert – und umgekehrt.

Ablauf

1. Die **View** bindet ihre Steuerelemente an Eigenschaften und Befehle des ViewModels. 2. Das **ViewModel** verwaltet den Anwendungszustand und kommuniziert mit dem Model. 3. Das **Model** speichert die Daten und führt Geschäftslogik aus. 4. Änderungen werden über das Bindungssystem automatisch synchronisiert.

Beispiel (C# / Pseudocode)

Ein einfaches MVVM-Beispiel in C#-ähnlicher Syntax:

// --- Model ---
public class User {
    public string Name { get; set; }
}

// --- ViewModel ---
using System.ComponentModel;
using System.Runtime.CompilerServices;
using System.Windows.Input;

public class UserViewModel : INotifyPropertyChanged {
    private User user = new User();

    public string Name {
        get => user.Name;
        set {
            user.Name = value;
            OnPropertyChanged();
        }
    }

    public ICommand SaveCommand { get; }

    public UserViewModel() {
        SaveCommand = new RelayCommand(Save);
    }

    private void Save() {
        Console.WriteLine($"Benutzer {Name} wurde gespeichert.");
    }

    public event PropertyChangedEventHandler PropertyChanged;
    protected void OnPropertyChanged([CallerMemberName] string propertyName = null)
        => PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName));
}
    • View (XAML-Beispiel):**
<StackPanel>
    <TextBox Text="{Binding Name, UpdateSourceTrigger=PropertyChanged}" />
    <Button Content="Speichern" Command="{Binding SaveCommand}" />
</StackPanel>
    • Ergebnis:**

Wenn der Benutzer den Text ändert, wird automatisch die `Name`-Eigenschaft im ViewModel aktualisiert. Beim Klick auf den Button wird der `SaveCommand` ausgeführt – ohne dass die View Code-Behind-Logik benötigt.

Vorteile

  • **Starke Entkopplung** zwischen Logik und Darstellung
  • **Automatische Synchronisierung** durch Datenbindung
  • **Hohe Testbarkeit** (ViewModel kann unabhängig von der UI getestet werden)
  • **Wiederverwendbarkeit** von ViewModels mit verschiedenen Views
  • Ideal für moderne UI-Frameworks mit **Binding-System**

Nachteile

  • Erhöhter Initialaufwand durch Implementierung von Bindings und PropertyChanged
  • Kann bei großen Projekten komplex werden
  • Erfordert Framework-Unterstützung (Bindings, Commands)

Typische Verwendung

  • GUI-Frameworks mit Datenbindung:
 * **WPF** und **MAUI** (C# / .NET)
 * **Xamarin.Forms**
 * **Blazor**
 * **Angular**, **Vue.js**, **React** (konzeptionell ähnlich)
  • Mobile-Apps (Cross-Plattform)
  • Client-seitige Webanwendungen (SPAs)

Unterschiede zu MVC und MVP

Merkmal MVC MVP MVVM
Verbindung Model–View Möglich Über Presenter Über ViewModel mit Bindings
Kommunikation View ↔ Controller ↔ Model View ↔ Presenter ↔ Model View ⇄ ViewModel ⇄ Model
Datenbindung Manuell Teilweise Automatisch
Testbarkeit Gut Sehr gut Sehr gut
Framework-Support Universal GUI-basiert Frameworks mit Binding-System

Beispielhafte Implementierungen

  • **C# / .NET:** WPF, UWP, MAUI, Xamarin.Forms
  • **JavaScript:** Vue.js, Angular, React (Hooks/State ≈ ViewModel)
  • **C++ / Qt:** QML-View mit C++-Backend
  • **Swift / iOS:** SwiftUI (State und ViewModel-Konzept)

Vergleich zu ähnlichen Mustern

Muster Fokus Besonderheit
Model-View-Controller (MVC) Entwurfsmuster Strikte Trennung von Logik und Darstellung Controller steuert Model und View
Model-View-Presenter (MVP) Entwurfsmuster Presenter vermittelt aktiv zwischen View und Model Kein automatisches Binding
Model-View-ViewModel (MVVM) Datenbindung zwischen View und Logik Automatische Synchronisierung

Vorteile gegenüber MVP

  • Weniger Code durch Binding-Mechanismen
  • ViewModel kennt die View nicht direkt
  • Verbesserte Wiederverwendbarkeit und Testbarkeit

Nachteile gegenüber MVP

  • Bindings sind frameworkabhängig
  • Debugging von Bindings oft schwieriger
  • Höherer Speicher-Overhead bei komplexen Bindungsstrukturen

Siehe auch

Quellen