You can edit the below JavaScript code to customize the image tool.
Apply Changes
function processImage(
originalImg,
textOverlay = "AU COURANT",
showText = 1,
filterContrast = 1.2,
filterSaturation = 0.80,
filterBrightness = 1.05,
vignetteIntensity = 0.35,
grainIntensityBase = 15
) {
// Parse numeric inputs in case they are provided as strings
const contrast = Number(filterContrast);
const saturation = Number(filterSaturation);
const brightness = Number(filterBrightness);
const vignette = Number(vignetteIntensity);
const grain = Number(grainIntensityBase);
const addText = Number(showText);
// Set up main canvas
const canvas = document.createElement('canvas');
const ctx = canvas.getContext('2d');
const width = originalImg.width;
const height = originalImg.height;
canvas.width = width;
canvas.height = height;
// Draw the original image onto the canvas
ctx.drawImage(originalImg, 0, 0);
// Retrieve the pixel data
const imgData = ctx.getImageData(0, 0, width, height);
const data = imgData.data;
// Luminance constants
const luR = 0.299;
const luG = 0.587;
const luB = 0.114;
// Apply the "Au Courant" fashionable filter (Color grading, contrast, desaturation)
for (let i = 0; i < data.length; i += 4) {
let r = data[i];
let g = data[i + 1];
let b = data[i + 2];
// 1. Brightness
r *= brightness;
g *= brightness;
b *= brightness;
// 2. Contrast
r = ((r / 255 - 0.5) * contrast + 0.5) * 255;
g = ((g / 255 - 0.5) * contrast + 0.5) * 255;
b = ((b / 255 - 0.5) * contrast + 0.5) * 255;
// 3. Saturation
const gray = r * luR + g * luG + b * luB;
r = gray + saturation * (r - gray);
g = gray + saturation * (g - gray);
b = gray + saturation * (b - gray);
// 4. Trendy Split Toning
// Adds warmth to highlights and cool tones to shadows for a modern, chic aesthetic
if (gray > 128) {
const shift = ((gray - 128) / 127) * 20;
r += shift; // Boost Red
g += shift * 0.5; // Slight boost to Green
b -= shift * 0.8; // Pull Blue
} else {
const shift = ((128 - gray) / 128) * 20;
r -= shift * 0.8; // Pull Red
g -= shift * 0.4; // Pull Green
b += shift; // Boost Blue
}
// Clamp values
data[i] = Math.min(255, Math.max(0, r));
data[i + 1] = Math.min(255, Math.max(0, g));
data[i + 2] = Math.min(255, Math.max(0, b));
}
// Put modified pixels back
ctx.putImageData(imgData, 0, 0);
// Apply Vignette overlay
if (vignette > 0) {
const gradient = ctx.createRadialGradient(
width / 2, height / 2, Math.min(width, height) * 0.35,
width / 2, height / 2, Math.max(width, height) * 0.75
);
gradient.addColorStop(0, 'rgba(0,0,0,0)');
gradient.addColorStop(1, `rgba(0,0,0,${vignette})`);
ctx.fillStyle = gradient;
ctx.fillRect(0, 0, width, height);
}
// Apply Film Grain texture (using an offscreen pattern canvas)
if (grain > 0) {
const grainCanvas = document.createElement('canvas');
grainCanvas.width = 120;
grainCanvas.height = 120;
const grainCtx = grainCanvas.getContext('2d');
const grainData = grainCtx.createImageData(120, 120);
for (let i = 0; i < grainData.data.length; i += 4) {
const v = Math.random() * 255;
grainData.data[i] = v;
grainData.data[i+1] = v;
grainData.data[i+2] = v;
grainData.data[i+3] = grain; // alpha transparency of the noise
}
grainCtx.putImageData(grainData, 0, 0);
ctx.fillStyle = ctx.createPattern(grainCanvas, 'repeat');
ctx.fillRect(0, 0, width, height);
}
// Apply Minimalist Styling / Watermark text representing "Au Courant"
if (addText > 0 && textOverlay && textOverlay.trim().length > 0) {
ctx.save();
const fontSize = Math.max(16, Math.floor(Math.min(width, height) * 0.035));
ctx.font = `300 ${fontSize}px "Helvetica Neue", Helvetica, Arial, sans-serif`;
ctx.textAlign = 'right';
ctx.textBaseline = 'bottom';
// Text styling
ctx.fillStyle = 'rgba(255, 255, 255, 0.9)';
ctx.shadowColor = 'rgba(0, 0, 0, 0.6)';
ctx.shadowBlur = 6;
ctx.shadowOffsetX = 1;
ctx.shadowOffsetY = 1;
const padding = fontSize + 10;
// Print text
ctx.fillText(textOverlay.toUpperCase(), width - padding, height - padding);
// Add a fashionable decorator line above the text
const textWidth = ctx.measureText(textOverlay.toUpperCase()).width;
ctx.beginPath();
const lineY = height - padding - fontSize - (fontSize * 0.3);
ctx.moveTo(width - padding - textWidth, lineY);
ctx.lineTo(width - padding, lineY);
ctx.strokeStyle = 'rgba(255, 255, 255, 0.9)';
ctx.lineWidth = Math.max(1, fontSize * 0.05);
ctx.stroke();
ctx.restore();
}
return canvas;
}
Apply Changes