/**
 * Custom Fields - field group builder (repeater, location switching, validation helpers).
 */
(function ($) {
	'use strict';

	var data = window.wppsCf || {};
	var strings = data.strings || {};
	var choiceTypes = data.choiceTypes || ['select', 'radio', 'checkbox'];
	var mediaTypes = data.mediaTypes || ['image', 'file', 'gallery'];
	var multipleTypes = data.multipleTypes || ['select', 'post_object', 'term', 'user'];
	var displayOnlyTypes = data.displayOnlyTypes || ['message'];
	var nestedTypes = data.nestedTypes || ['repeater', 'flexible_content', 'clone'];
	var relationalTypes = data.relationalTypes || ['post_object', 'term', 'user'];
	var allowedSubTypes = data.allowedSubTypes || ['text', 'textarea', 'number', 'email', 'url'];
	var supports = data.supports || {};

	function typeSupports(type, setting) {
		return Array.isArray(supports[setting]) && supports[setting].indexOf(type) !== -1;
	}

	function initTooltips() {
		if (typeof window.wppsAccordionTooltipsInit === 'function') {
			window.wppsAccordionTooltipsInit();
		}
	}
	var nextIndex = 0;
	var nextLocRuleIndex = 0;

	function slugify(value) {
		return String(value)
			.toLowerCase()
			.replace(/[^a-z0-9_]+/g, '_')
			.replace(/^_+|_+$/g, '')
			.replace(/^([0-9])/, 'f_$1');
	}

	function randomSuffix(length) {
		var len = length || 13;
		var chars = 'abcdefghijklmnopqrstuvwxyz0123456789';
		var out = '';
		for (var i = 0; i < len; i++) {
			out += chars.charAt(Math.floor(Math.random() * chars.length));
		}
		return out;
	}

	function generateGroupKey() {
		return ('group_' + randomSuffix(13)).substring(0, 64);
	}

	function generateFieldKey(label, fallback) {
		var slug = slugify(label) || slugify(fallback) || 'field';
		return (slug + '_' + randomSuffix(5)).substring(0, 64);
	}

	function updateFieldKey($row) {
		var $key = $row.find('.cf-field-key-input');
		if (!$key.length || $key.data('manual') || $key.data('cfPersisted')) {
			return;
		}
		var label = ($row.find('.cf-field-label-input').val() || '').trim();
		$key.val(generateFieldKey(label, 'field'));
		updateFieldKeyPreview($row);
	}

	function updateFieldKeyPreview($row) {
		var key = ($row.find('.cf-field-key-input').val() || '').trim();
		$row.find('.cf-field-key-preview code').text(key || '—');
	}

	function computeNextIndex() {
		var max = -1;
		$('#cf-fields-list .cf-field-row').each(function () {
			var idx = parseInt($(this).attr('data-index'), 10);
			if (!isNaN(idx) && idx > max) {
				max = idx;
			}
		});
		nextIndex = max + 1;
	}

	function reindexFieldRow($row, index) {
		$row.attr('data-index', String(index));
		$row.find('[name]').each(function () {
			var name = $(this).attr('name');
			if (name) {
				$(this).attr('name', name.replace(/fields\[[^\]]+\]/, 'fields[' + index + ']'));
			}
		});
		$row.find('[data-cf-name]').each(function () {
			var dataName = $(this).attr('data-cf-name');
			if (dataName) {
				$(this).attr('data-cf-name', dataName.replace(/fields\[[^\]]+\]/, 'fields[' + index + ']'));
			}
		});
		$row.find('[id]').each(function () {
			var id = $(this).attr('id');
			if (id) {
				$(this).attr('id', id.replace(/^cf-field-[^-]+-/, 'cf-field-' + index + '-'));
			}
		});
		$row.find('label[for]').each(function () {
			var target = $(this).attr('for');
			if (target) {
				$(this).attr('for', target.replace(/^cf-field-[^-]+-/, 'cf-field-' + index + '-'));
			}
		});
	}

	function refreshFieldTypeUI($row) {
		var type = $row.find('.cf-field-type-input').val();
		var isDisplayOnly = displayOnlyTypes.indexOf(type) !== -1;
		var isNested = nestedTypes.indexOf(type) !== -1;

		$row.find('.cf-field-choices').prop('hidden', choiceTypes.indexOf(type) === -1);
		$row.find('.cf-field-multiple').prop('hidden', multipleTypes.indexOf(type) === -1);
		$row.find('.cf-field-return').prop('hidden', mediaTypes.indexOf(type) === -1 || type === 'gallery');
		$row.find('.cf-field-message').prop('hidden', type !== 'message');
		$row.find('.cf-field-bounds').prop('hidden', !typeSupports(type, 'bounds'));
		$row.find('.cf-field-rows').prop('hidden', !typeSupports(type, 'rows'));
		$row.find('.cf-field-placeholder').prop('hidden', !typeSupports(type, 'placeholder'));
		$row.find('.cf-field-default').prop('hidden', !typeSupports(type, 'default'));
		$row.find('.cf-field-pattern').prop('hidden', !typeSupports(type, 'pattern'));
		$row.find('.cf-field-post-types').prop('hidden', type !== 'post_object');
		$row.find('.cf-field-taxonomy').prop('hidden', type !== 'term');
		$row.find('.cf-field-repeater').prop('hidden', type !== 'repeater');
		$row.find('.cf-field-flexible').prop('hidden', type !== 'flexible_content');
		$row.find('.cf-field-clone').prop('hidden', type !== 'clone');
		$row.find('.cf-field-bidirectional').prop('hidden', relationalTypes.indexOf(type) === -1);
		$row.find('.cf-field-conditional').prop('hidden', isDisplayOnly);
		$row.find('.cf-field-before-after').prop('hidden', !typeSupports(type, 'before_after'));
		$row.find('.cf-field-storage, .cf-field-required, .cf-field-show-list').prop(
			'hidden',
			isDisplayOnly || isNested
		);

		updateFieldKeyPreview($row);

		var typeLabel = type;
		if (data.fieldTypes && data.fieldTypes[type]) {
			typeLabel = data.fieldTypes[type].label;
		}
		$row.find('.cf-field-row__type').text(typeLabel);
	}

	function updateRowTitle($row) {
		var label = $row.find('.cf-field-label-input').val();
		$row.find('.cf-field-row__title').text(label && label.length ? label : strings.untitledField || 'Untitled field');
	}

	function addField() {
		var template = $('#cf-field-row-template').html();
		if (!template) {
			return;
		}
		computeNextIndex();
		var html = template.replace(/__INDEX__/g, String(nextIndex));
		var $row = $(html);
		$('#cf-fields-list .cf-fields-empty').remove();
		$('#cf-fields-list').append($row);
		$row.removeClass('collapsed');
		$row.find('.cf-field-row__toggle').attr('aria-expanded', 'true');
		refreshFieldTypeUI($row);
		updateFieldKey($row);
		if (window.wppsCfInitColorPickers) {
			window.wppsCfInitColorPickers($row);
		}
		initTooltips();
		$row.find('.cf-field-label-input').trigger('focus');
	}

	function computeNextLocRuleIndex() {
		var max = -1;
		$('#cf-location-rules-list .cf-rule-row').each(function () {
			var idx = parseInt($(this).attr('data-index'), 10);
			if (!isNaN(idx) && idx > max) {
				max = idx;
			}
		});
		nextLocRuleIndex = max + 1;
	}

	function syncLocationState() {
		var screen = $('#cf-loc-screen').val() || 'post';
		$('.cf-position-row, .cf-priority-row, .cf-style-row').prop('hidden', screen !== 'post');
	}

	var ruleValueChoices = (function () {
		var el = document.getElementById('cf-rule-value-choices');
		if (!el) {
			return {};
		}
		try {
			return JSON.parse(el.textContent) || {};
		} catch (e) {
			return {};
		}
	})();

	/**
	 * Show a dropdown for parameters with known values (post type, taxonomy,
	 * template, status, role); a text input for ID-based parameters. The
	 * inactive control is disabled so only one submits.
	 */
	function syncRuleValueControl($row) {
		var param = $row.find('.cf-rule-param').val();
		var operator = $row.find('.cf-rule-operator').val();
		var noValue = operator === 'empty' || operator === 'not_empty';
		var choices = ruleValueChoices[param];
		var hasChoices = choices && Object.keys(choices).length > 0;
		var $select = $row.find('.cf-rule-value-select');
		var $input = $row.find('.cf-rule-value');

		if (hasChoices) {
			// Keep the selection only while the parameter is unchanged
			// (or on the very first sync of a server-rendered row).
			var builtFor = $select.data('cfParam');
			var current = '';
			if (builtFor === param || (builtFor === undefined && !$select.prop('disabled'))) {
				current = $select.val() || '';
			}
			$select.empty();
			Object.keys(choices).forEach(function (val) {
				$select.append($('<option>').val(val).text(choices[val]));
			});
			if (current && !Object.prototype.hasOwnProperty.call(choices, current)) {
				$select.prepend($('<option>').val(current).text(current));
			}
			if (current) {
				$select.val(current);
			}
			$select.data('cfParam', param);
			$select.prop('hidden', noValue).prop('disabled', noValue);
			$input.prop('hidden', true).prop('disabled', true);
		} else {
			$input.prop('hidden', noValue).prop('disabled', noValue);
			$select.prop('hidden', true).prop('disabled', true);
		}
	}

	/**
	 * Parse a choices textarea ("value|Label" per line) into an array of
	 * { value, label } objects, mirroring Validator::parseChoices().
	 */
	function parseChoiceLines(raw) {
		var out = [];
		String(raw || '').split(/\r\n|\r|\n/).forEach(function (line) {
			line = line.trim();
			if (!line) {
				return;
			}
			var value = line;
			var label = line;
			var pipe = line.indexOf('|');
			if (pipe !== -1) {
				value = line.slice(0, pipe).trim();
				label = line.slice(pipe + 1).trim() || value;
			}
			if (value !== '') {
				out.push({ value: value, label: label });
			}
		});
		return out;
	}

	/** Find a top-level field row by its assigned field key. */
	function fieldRowByKey(key) {
		if (!key) {
			return null;
		}
		var $match = null;
		$('#cf-fields-list .cf-field-row').each(function () {
			var rowKey = $(this).children('.cf-field-row__body').children('input[name$="[key]"]').val();
			if (rowKey === key) {
				$match = $(this);
				return false;
			}
		});
		return $match;
	}

	/** Available value choices for a trigger field (only choice-based types). */
	function conditionalValueChoices(depKey) {
		var $dep = fieldRowByKey(depKey);
		if (!$dep) {
			return [];
		}
		var type = String($dep.find('.cf-field-type-input').first().val() || '');
		if (choiceTypes.indexOf(type) === -1) {
			return [];
		}
		return parseChoiceLines($dep.find('textarea[name$="[choices]"]').first().val());
	}

	function conditionalOperatorNeedsValue(operator) {
		return operator !== 'empty' && operator !== 'not_empty';
	}

	/**
	 * Build the value control for a conditional rule: a dropdown of the trigger
	 * field's choices when available, a text input as a fallback, or a hidden
	 * input for value-less operators. Mirrors the Options Page Builder pattern.
	 */
	function buildConditionalValueControl(name, selected, depKey, operator) {
		selected = selected == null ? '' : String(selected);

		if (!conditionalOperatorNeedsValue(operator)) {
			return $('<input type="hidden" class="cf-conditional-value">').attr('name', name).val('');
		}

		if (!depKey) {
			return $('<select class="cf-conditional-value" disabled>').attr('name', name).append(
				$('<option>').val('').text(strings.condSelectField || 'Select a field first')
			);
		}

		var choices = conditionalValueChoices(depKey);
		if (!choices.length) {
			return $('<input type="text" class="regular-text cf-conditional-value">').attr('name', name).val(selected);
		}

		var $select = $('<select class="cf-conditional-value">').attr('name', name);
		$select.append($('<option>').val('').text(strings.condSelectValue || 'Select a value'));
		var matched = false;
		choices.forEach(function (choice) {
			var $opt = $('<option>').val(choice.value).text(choice.label);
			if (String(choice.value) === selected) {
				$opt.prop('selected', true);
				matched = true;
			}
			$select.append($opt);
		});
		if (selected && !matched) {
			$select.prepend($('<option>').val(selected).text(selected).prop('selected', true));
		}
		return $select;
	}

	/** Rebuild the value control inside a single conditional rule row. */
	function refreshConditionalValueControl($ruleRow) {
		var $wrap = $ruleRow.find('.cf-conditional-value-wrap');
		if (!$wrap.length) {
			return;
		}
		var name = $wrap.attr('data-cf-name') || '';
		var depKey = String($ruleRow.find('select[name$="[field]"]').first().val() || '');
		var operator = String($ruleRow.find('select[name$="[operator]"]').first().val() || '==');
		var current = $wrap.find('.cf-conditional-value').val();
		if (current == null || current === '') {
			current = $wrap.attr('data-cf-selected') || '';
		}
		$wrap.empty().append(buildConditionalValueControl(name, current, depKey, operator));
	}

	function refreshAllConditionalValueControls() {
		$('#cf-fields-list .cf-conditional-rule-row').each(function () {
			refreshConditionalValueControl($(this));
		});
	}

	function subFieldOptionsHtml() {
		return allowedSubTypes
			.map(function (t) {
				return '<option value="' + t + '">' + t + '</option>';
			})
			.join('');
	}

	$(function () {
		computeNextIndex();
		computeNextLocRuleIndex();

		$('#cf-fields-list .cf-field-row').each(function () {
			refreshFieldTypeUI($(this));
		});

		syncLocationState();

		$('#cf-add-field').on('click', function (e) {
			e.preventDefault();
			addField();
		});

		function toggleFieldRow($row) {
			$row.toggleClass('collapsed');
			var expanded = !$row.hasClass('collapsed');
			$row.find('.cf-field-row__toggle').attr('aria-expanded', expanded ? 'true' : 'false');
		}

		$(document).on('click', '.cf-field-row__toggle', function (e) {
			e.preventDefault();
			e.stopPropagation();
			toggleFieldRow($(this).closest('.cf-field-row'));
		});

		$(document).on('click', '.cf-field-row__head', function (e) {
			if (!$(e.target).closest('.cf-field-row__handle, .cf-field-row__actions, .cf-field-row__duplicate, .cf-field-row__remove').length) {
				toggleFieldRow($(this).closest('.cf-field-row'));
			}
		});

		$('#cf-import-toggle').on('click', function (e) {
			e.preventDefault();
			$('#cf-import-panel').prop('hidden', function (_i, hidden) {
				return !hidden;
			});
		});

		$(document).on('click', '.cf-field-row__duplicate', function (e) {
			e.preventDefault();
			e.stopPropagation();
			var $source = $(this).closest('.cf-field-row');
			computeNextIndex();
			var $clone = $source.clone();
			reindexFieldRow($clone, nextIndex);
			$clone.find('.cf-field-key-input').val('').removeData('manual').removeData('cfPersisted');
			$clone.find('.cf-field-key-readonly').remove();
			$clone.find('.cf-field-name-input').remove();
			if (!$clone.find('.cf-field-key-preview').length) {
				$clone.find('.cf-field-storage .cf-field-control__label').after(
					'<span class="description cf-field-key-preview">' +
						(strings.fieldKeyPreview || 'Field key:') +
						' <code>—</code></span>'
				);
			}
			var label = $clone.find('.cf-field-label-input').val();
			if (label) {
				$clone.find('.cf-field-label-input').val(label + ' (Copy)');
			}
			updateFieldKey($clone);
			// Cloned tooltip roots carry the init marker but not the listeners.
			$clone.find('[data-wpps-accordion-tooltip-init]').removeAttr('data-wpps-accordion-tooltip-init');
			$source.after($clone);
			refreshFieldTypeUI($clone);
			$clone.find('.cf-conditional-rule-row').each(function () {
				refreshConditionalValueControl($(this));
			});
			updateRowTitle($clone);
			initTooltips();
			if ($('#cf-fields-list').sortable('instance')) {
				$('#cf-fields-list').sortable('refresh');
			}
		});

		$(document).on('click', '.cf-field-row__remove', function (e) {
			e.preventDefault();
			e.stopPropagation();
			if (!window.confirm(strings.confirmRemove || 'Remove this field?')) {
				return;
			}
			$(this).closest('.cf-field-row').remove();
			if (!$('#cf-fields-list .cf-field-row').length) {
				$('#cf-fields-list').html(
					'<p class="cf-fields-empty">' +
						(strings.noFieldsYet || 'No fields yet. Add your first field below.') +
						'</p>'
				);
			}
		});

		$(document).on('change', '.cf-field-type-input', function () {
			refreshFieldTypeUI($(this).closest('.cf-field-row'));
		});

		$(document).on('input', '.cf-field-label-input', function () {
			var $row = $(this).closest('.cf-field-row');
			updateRowTitle($row);
			updateFieldKey($row);
		});

		$('#cf-loc-screen').on('change', syncLocationState);

		$('#cf-location-rules-list .cf-rule-row').each(function () {
			syncRuleValueControl($(this));
		});

		$(document).on('change', '.cf-rule-param, .cf-rule-operator', function () {
			var $row = $(this).closest('.cf-rule-row');
			if ($row.length) {
				syncRuleValueControl($row);
			}
		});

		$('#cf-add-location-rule').on('click', function (e) {
			e.preventDefault();
			var template = $('#cf-location-rule-template').html();
			if (!template) {
				return;
			}
			computeNextLocRuleIndex();
			var html = template.replace(/__INDEX__/g, String(nextLocRuleIndex));
			$('#cf-location-rules-list .cf-rules-empty').remove();
			var $row = $(html.trim());
			$('#cf-location-rules-list').append($row);
			syncRuleValueControl($row);
		});

		$(document).on('click', '.cf-rule-remove', function (e) {
			e.preventDefault();
			$(this).closest('.cf-rule-row').remove();
			if (!$('#cf-location-rules-list .cf-rule-row').length) {
				$('#cf-location-rules-list').append('<p class="cf-rules-empty"></p>');
			}
		});

		$(document).on('change', '.cf-conditional-enable', function () {
			$(this).closest('.cf-field-conditional').find('.cf-conditional-panel').prop('hidden', !$(this).is(':checked'));
		});

		function buildConditionalRuleRow(prefix, idx, $currentRow) {
			var $row = $('<div class="cf-conditional-rule-row"></div>');

			var $field = $('<select>').attr('name', prefix + '[conditional][rules][' + idx + '][field]');
			$field.append($('<option>').val('').text('\u2014'));
			$('#cf-fields-list .cf-field-row').each(function () {
				if ($currentRow && this === $currentRow[0]) {
					return;
				}
				var key = $(this).children('.cf-field-row__body').children('input[name$="[key]"]').val();
				if (!key) {
					return;
				}
				var label = $(this).find('.cf-field-label-input').first().val() || key;
				$field.append($('<option>').val(key).text(label + ' (' + key + ')'));
			});

			var $op = $('<select>').attr('name', prefix + '[conditional][rules][' + idx + '][operator]');
			var ops = data.ruleOperators || { '==': '==', '!=': '!=' };
			Object.keys(ops).forEach(function (op) {
				$op.append($('<option>').val(op).text(ops[op]));
			});

			var valueName = prefix + '[conditional][rules][' + idx + '][value]';
			var $valueWrap = $('<span class="cf-conditional-value-wrap"></span>')
				.attr('data-cf-name', valueName)
				.attr('data-cf-selected', '')
				.append($('<input type="text" class="regular-text cf-conditional-value">').attr('name', valueName));
			var $remove = $('<button type="button" class="button-link cf-conditional-rule-remove" aria-label="' + (strings.removeCondition || 'Remove condition') + '">&times;</button>');

			$row.append($field, $op, $valueWrap, $remove);
			return $row;
		}

		$(document).on('click', '.cf-add-conditional-rule', function (e) {
			e.preventDefault();
			var $fieldRow = $(this).closest('.cf-field-row');
			var $rules = $(this).closest('.cf-conditional-panel').find('.cf-conditional-rules');
			var prefix = $fieldRow.find('.cf-field-type-input').attr('name').replace('[type]', '');
			var idx = $rules.find('.cf-conditional-rule-row').length;
			var $newRow = buildConditionalRuleRow(prefix, idx, $fieldRow);
			$rules.append($newRow);
			refreshConditionalValueControl($newRow);
		});

		$(document).on('click', '.cf-conditional-rule-remove', function (e) {
			e.preventDefault();
			$(this).closest('.cf-conditional-rule-row').remove();
		});

		// Rebuild the value control when the trigger field or operator changes.
		$(document).on('change', '.cf-conditional-rule-row select[name$="[field]"], .cf-conditional-rule-row select[name$="[operator]"]', function () {
			refreshConditionalValueControl($(this).closest('.cf-conditional-rule-row'));
		});

		// When a field's type or choices change, refresh dependent value dropdowns.
		$(document).on('input change', '#cf-fields-list textarea[name$="[choices]"], #cf-fields-list .cf-field-type-input', function () {
			refreshAllConditionalValueControls();
		});

		refreshAllConditionalValueControls();

		$(document).on('click', '.cf-add-subfield', function (e) {
			e.preventDefault();
			var $list = $(this).closest('.cf-field-repeater').find('.cf-subfields-list');
			var prefix = $list.data('prefix');
			var idx = $list.find('.cf-subfield-row').length;
			$list.append(
				'<div class="cf-subfield-row" data-index="' +
					idx +
					'"><input type="text" name="' +
					prefix +
					'[sub_fields][' +
					idx +
					'][label]" placeholder="Label"><input type="text" name="' +
					prefix +
					'[sub_fields][' +
					idx +
					'][name]" placeholder="Name"><select name="' +
					prefix +
					'[sub_fields][' +
					idx +
					'][type]">' +
					subFieldOptionsHtml() +
					'</select><input type="hidden" name="' +
					prefix +
					'[sub_fields][' +
					idx +
					'][key]" value=""><button type="button" class="button-link cf-subfield-remove">&times;</button></div>'
			);
		});

		$(document).on('click', '.cf-subfield-remove', function (e) {
			e.preventDefault();
			$(this).closest('.cf-subfield-row').remove();
		});

		$(document).on('click', '.cf-add-layout', function (e) {
			e.preventDefault();
			var $list = $(this).closest('.cf-field-flexible').find('.cf-layouts-list');
			var prefix = $list.data('prefix');
			var idx = $list.find('.cf-layout-row').length;
			$list.append(
				'<div class="cf-layout-row" data-index="' +
					idx +
					'"><input type="text" name="' +
					prefix +
					'[layouts][' +
					idx +
					'][key]" placeholder="Layout key"><input type="text" name="' +
					prefix +
					'[layouts][' +
					idx +
					'][label]" placeholder="Layout label"><textarea name="' +
					prefix +
					'[layouts][' +
					idx +
					'][sub_fields_json]" class="code" rows="3"></textarea><button type="button" class="button-link cf-layout-remove">&times;</button></div>'
			);
		});

		$(document).on('click', '.cf-layout-remove', function (e) {
			e.preventDefault();
			$(this).closest('.cf-layout-row').remove();
		});

		// Auto-generate the group key on new groups.
		var $groupKey = $('#cf-key');
		if ($groupKey.length && $groupKey.is('input')) {
			if (!$groupKey.val()) {
				$groupKey.val(generateGroupKey());
			}
			$groupKey.on('input', function () {
				$groupKey.data('manual', true);
			});
		}

		// Sortable field rows (matches Options Page Builder drag handle pattern).
		if (typeof $.fn.sortable === 'function') {
			$('#cf-fields-list').sortable({
				handle: '.cf-field-row__handle',
				items: '> .cf-field-row',
				placeholder: 'cf-field-row-placeholder',
				axis: 'y',
				tolerance: 'pointer',
			});
		}

		$(document).on('click', '.cf-delete', function (e) {
			if (!window.confirm(strings.confirmDelete || 'Delete this field group?')) {
				e.preventDefault();
			}
		});

		// Settings accordion tabs (Location / Presentation / Usage).
		$('.cf-settings-tab').on('click', function () {
			var target = $(this).data('tab');

			$('.cf-settings-tab')
				.removeClass('is-active')
				.attr('aria-selected', 'false');
			$(this).addClass('is-active').attr('aria-selected', 'true');

			$('.cf-settings-panel').each(function () {
				var match = this.id === 'cf-settings-tab-' + target;
				$(this).toggleClass('is-active', match).prop('hidden', !match);
			});
		});

		$(document).on('click', '.cf-usage-copy', function (e) {
			e.preventDefault();
			var $btn = $(this);
			var text = String($btn.data('copy') || '').trim();
			if (!text) {
				return;
			}

			function markCopied() {
				var original = $btn.data('cfCopyLabel');
				if (original === undefined) {
					$btn.data('cfCopyLabel', $.trim($btn.text()));
				}
				$btn.addClass('is-copied');
				if ($btn.find('.dashicons').length) {
					$btn.contents().filter(function () {
						return this.nodeType === 3;
					}).remove();
					$btn.append(document.createTextNode(' ' + (strings.copied || 'Copied')));
				} else {
					$btn.text(strings.copied || 'Copied');
				}
				window.setTimeout(function () {
					$btn.removeClass('is-copied');
					if ($btn.find('.dashicons').length) {
						$btn.contents().filter(function () {
							return this.nodeType === 3;
						}).remove();
						$btn.append(document.createTextNode(' ' + (strings.copy || 'Copy')));
					} else {
						$btn.text(original || strings.copy || 'Copy');
					}
				}, 1600);
			}

			if (navigator.clipboard && navigator.clipboard.writeText) {
				navigator.clipboard.writeText(text).then(markCopied);
				return;
			}

			var $temp = $('<textarea>').val(text).css({ position: 'fixed', left: '-9999px' }).appendTo('body');
			$temp[0].select();
			try {
				document.execCommand('copy');
				markCopied();
			} catch (err) {
			}
			$temp.remove();
		});

	});
})(jQuery);
