/**
* Igny8 Image Queue Processor
* Sequential image generation with individual progress tracking
*/
// Process AI Image Generation for Drafts (Sequential Image Processing with Queue Modal)
function processAIImageGenerationDrafts(postIds) {
console.log('Igny8: processAIImageGenerationDrafts called with postIds:', postIds);
// Event 1: Generate Images button clicked
if (window.addImageGenDebugLog) {
window.addImageGenDebugLog('INFO', 'Generate Images button clicked', {
postIds: postIds,
timestamp: new Date().toISOString()
});
}
// Get image generation settings from saved options (passed via wp_localize_script)
const desktopEnabled = window.IGNY8_PAGE?.imageSettings?.desktop_enabled || false;
const mobileEnabled = window.IGNY8_PAGE?.imageSettings?.mobile_enabled || false;
const maxInArticleImages = window.IGNY8_PAGE?.imageSettings?.max_in_article_images || 1;
// Event 2: Settings retrieved
if (window.addImageGenDebugLog) {
window.addImageGenDebugLog('SUCCESS', 'Settings retrieved', {
desktop: desktopEnabled,
mobile: mobileEnabled,
maxImages: maxInArticleImages
});
}
// Build image queue based on settings
const imageQueue = [];
postIds.forEach((postId, postIndex) => {
// Featured image (always)
imageQueue.push({
post_id: postId,
post_number: postIndex + 1,
type: 'featured',
device: '',
label: 'Featured Image',
post_title: `Post ${postIndex + 1}`
});
// Desktop in-article images
if (desktopEnabled) {
for (let i = 1; i <= maxInArticleImages; i++) {
imageQueue.push({
post_id: postId,
post_number: postIndex + 1,
type: 'article',
device: 'desktop',
index: i,
label: `desktop-${i}`,
section: i,
post_title: `Post ${postIndex + 1}`
});
}
}
// Mobile in-article images
if (mobileEnabled) {
for (let i = 1; i <= maxInArticleImages; i++) {
imageQueue.push({
post_id: postId,
post_number: postIndex + 1,
type: 'article',
device: 'mobile',
index: i,
label: `mobile-${i}`,
section: i,
post_title: `Post ${postIndex + 1}`
});
}
}
});
console.log('Igny8: Image queue built:', imageQueue);
// Show queue modal
showImageQueueModal(imageQueue, imageQueue.length);
// Start processing queue
processImageQueue(imageQueue, 0);
}
// Show modal with image queue and individual progress bars
function showImageQueueModal(queue, totalImages) {
if (window.currentProgressModal) {
window.currentProgressModal.remove();
}
const modal = document.createElement('div');
modal.id = 'igny8-image-queue-modal';
modal.className = 'igny8-modal';
let queueHTML = '';
queue.forEach((item, index) => {
const itemId = `queue-item-${index}`;
queueHTML += `
`;
});
modal.innerHTML = `
`;
document.body.appendChild(modal);
modal.classList.add('open');
window.currentProgressModal = modal;
}
// Process image queue sequentially with progressive loading
function processImageQueue(queue, currentIndex) {
if (currentIndex >= queue.length) {
// All done
console.log('Igny8: All images processed');
// Log to Image Generation Debug
if (window.addImageGenDebugLog) {
window.addImageGenDebugLog('SUCCESS', 'All images processed', {
total: queue.length,
timestamp: new Date().toISOString()
});
}
setTimeout(() => {
if (window.currentProgressModal) {
window.currentProgressModal.remove();
window.currentProgressModal = null;
}
showNotification('Image generation complete!', 'success');
// Reload table
if (window.loadTableData && window.IGNY8_PAGE?.tableId) {
window.loadTableData(window.IGNY8_PAGE.tableId);
}
}, 2000);
return;
}
const item = queue[currentIndex];
const itemElement = document.getElementById(`queue-item-${currentIndex}`);
if (!itemElement) {
console.error('Queue item element not found:', currentIndex);
// Log to Image Generation Debug
if (window.addImageGenDebugLog) {
window.addImageGenDebugLog('ERROR', 'Queue item element not found', {
index: currentIndex,
itemId: `queue-item-${currentIndex}`
});
}
setTimeout(() => processImageQueue(queue, currentIndex + 1), 100);
return;
}
// Update UI to processing
itemElement.setAttribute('data-status', 'processing');
itemElement.querySelector('.queue-status').textContent = '⏳ Generating...';
const progressFill = itemElement.querySelector('.queue-progress-fill');
const progressText = itemElement.querySelector('.queue-progress-text');
// Log to Image Generation Debug
if (window.addImageGenDebugLog) {
window.addImageGenDebugLog('INFO', `Processing ${item.label}`, {
postId: item.post_id,
type: item.type,
device: item.device || 'N/A',
index: item.index || 1,
queuePosition: `${currentIndex + 1}/${queue.length}`
});
}
// Progressive loading: 50% in 7s, 75% in next 5s, then 5% every second until 95%
let currentProgress = 0;
let phase = 1;
let phaseStartTime = Date.now();
const progressInterval = setInterval(() => {
const elapsed = Date.now() - phaseStartTime;
if (phase === 1 && currentProgress < 50) {
// Phase 1: 0% to 50% in 7 seconds (7.14% per second)
currentProgress += 0.714;
if (currentProgress >= 50 || elapsed >= 7000) {
currentProgress = 50;
phase = 2;
phaseStartTime = Date.now();
}
} else if (phase === 2 && currentProgress < 75) {
// Phase 2: 50% to 75% in 5 seconds (5% per second)
currentProgress += 0.5;
if (currentProgress >= 75 || elapsed >= 5000) {
currentProgress = 75;
phase = 3;
phaseStartTime = Date.now();
}
} else if (phase === 3 && currentProgress < 95) {
// Phase 3: 75% to 95% - 5% every second
if (elapsed >= 1000) {
currentProgress = Math.min(95, currentProgress + 5);
phaseStartTime = Date.now();
}
}
progressFill.style.width = currentProgress + '%';
progressText.textContent = Math.round(currentProgress) + '%';
}, 100);
// Generate single image
const formData = new FormData();
formData.append('action', 'igny8_ai_generate_single_image');
formData.append('nonce', window.IGNY8_PAGE.nonce);
formData.append('post_id', item.post_id);
formData.append('type', item.type);
formData.append('device', item.device || '');
formData.append('index', item.index || 1);
// Add meta box integration fields
formData.append('image_label', item.label || '');
formData.append('section', item.section || '');
fetch(window.IGNY8_PAGE.ajaxUrl, {
method: 'POST',
body: formData
})
.then(response => response.json())
.then(data => {
// Stop progressive loading
clearInterval(progressInterval);
if (data.success) {
// Success - complete to 100%
progressFill.style.width = '100%';
progressText.textContent = '100%';
itemElement.setAttribute('data-status', 'completed');
itemElement.querySelector('.queue-status').textContent = '✅ Complete';
// Display thumbnail if image URL is available
if (data.data?.image_url) {
const thumbnailDiv = itemElement.querySelector('.queue-thumbnail');
if (thumbnailDiv) {
thumbnailDiv.innerHTML = `
`;
}
}
console.log(`✓ Image ${currentIndex + 1} generated successfully`);
// Log to Image Generation Debug
if (window.addImageGenDebugLog) {
window.addImageGenDebugLog('SUCCESS', `${item.label} generated successfully`, {
postId: item.post_id,
attachmentId: data.data?.attachment_id,
provider: data.data?.provider,
queuePosition: `${currentIndex + 1}/${queue.length}`
});
}
// Process next image after short delay
setTimeout(() => processImageQueue(queue, currentIndex + 1), 500);
} else {
// Error - show at 90%
progressFill.style.width = '90%';
progressText.textContent = 'Failed';
itemElement.setAttribute('data-status', 'failed');
itemElement.querySelector('.queue-status').textContent = '❌ Failed';
const errorDiv = itemElement.querySelector('.queue-error');
errorDiv.textContent = data.data?.message || 'Unknown error';
errorDiv.style.display = 'block';
console.error(`✗ Image ${currentIndex + 1} failed:`, data.data?.message);
// Log to Image Generation Debug
if (window.addImageGenDebugLog) {
window.addImageGenDebugLog('ERROR', `${item.label} generation failed`, {
postId: item.post_id,
error: data.data?.message || 'Unknown error',
queuePosition: `${currentIndex + 1}/${queue.length}`
});
}
// Continue to next image despite error
setTimeout(() => processImageQueue(queue, currentIndex + 1), 1000);
}
})
.catch(error => {
// Exception - stop progressive loading
clearInterval(progressInterval);
progressFill.style.width = '90%';
progressText.textContent = 'Error';
itemElement.setAttribute('data-status', 'failed');
itemElement.querySelector('.queue-status').textContent = '❌ Error';
const errorDiv = itemElement.querySelector('.queue-error');
errorDiv.textContent = 'Exception: ' + error.message;
errorDiv.style.display = 'block';
console.error(`✗ Image ${currentIndex + 1} exception:`, error);
// Log to Image Generation Debug
if (window.addImageGenDebugLog) {
window.addImageGenDebugLog('ERROR', `${item.label} request exception`, {
postId: item.post_id,
error: error.message,
queuePosition: `${currentIndex + 1}/${queue.length}`
});
}
// Continue to next image despite error
setTimeout(() => processImageQueue(queue, currentIndex + 1), 1000);
});
}