Commit 94fcb056 authored by Tania Gómez's avatar Tania Gómez

Chords diagram plot

parent 8884b2e5
......@@ -19,7 +19,8 @@ let baseLayerPromises = [];
currentBaseLayer = 1;*/
//let drawnItems;
let od, flowMapsArray = [], odData = {};
let od, flowMapsArray = [],
odData = {};
/*Object.keys(baseFileSize).forEach((name) => {
if (name.split(".")[1] == "zip") {
......@@ -900,9 +901,9 @@ const createFlowLayer = (geojson, type, addOnCreate) => {
animatedCanvasBezierStyle = [];
// define styles based on properties and values
intervals[type].values.forEach( (val, idx) => {
intervals[type].values.forEach((val, idx) => {
canvasBezierStyle.push({
classMinValue: idx == 0 ? 0 : intervals[type].values[idx-1] + 1,
classMinValue: idx == 0 ? 0 : intervals[type].values[idx - 1] + 1,
classMaxValue: val,
symbol: {
strokeStyle: intervals[type].colors[idx],
......@@ -914,7 +915,7 @@ const createFlowLayer = (geojson, type, addOnCreate) => {
});
animatedCanvasBezierStyle.push({
classMinValue: idx == 0 ? 0 : intervals[type].values[idx-1] + 1,
classMinValue: idx == 0 ? 0 : intervals[type].values[idx - 1] + 1,
classMaxValue: val,
symbol: {
strokeStyle: intervals[type].colors[idx],
......@@ -931,12 +932,12 @@ const createFlowLayer = (geojson, type, addOnCreate) => {
// build data array from geojson to be used in amchart
let source = data.features;
let newData = [];
source.forEach(o => newData.push({'xVar': o.properties.muni_origen, 'yVar': o.properties.muni_destino, 'flowCount': o.properties.viajes}) );
source.forEach(o => newData.push({ 'xVar': o.properties.muni_origen, 'yVar': o.properties.muni_destino, 'flowCount': o.properties.viajes }));
let origins= [],
let origins = [],
destinations = [];
newData.forEach( data => {
newData.forEach(data => {
origins.push(data.xVar); // all origins
destinations.push(data.yVar) // all destinations
});
......@@ -944,16 +945,16 @@ const createFlowLayer = (geojson, type, addOnCreate) => {
destinations = destinations.filter((v, i, a) => a.indexOf(v) === i); // get unique ones
// add missing combinations with 0 trips
origins.forEach( (o) => {
destinations.forEach( (d) => {
if (!newData.some( data => data.xVar === o && data.yVar === d ) ) {
newData.push({'xVar': o, 'yVar': d, 'flowCount': 0});
origins.forEach((o) => {
destinations.forEach((d) => {
if (!newData.some(data => data.xVar === o && data.yVar === d)) {
newData.push({ 'xVar': o, 'yVar': d, 'flowCount': 0 });
}
})
});
// sort array by origins and then by destinations
newData.sort( (el1,el2) => {
newData.sort((el1, el2) => {
let compared = compare(el1, el2, "xVar")
return compared == 0 ? compare(el1, el2, "yVar") : compared;
});
......@@ -989,7 +990,7 @@ const createFlowLayer = (geojson, type, addOnCreate) => {
},
// dot styles
style: function (geoJsonFeature) {
style: function(geoJsonFeature) {
if (geoJsonFeature.properties.isOrigin) {
return {
renderer: canvasPointRenderer,
......@@ -1020,9 +1021,9 @@ const createFlowLayer = (geojson, type, addOnCreate) => {
animationDuration: 2000,
customLayerId: type,
pane: "pane_flujos"
}).bindTooltip( layer => { // what to display on hover
}).bindTooltip(layer => { // what to display on hover
let coords = layer.getLatLng();
let label = od.features.filter( f => f.properties.lng == coords.lng && f.properties.lat == coords.lat);
let label = od.features.filter(f => f.properties.lng == coords.lng && f.properties.lat == coords.lat);
return label[0].properties.nombre;
})
......@@ -1031,6 +1032,10 @@ const createFlowLayer = (geojson, type, addOnCreate) => {
flowMapLayer.addTo(map).on('click', odClick);
let amchart = am4core.registry.baseSprites.find(c => c.htmlContainer.id === "amchartdiv");
amchart.data = newData;
let amchart2 = am4core.registry.baseSprites.find(c => c.htmlContainer.id === "prueba2");
amchart2.data = newData;
amchart2.data = amchart2.data.filter(function(e) { return e.flowCount > 0 });
}
flowMapsArray.push(flowMapLayer);
resolve(flowMapsArray);
......@@ -1135,15 +1140,15 @@ const makeBaseMap = () => {
// create one flow, then another, then another...
// and finally set reset control funcionality
createFlowLayer("data/viajes_ocupados_desde.geojson", "ocupadosDesde", true)
.then( () => createFlowLayer("data/viajes_ocupados_hacia.geojson", "ocupadosHacia") )
.then( () => createFlowLayer("data/viajes_ocupados_entre.geojson", "ocupadosEntre") )
.then( () => createFlowLayer("data/viajes_ocupados_POIC_desde.geojson", "poicDesde") )
.then( () => createFlowLayer("data/viajes_ocupados_POIC_hacia.geojson", "poicHacia") )
.then( () => createFlowLayer("data/viajes_ocupados_POIC_entre.geojson", "poicEntre") )
.then( layers => {
.then(() => createFlowLayer("data/viajes_ocupados_hacia.geojson", "ocupadosHacia"))
.then(() => createFlowLayer("data/viajes_ocupados_entre.geojson", "ocupadosEntre"))
.then(() => createFlowLayer("data/viajes_ocupados_POIC_desde.geojson", "poicDesde"))
.then(() => createFlowLayer("data/viajes_ocupados_POIC_hacia.geojson", "poicHacia"))
.then(() => createFlowLayer("data/viajes_ocupados_POIC_entre.geojson", "poicEntre"))
.then(layers => {
// reset to all flows displayed
$("#resetFlows").on("click", () => {
layers.forEach( layer => {
layers.forEach(layer => {
if (map.hasLayer(layer)) {
layer.originAndDestinationGeoJsonPoints.features.forEach(function(feature) {
if (feature.properties.isOrigin === true) {
......
......@@ -40,23 +40,23 @@ am4core.ready(function() {
//heatLegend.minValue = minValue;
//heatLegend.maxValue = maxValue;
heatLegend.minValue = 0;
heatLegend.maxValue = intervals[option].values[intervals[option].values.length-1];
heatLegend.maxValue = intervals[option].values[intervals[option].values.length - 1];
// update heatLegend colors
let heatColors = [];
["#333", ...intervals[option].colors].forEach( c => heatColors.push(am4core.color(c)) );
["#333", ...intervals[option].colors].forEach(c => heatColors.push(am4core.color(c)));
heatLegend.minColor = heatColors[0];
heatLegend.maxColor = heatColors[intervals[option].colors.length - 1];
//let checkConditions = [minValue, ...intervals[option].values.slice(1)];
let checkConditions = [minValue, ...intervals[option].values];
let lastValue = intervals[option].values[intervals[option].values.length-1]
let lastValue = intervals[option].values[intervals[option].values.length - 1]
// Override heatLegend gradient
let gradient = new am4core.LinearGradient();
heatColors.forEach(function(color, index) {
// addColor(color, opacity, offset) use offset to put colors in proper alignment
gradient.addColor(color, undefined, (checkConditions[index] - checkConditions[0])/lastValue);
gradient.addColor(color, undefined, (checkConditions[index] - checkConditions[0]) / lastValue);
});
//heatLegend.markers.template.applyOnClones = true;
......@@ -70,14 +70,14 @@ am4core.ready(function() {
let workingValue = column.dataItem.values["value"].workingValue;
// use min max values calculated from data on beforedatavalidated
if (am4core.type.isNumber(workingValue)) {
checkConditions.forEach( (condition, index) => {
if ( index < checkConditions.length-1 ) {
if (workingValue >= condition && workingValue <= checkConditions[index+1]) {
checkConditions.forEach((condition, index) => {
if (index < checkConditions.length - 1) {
if (workingValue >= condition && workingValue <= checkConditions[index + 1]) {
//console.log(`${workingValue} entre ${condition} y ${checkConditions[index+1]}`)
fill = new am4core.Color(
am4core.colors.interpolate(
heatColors[index].rgb,
heatColors[index+1].rgb,
heatColors[index + 1].rgb,
workingValue
)
);
......@@ -119,7 +119,7 @@ am4core.ready(function() {
xAxis.events.on("sizechanged", function(ev) {
let axis = ev.target;
let cellWidth = axis.pixelWidth / (axis.endIndex - axis.startIndex);
axis.renderer.labels.template.maxWidth = 2*Math.ceil(cellWidth)*0.8;
axis.renderer.labels.template.maxWidth = 2 * Math.ceil(cellWidth) * 0.8;
});
// on data change change, resize labels
......@@ -127,7 +127,7 @@ am4core.ready(function() {
xAxis.events.on("datarangechanged", function(ev) {
let axis = ev.target;
let cellWidth = axis.pixelWidth / (axis.endIndex - axis.startIndex);
axis.renderer.labels.template.maxWidth = 2*Math.ceil(cellWidth)*0.8;
axis.renderer.labels.template.maxWidth = 2 * Math.ceil(cellWidth) * 0.8;
});
xAxis.renderer.labels.template.fontSize = 12;
......@@ -184,7 +184,7 @@ am4core.ready(function() {
columnTemplate.adapter.add("strokeWidth", function(width, column) {
var workingValue = column.dataItem.values["value"].workingValue;
if (am4core.type.isNumber(workingValue)) {
width = workingValue != 0 ? 1: 0;
width = workingValue != 0 ? 1 : 0;
}
return width;
});
......@@ -227,8 +227,7 @@ am4core.ready(function() {
column.strokeWidth = 2;
column.strokeOpacity = 0.2;
heatLegend.valueAxis.showTooltipAt(column.dataItem.value);
}
else {
} else {
column.strokeWidth = 0;
column.strokeOpacity = 0;
heatLegend.valueAxis.hideTooltip();
......@@ -246,4 +245,85 @@ am4core.ready(function() {
chart.responsive.enabled = true;
//+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++CC
// Themes begin
am4core.useTheme(am4themes_animated);
// Themes end
var cd_chart = am4core.create("prueba2", am4charts.ChordDiagram);
var cd_title = cd_chart.titles.create();
//cd_title.text = "Viajes de ocupados desde centros de mercado";
cd_title.fill = am4core.color(mainTextColor);
cd_title.fontSize = 13;
cd_title.align = "left";
cd_title.marginBottom = 20;
cd_title.paddingLeft = 10;
cd_chart.events.on("beforedatavalidated", function(ev) {
let option = $("#indicatorSelect").val();
let optionTitle = $("#indicatorSelect option:selected").text();
cd_title.text = "[bold]Conectividad origen -destino entre \n" + optionTitle.toLowerCase();
//var data = ev.target.data;
//let data = data.filter(function(e) { return e.flowCount > 0 });
//console.log(data);
});
cd_chart.dataFields.fromName = "xVar";
cd_chart.dataFields.toName = "yVar";
cd_chart.dataFields.value = "flowCount";
//cd_chart.labels.fontSize = 15;
// make nodes draggable
var nodeTemplate = cd_chart.nodes.template;
nodeTemplate.readerTitle = "Oculta/muestra para reorganizar la red"; //"Click to show/hide or drag to rearrange";
nodeTemplate.showSystemTooltip = true;
var nodeLink = cd_chart.links.template;
var bullet = nodeLink.bullets.push(new am4charts.CircleBullet());
bullet.fillOpacity = 0.8;
bullet.circle.radius = 3;
bullet.locationX = 0.5;
// create animations
cd_chart.events.on("over", function() {
// nodeTemplate.events.on("ready", function() {
for (var i = 0; i < cd_chart.links.length; i++) {
var link = cd_chart.links.getIndex(i);
var bullet = link.bullets.getIndex(0);
animateBullet(bullet);
}
})
function animateBullet(bullet) {
var duration = 3000 * Math.random() + 2000;
var animation = bullet.animate([{ property: "locationX", from: 0, to: 1 }], duration)
animation.events.on("animationended", function(event) {
animateBullet(event.target.object)
})
}
var label = nodeTemplate.label;
label.relativeRotation = 90;
label.fontSize = 10;
label.fill = am4core.color(mainTextColor);
//label.wrap = true;
//label.bent = true;
//cd_chart.responsive.enabled = true;
}); // end am4core.ready()
\ No newline at end of file
This diff is collapsed.
......@@ -494,4 +494,4 @@ am4core.ready(function() {
}); // end am4core.ready()*/
\ No newline at end of file
}); // end am4core.ready */
\ No newline at end of file
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment