You can edit the below JavaScript code to customize the image tool.
Apply Changes
async function processImage(
originalImg,
secondImageUrl = "",
layout = "horizontal",
matchDimensions = "false",
gap = "0",
backgroundColor = "#ffffff",
blendAlpha = "0.5"
) {
// Parse parameters
const numGap = parseInt(gap, 10) || 0;
const numBlendAlpha = parseFloat(blendAlpha) || 0.5;
const matchDims = matchDimensions.toLowerCase() === "true";
const w1 = originalImg.width;
const h1 = originalImg.height;
// Helper function to create a placeholder canvas if no valid second image is provided
function createPlaceholderCanvas(width, height) {
const c = document.createElement('canvas');
c.width = width;
c.height = height;
const cx = c.getContext('2d');
// Background
cx.fillStyle = '#f0f0f0';
cx.fillRect(0, 0, width, height);
// Striped pattern
cx.strokeStyle = '#dddddd';
cx.lineWidth = 4;
for (let i = -height; i < width + height; i += 20) {
cx.beginPath();
cx.moveTo(i, 0);
cx.lineTo(i - height, height);
cx.stroke();
}
// Text label
const fontHeight = Math.max(16, Math.min(width, height) / 10);
cx.font = `bold ${fontHeight}px Arial, sans-serif`;
cx.textAlign = 'center';
cx.textBaseline = 'middle';
const text = 'Image 2 Details Needed';
const metrics = cx.measureText(text);
// Text background for readability
cx.fillStyle = 'rgba(255, 255, 255, 0.85)';
cx.fillRect(
width / 2 - metrics.width / 2 - 10,
height / 2 - fontHeight / 2 - 10,
metrics.width + 20,
fontHeight + 20
);
cx.fillStyle = '#555555';
cx.fillText(text, width / 2, height / 2);
return c;
}
// Load or generate second image
let img2;
if (secondImageUrl && secondImageUrl.trim() !== "") {
try {
img2 = await new Promise((resolve, reject) => {
const img = new Image();
img.crossOrigin = "anonymous";
img.onload = () => resolve(img);
img.onerror = () => reject(new Error("Failed to load"));
img.src = secondImageUrl;
});
} catch (e) {
console.warn("Could not load second image from provided URL. Using placeholder.");
img2 = createPlaceholderCanvas(w1, h1);
}
} else {
img2 = createPlaceholderCanvas(w1, h1);
}
// Determine dimensions for drawing the second image
let finalW2 = img2.width;
let finalH2 = img2.height;
if (matchDims) {
if (layout === 'horizontal' || layout === 'horizontal-reverse') {
finalH2 = h1;
finalW2 = (img2.width / img2.height) * finalH2;
} else if (layout === 'vertical' || layout === 'vertical-reverse') {
finalW2 = w1;
finalH2 = (img2.height / img2.width) * finalW2;
}
}
// Prepare Output Canvas
const canvas = document.createElement('canvas');
const ctx = canvas.getContext('2d');
// Combine logic based on selected layout
if (layout === 'horizontal') {
canvas.width = w1 + numGap + finalW2;
canvas.height = Math.max(h1, finalH2);
ctx.fillStyle = backgroundColor;
ctx.fillRect(0, 0, canvas.width, canvas.height);
// Center images vertically
const y1 = (canvas.height - h1) / 2;
const y2 = (canvas.height - finalH2) / 2;
ctx.drawImage(originalImg, 0, y1, w1, h1);
ctx.drawImage(img2, w1 + numGap, y2, finalW2, finalH2);
} else if (layout === 'vertical') {
canvas.width = Math.max(w1, finalW2);
canvas.height = h1 + numGap + finalH2;
ctx.fillStyle = backgroundColor;
ctx.fillRect(0, 0, canvas.width, canvas.height);
// Center images horizontally
const x1 = (canvas.width - w1) / 2;
const x2 = (canvas.width - finalW2) / 2;
ctx.drawImage(originalImg, x1, 0, w1, h1);
ctx.drawImage(img2, x2, h1 + numGap, finalW2, finalH2);
} else if (layout === 'blend') {
// Blend mode ignores dimensional matching, stretches img2 over img1 bounds
canvas.width = w1;
canvas.height = h1;
ctx.fillStyle = backgroundColor;
ctx.fillRect(0, 0, canvas.width, canvas.height);
// Draw Base
ctx.drawImage(originalImg, 0, 0, w1, h1);
// Draw Overlay Overlay
ctx.globalAlpha = Math.max(0, Math.min(1, numBlendAlpha));
ctx.drawImage(img2, 0, 0, w1, h1);
ctx.globalAlpha = 1.0;
} else {
// Fallback safety (renders side by side without modifiers basically)
canvas.width = w1 + finalW2;
canvas.height = Math.max(h1, finalH2);
ctx.drawImage(originalImg, 0, 0, w1, h1);
ctx.drawImage(img2, w1, 0, finalW2, finalH2);
}
return canvas;
}
Apply Changes