Please bookmark this page to avoid losing your image tool!

Studio Company Year Image Identifier

(Free & Supports Bulk Upload)

Drag & drop your images here or

The result will appear here...
You can edit the below JavaScript code to customize the image tool.
async function processImage(originalImg, language = 'eng') {
    // Create the main container
    const container = document.createElement('div');
    container.style.display = 'flex';
    container.style.flexDirection = 'column';
    container.style.alignItems = 'center';
    container.style.fontFamily = 'system-ui, -apple-system, "Segoe UI", Roboto, Helvetica, Arial, sans-serif';
    container.style.width = '100%';
    container.style.maxWidth = '800px';
    container.style.margin = '0 auto';
    container.style.gap = '20px';
    container.style.padding = '20px';
    container.style.boxSizing = 'border-box';
    container.style.backgroundColor = '#f4f4f5';
    container.style.borderRadius = '12px';
    container.style.border = '1px solid #e4e4e7';

    // Header section
    const header = document.createElement('h2');
    header.textContent = 'Studio, Company & Year Identifier';
    header.style.margin = '0';
    header.style.color = '#18181b';
    container.appendChild(header);

    // Canvas to display and process image
    const canvasContainer = document.createElement('div');
    canvasContainer.style.position = 'relative';
    canvasContainer.style.width = '100%';
    canvasContainer.style.display = 'flex';
    canvasContainer.style.justifyContent = 'center';
    
    const canvas = document.createElement('canvas');
    canvas.width = originalImg.width;
    canvas.height = originalImg.height;
    canvas.style.maxWidth = '100%';
    canvas.style.maxHeight = '500px';
    canvas.style.objectFit = 'contain';
    canvas.style.borderRadius = '8px';
    canvas.style.boxShadow = '0 4px 6px -1px rgba(0, 0, 0, 0.1), 0 2px 4px -1px rgba(0, 0, 0, 0.06)';
    
    const ctx = canvas.getContext('2d');
    ctx.drawImage(originalImg, 0, 0);
    canvasContainer.appendChild(canvas);
    container.appendChild(canvasContainer);

    // Results / Status Panel
    const panel = document.createElement('div');
    panel.style.width = '100%';
    panel.style.backgroundColor = '#ffffff';
    panel.style.padding = '20px';
    panel.style.borderRadius = '8px';
    panel.style.boxShadow = '0 1px 3px 0 rgba(0, 0, 0, 0.1)';
    panel.style.boxSizing = 'border-box';
    
    const statusText = document.createElement('div');
    statusText.style.color = '#3f3f46';
    statusText.style.fontWeight = '500';
    statusText.style.textAlign = 'center';
    statusText.textContent = 'Loading Optical Character Recognition (OCR) engine...';
    panel.appendChild(statusText);

    const progressBar = document.createElement('div');
    progressBar.style.width = '100%';
    progressBar.style.height = '8px';
    progressBar.style.backgroundColor = '#e4e4e7';
    progressBar.style.borderRadius = '4px';
    progressBar.style.marginTop = '10px';
    progressBar.style.overflow = 'hidden';
    
    const progressFill = document.createElement('div');
    progressFill.style.width = '0%';
    progressFill.style.height = '100%';
    progressFill.style.backgroundColor = '#3b82f6';
    progressFill.style.transition = 'width 0.2s ease';
    progressBar.appendChild(progressFill);
    panel.appendChild(progressBar);

    const resultsDiv = document.createElement('div');
    resultsDiv.style.display = 'none';
    resultsDiv.style.marginTop = '15px';
    panel.appendChild(resultsDiv);

    container.appendChild(panel);

    // Function to dynamically load Tesseract.js if not available
    const loadTesseract = async () => {
        if (window.Tesseract) return;
        return new Promise((resolve, reject) => {
            const script = document.createElement('script');
            script.src = 'https://unpkg.com/tesseract.js@v5.0.0/dist/tesseract.min.js';
            script.onload = resolve;
            script.onerror = () => reject(new Error('Failed to load Tesseract.js'));
            document.head.appendChild(script);
        });
    };

    // Helper functions for entity extraction
    const extractYear = (txt) => {
        // Matches common year formats between 1800-2099
        const match = txt.match(/\b(18|19|20)\d{2}\b/g);
        return match ? match[match.length - 1] : null;
    };

    const extractStudio = (txt) => {
        // Identifies 1-4 words followed by a common studio identifier
        const match = txt.match(/\b(?:[A-Za-z0-9&'-]+\s+){1,4}(?:Studio|Studios|Pictures|Entertainment|Films|Productions)\b/i);
        return match ? match[0].trim() : null;
    };

    const extractCompany = (txt) => {
        // Identifies 1-4 words followed by a common company suffix
        const match = txt.match(/\b(?:[A-Za-z0-9&'-]+\s+){1,4}(?:Company|Co\.?|Inc\.?|LLC|Corp\.?|Corporation)\b/i);
        return match ? match[0].trim() : null;
    };

    // Start processing as soon as container is returned
    (async () => {
        try {
            await loadTesseract();

            const worker = await window.Tesseract.recognize(
                canvas,
                language,
                {
                    logger: m => {
                        if (m.status === 'recognizing text') {
                            statusText.textContent = `Scanning image for text... ${Math.round(m.progress * 100)}%`;
                            progressFill.style.width = `${Math.round(m.progress * 100)}%`;
                        } else {
                            statusText.textContent = m.status.charAt(0).toUpperCase() + m.status.slice(1) + '...';
                        }
                    }
                }
            );

            const { data: { text, words } } = worker;
            
            // Draw visually appealing bounding boxes over identified text areas
            ctx.lineWidth = 2;
            ctx.strokeStyle = 'rgba(59, 130, 246, 0.4)'; // Light blue boxes for recognized words
            words.forEach(w => {
                ctx.strokeRect(w.bbox.x0, w.bbox.y0, w.bbox.x1 - w.bbox.x0, w.bbox.y1 - w.bbox.y0);
            });

            // Extract the target metadata
            const year = extractYear(text);
            const studio = extractStudio(text);
            const company = extractCompany(text);

            // Hide loading UI, show results
            statusText.style.display = 'none';
            progressBar.style.display = 'none';
            resultsDiv.style.display = 'block';

            // Clean up text snippet for preview
            const cleanSnippet = text.replace(/[\n\r]+/g, ' ').trim();
            const snippetText = cleanSnippet.length > 80 ? cleanSnippet.substring(0, 80) + '...' : (cleanSnippet || 'No text detected.');

            // Format results
            const listItemStyle = "padding: 10px; border-bottom: 1px solid #f4f4f5; display: flex; justify-content: space-between; align-items: center;";
            const labelStyle = "font-weight: 600; color: #52525b; width: 30%;";
            const valStyle = "color: #18181b; font-weight: 500; text-align: right;";
            
            const renderRow = (label, val) => `
                <li style="${listItemStyle}">
                    <span style="${labelStyle}">${label}</span>
                    <span style="${valStyle}">${val ? `<span style="color: #059669;">✔️ ${val}</span>` : '<span style="color: #ef4444; font-weight: 400;">Not Detected</span>'}</span>
                </li>
            `;

            resultsDiv.innerHTML = `
                <div style="margin-bottom: 15px; background: #f8fafc; padding: 12px; border-radius: 6px; border: 1px solid #e2e8f0;">
                    <span style="font-weight:600; color:#475569; font-size: 14px;">Extracted Text Preview:</span><br/>
                    <em style="color:#64748b; font-size: 14px;">"${snippetText}"</em>
                </div>
                <h3 style="margin-top: 0; margin-bottom: 10px; color: #18181b; font-size: 18px;">Identification Results</h3>
                <ul style="list-style: none; padding: 0; margin: 0; border-top: 1px solid #f4f4f5;">
                    ${renderRow('🎬 Studio', studio)}
                    ${renderRow('🏢 Company', company)}
                    ${renderRow('📅 Year', year)}
                </ul>
            `;

        } catch (error) {
            statusText.textContent = 'Engine encountered an error. The image might be tainted by CORS rules or unreadable.';
            statusText.style.color = '#ef4444';
            progressFill.style.backgroundColor = '#ef4444';
            console.error(error);
        }
    })();

    return container;
}

Free Image Tool Creator

Can't find the image tool you're looking for?
Create one based on your own needs now!

Description

The Studio Company Year Image Identifier is an OCR-powered tool designed to scan images and automatically extract specific metadata related to production entities. By analyzing text within an image, the tool can identify and isolate studio names, company information, and production years. This tool is particularly useful for archivists, film historians, or media researchers looking to quickly catalog film credits, production logos, or vintage media assets without manual data entry.

Leave a Reply

Your email address will not be published. Required fields are marked *