You can edit the below JavaScript code to customize the image tool.
function processImage(originalImg, magicColor = "blue", effectStrength = 0.5) {
const canvas = document.createElement('canvas');
const ctx = canvas.getContext('2d');
// Ensure effectStrength is clamped between 0 and 1
const clampedEffectStrength = Math.max(0, Math.min(1, effectStrength));
// Use naturalWidth/Height for actual image dimensions, fallback to width/height
canvas.width = originalImg.naturalWidth || originalImg.width;
canvas.height = originalImg.naturalHeight || originalImg.height;
// If canvas dimensions are zero (e.g., image not loaded or invalid), return an empty canvas.
if (canvas.width === 0 || canvas.height === 0) {
console.warn("EnchantedPhotoFilter: Original image has zero dimensions.");
return canvas;
}
// Initial draw of the image onto the canvas
ctx.drawImage(originalImg, 0, 0, canvas.width, canvas.height);
// If effectStrength is very close to zero, effectively no filter is applied.
// Return the canvas with the original image drawn.
if (clampedEffectStrength < 0.01) {
return canvas;
}
// 1. Pixel-level manipulation (Saturation, Contrast, Brightness)
// This step modifies the pixel data directly for fundamental image adjustments.
const imageData = ctx.getImageData(0, 0, canvas.width, canvas.height);
const data = imageData.data;
// Adjust parameters based on effectStrength
const saturationBoost = 1.0 + (0.8 * clampedEffectStrength); // Max 80% saturation increase
const contrastFactor = 1.0 + (0.5 * clampedEffectStrength); // Max 50% contrast increase
const brightnessAdjustment = 15 * clampedEffectStrength; // Max +15 brightness shift (on a 0-255 scale)
for (let i = 0; i < data.length; i += 4) {
let r = data[i];
let g = data[i + 1];
let b = data[i + 2];
// Apply Saturation
// Standard luminance calculation
const lum = 0.299 * r + 0.587 * g + 0.114 * b;
r = lum + (r - lum) * saturationBoost;
g = lum + (g - lum) * saturationBoost;
b = lum + (b - lum) * saturationBoost;
// Apply Contrast
// Pixels are made lighter or darker relative to the midpoint (128)
r = contrastFactor * (r - 128) + 128;
g = contrastFactor * (g - 128) + 128;
b = contrastFactor * (b - 128) + 128;
// Apply Brightness
r += brightnessAdjustment;
g += brightnessAdjustment;
b += brightnessAdjustment;
// Clamp color values to the valid [0, 255] range
data[i] = Math.max(0, Math.min(255, r));
data[i + 1] = Math.max(0, Math.min(255, g));
data[i + 2] = Math.max(0, Math.min(255, b));
// Alpha channel (data[i+3]) is preserved
}
ctx.putImageData(imageData, 0, 0); // Apply modified pixel data back to the canvas
// 2. Apply Blur Filter
// A subtle blur enhances the "enchanted" feel; "dreamy" style gets a stronger blur.
let blurAmount = 0;
const lowerCaseMagicColor = magicColor.toLowerCase();
if (lowerCaseMagicColor === "dreamy") {
blurAmount = clampedEffectStrength * 1.5; // Up to 1.5px blur for "dreamy"
} else {
blurAmount = clampedEffectStrength * 0.4; // Up to 0.4px blur for other styles
}
if (blurAmount >= 0.1) { // Apply blur only if it's visually significant (>= 0.1px)
// To blur the current canvas content, draw it to a temporary canvas with the blur filter,
// then draw it back to the main canvas.
const tempCanvas = document.createElement('canvas');
tempCanvas.width = canvas.width;
tempCanvas.height = canvas.height;
const tempCtx = tempCanvas.getContext('2d');
tempCtx.filter = `blur(${blurAmount.toFixed(1)}px)`; // Set blur filter on temp context
tempCtx.drawImage(canvas, 0, 0); // Draw (and blur) main canvas content to tempCanvas
ctx.clearRect(0, 0, canvas.width, canvas.height); // Clear main canvas
ctx.drawImage(tempCanvas, 0, 0); // Draw blurred image from tempCanvas to main canvas
// The main context 'ctx' does not have its filter property set, so it's clean for next step.
}
// 3. Apply Color Overlay for Tinting
// This adds a layer of color using a specified blend mode for the "enchanted" tint.
let overlayColorRgba = '';
let blendMode = 'soft-light'; // Default blend mode for subtle tinting
// Overlay alpha scales with effectStrength. "dreamy" has a slightly lower max alpha.
let maxAlphaForOverlay = (lowerCaseMagicColor === 'dreamy' ? 0.45 : 0.65);
let actualOverlayAlpha = maxAlphaForOverlay * clampedEffectStrength;
if (actualOverlayAlpha >= 0.01) { // Apply overlay if alpha is noticeable
switch (lowerCaseMagicColor) {
case "purple": overlayColorRgba = `rgba(160, 32, 240, ${actualOverlayAlpha})`; break;
case "gold": overlayColorRgba = `rgba(255, 200, 50, ${actualOverlayAlpha})`; break;
case "pink": overlayColorRgba = `rgba(255, 120, 190, ${actualOverlayAlpha})`; break;
case "cyan": overlayColorRgba = `rgba(0, 200, 200, ${actualOverlayAlpha})`; break;
case "emerald": overlayColorRgba = `rgba(50, 205, 50, ${actualOverlayAlpha})`; break; // A vibrant green
case "dreamy":
overlayColorRgba = `rgba(100, 100, 200, ${actualOverlayAlpha})`; // Lavender-blue tint
blendMode = 'overlay'; // 'overlay' blend for a stronger, more distinct "dreamy" color effect
break;
case "blue": // Explicitly "blue"
default: // Default to "blue" for unrecognized magicColor values
overlayColorRgba = `rgba(60, 60, 220, ${actualOverlayAlpha})`; break;
}
if (overlayColorRgba) {
ctx.globalCompositeOperation = blendMode; // Set the blend mode
ctx.fillStyle = overlayColorRgba; // Set the fill color (tint)
ctx.fillRect(0, 0, canvas.width, canvas.height); // Apply the colored overlay
ctx.globalCompositeOperation = 'source-over'; // Reset blend mode to default for any subsequent drawing
}
}
return canvas; // Return the canvas with the "enchanted" filter applied
}
Free Image Tool Creator
Can't find the image tool you're looking for? Create one based on your own needs now!
The Enchanted Photo Filter Tool allows users to enhance their images with a unique ‘enchanted’ effect. By applying adjustments such as saturation, contrast, and brightness, along with a subtle blur and a customizable color overlay, users can create visually striking images that exude a dreamy quality. This tool is perfect for photographers, social media enthusiasts, or anyone looking to add a magical touch to their images for personal use, marketing materials, or artistic presentations.