Skip to content

Instantly share code, notes, and snippets.

@nharrisanalyst
Created May 10, 2016 19:52
Show Gist options
  • Select an option

  • Save nharrisanalyst/79c83e263ceb66fbdac58cee525513e0 to your computer and use it in GitHub Desktop.

Select an option

Save nharrisanalyst/79c83e263ceb66fbdac58cee525513e0 to your computer and use it in GitHub Desktop.

Sacramento County 311 Calls by Zipcode Up to Date API call<

Sacramento County 311 handles all County municipal service requests that are not police and fire related. this map and bar chart makes up to date request from http://data.saccounty.net/home api

for more info or data vist http://data.saccounty.net/home

<!DOCTYPE html>
<html>
<head>
<meta http-equiv="content-type" content="text/html; charset=UTF8">
<title>A real time data visualization</title>
<script src="https://d3js.org/d3.v3.min.js" charset="utf-8"></script>
<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.12.2/jquery.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/d3-legend/1.10.0/d3-legend.js"></script>
<script src="https://d3js.org/d3-queue.v2.min.js"></script>
<script>
q=d3_queue.queue();
</script>
<style>
#g0 { fill: #eafeea; }
#g1 { fill: #d5fdd5; }
#g2 { fill: #c1fcc1; }
#g3 { fill: #acfbac; }
#g4 { fill: #88e188; }
#g5 { fill: #6aaf6a; }
#g6 { fill: #4c7d4c; }
#g7 { fill: #2d4b2d; }
.g0 { fill: #eafeea; }
.g1 { fill: #d5fdd5; }
.g2 { fill: #c1fcc1; }
.g3 { fill: #acfbac; }
.g4 { fill: #88e188; }
.g5 { fill: #6aaf6a; }
.g6 { fill: #4c7d4c; }
.g7 { fill: #2d4b2d; }
.zipcode{stroke:black;}
</style>
</head>
<body>
<script>
(function(){
var rectData=[]
var scaleX
var data;
var dataGeo
var dataZipcode={};
var dataCalls={};
var h = 600;
var w = 550;
var width=400;
var svg =d3.select("body").append("svg")
.attr("width",w)
.attr("height",h)
.attr("id","svgone");
var projection= d3.geo.albers()
.scale(45000)
.rotate([120.5,.25,0]);
var path = d3.geo.path()
.projection(projection);
var quantize;
var newData;
var check;
var newDict={};
var mapDict={};
//ordinal scale
var ordinal=d3.scale.ordinal().domain(["#g0","#g1","#g2","#g3","#g4","#g5","#g6","#g7"])
.range(["#eafeea","#d5fdd5","#c1fcc1","#acfbac","#88e188","#6aaf6a","#4c7d4c","#2d4b2d"])
//mouseover mouseout
var selecetion;
var mouseover= function(d){
var z = this.getAttribute('class')
console.log(z)
if(z.slice(0,1)=="y"){
var z = this.getAttribute('class');
var y = z.slice(1,6);
d3.select("." + this.getAttribute('class'))
.style("fill","orange")
d3.select('.z'+y)
.style("fill","orange")
d3.select('#svgone')
.append("text")
.attr("class","text")
.attr({
x:5,
y:250,
"font-size": "12px",
"font-family":"Sans-Serif"
})
.text("Name: "+d.properties.PO_NAME)
d3.select('#svgone')
.append("text")
.attr("class","text")
.attr({
x:5,
y:260,
"font-size": "12px",
"font-family":"Sans-Serif"
})
.text("Zipcode: " +d.properties.ZIP5+ ", Calls: " +newDict[d.properties.ZIP5])}
else{
var z = this.getAttribute('class');
var y = z.slice(1,6);
d3.select("." + this.getAttribute('class'))
.style("fill","orange");
d3.select('.y'+y)
.style("fill","orange")
d3.select('#svgone')
.append("text")
.attr("class","text")
.attr({
x:5,
y:250,
"font-size": "12px",
"font-family":"Sans-Serif"
})
.text("Name: "+mapDict[d.zipcode].name)
d3.select('#svgone')
.append("text")
.attr("class","text")
.attr({
x:5,
y:260,
"font-size": "12px",
"font-family":"Sans-Serif"
})
.text("Zipcode: " +mapDict[d.zipcode].zipcode+ ", Calls: " +mapDict[d.zipcode].calls)}
};
var mouseout= function(d){
var z = this.getAttribute('class')
console.log(z.slice(0,1)=="y")
if(z.slice(0,1)=="y"){
var z = this.getAttribute('class');
var y = z.slice(1,6);
var color=ordinal('#'+quantize(newDict[d.properties.ZIP5]))
console.log(color)
d3.select("." + this.getAttribute('class'))
.style("fill",ordinal('#'+quantize(newDict[d.properties.ZIP5])))
d3.select('.z'+y)
.style("fill",ordinal('#'+quantize(newDict[d.properties.ZIP5])))
d3.selectAll(".text").remove()
}else{
console.log(d.calls)
console.log('#'+quantize(d.calls))
console.log(ordinal(quantize(d.calls)))
var z = this.getAttribute('class');
var y = z.slice(1,6);
d3.select("." + this.getAttribute('class'))
.style("fill",ordinal('#'+quantize(d.calls)));
d3.select('.y'+y)
.style("fill",ordinal('#'+quantize(d.calls)))}
d3.selectAll('.text').remove();
};
//defer double request
q.defer(d3.json,"http://saccounty.cloudapi.junar.com/api/v2/datastreams/311-CASES-BY-ZIPCO-SUMMA/data.json/?auth_key=77bf2351cdb42d68f577b6c54041550cf708b773")
.defer(d3.json,"saczipgeo.json")
.awaitAll(ready)
function ready(error,first){
if(error){alert("You had an error retrieving data");}
//preparing data and everything for first json file
data=first;
data=data[0];
data.result.fArray.forEach(function(value,i){
if(i%2==0){
dataZipcode[i]=data.result.fArray[i].fStr
}
if(i%2!=0){
dataCalls[i]=data.result.fArray[i].fStr
}
});
data=[];
for ( i=0;i<=108;i=i+2){
if(i==0){
data[i]={"zipcode":dataZipcode[i],"calls":dataCalls[i+1]};
}
data[i/2]={"zipcode":dataZipcode[i],"calls":dataCalls[i+1]};
};
//scale for data colors
var maxD=d3.max(data.slice(1,data.length-1),function(d){return parseInt(d.calls)});
console.log(maxD);
var minD=d3.min(data.slice(1,data.length-1),function(d){return d.calls});
quantize= d3.scale.quantize()
.domain([0,maxD])
.range(d3.range(8).map(function(i) { return "g"+i; }));
data.forEach(function(d){return newDict[d.zipcode]= +d.calls;});
//preparing for the second json
dataGeo=first[1];
dataGeo=dataGeo.features
//checking for zipcodes that had zero calls(will be undefined in the dataMap object
for(i=0;i<dataGeo.length;i++){
if (newDict[dataGeo[i].properties.ZIP5] === undefined){
newDict[dataGeo[i].properties.ZIP5]=0;
};
};
svg.selectAll("zipcode")
.data(dataGeo)
.enter().append("path")
.attr("d", path)
.attr("class",function(d){return 'y'+ d.properties.ZIP5})
.attr("id",function(d){return quantize(newDict[d.properties.ZIP5])})
.attr("stroke","black")
.on("mouseover",mouseover)
.on("mouseout",mouseout)
var svg2=d3.select("body")
.append("svg")
.attr({
width: width,
height:h,
id:"svgtwo"
});
scaleX = d3.scale.linear()
.domain([0,maxD])
.range([0,width]);
for(i=0;i<dataGeo.length;i++){
rectData[i] = {"zipcode":dataGeo[i].properties.ZIP5,"calls":newDict[dataGeo[i].properties.ZIP5]}
};
rectData.sort(function(a, b){
return b.calls-a.calls;
})
var barPadding=1;
svg2.selectAll("rect")
.data(rectData)
.enter()
.sort(function(a, b) {
return d3.ascending(a, b);
})
.append("rect")
.attr("width",function(d){return scaleX(d.calls)})
.attr("height", function(d,i){return (h/rectData.length)-barPadding;})
.attr("y",function(d,i){return (h/rectData.length)*i;})
.attr("id",function(d){return quantize(d.calls)})
.attr("class",function(d){return 'z'+d.zipcode;})
.on("mouseover",mouseover)
.on("mouseout",mouseout);
for(i=0;i<dataGeo.length;i++){
mapDict[dataGeo[i].properties.ZIP5]={'name':dataGeo[i].properties.PO_NAME,'zipcode':dataGeo[i].properties.ZIP5,'calls':newDict[dataGeo[i].properties.ZIP5]};
};
d3.select('#svgtwo')
.append('line')
.attr({
x1:0,
y1:0,
x2:0,
y2:h,
"stroke-width":"1px",
"stroke":"black",
});
//legend
svg.append("g")
.attr("class", "legendQuant")
.attr("transform", "translate(350,450)");
var legend = d3.legend.color()
.labelFormat(d3.format(".2f"))
.useClass(true)
.scale(quantize);
svg.select(".legendQuant")
.call(legend);
};})();
</script>
</body>
<html>
Display the source blob
Display the rendered blob
Raw
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment