<?php

/**
*
*/

class ProcessSettingsFactory extends \ProcessWire\Process {

	public static function getModuleInfo() {
		return array(
			'title' 	=> \ProcessWire\__('Process Settings Factory', \ProcessWire\wire("config")->paths->root . 'site/modules/SettingsFactory/ProcessSettingsFactory.module'),
			'summary' 	=> \ProcessWire\__('Unlimited settings pages.', \ProcessWire\wire("config")->paths->root . 'site/modules/SettingsFactory/ProcessSettingsFactory.module'),
			'version' 	=> '1.0.6',
			'author'    => 'Macrura',
			'permanent' => false,
			'autoload' 	=> false,
			'icon' 		=> 'check-square-o',
			'requires'	=> 'SettingsFactory',
			'permission' => 'settings-factory',
			"permissionMethod" => "hasSettingsPagePermission",
			"permissions" => ["settings-factory" => "Access settings factory pages"],
		);
	}


	protected $module = null;

	protected $settingsKey = null;

	public function init() {
		$this->module = $this->modules->get('SettingsFactory');
		$this->data = $this->modules->getConfig('SettingsFactory');
		parent::init();
	}

	public function ready() {
		$this->settingsKey = $this->wire('page')->name;
	}

	public function ___execute() {

		$form = $this->buildForm();

		if($this->input->post('submit_save')) {
			$this->processForm($form);
			$this->session->redirect("./");
			return '';
		} else {
			
			$out = $form->render();

			if($this->wire->user->isSuperuser()) {
				$moduleInfo = $this->wire('modules')->getModuleInfoVerbose($this->module);
				$filepath = $this->wire('page')->sp_filepath ? 'Using ' . $this->wire('page')->sp_filepath : 'No Path Specified.';
				$out .= "<p class='version detail'><i class='fa fa-check-square-o'></i> Settings Factory v$moduleInfo[versionStr] | $filepath";
				$out .= " | <a href='{$this->wire('page')->editUrl}' target='_blank'>Edit Process Settings</a></p>";
			}
			
			return $out;
		}


	}

	/**
	* getModuleInfo interface for required permission
	*
	* @param array $data
	* @return bool
	*
	*/
	public static function hasSettingsPagePermission(array $data) {

		$page = $data['page'];
		$user = $data['user'];
		$wire = $data['wire'];

		// if there is a specific permission setup for this settings page
		$permission = $wire->permissions->get("$page->name");
		if(!$permission->id) $permission = 'settings-factory';
		return $user->hasPermission($permission);

	}


	/**
	* Render form for admin page
	* @return string form markup
	*/
	protected function buildForm() {

		$languages = ($this->wire('languages')) ? $this->wire('languages') : '';
		$nonDefaultLanguages = ($languages) ? $languages->findNonDefault() : '';

		$form = new \ProcessWire\InputfieldForm();
		$form->attr('id', 'ProcessSettingsFactory');
		$form->attr('method', 'post');
		$form->attr('action', './');

		$wire = $this->wire;
		$module = $this->module;

		// ------------------------------------------------------------------------
		// Notice
		// ------------------------------------------------------------------------
		$fDefault = $wire->modules->get('InputfieldMarkup');
		$fDefault->name  = 'instructions';
		$fDefault->label = \ProcessWire\__('Instructions', \ProcessWire\wire("config")->paths->root . 'site/modules/SettingsFactory/ProcessSettingsFactory.module');
		$fDefault->markupText = \ProcessWire\__('Please check that you have correctly specified a path to a valid json or php file that defines your inputfields.', \ProcessWire\wire("config")->paths->root . 'site/modules/SettingsFactory/ProcessSettingsFactory.module');

		if(!$wire->page->sp_filepath) {
			$form->add($fDefault);
		}

		// ------------------------------------------------------------------------
		// USER DEFINED FIELDS
		// ------------------------------------------------------------------------
		if($wire->page->sp_filepath) {
			$path = $wire->config->paths->templates .  $wire->page->sp_filepath;
			$settingsKey = $wire->page->name;
			$modData = $this->modules->getConfig('SettingsFactory');
			$thisData = isset($modData[$settingsKey]) ? $modData[$settingsKey] : null;
			if(file_exists($path)) {

				$pathParts = pathinfo($path);

				if($pathParts['extension'] == 'json') {
					$json = file_get_contents($path);
					$fArray = json_decode($json, true);
				}

				if($pathParts['extension'] == 'php') {
					$fArray = \ProcessWire\wirerenderfile(\ProcessWire\wire('files')->compile($path,array('includes'=>true,'namespace'=>true,'modules'=>false,'skipIfNamespace'=>false)));
				}

				$form->add($fArray);
				$inputfields = $this->extractInputfields($fArray);
				foreach($inputfields as $key => $cField) {
					$name = $cField['name'];
					if($thisData && isset($thisData[$name])) {
						$cField['value'] = $thisData[$name] ?: '';
					} else {
						$cField['value'] = '';
					}
					$f = $form->get($name);
					$f->attr('value', $cField['value']);

					if($nonDefaultLanguages) {
						if($f->useLanguages) {
							foreach($nonDefaultLanguages as $language) {
								$f->set("value" . $language->id, $thisData[$name . "__" . $language->id ]);
							}
						}
					}

					if($cField['type'] == 'InputfieldCheckbox' && $cField['value'] == 1) {
						$f->attr('checked', 'checked');
					}
				}

			} else {
				$fDefault->markupText = \ProcessWire\__("The specified file was not found. ($path)", \ProcessWire\wire("config")->paths->root . 'site/modules/SettingsFactory/ProcessSettingsFactory.module');
				$form->add($fDefault);
			}
		}

		$f = $this->modules->get('InputfieldSubmit');
		$f->attr('name', 'submit_save');
		$f->attr('value', $this->_('Save'));
		$f->addClass('head_button_clone');
		$f->icon = 'save';
		$form->add($f);

		return $form;

	}


	/**
	* Extract the inputfields from nested tabs/fieldsets
	*/
	public function extractInputfields($inputfields) {
		$inputfieldsArray = new \ProcessWire\InputfieldWrapper();
		foreach($inputfields as $field) {
			if(is_array($field)) $inputfieldsArray->importArray($field);

			if($field instanceof \ProcessWire\InputfieldWrapper) {
				if(in_array('WireTab', $field->attributes)) {
					$this->wire('modules')->get('JqueryWireTabs');
					$this->wire('config')->scripts->append(\ProcessWire\wire('config')->urls->SettingsFactory.'wiretabs-init.js');
				}
				$inputfieldsArray->import($field->getAll());
			}
		}
		return $inputfieldsArray->getAll();
	}



	/**
	* Process configuration fields and populate to module
	* @param InputfieldWrapper $form
	*
	*/
	protected function processForm($form) {

    	$languages = ($this->wire('languages')) ? $this->wire('languages') : '';
		$nonDefaultLanguages = ($languages) ? $languages->findNonDefault() : '';

		$settingsKey = $this->wire('page')->name;
		$form->processInput($this->input->post);
		$thisData = $this->module->get($settingsKey);
		$valuesArray = array();
		foreach($thisData as $key => $value) {
			$f = $form->get($key);
			if(!$f) continue;
			if($nonDefaultLanguages) {
				if($f->useLanguages)
				foreach($nonDefaultLanguages as $language) $valuesArray[$key . "__" . $language->id ] = $f->get("value" . $language->id );
			}
			//$valuesArray[$key] = $f->attr('value');
			$valuesArray[$key] = is_array($f->attr('value')) ? array_values($f->attr('value')) : $f->attr('value');
		}
		$myData[$settingsKey] = $valuesArray;
		$newData = array_merge($this->data,$myData);

		$this->modules->saveModuleConfigData('SettingsFactory', $newData);
		$this->message(sprintf($this->_('Saved: %s'), $this->wire('page')->title));

	}



}
