UNPKG

@asgerami/zemenay-blog

Version:

Plug-and-play blog system for Next.js - Get a fully functional blog running in minutes with zero configuration

77 lines (76 loc) 4.78 kB
"use strict"; 'use client'; Object.defineProperty(exports, "__esModule", { value: true }); exports.ImageUpload = ImageUpload; exports.ImagePreview = ImagePreview; const jsx_runtime_1 = require("react/jsx-runtime"); const react_1 = require("react"); const imageUpload_1 = require("../lib/imageUpload"); function ImageUpload({ onImageUploaded, onError, className = '', accept = 'image/*', maxSize = 5 }) { const [uploading, setUploading] = (0, react_1.useState)(false); const [dragOver, setDragOver] = (0, react_1.useState)(false); const fileInputRef = (0, react_1.useRef)(null); const handleFileSelect = async (file) => { if (!file) return; // Validate file size if (file.size > maxSize * 1024 * 1024) { const error = `Image must be smaller than ${maxSize}MB`; onError === null || onError === void 0 ? void 0 : onError(error); return; } setUploading(true); try { const result = await (0, imageUpload_1.uploadImage)({ file, altText: file.name.split('.')[0] // Use filename without extension as default alt text }); if (result.success && result.image && result.publicUrl) { onImageUploaded(result.image, result.publicUrl); } else { onError === null || onError === void 0 ? void 0 : onError(result.error || 'Upload failed'); } } catch (error) { onError === null || onError === void 0 ? void 0 : onError(error instanceof Error ? error.message : 'Upload failed'); } finally { setUploading(false); } }; const handleFileInputChange = (event) => { var _a; const file = (_a = event.target.files) === null || _a === void 0 ? void 0 : _a[0]; if (file) { handleFileSelect(file); } }; const handleDrop = (event) => { event.preventDefault(); setDragOver(false); const file = event.dataTransfer.files[0]; if (file && file.type.startsWith('image/')) { handleFileSelect(file); } else { onError === null || onError === void 0 ? void 0 : onError('Please drop an image file'); } }; const handleDragOver = (event) => { event.preventDefault(); setDragOver(true); }; const handleDragLeave = (event) => { event.preventDefault(); setDragOver(false); }; const openFileDialog = () => { var _a; (_a = fileInputRef.current) === null || _a === void 0 ? void 0 : _a.click(); }; return ((0, jsx_runtime_1.jsxs)("div", { className: `image-upload ${className}`, children: [(0, jsx_runtime_1.jsx)("input", { ref: fileInputRef, type: "file", accept: accept, onChange: handleFileInputChange, style: { display: 'none' } }), (0, jsx_runtime_1.jsx)("div", { className: `upload-area ${dragOver ? 'drag-over' : ''} ${uploading ? 'uploading' : ''}`, onDrop: handleDrop, onDragOver: handleDragOver, onDragLeave: handleDragLeave, onClick: openFileDialog, children: uploading ? ((0, jsx_runtime_1.jsxs)("div", { className: "upload-progress", children: [(0, jsx_runtime_1.jsx)("div", { className: "spinner" }), (0, jsx_runtime_1.jsx)("p", { children: "Uploading image..." })] })) : ((0, jsx_runtime_1.jsxs)("div", { className: "upload-prompt", children: [(0, jsx_runtime_1.jsx)("div", { className: "upload-icon", children: "\uD83D\uDCF7" }), (0, jsx_runtime_1.jsxs)("p", { children: [(0, jsx_runtime_1.jsx)("strong", { children: "Click to upload" }), " or drag and drop"] }), (0, jsx_runtime_1.jsxs)("p", { className: "upload-hint", children: ["PNG, JPG, GIF up to ", maxSize, "MB"] })] })) })] })); } function ImagePreview({ image, publicUrl, onRemove, onInsert, className = '' }) { return ((0, jsx_runtime_1.jsxs)("div", { className: `image-preview ${className}`, children: [(0, jsx_runtime_1.jsx)("div", { className: "preview-image", children: (0, jsx_runtime_1.jsx)("img", { src: publicUrl, alt: image.alt_text || image.original_name, loading: "lazy" }) }), (0, jsx_runtime_1.jsxs)("div", { className: "preview-info", children: [(0, jsx_runtime_1.jsx)("p", { className: "image-name", children: image.original_name }), (0, jsx_runtime_1.jsxs)("p", { className: "image-size", children: [(image.file_size / 1024).toFixed(1), " KB"] })] }), (0, jsx_runtime_1.jsxs)("div", { className: "preview-actions", children: [onInsert && ((0, jsx_runtime_1.jsx)("button", { type: "button", onClick: onInsert, className: "insert-btn", children: "Insert" })), onRemove && ((0, jsx_runtime_1.jsx)("button", { type: "button", onClick: onRemove, className: "remove-btn", children: "Remove" }))] })] })); }