Please bookmark this page to avoid losing your image tool!

Image Marathon Tool

(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, bibNumber = "42195", eventName = "МАРАФОН", runnerName = "БЕГУН", themeColor = "#D32F2F") {
    const canvas = document.createElement('canvas');
    const ctx = canvas.getContext('2d');
    
    // Set canvas dimensions to match the original image
    canvas.width = originalImg.width;
    canvas.height = originalImg.height;

    // Draw the original image as background
    ctx.drawImage(originalImg, 0, 0);

    // Calculate dimensions for the Marathon Bib (Runners' race number)
    const bibWidth = Math.min(canvas.width * 0.7, 800);
    const bibHeight = bibWidth * 0.7; // Standard bib proportion
    const bibX = (canvas.width - bibWidth) / 2;
    // Place bib at the bottom with standard padding
    const bibY = canvas.height - bibHeight - (canvas.height * 0.05); 
    const cornerRadius = bibWidth * 0.03;

    // Helper function to draw rounded rectangles
    function drawRoundRect(x, y, w, h, r, isFill) {
        ctx.beginPath();
        ctx.moveTo(x + r, y);
        ctx.lineTo(x + w - r, y);
        ctx.quadraticCurveTo(x + w, y, x + w, y + r);
        ctx.lineTo(x + w, y + h - r);
        ctx.quadraticCurveTo(x + w, y + h, x + w - r, y + h);
        ctx.lineTo(x + r, y + h);
        ctx.quadraticCurveTo(x, y + h, x, y + h - r);
        ctx.lineTo(x, y + r);
        ctx.quadraticCurveTo(x, y, x + r, y);
        ctx.closePath();
        if (isFill) {
            ctx.fill();
        } else {
            ctx.stroke();
        }
    }

    // 1. Draw Bib Shadow
    ctx.shadowColor = 'rgba(0, 0, 0, 0.6)';
    ctx.shadowBlur = bibWidth * 0.03;
    ctx.shadowOffsetX = 0;
    ctx.shadowOffsetY = bibWidth * 0.01;

    // 2. Draw Bib Background (White card)
    ctx.fillStyle = '#ffffff';
    drawRoundRect(bibX, bibY, bibWidth, bibHeight, cornerRadius, true);

    // Reset shadow for the rest of the drawing
    ctx.shadowColor = 'transparent';

    // 3. Draw Colored Header / Inner Border
    const margin = bibWidth * 0.04;
    
    // Colored header block at the top of the bib
    ctx.fillStyle = themeColor;
    const headerHeight = bibHeight * 0.25;
    ctx.beginPath();
    ctx.moveTo(bibX + cornerRadius, bibY);
    ctx.lineTo(bibX + bibWidth - cornerRadius, bibY);
    ctx.quadraticCurveTo(bibX + bibWidth, bibY, bibX + bibWidth, bibY + cornerRadius);
    ctx.lineTo(bibX + bibWidth, bibY + headerHeight);
    ctx.lineTo(bibX, bibY + headerHeight);
    ctx.lineTo(bibX, bibY + cornerRadius);
    ctx.quadraticCurveTo(bibX, bibY, bibX + cornerRadius, bibY);
    ctx.closePath();
    ctx.fill();

    // Bottom barcode decoration
    ctx.fillStyle = '#000000';
    const barCodeWidth = bibWidth - (2 * margin);
    const barCodeY = bibY + bibHeight - margin - (bibHeight * 0.08);
    for(let i = 0; i < 40; i++) {
        const barW = (Math.random() * 0.02 + 0.005) * bibWidth;
        const barX = bibX + margin + (i / 40) * barCodeWidth;
        if(barX + barW < bibX + bibWidth - margin) {
             ctx.fillRect(barX, barCodeY, barW, bibHeight * 0.06);
        }
    }

    // Outer border ring line
    ctx.strokeStyle = '#e0e0e0';
    ctx.lineWidth = bibWidth * 0.005;
    drawRoundRect(bibX + margin / 2, bibY + margin / 2, bibWidth - margin, bibHeight - margin, cornerRadius * 0.5, false);

    // 4. Draw Safety Pin Holes
    ctx.fillStyle = '#333333';
    const holeRadius = bibWidth * 0.015;
    
    function drawHole(x, y) {
        // Inner hole
        ctx.beginPath();
        ctx.arc(x, y, holeRadius, 0, Math.PI * 2);
        ctx.fillStyle = '#000000';
        ctx.fill();
        // Pin ring reflection
        ctx.beginPath();
        ctx.arc(x, y, holeRadius * 1.5, 0, Math.PI * 2);
        ctx.strokeStyle = '#aaaaaa';
        ctx.lineWidth = holeRadius * 0.4;
        ctx.stroke();
    }
    
    const hMargin = margin;
    drawHole(bibX + hMargin, bibY + hMargin);
    drawHole(bibX + bibWidth - hMargin, bibY + hMargin);
    drawHole(bibX + hMargin, bibY + bibHeight - hMargin);
    drawHole(bibX + bibWidth - hMargin, bibY + bibHeight - hMargin);

    // 5. Draw Text Information
    ctx.textAlign = 'center';
    ctx.textBaseline = 'middle';

    // Event Name (Header)
    ctx.fillStyle = '#ffffff';
    ctx.font = `900 ${bibHeight * 0.15}px "Impact", "Arial Black", sans-serif`;
    ctx.fillText(eventName.toUpperCase(), canvas.width / 2, bibY + (headerHeight / 2));

    // Bib Number (Center)
    ctx.fillStyle = '#111111';
    ctx.font = `bold ${bibHeight * 0.4}px "Impact", "Arial Black", sans-serif`;
    ctx.fillText(bibNumber, canvas.width / 2, bibY + (bibHeight * 0.55));

    // Runner Name (Bottom)
    ctx.fillStyle = '#555555';
    ctx.font = `bold ${bibHeight * 0.1}px Arial, sans-serif`;
    ctx.fillText(runnerName.toUpperCase(), canvas.width / 2, bibY + bibHeight - margin - (bibHeight * 0.15));

    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 Image Marathon Tool allows users to overlay a customizable marathon race bib onto their photos. The tool automatically adds a realistic runner’s number card to the bottom of an image, featuring elements like a race event name, a participant’s name, a unique bib number, a decorative barcode, and even details like safety pin holes. This tool is ideal for marathon organizers, running enthusiasts, or social media users looking to create personalized commemorative images of their athletic achievements.

Leave a Reply

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