/** * Variant Creation Module * * Handles variant creation UI and API calls */ export class VariantCreation { constructor() { this.modal = null; this.assetId = null; this.init(); } init() { this.setupCreateButtons(); this.setupModal(); this.setupPresets(); this.setupSubmit(); } setupCreateButtons() { document.addEventListener('click', (e) => { const button = e.target.closest('[data-create-variant]'); if (!button) return; e.preventDefault(); this.assetId = button.closest('[data-asset-id]')?.dataset.assetId || window.location.pathname.split('/').pop(); this.showModal(); }); } setupModal() { // Create or get modal this.modal = document.getElementById('variant-create-modal'); if (!this.modal) { console.warn('Variant creation modal not found'); return; } // Setup close handlers this.modal.querySelectorAll('[data-close-variant-modal]').forEach(el => { el.addEventListener('click', () => this.closeModal()); }); // Setup quality slider const qualitySlider = this.modal.querySelector('#variant-quality'); const qualityValue = this.modal.querySelector('#quality-value'); if (qualitySlider && qualityValue) { qualitySlider.addEventListener('input', (e) => { qualityValue.textContent = e.target.value; }); } } setupPresets() { const presets = { '1200w': { variant: '1200w', width: 1200, quality: 85 }, '800w': { variant: '800w', width: 800, quality: 85 }, 'thumb@1x': { variant: 'thumb@1x', width: 200, quality: 80 }, 'thumb@2x': { variant: 'thumb@2x', width: 400, quality: 80 }, }; this.modal?.querySelectorAll('[data-preset]').forEach(button => { button.addEventListener('click', () => { const preset = presets[button.dataset.preset]; if (preset) { this.modal.querySelector('#variant-name').value = preset.variant; this.modal.querySelector('#variant-width').value = preset.width; this.modal.querySelector('#variant-quality').value = preset.quality; this.modal.querySelector('#quality-value').textContent = preset.quality; } }); }); } setupSubmit() { const submitButton = this.modal?.querySelector('#variant-create-submit'); if (!submitButton) return; submitButton.addEventListener('click', async () => { await this.createVariant(); }); } showModal() { if (!this.modal) return; // Reset form const form = this.modal.querySelector('#variant-create-form'); if (form) { form.reset(); this.modal.querySelector('#variant-quality').value = 85; this.modal.querySelector('#quality-value').textContent = '85'; } this.modal.style.display = 'block'; } closeModal() { if (this.modal) { this.modal.style.display = 'none'; } } async createVariant() { if (!this.assetId) { console.error('Asset ID not set'); return; } const form = this.modal.querySelector('#variant-create-form'); if (!form) return; const formData = new FormData(form); const data = { variant: formData.get('variant'), width: formData.get('width') ? parseInt(formData.get('width')) : null, height: formData.get('height') ? parseInt(formData.get('height')) : null, quality: formData.get('quality') ? parseInt(formData.get('quality')) : null, }; // Validate if (!data.variant) { if (window.Toast) { window.Toast.error('Variant name is required'); } else { alert('Variant name is required'); } return; } const submitButton = this.modal.querySelector('#variant-create-submit'); const originalText = submitButton.textContent; submitButton.disabled = true; submitButton.textContent = 'Creating...'; try { const response = await fetch(`/api/v1/assets/${this.assetId}/variants`, { method: 'POST', headers: { 'Content-Type': 'application/json', 'X-Requested-With': 'XMLHttpRequest', }, body: JSON.stringify(data), }); if (!response.ok) { const errorData = await response.json().catch(() => ({ error: 'Unknown error' })); throw new Error(errorData.error || `HTTP ${response.status}`); } const result = await response.json(); if (window.Toast) { window.Toast.success('Variant creation queued. It will be processed shortly.'); } else { alert('Variant creation queued successfully'); } this.closeModal(); // Reload page after a short delay to show new variant setTimeout(() => { window.location.reload(); }, 1500); } catch (error) { console.error('Failed to create variant:', error); if (window.Toast) { window.Toast.error(`Failed to create variant: ${error.message}`); } else { alert(`Failed to create variant: ${error.message}`); } } finally { submitButton.disabled = false; submitButton.textContent = originalText; } } } // Auto-initialize document.addEventListener('DOMContentLoaded', () => { new VariantCreation(); });