<?php

namespace TotalTheme\Admin;

use TotalTheme\License_Manager;

defined( 'ABSPATH' ) || exit;

/**
 * Theme License Activation and De-activation.
 */
final class License_Panel {

	/**
	 * Stores instance of the license manager.
	 */
	private $license_manager;

	/**
	 * Instance.
	 */
	private static $instance = null;

	/**
	 * Create or retrieve the instance of License_Panel.
	 */
	public static function instance() {
		if ( null === static::$instance ) {
			static::$instance = new self();
		}
		return static::$instance;
	}

	/**
	 * Private Constructor.
	 */
	private function __construct() {
		$this->license_manager = totaltheme_get_instance_of( 'License_Manager' );
		if ( $this->license_manager ) {
			$this->init_hooks();
		}
	}

	/**
	 * Hook into actions and filters.
	 */
	public function init_hooks() {
		$this->admin_notices();

		if ( self::is_enabled() ) {
			if ( $this->is_network_admin() ) {
				add_action( 'network_admin_menu', [ $this, 'add_network_admin_page' ] );
			} else {
				add_action( 'admin_menu', [ $this, 'add_admin_submenu_page' ], 1 );
			}
			add_action( 'wp_ajax_wpex_theme_license_form', [ $this, 'license_form_ajax' ] );
		}
	}

	/**
	 * Register admin notices.
	 */
	private function admin_notices(): void {
		$license_status = $this->license_manager->get_license_status();
		if ( 'active' === $license_status || 'staging' === $license_status ) {
			return;
		}
		add_action( 'admin_notices', function() use ( $license_status ) {
			$screen = get_current_screen();
			if ( isset( $screen->id ) && is_string( $screen->id ) && str_contains( $screen->id, 'wpex' ) ) {
				return;
			}
			$notice_class = 'notice notice-error is-dismissible';
			switch ( $license_status ) {
				case 'invalid':
					$notice_title     = esc_html__( 'Theme License Invalid', 'total' );
					$notice_link_text = esc_html__( 'Update License', 'total' );
					$notice_text      = esc_html__( 'Your current theme license appears to be invalid. Please activate a valid license.', 'total' );
					break;
				case 'invalid_staging':
					$notice_title     = esc_html__( 'Theme License Error', 'total' );
					$notice_link_text = esc_html__( 'Register License', 'total' );
					$notice_text      = esc_html__( 'This license was activated in staging mode but this site does not appear to be a development environment. Please register a proper license for live sites.', 'total' );
					break;
				case 'duplicate':
					$notice_title     = esc_html__( 'Duplicate Theme License', 'total' );
					$notice_link_text = esc_html__( 'Manage License', 'total' );
					$notice_text      = esc_html__( 'Your current theme license is already registered to a different domain. Please deactivate it and activate an unused license on this site. If your license was recently updated by our support team or you believe this is an error, you can click Manage License to go to the license page and re-verify.', 'total' );
					break;
				case 'inactive':
				case 'unregistered':
				default:
					$notice_title     = esc_html__( 'Theme License Missing', 'total' );
					$notice_link_text = esc_html__( 'Activate License', 'total' );
					$notice_text      = esc_html__( 'Please activate your theme license. Each domain where the theme is used requires a valid license.', 'total' );
					break;
			}
			echo '<div class="' . esc_attr( $notice_class ) . '">';
				echo '<p><strong>' . esc_html( $notice_title ) . '</strong>: ' . esc_html( $notice_text ) . '</p>';
				if ( $this->license_manager->is_license_network_actived() ) {
					echo '<p>' . esc_html__( 'This license is network-activated. Please contact your site administrator if you wish to register a license for this individual site.', 'total' ) . '</p>';
				} else {
					echo '<p><a href="' . esc_url( admin_url( 'admin.php?page=wpex-panel-theme-license' ) ) . '">' . esc_html( $notice_link_text ) . '</a> | <a target="_blank" rel="noopener noreferrer" href="https://1.envato.market/EPJRe">' . esc_html__( 'Purchase License', 'total' ) . '</a></p>';
				}
			echo '</div>';
		} );
	}

	/**
	 * Check if we should display the admin page.
	 */
	public static function is_enabled(): bool {
		$check = true;
		if ( is_multisite()
			&& ! is_main_site()
			&& totaltheme_call_non_static( 'License_Manager', 'is_license_network_actived' )
		) {
			$check = false;
		}
		return $check;
	}

	/**
	 * Check if we are on a multisite network admin screen.
	 */
	private function is_network_admin(): bool {
		return is_multisite() && is_network_admin();
	}

	/**
	 * Add network admin page.
	 */
	public function add_network_admin_page() {
		$hook_suffix = add_submenu_page(
			'themes.php',
			esc_html__( 'Total Theme License', 'total' ),
			esc_html__( 'Total Theme License', 'total' ),
			'manage_network_options',
			'total-theme-license',
			[ $this, 'render_admin_page' ]
		);

		add_action( "admin_print_styles-{$hook_suffix}", [ $this, 'enqueue_styles' ] );
		add_action( "admin_print_scripts-{$hook_suffix}", [ $this, 'enqueue_scripts' ] );
	}

	/**
	 * Add sub menu page.
	 */
	public function add_admin_submenu_page() {
		$hook_suffix = add_submenu_page(
			WPEX_THEME_PANEL_SLUG,
			esc_html__( 'Theme License', 'total' ),
			esc_html__( 'Theme License', 'total' ),
			'administrator', // admin only!
			WPEX_THEME_PANEL_SLUG . '-theme-license',
			[ $this, 'render_admin_page' ]
		);

		add_action( "load-{$hook_suffix}", [ $this, 'admin_help_tab' ] );
		add_action( "admin_print_styles-{$hook_suffix}", [ $this, 'enqueue_styles' ] );
		add_action( "admin_print_scripts-{$hook_suffix}", [ $this, 'enqueue_scripts' ] );
	}

	/**
	 * Add admin help tab.
	 */
	public function admin_help_tab() {
		$screen = get_current_screen();

		if ( ! $screen ) {
			return;
		}

		$screen->add_help_tab(
			[
				'id'      => 'totaltheme_panel',
				'title'   => esc_html__( 'Overview', 'total' ),
				'content' => '<p><strong>Please Read !!!</strong><p>A valid theme license is required for each domain using the Total WordPress theme. If you don\'t own a license please purchase one from <a href="https://1.envato.market/EPJRe" target="_blank" rel="noopener noreferrer">ThemeForest.com</a>.</p>This theme is exclusively sold at ThemeForest. Anywhere else providing a download for theme is doing so illegally and most likely includes malicous code.</p><p>A lot of effort, time and money is put into the development and maintance of this product which was created and developed by AJ Clarke from <a href="https://www.wpexplorer.com/" target="_blank" rel="noopener noreferrer">WPExplorer.com</a> and he kindly requests that you abide by the product\'s licensing terms.</p>',
			]
		);
	}

	/**
	 * Enqueue styles.
	 */
	public function enqueue_styles() {
		wp_enqueue_style(
			'totaltheme-admin-license-activation',
			totaltheme_get_css_file( 'admin/license-activation' ),
			[],
			WPEX_THEME_VERSION
		);
	}

	/**
	 * Enqueue scripts.
	 */
	public function enqueue_scripts() {
		wp_enqueue_script(
			'totaltheme-admin-license-activation',
			totaltheme_get_js_file( 'admin/license-activation' ),
			[ 'jquery' ],
			WPEX_THEME_VERSION,
			true
		);
	}

	/**
	 * Returns user capability for the admin page.
	 */
	private function get_user_capability() {
		return $this->is_network_admin() ? 'manage_network_options' : 'administrator';
	}

	/**
	 * Settings page output.
	 */
	public function render_admin_page() {
		if ( ! current_user_can( $this->get_user_capability() ) ) {
			return;
		}

		$this->enqueue_scripts();

		$license_status = $this->license_manager->get_license_status( true );
		$license        = ( 'unregistered' !== $license_status ) ? $this->license_manager->get_license() : '';
		?>

		<div class="wrap wpex-license-activation">
			<?php
			// Network activation notice
			if ( $this->is_network_admin() || ( is_multisite() && is_main_site() ) ) {
				echo '<div class="notice notice-info inline"><p><strong>' . esc_html__( 'Network License', 'total' ) . '</strong>: ' . esc_html__( 'Activating your license on this primary site will enable it across all subsites in the network.', 'total' ) . '</p></div>';
			}
			
			// License notices
			if ( 'invalid' === $license_status ) {
				echo '<div id="totaltheme-invalid-license-warning" class="notice notice-error inline"><p><strong>' . esc_html__( 'Invalid License', 'total' ) . '</strong>: ' . esc_html__( 'The current license is invalid.', 'total' ) . '</p></div>';
			} ?>

			<div class="wpex-license-activation__notice notice inline"></div>

			<div class="wpex-license-activation__card">

				<h2 class="wpex-license-activation__heading"><?php
					esc_html_e( 'Activate Theme License', 'total' );
				?><span class="wpex-license-activation__status-badge wpex-license-activation__status-badge--<?php echo esc_attr( $license_status ); ?>"><?php echo esc_html( $this->license_manager->get_license_status_label( $license_status ) ); ?></span></h2>

				<div class="wpex-license-activation__card-inner">

					<p class="wpex-license-activation__info"><?php echo sprintf(
						/* translators: open and closing link to the theme docs */
						esc_html__( 'Enter your purchase code below. Learn how to %sfind your purchase code%s.', 'total' ),
						'<a target="_blank" rel="noopener noreferrer" href="https://totalwptheme.com/docs/how-to-find-your-total-theme-license/">', '</a>'
					); ?></p>

					<form method="post" class="wpex-license-activation__form">

						<?php if ( $license ) { ?>
							<input type="text" class="wpex-license-activation__input" name="license" placeholder="<?php echo esc_attr( $license ); ?>" value="<?php echo esc_attr( $license ); ?>" data-license-status="<?php echo esc_attr( $license_status ); ?>" readonly="readonly" autocomplete="off" onclick="select()" required>
						<?php } else { ?>
							<input type="text" class="wpex-license-activation__input" name="license" placeholder="<?php esc_html_e( 'Enter your purchase code here.', 'total' ); ?>" autocomplete="off" required>
						<?php } ?>

						<?php if ( $this->license_manager->is_dev_environment() ) { ?>
							<p<?php if ( $license ) echo ' class="hidden"'; ?>>
								<label for="totaltheme-license-is-staging-checkbox">
									<input id="totaltheme-license-is-staging-checkbox" class="wpex-license-activation__checkbox" name="is_staging" type="checkbox"><?php esc_html_e( 'Enable Staging License Activation', 'total' ); ?>
								</label>
								<a href="#" role="button" class="wpex-license-activation__info-toggle" aria-expanded="false" aria-controls="totaltheme-staging-license-info"><span aria-hidden="true">(?)</span><span class="screen-reader-text"><?php esc_html_e( 'More information about Staging License Activation', 'total' ); ?></span></a>
							</p>

							<p id="totaltheme-staging-license-info" class="wpex-license-activation__warn hidden"><?php
								printf(
									esc_html__( 'Staging activation lets you use your license on a development, staging, or cloned site to access theme features and receive updates. The license will be verified to ensure it\'s valid but will not be registered as a live site. When activated in staging mode, a notice will display in your WordPress dashboard to indicate the site is running in a staging environment.%sIf you\'re building a new site and prefer not to display this notice, you can instead register the license normally and later transfer it to your live domain when the site is ready.', 'total' ),
									'<br><br>'
								);
							?></p>
						<?php } ?>

						<?php
						$is_staging_mode = in_array( $license_status, [ 'staging', 'invalid_staging' ], true );
						if ( ! $license || $is_staging_mode ) { ?>
							<p id="totaltheme-staging-license-warning" class="wpex-license-activation__warn<?php echo $is_staging_mode ? '' : ' hidden' ?>"><?php
								esc_html_e( 'Your license is currently registered in staging mode. To register it on a live site, click the Deactivate button, then re-add your license and activate it without checking "Enable Local License Activation".', 'total' );
							?></p>
						<?php } ?>

						<?php wp_nonce_field( 'wpex_theme_license_form_nonce', 'wpex_theme_license_form_nonce' ); ?>

						<div class="wpex-license-activation__submit">
							<?php
							$submit_classes = 'wpex-license-activation__button primary button-hero ';
							$submit_classes .= $license ? 'deactivate' : 'activate';
							$activate_txt   = esc_html__( 'Activate your license', 'total' );
							$deactivate_txt = esc_html__( 'Deactivate your license', 'total' );
							submit_button(
								$license ? $deactivate_txt : $activate_txt,
								$submit_classes,
								'submit',
								false,
								[
									'data-activate'   => $activate_txt,
									'data-deactivate' => $deactivate_txt,
								]
							); ?>
							<div class="wpex-license-activation__spinner"><?php echo totaltheme_get_loading_icon( 'wordpress' ); ?></div>
						</div>

					</form>

					<p class="wpex-license-activation__description"><?php 
						printf(
							/* translators: 1: open strong tag 2: close strong tag 3: open link to docs 4: close link to docs */
							esc_html__( 'A purchase code (license) is only valid for %1$sone live WordPress installation%2$s (single or multisite). Already using this theme on another site? %3$sPurchase a new license here%4$s. If you are running a multisite network, you only need to activate the license on the main site.', 
							'total' ),
							'<strong>',
							'</strong>',
							'<a target="_blank" rel="noopener noreferrer" href="https://1.envato.market/EPJRe">',
							'</a>'
						);
					?></p>

				</div>

			</div>

			<div class="wpex-license-activation__links">
				<a href="https://my.totalwptheme.com" target="_blank" rel="noopener noreferrer"><?php esc_html_e( 'Manage Your Licenses', 'total' ); ?></a>
			</div>

		</div>
	<?php }

	/**
	 * License form ajax.
	 */
	public function license_form_ajax() {
		if ( ! isset( $_POST['nonce'] )
			|| ! isset( $_POST['process'] )
			|| ! wp_verify_nonce( sanitize_text_field( wp_unslash( $_POST['nonce'] ) ), 'wpex_theme_license_form_nonce' )
		) {
			wp_die();
		}

		$response = [
			'message'       => '',
			'messageClass'  => 'notice-error',
			'success'       => false,
			'response_code' => '',
		];

		if ( empty( $_POST['license'] ) ) {
			$response['message'] = esc_html__( 'Please enter a license.', 'total' );
			$response['messageClass'] = 'notice-warning';
		} else {
			$license = sanitize_key( wp_unslash( $_POST['license'] ) );
			$process = sanitize_key( wp_unslash( $_POST['process'] ) );
			switch ( $process ) {
				case 'deactivate':
					$license_status = sanitize_key( wp_unslash( $_POST['licenseStatus'] ) );
					$response = wp_parse_args( $this->license_manager->deactivate_license( $license, $license_status ), $response );
					break;
				case 'activate':
					$is_staging = absint( wp_unslash( $_POST['isStaging'] ?? 0 ) );
					$response = wp_parse_args( $this->license_manager->activate_license( $license, $is_staging ), $response );
					break;
			}
		}

		wp_send_json( $response );
		wp_die();
	}

	/**
	 * Prevent cloning.
	 */
	private function __clone() {}

	/**
	 * Prevent unserializing.
	 */
	public function __wakeup() {
		trigger_error( 'Cannot unserialize a Singleton.', E_USER_WARNING);
	}

}
