diff --git a/source/class/Pqooxdoo/Application.js b/source/class/Pqooxdoo/Application.js index b0be2d4d80cf6055cd5a3c4dfd862b534a642163..719fc2fd8b833f25095a4a7af3214459b7500b21 100644 --- a/source/class/Pqooxdoo/Application.js +++ b/source/class/Pqooxdoo/Application.js @@ -6,7 +6,7 @@ qx.Class.define("Pqooxdoo.Application", { super.main(); let root = this.getRoot(); - root.setBackgroundColor("#87CEEB"); + root.setBackgroundColor("#87CEEB"); // Couleur de fond par défaut let container = new qx.ui.container.Composite(new qx.ui.layout.VBox(10)).set({ padding: 20, @@ -36,10 +36,28 @@ qx.Class.define("Pqooxdoo.Application", { let txtVille = new qx.ui.form.TextField().set({ placeholder: "Entrez une ville", width: 200 }); let btnAfficher = new qx.ui.form.Button("Obtenir la météo"); + // Historique de recherche + let historyContainer = new qx.ui.container.Composite(new qx.ui.layout.VBox(5)).set({ + padding: 10, + width: 200 + }); + + let historyLabel = new qx.ui.basic.Label("Historique de recherche").set({ + font: new qx.bom.Font(14, ["Arial", "sans-serif"]), + textColor: "#FFFFFF", + visibility: "hidden" // Masqué par défaut + }); + + let historyComboBox = new qx.ui.form.ComboBox().set({ width: 200, visibility: "hidden" }); // Masqué par défaut + + historyContainer.add(historyLabel); + historyContainer.add(historyComboBox); + searchContainer.add(title); searchContainer.add(dateLabel); searchContainer.add(txtVille); searchContainer.add(btnAfficher); + searchContainer.add(historyContainer); let weatherContainer = new qx.ui.container.Composite(new qx.ui.layout.VBox(10)).set({ padding: 10, @@ -96,14 +114,36 @@ qx.Class.define("Pqooxdoo.Application", { let doc = this.getRoot(); doc.add(container, { edge: 0 }); + let searchHistory = []; + btnAfficher.addListener("execute", () => { let ville = txtVille.getValue(); if (ville) { this._fetchWeatherData(ville, lblResultat, lblResultat1, imgWeather, lblHumidity, lblWind, lblPressure, lblTempMinMax, daysContainer); + if (!searchHistory.includes(ville)) { + searchHistory.push(ville); + historyComboBox.add(new qx.ui.form.ListItem(ville)); + } + + // Afficher l'historique après la première recherche + if (historyComboBox.getVisibility() === "hidden") { + historyLabel.setVisibility("visible"); + historyComboBox.setVisibility("visible"); + } } else { lblResultat.setValue("Veuillez entrer une ville"); } }); + + historyComboBox.addListener("changeSelection", (e) => { + let selectedItem = e.getData()[0]; + if (selectedItem) { + txtVille.setValue(selectedItem.getLabel()); + this._fetchWeatherData(selectedItem.getLabel(), lblResultat, lblResultat1, imgWeather, lblHumidity, lblWind, lblPressure, lblTempMinMax, daysContainer); + } + }); + + this._getLocationAndFetchWeather(lblResultat, lblResultat1, imgWeather, lblHumidity, lblWind, lblPressure, lblTempMinMax, daysContainer); }, _getFormattedDate(dayOffset = 0) { @@ -130,6 +170,12 @@ qx.Class.define("Pqooxdoo.Application", { lblWind.setValue(`Vent: ${response.wind.speed} m/s`); lblPressure.setValue(`Pression: ${response.main.pressure} hPa`); imgWeather.setSource(`https://openweathermap.org/img/wn/${response.weather[0].icon}@2x.png`); + + // Changer la couleur du fond en fonction de la météo + this._setBackgroundColorBasedOnWeather(response.weather[0].main); + }, this); + req.addListener("error", function (e) { + lblResultat.setValue("Erreur lors de la récupération des données"); }, this); req.send(); @@ -163,8 +209,8 @@ qx.Class.define("Pqooxdoo.Application", { let weatherIcon = new qx.ui.basic.Image().set({ source: `https://openweathermap.org/img/wn/${data.weather[0].icon}@2x.png`, scale: true, - width: 60, - height: 60 + width: 70, + height: 70 }); let tempLabel = new qx.ui.basic.Label(`${data.main.temp}°C`).set({ @@ -178,7 +224,126 @@ qx.Class.define("Pqooxdoo.Application", { daysContainer.add(dayBox); }); }, this); + forecastReq.addListener("error", function (e) { + lblResultat.setValue("Erreur lors de la récupération des prévisions"); + }, this); + forecastReq.send(); + }, + + _setBackgroundColorBasedOnWeather(weatherCondition) { + let root = this.getRoot(); + let backgroundColor = ""; + + switch (weatherCondition) { + case "Clear": + backgroundColor = "#87CEEB"; // Bleu clair pour le soleil + break; + case "Clouds": + backgroundColor = "#778899"; // Gris pour les nuages + break; + case "Rain": + backgroundColor = "#4682B4"; // Bleu plus sombre pour la pluie + break; + case "Snow": + backgroundColor = "#F0F8FF"; // Blanc pour la neige + break; + case "Thunderstorm": + backgroundColor = "#2F4F4F"; // Gris foncé pour l'orage + break; + default: + backgroundColor = "#87CEEB"; // Par défaut, bleu clair + } + + root.setBackgroundColor(backgroundColor); + }, + + _getLocationAndFetchWeather(lblResultat, lblResultat1, imgWeather, lblHumidity, lblWind, lblPressure, lblTempMinMax, daysContainer) { + if (navigator.geolocation) { + navigator.geolocation.getCurrentPosition((position) => { + let lat = position.coords.latitude; + let lon = position.coords.longitude; + this._fetchWeatherByCoords(lat, lon, lblResultat, lblResultat1, imgWeather, lblHumidity, lblWind, lblPressure, lblTempMinMax, daysContainer); + }, (error) => { + lblResultat.setValue("Impossible de récupérer la localisation"); + }); + } else { + lblResultat.setValue("La géolocalisation n'est pas supportée par ce navigateur"); + } + }, + + _fetchWeatherByCoords(lat, lon, lblResultat, lblResultat1, imgWeather, lblHumidity, lblWind, lblPressure, lblTempMinMax, daysContainer) { + let apiKey = "49862134e34fcce7bb7435c5d6ef0265"; + let url = `https://api.openweathermap.org/data/2.5/weather?lat=${lat}&lon=${lon}&appid=${apiKey}&units=metric&lang=fr`; + let forecastUrl = `https://api.openweathermap.org/data/2.5/forecast?lat=${lat}&lon=${lon}&appid=${apiKey}&units=metric&lang=fr`; + + let req = new qx.io.request.Xhr(url); + req.addListener("success", function (e) { + let response = e.getTarget().getResponse(); + lblResultat.setValue(`${response.name}, ${response.sys.country}`); + lblResultat1.setValue(`${response.weather[0].description}`); + lblTempMinMax.setValue(`Temp: ${response.main.temp}°C (min: ${response.main.temp_min}°C, max: ${response.main.temp_max}°C)`); + lblHumidity.setValue(`Humidité: ${response.main.humidity}%`); + lblWind.setValue(`Vent: ${response.wind.speed} m/s`); + lblPressure.setValue(`Pression: ${response.main.pressure} hPa`); + imgWeather.setSource(`https://openweathermap.org/img/wn/${response.weather[0].icon}@2x.png`); + + // Changer la couleur du fond en fonction de la météo + this._setBackgroundColorBasedOnWeather(response.weather[0].main); + }, this); + req.addListener("error", function (e) { + lblResultat.setValue("Erreur lors de la récupération des données"); + }, this); + req.send(); + + let forecastReq = new qx.io.request.Xhr(forecastUrl); + forecastReq.addListener("success", function (e) { + let response = e.getTarget().getResponse(); + let uniqueDays = {}; + let forecastData = response.list.filter(data => { + let date = new Date(data.dt * 1000).getDate(); + if (!uniqueDays[date]) { + uniqueDays[date] = true; + return true; + } + return false; + }); + + daysContainer.removeAll(); + forecastData.slice(0, 5).forEach((data, index) => { + let dayBox = new qx.ui.container.Composite(new qx.ui.layout.VBox(5)).set({ + alignX: "center", + width: 130, + height: 160, + backgroundColor: "#ADD8E6" + }); + + let dateLabel = new qx.ui.basic.Label(this._getFormattedDate(index + 1)).set({ + font: new qx.bom.Font(16, ["Arial", "sans-serif"]), + textColor: "#FFFFFF" + }); + + let weatherIcon = new qx.ui.basic.Image().set({ + source: `https://openweathermap.org/img/wn/${data.weather[0].icon}@2x.png`, + scale: true, + width: 70, + height: 70 + }); + + let tempLabel = new qx.ui.basic.Label(`${data.main.temp}°C`).set({ + font: new qx.bom.Font(14, ["Arial", "sans-serif"]), + textColor: "#FFFFFF" + }); + + dayBox.add(dateLabel); + dayBox.add(weatherIcon); + dayBox.add(tempLabel); + daysContainer.add(dayBox); + }); + }, this); + forecastReq.addListener("error", function (e) { + lblResultat.setValue("Erreur lors de la récupération des prévisions"); + }, this); forecastReq.send(); } } -}); +}); \ No newline at end of file