my-homelab-configs/apps/demos-static/public/privacy-redactor/privacy-redactor.js

55 lines
1.9 KiB
JavaScript

const canvas = document.getElementById('redactor-canvas');
const ctx = canvas.getContext('2d');
let imageBounds = null;
function placeholder() {
ctx.clearRect(0, 0, canvas.width, canvas.height);
ctx.fillStyle = '#f8fafc';
ctx.fillRect(0, 0, canvas.width, canvas.height);
ctx.fillStyle = '#52606d';
ctx.font = '18px Arial';
ctx.fillText('Choose an image to redact it locally.', 230, 132);
}
function blurRect(x, y, width, height) {
ctx.save();
ctx.filter = 'blur(14px)';
ctx.drawImage(canvas, x, y, width, height, x, y, width, height);
ctx.restore();
ctx.fillStyle = 'rgba(47, 133, 90, 0.18)';
ctx.fillRect(x, y, width, height);
}
document.getElementById('redactor-input').addEventListener('change', (event) => {
const [file] = event.target.files;
if (!file) return;
const image = new Image();
image.onload = () => {
const scale = Math.min(canvas.width / image.width, canvas.height / image.height);
const width = image.width * scale;
const height = image.height * scale;
const x = (canvas.width - width) / 2;
const y = (canvas.height - height) / 2;
ctx.clearRect(0, 0, canvas.width, canvas.height);
ctx.drawImage(image, x, y, width, height);
imageBounds = { x, y, width, height };
URL.revokeObjectURL(image.src);
};
image.src = URL.createObjectURL(file);
});
document.getElementById('auto-redact').addEventListener('click', () => {
const bounds = imageBounds || { x: 150, y: 45, width: 420, height: 170 };
blurRect(bounds.x + bounds.width * 0.33, bounds.y + bounds.height * 0.16, bounds.width * 0.28, bounds.height * 0.32);
blurRect(bounds.x + bounds.width * 0.12, bounds.y + bounds.height * 0.68, bounds.width * 0.42, bounds.height * 0.16);
});
document.getElementById('download-redacted').addEventListener('click', () => {
const link = document.createElement('a');
link.download = 'redacted-image.png';
link.href = canvas.toDataURL('image/png');
link.click();
});
placeholder();