You can edit the below JavaScript code to customize the image tool.
Apply Changes
function processImage(originalImg, themeColor = "#ff0033", intensity = "5") {
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 first
ctx.drawImage(originalImg, 0, 0, width, height);
// Apply VHS / Error Glitch Effect
const imgData = ctx.getImageData(0, 0, width, height);
const data = imgData.data;
const outData = ctx.createImageData(width, height);
const out = outData.data;
let shiftAmount = parseInt(intensity, 10);
if (isNaN(shiftAmount)) shiftAmount = 5;
const shiftOffset = shiftAmount * 4;
for (let y = 0; y < height; y++) {
// Determine random row glitch (horizontal tearing)
let isGlitchRow = Math.random() < 0.05 * shiftAmount;
let rowGlitchShift = isGlitchRow ? Math.floor((Math.random() - 0.5) * 10 * shiftAmount) : 0;
for (let x = 0; x < width; x++) {
let srcI = (y * width + x) * 4;
let destX = x + rowGlitchShift;
// Wrap around horizontal glitches
if (destX < 0) destX += width;
if (destX >= width) destX -= width;
let destI = (y * width + destX) * 4;
// RGB Channel Shift
let r_i = srcI - shiftOffset;
let b_i = srcI + shiftOffset;
// Retrieve pixel data mapping bounds to row
let r_val = (x - shiftAmount >= 0) ? data[r_i] : data[srcI]; // Red shifted left
let g_val = data[srcI + 1]; // Green stays
let b_val = (x + shiftAmount < width) ? data[b_i + 2] : data[srcI + 2]; // Blue shifted right
let a_val = data[srcI + 3]; // Alpha stays
out[destI] = r_val;
out[destI + 1] = g_val;
out[destI + 2] = b_val;
out[destI + 3] = a_val;
}
}
ctx.putImageData(outData, 0, 0);
// Apply CRT Scanlines
ctx.fillStyle = "rgba(0, 0, 0, 0.15)";
for (let i = 0; i < height; i += 4) {
ctx.fillRect(0, i, width, 2);
}
// Overlay Settings and Text Interface
const fontSizeSmall = Math.max(14, Math.floor(height * 0.035));
const fontSizeLarge = Math.max(30, Math.floor(height * 0.12));
ctx.shadowColor = "rgba(0, 0, 0, 0.9)";
ctx.shadowBlur = 6;
ctx.shadowOffsetX = 3;
ctx.shadowOffsetY = 3;
ctx.textBaseline = "top";
// Top Left: "Открыть настройки" (Open settings)
ctx.font = `bold ${fontSizeSmall}px "Courier New", Courier, monospace`;
ctx.fillStyle = "#ffffff";
ctx.textAlign = "left";
ctx.fillText("[ ] ОТКРЫТЬ НАСТРОЙКИ", 20, 20);
ctx.fillStyle = themeColor;
ctx.fillText(" x ", 26, 20);
// Top Right: "Options Text"
ctx.textAlign = "right";
ctx.fillStyle = "#00ffcc";
ctx.fillText("OPTIONS | TEXT", width - 20, 20);
// Bottom Right: "Кино Видео" (Cinema Video)
ctx.fillStyle = "#ffffff";
ctx.textAlign = "right";
ctx.textBaseline = "bottom";
ctx.fillText("▶ КИНО / ВИДЕО", width - 20, height - 20);
// Center: "Ошибка" (Error) with chromatic aberration effect
ctx.textAlign = "center";
ctx.textBaseline = "middle";
ctx.font = `bold ${fontSizeLarge}px "Courier New", Courier, monospace`;
const centerX = width / 2;
const centerY = height / 2;
// Cyan shadow layer
ctx.fillStyle = "#00ffff";
ctx.fillText("ОШИБКА", centerX - shiftAmount, centerY);
// Red shadow layer
ctx.fillStyle = "red";
ctx.fillText("ОШИБКА", centerX + shiftAmount, centerY);
// Main white layer
ctx.fillStyle = "#ffffff";
ctx.fillText("ОШИБКА", centerX, centerY);
// Sub-text under error
ctx.font = `bold ${fontSizeSmall}px "Courier New", Courier, monospace`;
ctx.fillStyle = "#ffcc00";
ctx.fillText("ERR_SETTINGS_OVERRIDE_FAILED", centerX, centerY + fontSizeLarge * 0.7);
return canvas;
}
Apply Changes