<?php
namespace homecn\action;

/**
  * @class 基类
  * @method getLanguage 子类必须实现这个类才能运行
  * @author Yangxing
  */
class baseAction extends \action
{
	public $userpower = [];
	public $isWxClient = null;
    /**
     * 中英文
     * @var mixed|string
     */
    public $language = 'cn';

     /**
     * @var int 0 代表中文，1代表英文
     */
    public static $isChina;

    /**
     * 获取参数
     * @var null
     */
    public $param = null;

    /**
     * 第几页
     * @var int
     */
    public $page;

    public  $total = 0;

	//url的分页参数
	public $pageName = 'page';

    /**
     * 分几页
     * @var int|mixed
     */
    public $pageSize;

    public $perPage;

    /**
     * baseAction constructor.
     */
	public function __construct()
	{
		$this->isWxClient = stripos($_SERVER['HTTP_USER_AGENT'], 'micromessenger') !== false;
        $this->param = \mvc::$req;
        $this->page = isset($this->param['page']) ? $this->param['page'] : 1;
        $this->pageSize = isset($_GET['pageSize']) ? $_GET['pageSize'] : 15 ;
        $this->perPage = isset($_GET['perPage']) ? $_GET['perPage'] : 25 ;

        //todo 待完成中英文判断 常量判断中英文
        $this->language = $_SESSION['MVC_LANG'];

		\view::set('isLogin', $_SESSION['cnuser']['u_id']);
		\view::set('lang', $GLOBALS['lang']);

		if(!empty($_SESSION['cnuser']['u_id']))
		{
			\p::init($_SESSION['cnuser']['u_id'], 'gsp_user_link_role');
			$this->userpower = \p::getData();
			$this->userpower = $this->userpower['Z000'];
			$this->userpower['fac'] = [];
			foreach(explode(',', $this->userpower['prl_fields']) as $v)
			{
				if(stripos($v, 'fac') === 0)
				{
					$this->userpower['fac'][] = substr($v, 3);
				}
			}
			$this->userpower['fac'] = array_unique($this->userpower['fac']);
		}
		//var_dump($this->userpower);
        \view::set('MVC_LANG', $_SESSION['MVC_LANG']);
	}

	//检测登录，如果未登录直接跳转到登录
	public function mustLogin()
	{
		if(!$this->isLogin())
		{
           if(isset($_SERVER['HTTP_REFERER'])) {
				$referrer = filter_var($_SERVER['HTTP_REFERER'], FILTER_VALIDATE_URL);
				$_SESSION['login_back_url'] =  $referrer ? $referrer : '';
			}
			if ($this->isAjaxRequest()) {

				$req = \mvc::$req;
				$callback =  !empty($req['callback']) ? $req['callback'] : '';

				if($callback){
					$response = [
						'status' => false,
						'code' => 401,
						'message' => '未登录',
						'redirect' => \mvc::$cfg['SELF_URI'] . 'user/login'
					];
					
					$json = json_encode($response, JSON_UNESCAPED_UNICODE);
					echo $callback . '(' . $json . ');';
					exit();
				}else{
					// AJAX请求返回JSON响应
					$this->exitToJson([
						'status' => false,
						'code' => 401,
						'message' => '未登录',
						'redirect' => \mvc::$cfg['SELF_URI'] . 'user/login'
					]);
				}
			} else {
				// 普通请求执行重定向
				header('Location:' . \mvc::$cfg['SELF_URI'] . 'user/login');
				exit();
			}
        }
	}

	/**
	 * 判断是否为AJAX请求
	 */
	private function isAjaxRequest()
	{
		return !empty($_SERVER['HTTP_X_REQUESTED_WITH']) 
			&& strtolower($_SERVER['HTTP_X_REQUESTED_WITH']) == 'xmlhttprequest';
	}

	//检测登录，如果未登录直接跳转到登录
	public function isLogin()
	{
		return !empty($_SESSION['cnuser']['u_id']);
	}

    /**
     * @取mod 中的数据返回 json
     * @return json
     */
    public function getJson()
    {
        $arr = explode('/',$_REQUEST['func']);
        $class = $arr[0];
        $func = $arr[1];
        $mod = makeOne('\model\homecn\\'.$class);
        $index = array_search('func', array_keys($_REQUEST)); 
        if($index !== FALSE){ 
            array_splice($_REQUEST, $index, 1); 
        }
        $data =call_user_func_array ( array ( $mod, $func ), $_REQUEST );
        $data = ['status' => true ,'code' => 0,'data' => $data];
        $this->exitToJson($data);
    }

    /**
     * @返回语言包json
     * @param $lang 语言版本
     * @return json
     */
    public function getLangJs($lang)
    {
        $path =  \mvc::$cfg['ROOT'] . 'language/';
        $arr = require($path . $lang.'.php');
        $json = json_encode($arr, JSON_UNESCAPED_UNICODE);
        echo 'var langArr = '. $json . ';';
    }

    /**
     * @param $rules 验证规则
     * @param $param 验证数据
     * @return bool 返回true 表示验证成功，验证错误会直接返回错误给前端
     */
    public function validator($rules,$param)
    {

        $validator = new validatorMod($rules);
        $validator->validate($param);
        if($validator->getError()){
            LibFc::ajaxJsonEncode(['status' => 'false' ,'data' => $validator->getError() ]);
        }else{
            return true;
        }
    }

    /**
     * 验证demo
     */
    public function vilidatorDemo()
    {
        $rules = [
            ['name|name', 'require|email|in:7,8,9|max:10|min:6|between:6,8|length:2', '名字不能为空|名字必须必须为正确的邮件地址'],
            ['test|测试', 'require'],
        ];
        $data = ['name' => '9'];
        $validator = new validatorMod($rules);
//        $validator->addRule(['name|名字', 'regex', '/^[0-8|a-z]+$/', '正则验证失败哦']);  //可以为二维数组，有|的正则验证只能通过addRule。
        $validator->validate($data);
        $validator->getAllErrors(); //获取所有验证错误 array
        //$validator->getError();  //获取第一条验证错误 string
        //var_dump($validator->getError());exit();
    }

	public function pages($dataArr)
	{
		$html = '';
		$page = $dataArr['page'];
		$pageCount = $dataArr['pagesize']? ceil($dataArr['recordCount']/$dataArr['pagesize']): 0;
		if($pageCount > 0)
		{
			$page = $page > $pageCount? $pageCount: $page;
			$html .= '
			<div class="pager">
				<div>当前条数:'.$dataArr['recordCount'].', 页码: '.$dataArr['page'].'/'.$pageCount.' </div>
				<ul class="pagination style2">
			';
			if($page > 1) $html .= '<li><a href="javascript:gopage('.($page-1).')"><i class="fa fa-chevron-left"></i></a></li>';
			$html .= '<li class="active"><a href="javascript:gopage('.$page.')">'.$page.'</a></li>';
			if($pageCount > $page) $html .= '<li><a href="javascript:gopage('.($page+1).')"><i class="fa fa-chevron-right"></i></a></li>';
			$html .= '</ul></div>';
		}
		return $html;
	}

    public function showPages($total,$perPage = 10, $all = false)
    {   
        $req = \mvc::$req;
        $this->total = $total > 0 ? (int) $total:    $this->total;
		$this->perPage = $perPage > 0 ? (int) $perPage: $this->perPage;
		$totalPage = ceil($this->total/$this->perPage);

		$nowPage = !empty($req[$this->pageName]) && $req[$this->pageName] > 0 ? (int) $req[$this->pageName] : 1;
		$nowPage = $nowPage > $totalPage? $totalPage: $nowPage;
	
		$urlParamArr = array();
		//全部小写
		if(is_array($req))
		{
			foreach($req as $K=>$V)
			{
				$urlParamArr[$K] = $V;
			}
		}
		$urlParamArr[$this->pageName] = '-_-page_-_';
		$Url = $_SERVER['PHP_SELF'].'?'.http_build_query($urlParamArr);
		$PageStr = '';
		if($totalPage > 0)
		{
			$PageStr .= $nowPage == 1 ? '<li class="page-disabled"><a href="javascript:">上一页</a></li>' : '<li><a href="'.self::ReplaceUrl($Url, $nowPage - 1).'">上一页</a></li>';
		}
		if($totalPage <= 7)
		{
			for($i = 1; $i <=$totalPage; $i++)
			{
				if($nowPage == $i)
				{
					$PageStr .= '<li class="page-choose"><a href="javascript:">'.$i.'</a></li>';
				}
				else
				{
					$PageStr .= '<li><a href="'.self::ReplaceUrl($Url, $i).'">'.$i.'</a></li>';
				}
			}
		}
		else
		{//上一页 5 6 7 8 9 10 11 12 下一页
			//计算开始页
			if($nowPage < 4)
			{//[1] [2] 3 [4]...
				$BPage = 1;
			}
			else if(($totalPage-$nowPage) < 3)
			{ 
				$BPage = $nowPage-6+($totalPage-$nowPage);
			}
			else
			{
				$BPage = $nowPage-3;
			}
			for($i = $BPage; $i < $BPage+7; $i++)
			{
				if($i > $totalPage)
				{
					break;
				}
				if($nowPage == $i)
				{
					$PageStr .= '<li class="page-choose"><a href="javascript:">'.$i.'</a></li>';
				}
				else
				{
					$PageStr .= '<li><a href="'.self::ReplaceUrl($Url, $i).'">'.$i.'</a></li>';
				}
			}
		}
		if($totalPage > 0)
		{
			$PageStr .= $nowPage == $totalPage ? '<li class="page-disabled"><a href="javascript:">下一页</a></li>' : '<li><a href="'.self::ReplaceUrl($Url, $nowPage + 1).'">下一页</a></li>';
		}
		//跳转到
		$GoHtml = '';
		if($totalPage > 10)
		{
			$GoHtml .= '<div class="page-go">共<b>'.$totalPage.'</b>页，到第 <input type="text" class="to_page_txt" size="3" base="'.$Url.'" onkeydown="javascript:if(event.keyCode==13){PAGE.jump();return false;}" value="'.$nowPage.'"/> 页 <button type="button" class="btn btn-info btn-sm to_page_btn" onclick="PAGE.jump()">跳转</button ></div>';
		}
		
		$per = '<div class="page-all">共<b>'.$total.'</b>条记录';
		if($all)
		{ 
			
			$per .= '，每页 <input type="text" class="to_pageall_txt" size="2" onkeydown="javascript:if(event.keyCode==13){PAGE.pagesize(this.value);return false;}" value="'.$perPage.'"/> 条';
		}
		$per .= '</div>';
		return '<div class="page-box">'.$per.'<ul class="page">'.$PageStr.'</ul>'.$GoHtml.'</div>';
    }

	public function exitToJson($data)
	{
		ob_clean();
		$json = json_encode($data, JSON_UNESCAPED_UNICODE);
        $json = str_replace('":null,"','":"","',$json);
        echo $json;
		exit;
	}

    private static function ReplaceUrl($Url, $Page)
	{
		return str_replace('-_-page_-_', $Page, $Url);
	}

	/**
	 * AJAX 分页显示
	 * @param $total 总记录数
	 * @param int $perPage 每页记录数
	 * @param bool $all 是否显示每页记录数设置
	 * @param string $ajaxCallback AJAX 回调函数名
	 * @param array $additionalParams 额外的参数
	 * @return string
	 */
	public function showAjaxPages($total, $perPage = 10, $all = false, $ajaxCallback = 'getCateList', $additionalParams = [])
	{
		$req = \mvc::$req;
		$this->total = $total > 0 ? (int) $total: $this->total;
		$this->perPage = $perPage > 0 ? (int) $perPage: $this->perPage;
		$totalPage = ceil($this->total/$this->perPage);

		$nowPage = !empty($req[$this->pageName]) && $req[$this->pageName] > 0 ? (int) $req[$this->pageName] : 1;
		$nowPage = $nowPage > $totalPage? $totalPage: $nowPage;

		// 构建 URL 参数，排除分页参数
		$urlParamArr = array();
		if(is_array($req))
		{
			foreach($req as $K=>$V)
			{
				if($K !== $this->pageName) { // 不包含分页参数
					$urlParamArr[$K] = $V;
				}
			}
		}
		
		// 合并额外参数
		$urlParamArr = array_merge($urlParamArr, $additionalParams);

		$PageStr = '';
		if($totalPage > 0)
		{
			// 构建回调函数参数
			$callbackParams = $this->buildCallbackParams($ajaxCallback, $urlParamArr, $nowPage - 1);
			$PageStr .= $nowPage == 1 
				? '<li class="page-disabled"><a href="javascript:">上一页</a></li>' 
				: '<li><a href="javascript:void(0);" onclick="'.$callbackParams.'">上一页</a></li>';
		}

		if($totalPage <= 7)
		{
			for($i = 1; $i <= $totalPage; $i++)
			{
				if($nowPage == $i)
				{
					$PageStr .= '<li class="page-choose"><a href="javascript:">'.$i.'</a></li>';
				}
				else
				{
					$callbackParams = $this->buildCallbackParams($ajaxCallback, $urlParamArr, $i);
					$PageStr .= '<li><a href="javascript:void(0);" onclick="'.$callbackParams.'">'.$i.'</a></li>';
				}
			}
		}
		else
		{
			// 计算开始页
			if($nowPage < 4)
			{
				$BPage = 1;
			}
			else if(($totalPage-$nowPage) < 3)
			{
				$BPage = $nowPage-6+($totalPage-$nowPage);
			}
			else
			{
				$BPage = $nowPage-3;
			}
			for($i = $BPage; $i < $BPage+7; $i++)
			{
				if($i > $totalPage)
				{
					break;
				}
				if($nowPage == $i)
				{
					$PageStr .= '<li class="page-choose"><a href="javascript:">'.$i.'</a></li>';
				}
				else
				{
					$callbackParams = $this->buildCallbackParams($ajaxCallback, $urlParamArr, $i);
					$PageStr .= '<li><a href="javascript:void(0);" onclick="'.$callbackParams.'">'.$i.'</a></li>';
				}
			}
		}

		if($totalPage > 0)
		{
			$callbackParams = $this->buildCallbackParams($ajaxCallback, $urlParamArr, $nowPage + 1);
			$PageStr .= $nowPage == $totalPage 
				? '<li class="page-disabled"><a href="javascript:">下一页</a></li>' 
				: '<li><a href="javascript:void(0);" onclick="'.$callbackParams.'">下一页</a></li>';
		}

		// AJAX 跳转到指定页
		$GoHtml = '';
		if($totalPage > 10)
		{
			$jumpCallbackParams = $this->buildJumpCallbackParams($ajaxCallback, $urlParamArr);
			$GoHtml .= '<div class="page-go">共<b>'.$totalPage.'</b>页，到第 
				<input type="text" class="to_page_txt" size="3" value="'.$nowPage.'" 
				onkeydown="javascript:if(event.keyCode==13){
					var page = parseInt(this.value);
					if(page >= 1 && page <= '.$totalPage.') {
						'.$jumpCallbackParams.'
					} else {
						alert(\'请输入1到'.$totalPage.'之间的页码\');
					}
					return false;
				}" /> 页 
				<button type="button" class="btn btn-info btn-sm to_page_btn" 
				onclick="
					var page = parseInt(document.querySelector(\'.to_page_txt\').value);
					if(page >= 1 && page <= '.$totalPage.') {
						'.$jumpCallbackParams.'
					} else {
						alert(\'请输入1到'.$totalPage.'之间的页码\');
					}
				">跳转</button>
			</div>';
		}

		$per = '<div class="page-all">共<b>'.$total.'</b>条记录';
		if($all)
		{
			$pageSizeCallbackParams = $this->buildPageSizeCallbackParams($ajaxCallback, $urlParamArr);
			$per .= '，每页 <input type="text" class="to_pageall_txt" size="2" 
				onkeydown="javascript:if(event.keyCode==13){
					'.$pageSizeCallbackParams.'
					return false;
				}" value="'.$perPage.'" /> 条';
		}
		$per .= '</div>';

		return '<div class="page-box">'.$per.'<ul class="page">'.$PageStr.'</ul>'.$GoHtml.'</div>';
	}

	/**
	 * 构建回调函数参数
	 * @param string $callback 回调函数名
	 * @param array $params 参数数组
	 * @param int $page 页码
	 * @return string
	 */
	private function buildCallbackParams($callback, $params, $page)
	{
		if($callback === 'getList'||$callback === 'loadModelCar') {
			// 对于 getList 函数，需要构建参数对象
			$paramStr = '{';
			foreach($params as $key => $value) {
				if(is_numeric($value)) {
					$paramStr .= "'{$key}': {$value}, ";
				} else {
					$paramStr .= "'{$key}': '{$value}', ";
				}
			}
			$paramStr .= "'page': {$page}";
			$paramStr .= '}';
			
			return "{$callback}({$paramStr})";
		}
		else {
			// 对于 getCateList 函数，按照原来的参数顺序
			$mm_id = isset($params['mm_id']) ? $params['mm_id'] : 'null';
			$mod3_id = isset($params['mod3_id']) ? $params['mod3_id'] : 'null';
			return "{$callback}({$mm_id}, {$mod3_id}, '.main.', {$page})";
		}
	}

	/**
	 * 构建跳转回调函数参数
	 * @param string $callback 回调函数名
	 * @param array $params 参数数组
	 * @return string
	 */
	private function buildJumpCallbackParams($callback, $params)
	{
		if($callback === 'getList') {
			$paramStr = '{';
			foreach($params as $key => $value) {
				if(is_numeric($value)) {
					$paramStr .= "'{$key}': {$value}, ";
				} else {
					$paramStr .= "'{$key}': '{$value}', ";
				}
			}
			$paramStr .= "'page': page";
			$paramStr .= '}';
			
			return "{$callback}({$paramStr})";
		} else {
			$mm_id = isset($params['mm_id']) ? $params['mm_id'] : 'null';
			$mod3_id = isset($params['mod3_id']) ? $params['mod3_id'] : 'null';
			return "{$callback}({$mm_id}, {$mod3_id}, '.main.', page)";
		}
	}

	/**
	 * 构建每页大小回调函数参数
	 * @param string $callback 回调函数名
	 * @param array $params 参数数组
	 * @return string
	 */
	private function buildPageSizeCallbackParams($callback, $params)
	{
		if($callback === 'getList') {
			$paramStr = '{';
			foreach($params as $key => $value) {
				if(is_numeric($value)) {
					$paramStr .= "'{$key}': {$value}, ";
				} else {
					$paramStr .= "'{$key}': '{$value}', ";
				}
			}
			$paramStr .= "'page': 1, 'perPage': this.value";
			$paramStr .= '}';
			
			return "{$callback}({$paramStr})";
		} else {
			$mm_id = isset($params['mm_id']) ? $params['mm_id'] : 'null';
			$mod3_id = isset($params['mod3_id']) ? $params['mod3_id'] : 'null';
			return "{$callback}({$mm_id}, {$mod3_id}, '.main.', 1, this.value)";
		}
	}
}