Skip to content

Instantly share code, notes, and snippets.

@basilesimon
Last active April 30, 2019 20:46
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save basilesimon/4e29417c54ad385fbc62e9c9a95494db to your computer and use it in GitHub Desktop.
Save basilesimon/4e29417c54ad385fbc62e9c9a95494db to your computer and use it in GitHub Desktop.
Satellite Projection (canvas)
license: gpl-3.0
<!DOCTYPE html>
<meta charset="utf-8">
<style>
</style>
<body>
<script src="//d3js.org/d3.v4.min.js"></script>
<script src="//d3js.org/d3-geo-projection.v2.min.js"></script>
<script src="//d3js.org/topojson.v2.js"></script>
<script src="//unpkg.com/d3-jetpack@2.0.20/build/d3-jetpack.js"></script>
<button onclick="zoom()">click to zoom</button>
<canvas width="960" height="500"></canvas>
<script>
const canvas = d3.select("canvas");
const width = canvas.property("width");
const height = canvas.property("height");
let context = canvas.node().getContext("2d");
let projection = d3.geoSatellite()
.distance(1.1)
.scale(5000)
.rotate([-38, -33, -30])
.center([0, 2])
.tilt(30)
.precision(0.1);
let path = d3.geoPath(projection, context);
const zoom = d3.zoom()
//.scaleExtent([5000, 20000])
.scaleExtent([1, 10])
.on('zoom', zoomed);
const graticule = d3.geoGraticule()
.extent([[-10,30], [80, 80]])
.step([3, 3]);
let render = function() {};
const draw = (error, land, circle, camp) => {
render = (projection, context) => {
context.clearRect(0, 0, width, height);
path = d3.geoPath(projection, context);
context.strokeStyle = "#ccc";
context.fillStyle = "#fff";
context.beginPath();
path(topojson.feature(land, land.objects.ne_10m_admin_0_countries2));
context.fill();
context.stroke();
context.closePath();
context.beginPath();
context.strokeStyle = "rgba(255,0,0,0.3)";
context.fillStyle = "rgba(255,0,0,0.1)";
path(topojson.feature(circle, circle.objects.Circle_Measure));
context.stroke();
context.fill();
context.closePath();
const shelters = topojson.feature(camp, camp.objects.Rukban_Structures_20190121).features;
for (let i=0; i<shelters.length; i++) {
context.beginPath();
const tent = shelters[i];
context.moveTo(projection(tent.geometry.coordinates)[0] + 1, projection(tent.geometry.coordinates)[1]);
context.arc(projection(tent.geometry.coordinates)[0], projection(tent.geometry.coordinates)[1], 1, 0, 2 * Math.PI);
context.fillStyle = "rgba(0,0,0,0.1)";
context.fill();
context.closePath();
}
};
canvas.call(zoom);
render(projection, context);
}
function zoomed () {
const t = d3.event.transform;
console.log(t, d3.zoomIdentity);
context.save();
// const proj = projection
// //.translate([t.x, t.y])
// .scale(t.k);
context.scale(t.k, t.k);
context.translate(t.x, t.y);
render(projection, context);
context.restore();
}
d3.queue()
.defer(d3.json, "https://gist.githubusercontent.com/basilesimon/e15cc6647a5ecc3c2c9b961215e8bf6b/raw/5733bff346be28f61ca2e2dcb982a82a48733bcd/sat.json")
.defer(d3.json, "https://gist.githubusercontent.com/basilesimon/20178b9d63dbda0fb8ed14590fcca036/raw/3214d4c452f83f7538d0b2c20e30d535711e8a80/circle.json")
.defer(d3.json, "https://gist.githubusercontent.com/basilesimon/614713d27f4c55d0392d77501f12b420/raw/8443dc30bb5f9b129a8e67e658c8c901a154f8fc/rukban.json")
.await(draw);
</script>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment