Built with blockbuilder.org
Last active
July 9, 2020 10:09
-
-
Save Hirosaji/9613b45348e785027cbcff576591ca1b to your computer and use it in GitHub Desktop.
Google Earth Engine × Mapbox - Reduction in NO2 by COVID-9
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Google Earth Engine × Mapbox - Reduction in NO2 by COVID-9 | |
license: mit |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<!DOCTYPE html> | |
<head> | |
<meta charset="utf-8"> | |
<script src="https://api.mapbox.com/mapbox-gl-js/v1.11.0/mapbox-gl.js"></script> | |
<link href="https://api.mapbox.com/mapbox-gl-js/v1.11.0/mapbox-gl.css" rel="stylesheet" /> | |
<script src="https://d3js.org/d3.v5.min.js"></script> | |
<style> | |
html, body { | |
margin: 0; | |
} | |
#mapid { | |
height: 700px; | |
} | |
.map-overlay { | |
position: absolute; | |
right: 0; | |
top: 600px; | |
padding: 10px 10px 5px; | |
background: rgba(255, 255, 255, 0.8); | |
margin-right: 20px; | |
font-family: Arial, sans-serif; | |
overflow: auto; | |
border-radius: 3px; | |
} | |
.map-overlay .unit { | |
margin: 0px; | |
text-align: right; | |
font-size: 0.5em; | |
color: #4a4a4a; | |
transform: scale(0.7) translate(62px, 0px); | |
} | |
#features { | |
top: 0; | |
height: 110px; | |
margin-top: 20px; | |
width: 250px; | |
padding-left: 30px; | |
} | |
/* tab */ | |
.tab-wrap { | |
display: flex; | |
flex-wrap: wrap; | |
margin: 10px; | |
} | |
.tab-label { | |
color: White; | |
background: LightGray; | |
font-weight: bold; | |
white-space: nowrap; | |
text-align: center; | |
padding: 10px .5em; | |
order: -1; | |
position: relative; | |
z-index: 1; | |
cursor: pointer; | |
border-radius: 5px 5px 0 0; | |
flex: 1; | |
} | |
.tab-label:not(:last-of-type) { | |
margin-right: 5px; | |
} | |
.tab-switch:checked+.tab-label { | |
background: #325A8C; | |
} | |
.tab-switch:checked+.tab-label+.tab-content { | |
height: auto; | |
overflow: auto; | |
padding: 15px; | |
opacity: 1; | |
transition: .5s opacity; | |
box-shadow: 0 0 3px rgba(0, 0, 0, 0.3); | |
} | |
.tab-switch { | |
display: none; | |
} | |
.tab-label { | |
margin-bottom: 1rem; | |
border-radius: 0; | |
} | |
.tab-label { | |
background: #fff; | |
color: #325a8c; | |
border: 2px solid; | |
} | |
.tab-switch:checked+.tab-label+.tab-content { | |
text-align: center; | |
} | |
.tab-switch:checked+.tab-label { | |
background: #325a8c; | |
color: #fff; | |
border-color: #325a8c; | |
} | |
.tab-label { | |
margin-bottom: 1rem; | |
border-radius: 0; | |
} | |
.tab-label:not(:last-of-type) { | |
margin-right: 0; | |
} | |
.tab-label { | |
background: #fff; | |
color: #325a8c; | |
border: 2px solid; | |
border-left: 0; | |
} | |
.tab-label:first-of-type { | |
border: 2px solid; | |
} | |
.tab-switch:checked+.tab-label+.tab-content { | |
text-align: center; | |
} | |
.tab-switch:checked+.tab-label { | |
background: #325a8c; | |
color: #fff; | |
border-color: #325a8c; | |
} | |
</style> | |
</head> | |
<body> | |
<div class='wrapper'> | |
<div id='mapid'></div> | |
<div class='map-overlay' id='features'><h2>COVID-19 impacts</h2><p>Reduced NO2 density on JP</p></div> | |
<div class='map-overlay' id='legend00'></div> | |
<div class='map-overlay' id='legend01'></div> | |
</div> | |
<div class="tab-wrap"> | |
<input id="tab01" type="radio" name="tab" class="tab-switch"><label class="tab-label" for="tab01">2019/04/16~ monthly mean</label> | |
<input id="tab02" type="radio" name="tab" class="tab-switch"><label class="tab-label" for="tab02">2020/04/16~ monthly mean</label> | |
<input id="tab03" type="radio" name="tab" class="tab-switch" checked="checked"><label class="tab-label" for="tab03">diff (2020-2019)</label> | |
</div> | |
<script> | |
// set bounds to Japan, Japan | |
var bounds = [ | |
[100.0, 15], // Southwest coordinates | |
[175.0, 52] // Northeast coordinates | |
]; | |
// set mapbox object | |
mapboxgl.accessToken = 'pk.eyJ1IjoiaGlyb3Nhamktc3ViIiwiYSI6ImNrYzVxbXJ6cDAwMzYydHF0dm11N2Y0ZTAifQ.6VeK9-csemGfG-DHvskwpg'; | |
const map = new mapboxgl.Map({ | |
container: 'mapid', | |
style: 'mapbox://styles/hirosaji-sub/ckc5vkqem0owx1il7skcxegk8', // stylesheet location | |
center: [139.95, 35.6], // starting position [lng, lat] | |
zoom: 8, // starting zoom lebel | |
minZoom: 4, | |
maxZoom: 11, | |
pitch: 30, | |
maxBounds: bounds, | |
}); | |
// set layer toggle event | |
var idPrefixList = ['no2-2019', 'no2-2020', 'no2-diff']; | |
d3.selectAll(".tab-switch").on("click", (_, i) => { | |
map.setLayoutProperty(idPrefixList[i] + '_small', 'visibility', 'visible'); | |
map.setLayoutProperty(idPrefixList[i] + '_big', 'visibility', 'visible'); | |
idPrefixList | |
.filter((_, j) => i!==j) | |
.forEach(idPrefix => { | |
map.setLayoutProperty(idPrefix + '_small', 'visibility', 'none'); | |
map.setLayoutProperty(idPrefix + '_big', 'visibility', 'none'); | |
}); | |
d3.select("#legend00").style("display", (i === 2) ? "block" : "none"); | |
d3.select("#legend01").style("display", (i === 2) ? "none" : "block"); | |
}) | |
// set legend | |
var diff_pallet = [ | |
{"color":"#aa1f2c","value":-150}, | |
{"color":"#0a0a29","value":0}, | |
{"color":"#342fd4","value":150}, | |
{"color":"#2d59d2","value":300}, | |
{"color":"#2d88cd","value":450}, | |
{"color":"#2db3c7","value":600}, | |
{"color":"#2ec2a8","value":750} | |
]; | |
var other_pallet = [ | |
{"color":"#ffffff","value":0}, | |
{"color":"#feebe2","value":500}, | |
{"color":"#fbb4b9","value":1000}, | |
{"color":"#f768a1","value":1500}, | |
{"color":"#c51b8a","value":2000}, | |
{"color":"#7a0177","value":2500} | |
]; | |
[diff_pallet, other_pallet].forEach((data, i) => { | |
var extent = d3.extent(data, d => d.value); | |
var padding = 15; | |
var width = 320; | |
var innerWidth = width - (padding * 2); | |
var barHeight = 8; | |
var height = 28; | |
var xScale = d3.scaleLinear() | |
.range([0, innerWidth]) | |
.domain(extent); | |
var xTicks = data.filter(f => f.value % 50 === 0).map(d => d.value); | |
var xAxis = d3.axisBottom(xScale) | |
.tickSize(barHeight * 2) | |
.tickValues(xTicks); | |
var svg = d3.select("#legend0" + i) | |
.style("display", (i === 0) ? "block" : "none") | |
.append("svg") | |
.attr("width", width) | |
.attr("height", height); | |
var g = svg | |
.append("g") | |
.attr("transform", "translate(" + padding + ", 0)"); | |
var defs = svg.append("defs"); | |
var linearGradient = defs.append("linearGradient").attr("id", "myGradient0" + i); | |
linearGradient.selectAll("stop") | |
.data(data) | |
.enter() | |
.append("stop") | |
.attr("offset", d => ((d.value - extent[0]) / (extent[1] - extent[0]) * 100) + "%") | |
.attr("stop-color", d => d.color); | |
g.append("rect") | |
.attr("width", innerWidth) | |
.attr("height", barHeight) | |
.style("fill", "url(#myGradient0" + i + ")"); | |
g.append("g") | |
.call(xAxis) | |
.select(".domain").remove(); | |
d3.select("#legend0" + i) | |
.append("p") | |
.attr("class", "unit") | |
.html("(10<sup>-7</sup> * mol/m<sup>2</sup>)"); | |
}); | |
</script> | |
</body> |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment