[(#REM) Modèle pour produire des graphiques avec Chart.js Usage recommandé (les 2 exemples produisent le même résultat) : - Dans le texte d'un contenu : - Dans un squelette : #MODELE{chart, type=line, data=#ARRAY{patates,#LISTE{10,20,30},poireaux,#LISTE{5,10,15}}} Paramètres : **obligatoires *recommandés - id_chart : Identifiant unique du graphe, par défaut généré aléatoirement - *class : Classes supplémentaires du conteneur - width : Largeur en px, sans l'unité - height : Hauteur en px, sans l'unité - **type : Type de graphique (string) pie (défaut) | line | bar | horizontalBar | radar | doughnut | polarArea | bubble | scatter | area | mixed - **data : Jeux de données (string|array) - a) soit des séries de nombres séparés par des virgules et le séparateur 'next' Ex. : "10,20,30 next 5,10,15" - b) soit un tableau linéaire Ex. #LISTE{10,20,30} - c) soit un tableau simple avec labels et données (recommandé) Ex. : #ARRAY{ patates, #ARRAY{10,20,30}, poireaux, #ARRAY{5,10,15} } - d) soit un tableau complet avec *toutes* les options, si on sait ce qu'on fait. Dans ce cas là, c'est vous qui décidez de tout : les couleurs etc. Ex. : #LISTE{ #ARRAY{label,patates, data,#LISTE{10,20,30}, borderColor,red}, #ARRAY{label,poireaux, data,#LISTE{5,10,15}, borderColor,blue} } Pour le type bubble, il faut des séries de 3 chiffres correspondant à x, y, et radius Pour le type scatter, il faut des séries de 2 chiffres correspondant à x et y - *labels : Labels utilisés en abscisse (string|array) - soit des mots séparés par des virgules : "2005,2006,2007" - soit un tableau : #LISTE{carotte,chou,tomate} - dataLabels : Labels de chaque jeu de données (string|array) Inutile si vous passez un tableau c) ou d) au paramètre 'data' - soit des mots séparés par des virgules : "patates,poireaux" - soit un tableau : #LISTE{patates,poireaux} - labelX : Label de l'abscisse (string) - labelY : Label de l'ordonnée (string) - uniteX : TODO Unité ajoutée aux valeurs de l'abscisse (string) - uniteY : TODO Unité ajoutée aux valeurs de l'ordonnée (string) - axeX : Afficher l'ordonnée (bool|string) true (défaut) | false - axeY : Afficher l'abscisse (bool|string) true (défaut) | false - beginAtZero : pour commencer les ordonnées à zéro - colors : Codes de couleurs à utiliser : nom, hexadécimal, rgb, rgba, hsl, hsla - soit des valeurs séparées par des virgules : "turquoise,blue" - soit un tableau : #LISTE{turquoise,blue} - borderWidth : Épaisseur des bordures, sans l'unité (int) Défaut = 1 - fill : Remplir ou pas les graphes (string|bool) true | false (dépend des types) - fontSize : Taille de police en px, sans l'unité (int) - fontColor : Code couleur de la police : nom, hexadécimal, etc. - lineTension : Lissage des courbes (int) Nombre entre 0 (lignes droites) et 1 (courbes, défaut) - options : Tableaux complet d'options, si on sait ce qu'on fait (array) Prend le pas sur les autres options données individuellement Exemple : #ARRAY{responsive,false} - stacked : Pour avoir des données empilées (string) true | false (défaut) - responsive : Mode responsive true (défaut) | false - datasets : => data - animation : ? - datasetFill : => fill - canvaswidth : => width - canvasheight : => height - strokeColor : => borderColor - pointColor : => backgroundColor - pointstrokecolor : => borderColor - pointHighlightFill : => backgroundColor - pointHighlightStroke : => borderColor - scaleFontSize : => fontSize - scaleFontColor : => fontColor - scaleLabelUnit : => uniteY - bezierCurve : => interpolation ] [(#REM) ============================ 1) Normaliser les paramètres ============================ ] [(#REM) Base ] #SET{type, #ENV{type,pie}|trim|strtolower} #SET{alias, #ARRAY{polararea,polarArea,horizontalbar,horizontalBar}} #SET{type, #GET{alias/#GET{type}}|sinon{#GET{type}}} [(#SET{id_random, #GET{type}|concat{_}|uniqid})] #SET{id_graph, #VAL{spipchart_}|concat{#ENV{id_chart,#ENV{id,#GET{id_random}}}}|replace{'\s'}} #SET{donnees, #ENV{data,#ENV{datasets}}} [(#REM) Dimensions ] #SET{width, #ENV{width,#ENV{canvaswidth}}} #SET{width_unit, #GET{width}|concat{#GET{width}|match{\w\{2\}$}|?{px}}} #SET{width_int, #GET{width}|intval|sinon{''}} #SET{height, #ENV{height,#ENV{canvasheight}}} #SET{height_unit, #GET{height}|concat{#GET{height}|match{\w\{2\}$}|?{px}}} #SET{height_int, #GET{height}|intval|sinon{''}} [(#REM) Apparence ] #SET{colors_defaut,#LISTE{#69D2E7,#E0E4CC,#F38630,#96CE7F,#CEBC17,#CE4264,#F7464A,#46BFBD,#FDB45C,#FD7B9B,#8C99FD,#A2DB2F,#DB7368,#6B84DB,#DBBF37,#DB97AB,#2EC087}} #SET{colors, #ENV{colors}|is_null|?{ #ARRAY, #ENV{colors}|is_string|?{#ENV{colors}|replace{' '}|explode{','}, #ENV{colors}} }} #SET{colors, #GET{colors}|array_merge{#GET{colors_defaut}}} #SET{fills, #ARRAY{line,false, bar,true, pie,true, radar,false, polarArea,false, scatter,false, bubble,true}} #SET{fill, #ENV{fill,#ENV{datasetFill,#GET{fills/#GET{type}}}}} #SET{lineTension, #ENV{lineTension,#ENV{bezierCurve}}} #SET{lineTension, #GET{lineTension}|is_null|?{'',#GET{lineTension}|=={true}|?{ 1, #GET{lineTension}|=={false}|?{0,#GET{lineTension}} }|floatval}} [(#REM) Axes ] #SET{axeX, #ENV{axeX}} #SET{axeY, #ENV{axeY}} #SET{labelX, #ENV{labelX}} #SET{labelY, #ENV{labelY}} #SET{uniteX, #ENV{uniteX}} #SET{uniteY, #ENV{uniteY}} #SET{beginAtZero, #ENV{beginAtZero}|?{#EVAL{true}, #EVAL{false}}} [(#REM) Options ] #SET{stacked, #ENV{stacked}|=={true}|?{true}} #SET{responsive, #ENV{responsive}|=={false}|?{false}} #SET{fontSize, #ENV{fontSize,#ENV{scaleFontSize}}|intval|sinon{''}} #SET{fontColor, #ENV{fontColor,#ENV{scaleFontColor}}} [(#REM) ================================== 2) Préparer les données pour le JS ================================== On construit 3 tableaux qu'ils nous suffira d'encoder en JS dans le script : data, labels, options. ] [(#REM) Jeux de données Au final on veut obtenir un tableau de la forme suivante : array ( array ( 'label' => 'patates', 'data' => array(10,30,20), 'option1' => 'x', 'option2' => 'y', ), array ( 'label' => 'poireaux', 'data' => array(20,40,10), 'option1' => 'x', 'option2' => 'y', ) ) ] [(#REM) On convertit le texte en tableau si nécessaire ] [(#GET{donnees}|is_string|oui) #SET{donnees, #VAL{chartjs_explode_virgule}|array_map{#GET{donnees}|explode{next}}} ] [(#REM) Si on a un tableau linéaire, on le réarrange ] [(#GET{donnees/0}|is_string|oui) #SET{donnees,#LISTE{#GET{donnees}}} ] [(#REM) Maintenant on a 2 options : - si on a un tableau complet on le prend tel quel - sinon on construit le tableau complet nous-même ] #SET{datasets, #ARRAY} #SET{datalabels, #ENV{dataLabels}|is_string|?{#ENV{dataLabels}|explode{','}, #ENV{dataLabels}}} [(#GET{datalabels}|is_array|oui) #SET{datalabels, #VAL{trim}|array_map{#GET{datalabels}}}] #SET{tableau_est_complet, #GET{donnees/0/data}|?{oui}} #SET{cle, #COMPTEUR_BOUCLE|moins{1}} #SET{label, #GET{datalabels/#GET{cle}}|sinon{#CLE}} #SET{data, #VALEUR} [(#COMPTEUR_BOUCLE|=={1}|oui)#SET{data,#ARRAY}] #SET{data, #GET{data}|push{#ARRAY{x,#VALEUR{0},y,#VALEUR{1},r,#VALEUR{2}}}} [(#COMPTEUR_BOUCLE|=={1}|oui)#SET{data,#ARRAY}] #SET{data, #GET{data}|push{#ARRAY{x,#VALEUR{0},y,#VALEUR{1}}}} #SET{multiple_colors,pie|doughnut|polarArea} #SET{borderColor, #GET{type}|match{#GET{multiple_colors}}|?{ #GET{colors}, #GET{colors/#GET{cle}} }} #SET{backgroundColor, #GET{type}|match{#GET{multiple_colors}}|?{ #GET{colors}, #GET{colors/#GET{cle}} }} #SET{dataset, #ARRAY{ label, #GET{label}, data, #GET{data}, borderColor, #GET{borderColor}, backgroundColor, #GET{backgroundColor}, fill, #GET{fill,true}, }} [(#GET{lineTension}|ou{#GET{lineTension}|=={0}}|oui) #SET{dataset, #GET{dataset}|array_merge{#ARRAY{lineTension,#GET{lineTension}}}} ] #SET{datasets, #GET{datasets}|push{#GET{dataset}}} #SET{datasets, #GET{donnees}} [(#REM) Labels en abscisse ] #SET{labels, #ENV{labels}|is_string|?{#ENV{labels}|explode{','}, #ENV{labels}}} [(#GET{labels}|is_array|oui) #SET{labels, #VAL{trim}|array_map{#GET{labels}}}] [(#REM) Options générales : - si on a un tableau complet, on le prend tel quel - sinon, on les prend individuellement ] #SET{options, #ENV{options}} #SET{scales, #ARRAY{ x, #ARRAY{ display, #GET{axeX}, stacked, #GET{stacked}, scaleLabel, #ARRAY{display,#GET{labelX}|?{true}, labelString,#GET{labelX}}, ticks, #ARRAY{ font, #ARRAY{ size, #GET{fontSize}, color, #GET{fontColor} } } }, y, #ARRAY{ display, #GET{axeY}, stacked, #GET{stacked}, scaleLabel, #ARRAY{display,#GET{labelY}|?{true}, labelString,#GET{labelY}}, beginAtZero, #GET{beginAtZero}, ticks, #ARRAY{ font, #ARRAY{ size, #GET{fontSize}, color, #GET{fontColor} } } } }} #SET{legend, #ARRAY} #SET{nb_dimensions, #LISTE{#GET{width_int},#GET{height_int}}|array_filter|count} #SET{maintainaspectratio, #GET{nb_dimensions}|=={1}|?{false}} #SET{options,#ARRAY{ scales, #GET{scales}, legend, #GET{legend}, responsive, #GET{responsive}, maintainAspectRatio, #GET{maintainaspectratio} }} #SET{options, #GET{options}|chartjs_array_filter_recursive} [(#REM) ======================== 3) Affichage du graphique ======================== ]
#FILTRE{compacte}