<?php

/**
 * Utilitaires pour l'import des observations et documents attachés
 *
 * @plugin     Biodiv
 * @copyright  2008-2025
 * @author     Renaud LAURETTE
 * @licence    GNU/GPL
 * @package    SPIP\Biodiv\Fonctions
 */
 
/** 
 * Taille maximale en octets d'une photo associée à une observation pour 
 * un téléchargement. Ne s'applique pas quand l'image est obtenue par 
 * redimensionnement automatique. 
 */
define('_TAILLE_MAX_OBSERVATION', 1048576); // 1 Mo


/**
 * Retourne les extensions autorisées pour les fichiers joints aux observations
 *
 * @return array	Tableau (extension => image-type)
 */
function documenter_observation_formats() {
	// les clefs sont les extensions acceptées en entrée qui seront converties en valeurs
	$formats = array(
		'jpg'  => 'jpg',
		'jpeg' => 'jpg',
		'jpe'  => 'jpg',
		'png'  => 'png',
		'gif'  => 'gif',
		'mp3'  => 'mp3'
		);
	return $formats;
}

/**
 * Taille maximale de fichier autorisée en téléchargement en fonction de l'extension
 *
 * @param string ext	Extension du nom de fichier
 * @return int			Taille autorisée en octets
 */
function taille_max_format($ext) 
{
	switch($ext) {
	case 'jpg':
	case 'png':
	case 'gif':
		return _TAILLE_MAX_OBSERVATION;
	case 'mp3':
		return 2*_TAILLE_MAX_OBSERVATION;
	default:
		return 0;
	}
}

/**
 * Génère un radical de nom de fichier pour une observation
 *
 * Lors du téléchargement d'un fichier ou du redimensionnement dynamique d'une image
 * le nom du fichier d'origine est remplacé par un nom généré automatiquement sur
 * la base de l'identifiant de l'observation à laquelle le document sera lié.
 *
 * @param int|string $idobs		Identifiant de l'observation
 * @param int $nbfich			Rang du document dans les attachements à l'observation
 * @return string				Nom (basename) de fichier généré
 * @example `obs_1678_3` sera généré pour la 3ème photo de l'observation 1678
 */

function radical_cible_observation($idobs,$nbfich) {
	$cible = "obs_" . $idobs . "_" . $nbfich;
	return $cible;
}

/**
 * Sépare le radical et l'extension d'un nom de fichier avec ou sans chemin en entrée
 *
 * @param string $file			Nom de fichier
 * @return array				[radical, extension]
 */
function radical_et_extension($file)
{
  $fichier = basename($file);
  $ext = substr($fichier,strrpos($fichier,".")+1);
  $radical = substr($fichier,0,strrpos($fichier,"."));
  return array($radical, $ext);
}

/**
 * Calcule la période du jour en fonction de l'heure
 *
 * Biodiv n'enregistre pas l'heure des observations mais seulement la période du jour.
 * Dans le cas où la date et l'heure sont obtenues d'informations EXIF d'une photo,
 * l'heure doit être convertie en période du jour.
 *
 * @used-by		date_et_periode_depuis_exif()
 * @param int $heure	Heure (0-23)
 * @return string		Période du jour
 */
function periode_du_jour($heure) 
{
  if(intval($heure) < 5) {
    $value = 'nuit';
  } elseif (intval($heure) < 7) {
    $value = 'lever du soleil';
  } elseif(intval($heure) < 12) {
    $value = 'matin';
  } elseif(intval($heure) < 19) {
    $value = 'apres-midi';
  } elseif(intval($heure) < 22) {
    $value = 'coucher du soleil';
  } else {
    $value = 'nuit';
  }
  return $value;
}

/**
 * Extraction de la date et de l'heure de l'EXIF d'une photo
 *
 * Traite une chaine contenant une date EXIF et en extrait les différents composants
 * pour les transformer en une date au format biodiv (mysql) et en une période du jour
 * retourne un array [date,periode] ou null
 *
 * @uses		periode_du_jour()
 * @param string $date_exif	Date EXIF
 * @return array|null		Tableau [YYYY-MM-DD,periode] 
 */
function date_et_periode_depuis_exif($date_exif) 
{
   $detp = array();
   $pattern=",(\d{4})\:(\d{2})\:(\d{2}) (\d{2})\:\d{2}\:\d{2},";
   
   if(preg_match($pattern,$date_exif,$parts)) {
     $detp['date'] = $parts[1]."-".$parts[2]."-".$parts[3];
     $detp['periode'] = periode_du_jour($parts[4]);
     return $detp;
   }
   
   return null;
}

/**
 * Controle de la validité d'un fichier à joindre à une observation
 *
 * Le fichier doit être lisible, sa taille est limitée, 
 * son extension doit être valide. 
 * Retourne l'extension à utiliser si ok, null sinon.
 * 
 * @uses	radical_et_extension()
 * @uses	documenter_observation_formats()
 *
 * @param string $chemin_complet	Chemin d'accès au fichier
 * @return array					[error_message|null, extension|null]
 */
function controle_fichier_observation($chemin_complet)
{
  // lisibilité
  if(!is_readable($chemin_complet)) 
  	  return array("Fichier illisible. ",null);
  
  // extension
  list($radical,$extension) = radical_et_extension($chemin_complet);
  $extok = documenter_observation_formats();
  if(in_array($extension, array_keys($extok))) 
  	  return array(null, $extok[$extension]);
  
  // échec
  return array("Extension '$extension' interdite. ",null);
  
  // TODO: clarifier limitation de taille
  if(filesize($chemin_complet) > taille_max_format($extok[$extension])) 
  	  return array("Fichier trop gros. ", null);
}



?>