<?php

/*******************************************************************************\
 * BIODIV, plugin et squelette pour SPIP - https://www.spip.net/               *
 *         dédié à la gestion d'observations naturalistes                      *
 *                                                                             *
 *         Copyright (C) 2008-2022 Renaud LAURETTE                             *
 *                                                                             *
 * BIODIV a été développé initialement pour le projet Biodiv.Balma de l'APCVEB *
 * (Association de Protection du Cadre de Vie et de l'Environnement balmanais) * 
 *     voir Biodiv.Balma : https://balma.biodiv.fr/                            *
 *     voir APCVEB : http://apcveb.free.fr/                                    *
 *                                                                             *
 *  Ce programme est un logiciel libre distribué sous licence GNU/GPL.         *
 *  Pour plus de détails voir les fichier COPYING.txt et LICENCE-BIODIV.md     *
\*******************************************************************************/

/*
 * Recoit un tableau data dont les index sont des années précédées d'un
 * x minuscule (eg. "x2007") et dont les valeurs sont des entiers positifs
 * (des comptages). Le script revoie un SVG dont la largeur fait 100% et
 * qui s'adapte en hauteur.
 * Parametres : 
 *		ENV{data} : le tableau
 *		ENV{titre} : le titre du graphique
 *		ENV{couleur} : la couleur de remplissage des barres
 */
    $i=0; $data = array(
     <BOUCLE_db(POUR) {tableau #ENV{data}} {","}> 
       "#CLE" => #VALEUR
     </BOUCLE_db>
     );
     
    if(count($data) == 0) {
        echo "<svg width='100%' height='auto' viewBox='-10 0 140 20'>\n"; 
        echo " <text x='50' y='60' transform='scale(0.2 0.2)' fill='black'>[(#ENV{titre}) - ]Aucune donnée.</text>\n";
        echo "</svg>\n";
    } else {
    
    $amin = $amax = $vmin = $vmax = $count =0;
    
    // Mise à jour des min/max
    foreach($data as $key => $value) {
      // Extraction de l'année
      preg_match('/x(\d{4})/',$key,$matches);
      $annee = $matches[1]; 
      $count += $value;
      if($i==0) {
      	$amin = $annee; $amax = $annee;
      	$i=1;
      } else {
      	$amin = ($annee < $amin)?$annee:$amin;
      	$amax = ($annee > $amax)?$annee:$amax;
      }
    }
     
    	// Dimensionnement des axes
    	$da = $amax - $amin +1;
    	$height = $da*10;
    	$yview = $height + 20;

    	// Graphique des années-mois
    	echo "<svg width='100%' height='auto' viewBox='-10 -2 260 $yview'>\n";
    	echo "<g style='stroke:black; stroke-width:0.5;'>\n";
    	echo "  <line x1='20' y1='$height' x2='20' y2='0' />\n";
    	echo "  <line x1='20' y1='$height' x2='125' y2='$height' />\n";
    	echo "</g>\n";
        echo " <g transform='scale(1 -1) translate(5 -$height)' style='stroke:black; fill:white; stroke-width:0.5;'>\n";

        $grid = array(); $valeurs = array();
        $imois = array('J','F','M','A','M','J','J','A','S','O','N','D');
        $vleg = "";
         
        for($i=0; $amin+$i <= $amax; $i++) {
          	// Initialisation des mois à white - 12 mois
          	for($j=0; $j<12; $j++) { $grid[$i][$j] = 'white'; }
          	$valeurs[$i]=0;
          	$py = $i*50 +20; $year = $amin+$i;
          	$vleg .= "<text x='-50' y='-$py' transform='scale(0.2 -0.2)' fill='black'>$year</text>\n";
        }
        $vleg .= "<text x='0' y='75' transform='scale(0.2 -0.2)' fill='black'>[(#ENV{titre}) - ]Total: $count observations</text>\n";
    
        foreach($data as $key => $value) {         
          	preg_match('/x(\d{4})-(\d{2})/',$key,$matches);
          	$annee = $matches[1]; $mois=$matches[2]-1;
          	$index = $annee - $amin;
            if($value==0) $color = 'white';
            	elseif($value==1) $color = '#93CA88';
            	elseif($value==2) $color = '#63A555';
            	elseif($value <5) $color = '#428733';
            	elseif($value <10) $color = '#276B19';
            	else $color = '#104805'; 
            $grid[$index][$mois] = $color;
            $valeurs[$index] += $value;
        }
        
        // Recherche des min/max des valeurs
        for($i=0; $amin+$i <= $amax; $i++) {
        	$value = $valeurs[$i];
        	if($i==0) {
        		$vmin = $value; $vmax=$value;
        	} else {
        		$vmin = ($value < $vmin)?$value:$vmin;
        		$vmax = ($value > $vmax)?$value:$vmax;
        	}
        }
        // Normalisation
        $dv = $vmax - $vmin;
    	if($dv > 0) {
    		$vb = floor(log10($dv));
    		$ygrad = pow(10,$vb);
    	} else {
    		$ygrad = 1;
    		$dv=1;
    	}
    	$yvmin = floor($vmin /$ygrad) * $ygrad;
    	$cy = 0;
    	if(($yvmin == $vmin) && ($vmin !=0)) {
    	  $yvmin = $yvmin - $ygrad;
    	  $cy = 1;
    	  }
    	$dyv = ceil($dv /$ygrad)+1+$cy;
    	$yvmax = $yvmin + $dyv*$ygrad;
        
        
        for($j=0; $j<12; $j++) {
            $px = $j * 10;
            for($i=0; $amin+$i <= $amax; $i++) {
            	$py = $i * 10;
            	echo "   <rect x='$px' y='$py' width='10' height='10' fill='".$grid[$i][$j]."'/>\n";
            }
            $tx = $j*50  + 20;
            echo "<text x='$tx' y='25' transform='scale(0.2 -0.2)' fill='black'>". $imois[$j] ."</text>\n";
        }
        
        echo $vleg;
        echo "</g>";
   	
    	/**** Graphique des années ****/   
    	$ys = floor(10/$dyv)*10;
    	echo "<g transform='scale(1 -1) translate(145 -$height)' style='stroke:black; fill:white; stroke-width:0.5;'>\n";
    	// axes et grille
    	echo "<line x1='0' y1='0' x2='0' y2='$height' />\n";
    	$ltx = $dyv * $ys; echo "<line x1='0' y1='0' x2='$ltx' y2='0' />\n";
    	echo "<g style='stroke:grey; stroke-width:0.2;'>\n";
    	for($i=1; $i<=$dyv; $i++) {
    		$ltx = $i*$ys;
    		echo "	<line x1='$ltx' y1='0' x2='$ltx' y2='$height' />\n";
    		$tx = ($ltx*5)-5; $yvg = $yvmin + ($i*$ygrad);
    		echo "	<text x='$tx' y='25' transform='scale(0.2 -0.2)' fill='black'>$yvg</text>\n";
    		}
    	
    	echo "	<text x='-5' y='25' transform='scale(0.2 -0.2)' fill='black'>$yvmin</text>\n";  	
    	echo "</g>\n";
    	
    	// Tracé des barres horizontales de données
    	echo "<g style='stroke:black; stroke-width:0.2;'>\n";
    	for($i=0; $amin+$i <= $amax; $i++) {
         	$px = $i*10 + 2;
         	$h = $ys*($valeurs[$i] - $yvmin)/$ygrad;
         	echo "   <rect y='$px' x='0' height='6' width='$h' fill='#ENV{couleur,#93CA88}'/>\n";
         	}
        echo "</g>\n";
         
        // Tracé des quantités
        for($i=0; $amin+$i <= $amax; $i++) {
         	$py = $i*50 + 20; $value = $valeurs[$i];
         	echo " <text x='-50' y='-$py' transform='scale(0.2 -0.2)' fill='black'>$value</text>\n";        
        }
        echo " </g>";
        echo "</svg>\n"; 
    }
?>