`n

Image Optimization Tools - Complete Guide

Published: September 25, 2024 | Reading time: 19 minutes

Image Optimization Overview

Image optimization reduces file sizes while maintaining visual quality:

Image Optimization Benefits
# Image Optimization Benefits
- Faster page load times
- Reduced bandwidth usage
- Better user experience
- Improved SEO rankings
- Lower hosting costs
- Mobile performance
- Core Web Vitals improvement

Image Compression Tools

Command Line Tools

Image Compression Tools
# Image Compression Tools

# 1. ImageMagick Installation
# Ubuntu/Debian
sudo apt update
sudo apt install imagemagick

# macOS
brew install imagemagick

# Windows
# Download from https://imagemagick.org/script/download.php

# 2. JPEG Optimization
# Basic JPEG compression
convert input.jpg -quality 85 -strip -interlace Plane output.jpg

# Advanced JPEG optimization
convert input.jpg \
    -resize "1920x>" \
    -quality 85 \
    -strip \
    -interlace Plane \
    -sampling-factor 4:2:0 \
    -colorspace sRGB \
    output.jpg

# Batch JPEG optimization
find ./images -name "*.jpg" -o -name "*.jpeg" | while read file; do
    echo "Optimizing $file..."
    convert "$file" \
        -resize "1920x>" \
        -quality 85 \
        -strip \
        -interlace Plane \
        "${file%.*}_optimized.jpg"
done

# 3. PNG Optimization
# Install pngquant
sudo apt install pngquant

# PNG compression
pngquant --quality=65-80 --ext .png --force input.png

# PNG optimization with ImageMagick
convert input.png \
    -resize "1920x>" \
    -strip \
    -define png:compression-level=9 \
    -define png:compression-strategy=1 \
    output.png

# Batch PNG optimization
find ./images -name "*.png" | while read file; do
    echo "Optimizing $file..."
    pngquant --quality=65-80 --ext .png --force "$file"
done

# 4. WebP Conversion
# Install WebP tools
sudo apt install webp

# Convert to WebP
cwebp -q 85 -m 6 -af input.jpg -o output.webp

# Batch WebP conversion
find ./images -name "*.jpg" -o -name "*.jpeg" -o -name "*.png" | while read file; do
    filename=$(basename "$file" | sed 's/\.[^.]*$//')
    echo "Converting $file to WebP..."
    cwebp -q 85 -m 6 -af "$file" -o "./webp/${filename}.webp"
done

# 5. AVIF Conversion
# Install AVIF tools
npm install -g avif-cli

# Convert to AVIF
avif --input input.jpg --output output.avif --quality 50

# Batch AVIF conversion
find ./images -name "*.jpg" -o -name "*.jpeg" -o -name "*.png" | while read file; do
    filename=$(basename "$file" | sed 's/\.[^.]*$//')
    echo "Converting $file to AVIF..."
    avif --input "$file" --output "./avif/${filename}.avif" --quality 50
done

# 6. Comprehensive Image Optimization Script
#!/bin/bash
# optimize-images.sh

INPUT_DIR="./src/images"
OUTPUT_DIR="./dist/images"
QUALITY=85
MAX_WIDTH=1920

# Create output directories
mkdir -p $OUTPUT_DIR/{jpg,png,webp,avif}

echo "Starting image optimization..."

# Process JPEG images
find $INPUT_DIR -name "*.jpg" -o -name "*.jpeg" | while read file; do
    filename=$(basename "$file")
    echo "Processing JPEG: $filename"
    
    # Optimize JPEG
    convert "$file" \
        -resize "${MAX_WIDTH}x>" \
        -quality $QUALITY \
        -strip \
        -interlace Plane \
        "$OUTPUT_DIR/jpg/$filename"
    
    # Convert to WebP
    cwebp -q $QUALITY -m 6 -af "$file" -o "$OUTPUT_DIR/webp/${filename%.*}.webp"
    
    # Convert to AVIF
    avif --input "$file" --output "$OUTPUT_DIR/avif/${filename%.*}.avif" --quality 50
done

# Process PNG images
find $INPUT_DIR -name "*.png" | while read file; do
    filename=$(basename "$file")
    echo "Processing PNG: $filename"
    
    # Optimize PNG
    pngquant --quality=65-80 --ext .png --force "$file"
    mv "${file%.*}-fs8.png" "$OUTPUT_DIR/png/$filename"
    
    # Convert to WebP
    cwebp -q $QUALITY -m 6 -af "$file" -o "$OUTPUT_DIR/webp/${filename%.*}.webp"
    
    # Convert to AVIF
    avif --input "$file" --output "$OUTPUT_DIR/avif/${filename%.*}.avif" --quality 50
done

echo "Image optimization completed!"

Node.js Image Optimization

Programmatic Image Processing

Node.js Image Optimization
# Node.js Image Optimization

# 1. Sharp Library Setup
npm install sharp
npm install --save-dev @types/sharp

# Basic Sharp usage
const sharp = require('sharp');

async function optimizeImage(inputPath, outputPath) {
    try {
        await sharp(inputPath)
            .resize(1920, null, { withoutEnlargement: true })
            .jpeg({ quality: 85, progressive: true })
            .png({ compressionLevel: 9 })
            .webp({ quality: 85 })
            .toFile(outputPath);
        
        console.log('Image optimized successfully');
    } catch (error) {
        console.error('Error optimizing image:', error);
    }
}

# 2. Advanced Image Processing
class ImageOptimizer {
    constructor() {
        this.supportedFormats = ['jpg', 'jpeg', 'png', 'webp', 'avif'];
        this.defaultOptions = {
            jpeg: { quality: 85, progressive: true },
            png: { compressionLevel: 9 },
            webp: { quality: 85 },
            avif: { quality: 50 }
        };
    }
    
    async optimizeImage(inputPath, outputDir, options = {}) {
        const sharp = require('sharp');
        const path = require('path');
        const fs = require('fs').promises;
        
        try {
            const image = sharp(inputPath);
            const metadata = await image.metadata();
            const filename = path.basename(inputPath, path.extname(inputPath));
            
            // Create output directory if it doesn't exist
            await fs.mkdir(outputDir, { recursive: true });
            
            const results = {};
            
            // Generate optimized versions
            for (const format of this.supportedFormats) {
                const outputPath = path.join(outputDir, `${filename}.${format}`);
                const formatOptions = { ...this.defaultOptions[format], ...options[format] };
                
                await image
                    .resize(options.width || 1920, null, { withoutEnlargement: true })
                    .toFormat(format, formatOptions)
                    .toFile(outputPath);
                
                const stats = await fs.stat(outputPath);
                results[format] = {
                    path: outputPath,
                    size: stats.size,
                    compression: ((metadata.size - stats.size) / metadata.size) * 100
                };
            }
            
            return results;
        } catch (error) {
            console.error('Error optimizing image:', error);
            throw error;
        }
    }
    
    async batchOptimize(inputDir, outputDir, options = {}) {
        const fs = require('fs').promises;
        const path = require('path');
        
        try {
            const files = await fs.readdir(inputDir);
            const imageFiles = files.filter(file => 
                this.supportedFormats.some(format => 
                    file.toLowerCase().endsWith(`.${format}`)
                )
            );
            
            const results = [];
            
            for (const file of imageFiles) {
                const inputPath = path.join(inputDir, file);
                console.log(`Processing: ${file}`);
                
                const result = await this.optimizeImage(inputPath, outputDir, options);
                results.push({ file, result });
            }
            
            return results;
        } catch (error) {
            console.error('Error in batch optimization:', error);
            throw error;
        }
    }
}

# 3. Responsive Image Generation
class ResponsiveImageGenerator {
    constructor() {
        this.breakpoints = [
            { width: 320, suffix: 'sm' },
            { width: 640, suffix: 'md' },
            { width: 1024, suffix: 'lg' },
            { width: 1920, suffix: 'xl' }
        ];
    }
    
    async generateResponsiveImages(inputPath, outputDir) {
        const sharp = require('sharp');
        const path = require('path');
        const fs = require('fs').promises;
        
        try {
            const filename = path.basename(inputPath, path.extname(inputPath));
            const results = {};
            
            for (const breakpoint of this.breakpoints) {
                const outputPath = path.join(outputDir, `${filename}-${breakpoint.suffix}.webp`);
                
                await sharp(inputPath)
                    .resize(breakpoint.width, null, { withoutEnlargement: true })
                    .webp({ quality: 85 })
                    .toFile(outputPath);
                
                const stats = await fs.stat(outputPath);
                results[breakpoint.suffix] = {
                    width: breakpoint.width,
                    path: outputPath,
                    size: stats.size
                };
            }
            
            return results;
        } catch (error) {
            console.error('Error generating responsive images:', error);
            throw error;
        }
    }
    
    generateHTML(srcSet) {
        const sources = Object.entries(srcSet)
            .map(([suffix, data]) => 
                `  `
            )
            .join('\n');
        
        return `
${sources}
  Responsive image
`;
    }
}

# 4. Image Optimization Middleware
const express = require('express');
const multer = require('multer');
const sharp = require('sharp');
const path = require('path');

const upload = multer({ dest: 'uploads/' });
const app = express();

app.post('/upload', upload.single('image'), async (req, res) => {
    try {
        const inputPath = req.file.path;
        const outputDir = 'optimized';
        
        const optimizer = new ImageOptimizer();
        const results = await optimizer.optimizeImage(inputPath, outputDir);
        
        res.json({
            success: true,
            originalSize: req.file.size,
            optimized: results
        });
    } catch (error) {
        res.status(500).json({
            success: false,
            error: error.message
        });
    }
});

# 5. Image Optimization API
class ImageOptimizationAPI {
    constructor() {
        this.optimizer = new ImageOptimizer();
        this.responsiveGenerator = new ResponsiveImageGenerator();
    }
    
    async optimizeImage(inputPath, options = {}) {
        const outputDir = path.join('output', Date.now().toString());
        return await this.optimizer.optimizeImage(inputPath, outputDir, options);
    }
    
    async generateResponsive(inputPath) {
        const outputDir = path.join('responsive', Date.now().toString());
        return await this.responsiveGenerator.generateResponsiveImages(inputPath, outputDir);
    }
    
    async getOptimizationStats(inputPath, outputPath) {
        const fs = require('fs').promises;
        
        const inputStats = await fs.stat(inputPath);
        const outputStats = await fs.stat(outputPath);
        
        return {
            originalSize: inputStats.size,
            optimizedSize: outputStats.size,
            compressionRatio: ((inputStats.size - outputStats.size) / inputStats.size) * 100,
            spaceSaved: inputStats.size - outputStats.size
        };
    }
}

Webpack Image Optimization

Build-Time Image Optimization

Webpack Image Optimization
# Webpack Image Optimization

# 1. Webpack Configuration
const path = require('path');
const ImageMinimizerPlugin = require('image-minimizer-webpack-plugin');

module.exports = {
    module: {
        rules: [
            {
                test: /\.(png|jpe?g|gif|svg)$/i,
                type: 'asset/resource',
                generator: {
                    filename: 'images/[name].[contenthash][ext]'
                }
            }
        ]
    },
    optimization: {
        minimizer: [
            new ImageMinimizerPlugin({
                minimizer: {
                    implementation: ImageMinimizerPlugin.imageminMinify,
                    options: {
                        plugins: [
                            ['gifsicle', { interlaced: true }],
                            ['jpegtran', { progressive: true }],
                            ['optipng', { optimizationLevel: 5 }],
                            ['svgo', {
                                plugins: [
                                    {
                                        name: 'preset-default',
                                        params: {
                                            overrides: {
                                                removeViewBox: false
                                            }
                                        }
                                    }
                                ]
                            }]
                        ]
                    }
                }
            })
        ]
    }
};

# 2. Advanced Webpack Image Optimization
const ImageMinimizerPlugin = require('image-minimizer-webpack-plugin');
const { extendDefaultPlugins } = require('svgo');

module.exports = {
    optimization: {
        minimizer: [
            new ImageMinimizerPlugin({
                minimizer: {
                    implementation: ImageMinimizerPlugin.sharpMinify,
                    options: {
                        encodeOptions: {
                            jpeg: {
                                quality: 85,
                                progressive: true
                            },
                            png: {
                                compressionLevel: 9
                            },
                            webp: {
                                quality: 85
                            },
                            avif: {
                                quality: 50
                            }
                        }
                    }
                },
                generator: [
                    {
                        type: 'asset',
                        preset: 'webp-custom-name',
                        implementation: ImageMinimizerPlugin.sharpGenerate,
                        options: {
                            encodeOptions: {
                                webp: {
                                    quality: 85
                                }
                            }
                        }
                    },
                    {
                        type: 'asset',
                        preset: 'avif-custom-name',
                        implementation: ImageMinimizerPlugin.sharpGenerate,
                        options: {
                            encodeOptions: {
                                avif: {
                                    quality: 50
                                }
                            }
                        }
                    }
                ]
            })
        ]
    }
};

# 3. Responsive Images with Webpack
const ResponsiveLoader = require('responsive-loader');
const Sharp = require('responsive-loader/sharp');

module.exports = {
    module: {
        rules: [
            {
                test: /\.(png|jpe?g)$/i,
                use: [
                    {
                        loader: ResponsiveLoader,
                        options: {
                            adapter: Sharp,
                            sizes: [320, 640, 1024, 1920],
                            placeholder: true,
                            placeholderSize: 50,
                            name: 'images/[name]-[width].[contenthash].[ext]'
                        }
                    }
                ]
            }
        ]
    }
};

# 4. Image Optimization Plugin
class ImageOptimizationPlugin {
    constructor(options = {}) {
        this.options = {
            quality: 85,
            formats: ['webp', 'avif'],
            sizes: [320, 640, 1024, 1920],
            ...options
        };
    }
    
    apply(compiler) {
        compiler.hooks.emit.tapAsync('ImageOptimizationPlugin', (compilation, callback) => {
            const sharp = require('sharp');
            const path = require('path');
            
            const processImage = async (asset) => {
                if (!this.isImage(asset.name)) return;
                
                const source = compilation.assets[asset.name].source();
                const image = sharp(source);
                const metadata = await image.metadata();
                
                // Generate optimized versions
                for (const format of this.options.formats) {
                    const optimizedName = this.getOptimizedName(asset.name, format);
                    const optimizedBuffer = await image
                        .toFormat(format, { quality: this.options.quality })
                        .toBuffer();
                    
                    compilation.assets[optimizedName] = {
                        source: () => optimizedBuffer,
                        size: () => optimizedBuffer.length
                    };
                }
                
                // Generate responsive sizes
                for (const size of this.options.sizes) {
                    for (const format of this.options.formats) {
                        const responsiveName = this.getResponsiveName(asset.name, size, format);
                        const responsiveBuffer = await image
                            .resize(size, null, { withoutEnlargement: true })
                            .toFormat(format, { quality: this.options.quality })
                            .toBuffer();
                        
                        compilation.assets[responsiveName] = {
                            source: () => responsiveBuffer,
                            size: () => responsiveBuffer.length
                        };
                    }
                }
            };
            
            Promise.all(Object.keys(compilation.assets).map(processImage))
                .then(() => callback())
                .catch(callback);
        });
    }
    
    isImage(filename) {
        return /\.(png|jpe?g|gif|svg)$/i.test(filename);
    }
    
    getOptimizedName(filename, format) {
        const ext = path.extname(filename);
        return filename.replace(ext, `.${format}`);
    }
    
    getResponsiveName(filename, size, format) {
        const ext = path.extname(filename);
        const base = filename.replace(ext, '');
        return `${base}-${size}.${format}`;
    }
}

# 5. Image Optimization Loader
const loaderUtils = require('loader-utils');
const sharp = require('sharp');

module.exports = function(content) {
    const callback = this.async();
    const options = loaderUtils.getOptions(this) || {};
    
    const {
        quality = 85,
        format = 'webp',
        width = null,
        height = null
    } = options;
    
    sharp(content)
        .resize(width, height, { withoutEnlargement: true })
        .toFormat(format, { quality })
        .toBuffer()
        .then(buffer => {
            callback(null, buffer);
        })
        .catch(error => {
            callback(error);
        });
};

module.exports.raw = true;

Automated Image Optimization

CI/CD Image Optimization

Automated Image Optimization
# Automated Image Optimization

# 1. GitHub Actions Workflow
name: Optimize Images

on:
  push:
    paths:
      - 'images/**'
  pull_request:
    paths:
      - 'images/**'

jobs:
  optimize-images:
    runs-on: ubuntu-latest
    
    steps:
    - uses: actions/checkout@v3
    
    - name: Setup Node.js
      uses: actions/setup-node@v3
      with:
        node-version: '18'
        cache: 'npm'
    
    - name: Install dependencies
      run: npm install
    
    - name: Optimize images
      run: |
        npm run optimize-images
    
    - name: Commit optimized images
      run: |
        git config --local user.email "action@github.com"
        git config --local user.name "GitHub Action"
        git add images/
        git diff --staged --quiet || git commit -m "Optimize images [skip ci]"
        git push

# 2. Image Optimization Script
#!/bin/bash
# optimize-images.sh

set -e

INPUT_DIR="./images"
OUTPUT_DIR="./optimized"
QUALITY=85
MAX_WIDTH=1920

echo "Starting image optimization..."

# Create output directory
mkdir -p $OUTPUT_DIR

# Install dependencies
npm install -g sharp-cli
npm install -g imagemin-cli
npm install -g imagemin-webp
npm install -g imagemin-avif

# Process images
find $INPUT_DIR -type f \( -name "*.jpg" -o -name "*.jpeg" -o -name "*.png" \) | while read file; do
    filename=$(basename "$file")
    echo "Processing: $filename"
    
    # Optimize original format
    imagemin "$file" --out-dir=$OUTPUT_DIR --plugin=webp --plugin=avif
    
    # Generate WebP version
    sharp-cli resize 1920 --format webp --quality 85 "$file" "$OUTPUT_DIR/${filename%.*}.webp"
    
    # Generate AVIF version
    sharp-cli resize 1920 --format avif --quality 50 "$file" "$OUTPUT_DIR/${filename%.*}.avif"
done

echo "Image optimization completed!"

# 3. Docker Image Optimization
FROM node:18-alpine

# Install image optimization tools
RUN apk add --no-cache \
    imagemagick \
    pngquant \
    webp-tools \
    libavif-tools

# Install Node.js packages
RUN npm install -g \
    sharp-cli \
    imagemin-cli \
    imagemin-webp \
    imagemin-avif

WORKDIR /app

COPY package*.json ./
RUN npm install

COPY . .

# Run image optimization
RUN npm run optimize-images

CMD ["npm", "start"]

# 4. Image Optimization Service
class ImageOptimizationService {
    constructor() {
        this.optimizer = new ImageOptimizer();
        this.queue = [];
        this.processing = false;
    }
    
    async addToQueue(imagePath, options = {}) {
        this.queue.push({ imagePath, options });
        
        if (!this.processing) {
            await this.processQueue();
        }
    }
    
    async processQueue() {
        this.processing = true;
        
        while (this.queue.length > 0) {
            const { imagePath, options } = this.queue.shift();
            
            try {
                await this.optimizer.optimizeImage(imagePath, options);
                console.log(`Optimized: ${imagePath}`);
            } catch (error) {
                console.error(`Error optimizing ${imagePath}:`, error);
            }
        }
        
        this.processing = false;
    }
    
    async optimizeBatch(imagePaths, options = {}) {
        const results = [];
        
        for (const imagePath of imagePaths) {
            try {
                const result = await this.optimizer.optimizeImage(imagePath, options);
                results.push({ imagePath, success: true, result });
            } catch (error) {
                results.push({ imagePath, success: false, error: error.message });
            }
        }
        
        return results;
    }
}

# 5. Image Optimization API
const express = require('express');
const multer = require('multer');
const sharp = require('sharp');
const path = require('path');

const app = express();
const upload = multer({ dest: 'uploads/' });

app.post('/optimize', upload.single('image'), async (req, res) => {
    try {
        const inputPath = req.file.path;
        const outputDir = 'optimized';
        
        const optimizer = new ImageOptimizer();
        const results = await optimizer.optimizeImage(inputPath, outputDir);
        
        res.json({
            success: true,
            originalSize: req.file.size,
            optimized: results
        });
    } catch (error) {
        res.status(500).json({
            success: false,
            error: error.message
        });
    }
});

app.post('/optimize-batch', upload.array('images', 10), async (req, res) => {
    try {
        const service = new ImageOptimizationService();
        const imagePaths = req.files.map(file => file.path);
        
        const results = await service.optimizeBatch(imagePaths);
        
        res.json({
            success: true,
            results: results
        });
    } catch (error) {
        res.status(500).json({
            success: false,
            error: error.message
        });
    }
});

# 6. Image Optimization Monitoring
class ImageOptimizationMonitor {
    constructor() {
        this.metrics = {
            totalProcessed: 0,
            totalSizeSaved: 0,
            averageCompression: 0,
            errors: 0
        };
    }
    
    recordOptimization(originalSize, optimizedSize) {
        this.metrics.totalProcessed++;
        this.metrics.totalSizeSaved += (originalSize - optimizedSize);
        this.metrics.averageCompression = 
            (this.metrics.totalSizeSaved / this.metrics.totalProcessed) / originalSize * 100;
    }
    
    recordError() {
        this.metrics.errors++;
    }
    
    getStats() {
        return {
            ...this.metrics,
            compressionRatio: this.metrics.averageCompression,
            errorRate: (this.metrics.errors / this.metrics.totalProcessed) * 100
        };
    }
    
    generateReport() {
        const stats = this.getStats();
        
        console.log('=== Image Optimization Report ===');
        console.log(`Total Images Processed: ${stats.totalProcessed}`);
        console.log(`Total Size Saved: ${(stats.totalSizeSaved / 1024 / 1024).toFixed(2)} MB`);
        console.log(`Average Compression: ${stats.compressionRatio.toFixed(2)}%`);
        console.log(`Error Rate: ${stats.errorRate.toFixed(2)}%`);
    }
}

Image Format Comparison

Modern Image Formats

Image Format Comparison
# Image Format Comparison

# 1. Format Support Matrix
const formatSupport = {
    jpeg: {
        browsers: ['Chrome', 'Firefox', 'Safari', 'Edge'],
        compression: 'Lossy',
        transparency: false,
        animation: false,
        fileSize: 'Large',
        quality: 'Good'
    },
    png: {
        browsers: ['Chrome', 'Firefox', 'Safari', 'Edge'],
        compression: 'Lossless',
        transparency: true,
        animation: false,
        fileSize: 'Large',
        quality: 'Excellent'
    },
    webp: {
        browsers: ['Chrome', 'Firefox', 'Safari', 'Edge'],
        compression: 'Lossy/Lossless',
        transparency: true,
        animation: true,
        fileSize: 'Small',
        quality: 'Excellent'
    },
    avif: {
        browsers: ['Chrome', 'Firefox'],
        compression: 'Lossy/Lossless',
        transparency: true,
        animation: true,
        fileSize: 'Very Small',
        quality: 'Excellent'
    }
};

# 2. Format Selection Logic
class ImageFormatSelector {
    constructor() {
        this.userAgent = navigator.userAgent;
    }
    
    selectBestFormat() {
        if (this.supportsAVIF()) {
            return 'avif';
        } else if (this.supportsWebP()) {
            return 'webp';
        } else if (this.supportsPNG()) {
            return 'png';
        } else {
            return 'jpeg';
        }
    }
    
    supportsAVIF() {
        return this.userAgent.includes('Chrome') || this.userAgent.includes('Firefox');
    }
    
    supportsWebP() {
        return this.userAgent.includes('Chrome') || 
               this.userAgent.includes('Firefox') || 
               this.userAgent.includes('Safari') || 
               this.userAgent.includes('Edge');
    }
    
    supportsPNG() {
        return true; // Universal support
    }
    
    generatePictureElement(imagePath, alt = '') {
        const basePath = imagePath.replace(/\.[^/.]+$/, '');
        
        return `
  
  
  
  ${alt}
`;
    }
}

# 3. Progressive Image Loading
class ProgressiveImageLoader {
    constructor() {
        this.observer = new IntersectionObserver(this.handleIntersection.bind(this));
    }
    
    handleIntersection(entries) {
        entries.forEach(entry => {
            if (entry.isIntersecting) {
                this.loadImage(entry.target);
                this.observer.unobserve(entry.target);
            }
        });
    }
    
    loadImage(img) {
        const src = img.dataset.src;
        const srcset = img.dataset.srcset;
        
        if (src) {
            img.src = src;
        }
        
        if (srcset) {
            img.srcset = srcset;
        }
        
        img.classList.add('loaded');
    }
    
    observeImages() {
        const images = document.querySelectorAll('img[data-src]');
        images.forEach(img => this.observer.observe(img));
    }
}

# 4. Image Optimization Best Practices
class ImageOptimizationBestPractices {
    constructor() {
        this.recommendations = {
            formats: {
                photos: 'webp, avif',
                graphics: 'png, svg',
                icons: 'svg, png',
                logos: 'svg, png'
            },
            sizes: {
                mobile: 320,
                tablet: 768,
                desktop: 1920
            },
            quality: {
                webp: 85,
                avif: 50,
                jpeg: 85,
                png: 9
            }
        };
    }
    
    getRecommendations(imageType, deviceType) {
        return {
            format: this.recommendations.formats[imageType],
            size: this.recommendations.sizes[deviceType],
            quality: this.recommendations.quality
        };
    }
    
    generateOptimizationPlan(images) {
        return images.map(image => {
            const recommendations = this.getRecommendations(image.type, image.device);
            
            return {
                ...image,
                recommendations,
                estimatedSavings: this.calculateSavings(image, recommendations)
            };
        });
    }
    
    calculateSavings(image, recommendations) {
        // Simplified calculation
        const currentSize = image.size;
        const estimatedSize = currentSize * 0.3; // 70% reduction
        return currentSize - estimatedSize;
    }
}

# 5. Image Optimization Metrics
class ImageOptimizationMetrics {
    constructor() {
        this.metrics = {
            totalImages: 0,
            totalSize: 0,
            optimizedSize: 0,
            formats: {},
            compression: {}
        };
    }
    
    recordImage(originalSize, optimizedSize, format) {
        this.metrics.totalImages++;
        this.metrics.totalSize += originalSize;
        this.metrics.optimizedSize += optimizedSize;
        
        if (!this.metrics.formats[format]) {
            this.metrics.formats[format] = 0;
        }
        this.metrics.formats[format]++;
        
        const compression = ((originalSize - optimizedSize) / originalSize) * 100;
        if (!this.metrics.compression[format]) {
            this.metrics.compression[format] = [];
        }
        this.metrics.compression[format].push(compression);
    }
    
    getReport() {
        const totalSavings = this.metrics.totalSize - this.metrics.optimizedSize;
        const averageCompression = (totalSavings / this.metrics.totalSize) * 100;
        
        return {
            totalImages: this.metrics.totalImages,
            totalSize: this.metrics.totalSize,
            optimizedSize: this.metrics.optimizedSize,
            totalSavings: totalSavings,
            averageCompression: averageCompression,
            formatDistribution: this.metrics.formats,
            compressionByFormat: this.metrics.compression
        };
    }
}

Best Practices

Image Optimization Guidelines

Optimization Best Practices

  • Use appropriate image formats
  • Implement responsive images
  • Optimize for different devices
  • Use lazy loading
  • Implement progressive loading
  • Monitor performance metrics
  • Automate optimization process

Common Mistakes

  • Using oversized images
  • Not implementing responsive images
  • Ignoring modern formats
  • No lazy loading
  • Poor compression settings
  • Not monitoring performance
  • Manual optimization only

Summary

Image optimization tools and techniques involve several key components:

  • Compression Tools: ImageMagick, Sharp, WebP, AVIF
  • Node.js Processing: Programmatic optimization, batch processing
  • Webpack Integration: Build-time optimization, responsive images
  • Automation: CI/CD pipelines, automated workflows
  • Format Comparison: Modern formats, browser support
  • Best Practices: Optimization guidelines, performance monitoring

Need More Help?

Struggling with image optimization or need help improving your website's image performance? Our performance experts can help you implement effective image optimization strategies.

Get Image Optimization Help