<?php
/**
 * compare_data.php - class for compare data.
 *
 * @author $Author: dtong $
 * @version $Id: compare_data.php,v 1.7 2011/05/09 04:48:53 dtong Exp $
 * @copyright Copyright (c) 2010, Tiller Software Co., Ltd.
*/

if ( ! defined('BASEPATH')) exit('No direct script access allowed');
require_once ('compare_data_config.php');

class Compare_data {
	private $config = false;

	function __construct () {
		$this->CI = & get_instance();
		$this->CI->load->model('unit/unit_model');
		//$this->CI->load->model('sort/sort_model');
		$this->CI->load->model('unit/lt_model');
		$this->CI->load->model('unit/resource_model');
		//$this->CI->load->model('sort/searchsort_model');
		$this->CI->load->model('unit/select_model');
		$this->CI->load->model('unit/last_model');

		osa_load_lang('unit');
		osa_load_lang('general');
		$this->CI->load->helper('date');
		$this->CI->load->library('unit/unit_init');
	}

	public function get_data_bytype($unit, $type, $module) {
		$unitid = FALSE;
		$unittype = FALSE;

		if ($unit !== FALSE && isset($unit)) {
			 if (is_object($unit) && isset($unit->unit->id)) {
			 	$unitid = (int)$unit->unit->id;
			 	$unittype = (int)$unit->unit->type;
			 }
		}

	   $TYPE_INT = $this->CI->unit_model->TYPE_INT;
	   $TYPE_UNI = $this->CI->unit_model->TYPE_UNI;

		if ($unittype == $TYPE_INT) {
			// if ($stage == CMS_UNIT_STAGE1)
			     //$unitid = (int)$unit->unit->parentid;
			     //$unitid = FALSE; // skip compare
		}
		elseif ($unittype == $TYPE_UNI) {
			 $currentid = $unitid;
			 $unitid = (int)$unit->unit->parentid;
		}

		$template = $unit->unit->template;

		$res = NULL;
		if ( $type === FALSE ){
			osa_errorlog(__METHOD__ . " -  Invalidate type", $type);
			echo $this->CI->load->view('unit/unit_htmlerror_view', array('errormsg'=>lang('unit_no_permissionmsg'),'form_name'=>'unit_history_form'),TRUE);
			exit;
		}
		$data = compare_data_config::get_data_module($type);
		if ( $data === FALSE ){
			osa_errorlog(__METHOD__ . " -  Invalidate data_module", $data);
			echo $this->CI->load->view('unit/unit_htmlerror_view', array('errormsg'=>lang('unit_no_permissionmsg'),'form_name'=>'unit_history_form'),TRUE);
			exit;
		}
		if ( array_key_exists($module, $data) )
			$data = $data[$module];
		if ( $data === FALSE ){
			osa_errorlog(__METHOD__ . " -  class module does not exist", $data);
			echo osa_buildererror();
			return FALSE;
		}
		$this->config = $data;
		$model = FALSE;
		$function = FALSE;
		if ($data !== FALSE && array_key_exists('model', $data))
			$model = $data['model'];
		if ($data !== FALSE && array_key_exists('function', $data))
			$function = $data['function'];

		if ($model !== FALSE && $function !== FALSE) {
			if ($unitid !== FALSE && $type !== FALSE) {
				$res = $this->CI->$model->$function($unitid , $type);
			}
		}

		if ($res != false && array_key_exists('sub_config', $data) && is_array($data['sub_config'] ) ) {
			foreach($data['sub_config'] as $sub_data) {
				if ($sub_data !== FALSE && array_key_exists('model', $sub_data))
					$model = $sub_data['model'];
				if ($sub_data !== FALSE && array_key_exists('function', $sub_data))
					$function = $sub_data['function'];

				if ($model !== FALSE && $function !== FALSE) {
					if ($unitid !== FALSE && $type !== FALSE) {
						$res['sub_data'][] = $this->CI->$model->$function($unitid , $type);
					}
				}
			}
		}
		return $res;
	}

	function compare_highlight(&$temp, $type, $color, $module) {
		$left = CMS_UNIT_COMPARE_LEFT;
		$right= CMS_UNIT_COMPARE_RIGHT;
		$unitleft = $temp[$left];
		$unitright = $temp[$right];

		$dbobjs_left  = $this->get_data_bytype($unitleft, $type, $module);
		$dbobjs_right = $this->get_data_bytype($unitright, $type, $module);

		if ($dbobjs_left === FALSE && $dbobjs_right === FALSE)
			return FALSE;

		$array = FALSE;
		$array = $this->data_to_array($dbobjs_left, $dbobjs_right);
		$alllevel = FALSE;
		if ( isset($this->config['alllevel']) )
			$alllevel = $this->config['alllevel'];
		$this->compare_array($cssid, $array ,
								   $this->config['db_id'],
	   						   $this->config['db_text'],
	   				         $this->config['db_type'],
	   				         $this->config['pre_css'],
	   				         $this->config['skipid']);
		$this->data_to_css($cssid, $temp, $color, $alllevel);
		if ( array_key_exists('sub_config', $this->config) && is_array($this->config['sub_config'])) {
			if (is_array($dbobjs_left) && array_key_exists('sub_data', $dbobjs_left))
				$dbobjs_left = $dbobjs_left['sub_data'];
			else
				$dbobjs_left = array();
			if (is_array($dbobjs_right) && array_key_exists('sub_data', $dbobjs_right))
				$dbobjs_right = $dbobjs_right['sub_data'];
			else
				$dbobjs_right = array();
			if (count($dbobjs_left) > count($dbobjs_right))
				$max_length = count($dbobjs_left);
			else
				$max_length = count($dbobjs_right);

			for ($i=0; $i < $max_length; $i++) {
				$config = $this->config['sub_config'][$i];
				$obj_left = array();
				if (array_key_exists($i, $dbobjs_left))
					$obj_left = $dbobjs_left[$i];
				$obj_right = array();
				if (array_key_exists($i, $dbobjs_right))
					$obj_right = $dbobjs_right[$i];

			   $sub_array = FALSE;

				if (!array_key_exists('groupbytext', $config))
					$config['groupbytext'] = FALSE;
			   if ($config['groupbytext'] === FALSE)
					$sub_array = $this->data_to_array($obj_left, $obj_right, $config['db_id'], $config['db_text']);
				else
					$sub_array = $this->sub_data_to_array($obj_left, $obj_right,
																	  $config['db_id'],
																	  $config['db_text'],
																	  $config['db_type'],
																	  $config['groupbytext']);

				$sub_cssid = array();
				$this->compare_array($sub_cssid, $sub_array ,
										   $config['db_id'],
			   						   $config['db_text'],
			   				         $config['db_type'],
			   				         $config['pre_css'],
			   				         $config['skipid']);

			   $this->data_to_css($sub_cssid, $temp, $color, $config['alllevel']);

		 		/* debug
		 		echo '<table width="100%" border="1"><tr valign="top"><td><pre>'. print_r($sub_array , true ) . '</pre></td>';
				  // echo '<td><pre>'. print_r($obj_right , true ) . '</pre></td> ';
			   echo '<td><pre>'. print_r($sub_cssid , true ) . '</pre></td></tr></table>';
			   */
			}
		}

		return TRUE;
	}

	private function data_to_css($cssarray, $html, $color='#FFDDDD', $alllevel=FALSE) {
		$skin = 'background-color: ';
		if (!is_array($cssarray) || count($cssarray)==0)
			 return $html;
		$alllevel = FALSE;
		if ( isset($this->config['alllevel']) )
			$alllevel = $this->config['alllevel'];
		$ishighlight = FALSE;
		foreach ($cssarray as $objdata) {
			if ($objdata === FALSE)
				break;

			foreach ($objdata as $key_lr => $css) {	//left or right
				if (isset($css) && $css != false) {
					foreach ($css as $type => $data) {
						$csscolor = $color;
						$style = "style='$skin {$csscolor}; '";
						$last  = count($data);
						if ($last<=1)
							$sep   = "border-top: solid 1px {$csscolor}; border-bottom: solid 1px {$csscolor}; \"";
						else
							$sep   = "border-top: solid 1px {$csscolor}; \"";
						foreach ($data as $key => $value) {
							$ishighlight = TRUE;
							$html[$key_lr]->unitbody = str_replace("$value","{$style}", $html[$key_lr]->unitbody );
						}
					}
				}
			}
			if ($ishighlight===TRUE && $alllevel===FALSE)
							 break;
		}
		return $html;
	}

	private function data_to_array($objleft, $objright, $fromid=FALSE, $fromtext=FALSE) {
		if ($fromid==FALSE || $fromtext==FALSE) {
			 $fromid = $this->config['db_id'];
			 $fromtext = $this->config['db_text'];
			 if (!is_array($fromid))
			 	  $fromid = array($fromid);
			 if (!is_array($fromtext))
			 	  $fromtext = array($fromtext);
		}
		if ($fromid==FALSE || $fromtext==FALSE)
			 return FALSE;
		if ($objleft==FALSE && $objright==FALSE)
			 return FALSE;

		$left = CMS_UNIT_COMPARE_LEFT;
		$right= CMS_UNIT_COMPARE_RIGHT;
		$cssid = CMS_UNIT_COMPARE_CSSID;

		$id    = 'id';
		$type  = 'type';
		$text  = 'text';
		$length= 'length';

		$data_comp = array($left=>$objleft, $right=>$objright);
		$save      = array($left=>null,  $right=>null);

		foreach ($data_comp as $key => $object) {
			$index = 1;
			if (isset($object) && $object != false) {
				$temp = array();
				foreach ($object as $data) {
					if (isset($data) && $data != false && is_array($data)) {
						foreach ($data as $value) {
							if (!is_object($value))
								continue;

							$temp[$value->type][$index][$type]  = $value->$type;

							if (is_array($fromid)) {
							foreach ($fromid as $field)
									$temp[$value->type][$index][$field] = $value->$field;
							}
							else
								$temp[$value->type][$index][$id]  = $value->$fromid;

							if (is_array($fromtext) && count($fromtext) > 0) {
								foreach ($fromtext as $field)
									$temp[$value->type][$index][$field] = $value->$field;
							}
							else
								$temp[$value->type][$index][$text]  = $value->$fromtext;

							if (isset($value->$length))
								$temp[$value->type][$index][$length]= $value->$length;

							$index += 1;
						}
					}
					else {
						if (isset($data->type)==FALSE ) {
							echo 'error data';
							//return TRUE;
						}
					//	$temp[$data->type][$index][$id]    = $data->$fromid;
						$temp[$data->type][$index][$type]  = $data->$type;

						if (is_array($fromid)) {
							foreach ($fromid as $field)
								$temp[$data->type][$index][$field] = $data->$field;
						}
						else
							$temp[$data->type][$index][$id]  = $data->$fromid;

						if (is_array($fromtext)) {
							foreach ($fromtext as $field)
								$temp[$data->type][$index][$field] = $data->$field;
						}
						else
							$temp[$data->type][$index][$text]  = $data->$fromtext;
/*
						if (is_array($fromtext)) {
							foreach ($fromtext as $field) {
								$temp[$data->type][$index][$field] = $data->$field;
								//$temp[$data->type][$index][$length.'_'.$field]= strlen($data->$field);
							}
						}
						else {
							$temp[$data->type][$index][$text]  = $data->$fromtext;
							//$temp[$data->type][$index][$length]= strlen($data->$fromtext);
						}*/
						$index += 1;
					}
				}
				$save[$key] = $temp;
			}
		}
		return $save;
	}

	private function sub_data_to_array($objleft, $objright, $fromid=FALSE, $fromtext=FALSE, $fromtype=FALSE, $groupby=FALSE) {
		if ($objleft==FALSE && $objright==FALSE)
			return FALSE;

		if ($fromid==FALSE || $fromtext==FALSE || $fromtype==FALSE || $groupby==FALSE ) {
			 return FALSE;
		}

		$left = CMS_UNIT_COMPARE_LEFT;
		$right= CMS_UNIT_COMPARE_RIGHT;

		$id    = 'id';
	   $choice= 'choice';
	   $text  = 'text1';

		$temp = array($left=>FALSE, $right=>FALSE);
		$data_comp = array($left=>$objleft, $right=>$objright);

		//make sub data to normal array
		foreach ($data_comp as $key => $sub) { // $key = left, right
			$data[$key] = array();
			if (isset($sub) && $sub != FALSE && !empty($sub) && is_array($sub) ) {
				foreach ($sub as $value) {
					if (isset($value) && $value != FALSE && !empty($value) && is_array($value) ) {
						 foreach ($value as $obj) {
						 	if ($obj != FALSE && is_array($obj)) {
						 		$data_id = 1;
						 		$keep = array();
						 		foreach ($obj as $subobj ) {
						 			if ($subobj != FALSE && is_object($subobj)) {
						 				$keep[$id] = $subobj->resid .'_'. $subobj->type .'_'. $subobj->choice;
						 				if ($groupby && isset($subobj->$text)) // fix bug
						 					$keep[$choice . $data_id] = md5($subobj->$text) . $subobj->restype .'_'. $subobj->type .'_'. $subobj->choice;
						 				else
						 					$keep[$choice . $data_id] = $subobj->restype .'_'. $subobj->type .'_'. $subobj->choice;
						 				$data_id += 1;
						 			}
						 	 	}

						 	 	if (!empty($fromtype) && is_array($fromtype))
						 	 		$fromtype = $fromtype[0];

								if ($fromtype !== FALSE && $key !== FALSE && $keep !== FALSE && is_array($keep) )
						 	 		$data[$key][$fromtype][] = $keep;
						 	 }
						 }
					}
				} // end for
			} // end if
		}

		if ($data[$left] == FALSE && $data[$right] == FALSE)
			return FALSE;

		return $data;
	}

	private function compare_array(&$output, $obj_array, $ids, $texts, $type=FALSE, $pre_css=FALSE, $skipid=FALSE) {
		$output = array();

		if ($obj_array===FALSE || !is_array($obj_array) || count($obj_array) != 2)
			 return FALSE;

		if ($ids !== FALSE && !is_array($ids))
			 $ids = array($ids);
		if ($texts !== FALSE && !is_array($texts))
			 $texts = array($texts);
      if ($pre_css !== FALSE && !is_array($pre_css))
			 if (count($texts) === 1)
			    $pre_css = array($texts[0]=>$pre_css);
			else
				 $pre_css = array($pre_css);

		if ($type===FALSE || $pre_css===FALSE)
			 return FALSE;
		if (!empty($type) && is_array($type))
			$type = $type[0]; //hardcode

		$left = CMS_UNIT_COMPARE_LEFT;
		$right= CMS_UNIT_COMPARE_RIGHT;
		$cssid = CMS_UNIT_COMPARE_CSSID;
		//$id = 'id';

		$save_comp = array($left=>array(), $right=>array());

		$objleft = FALSE;
		$objright = FALSE;

		foreach($obj_array as $key => $type_value) {
			if (!empty($type_value) && is_array($type_value) && array_key_exists($type, $type_value) && isset($type_value[$type]) ) {
				 $objtemp = array();
				 foreach($type_value[$type] as $item) {
				 	 $lastid = "";
				 	 $lastcss = "";
					 foreach ($ids as $index => $id) {
					 	if ($lastid !== $id) {
					 	    $lastid = $id;

					 	    $temp = array();
							 if ($skipid===FALSE) {
								 if (isset($item['type']))
								     $temp['type'] = $item['type'];
								     $temp[$id] = $item[$id];
						 	 }
						 	 if (isset($texts[$index]) && isset($item[$texts[$index]]) && $item[$texts[$index]] != '') {
						 	 	 if (array_key_exists($texts[$index], $pre_css)) {
								    $temp[$texts[$index]] = $item[$texts[$index]];
								    $css = $cssid."='{$pre_css[$texts[$index]]}{$item[$id]}'";
								    //echo '<pre>'; var_dump($item[$texts[$index]]); echo '</pre>';
								    $objtemp[$css] = serialize($temp);
						 	 	 }
						 	 	 else
						 	 	 	log_message('error', __METHOD__ . " - Not found index in array Pre_css");
						 	 }

						 	 if (array_key_exists($texts[$index], $pre_css) && $lastcss !== $pre_css[$texts[$index]])
						 	     $lastcss = $pre_css[$texts[$index]];
						 	 else
						 	 	 	log_message('error', __METHOD__ . " - Not found index in array Pre_css");
					 	}
					 	else {
					 		$temp = array();
					 		if (isset($texts[$index]) && isset($item[$texts[$index]])) {
							    //$temp[$texts[$index]] = $item[$texts[$index]];
							    $css = $cssid."='{$pre_css[$texts[$index]]}{$item[$id]}'";
						 	}

						 	if ($lastcss !== $pre_css[$texts[$index]]) {
						 		 $lastcss = $pre_css[$texts[$index]];
							 	 if ($skipid===FALSE) {
									 if (isset($item['type']))
									     $temp['type'] = $item['type'];
									     $temp[$id] = $item[$id];
							 	 }
							 	 if (isset($texts[$index]) && isset($item[$texts[$index]])) {
								    $temp[$texts[$index]] = $item[$texts[$index]];
								    $css = $cssid."='{$pre_css[$texts[$index]]}{$item[$id]}'";
								    $objtemp[$css] = serialize($temp);
							 	 }
						 	}
						 	else {
							 	if (array_key_exists($css, $objtemp) && isset($texts[$index]) && isset($item[$texts[$index]])) {
							 		 $temp = unserialize($objtemp[$css]);
						 		 	 if (!array_key_exists($texts[$index], $temp)) {
						 		 		$temp[$texts[$index]] = $item[$texts[$index]];
						 		 		$objtemp[$css] =  serialize($temp);
						 		  	 }
						 		}
						 	}
					 	}
					}
				 }
				 if ($objleft===FALSE && $left == $key)
				 	  $objleft = $objtemp;
				 elseif ($objright===FALSE  && $right == $key)
				 	  $objright = $objtemp;

			}
		}
		if (($objleft===FALSE && $objright===FALSE) || (count($objleft) == count($objright) && count($objright) ==0)  )
			 return FALSE;

		$objmin = $objleft;
		$objmax = $objright;

		$key_min = $left;
		$key_max = $right;

		$leftcount = 0;
	 	$rightcount = 0;

	 	if (is_array($objleft))
	 		 $leftcount = count($objleft);
	 	if (is_array($objright))
	 		 $rightcount = count($objright);

	 	if ($leftcount >= $rightcount) {
	 		 $objmin = $objright;
			 $objmax = $objleft;
			 $key_min = $right;
			 $key_max = $left;
		} else {
			 $objmin = $objleft;
			 $objmax = $objright;
			 $key_min = $left;
			 $key_max = $right;
		}

		$delete_min = array();
		$delete_max = array();

		if (is_array($objmax))
		foreach ($objmax as $index => $value) {
			if (is_array($objmin) && in_array($value , $objmin)) {
			    $delete_max[] = $index;
			    $delete_min[] = array_search($value, $objmin);
			}

			foreach ($delete_min as $index) {
				unset($objmin[$index]);
			}
		}

		foreach ($delete_max as $index) {
			unset($objmax[$index]);
		}

		if ($leftcount >= $rightcount) {
			$objleft = $objmax;
			$objright = $objmin;
		}
		else {
			$objleft = $objmin;
			$objright = $objmax;
		}

		if (is_array($objleft))
			foreach ($objleft as $index => $value) {
				$save_comp[$left][$type][] = $index;
			}
	   if (is_array($objright))
			foreach ($objright as $index => $value) {
				$save_comp[$right][$type][] = $index;
			}
		if (count($save_comp[$left])==0 && count($save_comp[$right])==0)
				$save_comp = FALSE;

		if ($save_comp !== FALSE)
			 $output[] = $save_comp;

		return $save_comp;
	}
}
