From 4c68f557322a98786f9fff462c9ce4313beb9359 Mon Sep 17 00:00:00 2001 From: JOE XMG <thunyathep.s@outlook.com> Date: Mon, 19 Feb 2024 15:24:59 +0100 Subject: [PATCH] update --- public/udigit4icity/index.html | 232 ++++++++++++++++++--------------- 1 file changed, 129 insertions(+), 103 deletions(-) diff --git a/public/udigit4icity/index.html b/public/udigit4icity/index.html index a17e0b8..8818943 100644 --- a/public/udigit4icity/index.html +++ b/public/udigit4icity/index.html @@ -5,15 +5,16 @@ <meta charset="UTF-8"> <meta http-equiv="X-UA-Compatible" content="IE=edge"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> - <title>Integrated Web Map and ECharts</title> - + <title>3D Web Mapping Application</title> <link rel="stylesheet" href="https://js.arcgis.com/4.28/esri/css/main.css"> <script src="https://cdn.plot.ly/plotly-latest.min.js"></script> <script src="https://api.mapbox.com/mapbox.js/v3.3.1/mapbox.js"></script> <link href="https://api.mapbox.com/mapbox.js/v3.3.1/mapbox.css" rel="stylesheet" /> - <!-- <link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/echarts@5.0.0/dist/echarts.min.css"> - <link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/echarts-gl@5.0.0/dist/echarts-gl.min.css"> --> + <script src="https://cdnjs.cloudflare.com/ajax/libs/echarts/5.5.0/echarts.common.min.js" integrity="sha512-klHlINboj5r1sfTjdyb2PJn7ixcYb5zN+WC/gbFlK3r8/nmhmwQ3yvi5q49tX39DcHX/HwPnXTIblG5/cb6IEA==" crossorigin="anonymous" referrerpolicy="no-referrer"></script> + + <script src="https://cdnjs.cloudflare.com/ajax/libs/echarts/5.5.0/echarts.min.js" integrity="sha512-k37wQcV4v2h6jgYf5IUz1MoSKPpDs630XGSmCaCCOXxy2awgAWKHGZWr9nMyGgk3IOxA1NxdkN8r1JHgkUtMoQ==" crossorigin="anonymous" referrerpolicy="no-referrer"></script> + <link rel="stylesheet" href="https://js.arcgis.com/4.28/esri/themes/dark/main.css" /> <style> @@ -24,7 +25,7 @@ #chartControls label, #chartControls select, #chartControls button { - font-size: 16px; + font-size: 16px; margin-bottom: 15px } @@ -35,15 +36,7 @@ overflow: hidden; } - #usage-pie-chart-container { - z-index: 1; - position: absolute; - top:10px; - right: 0px; - width: 20%; - height: 0.2px; - bottom:10%; - } + #mainMenu { position: absolute; @@ -68,9 +61,9 @@ } #main-menu { - width: 20%; + width: 20%; height: 100%; - background-color: #2c3e50; + background-color: #2c3e50; color: rgb(91, 89, 89); display: flex; flex-direction: column; @@ -126,6 +119,7 @@ position: absolute; top: 90%; left: 36%; + padding: 5px; background-color: rgba(255, 255, 255, 0.8); border-radius: 5px; @@ -161,27 +155,37 @@ left: 0; top: 2%; right:100; - width: 100%; + width: 100%; z-index: 3; } .dark-popup-content { - color: #232020; + color: #232020; background-color: #171515; /* to dark gray */ } +#usage-pie-chart { + display: none; + width: 600px; + height: 400px; + z-index: 1; + position: absolute; + top:65%; + right: 0%; + bottom:0%; + } + </style> </head> <body> <div id="container"> - <div id="usage-pie-chart-container" style="width: 300px; height: 300px; "> - <canvas id="usage-pie-chart" style="width: 100%; height: 100%;"></canvas> - </div> + <div id="main"></div> <div id="viewDiv"></div> <div id="timeSlider"></div> + <div id="usage-pie-chart"></div> <div class="legend"></div> <div class="legend-building"></div> @@ -195,7 +199,7 @@ </div> </div> - + </div> <div id="mainMenu"> <label for="measurementType">Select Measurement Type:</label> @@ -211,26 +215,25 @@ <option value="bar">Bar Chart</option> </select> + + <button id="loadDatastream">Load Datastream</button> <button id="toggleSpaceTime">Bus Space-Time Visualization</button> <button id="toggle3DButton">3D City Building</button> + </div> <script src="https://cdn.plot.ly/plotly-latest.min.js"></script> <script src="https://api.mapbox.com/mapbox.js/v3.3.1/mapbox.js"></script> - <!-- <script src="https://cdn.jsdelivr.net/npm/echarts@5.0.0/dist/echarts.min.js"></script> - <script src="https://cdn.jsdelivr.net/npm/echarts-gl@5.0.0/dist/echarts-gl.min.js"></script> --> - <script src="https://cdnjs.cloudflare.com/ajax/libs/echarts/5.5.0/echarts.min.js" integrity="sha512-k37wQcV4v2h6jgYf5IUz1MoSKPpDs630XGSmCaCCOXxy2awgAWKHGZWr9nMyGgk3IOxA1NxdkN8r1JHgkUtMoQ==" crossorigin="anonymous" referrerpolicy="no-referrer"></script> - <script src="https://cdn.jsdelivr.net/npm/chart.js"></script> - <script src="https://code.highcharts.com/highcharts.js"></script> + <script src="https://js.arcgis.com/4.28/"></script> <script> const data = [ - + ]; //to ensure if plotly and mapbox are loaded @@ -240,6 +243,9 @@ var selectedMeasurementType = document.getElementById("measurementType").value; var selectedChartType = document.getElementById("chartType").value; + + + // Mapping from sensor location to their corresponding Datastream id var datastreamIds = { "Co-working": { @@ -328,7 +334,7 @@ }, }, grid: { - left: '5%', + left: '4%', right: '15%', top: '10%', bottom: '10%', @@ -340,14 +346,14 @@ boundaryGap: false, axisLabel: { color: 'green', - fontSize: 18, + fontSize: 20, }, }, yAxis: { name: selectedMeasurementType.charAt(0).toUpperCase() + selectedMeasurementType.slice(1), axisLabel: { color: 'red', - fontSize: 18, + fontSize: 19, }, }, series: resultData.map(locationData => ({ @@ -419,6 +425,9 @@ }); } + + + function createLegendItem(color, label, id) { const legendItem = document.createElement("div"); legendItem.className = "legend-item"; @@ -476,7 +485,7 @@ type: 'scatter3d', x: coordinates.map(coord => coord[0]), y: coordinates.map(coord => coord[1]), - z: timestamps.map((time, i) => new Date(time).toISOString()), + z: timestamps.map((time, i) => new Date(time).toISOString()), mode: 'lines+markers', line: { color: 'dark' }, @@ -488,10 +497,10 @@ }); // to set the layout with mapbox _ access token - + const layout = { mapbox: { - style: 'light', + style: 'light', center: { lon: frames[0].data[0].lon[0], lat: frames[0].data[0].lat[0] }, zoom: 10, accesstoken: 'pk.eyJ1IjoicmVkaWV0OTk2MyIsImEiOiJjbHJ1cmk5aGUwaDRvMmpuYWM4Z2NqcmZuIn0.c11HYT-5ucd6g6mL03bp3Q', // Mapbox access token @@ -502,7 +511,7 @@ const layout = { title: 'X Axis', titlefont: { family: 'Arial, sans-serif', - size: 15, + size: 15, color: 'black' }, tickfont: { @@ -516,7 +525,7 @@ const layout = { title: 'Y Axis', titlefont: { family: 'Arial, sans-serif', - size: 15, + size: 15, color: 'black' }, tickfont: { @@ -530,7 +539,7 @@ const layout = { title: 'Time', titlefont: { family: 'Arial, sans-serif', - size: 16, + size: 16, color: 'black' }, tickfont: { @@ -540,7 +549,7 @@ const layout = { bold: true } }, - // Common font settings for both + // Common font settings for both font: { family: 'Arial, sans-serif', size: 12, @@ -573,6 +582,8 @@ function loadHistoricalRoutes() { animateHistoricalMovingFeatures('https://ogcapi.hft-stuttgart.de/ogc_api_moving_features/collections/bus_1/items', [226, 119, 40], 'Bus', 'Bus', 'busLegend'); } + + </script> <script> @@ -661,16 +672,16 @@ const popupTemplate = new PopupTemplate({ </tr> </table> - ` + ` }); const featureLayer1 = new FeatureLayer({ - url: "https://services.arcgis.com/1lplwYilIlo008hQ/arcgis/rest/services/Datastreams_observation_xy_splited/FeatureServer", + url: "https://services.arcgis.com/1lplwYilIlo008hQ/arcgis/rest/services/Datastreams_observation_xy/FeatureServer", renderer: new SimpleRenderer({ symbol: webStyleSymbol // specified symbol }), - popupTemplate: popupTemplate, - outFields: ["*"] // …include all fields + popupTemplate: popupTemplate, + outFields: ["*"] // …include all fields }); @@ -680,11 +691,11 @@ const featureLayer2 = new FeatureLayer({ url: "https://services.arcgis.com/1lplwYilIlo008hQ/arcgis/rest/services/Munakata_City_Road/FeatureServer", renderer: new SimpleRenderer({ symbol: new SimpleLineSymbol({ - color: '#7DF9FF', - width: 0.1 + color: '#7DF9FF', + width: 0.1 }) }), - outFields: ["*"], + outFields: ["*"], }); map.add(featureLayer2); @@ -847,72 +858,89 @@ map.add(featureLayer2); }); map.add(hostedLayer); - -// usage data with 'usage' and 'count' properties -const usageData = [ - { usage: "educational facilities", count: 100 }, - { usage: "Commercial Facilities", count: 200 }, -]; -// Additional usage -const additionalUsageData = [ - { usage: "apartment house", count: 150 }, - { usage: "factory", count: 75 }, +// Building usage data +const buildingUsageData = [ + { usage: "Educational facilities", count: 100 }, + { usage: "Commercial Facilities", count: 200 }, + { usage: "Apartment house", count: 150 }, + { usage: "Factory", count: 75 }, { usage: "Other", count: 50 }, { usage: "Residential", count: 300 }, - { usage: "business facility", count: 180 }, + { usage: "Business facility", count: 180 }, { usage: "Agriculture, Forestry and Fishing Facilities", count: 90 }, { usage: "Transportation warehouse facilities", count: 120 } ]; -// Combines all usage_data -const allUsageData = usageData.concat(additionalUsageData); - -// to extract labels and counts -const labels = allUsageData.map(item => item.usage); -const counts = allUsageData.map(item => item.count); - -// colors for each category -const colors = [ - "#FF6384", - "#347fb3", - "#FFCE56", - "#4BC0C0", - "#9966FF", - "#b57433", - "#3ca33c", - "#FF99CC", - "#BDBDBD" +// Extract labels, counts, and colors +const labels = buildingUsageData.map(item => item.usage); +const counts = buildingUsageData.map(item => item.count); +const colors = ["#FF6384", + '#347fb3','#FFCE56','#4BC0C0','#9966FF','#b57433','#3ca33c','#FF99CC','#BDBDBD' ]; -// Creating pie chart -const pieChartCanvas = document.getElementById("usage-pie-chart").getContext("2d"); -const usagePieChart = new Chart(pieChartCanvas, { - type: "pie", - data: { - labels: labels, - datasets: [{ - data: counts, - backgroundColor: colors - }] +// Create the pie chart using ECharts +const pieChartContainer = document.getElementById("usage-pie-chart"); +const usagePieChart = echarts.init(pieChartContainer); + +const options = { + title: { + text: 'Building Usage' + }, + tooltip: { + trigger: 'item', + formatter: function(params, ticket, callback) { + const dataIndex = params.dataIndex; + const totalUsage = counts.reduce((acc, cur) => acc + cur, 0); + const percentage = ((counts[dataIndex] / totalUsage) * 100).toFixed(2); + return `${params.name}: ${params.value} (${percentage}% of total: ${totalUsage})`; + } }, - options: { - title: { - display: true, - text: "Building Usage" - }, - legend: { - labels: { - fontColor: 'white' - } + series: [{ + type: 'pie', + data: buildingUsageData.map((item, index) => ({ + name: item.usage, + value: item.count + })), + itemStyle: { + color: (params) => colors[params.dataIndex] } - } -}); + }] +}; - // To add an event listener for toggling 3D plot visibility - document.getElementById("toggle3DButton").addEventListener("click", function () { +usagePieChart.setOption(options); + + +// Function to toggle 3D building and pie chart visibility +document.getElementById("toggle3DButton").addEventListener("click", function () { + // Toggle 3D building layer visibility hostedLayer.visible = !hostedLayer.visible; - }); + + // Toggle pie chart visibility based on 3D building visibility + const pieChartContainer = document.getElementById("usage-pie-chart"); + const echartContainer = document.getElementById("main"); + const legendContainer = document.querySelector('.legend'); + const currentDisplay = pieChartContainer.style.display; + const loadDatastreamButton = document.getElementById("loadDatastream"); + + if (hostedLayer.visible) { + // If 3D building is visible, show the pie chart + pieChartContainer.style.display = "block"; + echartContainer.style.display = "none"; + legendContainer.style.display = "none"; + } else { + // If 3D building is hidden, hide the pie chart + pieChartContainer.style.display = "none"; + echartContainer.style.display = "block"; + legendContainer.style.display = "block"; + } +}); + + + + + + const graphicsLayer = new GraphicsLayer(); map.add(graphicsLayer); @@ -1136,10 +1164,10 @@ animateMovingFeatures("https://ogcapi.hft-stuttgart.de/ogc_api_moving_features/c // Set the layout with mapbox style and access token const layout = { mapbox: { - style: 'light', + style: 'light', center: { lon: features[0].geometry.coordinates[0][0], lat: features[0].geometry.coordinates[0][1] }, zoom: 10, - accesstoken: 'pk.eyJ1IjoicmVkaWV0OTk2MyIsImEiOiJjbHJ1cmk5aGUwaDRvMmpuYWM4Z2NqcmZuIn0.c11HYT-5ucd6g6mL03bp3Q', + accesstoken: 'pk.eyJ1IjoicmVkaWV0OTk2MyIsImEiOiJjbHJ1cmk5aGUwaDRvMmpuYWM4Z2NqcmZuIn0.c11HYT-5ucd6g6mL03bp3Q', }, margin: { t: 0, b: 0, l: 0, r: 0 }, @@ -1157,8 +1185,6 @@ animateMovingFeatures("https://ogcapi.hft-stuttgart.de/ogc_api_moving_features/c } </script> -<script> -const thingsLocations = [ { thingId: 1, locationURL: "https://ogcapi.hft-stuttgart.de/sta/udigit4icity/v1.1/Things(1)/Locations", datastreamsURL: "https://ogcapi.hft-stuttgart.de/sta/udigit4icity/v1.1/Things(1)/Datastreams" }, { thingId: 2, locationURL: "https://ogcapi.hft-stuttgart.de/sta/udigit4icity/v1.1/Things(2)/Locations", datastreamsURL: "https://ogcapi.hft-stuttgart.de/sta/udigit4icity/v1.1/Things(2)/Datastreams" }, { thingId: 3, locationURL: "https://ogcapi.hft-stuttgart.de/sta/udigit4icity/v1.1/Things(3)/Locations", datastreamsURL: "https://ogcapi.hft-stuttgart.de/sta/udigit4icity/v1.1/Things(3)/Datastreams" }, { thingId: 4, locationURL: "https://ogcapi.hft-stuttgart.de/sta/udigit4icity/v1.1/Things(4)/Locations", datastreamsURL: "https://ogcapi.hft-stuttgart.de/sta/udigit4icity/v1.1/Things(4)/Datastreams" }, { thingId: 5, locationURL: "https://ogcapi.hft-stuttgart.de/sta/udigit4icity/v1.1/Things(5)/Locations", datastreamsURL : "https://ogcapi.hft-stuttgart.de/sta/udigit4icity/v1.1/Things(5)/Datastreams" }, ]; -</script> + </body> -- GitLab