Speichere diese Seite als Bookmark und verfolge unseren Projektstand!
Willkommen auf der Projekt Website der Alpine Ace - Ski App.
Im Vertiefungsmodul 4230: GeoInformatik & Raumanalyse I des Bachelorstudiengangs Geomatik an der Fachhochschule Nordwestschweiz (FHNW) wurde im Rahmen einer Projektarbeit die Geodateninfrastruktur (GDI) Alpine Ace-Ski App entwickelt. Abgesehen von der Vorgabe räumlich-zeitlicher Inhalte hatten wir freie Themenwahl.
Diese Seite widmet sich der GDI Alpine Ace-Ski App. Wintersport ist in der Schweiz nicht nur ein Nationalsport, sondern auch ein bedeutender Wirtschaftszweig, der durch die Digitalisierung stark verändert wurde. Mittlerweile ist es möglich, Tickets im Voraus online zu buchen, Webcams an verschiedenen Standorten abzurufen und persönliche Statistiken über den Skitag zu erfassen. Allerdings erstellt jedes Skigebiet eigene Plattformen mit ähnlichen Funktionen, was dazu führt, dass man für jedes Skigebiet eine separate App herunterladen oder mehrere Webseiten als Lesezeichen speichern muss, um die wichtigsten Informationen zu erhalten. Dies kann die Anzahl der Apps und Lesezeichen auf dem Smartphone erheblich erhöhen.
Aus diesem Grund wurde die GDI Alpine Ace-Ski App entwickelt. Unser Ziel ist es, eine zentrale Plattform für verschiedene Skigebiete zu schaffen, die alle wichtigen Funktionen für den Wintersport bietet. Dazu gehören:
Erkunden Sie unsere Seite, um mehr über dieses spannende Projekt zu erfahren und zu entdecken, wie die Alpine Ace-Ski App Ihr Wintersporterlebnis revolutionieren kann.
Die Installationsanleitung befindet sich hier.
Eine vollständige Geodateninfrastruktur (GDI) umfasst das Backend, das Frontend sowie die verwendeten Bibliotheken und API-Schnittstellen. Das folgende Schema zeigt die entwickelte und genutzte GDI der Alpine Ace-Ski App.

Architektur Client-Server Struktur
Die App enthält dabei eine Server Client Umgebung:
Das Backend beinhaltet alle unsichtbaren Inhalte und Daten, die sich auf dem Server, in unserem Fall der Raspberry PI, befinden. Dazu gehören folgenden Punkte:
In der Datei network_config.js muss vor dem Start der App die aktuelle IP Adresse eingetragen werden. Die IP Adresse wird in die lokalen API’s, sowie WFS Abfragen eingetragen. So kann die React App von verschieden Geräten genutzt werden, solange dies im selben Netzwerk sind.
Um dem User die aktuellsten Informationen über das Skigebiet zur Verfügung stellen zu können, werden folgende APIs verwendet:

Architektur der APIs
Meteo: Die Wetter Daten werden über https://open-meteo.com/ bezogen. Abfragen für nicht kommerzielle Nutzungen sind kostenlos. Insgesamt sind pro Tag 10’000 Abfragen möglich. Die Abfrage der aktuellen Wettersituation erfolgt im Viertelstunden Takt, die der Wettervorhersage erfolgt alle 24 Stunden.
Lawinensituation: Die aktuellen Lawineninformationen werden über https://aws.slf.ch/api/bulletin/caaml bezogen. Es handelt sich um eine API des Institut für Schnee und Lawinenforschung (SLF). Die Nutzung ist kostenlos. Die Abfrage der Daten erfolgt im 12 Stunden Takt.
Schneehöhen: Die Schneehöhen werden über https://measurement-api.slf.ch/ bezogen. Es handelt sich um eine API des SLF. Die Daten werden vom Interkantonalen Mess- und Informationssystem (IMIS) bezogen. Die Nutzung ist Kostenlos. Die Abfrage der Daten erfolgt alle 30 min.
Informationen über Skigebiet: Momentan stehen keine aktuellen Informationen zu den Skigebieten zur Verfügung. Bei den angezeigten Daten handelt es sich um Beispieldaten. Geplant ist ein Bezug im Viertelstunden Takt über die Webseiten der einzelnen Bergbahnen. Dies ist im Upcoming Feature Aktuelle Dashboard Daten mithilfe von Web-Scraping geplant. Dies ist in den Sommermonaten aber schwierig zun entwickeln, da nur wenige Daten von Skigebieten zur Verfügung stehen. Das Skigebiete Arosa Lenzerheide auf welchem das Projekt sich momentan fokussiert ist momentan geschlossen.
Um einen reibungslosen Datenbezug zu gewährleisten, werden die entsprechenden Skripte über die Datei main.py gesteuert. Diese Datei läuft im Hintergrund und ruft die einzelnen Skripte in den festgelegten Zeitintervallen auf und führt sie aus.
Der GeoServer wird genutzt, um alle räumlichen Daten zu Verfügung zu stellen, die in der Datenbank gespeichert sind. Die Daten werden via WFS vom GeoServer angefordert. Um CORS auf dem GeoServer zu aktivieren, ist unter die Konfigurationsdatei unter docs\web.xml abgelegt. In dieser wird CORS aktiviert, um auch von anderen Geräten Daten WFS Anfragen zu tätigen.
In diesem Projekt werden neben Sachdaten auch räumliche Daten wie Pisten und Anlagen, die Geometrien besitzen, verwendet. Um sicherzustellen, dass die Datenbank diese geometrischen Daten effizient verarbeiten kann, haben wir uns für die Nutzung einer relationalen Datenbank mit der räumlichen Erweiterung PostGIS entschieden. Dadurch kann PostgreSQL räumliche Abfragen und Operationen durchführen, was für unser Projekt von entscheidender Bedeutung ist.
Während des Betriebes der Plattform müssen verschiedene Systeme Lese- oder Schreibzugriff haben. Für die Datenbankverbindung werden folgende Informationen verwendet:
Die Informationen werden an verschiedenen Orten im Programm Code verwendet. Dafür wurde für Python und Javascript jeweils eine Config-Datei erstellt, in welchem die Verbindungsinformationen angegeben sind:
Python: API\config.py
Javascript: alpine_ace\src\DB\config.js
FME: Bei FME muss unter ` Tools -> FME Options -> Database Connections` die Datenbankverbindung zum GeoServer angepasst werden.
Das Datenbankschema ist in folgende Gruppen eingeteilt:
Folgende Daten werden mit Hilfe von FME in den GeoServer importiert:
Mit der Express-API greift die React App auf die Daten der Datenbank zu. Die Daten sind als API über den Port 5000 abrufbar.
Folgende Express-API’s sind vorhanden:
Das Frontend ist für das Auftreten unserer APP zuständig. Dabei baut unsere APP auf folgenden Technologien auf:
Der Vergleich zwischen Mock-Up und Endprodukt, die Erklärung zur Farbwahl und die einzelnen Funktionen werden in den nächsten Kapiteln beschrieben.
Das Mock-Up der App ist in Form einer interaktiven PowerPoint hier verfügbar: Mock-Up
Dieses Mock-Up zeigt die ersten Ideen, wie die App aussehen sollte (Farbschema), aber auch die ersten Funktionen, die realisiert sein wollten. In den folgenden Grafiken werden die umgesetzten Features mit dem Mock-Up verglichen.

|
|
Start |
|
![]() |
![]() |
Karte |
|
![]() |
![]() |
Wetter |
|
![]() |
![]() |
Statistiken |
|
![]() |
![]() |
Weg |
|
![]() |
![]() |
Navi |
|
![]() |
![]() |
Restaurant |
|
![]() |
![]() |
Für diese App wurde das Farbschema sorgfältig entwickelt, sodass es nicht nur funktional ist, sondern auch visuelle ansprechend und leicht verständlich für die Benutzer ist.
Die Hauptfarbe, #00112E, bildet das Fundament dieser App und verleiht ihr eine solide Basis.
Die Sekundärfarbe, #FF6155, wurde mit Bedacht gewählt, um wichtige Elemente wie Buttons und interaktive Funktionen hervorzuheben. Ihre lebendige Präsenz zieht die Aufmerksamkeit auf sich und führt die Benutzer intuitiv durch die App.
Für das Routing und die Elemente wurde #9EFF55 und #B655FF gewählt. Diese Farben wurden ausgewählt, da sie komplementär zu unserer Sekundärfarbe sind, was nicht nur visuell ansprechend ist, sondern auch einen starken Kontrast bietet, der die Benutzerführung erleichtert.
Die Darstellung von gefahrenen Strecken oder Routing-Strecken erfolgt in #FFA500. Diese kräftige Farbe hebt sich von den traditionellen Skipisten Farben ab und sorgt dafür, dass die Routen deutlich erkennbar sind, ohne mit den üblichen Farbkonventionen zu kollidieren.
Schliesslich wurde entschieden, die Skipisten auf der Karte mit den klassischen Farben Blau: #0077BA, Rot: #E40513 und Schwarz: #000000 darzustellen. Diese konventionelle Farben ermöglicht es den Benutzern, auf einen Blick zu erkennen, um welche Art von Piste es sich handelt, und trägt so zur Benutzerfreundlichkeit unserer App bei.
Die Kopfzeile ist in Menü und Untermenü gleich aufgebaut. Neben dem Logo in der Mitte, befindet sich links die Zurück-Pfeil und rechts das Zahnrad für die Einstellungen. Pfeil und Zahnrad sind aus der Symbol Bibliothek von MUI.
Beim anklicken des Symbols wird mittels eines Links auf das entsprechende Menü navigiert. In der Datei App.jsx ist die Kopfzeilen über jeder Menü Komponente. Einzig die Menüs Restaurant und Statistiken, welche über Untermenüs verfügen, haben eine eigene abgeänderte Kopfziele. Dort zeigt der Link auf das vorherig Menü.
Das Hauptmenü ist der wichtigste Ort der Webseite. Aus diesem wird in die Untermenüs navigiert. Die Untermenüs sind in sechs Kacheln angeordnet. Die wichtigsten Informationen zum Skigebiet wie die Lawinensituation, offene Anlagen und Pisten sind wie in einem Dashboard direkt über den Kacheln angeordnet.
In dieser Karten wird die aktuelle Lawinengefahr pro Region dargestellt. Die Lawinengefahr ist dabei in fünf Stufen unterteilt. Genauer beschrieben sind diese im Abschnitt Symbol Lawinengefahr. Im Hintergrund ist die Winterlandeskarte der Swisstopo.
swissboundaries3d_2024-01_2056_5728.gpkg.zip von der Swisstopo.Die Kantons- und Landesgrenzen werden direkt als GeoPackage dem Datenspeicher hinzugefügt. Sie sind nicht in der Datenbank, weil sich die Daten nicht häufig ändern. Die Daten sind ausserdem nur für den Hintergrund gedacht um die Lesbarkeit der Karte zu erhöhen.

Diagramme der aktuellen Pisten und Anlagen Informationen
b_danger aus den Bulletin Daten aufgeschlüsselt. Es wird unterschieden zwischen: low, moderate, considerable , high ,very_high, no_snow und no_rating. Die Dargestellten Piktogramme sehen wie folgt aus:
Piktogramme der Bulletins
b_danger aufgeschlüsselt. Es wird unterschieden zwischen: low, moderate, considerable , high ,very_high, no_snow und no_rating. Die Farben der Flächen sind dieselben wie vom SLF.hauptmenuSchaltfächenErstellen erstellt. In dieser wird der Name der Schaltfläche und die Route benötigt. Die Routen führen beim anklicken in das jeweilige Menü.In der Karte finden sich verschiedene Funktionen wieder. Beim Start der Karte befindet sich der Kartenausschnitt zentrisch über der Position des Nutzers. Der Ausschnitt kann danach beliebig verschoben, vergrössert oder verkleinert werden. In der Karte sind folgende Informationen dargestellt:
Pisten: Die Pisten werden in der jeweiligen Farbe des Schwierigkeitsgrades visualisiert. Beim Anwählen der Piste wird die jeweilige Pistennummer unterhalb der Karte eingeblendet. Geschlossene Pisten sind zu 50% transparent dargestellt.
Anlagen: Die Sesselbahnen, Seilbahnen und Skilifte werden als schwarze Linie dargestellt. Beim Anwählen wird der Name eingeblendet.
Restaurants und Bars: Die Verpflegungsmöglichkeiten im Skigebiet sind mit jeweiligem Piktogramm visualisiert. Nach dem Anwählen erscheinen Informationen zur Örtlichkeit sowie die Öffnungszeiten.
POI’s (points of interests): Zum Beispiel Parkplätze oder Bushaltestellen die Informationen wie den Namen enthalten.
Hintergrundkarte: Den Hintergrund bildet die Winterlandeskarte von Swisstopo.
Die Daten der Skigebiete wurden von der Plattform OpenSnowMap bezogen. Die Platform OpenSnowMap bezieht täglich alle Pisten und Skigebiete weltweit von Open Street Map.
planet_pistes.osm.gz von der Platform data.opensnowmap.org.
Die Daten wurden vor dem Import durch FME bereinigt. In einem QGIS Projekt wurden alle Flächen gelöscht, welche nicht innerhalb der Schweiz (Puffer + 10km) liegen. Die Flächen wurden anschliessend als Geopackage im Koordinatensystem EGSG:2056 gespeichert.
Die Flächen werden in der Workbench gefiltert auf Skigebiete (es gibt Pisten die als Flächen vorhanden sind in OSM). Das Attribut skigebiet_name und die ID skigebiet_id wird vergeben. Diese ID wird als Verknüpfung verwendet um die Zuordnung zum Skigebiet zu ermöglichen. Die Skigebiete werden anschliessend in der Tabelle skigebiet gespeichert. Die Skigebiete werden bis jetzt im Projekt nicht grafisch dargestellt. Sie dienen lediglich der Verknüpfung von andern Daten.
Das DHM25 ist das digitale Höhenmodell der Swisstopo mit einer Auflösung von 25 Meter.
DHM25_MM_ASCII_GRID.zip von der Swisstopo.Die Datei dhm25_grid_raster.asc ist mit mehr als 844 MB zu gross für das GitHub repository. Deshalb gibt es unter DB_PG ein Download Python Datei ASCII_Hoehenmodell_download.py. Dies lädt das DHM25 automatisch herunter, entzippt dieses und speichert es im Ordner ASCII_Hoehenmodell. Das Höhenmodell wird nur im FME Prozess geoserver_Datenimport.fmw verwendet, für die Richtungsbestimmung der Analgen und Pisten. Deshalb werden diese nicht in die Datenbank importiert.
Die Daten der Pisten wurden von der Platform OpenSnowMap bezogen. Die Platform OpenSnowMap bezieht täglich alle Pisten und Skigebiete weltweit von Open Street Map.
planet_pistes.osm.gz von der Platform data.opensnowmap.org.
Die Daten wurden vor dem Import durch FME bereinigt. In einem QGIS Projekt wurden alle Linien gelöscht, welche nicht innerhalb der Schweiz (Puffer + 10km) liegen. Die Linien wurden anschliessend als Geopackage im Koordinatensystem EGSG:2056 gespeichert.
Die Attribute sind für dieses Projekt so noch nicht nutzbar, da viele wichtige Informationen im Attribute other_tags sind. In der FME Workbench wird zuerst der Schwierigkeitsgrad extrahiert und im Attribut p_farbe festgehalten. Dasselbe passiert mit der Pistennummer p_nummer und Pistenname p_name. Multilines werden aufgesplittet in Linien. Für jede Linie wird eine ID erstellt, die piste_id. Die nicht mehr benötigten Attribute werden gelöscht. Für das Routing ist es später wichtig in welche Richtung die Piste verläuft. In einem benutzerdefinierten Transformer, dem Höhe_Start_und_Endpunkt_herausfinder, wird die Höhe des Starts und Endpunkts ermittelt. Die Höhe wird vom DHM25 abgegriffen. Ist die Höhe des Startpunktes tiefer als die des Endpunktes, wir die Orientierung der Piste umgedreht. Danach werden alle Pisten einem Skigebiet zugeordnet. Ist dies nicht möglich, wird diese Piste aussortiert. Bevor die Pisten gespeichert werden, wird das Attribut p_einweg vergeben. Dieses legt fest ab wann eine Piste als Einweg eingestuft (p_einweg = true) wird oder ob die Piste beidseitig befahrbar ist (p_einweg = false). Die Höhendifferenz wird als UserParameter angegeben vor dem Start des Prozesses. Der Standardwert ist 15m. Die Start- und Endpunkte werden in der Tabelle pisten_startpunkt, respektive pisten_endpunkt gespeichert und werden danach im Prozess Routing_geoserver.fmw.
verwendet.
Die Daten der Anlagen sind aus dem TLM3D Datensatz der Swisstopo. In der Objektklasse Öffentlicher Verkehr, im Liniendatensatz tlm oev uebrige bahn befinden sich sämtliche Sesselbahnen, Gondelbahnen, Standseilbahnen und Bügellifte der Schweiz.
swisstlm3d_2024-03_2056_5728.gpkg.zip von der Swisstopo.
In der Workbench werden die anlage_id erstellt und das Attribut name in a_name umbenannt. Für das Routing ist es später wichtig, in welche Richtung die Anlage verläuft. In einem v Transformer, dem Höhe_Start_und_Endpunkt_herausfinder, wird die Höhe des Starts und Endpunkts ermittelt. Die Höhe wird vom DHM25
abgegriffen. Ist die Höhe des Startpunktes tiefer als die des Endpunktes, wir die Orientierung der Anlage umgedreht. Danach werden alle Anlagen einem Skigebiet zugeordnet. Wenn dies nicht möglich ist, wird diese Anlage aussortiert. Bevor die Anlagen gespeichert werden, wird das Attribut a_einweg vergeben. Dieses legt fest, ab wann eine Anlage als Einweg eingestuft (a_einweg = true) wird, oder ob die Anlage beidseitig befahrbar ist (a_einweg = false). Die Höhendifferenz wird als UserParameter angeben vor dem Start des Prozesses. Der Standartwert ist 15m. Die Start- und Endpunkte werden in der Tabelle anlagen_startpunkt, respektive anlagen_endpunkt gespeichert und werden danach im Prozess Routing_geoserver.fmw verwendet.
Beim Datenimport in die Datenbank werden die Koordinaten von WGS84 in LV95 transformiert. Anschliessend wird jeder Parkplatz mit Hilfe des NeighborFinder dem nächsten Skigebiet zugewiesen.
Beim Datenimport in die Datenbank werden die Koordinaten von WGS84 in LV95 transformiert. Anschliessend wird jede Haltestelle mit Hilfe des NeighborFinder dem nächsten Skigebiet zugewiesen.
Beim Öffnen werden zuerst alle WFS Daten bezogen, über die eigens erstellte Funkion createVectorSource aus der Datei kartenWFS.js. Mitgeliefert wird der Name des Layers der bezogen wird. In der Datei kartenLayerStyle.js sind alle Symbolisierungen von Vektordaten gespeichert. Die ist wie eine CSS-Datei. Die Symbolisierung muss nur in dieser Datei verändert werden und der Layer wird in allen Karten im Projekt angepasst. Die Winterlandeskarte wird über die Funktion SwisstopoLayer aus der Datei swisstopoLayer.js bezogen. In dieser sind auch die Quellenangaben. Diese sind in der Karte unten Links auf der Info Schaltfläche abrufbar, mit einem Link auf die Webseite der Swisstopo. Für das initialisieren der Karte wird der Ausschnitt und die Zoomstufe angeben. Mit der Open Layer Funktion controls wir bei Klicken auf die Schaltfläche E oben links, wird ein angegebener Bereich gezoomt. Wenn auf ein Layer geklickt wird, auf das Element gezoomt. Die Zoomstufe ist abhängig von der Grösse des Elements. In der Box unterhalb der Karte werden die Attribute vom selektieren Element angezeigt. Die Grösse der Box ist abhängig, wie viele Attribute vorhanden sind.
Im Wetter-Menü findet man alle relevanten Informationen zu den Bedingungen im Skigebiet. Dazu gehören die Temperaturvorhersage für den aktuellen Tag, die aktuelle Temperatur, die Schneehöhe, das aktuelle Wetter, die Windgeschwindigkeit und die Windrichtung.
Das Wetter-Menü ist in zwei Bereiche unterteilt: Im oberen Teil wird die Wettervorhersage präsentiert, während im unteren Teil die aktuelle Wettersituation dargestellt wird. Die Vorhersage wird in einem Diagramm visualisiert, wobei die Betriebszeiten der Skilifte grau hervorgehoben sind, um den Fokus auf die relevanten Zeiträume zu lenken. Der Bereich mit den aktuellen Informationen befindet sich im unteren Abschnitt der App. Windrichtung und Wetter werden dabei durch Symbole veranschaulicht.
Wettervorhersage
Die täglichen Wettervorhersagen werden von einer lokalen API abgerufen:
http://localhost:5000/api/prognoseDie abgerufenen Daten werden in die entsprechende Zustandsvariablen weatherChartData gespeichert. Die Daten werden dann in einem Liniendiagramm dargestellt. Das Diagramm wird mit Vega dargestellt.
Aktuelle Wetterdaten
Die aktuellen Wetterdaten werden von einer lokalen API abgerufen:
http://localhost:5000/api/messdatenhttp://localhost:5000/api/schneehoeheDie abgerufenen Daten werden dabei in den entsprechenden Zustandsvariablen snowData und weatherData gespeichert. Ebenfalls ist eine Fehlerbehandlung vorahnend, um Netzwerkfehler und fehlerhafte API-Antworten zu behandeln. Die Darstellung erfolgt über benutzerdefinierte Komponente, welche die jeweiligen Wetterinformation anzeigen, einschliesslich Temperatur, Wetterbedingungen, Windgeschwindigkeit und Windrichtung. Dabei erfolgt das aufrufen der Wetterinformationen über weatherData.md_temperatur, weatherData.md_wetter, weatherData.md_windrichtung, weatherData.md_windgeschwindigkeit. Wetter und Windrichtung verwenden Material-UI-Icons zur visuellen Darstellung.
Im Statistik-Menü finden Sie alle relevanten Informationen zu vergangenen Skitagen. Hier können Sie Vergleiche über die gesamte Saison hinweg anstellen, verschiedene Saisons miteinander vergleichen oder einzelne Tage im Detail auswerten.
Das Menü Statistiken zeigt die Informationen zu den gefahrenen Pistenkilometern. Die Informationen stammen vom Live-Tracking. Das Menü ist aufgeteilt in verschiedene Tagesstatistiken und den Saisonverlauf. Für jeden Tag wird die zurückgelegte Distanz angezeigt, sowie Höhenmeter, Dauer des Wintersporttages und die Anzahl der benutzten Anlagen. Der Saisonverlauf zeigt die über die gesamte Saison zurückgelegte Distanz sowie weitere Informationen und den Tagesdurchschnitt. Für jeden Tag wird der zurückgelegte Weg in der Karte dargestellt. Dieser erscheint nach Anklicken der jeweiligen Tagesstatistiken. Unterhalb der Karte sind zwei Liniendiagramme, welche die Geschwindigkeit und die Höhenmeter in Abhängigkeit der Zeit abbilden. Zum einen kann der ganze Tag abgespielt werden in der Karte und im Diagramm, zum andern kann im Diagramm ein Zeitpunkt ausgewählt werden. Der Marker springt dann zur Position in der Karte zum entsprechenden Zeitpunkt. So kann der Wintersporttag analysiert werden.
Statistiken
Die Daten, die während eines Skitages aufgezeichnet wurden, können mit dem Python-Skript gpx_to_db.py in die App importiert werden. Dieses Skript liest die Informationen aus der gpx-Datei, wandelt sie um und erstellt eine neue Zeile mit diesen Informationen in der Datenbank in der Tabelle skidaten. Die Daten werden dann für die Darstellung in der App mithilfe eines Node-Servers erhoben.
Auf der Statistiken-Seite können die Daten entweder vom neuesten zum ältesten oder vom ältesten zum neuesten mithilfe einer einfachen Schaltfläche sortiert werden.
Wenn die Statistiken-Seite geöffnet wird, werden zunächst alle Daten aus der Tabelle skidaten angezeigt. Es ist möglich, mithilfe des Dropdown-Menüs eine bestimmte Saison auszuwählen, von der man die einzelnen Skitage sehen möchte.
Statistiken Viewer
Vom Menü Statistik aus, kann auf die verschiedenen Positionsaufnahmen navigiert werden. Es öffnet sich eine Karte in der die zurückgelegte Strecke angezeigt wird.
Um jede Box mit den Informationen zur Strecke befindet sich ein Link zum StatistikenViewer.. Dies ist die Karte, auf der die Strecke angezeigt wird. Der Link beinhaltet die Skidaten_ID als Parameter in der URL des angeklickten Restaurants.
Beispiel: http://localhost:3000/StatistikenViewer?Skidaten_ID=6.
Im StatistikenViewer wird mit einem useEffect die Skidaten_ID aus der URL extrahiert. Diese wird dann für eine WFS Anfrage verwendet auf den GeoServer. In dieser Abfrage wird wieder die Skidaten_ID mitgegeben. Diese ist folgendermassen aufgebaut:
http://localhost:8080/geoserver/wfs?service=WFS&version=1.0.0&request=getFeature&typeName=Alpine_Ace:a_a_skidaten_weg&viewparams=Skidaten_ID:11;&outputformat=application/json
Dabei ist Alpine_Ace:a_a_skidaten_weg der Name der SQL View auf dem GeoServer.
Die SQL View ist folgendermassen definiert:
SELECT
v.Skidaten_ID,
v.SD_Date,
v.SD_Hoehenmeter,
v.SD_Distanz,
v.SD_Dauer,
v.SD_Geschwindigkeit,
v.SD_MaxGeschwindigkeit,
v.SD_Saison,
v.Benutzername,
v.SD_Geometrie
FROM
Skidaten AS v
WHERE
v.Skidaten_ID = %Skidaten_ID%
Der Parameter ist %Skidaten_ID% hat dabei den Standardwert 0 und den Wertebereich \d+. Dieser lässt nur positive Integer zu.
Die zurückgegeben Informationen vom WFS werden dem Layer skidatenAnfrageLayer zugeordnet und in der Karte dargestellt.
Balkendiagramm
Vom Menü Statistiken aus, kann mithilfe den Button Graph zu Statistiken in Form von Balkendiagrammen wechseln werden. In diesem neuen Fenster werden die Statistiken in Form von vier verschiedenen Balkendiagrammen dargestellt: Höhenmeter, Distanz, mittlere Geschwindigkeit, maximale Geschwindigkeit.
Die Balkendiagrammen sind beim Öffnen der Seite eine Zusammenfassung der Statistiken pro Saison. Danach kann man mit einem Klick auf das Dropdown eine Saison auswählen und die Statistiken pro Saison darstellen. Wenn eine Saison ausgewählt wurde, wird nicht mehr die Saisonzusammenfassung dargestellt, sondern jeder Skitag wird durch einen Balken repräsentiert.
Die Balkendiagramme werden mithilfe der Bibliothek Recharts erstellt. Die Skidaten werden über API-Aufrufe abgerufen, formatiert und sortiert. Die Diagramme werden dann mithilfe der Komponenten BarChart, Bar, XAxis und YAxis von Recharts erstellt, wobei Material-UI für Stil und Layout verwendet wird.
Im Menü Navi wird der Start- und Zielpunkt auf der Karte an die gewünschte Position verschoben. Der kürzeste Weg zum Ziel wird danach in der Karte als Route hervorgehoben. Durch das Anklicken des Reset Button verschwinden die Marker und die Route von der Karte.
Alle Relevanten Dateien sind im Ordner Routing gespeichert.
Die Navigation basiert auf den Daten der Pisten und Anlagen. Diese müssen zuerst aufbereitet werden und sind in separaten Tabellen angelegt. Das Routing wird serverseitig in der Datenbank berechnet. Dafür wird die Extension pgrouting verwendet.
Bei der Nutzung wird ein Startpunkt angegeben. In einem ersten Schritt wird in der Datenbank nach dem nächsten Startpunkt (Node) gesucht. Dasselbe passiert mit dem Zielpunkt. Über ein topologisches Netzwerk aus gerichteten Graphen (edges) wird dann die kürzeste Distanz mithilfe des Dijkstra Algorithmus errechnet.

Die Daten werden in der FME Workbench Routing_geoserver.fmw aufbereitet. Dabei wird eine Verbindungslinie zwischen den Anlagen und Pisten berechnet um ein durchgängiges topologisches Netzwerk zu erhalten. Grund für die Aufbereitung ist, dass beide Datensätze verschiedene Datengrundlagen haben. Die jeweiligen Start- oder Endpunkte schliessen dabei nicht aufeinander ab. In einem weiteren Schritt werden alle Linien die beidseitig sind, dupliziert. Beim Duplikat wir die Orientierung gedreht.
Für das Routing muss die Datenbank erweitert werden. Aus der Datei alpine_ace_routing_DB_erweitern.txt wird der SQL Code geladen der in der Datenbank mit einem SQLExecutor ausgeführt wird in der Datenbank. Es werden dabei zwei Tabellen erstellt. a_a_routing für das Routing der Pisten und a_a_anlage_routing für das Routing der Anlagen. Beide Tabellen sind nur für die Berechnung des Routings relevant und nachher inaktiv.
Zuerst werden die Koordinaten Start- und Endpunkte der Anlagen und Pisten extrahiert. Dann werden die Anlagen Endpunkte mit dem Pisten Startpunkt über den NeighborFinder gematcht . Genau gleich werden die Pisten Enden mit dem Anlagen Startpunkt über den NeighborFinder gematcht . Bei beiden Schritten ist die Anzahl der Matches nicht begrenzt und die Maximaldistanz kann über den UserParameter max_distanz_anlagen_end_pisten_start, respektive max_distanz_pisten_end_anlagen_starteingegeben werden. Der Standardwert ist 50 Meter. In einem zweiten Schritt werden die nicht gematchten Anlagen Endpunkte mit den Pisten Startpunkten gematcht. Dasselbe gilt für die nicht gematchten Pisten Startpunkte. Auch wieder mit dem NeighborFinder und nur einem Match mit einer Maximaldistanz von 120 Meter. Bei ersten Schritt mit der kürzeren Distanz werden nur die umliegenden Verbindungen hergestellt. Beim zweiten Schritt werden längere Verbindungen hergestellt, damit alle Anlagen oder Pisten in Netzwerk untereinander verbunden sind. Um zu verhindern, dass falsche Verbindungen entstehen ist nur ein Match zugelassen. Die Distanzen 50 Meter und 120 Meter sind Erfahrungswerte. Die Geometrien der Punkte werden anschliessend gelöscht. Mit den zuvor extrahierten Koordinaten wird anschliessend ein Punkt erstellt. Zwischen den jeweiligen Start und Endpunkten wird eine direkte Verbindungslinie berechnet. Die Orientierung der Line ist von oben nach unten. Die Pisten aus der Datenbank werden anschliessend mit den Verbindungslinien zusammengeführt. Alle Linien die das Attribut routing_einweg = true haben werden dupliziert und die Orientierung gedreht, damit in beide Richtungen eine Verbindung besteht. Die Verbindungen und Pisten werden in der Tabelle a_a_routing gespeichert. Dasselbe passiert mit den Anlagen welche beidseitig sind. Diese werden in der Tabelle a_a_anlage_routing gespeichert.
Mit Hilfe des QGIS Projektes Alpine_ace_Routing.qgz können Änderungen in den Routing Tabellen vorgenommen werden. Beim Start des Projekts muss der Benutzername und das Passwort der Datenbank eingetragen werden.
Die Änderungen müssen in der Datengrundlage Routing vorgenommen werden . Es dürfen nur die Tabellen a_a_routing und a_a_anlage_routing angepasst werden. Der Pfeil zeigt jeweils die Orientierung der Verbindungslinien an. Nach vollbrachter Änderung muss die Berechnung des Routings in pgAdmin 4 erfolgen.
Einweg oder beidseitig anpassen : Die gewünschte Piste oder Anlage anwählen, in den Bearbeitungsmodus setzen und in der Attributtabelle das Attribut routing_einweg anpassen. Nach erfolgter Änderung den Layer speichern.
a_a_routing in Bearbeitung setzen, den Fangmodus einschalten (Magnetsymbol) und die gewünschte Verbindungslinie einzeichnen und in das Attribut routing_einweg abfüllen. Wenn eine Verbindung beidseitig ist, muss diese auch auf beide Seiten eingezeichnet werden. Nach erfolgter Änderung den Layer speichern.Falls die Fehlermeldung: Konnte Änderungen am Layer a_a_routing nicht festschreiben
Fehler: FEHLER: Ein Objekt nicht hinzugefügt. erscheint, liegt dies meist an der Vergabe der id in der Tabelle.
Behoben kann dieses Problem werden, wenn unter: Eigenschaften --> Attributformular --> Verfügbare Element --> Fields --> id --> Vorgaben den Ausdruck maximum( "id" ) + 1 eingefügt wird. Dieser erhöht den aktuell höchsten Wert der id um 1 und setzt diesen ins Attributformular automatisch ein. Zusätzlich die Checkbox bei Vorgabewert bei Aktualisierung anwenden setzen.

Im pgAdmin 4 wird anschliessend das Routing berechnet, der Code dafür liegt in der Datei alpine_ace_routing.txt. Zuerst werden für die Anlagen und die Pisten separat die Knoten berechnet mit dem Befehl pgr_nodeNetwork. Daraus resultieren die beiden Tabellen a_a_routing_noded und a_a_anlage_routing_noded Dies geschieht getrennt, da überall, wo sich zwei Linien schneiden, ein Knoten erstellt wird. Da die Anlagen über den Pisten sind dürfen zwischen diesen Linien keine Punkte erstellt werden. In die beiden Tabellen werden die Attribute der Ursprungsdaten kopiert. Die Knoten der Anlagen werden in Tabelle a_a_routing_noded kopiert. Darin wird das Routing gerechnet mit dem Befehl pgr_createTopology.
Ursprünglich war geplant, die Funktion Einweg Routing über die reverse_cost zu steuern. Deshalb wurden Kosten in Abhängigkeit der Distanz vergeben. Wenn eine Strecke einseitig ist, wurde zu den reverse_cost eine Million addiert. Für beidseitige Strecken sind die Kosten in beide Richtungen gleich. Dies findet aber im jetzigen Routing keine Anwendung, da beidseitige Strecken doppelt in beide Richtungen im Datensatz vorhanden sind.
Für das Routing werden zwei SQL views benötigt.
SQL view a_a_nearest_vertex:
SELECT
v.id,
v.the_geom
FROM
a_a_routing_noded_vertices_pgr AS v,
a_a_routing_noded AS e
WHERE
v.id = (
SELECT
id
FROM
a_a_routing_noded_vertices_pgr
ORDER BY
the_geom <-> ST_SetSRID(ST_MakePoint(%x%, %y%), 2056)
LIMIT 1
)
AND (e.source = v.id OR e.target = v.id)
GROUP BY
v.id, v.the_geom

Diese SQL view bekommt als Parameter das Koordinatenpaar %x% und %y% mit dem Wertebereich ^[\d\.\+]+$ Dieser lässt Positive Gleitkommazahlen zu. Es sucht in der Tabelle a_a_routing_noded den nächsten Knoten. Ausgeben wird die Geometrie des Knotens und die id.
Beispiel:
http://localhost:8080/geoserver/wfs?service=WFS&version=1.0.0&request=getFeature&typeName=Alpine_Ace:a_a_nearest_vertex&viewparams=x:2648338;y:1137974;&outputformat=application/json
SQL view a_a_shortest_path_test:
SELECT
min(r.seq) AS seq,
e.old_id AS id,
e.p_farbe,
sum(e.distance) AS distance,
ST_Collect(e.the_geom) AS geom,
sum(e.cost) AS cost, -- Adding the 'cost' column
sum(e.rcost) AS rcost -- Adding the 'rcost' column
FROM
pgr_dijkstra(
'SELECT id,source,target,distance AS cost, rcost FROM a_a_routing_noded', %source%, %target%, false
) AS r,
a_a_routing_noded AS e
WHERE
r.edge = e.id
GROUP BY
e.old_id, e.p_farbe

Diese SQL view bekommt als Parameter die Knoten ID des Startpunktes %source% und des Zielpunktes %target% mit dem Wertebereich \d+, der nur positive Integer zulässt. Mit Hilfe des Dijkstra Algorithmus wird die kürzeste Distanz zwischen den beiden Punkten im Topologie Netzwerk berechnet. Ausgegeben werde die einzelnen die Geometrien der Strecken, seq (Sequenznummer für die Reihenfolge), p_farbe und die distance.
Beispiel:
http://localhost:8080/geoserver/wfs?service=WFS&version=1.0.0&request=GetFeature&typeName=Alpine_Ace:a_a_shortest_path&viewparams=source:3862;target:2114;&outputformat=application/json
Dijkstra ist ein Algorithmus mit welchem der kürzeste Weg zwischen Start und Ziel, in einem Netzwerk berechnet werden kann. Dies ist mit Einbezug von von Kosten möglich, in diesem Fall dem Abstand zwischen den Konten (Distanz). Der Dijkstra Algorithmus kann auch die Heuristik miteinbeziehen. Diese ist eine Schätzung, welche eine Annäherung zur optimalen Lösung ist.(geoinformation.net o.J) Diese muss aber nicht korrekt sein. Die Annäherung kann zum Beispiel die Luftlinie zwischen Start und Endpunkt sein. Der Dijkstra Algorithmus mit Heuristik wird als A\* bezeichnet. Mit der Schätzung ist der Algorithmus meist schneller, da dieser einen Anhaltspunkt hat in welche Richtung die Suche los gehen soll.(Sun/Ding/Jiang 2017)
Wieso wird nicht der A\* Algorithmus verwendet? Die Luftlinienschätzung funktioniert bei den Anlagen weniger gut, da diese dem Gelände hinauf verlaufen. Dabei nicht immer in die Richtung des Zielpunktes zeigen. Der Geschwindigkeitsgewinn ist bei grossen Netzwerken mit mehren hundert Knoten signifikant. Da aber die längste Strecke in der Lenzerheide von der Bergstation Piz Scalottas zur Brüggerhorn Black Diamond Piste nur 87 Teilstücke umfasst, ist dies nicht sehr lange. Dies bedeutet, der Zeitgewinn bei diesem einfachen Netzwerk ist nicht gross. Um aber dies Umfassend zu klären müssten beide Algorithmen an den Daten getestet und verglichen werden.
Durch anklicken der Schaltfläche START oder ZIEL wird der Start, respektive Ziel Marker in den Mittelpunkt des Kartenausschnittes gesetzt. Sobald der Start oder Ziel Marker erstellt ist, wird die Schaltfläche für das erstellen deaktiviert. Den Start und Ziel Marker mittels des Attribut markerType unterschieden. Das Icon bezieht der Marker aus der Ordner Karte_Symbole vom online Github Repository, da dies per lokalen Ordner nicht funktioniert. Mit der Position des Markers wird über die Funktion fetchNearestVertex mit der SQL View a_a_nearest_vertex die nächste Node_ID gesucht. Diese wird dann als nodeSource beim Start Marker und als nodeTarget beim Ziel Marker gesetzt. Wenn die Marker verschoben werden, wir die Funktion fetchNearestVertex wieder aufgerufen und die Node_ID aktualisiert. Wenn die nodeSource oder nodeTarget den Wert ändern wird die Funktion handleLoadRoute gestartet. Diese löscht als erstes die alte Route und lädt die neue Route mit der SQL View a_a_shortest_path in der die Parameter nodeSource und nodeTarget verwendet werden. Der Stil für den Layer kommt aus der Datei kartenLayerStyle.js, dem CSS für die Layer Symbolisierung.
Mit der Funktion resetMarkerUndRoute wird durch anklicken von der Schaltfläche RESET gestartet. Dabei werden die Marker und den Routen Layer gelöscht. Die Schaltflächen START und Ziel werden wieder aktiviert (verwendbar).
In der Karte sind die Layer Pisten und Anlagen mit der Winterlandeskarte im Hintergrund. Der Import der WFS und WMS Daten, die Symbolisierung, die Quellenangaben der Hintergrundkarte und das Zoomen auf einen vorgeben Bereich über die Schaltfläche E ist gleich wie in der Karte der Mit der Funktion setZIndex wird die Darstellungsreihenfolge gesetzt. Dabei ist 1 zu unterst und 5 zuoberst:
Die Restaurants des Skigebietes werden in Kacheln angeordnet. In diesen Kacheln ist jeweils ein Bild des Restaurants und darunter der Name. Nach dem Anklicken einer Kachel wird das gewählte Restaurant in der Karte dargestellt. Unterhalb der Karte werden die Informationen zu Öffnungszeiten und Kontaktinformationen wie Telefonnummer oder Webseite angezeigt.

Beim Datenimport in die Datenbank werden die Koordinaten von WGS84 in LV95 transformiert. Anschliessend wird jedes Restaurant mithilfe des NeighborFinder dem nächsten Skigebiet zugewiesen.
Vom Hauptmenü aus kann auf die Schaltfläche Restaurants navigiert werden. Dort befinden sich die Bilder der Restaurants und unterhalb der dazugehörige Name. Beim Anklicken des Bildes oder Textes öffnet sich die Karte und es wird auf die Position des Restaurants gezoomt. Unterhalb der Karte werden die Informationen angezeigt.
SELECT * FROM Restaurant ORDER BY r_name; abgesetzt. Mit diesem Befehl werden die gespeicherten Daten von der Datenbank alphabetisch nach dem Attribut r_name sortiert zurückgegeben. Die Daten können dann unter dem Pfad: http://localhost:5000/api/restaurant bezogen werden.Jedes Element wird im Array mittels der map() Funktion in einer eigenen Box dargestellt. Für jedes Restaurant befindet sich ein Bild in der React-App im Ordner /Restaurant_data/ . Der restliche Pfad der Bilddatei ist im Attribut r_dateipfad_bildname gespeichert. So wird für jedes Restaurant das dazugehörige Bild angezeigt. Unterhalb des Bildes ist der Restaurant Name. Dieser ist ebenfalls die Bildbeschreibung.
Um jede Box welche Bild und Restaurant Name beinhaltet, befindet sich ein Link auf den Restaurant_Viewer. Dies ist die Karte, auf der die Position und die Kontaktinformationen des Restaurants angezeigt werden. Der Link beinhaltet die Restaurant_ID als Parameter in der URL des angeklickten Restaurants.
Beispiel: http://localhost:3000/Restaurant_Viewer?Restaurant_ID=15
Restaurant_ID aus der URL extrahiert. Diese wird dann für eine WFS Anfrage verwendet auf den GeoServer. In dieser Abfrage wird wieder die Restaurant_ID mitgegeben. Diese ist folgendermassen aufgebaut:
http://localhost:8080/geoserver/wfs?service=WFS&version=1.0.0&request=getFeature&typeName=Alpine_Ace:a_a_restaurant&viewparams=Restaurant_ID:50;&outputformat=application/json
Dabei ist Alpine_Ace:a_a_restaurant der Name der SQL View auf dem GeoServer.
Die SQL View ist folgendermassen definiert:
SELECT
v.Restaurant_ID,
v.R_Name,
v.R_Oeffnungszeiten,
v.R_Telefon,
v.R_Email,
v.R_Webseite,
v.R_Geometry
FROM
Restaurant AS v
WHERE
v.Restaurant_ID= %Restaurant_ID%
Der Parameter %Restaurant_ID% hat dabei den Standardwert 0 und den Wertebereich \d+. Dieser lässt nur positive Integer zu. Die WFS Anfrage gibt nur die Attribute zurück die unterhalb der Karte angezeigt werden.
restaurantAnfrageLayer zugeordnet. Dieser bekommt dann die Stil Eigenschaften restaurantStyle zugwiesen Dies umfasst das ein Icon aus einer svg Datei. Die weiteren Informationen vom Feature werden extrahiert, damit diese unterhalb der Karte dargestellt werden können. Von der Start Position der Karte wird anschliessend auf die Restaurant Position gezoomt mittels einer Animation. Unterhalb der Karte werden dann die Informationen des Restaurants angezeigt.Folgende Features werden in der AlpineAce V2.0 eingebaut. Die Datenbank ist dafür bereits ausgelegt, was die Implementierung der Features vereinfachen sollte.

Upcoming features in AlpineACE V2.0
In der Karte wird die aktuelle Position des Gerätes angezeigt mit einem Marker. Dies erleichter das Nutzen der Karte und die Navifunktion.
In der Karte werden alle Symbole erklärt. Zusätzlich lassen sich die verschiedenen Layers beliebig ein und ausblenden.
|
In der Karte kann das Zoomen zur Piste oder Anlage verbessert werden. Es wird momentan nur ein Teil der Linie dargestellt. Dies könnte behoben werden beim Import im geoserver_Datenimport.fmw. Pisten und Anlagen könnten mit dem Transformer Aggregator nach dem Attribut Namen als eine Geometry zusammengesetzt werden. Im Frontend ist die Funktionalität nach der Ausdehnung der Geometrie bereits vorhanden.
In Version 2.0 werden die Daten im Dashboard direkt von den Webseiten der Bergbahnen bezogen, um stets die aktuellsten Informationen bereitstellen zu können. Die Daten werden dann alle 15 min aktualisiert, somit ist eine hohe Aktualität gewährleistet. Eine weitere Möglichkeit wäre Webscraping von der Webseite Bergfex. Auf dieser sind sämtlich Anlage und Pisten Informationen von Skigebieten der Schweiz vorhanden. Das Webscraping müsst so nur für einer Webseite programmiert werden und nciht für jedes Skigebiet neu.
Das Attribut Status ist bei den Pisten und Analgen momentan leer. Wenn die Daten von Bergbahnen automatisch bezogen werden, könnten geschlossene Pisten und Analgen zusätzlich in der Karte differenziert symbolisiert werden. Auch das Routing könnte so angepasst werden, damit nur Routen angezeigt werden über offene Pisten und Anlagen. Das Datenbankschema wäre bereit für dieses Feature. Es existiert das Attribut Status auch in den Routing Tabellen. Wäre diese offen, ist das Attribut Status true und wenn geschlossen false.
Damit das Skierlebnis sich nicht nur auf ein Skigebiet beschränkt, wird es möglich sein, mehrere Skigebiete auszuwählen. Dabei muss beim Starten der Web-App das gewünschte Skigebiet gewählt werden und anschliessend werden die Informationen des ausgewählten Skigebiets dargestellt. Es wird möglich sein, Favoriten festzulegen, damit nicht immer gesucht werden muss.
|
Mit einem Bewertungsmenü sollen die Nutzer sowohl Restaurants als auch die Pisten bewerten können. Somit lassen sich Daten über die Nutzererfahrung und das Qualitätsempfinden sammeln. Das Bewertungsmenü wird dabei nach einem Restaurant Besuch automatisch geöffnet. Es kann aber auch manuell über das Hauptmenü geöffnet werden.
|
In den Einstellungen kann die Webapp an die Bedürfnisse des Nutzers angepasst werden. Wenn die Einstellungen verändert werden, muss dies mit dem Knopf speichern bestätigt werden. Folgende Einstellungen werden möglich sein:
|
Um Ihr Skierlebnis weiter zu verbessern, wird es bald möglich sein, ein Benutzerkonto anzulegen. Mit einem Konto kann man seine Statistiken sicher speichern und die Daten sind nicht mehr an ein einzelnes Gerät gebunden. So wird das individuelle Nutzungserlebnis optimal unterstützt.
Um den Vergleich von Skitagen zu vereinfachen, wird ein Live-Tracking in die App integriert. Dadurch ist das Aufzeichnen nicht mehr von einem zusätzlichen Gerät wie einer GPS-Uhr abhängig. Die Tracking-Funktion kann einfach durch ein Wischen eines Buttons von links nach rechts aktiviert werden.
Rückmeldungen aus dem Gelände sind unerlässlich für ein zuverlässiges Lawinenbulletin. Um die Rückmeldung zu gewährleisten, wird ein Button mit einer Verlinkung zum Rückmeldetool (https://pro.slf.ch/reply/public/#/) des Instituts für Schnee und Lawinenforschung gemacht. Damit kann ein Beitrag zu einem qualitativ hochwertigen Lawinenbulletin geleistet werden.
Das Projekt war sehr umfassend mit verschieden Herausforderungen über alle Projektphasen hinaus.
Besprechungen mit Whiteboard : Die regelmässigen Besprechungen im Team haben sich als äusserts wertvoll erwiesen, um das weitere Vorgehen zu planen, Probleme zu lösen und neue Ideen zu entwickeln. Durch die kontinuierliche Nutzung eines Whiteboards konnten wir unsere Gedanken und Pläne effektiv visualisieren. Diese Visualisierungen ermöglichten es uns, verschiedene Ansätze schnell auszuprobieren und zu bewerten. Das Whiteboard hat sich dabei als unverzichtbares Planungstool etabliert und wesentlich zur Effizienz unserer Meetings beigetragen.
API Datenbezug : Bezug von Daten mittels API-Adressen und Speicherung in ein RDBS.
Geoserver : Aufsetzen und Betreiben des GeoServer auf den Betriebssystem Windows und Raspberry Pi OS.
SQL Views : Mit SQL Views auf dem GeoServer können nur gewünschte Objekte per WFS bezogen werden. Die Parameter werden dabei per URL übergeben. Es konnten verschiedenste SQL Views mit unterschiedlichen Parameter, Wertebereiche und Funktionen kreiert werden.
React App Mobile Version : Entwickeln einer React Webseite spezifisch auf mobile Endgeräte. Die Komponenten passen sich dabei automatisch der Grösse des Bildschirms an.
CORS : Was Cross-Origin Ressource Sharing ist und wie dies in der Express-API und im GeoServer gehandhabt wird, damit schlussendlich Daten auch auf Drittgeräten angezeigt werden.
Open Layer : Mit der Open Layer Bibliothek konnten unterschiedliche Funktionen genutzt werden.
Routing : Mithilfe der Erweiterung pgrouting konnten Routing Netzwerke über mehrere Ebenen berechnet werden. Dabei wurde vertieftes Verständnis für das automatische Erstellen von Knoten, Netzwerk Topologien (gerichtet/ungerichtet, gewichtet/ungewichtet) und Routing Algorithmen (Dijkstra, A\*) erworben.
Vega Diagramme : Die Nutzung von Vega und Vega-Lite hat sich als äusserst effektiv erwiesen, um Daten anschaulich im Zusammenhang mit Javascript darzustellen. Diese beiden Tools bieten eine flexible und leistungsfähige Möglichkeit zur Datenvisualisierung, die uns geholfen hat, komplexe Datensätze verständlich und übersichtlich zu präsentieren.
Git Hub README : Im README wurde eine Installationsanleitung für das Projekt erstellt und getestet. Es sind die ersten Erfahrungen, um ein README zu schreiben. Bisher wurde dieses nur gelesen. Dies ist ein spannender Perspektivenwechsel..
Git Hub Page : Erstellen einer Web-Dokumentation auf GitHub mit Markdown-Dateien.
CORS : Den Zugriff auf andere Webressourcen in der React App wurde zuerst nicht definiert. So wurde Teile der Webseite nicht geladen.
Routing : Zuerst wurden die Konten für die Pisten und Anlagen gemeinsam erstellt. Dies hatte zur Folge, dass die Navigationsroute beim Kreuzen die Anlage genutzt und/oder verlassen hat. Das konnte gelöst werden, indem die Konten getrennt berechnet wurden. Dies brachte zusätzliche Komplexität mit den Attributen der Routen Tabellen und der manuellen Bearbeitung.
GIT Hub merge conflict : Mehrmals während der Bearbeitung des Projekts entstanden Konflikte, da an der gleichen Stelle im Code gearbeitet wurde. Dies konnte mit verbesserter Kommunikation gelöst werden. Die Verbindungsinformationen waren der häufigste Grund für ein Konflikt. Dies konnte mit einer separaten Config-Datei gelöst werden, welche in der gitignore-Datei eingetragen ist.
GIT Hub Limit : Das DHM25 mit einer Grösse von mehr als 100Mb können nicht hochgeladen werden. Wird dies versucht, entsteht ein Fehler und blockiert das ganze GitHub-Repository. Gelöst wurde dies mit einem Eintrag in der gitignore-Datei. Der Bezug vom DHM25 wurde mittels automatischen Download Skript gelöst. Dieses führt die den Download aus, entzippt dieses und legt es im korrekten Verzeichnis ab.
Namenskonventionen : Teilweisse änderten sich die Namen von Funktionen im Laufe des Projekts. Dabei mussten Dateinamen und Konstante über alle Skripts angepasst werden. Mit bessere Absprache untereinander und einer guten Umbenennungsfunktion konnte dem Problem entgegengesetzt werden. Die Mischung zwischen den Sprachen Deutsch Englisch besteht aber weiterhin.
Vega : Es traten Probleme mit der Darstellung von Daten der Datenbank, welche über eine Express-API bezogen werden, mit Vega auf. Daher sind alle verwendeten Diagramme momentan noch Hard gecoded.
Probleme Unterteilen : Probleme in kleinstmögliche Form reduzieren und sich Hilfe in Foren suchen oder Chat-GPT konsultieren. Nutzer von Foren helfen nur, wenn der Code kurz und dieser gut beschreiben ist (teilweise wird der Fehler beim Dokumentieren bereits gefunden).
Funktionen : Mehr Funktionen schreiben, um Redundanzen möglichst klein zu halten. Faustregeln: Wird der gleiche Code mehr als drei Mal verwendet im Projekt gehört dieser in eine Funktion.
Verbindungsinformationen Datenbank : Wenn möglich alle Verbindungsinformationen für alle gleich (DB Name, Passwort, Host und Port) während der Entwicklung und diese in separaten Config-Dateien speichern.
Sprache und Namenskonventionen festlegen : Vor dem Projekt Start sollte die Sprache (Code und Dokumentation) festgelegt werden. Für den Code sollte ausschliesslich Englisch genutzt werden. Schreibfehler können mit einem Rechtschreiben-Plug-in verhindert werden.
Folgend sind alle Quellen für diese Arbeit in mehreren Kategorien unterteilt und aufgelistet.s
geoinformation.net (o.J.). Lernmodul 7: Geo-Algorithmen und -Datenstrukturen - Dijkstra-Erweiterungen. URL: http://www.geoinformation.net/lernmodule/folien/Lernmodul_07/druck/lm7_le2.pdf [Zugriffsdatum: 28. Mai 2024].
SUN, Yan-Jiang/DING, Xiang-Qian/JIANG, Lei-Na (2017). Heuristic Pathfinding Algorithm Based on Dijkstra. In. Qingdao, Shandong, China. DOI: 10.2991/eeeis-17.2017.59.
Namen der Datenquelle |
Link |
|
Wetterdaten |
https://open-meteo.com/ |
|
Lawinensituation |
https://aws.slf.ch/api/bulletin/caaml |
|
Schneehöhe |
https://measurement-api.slf.ch/ |
|
Haltestellen |
https://www.google.com/maps |
|
Anlagen |
https://www.swisstopo.admin.ch/de/landschaftsmodell-swisstlm3d |
|
Pisten |
data.opensnowmap.org. |
|
DHM25 |
https://www.swisstopo.admin.ch/de/hoehenmodell-dhm25 |
|
Namen der Library |
Link zur Dokumentation |
|
openmeteo-requests |
|
|
psycopg2 |
|
|
requests |
|
|
requests-cache |
|
|
retry-requests |
|
|
pyproj |
|
|
pandas |
|
|
shutil |
|
Namen der Library |
Link zur Dokumentation |
|
React |
|
|
MUI |
|
|
npm |
|
|
Vega |
|
|
Express |
|
Namen des Hilfsmittel |
Anwendungsfall |
Link zur Webseite |
|
Duden |
Synonym Suche |
|
|
German - Code Spell Checker |
Rechtschreibprüfung in der Dokumentation |
https://marketplace.visualstudio.com/items?itemName=streetsidesoftware.code-spell-checker-german |
|
deepl |
Rechtschreibprüfung in der Dokumentation |
|
|
ChatGPT |
Code Beispiele, Code Fehlersuche |