diff -r efd9c589177a -r c0b4a8b5a012 toolkit/exemples/libraries/nco/streamgraph.js --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/toolkit/exemples/libraries/nco/streamgraph.js Thu Apr 10 14:20:23 2014 +0200 @@ -0,0 +1,453 @@ +/** + * Streamgraph + * + * Faut-il remettre la grille pour que le curseur puisse y coller + * Faut-il un template html pour la timeline? + */ + +function Streamgraph(json, parametres) { + this.parametres = { + name: null, + hauteur: 400, + largeur: 900, + selector: "#streamgraph", + + couleurs: null, + relations: null, + activerSelection: false, + activerCurseur: false, + activerTimeline: false, + + transitionDuration: 1000 + }; + + this.etendre(parametres); + + /* -- Gestion des valeurs par défaut -- */ + if (null==this.parametres.name) { + this.parametres.name = this.parametres.selector; + } + + /* -- Initialisation d'attributs -- */ + var object = this; + this.streamgraph = null; + this.visuel = null; + + this.area = d3.svg.area() + .x(function(d) { + return d.x * object.parametres.largeur / object.mx; + }) + .y0(function(d) { + return object.parametres.hauteur + - d.y0 * object.parametres.hauteur / object.my; + }) + .y1(function(d) { + return object.parametres.hauteur + - (d.y + d.y0) * object.parametres.hauteur / object.my; + }); + + + this.dataJSON = json; + this.dataStreamgraph = this.getDataStreamgraph(this.dataJSON); + + this.duree = this.dataStreamgraph[0].length; + this.nbClusters = this.dataStreamgraph.length; + + if (null==this.parametres.couleurs) { + this.parametres.couleurs = new Couleurs(this.nbClusters); + } + + this.pas = this.parametres.largeur/this.duree; + this.mx = this.dataStreamgraph[0].length - 1; + this.my = d3.max(this.dataStreamgraph, function(d) { + return d3.max(d, function(d) { + return d.y0 + d.y; + }); + }); + + /* -- Create the streamgraph -- */ + + /* -- Création des éléments HTML -- */ + + /* -- Création des barres de sélection -- */ + if (this.parametres.activerSelection) { + jQuery(this.parametres.selector) + .prepend("
") + .prepend("") + .prepend("") + .prepend("") + .prepend(""); + + // Sélecteurs latéraux + this.selecteurGauche = jQuery(this.parametres.selector + ' .selecteur.gauche'); + this.selecteurDroit = jQuery(this.parametres.selector + ' .selecteur.droite'); + this.selection = jQuery(this.parametres.selector + ' .selection'); + this.cacheDroit = jQuery(this.parametres.selector + ' .cache.droite'); + this.cacheGauche = jQuery(this.parametres.selector + ' .cache.gauche'); + } + + /* -- Création d'un curseur -- */ + if (this.parametres.activerCurseur) { + this.curseur = d3.select(this.parametres.selector) + .append("div").classed("curseur", true); + } + + /* -- Création de l'élément streamgraph -- */ + this.visuel = d3.select(this.parametres.selector) + .style("width", this.parametres.largeur + "px") + .style("height", this.parametres.hauteur + "px") + .append("svg:svg"); + + this.visuel.selectAll("path") + .data(this.dataStreamgraph).enter().append("svg:path") + .style("fill", function(datum, index) { + return object.parametres.couleurs.get(index); + }) + .attr("d", this.area); + + if (null!=this.parametres.relations) { + this.parametres.relations.add(this.parametres.name, this); + + this.visuel.selectAll("path") + .each(function(datum, index) { + var item = d3.select(this).attr("id", index); + datum["relationName"] = object.parametres.name +'.cluster.'+ index; + object.parametres.relations.add(datum.relationName, item); + }); + } + + /* -- Création d'une timeline -- */ + if (this.parametres.activerTimeline) { + this.timeline = d3.select(this.parametres.selector) + .append("div").classed("timeline", true); + this.generateTimeline(); + } + + /* -- Configuration des barres de sélection -- */ + if (this.parametres.activerSelection) { + // Sélecteur gauche + this.selecteurGauche.draggable({ + axis : 'x', + cursor: "move", + containment: [0, 0, + this.parametres.largeur - parseInt(this.selecteurDroit.css("width")), + this.parametres.hauteur], + drag: function() { object.followSelecteur(object.parametres.selector, object.parametres.largeur); }, + stop: function(e, ui){ + object.calculerPositions(); + object.followSelecteur(object.parametres.selector, object.parametres.largeur); + object.contain(object.parametres.selector, object.parametres.largeur ); + if (undefined!=object.__onselectionResize) { + object.__onselectionResize( + object.positionsBarres[0], object.positionsBarres[1]); + } + } + }); + + // Sélecteur droit + this.selecteurDroit.draggable({ + axis : 'x', + cursor: "move", + containment: [0, 0, + this.parametres.largeur - parseInt(this.selecteurDroit.css("width")), + this.parametres.hauteur], + drag: function() { object.followSelecteur(object.parametres.selector, object.parametres.largeur); }, + stop: function(e, ui){ + object.calculerPositions(); + object.followSelecteur(object.parametres.selector, object.parametres.largeur); + object.contain(object.parametres.selector, object.parametres.largeur ); + if (undefined!=object.__onselectionResize) { + object.__onselectionResize( + object.positionsBarres[0], object.positionsBarres[1]); + } + } + }); + + // Barre de déplacement de la sélection + this.selection.draggable({ + axis : 'x', + cursor: "move", + containment: [ + parseInt(this.selecteurGauche.css("width")), + 0, + this.parametres.largeur - parseInt(this.selecteurDroit.css("width")), + this.parametres.hauteur], + drag: function() { object.followSelection(object.parametres.selector, object.parametres.largeur); }, + stop: function(e, ui) { + object.followSelection(object.parametres.selector, object.parametres.largeur); + object.calculerPositions(); + object.contain(object.parametres.selector, object.parametres.largeur); + if (undefined!=object.__onselectionResize) { + object.__onselectionResize( + object.positionsBarres[0], object.positionsBarres[1]); + } + } + }); + + /* -- Placement initial des éléments -- */ + this.selecteurGauche.css("left", "0px"); + this.selecteurDroit.css("left", this.parametres.largeur - parseInt(this.selecteurDroit.css("width")) + "px"); + this.cacheGauche.css({"left": "0px", "width": "0px"}); + this.cacheDroit.css({"left": this.largeur + "px", "width": "0px"}); + + this.positionsBarres = [0, this.duree]; + } + + /* -- Configuration du curseur -- */ + if (this.parametres.activerCurseur) { + if (undefined!=this.parametres.relations) { + this.parametres.relations.add(this.parametres.name + ".curseur"); + } + } +}; + +Streamgraph.prototype = { + constructor: Streamgraph, + + etendre: function(parametres) { + if (null==parametres || "object"!=typeof(parametres)) { + return; + } + + for (var cle in parametres) { + this.parametres[cle] = parametres[cle]; + } + }, + + getDataStreamgraph : function(clusters) { + var data = new Array(), + duree = clusters[0].timeline.length; + + var dataCluster, timeline; + for (var i=0, end=clusters.length; i