index.html
<!DOCTYPE html>
<meta charset="utf-8">
<title>Rain drop -Japan-</title>
<style>
html, body, svg {
width:100%;
height:100%;
margin: 0px;
padding: 0px;
}
</style>
<body>
<svg>
</svg>
<br>
<script src="https://cdnjs.cloudflare.com/ajax/libs/d3/3.5.3/d3.min.js"></script>
<script src="d3.geo2circle.js"></script>
<script>
var projection = d3.geo
.mercator()
.scale(1500)
.translate([500 , 350])
.center([139.0032936, 36.3219088]);
var path = d3.geo.path().projection(projection);
d3.json('todofuken.geojson', function(json) {
var svg = d3.select('svg')
var calcCoords = function(polygon, properties) {
var geoCoords = polygon.map(projection);
var scatterCoords = d3.geo2circle(geoCoords, 6);
var scatterPathString = 'M' + scatterCoords.join('L') + 'Z';
var geoPathString = 'M' + geoCoords.join('L') + 'Z';
return { scatterPath: scatterPathString, geoPath: geoPathString , properties:properties};
};
var pathDataSet = [];
for (var i = 0; i < json.features.length; i++) {
var geometry = json.features[i].geometry;
var properties =json.features[i].properties;
properties.geometry = geometry;
if (geometry.type == 'Polygon') {
pathDataSet.push(calcCoords(geometry.coordinates[0], properties));
} else if (geometry.type == 'MultiPolygon') {
geometry.coordinates.forEach(function(coordinates){
pathDataSet.push(calcCoords(coordinates[0], properties));
});
}
}
var raindrop = svg.selectAll('path')
.data(pathDataSet )
.enter()
.append('path')
.attr({
'stroke':'white',
'fill':'#6666ff',
'opacity':0.9
})
.attr('d', function(d){ return d.scatterPath } )
.attr('transform', function(d, i){
var center = path.centroid(d.properties.geometry);
var y = ~~center[1];
return 'translate(0,'+(0-y)+')';
});
var update = function(){
raindrop
.transition()
.duration(1000)
.delay(function(d){ return (Math.random() * 10 ) * 1000 })
.attr('opacity', 0.6)
.attr('transform','translate(0,0)')
.attr('d', function(d){ return d.geoPath } )
.each("end", function () {
d3.select(this)
.transition()
.duration(1000)
.delay(function(d){ return (Math.random() * 10 ) * 1000 })
.attr("opacity", 0)
.each("end", function () {
d3.select(this).attr('d', function(d){ return d.scatterPath } )
.attr('transform', function(d, i){
var center = path.centroid(d.properties.geometry);
var y = ~~center[1];
return 'translate(0,'+(0-y)+')';
})
.attr("opacity", 0.9);
});
});
setTimeout(update, 1000 * 10);
}
update();
});
</script>
d3.geo2circle.js
if(!d3.geo2circle) d3.geo2circle = function(coordinates, radius) {
var circle = [],
length = 0,
lengths = [length],
polygon = d3.geom.polygon(coordinates),
p0 = coordinates[0],
p1,
x,
y,
i = 0,
n = coordinates.length;
while (++i < n) {
p1 = coordinates[i];
x = p1[0] - p0[0];
y = p1[1] - p0[1];
lengths.push(length += Math.sqrt(x * x + y * y));
p0 = p1;
}
var area = polygon.area(),
radius = (radius) ? radius : Math.sqrt(Math.abs(area) / Math.PI),
centroid = polygon.centroid(-1 / (6 * area)),
angle,
i = -1,
k = 2 * Math.PI / lengths[lengths.length - 1];
while (++i < n) {
angle = lengths[i] * k;
circle.push([
centroid[0] + radius * Math.cos(angle),
centroid[1] + radius * Math.sin(angle)
]);
}
return circle;
};