Linux heracles.o2switch.net 4.18.0-553.62.1.lve.el8.x86_64 #1 SMP Mon Jul 21 17:50:35 UTC 2025 x86_64
/
home
/
ophq1335
/
www
/
wp-content
/
plugins
/
wp-seopress
/
assets
/
js
/
/home/ophq1335/www/wp-content/plugins/wp-seopress/assets/js/seopress-promo-modal.js
/** * SEOPress Promotion Modal * * Standalone React component using wp-components Modal. * Loads on SEOPress admin pages to display promotional modals. * * @package SEOPress * @since 9.6.0 */ (function() { 'use strict'; const { createElement, render, useState, useEffect } = wp.element; // React 18+ uses createRoot, fallback to render for older versions const createRoot = wp.element.createRoot || null; const { Modal, Button } = wp.components; /** * Promotion Modal Component */ function PromoModal({ promotion, onDismiss }) { const [isOpen, setIsOpen] = useState(true); if (!isOpen || !promotion) { return null; } const handleDismiss = () => { setIsOpen(false); if (onDismiss) { onDismiss(promotion.id, promotion.dismiss_duration || 30); } }; const handleCtaClick = () => { // Track click if (window.seopressPromotions && window.seopressPromotions.stats_endpoint) { if (navigator.sendBeacon) { const data = new FormData(); data.append('ad_id', promotion.id); data.append('action', 'click'); navigator.sendBeacon(window.seopressPromotions.stats_endpoint, data); } } }; const bgColor = promotion.styling?.background_color || '#4E21E7'; const textColor = promotion.styling?.text_color || '#FFFFFF'; const buttonStyle = promotion.styling?.button_style || 'primary'; // Button styles based on API setting const getButtonStyles = () => { const baseStyles = { display: 'inline-block', padding: '14px 32px', borderRadius: '8px', textDecoration: 'none', fontSize: '15px', fontWeight: '600', textAlign: 'center', cursor: 'pointer' }; switch (buttonStyle) { case 'secondary': return { ...baseStyles, backgroundColor: 'transparent', color: textColor, border: `2px solid ${textColor}` }; case 'link': return { ...baseStyles, backgroundColor: 'transparent', color: textColor, border: 'none', textDecoration: 'underline', padding: '14px 0' }; case 'primary': default: return { ...baseStyles, backgroundColor: textColor, color: bgColor, border: 'none' }; } }; return createElement( Modal, { title: null, onRequestClose: handleDismiss, className: 'seopress-promo-modal', overlayClassName: 'seopress-promo-modal-overlay', isDismissible: promotion.dismissible !== false, }, createElement( 'div', { className: 'seopress-promo-modal-content', style: { backgroundColor: bgColor, color: textColor } }, // Icon promotion.icon && createElement( 'div', { className: 'seopress-promo-modal-icon' }, createElement('span', { className: `dashicons dashicons-${promotion.icon}`, style: { color: textColor } }) ), // Title promotion.title && createElement( 'h2', { className: 'seopress-promo-modal-title', style: { color: textColor } }, promotion.title ), // Body promotion.body && createElement( 'p', { className: 'seopress-promo-modal-body', style: { color: textColor, opacity: 0.9 } }, promotion.body ), // Actions createElement( 'div', { className: 'seopress-promo-modal-actions' }, // CTA Button promotion.cta_url && createElement( 'a', { href: promotion.cta_url, target: '_blank', rel: 'noopener noreferrer', className: 'seopress-promo-modal-cta', style: getButtonStyles(), onClick: handleCtaClick }, promotion.cta_text || 'Learn More' ), // Dismiss Button (if dismissible) promotion.dismissible !== false && createElement( Button, { variant: 'link', onClick: handleDismiss, className: 'seopress-promo-modal-dismiss', style: { color: textColor, opacity: 0.8 } }, 'Remind me later' ) ) ) ); } /** * Initialize the modal */ function init() { // Check if promotion data exists if (!window.seopressPromoModal || !window.seopressPromoModal.promotion) { return; } const promotion = window.seopressPromoModal.promotion; // Create mount point const mountPoint = document.createElement('div'); mountPoint.id = 'seopress-promo-modal-root'; document.body.appendChild(mountPoint); // Handle dismiss const handleDismiss = (promoId, duration) => { // Send AJAX to save dismissal if (window.seopressPromotions && window.seopressPromotions.dismiss_nonce) { const formData = new FormData(); formData.append('action', 'seopress_dismiss_promotion'); formData.append('promo_id', promoId); formData.append('duration', duration); formData.append('_ajax_nonce', window.seopressPromotions.dismiss_nonce); fetch(window.ajaxurl || '/wp-admin/admin-ajax.php', { method: 'POST', body: formData }); // Track dismiss if (window.seopressPromotions.stats_endpoint) { if (navigator.sendBeacon) { const data = new FormData(); data.append('ad_id', promoId); data.append('action', 'dismiss'); navigator.sendBeacon(window.seopressPromotions.stats_endpoint, data); } } } }; // Render (React 18+ uses createRoot, fallback to render for older versions) const modalElement = createElement(PromoModal, { promotion: promotion, onDismiss: handleDismiss }); if (createRoot) { const root = createRoot(mountPoint); root.render(modalElement); } else { render(modalElement, mountPoint); } } // Initialize when DOM is ready if (document.readyState === 'loading') { document.addEventListener('DOMContentLoaded', init); } else { init(); } })();