feat: ZIP import, rotation, feather slider, lightbox + config déploiement
- Import ZIP produits (HEIC/JPG/PNG, structure dossiers conservée) - Rotation des images ±90° avec aperçu CSS et export canvas - Slider récupération des bords (feather 0–5 px) - Lightbox plein écran (clic miniature, Échap, fond noir) - Fix timeout HEIC 30s → 120s - Fix MIME type blobs JSZip pour heic2any - Dockerfile nginx:alpine + docker-compose.yml pour déploiement Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
@@ -0,0 +1,46 @@
|
||||
/**
|
||||
* Rotation d'un Blob image via Canvas.
|
||||
* @param {Blob} blob — image source (JPEG)
|
||||
* @param {number} degrees — angle de rotation en degrés (0, 90, 180, 270)
|
||||
* @returns {Promise<Blob>} Blob JPEG pivoté, ou le blob original si degrees === 0
|
||||
*/
|
||||
export async function rotateBlob(blob, degrees) {
|
||||
const norm = ((degrees % 360) + 360) % 360;
|
||||
if (norm === 0) return blob;
|
||||
|
||||
const url = URL.createObjectURL(blob);
|
||||
|
||||
return new Promise((resolve, reject) => {
|
||||
const img = new Image();
|
||||
|
||||
img.onload = () => {
|
||||
// Pour 90° ou 270°, largeur et hauteur sont inversées
|
||||
const swap = norm === 90 || norm === 270;
|
||||
const w = swap ? img.naturalHeight : img.naturalWidth;
|
||||
const h = swap ? img.naturalWidth : img.naturalHeight;
|
||||
|
||||
const canvas = document.createElement('canvas');
|
||||
canvas.width = w;
|
||||
canvas.height = h;
|
||||
const ctx = canvas.getContext('2d');
|
||||
|
||||
ctx.translate(w / 2, h / 2);
|
||||
ctx.rotate((norm * Math.PI) / 180);
|
||||
ctx.drawImage(img, -img.naturalWidth / 2, -img.naturalHeight / 2);
|
||||
|
||||
URL.revokeObjectURL(url);
|
||||
canvas.toBlob(
|
||||
b => b ? resolve(b) : reject(new Error('rotateBlob : toBlob a retourné null')),
|
||||
'image/jpeg',
|
||||
0.92
|
||||
);
|
||||
};
|
||||
|
||||
img.onerror = () => {
|
||||
URL.revokeObjectURL(url);
|
||||
reject(new Error('rotateBlob : impossible de charger le blob'));
|
||||
};
|
||||
|
||||
img.src = url;
|
||||
});
|
||||
}
|
||||
Reference in New Issue
Block a user