<?php
/**
 * @version        4.3.0
 * @package        Joomla
 * @subpackage     Helpdesk Pro
 * @author         Tuan Pham Ngoc
 * @copyright      Copyright (C) 2013 - 2021 Ossolution Team
 * @license        GNU/GPL, see LICENSE.php
 */

namespace OSSolution\HelpdeskPro\Site\View\Ticket;

use HelpdeskProHelperBootstrap;
use Joomla\CMS\Captcha\Captcha;
use Joomla\CMS\HTML\HTMLHelper;
use Joomla\CMS\Language\Text;
use Joomla\CMS\Plugin\PluginHelper;
use Joomla\CMS\Router\Route;
use Joomla\CMS\Uri\Uri;
use Joomla\Registry\Registry;
use Joomla\Utilities\ArrayHelper;
use OSL\View\HtmlView;
use OSSolution\HelpdeskPro\Site\Helper\Database as HelpdeskproHelperDatabase;
use OSSolution\HelpdeskPro\Site\Helper\Helper as HelpdeskproHelper;
use OSSolution\HelpdeskPro\Site\Helper\Html as HelpdeskproHelperHtml;
use OSSolution\HelpdeskPro\Site\Helper\Jquery as HelpdeskproHelperJquery;
use OSSolution\HelpdeskPro\Site\Helper\Route as RouteHelper;

defined('_JEXEC') or die;

/**
 * Class Html
 *
 * @property \OSSolution\HelpdeskPro\Admin\Model\Ticket $model
 */
class Html extends HtmlView
{
	protected function beforeRender()
	{
		// Load jQuery validation engine
		HelpdeskproHelperJquery::validateForm();

		// Remove the uploaded files data from section
		$this->container->session->clear('hdp_uploaded_files');
		$this->container->session->clear('hdp_uploaded_files_original_names');
		$this->bootstrapHelper = HelpdeskProHelperBootstrap::getInstance();

		$layout = $this->getLayout();

		if ($layout == 'form')
		{
			$this->beforeRenderTicketForm();

			return;
		}

		HelpdeskproHelper::loadEditable();

		/* @var \JApplicationSite $app */
		$app         = $this->container->app;
		$user        = $this->container->user;
		$config      = HelpdeskproHelper::getConfig();
		$fieldSuffix = HelpdeskproHelper::getFieldSuffix();
		$item        = $this->model->getData();

		if (!$item->id)
		{
			$app->enqueueMessage(Text::_('HDP_TICKET_NOT_EXISTS'));
			$app->redirect(Route::_(RouteHelper::getTicketsRoute(), false));
		}

		// Require users to login if they try to access support ticket via public link
		if (!$config->allow_public_user_submit_ticket && $item->is_ticket_code)
		{
			$redirectUrl = RouteHelper::getTicketRoute($item->id);

			if ($user->id)
			{
				$app->redirect(Route::_($redirectUrl, false));
			}
			else
			{
				$app->enqueueMessage(Text::_('HDP_PLEASE_LOGIN_TO_CONTINUE'));
				$app->redirect(Route::_('index.php?option=com_users&view=login&return=' . base64_encode($redirectUrl)));
			}
		}

		$canAccess = HelpdeskproHelper::checkTicketAccess($item);

		if (!$canAccess)
		{
			if (!$user->id && !$item->is_ticket_code)
			{
				$app->enqueueMessage(Text::_('HDP_PLEASE_LOGIN_TO_CONTINUE'));
				$app->redirect(Route::_('index.php?option=com_users&view=login&return=' . base64_encode(Uri::getInstance()->toString())));
			}
			else
			{
				$app->enqueueMessage(Text::_('HDP_INVALID_TICKET'), 'warning');
				$app->redirect(Uri::root());
			}
		}

		$rows = HelpdeskproHelperDatabase::getAllCategories(
			'ordering',
			['access IN (' . implode(',', $user->getAuthorisedViewLevels()) . ')'],
			$fieldSuffix
		);

		$children = [];

		if ($rows)
		{
			// first pass - collect children
			foreach ($rows as $v)
			{
				$pt   = $v->parent_id;
				$list = @$children[$pt] ? $children[$pt] : [];
				array_push($list, $v);
				$children[$pt] = $list;
			}
		}

		$categories = HTMLHelper::_('menu.treerecurse', 0, '', [], $children, 9999, 0, 0);

		$rowStatuses = HelpdeskproHelperDatabase::getAllStatuses('ordering', $fieldSuffix);

		$rowPriorities = HelpdeskproHelperDatabase::getAllPriorities('ordering', $fieldSuffix);

		if ($user->id == $item->user_id || $item->is_ticket_code)
		{
			$isCustomer = 1;
		}
		else
		{
			$isCustomer = 0;
		}

		if ($isCustomer && ($item->status_id == $config->closed_ticket_status))
		{
			$canComment = false;
		}
		else
		{
			$canComment = true;
		}

		$message = $this->input->getHtml('message');

		if ($config->highlight_code)
		{
			HelpdeskproHelper::loadHighlighter();
		}

		$this->loadCaptcha($app, $config);

		// Add js variables
		$maxNumberOfFiles = $config->max_number_attachments ? (int) $config->max_number_attachments : 1;

		$siteUrl = Uri::root();
		$this->container->document->addScriptDeclaration("
			var maxAttachment = $maxNumberOfFiles;
			var currentCategory = 0;
			var currentNumberAttachment = 1;
			var currentStatus = 0;
			var hdpSiteUrl = '$siteUrl';
			var jItemId = " . (int) $this->Itemid . ";
		");

		PluginHelper::importPlugin('helpdeskpro');

		//Trigger plugins
		$results = $this->container->app->triggerEvent('onViewTicket', [$item]);

		// Pathway
		$pathway = $app->getPathway();
		$pathway->addItem(Text::sprintf('HDP_TICKET_NUMBER', $item->id));

		$this->fields        = HelpdeskproHelper::getFields($item->category_id);
		$this->messages      = $this->model->getMessages();
		$this->fieldValues   = $this->model->getFieldsValue();
		$this->rowStatuses   = $rowStatuses;
		$this->rowPriorities = $rowPriorities;
		$this->categories    = $categories;
		$this->config        = $config;
		$this->item          = $item;
		$this->isCustomer    = $isCustomer;
		$this->canComment    = $canComment;
		$this->message       = $message;
		$this->results       = $results;
	}

	/**
	 * Prepare data to render submit ticket form
	 *
	 * @throws \Exception
	 */
	private function beforeRenderTicketForm()
	{
		/* @var \JApplicationSite $app */
		$app         = $this->container->app;
		$user        = $this->container->user;
		$config      = HelpdeskproHelper::getConfig();
		$fieldSuffix = HelpdeskproHelper::getFieldSuffix();
		$userId      = $user->get('id');
		$active      = $app->getMenu()->getActive();

		if ($active && isset($active->query['view'], $active->query['layout'])
			&& $active->query['view'] == 'ticket' && $active->query['layout'] == 'form')
		{
			$params = $active->getParams();
		}
		else
		{
			$params = new Registry;
		}

		$categoryId = $this->input->getInt('category_id', (int) $params->get('default_category_id'));

		$priorityId = $this->input->getInt('priority_id', 0);

		if (!$userId && !$config->allow_public_user_submit_ticket)
		{
			//Redirect user to login page
			$app->enqueueMessage(Text::_('HDP_LOGIN_TO_SUBMIT_TICKET'));
			$app->redirect('index.php?option=com_users&view=login&return=' . base64_encode(Uri::getInstance()->toString()));
		}

		$filters = ['access IN (' . implode(',', $user->getAuthorisedViewLevels()) . ')'];

		if ($params->get('category_ids'))
		{
			$categoryIds = array_filter(ArrayHelper::toInteger(explode(',', $params->get('category_ids'))));

			if (count($categoryIds))
			{
				$filters[] = ['id IN (' . implode(',', $categoryIds) . ')'];
			}
		}

		$rows = HelpdeskproHelperDatabase::getAllCategories(
			'ordering',
			$filters,
			$fieldSuffix
		);

		$lists['category_id'] = HelpdeskproHelperHtml::buildCategoryDropdown(
			$categoryId,
			'category_id',
			'class="uk-select form-control input-xlarge form-select validate[required]" onchange="HDP.showFields(this.form);"',
			$rows
		);

		$rowPriorities = HelpdeskproHelperDatabase::getAllPriorities('ordering', $fieldSuffix);

		if (count($rowPriorities))
		{
			$options              = [];
			$options[]            = HTMLHelper::_('select.option', '', Text::_('HDP_CHOOSE_PRIORITY'), 'id', 'title');
			$options              = array_merge($options, $rowPriorities);
			$lists['priority_id'] = HTMLHelper::_('select.genericlist', $options, 'priority_id',
				[
					'option.text.toHtml' => false,
					'option.text'        => 'title',
					'option.key'         => 'id',
					'list.attr'          => 'class="uk-select input-large validate[required] form-select"',
					'list.select'        => $priorityId > 0 ? $priorityId : $config->default_ticket_priority_id]);
		}

		// Custom fields
		$rowFields = HelpdeskproHelper::getAllFields();
		$form      = new \HDPForm($rowFields);

		$relation = HelpdeskproHelper::getFieldCategoryRelation();
		$form->prepareFormField($categoryId, $relation);

		$fieldJs = "fields = new Array();\n";
		foreach ($relation as $catId => $fieldList)
		{
			$fieldJs .= ' fields[' . $catId . '] = new Array("' . implode('","', $fieldList) . '");' . "\n";
		}

		$this->container->document->addScriptDeclaration($fieldJs);

		$data = $this->input->getData();

		if ($this->input->getMethod() == 'POST')
		{
			$useDefault = false;
		}
		else
		{
			$useDefault = true;
		}

		$form->bind($data, $useDefault);

		$this->loadCaptcha($app, $config);

		$maxNumberOfFiles = $config->max_number_attachments ? (int) $config->max_number_attachments : 1;

		$this->container->document->addScriptDeclaration("
			var maxAttachment = $maxNumberOfFiles;
			var currentCategory = $categoryId;
			var currentNumberAttachment = 1; 
		");

		// Pathway
		$pathway = $app->getPathway();
		$pathway->addItem(Text::_('HDP_NEW_TICKET'));

		$this->lists         = $lists;
		$this->config        = $config;
		$this->userId        = $userId;
		$this->form          = $form;
		$this->categoryId    = $categoryId;
		$this->params        = $params;
		$this->rowCategories = $rows;
	}

	/**
	 * Load captcha for submit ticket and add comment form
	 *
	 * @param   \JApplicationSite   $app
	 * @param   \OSL\Config\Config  $config
	 */
	protected function loadCaptcha($app, $config)
	{
		// Captcha
		$showCaptcha = 0;
		$user        = $this->container->user;

		if (!$config->enable_captcha || ($user->id && $config->enable_captcha == '2'))
		{
			$enableCaptcha = false;
		}
		else
		{
			$enableCaptcha = true;
		}

		if ($enableCaptcha)
		{
			$captchaPlugin = $app->get('captcha', $this->container->appConfig->get('captcha'));

			if (!$captchaPlugin)
			{
				// Hardcode to recaptcha, reduce support request
				$captchaPlugin = 'recaptcha';
			}

			// Check to make sure Captcha is enabled
			$plugin = PluginHelper::getPlugin('captcha', $captchaPlugin);

			if ($plugin)
			{
				$showCaptcha   = 1;
				$this->captcha = Captcha::getInstance($captchaPlugin)->display('dynamic_recaptcha_1', 'dynamic_recaptcha_1', 'required');
			}
			else
			{
				$app->enqueueMessage(Text::_('EB_CAPTCHA_NOT_ACTIVATED_IN_YOUR_SITE'), 'error');
			}
		}

		$this->showCaptcha = $showCaptcha;
	}
}