using System;
using System.Drawing;
using System.Text;
using System.Windows.Forms;
using uPLibrary.Networking.M2Mqtt;
using uPLibrary.Networking.M2Mqtt.Messages;
using Newtonsoft.Json;
using System.Globalization;
using LiveCharts;
using LiveCharts.Wpf;

namespace Wetterstation
{
    public partial class Hintergrund : Form
    {
        //Variable fuer den Debugmodues
        private bool debug = false;

        private MqttClient myClient;

        //Objekt für die Settings erstellen
        SettingsModel WeatherstationSettings = new SettingsModel();

        String graphLastTimestamp = null;

        //Sensorobjekte erstellen (fuer jede Messtelle und fuer Openweathermap)
        Sensor node1In = new Sensor();
        Sensor node1Out = new Sensor();
        Sensor owm = new Sensor();

        
        public Hintergrund()
        {
            InitializeComponent();

            //Settings aus der Datenbank laden
            WeatherstationSettings = SqliteDataAccess.LoadWeatherstationSettings();
            lbCity.Text = WeatherstationSettings.city;
            
            // Start a timer for date and time
            Timer t = new Timer();
            t.Interval = 1000;
            t.Tick += new EventHandler(this.t_DateTime);
            t.Start();

            mqttStart();
            updateChart();
        }

        //Historiediagramm auf den neuesten Stand bringen
        private void updateChart()
        {
            cartesianChart1.Series = new SeriesCollection
            {
                new LineSeries
                {
                    Title = "Temperatur",
                    Values = new ChartValues<double> {},
                    ScalesYAt = 0,
                    PointGeometry = null
                },
                new LineSeries
                {
                    Title = "Luftfeuchtigkeit",
                    Values = new ChartValues<int> {},
                    ScalesYAt = 1,
                    PointGeometry = null
                },
                new LineSeries
                {
                    Title = "Luftdruck",
                    Values = new ChartValues<int> {},
                    ScalesYAt = 2,
                    PointGeometry = null
                },
                new LineSeries
                {
                    Title = "Wind Geschwindigkeit",
                    Values = new ChartValues<double> {},
                    ScalesYAt = 3,
                    PointGeometry = null
                }
            };

            cartesianChart1.AxisY.Add(new Axis
            {
                LabelFormatter = val => val + " °C",
                IsEnabled = false,
                Position = AxisPosition.LeftBottom
            });

            cartesianChart1.AxisY.Add(new Axis
            {
                LabelFormatter = val => val + " %",
                IsEnabled = false,
                Position = AxisPosition.LeftBottom
            });

            cartesianChart1.AxisY.Add(new Axis
            {
                LabelFormatter = val => val + " hPa",
                IsEnabled = true,
                Position = AxisPosition.RightTop
            });

            cartesianChart1.AxisY.Add(new Axis
            {
                LabelFormatter = val => val + " ms",
                IsEnabled = false,
                Position = AxisPosition.LeftBottom
            });

            cartesianChart1.AxisX.Add(new Axis
            {
                Title = "Uhrzeit",
                Labels = new[] { "" }
            });

            cartesianChart1.LegendLocation = LegendLocation.Right;

            //modifying the series collection will animate and update the chart
            //cartesianChart1.Series.Add(new LineSeries
            //{
            //    Values = new ChartValues<double> { 5, 3, 2, 4, 5 },
            //    LineSmoothness = 0, //straight lines, 1 really smooth lines
            //});

            //modifying any series values will also animate and update the chart
        }

        //Uhreit und Datum bestimmen und anzeigen
        private void t_DateTime(object sender, EventArgs e)
        {
            lbUhr.Text = DateTime.Now.ToLongTimeString();
            lbDatum.Text = DateTime.Now.ToShortDateString();
        }
        // MQTT connect
        public void mqttStart()
        {
            String topic_publish = "/wetterstation/backend/" + WeatherstationSettings.frontendId + "/";
            String topic_subscribe = "/wetterstation/frontend/" + WeatherstationSettings.frontendId + "/#";

            System.Console.WriteLine("Mqtt wird gestartet ....");
            // Create Client instance
            this.myClient = new MqttClient("mqtt.itstall.de");

            // Register to message received
            myClient.MqttMsgPublishReceived += client_recievedMessage;

            string clientId = Guid.NewGuid().ToString();
            this.myClient.Connect("", "wetterstation", "wetterstation");

            // Subscribe to topic
            this.myClient.Subscribe(new String[] { topic_subscribe }, new byte[] { MqttMsgBase.QOS_LEVEL_EXACTLY_ONCE });

            this.myClient.Publish(topic_publish, Encoding.UTF8.GetBytes("Request_frontend"));
        }
        // Send message per MQTT
        public void msgPublish(String topic, String message)
        {
            Console.Write("Sending via MQTT: ");
            Console.Write("Topic: " + topic);
            Console.WriteLine("Message: " + message);
            this.myClient.Publish(topic, Encoding.UTF8.GetBytes(message));
        }
        // Got message from MQTT
        private void client_recievedMessage(object sender, MqttMsgPublishEventArgs e)
        {
            // Handle message received
            var message = System.Text.Encoding.Default.GetString(e.Message);

            if (e.Topic.Equals(WeatherstationSettings.mqtt_topic_frontend + WeatherstationSettings.frontendId + "/weather"))
            {
                this.updateFormWeather(message);
            }
            else if (e.Topic.Equals(WeatherstationSettings.mqtt_topic_frontend + WeatherstationSettings.frontendId + "/forecast"))
            {
                this.updateFormForecast(message);
            }
            else if (e.Topic.Equals(WeatherstationSettings.mqtt_topic_frontend + WeatherstationSettings.frontendId + "/forecastNext"))
            {
                this.updateFormForecastNext(message);
            }
            else if (e.Topic.Equals(WeatherstationSettings.mqtt_topic_frontend + WeatherstationSettings.frontendId + "/sensors"))
            {
                this.updateFormSensors(message);
            }
            else if (e.Topic.Equals(WeatherstationSettings.mqtt_topic_frontend + WeatherstationSettings.frontendId + "/graph"))
            {
                Console.WriteLine(WeatherstationSettings.mqtt_topic_frontend + WeatherstationSettings.frontendId + "/graph");
                this.updateFormChart(message);
            }
            
        }
        // Update graph on frontend
        public void updateFormChart(String message)
        {
            double temp;
            int humidity;
            int pressure;
            double windSpeed;
            dynamic weatherData = JsonConvert.DeserializeObject(message.ToString());

            if (graphLastTimestamp == null)
            {
                //Json String aufdroeseln und Werte rotierend abspeichern
                int i = 0;
                foreach (var result in weatherData["results"][0]["series"][0]["values"])
                {
                    if (result[2] == null) temp = 0;
                    else temp = result[1];
                    if (result[1] == null) humidity = 0;
                    else humidity = result[2];
                    if (result[3] == null) pressure = 0;
                    else pressure = result[3];
                    if (result[4] == null) windSpeed = 0;
                    else windSpeed = result[4];

                    cartesianChart1.Series[0].Values.Add(Math.Round(temp, 1));
                    cartesianChart1.Series[1].Values.Add(humidity);
                    cartesianChart1.Series[2].Values.Add(pressure);
                    cartesianChart1.Series[3].Values.Add(Math.Round(windSpeed, 1));
                }
                graphLastTimestamp = weatherData["results"][0]["series"][0]["values"][96][0].ToString();
            }
            else
            {
                //Prüfen ob sich Timestamp geändert hat
                if (graphLastTimestamp != weatherData["results"][0]["series"][0]["values"][96][0].ToString())
                {
                    cartesianChart1.Series[0].Values.RemoveAt(0);
                    cartesianChart1.Series[1].Values.RemoveAt(0);
                    cartesianChart1.Series[2].Values.RemoveAt(0);
                    cartesianChart1.Series[3].Values.RemoveAt(0);

                    //prüfen ob Daten geliefert wurden. Wenn icht Wert auf 0 ansonsten auf gelieferten Wert
                    if (weatherData["results"][0]["series"][0]["values"][96][1] == null) temp = 0;
                    else temp = weatherData["results"][0]["series"][0]["values"][96][1];
                    if (weatherData["results"][0]["series"][0]["values"][96][2] == null) humidity = 0;
                    else humidity = weatherData["results"][0]["series"][0]["values"][96][2];
                    if (weatherData["results"][0]["series"][0]["values"][96][3] == null) pressure = 0;
                    else pressure = weatherData["results"][0]["series"][0]["values"][96][3];
                    if (weatherData["results"][0]["series"][0]["values"][96][4] == null) windSpeed = 0;
                    else windSpeed = weatherData["results"][0]["series"][0]["values"][96][4];

                    //Container mit Werten fuellen
                    cartesianChart1.Series[0].Values.Add(Math.Round(temp, 1));
                    cartesianChart1.Series[1].Values.Add(humidity);
                    cartesianChart1.Series[2].Values.Add(pressure);
                    cartesianChart1.Series[3].Values.Add(Math.Round(windSpeed, 1));
                    
                    graphLastTimestamp = weatherData["results"][0]["series"][0]["values"][96][0].ToString();
                }
            }
        }
        // Update general weather objects on frontend
        public void updateFormWeather(String message)
        {
            Console.WriteLine("Entered updateFormWeather");
            Console.WriteLine(message);
            try
            {
                //JSON Daten aufdroesseln 
                dynamic weatherData = JsonConvert.DeserializeObject(message.ToString());
                //Wenn keine Daten von den Sensoren vorliegen nimm die Werte von Openweathermap
                if (!node1Out.temperature)
                {
                    lbAussenTemp.Invoke(new Action(() => { lbAussenTemp.Text = weatherData.temp + " °C"; }));
                    lbTempOutMin.Invoke(new Action(() => { lbTempOutMin.Text = weatherData.tempMin + " °C"; }));
                    lbTempOutMax.Invoke(new Action(() => { lbTempOutMax.Text = weatherData.tempMax + " °C"; }));
                    owm.Temperatures = weatherData.temp;

                    //Tendenzpfeil entsprechend setzen u.o. ausblenden
                    if (owm.tempTendenz() == -1) pbTendenzTempOut.Invoke(new Action(() => { pbTendenzTempOut.Visible = false; }));
                    else pbTendenzTempOut.Invoke(new Action(() => { pbTendenzTempOut.Visible = true; }));
                    pbTendenzTempOut.Invoke(new Action(() => { pbTendenzTempOut.Image = RotateImage((Bitmap)global::Wetterstation.Properties.Resources.ResourceManager.GetObject("Tendenz"), owm.tempTendenz()); }));
                }
                if(!node1Out.humidity)
                {
                    lbLuftfeuchtAussen.Invoke(new Action(() => { lbLuftfeuchtAussen.Text = weatherData.humidity + " %"; }));
                    owm.Humiditys = (double)weatherData.humidity;
                    if (owm.humidityTendenz() == -1) lbTendenzHumidityOut.Invoke(new Action(() => { lbTendenzHumidityOut.Visible = false; }));
                    else lbTendenzHumidityOut.Invoke(new Action(() => { lbTendenzHumidityOut.Visible = true; }));
                    lbTendenzHumidityOut.Invoke(new Action(() => { lbTendenzHumidityOut.Image = RotateImage((Bitmap)global::Wetterstation.Properties.Resources.ResourceManager.GetObject("Tendenz"), owm.humidityTendenz()); }));
                }
                if(!node1Out.windSpeed)
                {
                    lbWindSpeed.Invoke(new Action(() => { lbWindSpeed.Text = weatherData.windSpeed + " ms"; }));
                }
                if (!node1Out.windDegre)
                {
                    lbWindricht.Invoke(new Action(() => { lbWindricht.Text = weatherData.windDeg + " °"; }));
                    pbKompassrose.Invoke(new Action(() => { pbKompassrose.Image = RotateImage((Bitmap)global::Wetterstation.Properties.Resources.ResourceManager.GetObject("WindRose_neu"), (int)weatherData.windDeg); }));
                }
                if (!node1Out.pressure && !node1In.pressure)
                {
                    lbLuftdruck.Invoke(new Action(() => { lbLuftdruck.Text = weatherData.pressure + " mbar"; }));
                    owm.Pressures = (double)weatherData.pressure;
                    if (owm.pressureTendenz() == -1) pbTendenzPressure.Invoke(new Action(() => { pbTendenzPressure.Visible = false; }));
                    else pbTendenzPressure.Invoke(new Action(() => { pbTendenzPressure.Visible = true; }));
                    pbTendenzPressure.Invoke(new Action(() => { pbTendenzPressure.Image = RotateImage((Bitmap)global::Wetterstation.Properties.Resources.ResourceManager.GetObject("Tendenz"), owm.pressureTendenz()); }));
                }
                if(!node1Out.rain)
                {
                    lbRain1h.Invoke(new Action(() => { lbRain1h.Text = weatherData.rain1h + " mm"; }));
                }
                lbRain3h.Invoke(new Action(() => { lbRain3h.Text = weatherData.rain3h + " mm"; }));
                if (!node1Out.snow)
                {
                    lbSnow1h.Invoke(new Action(() => { lbSnow1h.Text = weatherData.snow1h + " mm"; }));
                }
                lbSnow3h.Invoke(new Action(() => { lbSnow3h.Text = weatherData.snow3h + " mm"; }));
            }
            catch (Exception ignored) {
                Console.WriteLine(ignored.Message);
            }
        }
        // Rotate an image
        private Bitmap RotateImage(Bitmap bmp, float angle)
        {
            float height = bmp.Height;
            float width = bmp.Width;
            int hypotenuse = System.Convert.ToInt32(System.Math.Floor(Math.Sqrt(height * height + width * width)));
            Bitmap rotatedImage = new Bitmap(hypotenuse, hypotenuse);
            using (Graphics g = Graphics.FromImage(rotatedImage))
            {
                g.TranslateTransform((float)rotatedImage.Width / 2, (float)rotatedImage.Height / 2); //set the rotation point as the center into the matrix
                g.RotateTransform(angle); //rotate
                g.TranslateTransform(-(float)rotatedImage.Width / 2, -(float)rotatedImage.Height / 2); //restore rotation point into the matrix
                g.DrawImage(bmp, (hypotenuse - width) / 2, (hypotenuse - height) / 2, width, height);
            }
            return rotatedImage;
        }
        // Update forecast images
        public void updateFormForecast(String message)
        {
            Console.WriteLine("Entered updateFormForecast");
            try
            {
                dynamic weatherData = JsonConvert.DeserializeObject(message.ToString());

                if (weatherData[0].icon1 != null) lbForecastImage1.Invoke(new Action(() => { lbForecastImage1.Image = global::Wetterstation.Properties.Resources.ResourceManager.GetObject("_" + weatherData[0].icon1 + "_2x"); }));
                lbForecastTemp1.Invoke(new Action(() => { lbForecastTemp1.Text = weatherData[0].temp + " °C"; }));
                lbForecastDay1.Invoke(new Action(() => { lbForecastDay1.Text = getDayFromDateString(weatherData[0].from.ToString()); }));

                if (weatherData[1].icon1 != null) lbForecastImage2.Invoke(new Action(() => { lbForecastImage2.Image = global::Wetterstation.Properties.Resources.ResourceManager.GetObject("_" + weatherData[1].icon1 + "_2x"); }));
                lbForecastTemp2.Invoke(new Action(() => { lbForecastTemp2.Text = weatherData[1].temp + " °C"; }));
                lbForecastDay2.Invoke(new Action(() => { lbForecastDay2.Text = getDayFromDateString(weatherData[1].from.ToString()); }));

                if (weatherData[2].icon1 != null) lbForecastImage3.Invoke(new Action(() => { lbForecastImage3.Image = global::Wetterstation.Properties.Resources.ResourceManager.GetObject("_" + weatherData[2].icon1 + "_2x"); }));
                lbForecastTemp3.Invoke(new Action(() => { lbForecastTemp3.Text = weatherData[2].temp + " °C"; })); lbForecastDay1.Invoke(new Action(() => { lbForecastDay1.Text = getDayFromDateString(weatherData[0].from.ToString()); }));
                lbForecastDay3.Invoke(new Action(() => { lbForecastDay3.Text = getDayFromDateString(weatherData[2].from.ToString()); }));

                if (weatherData[3].icon1 != null) lbForecastImage4.Invoke(new Action(() => { lbForecastImage4.Image = global::Wetterstation.Properties.Resources.ResourceManager.GetObject("_" + weatherData[3].icon1 + "_2x"); }));
                lbForecastTemp4.Invoke(new Action(() => { lbForecastTemp4.Text = weatherData[3].temp + " °C"; }));
                lbForecastDay4.Invoke(new Action(() => { lbForecastDay4.Text = getDayFromDateString(weatherData[3].from.ToString()); }));

                if (weatherData[4].icon1 != null) lbForecastImage5.Invoke(new Action(() => { lbForecastImage5.Image = global::Wetterstation.Properties.Resources.ResourceManager.GetObject("_" + weatherData[4].icon1 + "_2x"); }));
                lbForecastTemp5.Invoke(new Action(() => { lbForecastTemp5.Text = weatherData[4].temp + " °C"; }));
                lbForecastDay5.Invoke(new Action(() => { lbForecastDay5.Text = getDayFromDateString(weatherData[4].from.ToString()); }));
            }
            catch (Exception ignored) { }
        }
        // Update next forecast
        public void updateFormForecastNext(String message)
        {
            Console.WriteLine("Entered updateFormForecastNext");
            try
            {
                dynamic weatherData = JsonConvert.DeserializeObject(message.ToString());

                if (weatherData.icon1 != null) pbForecastNext.Invoke(new Action(() => { pbForecastNext.Image = global::Wetterstation.Properties.Resources.ResourceManager.GetObject("_" + weatherData.icon1 + "_2x"); }));
                lbForecastNextFrom.Invoke(new Action(() => { lbForecastNextFrom.Text = getTimeFromDateString(weatherData.from.ToString()); }));
                lbForecastNextClouds.Invoke(new Action(() => { lbForecastNextClouds.Text = weatherData.clouds; }));
                lbForecastNextHumidity.Invoke(new Action(() => { lbForecastNextHumidity.Text = weatherData.humidity; }));
                lbForecastNextPressure.Invoke(new Action(() => { lbForecastNextPressure.Text = weatherData.pressure; }));
                lbForecastNextRain.Invoke(new Action(() => { lbForecastNextRain.Text = weatherData.rain3h; }));
                lbForecastNextSnow.Invoke(new Action(() => { lbForecastNextSnow.Text = weatherData.snow3h; }));
                lbForecastNextTemp.Invoke(new Action(() => { lbForecastNextTemp.Text = weatherData.temp; }));
                lbForecastNextWindSpeed.Invoke(new Action(() => { lbForecastNextWindSpeed.Text = weatherData.windSpeed; }));
            }
            catch (Exception ignored) { }
        }
        public String getTimeFromDateString(String strDate)
        {
            DateTime dt = DateTime.ParseExact(strDate, "yyyy-MM-dd HH:mm:ss", CultureInfo.InvariantCulture);
            CultureInfo culture = new CultureInfo("de-DE");
            return dt.ToString("HH:mm");
        }
        public String getDayFromDateString(String strDate)
        {
            DateTime dt = DateTime.ParseExact(strDate, "yyyy-MM-dd HH:mm:ss", CultureInfo.InvariantCulture);
            CultureInfo culture = new CultureInfo("de-DE");
            return culture.DateTimeFormat.GetDayName(dt.DayOfWeek).Substring(0, 2).ToString();
        }
        public void updateFormSensors(String message)
        {
            Console.WriteLine("Entered updateFormSensors");
            Console.WriteLine(message);
            try
            {
                dynamic weatherData = JsonConvert.DeserializeObject(message.ToString());
                if (weatherData[0]["client"] == WeatherstationSettings.node1Id && weatherData[0]["sensor"] == WeatherstationSettings.node1Innen)
                {
                    node1In.host = weatherData[0]["client"];
                    node1In.name = weatherData[0]["sensor"];
                }
                if (weatherData[0]["client"] == WeatherstationSettings.node1Id && weatherData[0]["sensor"] == WeatherstationSettings.node1Aussen)
                {
                    node1Out.host = weatherData[0]["client"];
                    node1Out.name = weatherData[0]["sensor"];
                }
                if (weatherData[0]["client"] == node1In.host && weatherData[0]["sensor"] == node1In.name && weatherData[0]["temperature"] != null)
                {
                    node1In.temperature = true;
                    if (node1In.tempMin == 0) node1In.tempMin = weatherData[0]["temperature"];
                    if (node1In.tempMax == 0) node1In.tempMax = weatherData[0]["temperature"];
                    if ((double)weatherData[0]["temperature"] > node1In.tempMax) node1In.tempMax = weatherData[0]["temperature"];
                    if ((double)weatherData[0]["temperature"] < node1In.tempMin) node1In.tempMin = weatherData[0]["temperature"];
                    lbInnenTemp.Invoke(new Action(() => { lbInnenTemp.Text = weatherData[0]["temperature"] + " °C"; }));
                    lbTempInMin.Invoke(new Action(() => { lbTempInMin.Text = node1In.tempMin + " °C"; }));
                    lbTempInMax.Invoke(new Action(() => { lbTempInMax.Text = node1In.tempMax + " °C"; }));
                    node1In.Temperatures = (double)weatherData[0]["temperature"];
                    if (node1In.tempTendenz() == -1) pbTendenzTempIn.Invoke(new Action(() => { pbTendenzTempIn.Visible = false; }));
                    else pbTendenzTempIn.Invoke(new Action(() => { pbTendenzTempIn.Visible = true; }));
                    pbTendenzTempIn.Invoke(new Action(() => { pbTendenzTempIn.Image = RotateImage((Bitmap)global::Wetterstation.Properties.Resources.ResourceManager.GetObject("Tendenz"), node1In.tempTendenz()); }));
                }
                if (weatherData[0]["client"] == node1In.host && weatherData[0]["sensor"] == node1In.name && weatherData[0]["humidity"] != null)
                {
                    node1In.humidity = true;
                    lbLuftFeuchtInnen.Invoke(new Action(() => { lbLuftFeuchtInnen.Text = weatherData[0]["humidity"] + " %"; }));
                    node1Out.Humiditys = (double)weatherData[0]["humidity"];
                    if (node1In.humidityTendenz() == -1) lbTendenzHumidityIn.Invoke(new Action(() => { lbTendenzHumidityIn.Visible = false; }));
                    else lbTendenzHumidityIn.Invoke(new Action(() => { lbTendenzHumidityIn.Visible = true; }));
                    lbTendenzHumidityIn.Invoke(new Action(() => { lbTendenzHumidityIn.Image = RotateImage((Bitmap)global::Wetterstation.Properties.Resources.ResourceManager.GetObject("Tendenz"), node1In.humidityTendenz()); }));
                }
                if (weatherData[0]["client"] == node1In.host && weatherData[0]["sensor"] == node1In.name && weatherData[0]["pressure"] != null)
                {
                    node1In.pressure = true;
                    lbLuftdruck.Invoke(new Action(() => { lbLuftdruck.Text = weatherData[0]["pressure"] + " hPa"; }));
                    node1In.Pressures = (double)weatherData[0]["pressure"];
                    if (node1In.pressureTendenz() == -1) pbTendenzPressure.Invoke(new Action(() => { pbTendenzPressure.Visible = false; }));
                    else pbTendenzPressure.Invoke(new Action(() => { pbTendenzPressure.Visible = true; }));
                    pbTendenzPressure.Invoke(new Action(() => { pbTendenzPressure.Image = RotateImage((Bitmap)global::Wetterstation.Properties.Resources.ResourceManager.GetObject("Tendenz"), node1In.pressureTendenz()); }));
                }
                if (weatherData[0]["client"] == node1Out.host && weatherData[0]["sensor"] == node1Out.name && weatherData[0]["temperature"] != null)
                {
                    node1Out.temperature = true;
                    if (node1In.tempMin == 0) node1Out.tempMin = weatherData[0]["temperature"];
                    if (node1In.tempMax == 0) node1Out.tempMax = weatherData[0]["temperature"];
                    if ((double)weatherData[0]["temperature"] > node1Out.tempMax) node1Out.tempMax = weatherData[0]["temperature"];
                    if ((double)weatherData[0]["temperature"] < node1Out.tempMin) node1Out.tempMin = weatherData[0]["temperature"];
                    lbAussenTemp.Invoke(new Action(() => { lbAussenTemp.Text = weatherData[0]["temperature"] + " °C"; }));
                    lbTempOutMin.Invoke(new Action(() => { lbTempOutMin.Text = node1Out.tempMin + " °C"; }));
                    lbTempOutMax.Invoke(new Action(() => { lbTempOutMax.Text = node1Out.tempMax + " °C"; }));
                    node1Out.Temperatures = (double)weatherData[0]["temperature"];
                    if (node1Out.tempTendenz() == -1) pbTendenzTempOut.Invoke(new Action(() => { pbTendenzTempOut.Visible = false; }));
                    else pbTendenzTempOut.Invoke(new Action(() => { pbTendenzTempOut.Visible = true; }));
                    pbTendenzTempOut.Invoke(new Action(() => { pbTendenzTempOut.Image = RotateImage((Bitmap)global::Wetterstation.Properties.Resources.ResourceManager.GetObject("Tendenz"), node1Out.tempTendenz()); }));
                }
                if (weatherData[0]["client"] == node1Out.host && weatherData[0]["sensor"] == node1Out.name && weatherData[0]["humidity"] != null)
                {
                    node1Out.humidity = true;
                    lbLuftfeuchtAussen.Invoke(new Action(() => { lbLuftfeuchtAussen.Text = weatherData[0]["humidity"] + " %"; }));
                    node1Out.Humiditys = (double)weatherData[0]["humidity"];
                    if (node1Out.humidityTendenz() == -1) lbTendenzHumidityOut.Invoke(new Action(() => { lbTendenzHumidityOut.Visible = false; }));
                    else lbTendenzHumidityOut.Invoke(new Action(() => { lbTendenzHumidityOut.Visible = true; }));
                    lbTendenzHumidityOut.Invoke(new Action(() => { lbTendenzHumidityOut.Image = RotateImage((Bitmap)global::Wetterstation.Properties.Resources.ResourceManager.GetObject("Tendenz"), node1Out.humidityTendenz()); }));
                }

            }
            catch (Exception ignored) {
                Console.WriteLine(ignored.Message);
            }
        }
        public void updateFormComplete()
        {
            WeatherstationSettings = SqliteDataAccess.LoadWeatherstationSettings();
            lbCity.Text = WeatherstationSettings.city;
        }
        public void updateSettings2Mqtt()
        {
            Console.WriteLine(JsonConvert.SerializeObject(WeatherstationSettings).ToString());
            this.msgPublish(WeatherstationSettings.mqtt_topic_backend + "settings", JsonConvert.SerializeObject(WeatherstationSettings).ToString());
        }
        private void BtSystemKnopf_Click(object sender, EventArgs e)
        {
            Form settings = new Settings();
            // Settings als Dialog starten, dann wird das Frontend geblockt und auf abschluss gewartet
            settings.ShowDialog();
            updateFormComplete();
            // MQTT beenden und Verbindung neu aufbauen
            this.myClient.Disconnect();
            this.mqttStart();
            // Neue Einstellungen an Backend senden
            this.updateSettings2Mqtt();
        }
        private void Hintergrund_FormClosed(object sender, FormClosedEventArgs e)
        {
            this.myClient.Disconnect();
            Application.Exit();
        }
    }
}