Outlook: Explorer automatisieren

Outlook ist wohl die Schaltzentrale an allen Arbeitsplätzen, die mit Microsoft Office arbeiten. Es bietet schon von Haus aus sehr viele Möglichkeiten, um E-Mails, Termine, Aufgaben oder Kontakte zu verwalten. Wenn man länger damit arbeitet, kommen einem früher oder später Ideen, wie man es noch weiter automatisieren könnte. Beispielsweise, um die Inhalte von E-Mails, die man in einen bestimmten Ordner verschiebt, gleich in Aufgaben umzuwandeln, vorgefertigte Antworten für E-Mails bereitzuhalten und so weiter. Der Weg zur Umsetzung führt über die Programmierung per VBA und genauer von VBA-Ereignissen. Denn für fast jede Aktion, die wir in Outlook durchführen, ob es nun das Erstellen oder Abschicken einer E-Mail, das Anlegen einer Aufgabe, das Öffnen eines Kontaktes ist, können wir ein Ereignis definieren, für das wir eine passende Prozedur hinterlegen. Dieser Artikel zeigt die wichtigsten Elemente des Hauptelements der Benutzeroberfläche von Outlook, nämlich dem Explorer, und wie wir diese direkt im VBA-Projekt von Outlook für unsere Zwecke anpassen können.

Die Benutzeroberfläche von Outlook bietet eine Menge Möglichkeiten, mit denen der Benutzer diese bedienen kann. Und um alle denkbaren Ideen für die Automatisierungen von Outlook umzusetzen, wollen wir in der Lage sein, all diese Benutzeraktionen abzufangen, indem wir dafür entsprechende Ereignisprozeduren hinterlegen. Die Basis dafür sind die folgenden Schritte:

  • Identifizieren, welcher VBA-Klasse der Outlook-Bibliothek ein Element der Benutzeroberfläche von Outlook entspricht.
  • Diese Klasse in Form einer Objektvariablen deklarieren und referenzieren.
  • Für die Objektvariable die gewünschten Ereignisprozeduren implementieren.

Die Basis: Die Application-Klasse

Die Grundlage für alle Zugriffe auf die Elemente der Benutzeroberfläche von Outlook ist die Application-Klasse. Diese beschreiben wir mit allen Eigenschaften, Methoden und Ereignissen ausführlich im Artikel Outlook: Die Application-Klasse (www.vbentwickler.de/305).

Fenstertypen unter Outlook

Bevor wir beginnen, ein Fenster unter Outlook zu referenzieren, stellen wir zunächst die verschiedenen Fenster vor. Es gibt die folgenden beiden Fenstertypen:

  • Explorer: Eigentliches Outlook-Fenster. Es kann auch mehrere davon geben, je nachdem, wie oft der Benutzer Outlook geöffnet hat. Auch mehrere Explorer-Fenster unterliegen jedoch immer einem einzigen Application-Objekt. Der Aufruf der Quit-Methode des übergeordneten Application-Objekts schließt daher immer alle Explorer-Fenster.
  • Inspector: Ein Inspector-Fenster ist eines der Fenster, mit dem Sie per Doppelklick auf eines der Elemente in den Ordnern eines Explorer-Fensters die Details des jeweiligen Elements anzeigen – beispielsweise für E-Mails, Termine, Kontakte et cetera.

Auf die Fenster von Outlook zugreifen

Bereits die verschiedenen Fenster von Outlook bieten einige Möglichkeiten zur Programmierung und halten dementsprechend auch einige Ereignisse bereit. Bevor wir diese vorstellen, müssen wir jedoch zunächst einmal Zugriff auf das gewünschte Fenster erhalten.

Dafür gibt es zunächst die folgenden drei Methoden:

  • ActiveExplorer: ActiveExplorer liefert einen Verweis auf das oberste Element der geöffneten Outlook-Explorer zurück, also das Element, das zuletzt aktiviert wurde. Das gilt auch, wenn zwischenzeitlich Fenster einer anderen Anwendung aktiviert wurden.
  • ActiveInspector: Liefert einen Verweis auf das Inspector-Element für das oberste Inspector-Objekt, also das Element, das zuletzt aktiviert wurde. Es kann auch sein, dass gar kein Inspector-Fenster geöffnet ist, dann liefert ActiveInspector den Wert Nothing.
  • ActiveWindow: ActiveWindow liefert immer einen Verweis auf das oberste Element der geöffneten Explorer– und Inspector-Elemente. Der Typ des zurückgelieferten Elements lautet dementsprechend entweder Explorer oder Inspector.

Die folgenden Anweisungen geben jeweils den Titel des ermittelten Explorer– beziehungsweise Inspector-Elements aus:

  Application.ActiveExplorer.Caption
  Application.ActiveInspector.Caption
  Application.ActiveWindow.Caption

Wir können auch alle Explorer– oder alle Inspector-Elemente durchlaufen. Hier zunächst die Ausgabe der Titel aller aktuell geöffneten Explorer-Elemente:

Private Sub AlleExplorer()
     Dim objExplorer As Explorer
     For Each objExplorer In Application.Explorers
         Debug.Print objExplorer.Caption
     Next objExplorer
End Sub

Das gelingt auch für alle geöffneten Inspector-Elemente:

Private Sub AlleInspectors()
     Dim objInspector As Inspector
     For Each objInspector In Application.Inspectors
         Debug.Print objInspector.Caption
     Next objInspector
End Sub

Ereignis beim Öffnen eines neuen Explorers

Mit dem Implementieren von Ereignissen können wir gleich beim Öffnen eines neuen Explorers beginnen. Wenn der Benutzer beispielsweise neben dem ersten Explorer-Fenster ein weiteres öffnet, weil er eines mit E-Mails und eines mit Terminen nebeneinander anzeigen möchte, fangen wir das wie folgt ab. Dazu deklarieren wir im allgemeinen Teil der Klasse ThisOutlookSession die folgende Variable:

Dim WithEvents objExplorers As Explorers

Diese Variable müssen wir füllen, am einfachsten in der beim Start von Outlook automatisch ausgeführten Ereignisprozedur Application_Startup:

Private Sub Application_Startup()
     Set objExplorers = Application.Explorers
End Sub

Und für das Ereignis NewExplorer der Auflistung objExplorers hinterlegen wir dann die folgende Ereignisprozedur:

Private Sub objExplorers_NewExplorer(ByVal Explorer _
         As Explorer)
     MsgBox "Neuer Explorer: " & Explorer.Caption
End Sub

Explorer-Fenster referenzieren

Auch das Explorer-Fenster bietet einige Ereignisse an, die wir implementieren können. Wollen wir diese implementieren, benötigen wir auch für dieses Fenster eine passende Objektvariable, die wir mit dem Schlüsselwort WithEvents deklarieren:

Dim WithEvents objExplorer As Explorer

Eigentlich können wir bereits das vorherige Beispiel nutzen, um diese Variable zu füllen:

Private Sub objExplorers_NewExplorer(ByVal Explorer _
         As Explorer)
     Set objExplorer = Explorer
End Sub

Wenn wir hingegen direkt beim Starten von Outlook das aktuelle Explorer-Fenster mit dieser Variablen referenzieren wollen, gelingt dies wie folgt:

Private Sub Application_Startup()
     Set objExplorer = Explorer
End Sub

Auf das Wechseln des Bereichs im Explorer reagieren

In Bild 1 sehen wir einen typischen Outlook-Explorer. Anhand dieses Beispiels wollen wir uns einige Ereignisse ansehen, die der Benutzer durch verschiedene Aktionen auslösen kann. Eines vorneweg: Das Betätigen der Elemente im modernisierten Ribbon werden wir in diesem Artikel nicht dokumentieren.

Die Benutzeroberfläche von Outlook mit den typischen Elementen

Bild 1: Die Benutzeroberfläche von Outlook mit den typischen Elementen

Ob und wie wir auf das Betätigen der Ribbonbefehle durch den Benutzer reagieren können, zeigen wir in einem eigenen Artikel auf. Hier ermitteln und referenzieren wir zunächst einmal den aktuellen Ordner und reagieren dann darauf, wenn der Benutzer diesen Ordner wechselt. Unter Ordnern verstehen wir die in der Abbildung mit der Zahl 2 und 3 markierten Elemente.

Wenn der Benutzer beispielsweise vom Ordner Posteingang zu Gesendete Elemente wechselt, löst er damit das Ereignis FolderSwitch aus. Dieses implementieren wir beispielsweise wie folgt:

Private Sub objExplorer_FolderSwitch()
     Debug.Print "Der Ordner wurde gewechselt in: ", _
         objExplorer.CurrentFolder
End Sub

Dies gibt nach dem Wechseln zum Ordner Gesendete Elemente den Text Gesendete Elemente aus. Das gleiche Ereignis wird ausgelöst, wenn wir zu einem der anderen Bereiche wechseln, die in der Abbildung mit der Zahl 1 markiert sind.

Durch das Wechseln beispielsweise vom Bereich E-Mails zu Kalender zeigt Outlook nämlich automatisch den zuletzt für diesen Bereich markierten Ordner an.

Ereignisse beim Wechseln der Ansicht

Outlook bietet verschiedene Ansichten an, wenn wir im Ribbon zur Registerseite Ansicht wechseln und dann auf Ansicht ändern klicken. Wir erhalten dann die Auswahl der Ansichten aus Bild 2. Wählen wir hier einen anderen als den aktuellen Eintrag aus, lösen wir damit zwei Ereignisse aus: BeforeViewSwitch und ViewSwitch.

Ändern der Ansicht für die Elemente eines Ordners

Bild 2: Ändern der Ansicht für die Elemente eines Ordners

Die Prozedur für das Ereignis BeforeViewSwitch liefert zwei Parameter – die Bezeichnung der gewählten neuen Ansicht mit NewView und den Rückgabeparameter Cancel. In dieser Prozedur können wir prüfen, ob die Bedingungen für den Wechsel der Ansicht erfüllt sind und falls nicht, können wir den Wechsel durch Einstellen von Cancel auf den Wert True stoppen.

Im folgenden Beispiel geben wir jedoch nur den Namen der gewählten Ansicht aus:

Private Sub objExplorer_BeforeViewSwitch( _
         ByVal NewView As Variant, Cancel As Boolean)
     Debug.Print "Explorer_BeforeViewSwitch", NewView
End Sub

Das zweite Ereignis ViewSwitch wird nur ausgelöst, wenn der Wechsel der Ansicht tatsächlich erfolgt ist, also wenn der Parameter Cancel in der Ereignisprozedur für das Ereignis BeforeViewSwitch nicht auf True eingestellt wurde. Hier geben wir nochmals die aktuelle Ansicht aus, die wir diesmal nicht per Parameter erhalten, sondern über die Eigenschaft CurrentView ermitteln:

Private Sub objExplorer_ViewSwitch()
     Debug.Print "Die Ansicht wurde geändert in: ", _
         objExplorer.CurrentView
End Sub

Alle Explorer-Fenster referenzieren

Etwas komplizierter wird es, wenn wir Ereignisse für mehr als ein Explorer-Fenster nutzen wollen. In diesem Fall müssen wir für jedes Explorer-Fenster, das geöffnet ist, eine eigene Objektvariable reservieren und diese mit einem Verweis auf das jeweilige Explorer-Fenster versehen. Nun ist die Menge der zu erwartenden Explorer-Fenster in den meisten Fällen überschaubar. Ich selbst hatte genau genommen noch nie den Bedarf, mehr als einen Outlook-Explorer zu öffnen – ich bin einfach zwischen den verschiedenen Ordnern hin- und hergesprungen. Auf die Idee, beispielsweise zwei Explorer-Fenster für E-Mails und Termine nebeneinander zu platzieren, um diese gleichzeitig im Überblick zu haben, bin ich zuvor nie gekommen.

Allerdings können wir nicht ausschließen, dass es da draußen Benutzer gibt, die diese sicher durchaus praktische Darstellung nutzen und daher kümmern wir uns auch um diesen Fall. Auch wenn die meisten Benutzer vermutlich eine begrenzte Anzahl von Explorern verwenden, was dazu verleiten könnte, einige Variablen wie objExplorer1, objExplorer2 und so weiter zu verwenden, so müsste man in diesem Fall doch für jedes dieser Objekte einzeln die jeweiligen Ereignisprozeduren anlegen. Und das würde zu viel Arbeit bedeuten, wenn man einmal eine der Prozeduren anpassen wollte – dann müssten diese Änderungen immer gleich mehrfach durchgeführt werden.

Also wählen wir einen alternativen Ansatz, bei dem wir eine Wrapper-Klasse für die Explorer-Elemente anlegen. Diese sieht wie in Listing 1 aus, wobei wir hier nur die vier bisher vorgestellten Ereignisse implementiert haben.

Dim WithEvents m_Explorer As Outlook.Explorer
Public Property Set Explorer(obj As Outlook.Explorer)
     Set m_Explorer = obj
End Property
Private Sub m_Explorer_BeforeFolderSwitch(ByVal NewFolder As Object, Cancel As Boolean)
     Debug.Print "Folder wird zu ''" & m_Explorer.CurrentFolder & "'' geändert."
End Sub
Private Sub m_Explorer_BeforeViewSwitch(ByVal NewView As Variant, Cancel As Boolean)
     Debug.Print "View wird zu ''" & m_Explorer.CurrentView & "'' geändert."
End Sub
Private Sub m_Explorer_FolderSwitch()
     Debug.Print "Folder wurde zu ''" & m_Explorer.CurrentFolder & "'' geändert."
End Sub
Private Sub m_Explorer_ViewSwitch()
     Debug.Print "View wurde zu ''" & m_Explorer.CurrentView & "'' geändert."
End Sub

Listing 1: Code der Wrapperklasse clsExplorerWrapper

Schau Dir diese Konstellation genau an, denn sie wird immer und immer wieder auftreten – ob für einzelne Objekte, deren Ereignisse wir implementieren wollen oder für mehrere, die wir wie im vorliegenden Beispiel in einer Collection speichern.

Wir legen also eine neue Klasse an, die wir in diesem Fall clsExplorerWrapper nennen. Dazu betätigen wir als Erstes den Menübefehl Einfügen|Klassenmodul. Danach ändern wir den Namen des Klassenmoduls beispielsweise von Klasse1 in clsExplorerWrapper, indem wir dieses im Projekt-Explorer markieren und dann die Eigenschaft (Name) im Eigenschaften-Bereich einstellen. Übrigens: Im Gegensatz zu den VBA-Projekten beispielsweise von Access-Datenbanken bietet Outlook für neu angelegte Module, deren Standardname wie Modul1 oder Klasse1 nicht durch den Entwickler geändert wurde, beim Speichern nicht die Möglichkeit, den Modulnamen zu ändern.

Möchten Sie weiterlesen? Dann lösen Sie Ihr Ticket!
Hier geht es zur Bestellung des Jahresabonnements des Magazins DATENBANKENTWICKLER:
Zur Bestellung ...
Danach greifen Sie sofort auf alle rund 200 Artikel unseres Angebots zu - auch auf diesen hier!
Oder haben Sie bereits Zugangsdaten? Dann loggen Sie sich gleich hier ein:

Schreibe einen Kommentar