Please bookmark this page to avoid losing your image tool!

Image Bat Theft Case Story Generator

(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,
  caseNumber = "04-BM-2023",
  batCount = "13",
  suspectName = "Неизвестный фигурант",
  detective = "инспектор А.В. Крылов"
) {
  // Create and configure the canvas
  const canvas = document.createElement("canvas");
  const ctx = canvas.getContext("2d");
  
  canvas.width = 800;
  canvas.height = 1100;

  // 1. Draw Manila Folder Background
  ctx.fillStyle = "#e0cfab"; 
  ctx.fillRect(0, 0, canvas.width, canvas.height);

  // Add a slight radial gradient/vignette to simulate age/lighting
  const grad = ctx.createRadialGradient(
    canvas.width / 2, canvas.height / 2, 200, 
    canvas.width / 2, canvas.height / 2, 800
  );
  grad.addColorStop(0, "rgba(255,255,255,0.1)");
  grad.addColorStop(1, "rgba(0,0,0,0.15)");
  ctx.fillStyle = grad;
  ctx.fillRect(0, 0, canvas.width, canvas.height);

  // Decorative folder line
  ctx.strokeStyle = "#5a4b31";
  ctx.lineWidth = 1;
  ctx.beginPath();
  ctx.moveTo(30, 20);
  ctx.lineTo(30, canvas.height - 20);
  ctx.stroke();

  // 2. Draw Header Text
  ctx.font = "bold 24px 'Courier New', Courier, monospace";
  ctx.fillStyle = "#111";
  ctx.textAlign = "left";
  
  const currentDate = new Date().toLocaleDateString("ru-RU");
  ctx.fillText(`АРХИВ: СЕКРЕТНО`, 50, 50);
  ctx.textAlign = "right";
  ctx.fillText(`ДАТА: ${currentDate}`, canvas.width - 50, 50);

  // Title
  ctx.textAlign = "center";
  ctx.font = "bold 32px 'Courier New', Courier, monospace";
  ctx.fillText(`ДЕЛО № ${caseNumber}`, canvas.width / 2, 110);
  
  ctx.font = "bold 28px 'Courier New', Courier, monospace";
  ctx.fillText(`О ПОХИЩЕННЫХ ЛЕТУЧИХ МЫШАХ`, canvas.width / 2, 150);
  
  // 3. Draw the Image (Evidence / Suspect)
  const imgMaxW = 500;
  const imgMaxH = 350;
  const ratio = Math.min(imgMaxW / originalImg.width, imgMaxH / originalImg.height);
  const drawW = originalImg.width * ratio;
  const drawH = originalImg.height * ratio;
  
  const imgX = (canvas.width - drawW) / 2;
  const imgY = 220;

  // Draw photo white border (polaroid effect)
  ctx.save();
  ctx.shadowColor = "rgba(0, 0, 0, 0.4)";
  ctx.shadowBlur = 10;
  ctx.shadowOffsetX = 3;
  ctx.shadowOffsetY = 3;
  ctx.fillStyle = "#fdfdfd";
  ctx.fillRect(imgX - 15, imgY - 15, drawW + 30, drawH + 60); // Bottom padding for polaroid style
  ctx.restore();

  // Draw the actual image
  ctx.drawImage(originalImg, imgX, imgY, drawW, drawH);

  // Handwritten note on polaroid
  ctx.font = "italic 16px 'Georgia', serif";
  ctx.fillStyle = "#333";
  ctx.textAlign = "center";
  ctx.fillText("Вещдок №1 (Фото с места инцидента)", canvas.width / 2, imgY + drawH + 25);

  // Draw masking tape holding the photo
  ctx.save();
  ctx.fillStyle = "rgba(225, 225, 215, 0.8)";
  ctx.shadowColor = "rgba(0, 0, 0, 0.2)";
  ctx.shadowBlur = 4;
  ctx.translate(canvas.width / 2, imgY - 15);
  ctx.rotate(-0.06); 
  ctx.fillRect(-70, -10, 140, 25);
  ctx.restore();

  // 4. Generate & Draw the Story (Case File Draft)
  const storyTemplate = `ОБСТОЯТЕЛЬСТВА ИНЦИДЕНТА:
Под покровом ночи злоумышленники проникли в специализированный вольер. Было похищено как минимум ${batCount} редких особей, относящихся к подотряду летучих мышей. На месте преступления найдены лишь обрывки сети, надкушенный манго и странный высокочастотный локатор.

ПОДОЗРЕВАЕМЫЕ ЛИЦА И УЛИКИ:
К делу приобщен ${suspectName}, чей профиль/отпечаток зафиксирован на фотокарточке выше. Особые приметы подозреваемого: неестественная любовь к сумеркам, избегание чеснока и подозрительно острый слух. Соседи утверждают, что в последние недели подозреваемый скупал насекомых и фрукты оптовыми партиями.

ЗАКЛЮЧЕНИЕ СЛЕДСТВИЯ:
Ведущий дело ${detective} постановил, что целью похищения, вероятно, является создание подпольной ультразвуковой лаборатории или попытка вырастить гигантскую армию рукокрылых. Статус расследования переведён в режим максимальной срочности.`;

  ctx.font = "18px 'Courier New', Courier, monospace";
  ctx.fillStyle = "#1a1a1a";
  ctx.textAlign = "left";
  
  const textX = 60;
  const textY = imgY + drawH + 90;
  const maxTextWidth = canvas.width - 120;
  const lineHeight = 28;

  // Helper function to wrap text
  function wrapText(context, text, x, y, maxWidth, lineHeight) {
    const paragraphs = text.split('\n');
    let currentY = y;

    for (let p = 0; p < paragraphs.length; p++) {
      const words = paragraphs[p].split(' ');
      let line = '';

      for (let n = 0; n < words.length; n++) {
        const testLine = line + words[n] + ' ';
        const metrics = context.measureText(testLine);
        const testWidth = metrics.width;
        
        if (testWidth > maxWidth && n > 0) {
          context.fillText(line, x, currentY);
          line = words[n] + ' ';
          currentY += lineHeight;
        } else {
          line = testLine;
        }
      }
      context.fillText(line, x, currentY);
      currentY += lineHeight; // extra space between paragraphs
    }
  }

  wrapText(ctx, storyTemplate, textX, textY, maxTextWidth, lineHeight);

  // 5. Draw "Top Secret" Rubber Stamp
  ctx.save();
  ctx.translate(canvas.width / 2 + 150, canvas.height - 180);
  ctx.rotate(-Math.PI / 8); 
  ctx.font = "bold 45px 'Courier New', Courier, monospace";
  ctx.fillStyle = "rgba(180, 20, 20, 0.5)";       // Faded red ink
  ctx.strokeStyle = "rgba(180, 20, 20, 0.5)";
  ctx.lineWidth = 4;
  ctx.textAlign = "center";
  ctx.textBaseline = "middle";
  
  // Stamp border
  ctx.strokeRect(-220, -40, 440, 80);
  // Inner border
  ctx.lineWidth = 2;
  ctx.strokeRect(-212, -32, 424, 64);
  // Stamp text
  ctx.fillText("СОВЕРШЕННО СЕКРЕТНО", 0, 0);
  
  // Add some random "scratch" lines over the stamp to make it look gritty
  for (let i = 0; i < 5; i++) {
    ctx.beginPath();
    ctx.moveTo(Math.random() * 400 - 200, Math.random() * 60 - 30);
    ctx.lineTo(Math.random() * 400 - 200, Math.random() * 60 - 30);
    ctx.strokeStyle = "rgba(224, 207, 171, 0.8)"; // Canvas background color
    ctx.stroke();
  }
  ctx.restore();

  // Signature
  ctx.fillStyle = "rgba(0,0,100,0.8)";
  ctx.font = "italic 26px 'Georgia', serif";
  ctx.textAlign = "right";
  ctx.fillText("Подпись: _________", canvas.width - 60, canvas.height - 50);

  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 transforms an uploaded image into a stylized, fictional crime dossier themed around a mysterious bat theft investigation. It overlays the image onto a digital Manila folder background with a Polaroid-style effect, complete with masking tape and handwritten notes. The generator automatically populates a dramatic case file containing custom details such as a case number, the number of bats stolen, suspect names, and a detective’s signature. It also features creative visual elements like a ‘Top Secret’ rubber stamp to enhance the investigative atmosphere. This tool is ideal for creative storytelling, tabletop role-playing games (RPGs), or making unique, themed social media content.

Leave a Reply

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