Please bookmark this page to avoid losing your image tool!

Photo Pencil Sketch Filter

(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, blurRadius = 3) {
    const width = originalImg.width;
    const height = originalImg.height;

    // 1. Create the main canvas that will be returned
    const canvas = document.createElement('canvas');
    canvas.width = width;
    canvas.height = height;
    const ctx = canvas.getContext('2d');

    // 2. Get original image pixel data and create a grayscale version
    // We use a temporary canvas to draw the original image and get its ImageData
    const tempCanvasOriginal = document.createElement('canvas');
    tempCanvasOriginal.width = width;
    tempCanvasOriginal.height = height;
    // Add { willReadFrequently: true } as a hint for potential performance optimization if supported
    const tempCtxOriginal = tempCanvasOriginal.getContext('2d', { willReadFrequently: true });
    tempCtxOriginal.drawImage(originalImg, 0, 0);
    const originalPixelData = tempCtxOriginal.getImageData(0, 0, width, height);
    
    // This ImageData will store the grayscale version of the original image
    // It will serve as the "base" layer for the Color Dodge blending
    const grayscaleImageData = tempCtxOriginal.createImageData(width, height);
    
    for (let i = 0; i < originalPixelData.data.length; i += 4) {
        const r = originalPixelData.data[i];
        const g = originalPixelData.data[i+1];
        const b = originalPixelData.data[i+2];
        // Standard luminance calculation, rounded to nearest integer
        const gray = Math.round(0.299 * r + 0.587 * g + 0.114 * b);
        
        grayscaleImageData.data[i] = gray;
        grayscaleImageData.data[i+1] = gray;
        grayscaleImageData.data[i+2] = gray;
        grayscaleImageData.data[i+3] = originalPixelData.data[i+3]; // Preserve original alpha
    }

    // 3. Create an inverted version of the grayscale image
    // This ImageData will be blurred and used as the "blend" layer in Color Dodge
    const invertedImageData = tempCtxOriginal.createImageData(width, height);
    for (let i = 0; i < grayscaleImageData.data.length; i += 4) {
        const gray = grayscaleImageData.data[i]; // R, G, B are the same (it's grayscale)
        const invertedGray = 255 - gray;
        
        invertedImageData.data[i] = invertedGray;
        invertedImageData.data[i+1] = invertedGray;
        invertedImageData.data[i+2] = invertedGray;
        invertedImageData.data[i+3] = 255; // Use solid alpha for the layer to be blurred
                                           // This ensures blur doesn't mix with transparent pixels
    }

    // 4. Blur the inverted grayscale image
    // First, put the inverted image data onto a temporary canvas
    const tempCanvasForInverted = document.createElement('canvas');
    tempCanvasForInverted.width = width;
    tempCanvasForInverted.height = height;
    const tempCtxForInverted = tempCanvasForInverted.getContext('2d', { willReadFrequently: true });
    tempCtxForInverted.putImageData(invertedImageData, 0, 0);

    // Create another canvas to draw the blurred version onto
    const blurredCanvas = document.createElement('canvas');
    blurredCanvas.width = width;
    blurredCanvas.height = height;
    const blurredCtx = blurredCanvas.getContext('2d', { willReadFrequently: true });
    
    // Apply the blur filter using CanvasRenderingContext2D.filter.
    // If blurRadius is 0 or less, no blur is effectively applied by the logic,
    // but CSS blur(0px) means no blur.
    if (blurRadius > 0) {
      blurredCtx.filter = `blur(${blurRadius}px)`;
    }
    
    // Draw the inverted image (from tempCanvasForInverted) onto blurredCanvas.
    // The filter on blurredCtx will cause the drawn image to be blurred.
    blurredCtx.drawImage(tempCanvasForInverted, 0, 0);
    
    // Reset the filter if it was applied, good practice for context reuse.
    if (blurRadius > 0) {
      blurredCtx.filter = 'none';
    }
    
    // Get the pixel data of the blurred inverted image
    const blurredInvertedPixelData = blurredCtx.getImageData(0, 0, width, height);

    // 5. Blend the original grayscale image with the blurred inverted image using Color Dodge
    // The result of this blend will be the pencil sketch effect.
    const finalImageData = ctx.createImageData(width, height);
    for (let i = 0; i < finalImageData.data.length; i += 4) {
        const baseGray = grayscaleImageData.data[i];      // Pixel from original grayscale image
        const blendGray = blurredInvertedPixelData.data[i]; // Pixel from blurred inverted image

        let dodgedValue;
        if (blendGray === 255) {
            // If the blend layer pixel is white, the Color Dodge result is white.
            // This happens when the original inverted pixel was white (original gray was black)
            // and remained white after blurring.
            dodgedValue = 255;
        } else {
            // Standard Color Dodge formula for 8-bit values: Result = (Base * 255) / (255 - Blend)
            // If Base is 0 (black), the result will be 0 (black).
            const denominator = 255 - blendGray;
            dodgedValue = (baseGray * 255) / denominator;
        }
        
        // Clamp the value to the 0-255 range, and round to the nearest integer.
        dodgedValue = Math.min(255, Math.max(0, Math.round(dodgedValue)));

        finalImageData.data[i] = dodgedValue;
        finalImageData.data[i+1] = dodgedValue;
        finalImageData.data[i+2] = dodgedValue;
        finalImageData.data[i+3] = originalPixelData.data[i+3]; // Preserve original alpha for the final image
    }

    // Put the final blended image data onto the main canvas
    ctx.putImageData(finalImageData, 0, 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

The Photo Pencil Sketch Filter transforms your images into a pencil sketch effect, providing a unique artistic rendition of your photos. This tool allows users to apply a grayscale filter, invert colors, and blend layers for an authentic sketch appearance. It is ideal for enhancing portraits, creating artistic illustrations, or generating custom artwork from your photos, making it a valuable resource for artists, designers, and anyone looking to add a creative touch to their images.

Leave a Reply

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