From 62a17bc63df569935ed97067da39859e6a6eed89 Mon Sep 17 00:00:00 2001 From: schrom01 Date: Mon, 15 Aug 2022 01:10:34 +0200 Subject: [PATCH] created Dashboard --- FileIO/__init__.py | 15 +++ Webserver/Templates/dashboard.html | 112 +++++++++++++------- Webserver/Templates/header.html | 7 +- Webserver/Templates/system.html | 2 +- Webserver/Templates/times.html | 2 +- Webserver/Templates/zone.html | 52 ++++++++++ Webserver/Templates/zones.html | 2 +- Webserver/Translater.py | 38 +++++++ Webserver/__init__.py | 76 ++++++++------ Webserver/static/Styles/dashboard.css | 141 ++++++++++++++++++++++++++ Webserver/static/Styles/header.css | 9 +- Webserver/static/Styles/main.css | 6 ++ Zone.py | 25 +++++ 13 files changed, 413 insertions(+), 74 deletions(-) create mode 100644 FileIO/__init__.py create mode 100644 Webserver/Templates/zone.html create mode 100644 Webserver/Translater.py create mode 100644 Webserver/static/Styles/dashboard.css create mode 100644 Zone.py diff --git a/FileIO/__init__.py b/FileIO/__init__.py new file mode 100644 index 0000000..6b53a7f --- /dev/null +++ b/FileIO/__init__.py @@ -0,0 +1,15 @@ +from Zone import Zone + +def loadZones(): + zones = [] + for i in range(12): + zones.append(Zone(i+1, "Zone " + str(i+1), 90, 10, True, False)) + return zones + + + + +if __name__ == "__main__": + zones = loadZones() + for zone in zones: + print(zone.name) \ No newline at end of file diff --git a/Webserver/Templates/dashboard.html b/Webserver/Templates/dashboard.html index 47748ae..8f58116 100644 --- a/Webserver/Templates/dashboard.html +++ b/Webserver/Templates/dashboard.html @@ -2,8 +2,28 @@ + - Bewässerungssystem + {{ translater.getTranslation("Irrigation") }}{{ translater.getTranslation("system") }} + + {% include "header.html" %} @@ -11,43 +31,67 @@
-

Dashboard

+

{{ translater.getTranslation("Dashboard") }}

-
-

- Lorem, ipsum dolor sit amet consectetur adipisicing elit. - Sed excepturi quod dicta temporibus eveniet corporis incidunt molestiae, laborum deleniti. - Molestiae architecto quod veritatis laudantium aliquid aperiam earum quia voluptates saepe! - Lorem, ipsum dolor sit amet consectetur adipisicing elit. - Sed excepturi quod dicta temporibus eveniet corporis incidunt molestiae, laborum deleniti. - Molestiae architecto quod veritatis laudantium aliquid aperiam earum quia voluptates saepe! - Lorem, ipsum dolor sit amet consectetur adipisicing elit. - Sed excepturi quod dicta temporibus eveniet corporis incidunt molestiae, laborum deleniti. - Molestiae architecto quod veritatis laudantium aliquid aperiam earum quia voluptates saepe! -

-

- Lorem, ipsum dolor sit amet consectetur adipisicing elit. - Sed excepturi quod dicta temporibus eveniet corporis incidunt molestiae, laborum deleniti. - Molestiae architecto quod veritatis laudantium aliquid aperiam earum quia voluptates saepe! -

-

- Lorem, ipsum dolor sit amet consectetur adipisicing elit. - Sed excepturi quod dicta temporibus eveniet corporis incidunt molestiae, laborum deleniti. - Molestiae architecto quod veritatis laudantium aliquid aperiam earum quia voluptates saepe! -

-

- Lorem, ipsum dolor sit amet consectetur adipisicing elit. - Sed excepturi quod dicta temporibus eveniet corporis incidunt molestiae, laborum deleniti. - Molestiae architecto quod veritatis laudantium aliquid aperiam earum quia voluptates saepe! -

-

- Lorem, ipsum dolor sit amet consectetur adipisicing elit. - Sed excepturi quod dicta temporibus eveniet corporis incidunt molestiae, laborum deleniti. - Molestiae architecto quod veritatis laudantium aliquid aperiam earum quia voluptates saepe! -

+
+ {% for zone in zones %} +
+ +

{{ zone.name }}

+
+ + + + + + + + + + + + + + + + + + + + + + + + +
+ + + + {{ translater.getTranslation("state") }}: +

{{ translater.getTranslation("switched on") if zone.state else translater.getTranslation("switched off") }}

+

{{ translater.getTranslation("turn off") if zone.state else translater.getTranslation("turn on") }}

+
+ +

{{'A' if zone.autoMode else 'M'}}

+
+
{{ translater.getTranslation("operating mode") }}:{{translater.getTranslation("automatic mode") if zone.autoMode else translater.getTranslation("manual mode")}}
+ + + + {{ translater.getTranslation("actual humidity") }}:{{ zone.actualValue}}
+ + {{ translater.getTranslation("desired humidity") }}:{{ zone.setValue }}
+

{{ zone.number }}

+
+ + {% endfor %} + + +
+



\ No newline at end of file diff --git a/Webserver/Templates/header.html b/Webserver/Templates/header.html index 0fd3171..8b87bdb 100644 --- a/Webserver/Templates/header.html +++ b/Webserver/Templates/header.html @@ -3,7 +3,6 @@ - Bewässerungssystem
@@ -20,12 +19,12 @@
- Tropfen + -

Bewässerungs-
system

+

{{ translater.getTranslation("Irrigation") }}-
{{ translater.getTranslation("system") }}

- Blumenbeet +
diff --git a/Webserver/Templates/system.html b/Webserver/Templates/system.html index 9ab9679..4875170 100644 --- a/Webserver/Templates/system.html +++ b/Webserver/Templates/system.html @@ -3,7 +3,7 @@ - Bewässerungssystem + {{ translater.getTranslation("Irrigation") }}{{ translater.getTranslation("system") }} {% include "header.html" %} diff --git a/Webserver/Templates/times.html b/Webserver/Templates/times.html index de4cd50..a3b998b 100644 --- a/Webserver/Templates/times.html +++ b/Webserver/Templates/times.html @@ -3,7 +3,7 @@ - Bewässerungssystem + {{ translater.getTranslation("Irrigation") }}{{ translater.getTranslation("system") }} {% include "header.html" %} diff --git a/Webserver/Templates/zone.html b/Webserver/Templates/zone.html new file mode 100644 index 0000000..7a1604f --- /dev/null +++ b/Webserver/Templates/zone.html @@ -0,0 +1,52 @@ + + + + + + {{ translater.getTranslation("Irrigation") }}{{ translater.getTranslation("system") }} + + + {% include "header.html" %} + +
+ +

Zone

+ +
+

+ Lorem, ipsum dolor sit amet consectetur adipisicing elit. + Sed excepturi quod dicta temporibus eveniet corporis incidunt molestiae, laborum deleniti. + Molestiae architecto quod veritatis laudantium aliquid aperiam earum quia voluptates saepe! + Lorem, ipsum dolor sit amet consectetur adipisicing elit. + Sed excepturi quod dicta temporibus eveniet corporis incidunt molestiae, laborum deleniti. + Molestiae architecto quod veritatis laudantium aliquid aperiam earum quia voluptates saepe! + Lorem, ipsum dolor sit amet consectetur adipisicing elit. + Sed excepturi quod dicta temporibus eveniet corporis incidunt molestiae, laborum deleniti. + Molestiae architecto quod veritatis laudantium aliquid aperiam earum quia voluptates saepe! +

+

+ Lorem, ipsum dolor sit amet consectetur adipisicing elit. + Sed excepturi quod dicta temporibus eveniet corporis incidunt molestiae, laborum deleniti. + Molestiae architecto quod veritatis laudantium aliquid aperiam earum quia voluptates saepe! +

+

+ Lorem, ipsum dolor sit amet consectetur adipisicing elit. + Sed excepturi quod dicta temporibus eveniet corporis incidunt molestiae, laborum deleniti. + Molestiae architecto quod veritatis laudantium aliquid aperiam earum quia voluptates saepe! +

+

+ Lorem, ipsum dolor sit amet consectetur adipisicing elit. + Sed excepturi quod dicta temporibus eveniet corporis incidunt molestiae, laborum deleniti. + Molestiae architecto quod veritatis laudantium aliquid aperiam earum quia voluptates saepe! +

+

+ Lorem, ipsum dolor sit amet consectetur adipisicing elit. + Sed excepturi quod dicta temporibus eveniet corporis incidunt molestiae, laborum deleniti. + Molestiae architecto quod veritatis laudantium aliquid aperiam earum quia voluptates saepe! +

+
+ +
+ + + \ No newline at end of file diff --git a/Webserver/Templates/zones.html b/Webserver/Templates/zones.html index 277275c..10d4e81 100644 --- a/Webserver/Templates/zones.html +++ b/Webserver/Templates/zones.html @@ -3,7 +3,7 @@ - Bewässerungssystem + {{ translater.getTranslation("Irrigation") }}{{ translater.getTranslation("system") }} {% include "header.html" %} diff --git a/Webserver/Translater.py b/Webserver/Translater.py new file mode 100644 index 0000000..fb9f9b0 --- /dev/null +++ b/Webserver/Translater.py @@ -0,0 +1,38 @@ +from enum import Enum +class Language(Enum): + ENGLISH = 1 + GERMAN = 2 + +class Translater: + def __init__(self, language): + self.language = language + self.dict_german = { "Irrigation": "Bewässerungs", + "system": "system", + "Dashboard": "Startseite", + "irrigation zones": "Bewässerungszonen", + "blocking times": "Sperrzeiten", + "system settings": "Systemeinstellungen", + "Zone": "Zone", + "state": "Status", + "operating mode": "Betriebsmodus", + "actual humidity": "momentane Feuchtigkeit", + "desired humidity": "gewünschte Feuchtigkeit", + "switched on": "eingeschaltet", + "switched off": "ausgeschaltet", + "turn on": "einschalten", + "turn off": "ausschalten", + "manual mode": "Handbetrieb", + "automatic mode": "Automatikbetrieb", + "switch to manual mode": "Auf Handbetrieb umstellen", + "switch to automatic mode": "Auf Automatikbetrieb umstellen", + } + + + def getTranslation(self, english_String): + match self.language: + case Language.ENGLISH: + return english_String + case Language.GERMAN: + return self.dict_german[english_String] + case _: + return "no translations for these language" diff --git a/Webserver/__init__.py b/Webserver/__init__.py index 824100c..27f411e 100644 --- a/Webserver/__init__.py +++ b/Webserver/__init__.py @@ -1,41 +1,59 @@ from flask import Flask, render_template, request, redirect, url_for from flask_navigation import Navigation +from FileIO import loadZones +from Translater import Translater, Language +from Zone import getZone -app = Flask("Bewässerungssystem") -nav = Navigation(app) -nav.Bar('top', [ - nav.Item('Dashboard', 'showDashboard'), - nav.Item('Bewässerungszonen', 'showZones'), - nav.Item('Sperrzeiteneinstellung', 'showTimes'), - nav.Item('Systemeinestellungen', 'showSystem') - #nav.Item('Gfg', 'gfg', {'page': 5}), #(example with pages) -]) -#Example Route with pages: -#@app.route('/gfg/') -#def gfg(page): -# return render_template('gfg.html', page=page) +def startWebserver(port, translater, zones): -@app.route('/') -def startPage(): - return redirect(url_for('showDashboard')) -@app.route('/dashboard') -def showDashboard(): - return render_template('dashboard.html') + app = Flask("Bewässerungssystem") + nav = Navigation(app) -@app.route('/zonen') -def showZones(): - return render_template('zones.html') + nav.Bar('top', [ + nav.Item(translater.getTranslation('Dashboard'), 'showDashboard'), + nav.Item(translater.getTranslation('irrigation zones'), 'showZones'), + nav.Item(translater.getTranslation('blocking times'), 'showTimes'), + nav.Item(translater.getTranslation('system settings'), 'showSystem') + #nav.Item('Gfg', 'gfg', {'page': 5}), #(example with pages) + ]) -@app.route('/times') -def showTimes(): - return render_template('times.html') + #Example Route with pages: + #@app.route('/gfg/') + #def gfg(page): + # return render_template('gfg.html', page=page) -@app.route('/system') -def showSystem(): - return render_template('system.html') + + @app.route('/') + def startPage(): + return redirect(url_for('showDashboard')) + + @app.route('/dashboard') + def showDashboard(): + return render_template('dashboard.html', translater=translater, zones=zones) + + @app.route('/zones') + @app.route('/zones/') + def showZones(zoneNumber=False): + if(zoneNumber): + return render_template('zone.html', translater=translater, zone=getZone(zones, zoneNumber)) + else: + return render_template('zones.html', translater=translater, zones=zones) + + + @app.route('/times') + def showTimes(): + return render_template('times.html', translater=translater) + + @app.route('/system') + def showSystem(): + return render_template('system.html', translater=translater) + + app.run(debug=True, port=port) if __name__ == "__main__": - app.run(debug=True, port=80) \ No newline at end of file + zones = loadZones() + translater = Translater(Language.ENGLISH) + startWebserver(80, translater, zones) \ No newline at end of file diff --git a/Webserver/static/Styles/dashboard.css b/Webserver/static/Styles/dashboard.css new file mode 100644 index 0000000..857f94e --- /dev/null +++ b/Webserver/static/Styles/dashboard.css @@ -0,0 +1,141 @@ +#content{ + display: grid; + grid-template-columns: repeat(3, 1fr); + /* grid-template-rows: repeat( {{ zones|length }} , minmax(150px, auto)); moved to content div to use jinja */ + grid-gap: 30px; + margin: 0 auto; +} +.zone{ + position: relative; + background: green; + color: white; + font-size: larger; + padding-left: 30px; + padding-bottom: 30px; + padding-right: 30px; +} +.zone a{ + color: inherit; + text-decoration: inherit; +} + +.zone:hover{ + animation: scale 0.5s linear 0.0s normal both; +} + + +@keyframes scale{ + 0% {transform: scale3d(100%, 100%, 100%);} + 100% {transform: scale3d(107%, 120%, 100%);} +} + +.zone h3{ + padding-top: 25px; + padding-bottom: 25px; +} +.zone_number{ + position: absolute; + top: 15px; + right: 30px;; +} + +.zone table{ + table-layout: auto; + width: 100%; +} + + +td.icon{ + text-align: left; + width: 30px; +} +td.property{ + text-align: left; +} +td.value{ + text-align: left; + position: relative; +} + +.state{ + display: inline; +} +.on_off{ + display: none; + color: green; + position: absolute; + background: #bbb; + padding-right: 50px; + padding-left: 5px; + top: -15px; + left: 0px; + z-index: 1; +} +.state:hover + .on_off, .on_off:hover{ + display: inline; +} + + + + +.outer_dot { + height: 30px; + width: 30px; + background-color: #bbb; + border-radius: 50%; + display: inline-block; + margin-right: 10px; + z-index: 1; +} +.inner_icon{ + color: black; + font-size: 16px; + font-weight: bold; + font-family: 'Gill Sans', 'Gill Sans MT', Calibri, 'Trebuchet MS', sans-serif; + height: 15px; + width: 15px; + margin-left: 7.5px; + margin-top: 7.5px; + border-radius: 50%; + display: inline-block; + z-index: 2; +} +.dot_green { + background-color: green; +} +.dot_red { + background-color: red; +} + +@media screen and (min-width: 2051px){ + .zone:nth-child(even){ + background: blue; + } +} + +@media screen and (max-width: 2050px) and (min-width: 1351px){ + #content{ + grid-template-columns: repeat(2, 1fr); + } + .zone:nth-child(4n){ + background: blue; + } + .zone:nth-child(4n+1){ + background: blue; + } +} + +@media screen and (max-width: 1350px){ + #content{ + grid-template-columns: repeat(1, 1fr); + } + .zone{ + max-width: 600px; + } + .zone:nth-child(even){ + background: blue; + } +} + + + diff --git a/Webserver/static/Styles/header.css b/Webserver/static/Styles/header.css index 3e8281a..570ac50 100644 --- a/Webserver/static/Styles/header.css +++ b/Webserver/static/Styles/header.css @@ -4,13 +4,14 @@ header{ position: sticky; left: 0px; top: 0px; + z-index: 20; } nav{ - z-index: 1; + z-index: 21; position: absolute; top: 0px; - right: 20px; + right: 25px; } nav ul li{ @@ -21,13 +22,13 @@ nav ul li a{ white-space: nowrap; text-decoration: none; color: white; - background-color: green; + background-color: blue; padding: 5px; margin: 10px; } nav ul li a:hover{ - background-color: darkgreen; + background-color: darkblue; } .active{ diff --git a/Webserver/static/Styles/main.css b/Webserver/static/Styles/main.css index e626abb..453347f 100644 --- a/Webserver/static/Styles/main.css +++ b/Webserver/static/Styles/main.css @@ -4,3 +4,9 @@ main{ margin-left: auto; margin-right: auto; } + +h2{ + font-family: "Century Gothic", CenturyGothic, AppleGothic, sans-serif; + text-transform: uppercase; + margin-bottom: 2em; +} \ No newline at end of file diff --git a/Zone.py b/Zone.py new file mode 100644 index 0000000..43b5fa4 --- /dev/null +++ b/Zone.py @@ -0,0 +1,25 @@ +class Zone: + def __init__(self, number=0, name="", actualValue="100", setValue="0", autoMode=False, state=False): + self.number = number + self.name = name + self.actualValue = actualValue + self.setValue = setValue + self.autoMode = autoMode #False = manual, True = automatic + self.state = state #True = off, True = on + + + def refreshStatus(self): + if(self.AutoMode): + if(self.actualValue < self.setValue): + self.state = True + else: + self.state = False + + def getStatus(self): + self.refreshStatus() + return self.state + +def getZone(zones, number): + for zone in zones: + if(zone.number == number): + return zone \ No newline at end of file