<?php

class helper_plugin_pot extends DokuWiki_Plugin {

	// Original code from plugin:color
	// validate color value $c
	// this is cut price validation - only to ensure the basic format is
	// correct and there is nothing harmful
	// three basic formats  "colorname", "#fff[fff]", "rgb(255[%],255[%],255[%])"


	function _isValidcolor($c) {

		$c = trim($c);

		$pattern = "/
            (^[a-zA-Z]+$)|                                #colorname - not verified
            (^\#([0-9a-fA-F]{3}|[0-9a-fA-F]{6})$)|        #colorvalue
            (^rgb\(([0-9]{1,3}%?,){2}[0-9]{1,3}%?\)$)     #rgb triplet
            /x";
		//print("<pre>".print_r($c, true)."</pre>");
		preg_match($pattern, $c, $out);
		//		return (preg_match($pattern, $c));
		return $out[0];
	}


	/**
	* format settings
	* we expect something like: " key=value | key2=value2 | key3=value3 "
	* and format it to an array[key][value]
	*/
	function _formatsettings($potsettings) {
		$pureset = $potsettings;
		$potsettings = explode('|', $potsettings); // splitt template name and arguments
		$potsettings = array_map('trim', $potsettings); //remove whitespaces, linebreaks
		$potsettings = array_filter($potsettings); //remove empty array entries
		$formatedsettings = array();

		foreach ($potsettings as $potsets) {
			$temp = explode('=', $potsets);
			$key = trim($temp[0]);
			$value = trim($temp[1]);

			// check some of the key=value to fit the value the way we like
			switch ($key) {
				case 'potid':
					$formatedsettings[$key] = $value;
					break;
				case 'color+':
					if ($value != '') {
						$formatedsettings[$key] = "color:".$this->_isValidcolor($value).";";
					} else {
						$value = "";
					}
					break;
				case 'color-':
					if ($value != '') {
						$formatedsettings[$key] = "color:".$this->_isValidcolor($value).";";
					} else {
						$value = "";
					}
					break;
				case 'display': // only limitet styles are allowed
					if ($value == 'none') {
						$value = 'display:none;';
					} else {
						//$value = 'display:inline-block;';
						$value = 'display:flex;';
					}
					$formatedsettings[$key] = $value;
					break;
				case 'float': // only limitet styles are allowed
					if ($value == 'right') {
						$value = 'float:right;';
					} else {
						//$value = 'display:inline-block;';
						$value = 'float:left;';
					}
					$formatedsettings[$key] = $value;
					break;
				case 'width': // TODO check value
					if ($value == '' || $value == 0) {
						$value = "";
						if ($formatedsettings['display'] != 'none') {
							$formatedsettings['display'] = ""; //no "width="" forces other no "display="
						} else {
							$value = "width:$value;";
						}
					}
					$formatedsettings[$key] = $value;
					break;
				case 'set':
					$formatedsettings[$key] = $value;
					$formatedsettings['pagedefault'] = preg_replace('/set|field/', 'var$0', $pureset); //replace var and field to avoid circles ?
					break;
				case 'defaultsettings':
					$formatedsettings[$key] = $value;
					break;

				default:
					$formatedsettings[$key] = $value;
					break;
			}
		}
		return $formatedsettings;
	}


	/**
	* calculating
	* we need: formula, decimals, sign for decimal-point, sign for thousend-point
	* we get: array with: result, formula, type
	*/
	function _calculate($formula, $mdec) {

		$calc = $formula;
		/**
		* this program section is based on
		* Plugin calc : petite calculatrice.
		*
		* @license    GPL 2 (http://www.gnu.org/licenses/gpl.html)
		* @author     Etienne Mauvais <emauvaisfr@yahoo.fr>
		*/
		$encore = 1;
		while ($encore) {
			$encore = 0;
			$calc = preg_replace_callback("/([a-z].+?\(.*?\))/",
				create_function('$f',
					'GLOBAL $encore;
							   $autorisees=Array("abs", "acos", "acosh", "asin", "asinh", "atan", "atan2", "atanh",
							                     "base_convert", "bindec",
							                     "ceil", "cos", "cosh",
							                     "decbin", "dechex", "decoct", "deg2rad",
							                     "exp", "expm1",
							                     "floor", "fmod",
							                     "getrandmax",
							                     "hexdec", "hypot",
							                     "is_finite", "is_infinite", "is_nan",
							                     "lcg_value", "log", "log10", "log1p",
							                     "max", "min", "mt_getrandmax", "mt_rand", "mt_srand",
							                     "octdec",
							                     "pi", "pow",
							                     "rad2deg", "rand", "round",
							                     "sin", "sinh", "sqrt", "srand",
							                     "tan", "tanh");

							   //print "  Trouve : ".$f[1];

							   $nomF=explode("(",$f[1]);
							   $nomF=$nomF[0];

							   if(in_array($nomF, $autorisees)) {
							     //print " -> autorisee\n";
							     return $f[1];
							   }
							   else {
							     //print " -> interdite !!!\n";
							     $encore=1;
							     return "";
							   }'
				),
				$calc);
		}

		//On retire les ";" et les "$"
		//Remove the ";" and the "$".
		$calc = preg_replace("/;/", "", $calc);
		$calc = preg_replace("/\$/", "", $calc);
		//if (is_numeric($calc)) { $calc = $calc; } else { $calc = "'$calc'"; }

		//On affiche un commentaire dans le source de la page
		//A comment is displayed in the source of the page
		//$renderer->doc .= "\n<!-- Calc : $calc -->\n";


		$calc_propre = $calc;
		$calc = "\$n=$calc;";

		//On passe en mode track_errors (apres avoir recupere l'ancien mode)
		//We switch to track_errors mode (after recovering the old mode)
		$track = ini_get('track_errors');
		ini_set('track_errors', 'true');
		$php_errormsg = "";
		try {
			eval($calc);
		}
		catch (Exception $e) {
			$error = "\"<b>Bad value...</b> ".$e->getMessage()."\"";
			//	      $renderer->doc .= "\"".$this->getLang('calc_valeurincorrecte')."\"";
			//	return true;
		}
		//On repasse dans l'ancien mode track_error
		//We go back to the old track_error mode
		ini_set('track_error', $track);

		//S'il y a eu une erreur (non catchee par try)
		//If there was an error (not catchee by try)
		if ($php_errormsg) {
			$error = "<b>pot Error: </b> ".$php_errormsg." <br /> check the formula:  ";
			//	      $renderer->doc .= "\"<b>".$this->getLang('calc_erreur')."</b> ".$php_errormsg."\"";
			//return true;
		}

		//Si la valeur retournee n'est pas un nombre (ex : sqrt(-1)
		//If the returned value is not a number (ex : sqrt(-1)
		if (is_nan($n)) {
			$error = "\"Bad value...\"";
			//	      $renderer->doc .= "\"".$this->getLang('calc_valeurincorrecte')."\"";
			//return true;
		}

		$out = $n;
		$result = preg_replace("/ /", "&nbsp;", $out);

		$type = 'formula';
		$calculated['error'] = $error;
		$calculated['type'] = $type;
		$calculated['result'] = $result;
		$calculated['formula'] = $formula;

		return $calculated;
	}
}