Announcement

Collapse
No announcement yet.

Model View Controller (MVC) - Verständnisfrage

Collapse
X
  • Filter
  • Time
  • Show
Clear All
new posts

  • Model View Controller (MVC) - Verständnisfrage

    Hallo,
    ich versuche für meine Anwendung GUI-seitig das MVC-Pattern anzuwenden.

    In meiner Model-Klasse definiere ich diverse Delegates und Events. Z. B.:
    Code:
    internal event EventHandler RaiseStartRechungenListEvent;
    
    internal delegate void RechungenTableLoadedEventHandler(object sender, LoadRechungenTableEventArgs a);
    internal event RechungenTableLoadedEventHandler RaiseRechungenTableLoadedEvent;
    
    internal delegate void RechungLoadedEventHandler(object sender, LoadRechungEventArgs a);
    internal event RechungLoadedEventHandler RaiseRechungLoadedEvent;
    Weiterhin halte ich dort die Methoden, die aus bestimmten Benutzeraktionen angetriggert werden:
    Code:
    internal virtual void OnRaiseStartRechungenListEvent(){
    	EventHandler handler = RaiseStartRechungenListEvent;
    
    	if (handler != null) {
    		handler(this, new EventArgs());
    	}
    }
    
    internal virtual void OnRaiseLoadRechungenTableEvent(...){
    	//Laden einer DataTable mit n Rechungen aus der DB und Füllen eines DataGrids
    	DataTable RechungenTable = GetRechungen(...);
    
    	RechungenTableLoadedEventHandler handler = RaiseRechungenTableLoadedEvent;
    
    	if (handler != null) {
    		handler(this, new LoadRechungenTableEventArgs(RechungenTable, eiListControl));
    	}
    }
    
    internal virtual void OnRaiseLoadRechungEvent(int nummer){
    	//Laden des Datensatzes aus der DB und Objekterstellung
    	BCRechung Rechung = GetRechung(...);
    
    	RechungLoadedEventHandler handler = RaiseRechungLoadedEvent;
    
    	if (handler != null) {
    		handler(this, new LoadRechungEventArgs(Rechung));
    	}
    }
    In meiner Controller-Klasse habe ich einen Verweis auf das Model und registriere dort die Events:
    Code:
    _eoModel.RaiseStartRechungenListEvent -= new EventHandler(StartRechungenList);
    _eoModel.RaiseRechungLoadedEvent -= new EOModel.RechungLoadedEventHandler(LoadRechung);
    _eoModel.RaiseRechungenTableLoadedEvent -= new EOModel.RechungenTableLoadedEventHandler(LoadRechungenTable);
    Schließlich sind im Controller die Methoden definiert, die sich für die ausgelösten Events interessieren:
    void StartRechungenList(object sender, EventArgs e) {...}
    void LoadRechungenTable(object sender, LoadRechungenTableEventArgs e) {...}
    void LoadRechung(object sender, LoadRechungEventArgs e) {...}

    Zu guter Letzt habe ich Windows-Forms, die einen Verweis auf das Model beinhalten und demnach als Views fungieren. Alle Views und der Controller haben dabei eine einzige Model-Instanz, die in der Initialisierung des Controllers erstellt wird.

    Das klappt auch wunderbar. Das Problem ist nun folgendes: Wenn sich jetzt weitere Abbonenten für die Events anmelden, dann werden diese natürlich auch dort empfangen, was technisch gesehen korrekt ist. Semantisch ist es aber für meine Vorstellungen Blödsinn:

    Nach Programmstart (via OnRaiseStartRechungenListEvent) gibt der Anwender Kriterien für eine SQL-Abfrage an (OnRaiseLoadRechungenTableEvent). Die Abfrage liefert eine DataTable, deren Einträge aufbereitet in einem Grid dargestellt werden. Wird nun ein bestimmter Grideintrag zur Bearbeitung ausgewählt, dann öffnet sich eine View zum detaillierten Bearbeiten des Datensatzes (OnRaiseLoadRechungEvent).

    Wenn ich aber zwei unabhängige Grids habe, die das selbe Model haben und "RechungLoadedEventHandler" abbonieren, dann kommt dort das selbe Event in beiden Fällen an. Und das ist, was ich nicht gebrauchen kann. Jedes Grid sollte unabhängig vom Anderen die Bearbeitung einer bestimmten Rechung erlauben.

    Mache ich einen Denkfehler, was MVC betrifft oder ist für diesen speziellen (aber meiner Meinung nach ganz alltäglichen) Anwendungsfall MVC ungeeignet?

    Gruß,
    Gunter

  • #2
    Hallo,

    ich versuche für meine Anwendung GUI-seitig das MVC-Pattern anzuwenden.
    schön - aber warum wird das Rad dann neu erfunden? Bereits der von Visual Studio 2005 vordefinierte Weg für die visuell konfigurierte Datenbindung verbaut eine der möglichen MVC-Implementierungsalternativen (auch wenn das Ergebnis nicht als MVC beschriftet wird).

    Jedes Grid sollte unabhängig vom Anderen die Bearbeitung einer bestimmten Rechung erlauben.
    Das typisierte DataSet ist sowohl das Model als auch über die partitiellen Klassen der frei erweiterbare Controller. Die Datenbindung regelt über die BindingContext-Instanz (alias BindingSource-Komponente) die Gültigkeit des virtuellen Datensatzzeigers im Model.

    Comment


    • #3
      Originally posted by Andreas Kosch View Post
      Bereits der von Visual Studio 2005 vordefinierte Weg für die visuell konfigurierte Datenbindung verbaut eine der möglichen MVC-Implementierungsalternativen (auch wenn das Ergebnis nicht als MVC beschriftet wird).
      Leider verstehe ich nichts von dem, was du geschrieben hast.

      Originally posted by Andreas Kosch View Post
      Das typisierte DataSet ist sowohl das Model als auch über die partitiellen Klassen der frei erweiterbare Controller. Die Datenbindung regelt über die BindingContext-Instanz (alias BindingSource-Komponente) die Gültigkeit des virtuellen Datensatzzeigers im Model.
      Die DataTables benutze ich nur zum Austausch der DB-Daten zwischen Datenbank und Grids (für Auflistungen) bzw. "echten" Geschäftsobjekten auf hoher Abstraktionsebene. Die Geschäftsobjekte beinhalten keinerlei DataSets und DataTables sondern tauschen sich nur über Load- und Save-Methoden mit der DB aus, wobei dann DataTables auf niedriger Ebene benutzt werden.

      Ganz unabhängig von MVC oder sonstigen Pattern: Ich verwende keine DataSets für die Geschäftskomponenten weil vieles aus den Präsentationschichten nicht so ohne weiteres 1 zu 1 mit der DB in Einklang zu bringen ist. Das fängt schon damit an, wie ein Datum gespeichert ist oder wie Flags behandelt werden. Es ist halt "historisch gewachsen". Der neue objektoriente Ansatz als Ersatz für die ganzen alten Programme eröffnet nun die Möglichkeit, mit Geschäftskomponenten auf hoher Abstraktionsebene zu hantieren ohne die immer noch bestehende Alt-Datenbank zu ändern.

      Comment

      Working...
      X