Please bookmark this page to avoid losing your image tool!

Apply VHSRip Glitch Effect To Photo

(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.
function processImage(originalImg, intensity = 1.0, colorShift = 5, showVHSOverlay = 1) {
    // Ensure parameters are numbers
    intensity = parseFloat(intensity);
    colorShift = parseInt(colorShift, 10);
    showVHSOverlay = parseInt(showVHSOverlay, 10);

    const canvas = document.createElement('canvas');
    const w = originalImg.width;
    const h = originalImg.height;
    canvas.width = w;
    canvas.height = h;
    const ctx = canvas.getContext('2d');
    
    // Draw solid black background in case of transparent image
    ctx.fillStyle = '#000000';
    ctx.fillRect(0, 0, w, h);
    ctx.drawImage(originalImg, 0, 0);

    // 1. Apply Glitched Block Shifts (Tracking Distortion)
    const numShifts = Math.floor(20 * intensity);
    for (let i = 0; i < numShifts; i++) {
        const y = Math.random() * h;
        // Slice height varies between 2px and 5% of height
        const sliceHeight = Math.random() * (h * 0.05) + 2; 
        const shiftMax = w * 0.05 * intensity; 
        const shiftX = (Math.random() - 0.5) * shiftMax;
        
        ctx.drawImage(canvas, 0, y, w, sliceHeight, shiftX, y, w, sliceHeight);
        
        // Wrap around the shifted boundary to fill transparency gaps
        if (shiftX < 0) {
            ctx.drawImage(canvas, 0, y, w, sliceHeight, w + shiftX, y, w, sliceHeight);
        } else {
            ctx.drawImage(canvas, 0, y, w, sliceHeight, shiftX - w, y, w, sliceHeight);
        }
    }

    // 2. Pixel Manipulation (Chromatic Aberration, Noise, Scanlines)
    const imgData = ctx.getImageData(0, 0, w, h);
    const data = imgData.data;
    const outData = new Uint8ClampedArray(data);
    const shiftAmount = Math.floor(colorShift * intensity);

    for (let y = 0; y < h; y++) {
        const isScanline = (y % 3 === 0);
        
        // Create a horizontal wave tracking band near the bottom
        const wave = Math.sin(y * 0.05) * 15;
        const isTrackingBand = (y > h * 0.88 + wave && y < h * 0.95);
        
        for (let x = 0; x < w; x++) {
            const i = (y * w + x) * 4;
            
            // Chromatic Aberration: Shift Red left, Blue right
            const rx = Math.max(0, x - shiftAmount);
            const bx = Math.min(w - 1, x + shiftAmount);
            
            const ri = (y * w + rx) * 4;
            const bi = (y * w + bx) * 4;
            
            let r = data[ri];
            let g = data[i + 1];  // Green stays in place
            let b = data[bi + 2];
            
            // Color grading: boost greens, drop blues to look washed out/magnetic
            g = Math.min(255, g * 1.05);
            b = b * 0.95;
            
            // CRT Scanlines: Darken specific rows
            if (isScanline) {
                r *= 0.85;
                g *= 0.85;
                b *= 0.85;
            }
            
            // Add Static / Noise
            let noiseProb = 0.03 * intensity;
            if (isTrackingBand) noiseProb = 0.4 * intensity; // High noise in tracking band
            
            if (Math.random() < noiseProb) {
                const noise = (Math.random() - 0.5) * 120 * intensity;
                r = Math.min(255, Math.max(0, r + noise));
                g = Math.min(255, Math.max(0, g + noise));
                b = Math.min(255, Math.max(0, b + noise));
            }
            
            outData[i] = r;
            outData[i + 1] = g;
            outData[i + 2] = b;
            outData[i + 3] = 255; // Set solid alpha
        }
    }
    
    // Apply edited pixels back onto canvas
    imgData.data.set(outData);
    ctx.putImageData(imgData, 0, 0);

    // 3. Add CRT Vignette Darkening effect
    const gradient = ctx.createRadialGradient(
        w / 2, h / 2, Math.max(w, h) * 0.35, 
        w / 2, h / 2, Math.max(w, h) * 0.75
    );
    gradient.addColorStop(0, 'rgba(0, 0, 0, 0)');
    gradient.addColorStop(1, 'rgba(0, 0, 0, 0.6)');
    ctx.fillStyle = gradient;
    ctx.fillRect(0, 0, w, h);

    // 4. VHS "PLAY" and Timestamp Text Overlay
    if (showVHSOverlay === 1) {
        const fontSize = Math.max(16, Math.floor(h * 0.05));
        ctx.font = `bold ${fontSize}px "Courier New", Courier, monospace`;
        ctx.textBaseline = 'top';
        
        // Add fake CRT screen glow
        ctx.shadowColor = 'rgba(255, 255, 255, 0.8)';
        ctx.shadowBlur = Math.max(2, Math.floor(h * 0.01));
        ctx.fillStyle = '#ffffff';

        // Add some slight text jitter down or right for extra aesthetic effect
        const textJitterX = (Math.random() - 0.5) * 3 * intensity;
        const textJitterY = (Math.random() - 0.5) * 3 * intensity;
        
        ctx.fillText("PLAY ►", w * 0.05 + textJitterX, h * 0.05 + textJitterY);
        
        ctx.textBaseline = 'bottom';
        ctx.fillText("SP  0:00:00", w * 0.05 + textJitterX, h * 0.95 + textJitterY);
        
        // Reset Shadow
        ctx.shadowBlur = 0;
    }

    return canvas;
}

Free Image Tool Creator

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

Description

This tool applies a retro VHS glitch effect to your photos, simulating the nostalgic aesthetic of vintage analog video tapes. It uses several digital manipulation techniques, including tracking distortions (block shifts), chromatic aberration, scanlines, and static noise to create an authentic lo-fi look. Additionally, the tool can add a CRT vignette and classic on-screen overlays, such as ‘PLAY’ indicators and timestamps. This is ideal for digital artists, social media content creators looking for a retro vibe, or anyone wanting to give their modern photos a nostalgic, analog feel.

Leave a Reply

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