<?php

if ( ! defined( 'ABSPATH' ) ) {
	exit;
}

class Pixelmole_Followup_Admin {
	const REVIEW_DELAY_SECONDS = 1209600; // 14 days.
	const REVIEW_MIN_SENT_EMAILS = 5;

	/** @var Pixelmole_Followup_Plugin */
	private $plugin;

	/** @var Pixelmole_Followup_Logger */
	private $logger;

	public function __construct( Pixelmole_Followup_Plugin $plugin, Pixelmole_Followup_Logger $logger ) {
		$this->plugin = $plugin;
		$this->logger = $logger;
	}

	public function register_hooks() {
		add_action( 'admin_menu', [ $this, 'register_settings_page' ] );
		add_action( 'admin_init', [ $this, 'register_settings' ] );
		add_action( 'admin_init', [ $this, 'handle_review_prompt_action' ] );
		add_action( 'admin_notices', [ $this, 'render_review_notice' ] );
		add_action( 'admin_enqueue_scripts', [ $this, 'enqueue_assets' ] );
		add_filter( 'allowed_redirect_hosts', [ $this, 'allow_review_redirect_host' ] );
		add_filter( 'admin_body_class', [ $this, 'filter_body_class' ] );
		add_filter( 'plugin_action_links_' . plugin_basename( PIXELMOLE_FOLLOWUP_FILE ), [ $this, 'add_settings_link' ] );
		add_action( 'wp_ajax_pixelmole_cancel_followup_email', [ $this, 'ajax_cancel_scheduled_email' ] );
		add_action( 'admin_post_pixelmole_followup_save_settings', [ $this, 'handle_save_settings' ] );
		add_filter( 'mce_external_plugins', [ $this, 'register_tinymce_plugin' ] );
		add_filter( 'mce_buttons', [ $this, 'register_tinymce_button' ] );
		add_filter( 'manage_edit-shop_order_columns', [ $this, 'add_followup_status_column' ] );
		add_action( 'manage_shop_order_posts_custom_column', [ $this, 'render_followup_status_column' ], 10, 2 );
		add_filter( 'manage_woocommerce_page_wc-orders_columns', [ $this, 'add_followup_status_column' ] );
		add_action( 'manage_woocommerce_page_wc-orders_custom_column', [ $this, 'render_followup_status_column_hpos' ], 10, 2 );
	}

	public function add_settings_link( array $links ) {
		$url = add_query_arg(
			[ 'page' => $this->plugin->get_menu_slug() ],
			admin_url( 'admin.php' )
		);
		$links[] = '<a href="' . esc_url( $url ) . '">' . esc_html__( 'Settings', 'pixelmole-follow-up-emails' ) . '</a>';

		return $links;
	}

	public function register_settings_page() {
		add_submenu_page(
			'woocommerce',
			__( 'Follow-up emails', 'pixelmole-follow-up-emails' ),
			__( 'Follow-up emails', 'pixelmole-follow-up-emails' ),
			'manage_woocommerce',
			$this->plugin->get_menu_slug(),
			[ $this, 'render_settings_page' ]
		);
	}

	public function register_settings() {
		add_settings_section(
			'pixelmole_followup_main',
			__( 'Email settings', 'pixelmole-follow-up-emails' ),
			function () {
				echo '<p>' . esc_html__( 'Set the sender, subject, and content of the email. You can use placeholders.', 'pixelmole-follow-up-emails' ) . '</p>';
				echo '<p><strong>' . esc_html__( 'Available placeholders:', 'pixelmole-follow-up-emails' ) . '</strong> {{site_name}}, {{site_url}}, {{customer_first_name}}, {{customer_last_name}}</p>';
			},
			$this->plugin->get_menu_slug()
		);

		add_settings_field( 'enabled', '', [ $this, 'field_enabled' ], $this->plugin->get_menu_slug(), 'pixelmole_followup_main' );
		add_settings_field( 'from_name', __( 'From name', 'pixelmole-follow-up-emails' ), [ $this, 'field_from_name' ], $this->plugin->get_menu_slug(), 'pixelmole_followup_main' );
		add_settings_field( 'from_email', __( 'From email address', 'pixelmole-follow-up-emails' ), [ $this, 'field_from_email' ], $this->plugin->get_menu_slug(), 'pixelmole_followup_main' );
		add_settings_field( 'subject', __( 'Subject', 'pixelmole-follow-up-emails' ), [ $this, 'field_subject' ], $this->plugin->get_menu_slug(), 'pixelmole_followup_main' );
		add_settings_field( 'body', __( 'Content', 'pixelmole-follow-up-emails' ), [ $this, 'field_body' ], $this->plugin->get_menu_slug(), 'pixelmole_followup_main' );
		add_settings_field( 'delay', __( 'Send after', 'pixelmole-follow-up-emails' ), [ $this, 'field_delay' ], $this->plugin->get_menu_slug(), 'pixelmole_followup_main' );
	}

	public function handle_review_prompt_action() {
		if ( ! current_user_can( 'manage_woocommerce' ) ) {
			return;
		}

		$action = isset( $_GET['pixelmole_review_action'] ) ? sanitize_key( wp_unslash( $_GET['pixelmole_review_action'] ) ) : ''; // phpcs:ignore WordPress.Security.NonceVerification.Recommended
		if ( ! in_array( $action, [ 'reviewed', 'later', 'dismiss' ], true ) ) {
			return;
		}

		$nonce = isset( $_GET['_pixelmole_review_nonce'] ) ? sanitize_text_field( wp_unslash( $_GET['_pixelmole_review_nonce'] ) ) : ''; // phpcs:ignore WordPress.Security.NonceVerification.Recommended
		if ( ! wp_verify_nonce( $nonce, 'pixelmole_review_prompt' ) ) {
			return;
		}

		if ( 'later' === $action ) {
			update_option( Pixelmole_Followup_Plugin::REVIEW_SNOOZE_UNTIL_OPTION, time() + self::REVIEW_DELAY_SECONDS );
		} else {
			update_option( Pixelmole_Followup_Plugin::REVIEW_STATUS_OPTION, 'dismissed' );
		}

		if ( 'reviewed' === $action ) {
			wp_safe_redirect( 'https://wordpress.org/support/plugin/pixelmole-follow-up-emails/reviews/#new-post' );
			exit;
		}

		$redirect = add_query_arg(
			[
				'page' => $this->plugin->get_menu_slug(),
				'tab'  => 'settings',
			],
			admin_url( 'admin.php' )
		);
		wp_safe_redirect( $redirect );
		exit;
	}

	public function render_review_notice() {
		if ( ! $this->should_show_review_notice() ) {
			return;
		}

		$actions    = $this->get_review_action_links();
		?>
		<div class="notice notice-info pixelmole-review-notice">
			<div class="pixelmole-review-notice-icon" aria-hidden="true">
				<span class="dashicons dashicons-star-filled"></span>
			</div>
			<div class="pixelmole-review-notice-content">
				<p>
					<?php esc_html_e( 'Thanks for using Pixelmole Follow-up Emails. If it helps your store, would you mind leaving a quick review?', 'pixelmole-follow-up-emails' ); ?>
				</p>
				<p>
					<a href="<?php echo esc_url( $actions['reviewed'] ); ?>" class="button button-primary" target="_blank" rel="noopener noreferrer"><?php esc_html_e( 'Leave a review', 'pixelmole-follow-up-emails' ); ?></a>
					<a href="<?php echo esc_url( $actions['later'] ); ?>" class="button button-secondary"><?php esc_html_e( 'Maybe later', 'pixelmole-follow-up-emails' ); ?></a>
					<a href="<?php echo esc_url( $actions['dismiss'] ); ?>" class="button-link"><?php esc_html_e( 'Don’t show again', 'pixelmole-follow-up-emails' ); ?></a>
				</p>
			</div>
		</div>
		<?php
	}

	public function allow_review_redirect_host( $hosts ) {
		$hosts[] = 'wordpress.org';
		return array_values( array_unique( $hosts ) );
	}

	public function sanitize_settings( $input ) {
		$output = [];
		$output['enabled']    = ! empty( $input['enabled'] ) ? 1 : 0;
		$output['from_name']  = isset( $input['from_name'] ) ? sanitize_text_field( $input['from_name'] ) : '';
		$output['from_email'] = isset( $input['from_email'] ) ? sanitize_email( $input['from_email'] ) : '';
		$output['subject']    = isset( $input['subject'] ) ? sanitize_text_field( $input['subject'] ) : '';

		$body = isset( $input['body'] ) ? (string) $input['body'] : '';
		$body = $this->normalize_site_url_placeholder( $body );
		$output['subject'] = $this->normalize_site_url_placeholder( $output['subject'] );

		$allowed = [
			'a'      => [
				'href'   => [],
				'title'  => [],
				'target' => [],
				'rel'    => [],
				'class'  => [],
				'style'  => [],
				'role'   => [],
			],
			'button' => [
				'type'   => [],
				'class'  => [],
				'style'  => [],
				'role'   => [],
			],
			'img'    => [
				'src'    => [],
				'alt'    => [],
				'class'  => [],
				'style'  => [],
				'width'  => [],
				'height' => [],
				'srcset' => [],
				'sizes'  => [],
			],
			'div'    => [
				'class' => [],
				'style' => [],
			],
			'span'   => [
				'class' => [],
				'style' => [],
			],
			'br'     => [],
			'hr'     => [],
			'em'     => [],
			'strong' => [],
			'p'      => [
				'class' => [],
				'style' => [],
			],
			'ul'     => [
				'class' => [],
				'style' => [],
			],
			'ol'     => [
				'class' => [],
				'style' => [],
			],
			'li'     => [
				'class' => [],
				'style' => [],
			],
			'table'  => [
				'class'       => [],
				'style'       => [],
				'cellpadding' => [],
				'cellspacing' => [],
				'border'      => [],
				'width'       => [],
			],
			'tbody'  => [],
			'thead'  => [],
			'tfoot'  => [],
			'tr'     => [
				'class' => [],
				'style' => [],
			],
			'td'     => [
				'class'   => [],
				'style'   => [],
				'colspan' => [],
				'rowspan' => [],
			],
			'th'     => [
				'class'   => [],
				'style'   => [],
				'colspan' => [],
				'rowspan' => [],
			],
			'h1'     => [ 'class' => [], 'style' => [] ],
			'h2'     => [ 'class' => [], 'style' => [] ],
			'h3'     => [ 'class' => [], 'style' => [] ],
			'h4'     => [ 'class' => [], 'style' => [] ],
			'h5'     => [ 'class' => [], 'style' => [] ],
			'h6'     => [ 'class' => [], 'style' => [] ],
		];
		$output['body'] = wp_kses( $body, $allowed );

		$output['delay_amount'] = isset( $input['delay_amount'] ) ? absint( $input['delay_amount'] ) : 0;
		$unit                   = isset( $input['delay_unit'] ) ? sanitize_key( $input['delay_unit'] ) : 'days';
		$allowed_units          = [ 'minutes', 'hours', 'days' ];
		$output['delay_unit']   = in_array( $unit, $allowed_units, true ) ? $unit : 'days';

		return $output;
	}

	private function normalize_site_url_placeholder( $value ) {
		$patterns = [
			'https://{{site_url}}',
			'http://{{site_url}}',
		];

		return str_replace( $patterns, '{{site_url}}', $value );
	}

	public function handle_save_settings() {
		if ( ! current_user_can( 'manage_woocommerce' ) ) {
			wp_die( esc_html__( 'You are not allowed to perform this action.', 'pixelmole-follow-up-emails' ) );
		}

		check_admin_referer( $this->plugin->get_nonce_key(), 'pixelmole_followup_nonce' );

		$input = isset( $_POST[ $this->plugin->get_option_key() ] )
			? (array) wp_unslash( $_POST[ $this->plugin->get_option_key() ] ) // phpcs:ignore WordPress.Security.ValidatedSanitizedInput.InputNotSanitized -- Sanitized in sanitize_settings().
			: [];

		$settings = $this->sanitize_settings( $input );
		$this->plugin->get_email_store()->upsert_primary_email( $settings );

		$redirect = add_query_arg(
			[
				'page'    => $this->plugin->get_menu_slug(),
				'tab'     => 'settings',
				'updated' => 'true',
			],
			admin_url( 'admin.php' )
		);

		wp_safe_redirect( $redirect );
		exit;
	}

	public function enqueue_assets( $hook ) {
		$is_plugin_screen = ( 'woocommerce_page_' . $this->plugin->get_menu_slug() === $hook );
		$is_orders_screen = $this->is_orders_screen();

		if ( ! $is_plugin_screen && ! $is_orders_screen ) {
			return;
		}

		if ( $is_plugin_screen ) {
			wp_enqueue_style(
				'pixelmole-follow-up-emails-admin',
				$this->plugin->get_asset_url( 'assets/css/admin.css' ),
				[],
				$this->plugin->get_version()
			);
		}

		if ( $is_orders_screen ) {
			wp_enqueue_style(
				'pixelmole-follow-up-emails-orders',
				$this->plugin->get_asset_url( 'assets/css/orders-admin.css' ),
				[],
				$this->plugin->get_version()
			);
		}

		if ( ! $is_plugin_screen ) {
			return;
		}

		wp_enqueue_script(
			'pixelmole-follow-up-emails-admin',
			$this->plugin->get_asset_url( 'assets/js/pixelmole-follow-up-emails-admin.js' ),
			[ 'jquery' ],
			$this->plugin->get_version(),
			true
		);

		wp_localize_script(
			'pixelmole-follow-up-emails-admin',
			'PixelMoleFollowup',
			[
				'ajaxUrl' => admin_url( 'admin-ajax.php' ),
				'nonce'   => wp_create_nonce( $this->plugin->get_nonce_key() ),
				'i18n'    => [
					'confirmCancel' => __( 'Are you sure you want to delete this email? This action cannot be undone.', 'pixelmole-follow-up-emails' ),
					'cancelSuccess' => __( 'Scheduled email canceled.', 'pixelmole-follow-up-emails' ),
					'cancelError'   => __( 'Could not cancel the scheduled email. It might have already been sent.', 'pixelmole-follow-up-emails' ),
				],
				'colors'  => [
					'accent' => $this->get_email_accent_color(),
				],
			]
		);
	}

	public function filter_body_class( $classes ) {
		if ( ! $this->is_plugin_screen() ) {
			return $classes;
		}

		return $classes . ' follow-up-mail-admin';
	}

	public function render_settings_page() {
		if ( ! current_user_can( 'manage_woocommerce' ) ) {
			return;
		}

		$tabs = [
			'settings'  => [
				'label' => __( 'Email settings', 'pixelmole-follow-up-emails' ),
				'icon' => 'admin-customizer'
			],
			'scheduled' => [
				'label' => __( 'Scheduled emails', 'pixelmole-follow-up-emails' ),
				'icon' => 'calendar-alt'
			],
			'analytics' => [
				'label' => __( 'Sent emails', 'pixelmole-follow-up-emails' ),
				'icon' => 'chart-bar'
			]
		];

		$current_tab = isset( $_GET['tab'] ) ? sanitize_key( wp_unslash( $_GET['tab'] ) ) : 'settings'; // phpcs:ignore WordPress.Security.NonceVerification.Recommended
		if ( ! array_key_exists( $current_tab, $tabs ) ) {
			$current_tab = 'settings';
		}

		$base_url = admin_url( 'admin.php?page=' . $this->plugin->get_menu_slug() );
		?>
		<div class="wrap">
			<div class="page-header">
				<img src="<?php echo esc_url( $this->plugin->get_asset_url( 'assets/img/logo.png' ) ); ?>" alt="<?php esc_attr_e( 'Pixelmole logo', 'pixelmole-follow-up-emails' ); ?>" />
				<div class="page-header-content">
					<h1><?php esc_html_e( 'Follow-up emails', 'pixelmole-follow-up-emails' ); ?></h1>
					<h2><?php esc_html_e( 'by', 'pixelmole-follow-up-emails' ); ?> <a href="https://pixelmole.com" target="_blank">Pixelmole</a></h2>
					<div class="page-header-notices">
						<?php if ( isset( $_GET['updated'] ) ) : // phpcs:ignore WordPress.Security.NonceVerification.Recommended ?>
							<div class="notice notice-success is-dismissible">
								<p><?php esc_html_e( 'Settings saved.', 'pixelmole-follow-up-emails' ); ?></p>
							</div>
						<?php endif; ?>
					</div>
				</div>
			</div>
			<nav class="nav-tab-wrapper">
				<?php foreach ( $tabs as $tab_key => $tab_data ) : ?>
					<?php
					$tab_label = $tab_data['label'];
					$tab_icon = !empty( $tab_data['icon'] ) ? 'dashicons-' . $tab_data['icon'] : '';
					$tab_url   = esc_url( add_query_arg( 'tab', $tab_key, $base_url ) );
					$tab_class = 'nav-tab' . ( $tab_key === $current_tab ? ' nav-tab-active' : '' );
					?>
					<a href="<?php echo esc_url( $tab_url ); ?>" class="<?php echo esc_attr( $tab_class ); ?>">
						<?php if (!empty($tab_icon)) : ?>
						<span class='dashicons <?php echo esc_html( $tab_icon ) ?>'></span>
						<?php endif; ?>
						<?php echo esc_html( $tab_label ); ?>
					</a>
				<?php endforeach; ?>
			</nav>

			<?php if ( 'analytics' === $current_tab ) : ?>
				<?php $this->render_analytics_tab(); ?>
			<?php elseif ( 'scheduled' === $current_tab ) : ?>
				<?php $this->render_scheduled_tab(); ?>
			<?php else : ?>
				<div class="page-wrapper">
					<div class="pixelmole-settings-layout">
						<div class="pixelmole-settings-form">
							<form method="post" action="<?php echo esc_url( admin_url( 'admin-post.php' ) ); ?>">
								<?php wp_nonce_field( $this->plugin->get_nonce_key(), 'pixelmole_followup_nonce' ); ?>
								<input type="hidden" name="action" value="pixelmole_followup_save_settings" />
								<div class="panel no-margin">
									<?php do_settings_sections( $this->plugin->get_menu_slug() ); ?>
									<div class="page-submit">
										<?php submit_button(); ?>
									</div>
								</div>
							</form>
						</div>

						<div class="pixelmole-settings-resizer" role="separator" aria-orientation="vertical" aria-label="<?php echo esc_attr__( 'Resize panels', 'pixelmole-follow-up-emails' ); ?>"></div>

						<div class="pixelmole-settings-side">
							<div class="panel">
								<h2><?php echo esc_html__( 'Send test email', 'pixelmole-follow-up-emails' ); ?></h2>
								<div class="test-mail-fields">
									<input type="email" id="pixelmole-test-email" class="regular-text" placeholder="you@example.com" />
									<button class="button button-primary" id="pixelmole-send-test"><?php echo esc_html__( 'Send test', 'pixelmole-follow-up-emails' ); ?></button>
								</div>
								<span id="pixelmole-test-result" class="pixelmole-test-result" role="status" aria-live="polite"></span>
							</div>

							<div class="panel no-margin pixelmole-settings-preview">
								<h2><?php echo esc_html__( 'Preview', 'pixelmole-follow-up-emails' ); ?></h2>
								<iframe id="pixelmole-email-preview" title="<?php echo esc_attr__( 'Email preview', 'pixelmole-follow-up-emails' ); ?>"></iframe>
							</div>
						</div>
					</div>
				</div>
			<?php endif; ?>
		</div>
		<div class="pixelmole-feedback is-collapsed">
			<button type="button" class="pixelmole-feedback-close" aria-label="<?php echo esc_attr__( 'Toggle feedback prompt', 'pixelmole-follow-up-emails' ); ?>">
				<span class="dashicons dashicons-no-alt only-open" aria-hidden="true"></span>
				<span class="dashicons dashicons-admin-comments only-closed" aria-hidden="true"></span>
			</button>
			<div class="pixelmole-feedback-body">
				<span class="dashicons dashicons-admin-comments" aria-hidden="true"></span>
				<a class="button button-primary" href="<?php echo esc_url( $this->get_feedback_mailto() ); ?>">
					<?php echo esc_html__( 'Have an idea or something we can improve?', 'pixelmole-follow-up-emails' ); ?>
				</a>
				<p><?php echo esc_html__( 'This plugin is still in active development - your input shapes what comes next.', 'pixelmole-follow-up-emails' ); ?></p>
			</div>
		</div>
		<?php
	}

	public function field_from_name() {
		$val = esc_attr( $this->get_settings()['from_name'] );
		echo '<input type="text" name="' . esc_attr( $this->plugin->get_option_key() ) . '[from_name]" value="' . esc_attr( $val ) . '" class="regular-text" />';
	}

	public function field_from_email() {
		$val = esc_attr( $this->get_settings()['from_email'] );
		echo '<input type="email" name="' . esc_attr( $this->plugin->get_option_key() ) . '[from_email]" value="' . esc_attr( $val ) . '" class="regular-text" />';
	}

	public function field_subject() {
		$val = esc_attr( $this->get_settings()['subject'] );
		echo '<input type="text" name="' . esc_attr( $this->plugin->get_option_key() ) . '[subject]" value="' . esc_attr( $val ) . '" class="regular-text" />';
	}

	public function field_body() {
		$val = $this->get_settings()['body'];
		wp_editor(
			$val,
			'pixelmole_followup_body',
			[
				'textarea_name' => $this->plugin->get_option_key() . '[body]',
				'textarea_rows' => 10,
				'media_buttons' => true,
				'tinymce'       => [
					'toolbar1'      => 'formatselect bold italic underline | link unlink pixelmoleFollowupButton | bullist numlist | hr | alignleft aligncenter alignright | removeformat',
					'toolbar2'      => 'table image blockquote',
					'content_style' => 'body { font-family: sans-serif; font-size: 15px; }',
				],
				'quicktags'     => true,
			]
		);
	}

	public function field_enabled() {
		$checked = checked( 1, (int) $this->get_settings()['enabled'], false );
		echo '<label class="switch"><input type="checkbox" name="' . esc_attr( $this->plugin->get_option_key() ) . '[enabled]" value="1" ' . esc_attr( $checked ) . ' /><div class="slider"></div> ' . esc_html__( 'Enable automatic follow-up emails', 'pixelmole-follow-up-emails' ) . '</label>';
		echo '<p class="description">' . esc_html__( 'Disable to temporarily stop sending follow-up emails', 'pixelmole-follow-up-emails' ) . '</p>';
	}

	public function field_delay() {
		$settings = $this->get_settings();
		$amount   = isset( $settings['delay_amount'] ) ? (int) $settings['delay_amount'] : 0;
		$unit     = isset( $settings['delay_unit'] ) ? $settings['delay_unit'] : 'days';
		?>
		<div class="delay-fields">
			<input type="number" min="0" step="1" name="<?php echo esc_attr( $this->plugin->get_option_key() ); ?>[delay_amount]" value="<?php echo esc_attr( $amount ); ?>" class="small-text" />
			<select name="<?php echo esc_attr( $this->plugin->get_option_key() ); ?>[delay_unit]">
				<?php
				$options = [
					'minutes' => __( 'minutes', 'pixelmole-follow-up-emails' ),
					'hours'   => __( 'hours', 'pixelmole-follow-up-emails' ),
					'days'    => __( 'days', 'pixelmole-follow-up-emails' ),
				];
				foreach ( $options as $value => $label ) {
					printf(
						'<option value="%1$s"%2$s>%3$s</option>',
						esc_attr( $value ),
						selected( $unit, $value, false ),
						esc_html( $label )
					);
				}
				?>
			</select>
		</div>
		<p class="description"><?php esc_html_e( 'Define how long after the order the follow-up email should be sent. Use 0 to send it right after the trigger.', 'pixelmole-follow-up-emails' ); ?></p>
		<?php
	}

	private function render_analytics_tab() {
		if ( ! $this->logger_has_table() ) {
			echo '<div class="page-wrapper">';
			echo '<p>' . esc_html__( 'No emails have been sent yet, or the log hasn’t been created yet.', 'pixelmole-follow-up-emails' ) . '</p>';
			echo '</div>';
			return;
		}

		$per_page = 20;
		$paged    = isset( $_GET['paged'] ) ? max( 1, absint( $_GET['paged'] ) ) : 1; // phpcs:ignore WordPress.Security.NonceVerification.Recommended
		$result   = $this->logger->get_logs( $paged, $per_page );
		$logs     = $result['items'];

		if ( empty( $logs ) ) {
			echo '<div class="page-wrapper">';
			echo '<p>' . esc_html__( 'No emails have been sent yet.', 'pixelmole-follow-up-emails' ) . '</p>';
			echo '</div>';
			return;
		}

		$date_format = get_option( 'date_format' ) . ' ' . get_option( 'time_format' );
		?>
		<div class="page-wrapper">
			<table class="widefat striped pixelmole-analytics-table">
				<thead>
					<tr>
						<th><?php echo esc_html__( 'Date', 'pixelmole-follow-up-emails' ); ?></th>
						<th><?php echo esc_html__( 'Receiver', 'pixelmole-follow-up-emails' ); ?></th>
						<th><?php echo esc_html__( 'Subject', 'pixelmole-follow-up-emails' ); ?></th>
						<th><?php echo esc_html__( 'Order', 'pixelmole-follow-up-emails' ); ?></th>
					</tr>
				</thead>
				<tbody>
					<?php foreach ( $logs as $log ) : ?>
						<?php
						$sent_at      = isset( $log['sent_at'] ) ? $log['sent_at'] : '';
						$timestamp    = $sent_at ? strtotime( $sent_at . ' UTC' ) : false;
						$display_date = $timestamp ? date_i18n( $date_format, $timestamp ) : '';
						$type         = isset( $log['email_type'] ) ? $log['email_type'] : 'followup';
						$type_label   = 'test' === $type ? __( 'Test', 'pixelmole-follow-up-emails' ) : __( 'Automatic', 'pixelmole-follow-up-emails' );
						$order_id     = isset( $log['order_id'] ) ? absint( $log['order_id'] ) : 0;
						$order_column = $order_id
							? sprintf(
								'<a href="%1$s">#%2$d</a>',
								esc_url( admin_url( 'post.php?post=' . $order_id . '&action=edit' ) ),
								$order_id
							)
							: '&mdash;';
						?>
						<tr>
							<td>
								<?php echo esc_html( $display_date ); ?>
							</td>
							<td><?php echo esc_html( $log['recipient'] ); ?></td>
							<td>
								<?php
									if ( $type_label == 'Test')
									{
										echo '<span class="pill">';
										echo esc_html( $type_label );
										echo '</span>';
									}
								?>
								<?php
									echo '<span class="subject">';
									echo esc_html( $log['subject'] );
									echo '</span>';
								?>
							</td>
							<td><?php echo wp_kses_post( $order_column ); ?></td>
						</tr>
					<?php endforeach; ?>
				</tbody>
			</table>
		</div>
		<?php
		$total_pages = (int) ceil( $result['total'] / $per_page );
		if ( $total_pages > 1 ) {
			$base_url = add_query_arg(
				[
					'tab'   => 'analytics',
					'paged' => '%#%',
				],
				admin_url( 'admin.php?page=' . $this->plugin->get_menu_slug() )
			);

			$pagination = paginate_links(
				[
					'base'      => $base_url,
					'format'    => '',
					'current'   => $paged,
					'total'     => $total_pages,
					'prev_text' => '&laquo;',
					'next_text' => '&raquo;',
					'type'      => 'array',
				]
			);

			if ( ! empty( $pagination ) ) {
				echo '<div class="tablenav"><div class="tablenav-pages">';
				foreach ( $pagination as $link ) {
					echo wp_kses_post( $link );
				}
				echo '</div></div>';
			}
		}
	}

	private function get_settings() {
		return $this->plugin->get_settings();
	}

	private function render_scheduled_tab() {
		$scheduled_emails = $this->get_scheduled_emails();
		echo '<div class="page-wrapper">';

		if ( empty( $scheduled_emails ) ) {
			echo '<p><i>' . esc_html__( 'There are currently no follow-up emails scheduled.', 'pixelmole-follow-up-emails' ) . '</i></p>';
			echo '</div>';
			return;
		}

		$date_format = get_option( 'date_format' ) . ' ' . get_option( 'time_format' );
		echo '<table class="widefat striped pixelmole-scheduled-table">';
		echo '<thead><tr>';
		echo '<th>' . esc_html__( 'Send at', 'pixelmole-follow-up-emails' ) . '</th>';
		echo '<th>' . esc_html__( 'Order', 'pixelmole-follow-up-emails' ) . '</th>';
		echo '<th>' . esc_html__( 'Customer', 'pixelmole-follow-up-emails' ) . '</th>';
		echo '<th>' . esc_html__( 'Email', 'pixelmole-follow-up-emails' ) . '</th>';
		echo '<th>' . esc_html__( 'Actions', 'pixelmole-follow-up-emails' ) . '</th>';
		echo '</tr></thead><tbody>';
		foreach ( $scheduled_emails as $email ) {
			$send_at   = date_i18n( $date_format, $email['timestamp'] );
			$order_col = '&mdash;';

			if ( $email['order_id'] ) {
				$order_url = admin_url( 'post.php?post=' . $email['order_id'] . '&action=edit' );
				$order_col = sprintf(
					'<a href="%1$s">#%2$d</a>',
					esc_url( $order_url ),
					absint( $email['order_id'] )
				);
			}
			$button = '&mdash;';
			if ( $email['order_id'] ) {
				$button = sprintf(
					'<button type="button" class="button button-secondary pixelmole-cancel-email" data-order-id="%1$d" data-timestamp="%2$d">%3$s</button>',
					absint( $email['order_id'] ),
					absint( $email['timestamp'] ),
					esc_html__( 'Cancel sending', 'pixelmole-follow-up-emails' )
				);
			}

			echo '<tr>';
			echo '<td>' . esc_html( $send_at ) . '</td>';
			echo '<td>' . wp_kses_post( $order_col ) . '</td>';
			echo '<td>' . ( $email['customer_name'] ? esc_html( $email['customer_name'] ) : '&mdash;' ) . '</td>';
			echo '<td>' . ( $email['recipient'] ? esc_html( $email['recipient'] ) : '&mdash;' ) . '</td>';
			echo '<td>' . wp_kses_post( $button ) . '</td>';
			echo '</tr>';
		}
		echo '</tbody></table>';
		echo '</div>';
	}

	private function get_scheduled_emails() {
		if ( ! function_exists( '_get_cron_array' ) ) {
			return [];
		}

		$cron = _get_cron_array();
		if ( ! is_array( $cron ) ) {
			return [];
		}

		$hook            = $this->plugin->get_cron_hook();
		$scheduled_items = [];

		foreach ( $cron as $timestamp => $hooks ) {
			if ( empty( $hooks[ $hook ] ) ) {
				continue;
			}

			foreach ( $hooks[ $hook ] as $event ) {
				$args     = isset( $event['args'] ) ? $event['args'] : [];
				$order_id = isset( $args[0] ) ? absint( $args[0] ) : 0;

				$customer_name = '';
				$recipient     = '';

				if ( function_exists( 'wc_get_order' ) && $order_id ) {
					$order = wc_get_order( $order_id );
					if ( $order ) {
						$recipient     = $order->get_billing_email();
						$customer_name = trim( $order->get_billing_first_name() . ' ' . $order->get_billing_last_name() );
					}
				}

				$scheduled_items[] = [
					'timestamp'     => (int) $timestamp,
					'order_id'      => $order_id,
					'customer_name' => $customer_name,
					'recipient'     => $recipient,
				];
			}
		}

		usort(
			$scheduled_items,
			function ( $a, $b ) {
				return $a['timestamp'] <=> $b['timestamp'];
			}
		);

		return $scheduled_items;
	}

	public function ajax_cancel_scheduled_email() {
		check_ajax_referer( $this->plugin->get_nonce_key(), 'nonce' );

		if ( ! current_user_can( 'manage_woocommerce' ) ) {
			wp_send_json_error(
				[ 'message' => __( 'You are not allowed to perform this action.', 'pixelmole-follow-up-emails' ) ],
				403
			);
		}

		$order_id  = isset( $_POST['orderId'] ) ? absint( wp_unslash( $_POST['orderId'] ) ) : 0;
		$timestamp = isset( $_POST['timestamp'] ) ? absint( wp_unslash( $_POST['timestamp'] ) ) : 0;

		if ( ! $order_id || ! $timestamp ) {
			wp_send_json_error(
				[ 'message' => __( 'Invalid request data.', 'pixelmole-follow-up-emails' ) ],
				400
			);
		}

		$hook = $this->plugin->get_cron_hook();
		$event = wp_get_scheduled_event( $hook, [ $order_id ], $timestamp );

		if ( ! $event ) {
			wp_send_json_error(
				[ 'message' => __( 'Follow-up email is no longer scheduled.', 'pixelmole-follow-up-emails' ) ],
				404
			);
		}

		$unscheduled = wp_unschedule_event( $timestamp, $hook, [ $order_id ] );

		if ( ! $unscheduled ) {
			wp_send_json_error(
				[ 'message' => __( 'Could not cancel the follow-up email. Please try again.', 'pixelmole-follow-up-emails' ) ],
				500
			);
		}

		if ( function_exists( 'wc_get_order' ) ) {
			$order = wc_get_order( $order_id );
			if ( $order ) {
				$order->update_meta_data( '_pixelmole_followup_cancelled', 'yes' );
				$order->save();
			}
		}

		wp_send_json_success(
			[ 'message' => __( 'Scheduled email canceled.', 'pixelmole-follow-up-emails' ) ]
		);
	}

	private function get_current_screen_id() {
		if ( ! function_exists( 'get_current_screen' ) ) {
			return '';
		}

		$screen = get_current_screen();
		return $screen ? $screen->id : '';
	}

	private function logger_has_table() {
		return $this->logger->table_exists();
	}

	public function register_tinymce_plugin( $plugins ) {
		$plugins['pixelmole_followup_button'] = $this->plugin->get_asset_url( 'assets/js/tinymce-button.js' );
		return $plugins;
	}

	public function register_tinymce_button( $buttons ) {
		$buttons[] = 'pixelmoleFollowupButton';
		return $buttons;
	}

	private function is_plugin_screen() {
		$screen_id = $this->get_current_screen_id();
		if ( $screen_id && 'woocommerce_page_' . $this->plugin->get_menu_slug() === $screen_id ) {
			return true;
		}

		$page = isset( $_GET['page'] ) ? sanitize_text_field( wp_unslash( $_GET['page'] ) ) : ''; // phpcs:ignore WordPress.Security.NonceVerification.Recommended
		return $page === $this->plugin->get_menu_slug();
	}

	private function is_orders_screen() {
		$screen_id = $this->get_current_screen_id();

		if ( in_array( $screen_id, [ 'edit-shop_order', 'woocommerce_page_wc-orders' ], true ) ) {
			return true;
		}

		$post_type = isset( $_GET['post_type'] ) ? sanitize_key( wp_unslash( $_GET['post_type'] ) ) : ''; // phpcs:ignore WordPress.Security.NonceVerification.Recommended
		return 'shop_order' === $post_type;
	}

	private function get_email_accent_color() {
		$default = '#96588a';
		$color   = get_option( 'woocommerce_email_base_color', $default );
		$color   = (string) $color;
		$color   = sanitize_hex_color( $color );

		return $color ? $color : $default;
	}

	private function get_feedback_mailto() {
		$plugin_version = $this->plugin->get_version();
		$wp_version     = get_bloginfo( 'version' );
		$wc_version     = defined( 'WC_VERSION' ) ? WC_VERSION : 'n/a';
		$admin_locale   = function_exists( 'get_user_locale' ) ? get_user_locale() : get_locale();
		$site_locale    = get_locale();

		$subject = sprintf(
			'Feedback - Pixelmole Follow-up Emails v%s',
			$plugin_version
		);

		$body_lines = [
			'Hi Pixelmole,',
			'',
			__( 'I have some feedback about your plugin:', 'pixelmole-follow-up-emails' ),
			'',
			'---',
			'Plugin version: ' . $plugin_version,
			'WordPress version: ' . $wp_version,
			'WooCommerce version: ' . $wc_version,
			'Admin locale: ' . $admin_locale,
			'Site locale: ' . $site_locale,
			'Site: ' . home_url(),
		];

		$body = implode( "\n", $body_lines );

		return sprintf(
			'mailto:info@pixelmole.com?subject=%s&body=%s',
			rawurlencode( $subject ),
			rawurlencode( $body )
		);
	}

	private function should_show_review_notice() {
		if ( ! current_user_can( 'manage_woocommerce' ) || ! $this->is_plugin_screen() ) {
			return false;
		}

		$status = get_option( Pixelmole_Followup_Plugin::REVIEW_STATUS_OPTION, '' );
		if ( 'dismissed' === $status ) {
			return false;
		}

		$activated_at = absint( get_option( Pixelmole_Followup_Plugin::ACTIVATED_AT_OPTION, 0 ) );
		if ( ! $activated_at || ( time() - $activated_at ) < self::REVIEW_DELAY_SECONDS ) {
			return false;
		}

		$snooze_until = absint( get_option( Pixelmole_Followup_Plugin::REVIEW_SNOOZE_UNTIL_OPTION, 0 ) );
		if ( $snooze_until && $snooze_until > time() ) {
			return false;
		}

		return $this->logger->get_followup_email_count() >= self::REVIEW_MIN_SENT_EMAILS;
	}

	private function get_review_action_links() {
		$base = add_query_arg(
			[
				'page' => $this->plugin->get_menu_slug(),
				'tab'  => 'settings',
			],
			admin_url( 'admin.php' )
		);

		$nonce = wp_create_nonce( 'pixelmole_review_prompt' );

		return [
			'reviewed' => add_query_arg(
				[
					'pixelmole_review_action' => 'reviewed',
					'_pixelmole_review_nonce' => $nonce,
				],
				$base
			),
			'later'   => add_query_arg(
				[
					'pixelmole_review_action' => 'later',
					'_pixelmole_review_nonce' => $nonce,
				],
				$base
			),
			'dismiss' => add_query_arg(
				[
					'pixelmole_review_action' => 'dismiss',
					'_pixelmole_review_nonce' => $nonce,
				],
				$base
			),
		];
	}

	public function add_followup_status_column( $columns ) {
		$new_columns = [];
		$inserted    = false;

		foreach ( $columns as $key => $label ) {
			$new_columns[ $key ] = $label;
			if ( 'order_status' === $key ) {
				$new_columns['pixelmole_followup_status'] = __( 'Follow-up', 'pixelmole-follow-up-emails' );
				$inserted = true;
			}
		}

		if ( ! $inserted ) {
			$new_columns['pixelmole_followup_status'] = __( 'Follow-up', 'pixelmole-follow-up-emails' );
		}

		return $new_columns;
	}

	public function render_followup_status_column( $column, $post_id ) {
		if ( 'pixelmole_followup_status' !== $column ) {
			return;
		}

		if ( ! function_exists( 'wc_get_order' ) ) {
			return;
		}

		$order = wc_get_order( $post_id );
		if ( ! $order ) {
			return;
		}

		echo wp_kses_post( $this->get_followup_status_badge( $order ) );
	}

	public function render_followup_status_column_hpos( $column, $order ) {
		if ( 'pixelmole_followup_status' !== $column || ! $order ) {
			return;
		}

		echo wp_kses_post( $this->get_followup_status_badge( $order ) );
	}

	private function get_followup_status_badge( $order ) {
		$status = 'none';
		$text   = __( 'Not scheduled', 'pixelmole-follow-up-emails' );
		$title  = $text;
		$link   = '';

		$sent      = $order->get_meta( '_pixelmole_followup_sent', true );
		$cancelled = $order->get_meta( '_pixelmole_followup_cancelled', true );
		$scheduled = wp_next_scheduled( $this->plugin->get_cron_hook(), [ $order->get_id() ] );

		if ( 'yes' === $sent ) {
			$status = 'sent';
			$text   = __( 'Sent', 'pixelmole-follow-up-emails' );
			$title  = $text;
			$link   = admin_url( 'admin.php?page=' . $this->plugin->get_menu_slug() . '&tab=analytics' );
		} elseif ( $scheduled ) {
			$status = 'scheduled';
			$text   = __( 'Scheduled', 'pixelmole-follow-up-emails' );
			$title  = $text;
			$link   = admin_url( 'admin.php?page=' . $this->plugin->get_menu_slug() . '&tab=scheduled' );
		} elseif ( 'yes' === $cancelled ) {
			$status = 'cancelled';
			$text   = __( 'Cancelled', 'pixelmole-follow-up-emails' );
			$title  = $text;
		}

		$badge = sprintf(
			'<span class="pixelmole-followup-status is-%1$s" title="%2$s" aria-label="%2$s"><span class="dashicons dashicons-email-alt"></span><span class="pixelmole-followup-status-dot" aria-hidden="true"></span><span class="screen-reader-text">%2$s</span></span>',
			esc_attr( $status ),
			esc_attr( $title )
		);

		if ( $link ) {
			return sprintf(
				'<a class="pixelmole-followup-status-link" href="%1$s">%2$s</a>',
				esc_url( $link ),
				$badge
			);
		}

		return $badge;
	}
}
