colibri.php
<?php
$start = microtime(true);
set_time_limit(0);
$groups_db = json_decode(file_get_contents("http://proyectocolibri.es/api/v1/group/"));
$groups = array();
foreach ($groups_db->objects as $group_db) {
$groups[$group_db->id]['id'] = $group_db->id;
$groups[$group_db->id]['short_name'] = trim($group_db->acronym);
$groups[$group_db->id]['name'] = trim($group_db->name);
}
foreach ($groups_db->objects as $group_db) {
foreach ($group_db->members as $mp) {
$mps[$mp->id]['id'] = $mp->id;
$mps[$mp->id]['group'] = $groups[$group_db->id]['id'];
$p_ar = explode('/',$mp->party);
$mps[$mp->id]['party'] = $p_ar[count($p_ar)-2];
$mps[$mp->id]['region'] = $mp->member->division;
$mps[$mp->id]['last_name'] = $mp->member->second_name;
$mps[$mp->id]['first_name'] = $mp->member->name;
}
}
$fout = fopen('es_congreso_mp_vote.csv',"w+");
$vote2vote = array(
'No' => 'n',
'Sí' => 'y',
'Abstención' => 'a',
'No vota' => 'm'
);
$url = "http://proyectocolibri.es/api/v1/session/?limit=100&offset=0";
$sessions_db = json_decode(file_get_contents($url));
foreach ($sessions_db->objects as $row) {
foreach ($row->votings as $link) {
$url = "http://proyectocolibri.es" . $link;
$division_db = json_decode(file_get_contents($url));
foreach ($division_db->votes as $v) {
$m_ar = explode('/',$v->member);
$mp_id = $m_ar[count($m_ar)-2];
$division = array(
'mp_code' => $mp_id,
'division_code' => $division_db->id,
'divided_on' => $row->date,
'vote_kind_code' => $vote2vote[$v->vote],
'division_name' => $division_db->title,
'group_name' => $groups[$mps[$mp_id]['group']]['name'],
'mp_name' => $mps[$mp_id]['last_name'] . ', ' . $mps[$mp_id]['first_name']
);
fputcsv($fout,$division);
}
}
}
fclose($fout);
$time_taken = microtime(true) - $start;
echo "run time:".$time_taken;
?>
motion.js
function x(d) { return d.d1; }
function y(d) { return d.d2; }
function z(d) { return d.d3; }
function radius(d) {
return 1;
}
function color(d) { return d.color; }
function mid(d) { return d.id; }
function key(d) { return d.id; }
function display(d) { return d.display;}
function mname(d) {return d.name;}
var margin = {top: 19.5, right: 19.5, bottom: 19.5, left: 39.5},
width = parameters.width - margin.right,
height = parameters.height - margin.top - margin.bottom;
var xScale = d3.scale.linear().domain([parameters.xscale[0], parameters.xscale[1]]).range([0, width]),
yScale = d3.scale.linear().domain([parameters.yscale[0], parameters.yscale[1]]).range([height, 0]),
radiusScale = d3.scale.sqrt().domain([0, 1]).range([0, 10]);
var colorScale = d3.scale.category20c();
var xAxis = d3.svg.axis().orient("bottom").scale(xScale).ticks(12, d3.format(",d")),
yAxis = d3.svg.axis().scale(yScale).orient("left");
var svg = d3.select("#chart svg")
.attr("width", width + margin.left + margin.right)
.attr("height", height + margin.top + margin.bottom)
.append("g")
.attr("transform", "translate(" + margin.left + "," + margin.top + ")");
svg.append("g")
.attr("class", "x axis")
.attr("transform", "translate(0," + height + ")")
.call(xAxis);
svg.append("g")
.attr("class", "y axis")
.call(yAxis);
svg.append("text")
.attr("class", "x label")
.attr("text-anchor", "end")
.attr("x", width)
.attr("y", height - 6)
.text("Dimension 1");
svg.append("text")
.attr("class", "y label")
.attr("text-anchor", "end")
.attr("y", 6)
.attr("dy", ".75em")
.attr("transform", "rotate(-90)")
.text("Dimension 2");
tmp_month = Math.ceil((parameters.start - Math.floor(parameters.start))*12);
tmp_year = Math.floor(parameters.start) + '/' + tmp_month;
var label = svg.append("text")
.attr("class", "year label")
.attr("text-anchor", "end")
.attr("y", height - 24)
.attr("x", width)
.text(tmp_year);
var formatTime = d3.time.format("%e %B");
var div = d3.select("body").append("div")
.attr("class", "tooltip")
.style("opacity", 0);
d3.json(parameters.data, function(nations) {
var bisect = d3.bisector(function(d) { return d[0]; });
var dot = svg.append("g")
.attr("class", "dots")
.selectAll(".dot")
.data(interpolateData(parameters.start))
.enter().append("circle")
.attr("class", "dot")
.call(position)
.call(checkCheckboxes)
.sort(order)
.on("mouseover", showTooltip)
.on("mouseout", hideTooltip)
.on("mousedown", switchHighlight);
function checkCheckboxes() {
$(".checkbox-mp").each(function(i) {
a = $(this).attr('id').split('-');
id = a[a.length-1];
if ($('#checkbox-h-'+id).prop('checked'))
highlight($('#dot-'+id));
});
}
function switchHighlight(d) {
a = d.id.split('-');
id = a[a.length-1];
if ($('#'+d.id).attr("class") == 'dot') {
highlight($('#'+d.id));
$("input#checkbox-h-"+id).attr("checked",true).checkboxradio("refresh");
} else {
dehighlight($('#'+d.id));
$("input#checkbox-h-"+id).attr("checked",false).checkboxradio("refresh");
}
}
function showTooltip(d) {
div.transition()
.duration(200)
.style("opacity", .9);
div .html(d.name + "<br/>" + d.group)
.style("left", (d3.event.pageX) + "px")
.style("top", (d3.event.pageY - 28) + "px");
}
function hideTooltip(d) {
div.transition()
.duration(500)
.style("opacity", 0)
}
var i=0;
var playing = false;
$("#play").click(function() {
if(playing === false) {
startPlaying();
} else {
stopPlaying();
}
});
function startPlaying() {
playing = true;
$("#playText").html("Stop ||");
$('#slider').slider('disable');
svg.transition()
.duration(30000*(parameters.untilchart-parseFloat($('#slider').val()))/(parameters.untilchart-parameters.sincechart+0.0001))
.ease("linear")
.tween("year", function() {return tweenYear($('#slider').val()) })
.each("end", stopPlaying);
}
function stopPlaying() {
playing = false;
$("#playText").html("Play >");
svg.transition().duration(0);
$('#slider').slider('enable');
}
function position(dot) {
dot .attr("cx", function(d) { return xScale(x(d)); })
.attr("cy", function(d) { return yScale(y(d)); })
.attr("r", function(d) { return radiusScale(radius(d)) })
.attr("id", function(d) {return mid(d);})
.style("fill", function (d) { return gradient(color(d)) })
.attr("display", function (d) { return display(d);})
.attr("title", function (d) {return mname(d);});
}
function order(a, b) {
return radius(b) - radius(a);
}
function tweenYear(start) {
var year = d3.interpolateNumber(parseFloat(start),parameters.untilchart);
return function(t) { displayYear(year(t)); };
}
function displayYear(year) {
dot.data(interpolateData(year), key).call(position).sort(order);
month = Math.ceil((year - Math.floor(year))*12);
label.text(Math.floor(year) + '/' + month);
i++;
if ((i%25) == 0) {
$("#slider").val(year);
$('#slider').slider('refresh');
}
}
function interpolateData(year) {
return nations.map(function(d) {
return {
name: d.name,
id: "dot-"+d.id,
d1: interpolateValues(d.d1, year),
d2: interpolateValues(d.d2, year),
color: findColor(d.color, year, true),
display: isDisplayed(d.d1, year),
title: d.name,
group: findColor(d.color, year, false)
};
});
}
function interpolateValues(values, year) {
var i = bisect.left(values, year, 0, values.length - 1),
a = values[i];
if (i > 0) {
var b = values[i - 1],
t = (year - a[0]) / (b[0] - a[0]);
return a[1] * (1 - t) + b[1] * t;
}
return a[1];
}
function findColor(values, year, color) {
var i = bisect.left(values, year, 0, values.length - 1);
if (color)
return values[i][2];
else
return values[i][1];
}
function isDisplayed(values, year) {
if ( (year < values[0][0]) || (year > values[values.length - 1][0]))
return 'none';
else
return 'inherit';
}
function highlight(d) {
d.attr("class","dot highlighted");
}
function dehighlight(d) {
d.attr('class','dot');
}
$('.checkbox-mp').click (function () {
var thisCheck = $(this);
a = $(this).attr('id').split('-');
id = a[a.length-1];
if (thisCheck.is (':checked')) {
highlight($("#dot-"+id));
} else {
dehighlight($("#dot-"+id));
}
});
$('#slider').ready(function() {
$('#slider').change(function(){
displayYear($(this).val());
});
});
function shadeColor(color, percent) {
var R = parseInt(color.substring(1,3),16)
var G = parseInt(color.substring(3,5),16)
var B = parseInt(color.substring(5,7),16);
R = parseInt(R * (100 + percent) / 100);
G = parseInt(G * (100 + percent) / 100);
B = parseInt(B * (100 + percent) / 100);
R = (R<255)?R:255;
G = (G<255)?G:255;
B = (B<255)?B:255;
var RR = ((R.toString(16).length==1)?"0"+R.toString(16):R.toString(16));
var GG = ((G.toString(16).length==1)?"0"+G.toString(16):G.toString(16));
var BB = ((B.toString(16).length==1)?"0"+B.toString(16):B.toString(16));
return "#"+RR+GG+BB;
}
function gradient(baseColor)
{
var gradientId = "gradient" + baseColor.substring(1)
console.log("COLOR: " + gradientId);
var darkColor = shadeColor(baseColor, -20)
var grad = d3.select("#gradients").selectAll("#" + gradientId)
.data([ gradientId ])
.enter()
.append("radialGradient")
.attr("id", gradientId)
.attr("gradientUnits", "objectBoundingBox")
.attr("fx", "30%")
.attr("fy", "30%")
grad.append("stop")
.attr("offset", "0%")
.attr("style", "stop-color:#FFFFFF")
grad.append("stop")
.attr("offset", "40%")
.attr("style", "stop-color:" + baseColor)
grad.append("stop")
.attr("offset", "100%")
.attr("style", "stop-color:" + darkColor)
console.log("url(#" + gradientId + ")")
return "url(#" + gradientId + ")";
}
});