
// Delegated click handler for Add buttons rendered in the search results table.
jQuery(document).on('click', '.scholar-sync-add-btn', function () {
	addAuthorFromSearch(this);
});

// Toggle the "not synced" explanation box (with its re-enable checkbox) when its badge
// is clicked or activated via keyboard. Pure show/hide — the checkbox inside is a normal
// form field, submitted with the rest of the form on the page's existing Update button.
jQuery(document).on('click', '.scholar-sync-sync-badge', function () {
	toggleSyncExplain(this);
});
jQuery(document).on('keydown', '.scholar-sync-sync-badge', function (e) {
	if (e.key === 'Enter' || e.key === ' ') {
		e.preventDefault();
		toggleSyncExplain(this);
	}
});
function toggleSyncExplain(badge) {
	var explain = jQuery(badge).next('.scholar-sync-sync-explain');
	explain.prop('hidden', !explain.prop('hidden'));
}

// Replaces server-rendered "GMT+0000"-labeled times with the viewer's own local time —
// the server can't know the visitor's timezone, but the browser always does, so no
// timezone label is needed once converted. Falls back to the server-rendered text
// (already unambiguous, just less convenient) if the browser can't parse the ISO value.
function scholarSyncLocalizeTimes(root) {
	(root || document).querySelectorAll('.scholar-sync-local-time[data-utc]').forEach(function (el) {
		var d = new Date(el.getAttribute('data-utc'));
		if (!isNaN(d.getTime())) {
			el.textContent = d.toLocaleString();
		}
	});
}
document.addEventListener('DOMContentLoaded', function () {
	scholarSyncLocalizeTimes(document);
});

/**
 * Reads author profile data from a search-result button's data attributes,
 * saves the profile via AJAX, then kicks off the article-sync loop.
 */
function addAuthorFromSearch(btn) {
	var scholarId    = btn.getAttribute('data-id')             || '';
	var name         = btn.getAttribute('data-name')           || '';
	var affiliations = btn.getAttribute('data-affiliations')   || '';
	var hIndex       = btn.getAttribute('data-h-index')        || '0';
	var citations    = btn.getAttribute('data-citations')      || '0';
	var i10Index     = btn.getAttribute('data-i10-index')      || '0';
	var interests    = btn.getAttribute('data-interests')      || '';
	var countsByYear = btn.getAttribute('data-counts-by-year') || '[]';

	jQuery('#search-author-form').hide();
	jQuery('.wp-list-table').hide();
	jQuery('#search-author-loader').show();
	jQuery('#search-author-loader div').text('Saving author profile…');

	jQuery.post(
		scholar_sync_ajax_object.ajax_url,
		{
			action:         'scholar_sync_save_author_profile',
			nonce:          scholar_sync_ajax_object.add_author_nonce,
			scholar_id:     scholarId,
			name:           name,
			affiliations:   affiliations,
			h_index:        hIndex,
			citations:      citations,
			i10_index:      i10Index,
			interests:      interests,
			counts_by_year: countsByYear,
		}
	).done(function (response) {
		if (response && response.success) {
			jQuery('#search-author-loader div').text('Loading articles…');
			manageAuthor(scholarId, 'add', true);
		} else {
			var msg = (response && response.data && response.data.message)
				? response.data.message
				: 'Error saving author profile.';
			addAuthorShowError(msg, false);
		}
	}).fail(function (xhr) {
		addAuthorShowError('HTTP ' + xhr.status + ': ' + xhr.statusText, false);
	});
}

function addAuthorShowError(message, isUpgradeRequired) {
	jQuery('#search-author-loader').hide();
	jQuery('#search-author-form').show();
	jQuery('.wp-list-table').show();
	var $msg = jQuery('#message_display');
	$msg.html(message);
	$msg.toggleClass('scholar-sync-upgrade-notice', !! isUpgradeRequired);
	$msg.show();
}

function synAuthor(scholarId) {
	manageAuthor(scholarId, "sync");
}

/**
 * manageAuthor is used both for add and sync — initiates and drives the
 * paginated article-sync loop against the REST add-author endpoint.
 *
 * @param {string}  scholarId      OpenAlex short ID (e.g. "A5061143819").
 * @param {string}  actionType     "add" or "sync".
 * @param {boolean} profilePresaved  Pass true when the author row was already
 *                                  created by addAuthorFromSearch so the REST
 *                                  endpoint skips its "already exists" guard.
 */
function manageAuthor(scholarId, actionType, profilePresaved) {
	jQuery('#search-author-form').hide();
	jQuery(".wp-list-table").hide();
	jQuery('#search-author-loader').show();

	let formData = {
		author: scholarId,
		action: actionType,
	};
	if (profilePresaved) {
		formData.profile_presaved = 1;
	}

	let totalCreated = 0;
	let totalUpdated = 0;

	function fetchPage(formData) {
		jQuery.ajax({
			url: scholar_sync_ajax_object.rest + 'customer/sync',
			type: "POST",
			data: formData,
			cache: false,
			headers: { 'X-WP-Nonce': scholar_sync_ajax_object.rest_nonce },
			success: function (obj) {
				if (obj.has_error) {
					displayError(obj.message, obj.upgrade_required);
				} else {
					const authorId = obj.author_id;
					const nextTransactionId = obj.transaction_id;
					totalCreated += obj.articles_created || 0;
					totalUpdated += obj.articles_updated || 0;
					if ( ! nextTransactionId ) {
						// No transaction_id → sync is complete
						if (actionType === "add") {
							document.location.href = scholar_sync_ajax_object.url + '/wp-admin/admin.php?page=scholar-sync-preview-slug&author-id=' + authorId + '&is-new=1&_wpnonce=' + scholar_sync_ajax_object.preview_nonce;
						} else if (actionType === "sync") {
							displaySyncResults(totalCreated, totalUpdated);
						}
					} else {
						// More pages - continue with the server-provided transaction_id
						formData.transaction_id = nextTransactionId;
						formData.running_created = totalCreated;
						formData.running_updated = totalUpdated;
						const total = totalCreated + totalUpdated;
						const progressMsg = total > 0
							? total + ' articles synced so far...'
							: 'Loading articles...';
						jQuery('#search-author-loader div').text(progressMsg);
						fetchPage(formData);
					}
				}
			},
			error: function (exception) {
				displayError("HTTP " + exception.status + " " + exception.statusText + ": " + exception.responseText);
			}
		});
	}

	function displayError(message, isUpgradeRequired) {
		jQuery("#search-author-loader").hide();
		var $msg = jQuery("#message_display").length
			? jQuery("#message_display")
			: jQuery("#sync-results");
		$msg.html(message);
		scholarSyncLocalizeTimes($msg[0]);
		$msg.toggleClass('scholar-sync-upgrade-notice', !! isUpgradeRequired);
		$msg.show();
		jQuery("#search-author-form").show();
		jQuery(".wp-list-table").show();
	}

	// Initial call
	fetchPage(formData);
}

function syncAuthorForm(page, syncArticles, syncCitations, authorId) {
	if (document.getElementById("author-id").value == null) {
		syncArticles = document.getElementById("sync-articles").checked;
		syncCitations = document.getElementById("sync-citations").checked;
		authorId = document.getElementById("author-id").value;
	}
	let form_data = {
		id: authorId,
		articles: syncArticles,
		citations: syncCitations,
		page: page
	};
	jQuery.ajax({
		url: scholar_sync_ajax_object.rest + 'customer/sync-author',
		type: "POST",
		data: form_data,
		cache: false,
		success: function (obj) {
			if (obj.status != "success") {
				jQuery("#message_display").html(obj.message);
				jQuery("#message_display").show()
			} else {
				// jQuery("#message_display").hide();
				// jQuery("#add-author-value").val(obj.author_id);
				// jQuery("#add-author-form").submit();
			}
			// Template.clickInformationStep2(JSON.parse(data));
		},
		error: function (exception) {
			jQuery("#message_display").html("Internal error 6772");
			jQuery("#message_display").show()
		}
	});
}

function displaySyncResults(articlesCreated, articlesUpdated) {
	if (articlesCreated == null) articlesCreated = 0;
	if (articlesUpdated == null) articlesUpdated = 0;

	jQuery('#search-author-loader').hide();

	// Show success notice near the Sync button.
	var $results = jQuery('#sync-results');
	if ($results.length) {
		var msg;
		if (articlesCreated === 0 && articlesUpdated === 0) {
			msg = 'Sync completed. No changes detected - articles are already up to date.';
		} else {
			var parts = [];
			if (articlesCreated > 0) { parts.push(articlesCreated + ' article' + (articlesCreated !== 1 ? 's' : '') + ' added'); }
			if (articlesUpdated > 0) { parts.push(articlesUpdated + ' article' + (articlesUpdated !== 1 ? 's' : '') + ' updated'); }
			msg = 'Sync completed: ' + parts.join(', ') + '.';
		}
		$results.html('<div style="color:#00a32a;font-weight:600;padding:6px 0;">\u2713 ' + msg + '</div>');
		$results.show();
	}

	// Prepend a row to the sync history table.
	const newRow = `<tr>
		<td class="col-date">Just Now</td>
		<td class="col-type">Manual</td>
		<td class="col-outcome"><span style="color:#00a32a;font-weight:600;">Success</span></td>
		<td class="col-num">${articlesCreated}</td>
		<td class="col-num">${articlesUpdated}</td>
		<td class="col-msg">-</td>
	</tr>`;

	const $table = jQuery('#scholar-sync-sync-history-table');
	jQuery('#scholar-sync-no-sync-msg').hide();
	$table.show();
	$table.find('tbody').prepend(newRow);
}

function clickShortcodeSettings(obj) {
		const author_id = document.getElementById("author-id").value;
		const arr = ['header', 'search', 'index', 'cited-by'];
		let str = '[scholar-sync-scholar id="' + author_id + '"';

		arr.forEach(function (item) {
			let val = document.getElementById(item).checked?1:0;
			if (obj == null) {
				// first time
				// val = getOption(option_prefix + item);
				document.getElementById(item).checked = (val == 1);
			}
			if (val == 0) {
				str += ' ' + item + '="' + val + '"';
			}
		});
		str += ']';
		document.getElementById('scholar-sync-shortcode').value = str;
		if (obj != null) {
			const option_id = obj.attributes['prefix'].value + 'display-' + obj.id + '-' + author_id;
			addUserOption(option_id ,  obj.checked?1:0);
		}
}

function copyToClipboard(elementId) {
	const val = document.getElementById(elementId).value;
	navigator.clipboard.writeText(val);
	showToastMessage("Copied to clipboard");
}

function showToastMessage(message) {
	const toast = document.createElement('div');
	toast.classList.add('toast');
	toast.textContent = message;
	document.body.appendChild(toast);
	setTimeout(() => {
		toast.classList.add('toast--visible');
	}, 100);
	setTimeout(() => {
		toast.classList.remove('toast--visible');
		setTimeout(() => {
			document.body.removeChild(toast);
		}, 300);
	}, 3000);
}

function addUserOption(option_name, option_value) {
	const form_data = {
		option: option_name,
		value: option_value
	};
	jQuery.ajax({
		url: scholar_sync_ajax_object.rest + 'add-option',
		type: 'GET',
		data: form_data,
		cache: false,
		headers: { 'X-WP-Nonce': scholar_sync_ajax_object.rest_nonce },
		error: function () {}
	});
}

function clickMessageDismiss(obj) {
	jQuery(obj).parent().hide();
}

function openNav() {
	document.getElementById("mySidenav").style.width = "250px";
}

function closeNav() {
	document.getElementById("mySidenav").style.width = "0";
}

function clickSubmitSearchAuthor() {
	const scholarSyncAlert = document.getElementById("scholar-sync-alert");
	if (scholarSyncAlert) scholarSyncAlert.style.display = "none";
	const instructionWindow = document.getElementById("instruction-window");
	if (instructionWindow) instructionWindow.style.display = "none";
	const imageWait = document.getElementById("image-wait");
	if (imageWait) imageWait.style.display = "block";
}


function gotoPage(link) {
	document.location.href = link;
}

// Create the instruction window
function openInstructions(title, message, point, instruction_id) {
	if (!point) point = { x: '20%', y: '20%' };
	const isMobile = window.innerWidth < 782;

	// Build DOM safely with textContent - no innerHTML with variables
	const win = document.createElement('div');
	win.id = 'instruction-window';

	const hdr = document.createElement('div');
	hdr.id = 'instruction-header';
	hdr.style.cssText = 'padding:10px;font-size:16px;cursor:grab;';

	const titleSpan = document.createElement('span');
	titleSpan.id = 'instruction-title';
	titleSpan.textContent = title;

	const closeBtn = document.createElement('button');
	closeBtn.id = 'close-btn';
	closeBtn.textContent = '\u00d7';
	closeBtn.style.cssText = 'float:right;margin-left:auto;';

	hdr.appendChild(titleSpan);
	hdr.appendChild(closeBtn);

	const bdy = document.createElement('div');
	bdy.id = 'instruction-body';
	bdy.style.padding = '10px';
	bdy.textContent = message;

	const ftr = document.createElement('div');
	ftr.id = 'instruction-footer';
	ftr.style.cssText = 'padding:10px;display:flex;align-items:center;';

	const lbl = document.createElement('label');
	lbl.style.cssText = 'display:flex;align-items:center;color:gray;font-size:12px;';

	const chk = document.createElement('input');
	chk.type = 'checkbox';
	chk.id = 'do-not-show';
	chk.style.marginRight = '5px';

	lbl.appendChild(chk);
	lbl.appendChild(document.createTextNode("Don't show this message again"));
	ftr.appendChild(lbl);

	win.appendChild(hdr);
	win.appendChild(bdy);
	win.appendChild(ftr);

	if (isMobile) {
		win.style.cssText = 'position:relative;top:auto;left:auto;width:100%;box-sizing:border-box;margin-top:12px;';
		const form = document.getElementById('search-author-form');
		if (form && form.parentNode) {
			form.parentNode.insertBefore(win, form.nextSibling);
		} else {
			document.body.appendChild(win);
		}
	} else {
		win.style.position = 'absolute';
		document.body.appendChild(win);

		const calcPos = (value, maxSize, offset) => {
			if (typeof value === 'string' && value.endsWith('%')) {
				return Math.min((parseFloat(value) / 100) * maxSize, maxSize - offset);
			}
			return Math.min(parseInt(value, 10), maxSize - offset);
		};

		win.style.left = calcPos(point.x, window.innerWidth, win.offsetWidth) + 'px';
		win.style.top  = calcPos(point.y, window.innerHeight, win.offsetHeight) + 'px';

		// Drag functionality
		let isDragging = false, dragX, dragY;
		hdr.addEventListener('mousedown', (e) => {
			isDragging = true;
			dragX = e.clientX - win.offsetLeft;
			dragY = e.clientY - win.offsetTop;
			document.body.style.userSelect = 'none';
		});
		document.addEventListener('mousemove', (e) => {
			if (isDragging) {
				win.style.left = (e.clientX - dragX) + 'px';
				win.style.top  = (e.clientY - dragY) + 'px';
			}
		});
		document.addEventListener('mouseup', () => {
			isDragging = false;
			document.body.style.userSelect = '';
		});
	}

	closeBtn.addEventListener('click', () => {
		if (chk.checked) {
			addUserOption(instruction_id, 1);
		}
		win.style.display = 'none';
	});
}

jQuery(function ($) {
    var $btn = $('#scholar-sync-select-image');
    if ( ! $btn.length || typeof wp === 'undefined' || typeof wp.media === 'undefined' ) {
        return;
    }
    var mediaFrame;
    $btn.on('click', function () {
        if (mediaFrame) {
            mediaFrame.open();
            return;
        }
        mediaFrame = wp.media({
            title: 'Select Thumbnail Image',
            button: { text: 'Use this image' },
            multiple: false
        });
        mediaFrame.on('select', function () {
            var attachment = mediaFrame.state().get('selection').first().toJSON();
            $('#thumbnail').val(attachment.url);
            $('#scholar-sync-thumbnail-preview').attr('src', attachment.url);
        });
        mediaFrame.open();
    });

    var $preview = $('#scholar-sync-thumbnail-preview');
    $('#thumbnail').on('blur', function () {
        var url = $(this).val().trim();
        $preview.attr('src', url || $preview.data('default'));
    });
});

jQuery(function ($) {
    var $btn = $('#scholar-sync-select-article-image');
    if ( ! $btn.length || typeof wp === 'undefined' || typeof wp.media === 'undefined' ) {
        return;
    }
    var $input   = $('#article_image');
    var $preview = $('#scholar-sync-article-image-preview');
    var mediaFrame;
    $btn.on('click', function () {
        if (mediaFrame) {
            mediaFrame.open();
            return;
        }
        mediaFrame = wp.media({
            title: 'Select Article Image',
            button: { text: 'Use this image' },
            multiple: false
        });
        mediaFrame.on('select', function () {
            var attachment = mediaFrame.state().get('selection').first().toJSON();
            $input.val(attachment.url);
            $preview.attr('src', attachment.url).prop('hidden', false);
        });
        mediaFrame.open();
    });

    $input.on('blur', function () {
        var url = $(this).val().trim();
        $preview.attr('src', url).prop('hidden', url === '');
    });
});

function scholarSyncGenerateShortName(fullName) {
	var parts = fullName.trim().split(/\s+/);
	if (parts.length === 0 || parts[0] === '') { return ''; }

	// Strip honorific prefixes, case-insensitively, repeatedly, as long as a word remains.
	// Kept in sync by hand with admin/scholar_sync_functions.php and
	// public/js/scholar-sync-article-card.js.
	var PREFIXES = ['dr', 'prof', 'professor', 'mr', 'mrs', 'ms', 'mx', 'miss'];
	while (parts.length > 1) {
		var candidate = parts[0].replace(/\.$/, '').toLowerCase();
		if (PREFIXES.indexOf(candidate) === -1) { break; }
		parts.shift();
	}

	return parts[0].charAt(0).toUpperCase() + ' ' + parts[parts.length - 1];
}

(function () {
	if (window.location.search.indexOf('highlight=thumbnail') === -1) { return; }
	document.addEventListener('DOMContentLoaded', function () {
		var field = document.getElementById('thumbnail');
		if (!field) { return; }
		field.scrollIntoView({ behavior: 'smooth', block: 'center' });
		var style = document.createElement('style');
		style.textContent = '@keyframes scholar-sync-thumbnail-blink { 0%,100%{ outline: none; background: transparent; } 50%{ outline: 3px solid #2271b1; background: #e8f0fe; } }';
		document.head.appendChild(style);
		field.style.animation = 'scholar-sync-thumbnail-blink 0.7s ease-in-out 3';
	});
}());
