© elenabsl/Shutterstock.com
Realtime-Cross-Platform-Apllikationen - Teil 2

Zeichen setzen in Electron und Cordova


Bisher hat unsere Angular-Applikation eine Echtzeitkomponente durch SignalR erhalten und ist so jederzeit auf allen Endgeräten aktualisierbar. Die Portierbarkeit auf diese Endgeräte fehlt noch und soll nun möglichst kompakt und dennoch übersichtlich implementiert werden.

Im ersten Teil hatten wir als Ausgangspunkt eine Angular-Applikation vorliegen. Dieser haben wir durch SignalR und Cross-Origin Ressource Sharing eine Echtzeitkomponente verpasst. In den nächsten Schritten soll die Applikation für mobile Geräte zugänglich gemacht und anschließend auch als Desktopapplikation verfügbar werden. Für Letzteres setzen wir Electron ein und Cordova für die mobile Version.

Desktopapplikationen mit Electron

Schauen wir uns zunächst an, was Electron ist: In Kurzform ist Electron [1] ein Framework, mit dem man Desktopapplikationen mittels JavaScript, HTML und CSS bauen kann. Es kann dabei Applikationen für Mac, Windows und Linux erstellen, ist Open Source und benutzt Node.js und Chromium, also das Herzstück von Googles Chrome-Browser, um Applikationen ausführen zu können. Viele bekannte Applikationen nutzen den Webstack, um Applikationen zu entwickeln, die dann mittels Electron auf dem PC zu finden sind. Zu den bekanntesten gehören Slack, Twitch, der WhatsApp-Client und Visual Studio Code.

Eine Electron-Applikation benutzt also Node.js. Somit wird eine package.json-Datei benötigt, die grundlegende Informationen bereitstellt. Zusätzlich wird eine JavaScript-Datei benötigt, die ein initiales Desktopfenster öffnet und eine Applikation anzeigen kann. Sie ist der Startpunkt jeder Electron-Applikation und erstellt den Main-Prozess. Dieser ist in der Lage, einen oder mehrere Renderer-Vorgänge zu starten, aber auch mit dem Betriebssystem zu kommunizieren. Im Renderer-Prozess wird später die Webapplikation angezeigt, die wir soeben mit ng build--prod im dist-Ordner erstellt haben. Um eine Webapplikation in einem Renderer-Prozess anzeigen zu können, brauchen wir noch eine index.html-Datei, die die visuellen Elemente darstellt, die wiederum unsere Applikation definieren. Diese index.html wurde schon durch Angular bzw. die CLI erstellt.

Bevor wir loslegen, müssen wir Electron installieren. Das geht mit npm install electron -g. Danach ist Elec-tron in der Konsole als Befehl verfügbar. Um die Anwendung nun nach Electron zu portieren, benötigt es einige Schritte, die als Nächstes auf uns zukommen:

  1. Angular-Anwendung für Electron erstellen

  2. Electron-JavaScript-Datei anlegen, um Main-Prozess auszuführen

  3. Dateien in einen Ordner kopieren

  4. in eine *.exe umwandeln

Angular-Anwendung für Electron erstellen

Der Vorgang, eine Angular-Anwendung für Electron zu erstellen, ist wie ein normaler Produktions-Build, jedoch müssen wir beim BASE_HREF-Parameter aufpassen. In einem normalen Produktions-Build ist der Basispfad für die Applikation auf / festgelegt und beschreibt das Root-Verzeichnis der Applikation. Im Kontext von Electron entspricht das Root-Verzeichnis dem Root der Festplatte (meistens C:\). Dort sind allerdings unsere JavaScript- und CSS-Dateien nicht zu finden. Deshalb ändern wir den BASE_HREF auf ./. So werden unsere Dateien wieder relativ zum ausführbaren Pfad gefunden. Mit dem Befehl ng build --prod --base-href ./ kann der Pfad beim Erstellen der Applikation überschrieben werden.

Electron-Dateien anlegen

In einem Ordner assets/desktop können wir die Dateien erstellen, die wir für Electron benötigen. Die Datei main.js ist der Einstiegspunkt von Electron, damit unsere Applikation wie in Listing 1 gehostet werden kann.

Listing 1

const { app, BrowserWindow } = require('electron') function createWindow () { const win = new BrowserWindow({ width: 800, height: 600, webPreferences: { nodeIntegration: true } }) win.loadFile('index.html') } app.whenReady().then(createWindow) app.on('window-all-closed', () => { if (process.platform !== 'darwin') { app.quit() } }) app.on('activate', () => { if (BrowserWindow.getAllWindows().length === 0) { createWindow() } })

In der Funktion createWindow() wird ein neues Browserfenster erstellt, das mit loadFile() unsere Webapplikation mit der index.html als Startpunkt anzeigt. Falls alle aktiven Fenster geschlossen sind (all-window-closed), wird die Applikation beendet. Nur für den Fall, dass nach der Aktivierung kein Fenster mehr geöffnet ist, wird ein neues Fenster erstellt (activate-Ereignis). Die package.json-Datei enthält Metadaten für unsere Applikation, wie beispielsweise in Listing 2 zu sehen ist.

Listing 2

{ "name": "my-electron-app", "version": "0.0.1", "author": "Fabian Gosebrink", "description": "My Electron app", "main": "main.js" }

Die Property main zeigt auf unsere main.js-Datei, mit der wir das Browserfenster etc. erstellen. Diese beiden Dateien zusammen mit allen Angular-Dateien sind die Grundlage für die Electron-Anwendung. Die Angular-Dateien können nun mit den Electron-Dateien in einen Ordner kopiert werden. Wie der Ordner heißt, spielt dabei keine Rolle. Damit man den Zwischenschritt sehen kann, verwende ich gerne einen .temp-Ordner, hier zu sehen in Abbildung 1.

gosebrink_crossplatform_teil2_1.tif_fmt1.jpgAbb. 1: Ordnerinhalt des Ordners mit allen benötigten Dateien einer Electron-Applikation

Erstellen einer ausführbaren Datei

Um aus den Dateien ein Executable zu erstellen, kann der Electron Packager verwendet werden. Er lässt sich über npm install electron-packager -g global installieren. Nun kann mit dem Befehl electron-packager --out=path/to/folder/with/electron/and/angular/files eine Anwendung verpackt und eine *.exe erstellt werden. Mit dem Parameter --platform=win32,linux können wir entsprechende Anwendungen für Linux und Windows erstellen. Im Ordner mit den Electron- und Angular-Dateien erstellen wir durch den Befehl electron-packager ./ --electronVersion=11.1.1 --platform="win32,linux" die ausführbaren Dateien für Windows und Linux. (Abb. 2)

gosebrink_crossplatform_teil2_2.tif_fmt1.jpgAbb. 2: Windows Terminal beim Erstellen einer Electron-Applikation
gosebrink_crossplatform_teil2_3.tif_fmt1.jpgAbb. 3: Screenshot der fertigen Angular-Applikation als Electron-Anwendung

Die Desktopapplikation baut nun, wie die Webapplikation auch, eine Verbindung zum Azure-Server auf (Abb. 3), ruft die vorhandenen Items ab und synchronisiert die Daten via SignalR mit WebSockets. Falls wir nun die Webanwendung parallel starten, können wir schon Einträge hin- und herschicken.

Hinzufügen eines Icons und Symbols im System Tray

Um die Applikation noch besser in das Betriebssystem zu integrieren, können unter anderem noch ein Icon für die *.exe und ein Icon ins System Tray inklusive eines Tray-Menüs hinzugefügt werden. Das Icon kann wieder im assets/desktop-Ordner hinterlegt werden und ist im Format *.ico verfügbar. Dafür verwendet man folgenden Befehl:

electron-packager ./ --electronVersion=11.1.1 --platform="win32,linux" –icon=path/to/my/icon

Um mit Electron ein Menü für das System Tray zu erzeugen (Listing 3), legen wir eine...

Neugierig geworden? Wir haben diese Angebote für dich:

Angebote für Gewinner-Teams

Wir bieten Lizenz-Lösungen für Teams jeder Größe: Finden Sie heraus, welche Lösung am besten zu Ihnen passt.

Das Library-Modell:
IP-Zugang

Das Company-Modell:
Domain-Zugang