/**
 * Currency Input Utility
 *
 * Enhances .ambh-currency-input elements:
 *  - Wraps with a currency symbol prefix
 *  - Enforces locale-specific decimal separator (EUR: comma, USD/GBP: period)
 *  - Normalises value to machine float before form submit
 *
 * Reads config from window.ambhCurrencyInput (set via wp_localize_script).
 * Exposes .parseAmount() and .formatDisplay() for use by other scripts.
 *
 * @package AmbassadorHub
 */
( function () {
	'use strict';

	var cfg = window.ambhCurrencyInput || { symbol: '€', decimal: ',', thousands: '.' };
	var isCommaDecimal = cfg.decimal === ',';

	/**
	 * Parse a user-entered display string to a machine float.
	 *
	 * EUR:     '1.234,56' → 1234.56   '1,50' → 1.5   '1,5' → 1.5
	 * USD/GBP: '1,234.56' → 1234.56   '1.50' → 1.5
	 */
	function parseAmount( value ) {
		if ( value === '' || value === null || value === undefined ) return NaN;
		value = String( value ).trim();
		if ( isCommaDecimal ) {
			value = value.replace( /\./g, '' ).replace( ',', '.' );
		} else {
			value = value.replace( /,/g, '' );
		}
		return parseFloat( value );
	}

	/**
	 * Format a machine float for display in an input field.
	 * Uses the configured decimal separator; no thousands separator.
	 *
	 * 1234.5 → '1234,50' (EUR) or '1234.50' (USD/GBP)
	 */
	function formatDisplay( value ) {
		var num = typeof value === 'number' ? value : parseAmount( String( value ) );
		if ( isNaN( num ) || num <= 0 ) return '';
		var fixed = num.toFixed( 2 );
		return isCommaDecimal ? fixed.replace( '.', ',' ) : fixed;
	}

	/**
	 * Wrap an input with a currency symbol prefix span.
	 */
	function wrapInput( input ) {
		var wrapper = document.createElement( 'span' );
		wrapper.className = 'ambh-currency-wrap';

		var symbol = document.createElement( 'span' );
		symbol.className = 'ambh-currency-symbol';
		symbol.textContent = cfg.symbol;
		symbol.setAttribute( 'aria-hidden', 'true' );

		input.parentNode.insertBefore( wrapper, input );
		wrapper.appendChild( symbol );
		wrapper.appendChild( input );
	}

	/**
	 * Insert a character at the current cursor position.
	 */
	function insertChar( input, char ) {
		var start = input.selectionStart;
		var end   = input.selectionEnd;
		input.value = input.value.substring( 0, start ) + char + input.value.substring( end );
		input.selectionStart = input.selectionEnd = start + 1;
		input.dispatchEvent( new Event( 'input', { bubbles: true } ) );
	}

	/**
	 * Enforce correct decimal format:
	 *  - Strip characters that are not digits or the decimal separator
	 *  - Allow at most one decimal separator
	 *  - Limit to two digits after the decimal separator
	 */
	function enforceFormat( input ) {
		var value    = input.value;
		var decimal  = cfg.decimal;
		var cursor   = input.selectionStart;
		var lenBefore = value.length;

		var escaped = isCommaDecimal ? ',' : '\\.';
		var cleaned = value.replace( new RegExp( '[^0-9' + escaped + ']', 'g' ), '' );

		var sepIdx = cleaned.indexOf( decimal );
		if ( sepIdx !== -1 ) {
			var intPart = cleaned.substring( 0, sepIdx + 1 );
			var decPart = cleaned.substring( sepIdx + 1 )
				.replace( /[^0-9]/g, '' )
				.substring( 0, 2 );
			cleaned = intPart + decPart;
		}

		if ( input.value !== cleaned ) {
			input.value = cleaned;
			var newCursor = Math.max( 0, cursor - ( lenBefore - cleaned.length ) );
			try { input.setSelectionRange( newCursor, newCursor ); } catch ( _ ) {}
		}
	}

	/**
	 * Normalise all .ambh-currency-input values in a form to machine floats
	 * before the form data is sent to the server.
	 */
	function bindFormNormalise( form ) {
		if ( form._ambhCurrencyBound ) return;
		form._ambhCurrencyBound = true;
		form.addEventListener( 'submit', function () {
			form.querySelectorAll( '.ambh-currency-input' ).forEach( function ( inp ) {
				var parsed = parseAmount( inp.value );
				inp.value = isNaN( parsed ) ? '' : String( parsed );
			} );
		}, true );
	}

	/**
	 * Initialise a single currency input element.
	 */
	function initInput( input ) {
		if ( input.dataset.ambhCurrencyInit ) return;
		input.dataset.ambhCurrencyInit = '1';

		wrapInput( input );
		input.setAttribute( 'inputmode', 'decimal' );
		input.setAttribute( 'autocomplete', 'off' );

		// Format stored machine float → display format on load.
		if ( input.value !== '' ) {
			var formatted = formatDisplay( input.value );
			if ( formatted !== '' ) {
				input.value = formatted;
			}
		}

		// EUR: convert a typed period into a comma.
		if ( isCommaDecimal ) {
			input.addEventListener( 'keydown', function ( e ) {
				if ( e.key === '.' || e.key === 'Decimal' ) {
					e.preventDefault();
					insertChar( this, ',' );
				}
			} );
		}

		input.addEventListener( 'input', function () {
			enforceFormat( this );
		} );

		var form = input.closest( 'form' );
		if ( form ) {
			bindFormNormalise( form );
		}
	}

	function init() {
		document.querySelectorAll( '.ambh-currency-input' ).forEach( initInput );
	}

	// Extend the config object with utility functions so other scripts can use them.
	cfg.parseAmount   = parseAmount;
	cfg.formatDisplay = formatDisplay;
	window.ambhCurrencyInput = cfg;

	if ( document.readyState === 'loading' ) {
		document.addEventListener( 'DOMContentLoaded', init );
	} else {
		init();
	}
} )();
