83 lines
2.1 KiB
JavaScript
83 lines
2.1 KiB
JavaScript
import { useRef, useState } from 'react';
|
|
import ContentPasteIcon from '@mui/icons-material/ContentPaste';
|
|
import { article } from '../../api';
|
|
import { PanelTile } from '../panels';
|
|
import { requireObject } from '../../utils/apiShape';
|
|
import { prepareArticlePhoto } from '../../utils/prepareArticlePhoto';
|
|
import { pasteImageOrFallback } from '../../utils/pasteImage';
|
|
import { primaryPhoto } from '../../utils/articleDetail';
|
|
import ArticlePhoto from './ArticlePhoto';
|
|
|
|
export default function ArticlePhotoTile({
|
|
article: articleData,
|
|
onArticleUpdated,
|
|
wide = 1,
|
|
minHeight = 0,
|
|
sx,
|
|
tileKey,
|
|
}) {
|
|
const fileInputRef = useRef(null);
|
|
const [busy, setBusy] = useState(false);
|
|
const photo = primaryPhoto(articleData);
|
|
const imageUrl = photo?.url;
|
|
|
|
const uploadRawImage = async (rawBlob) => {
|
|
setBusy(true);
|
|
try {
|
|
const file = await prepareArticlePhoto(rawBlob);
|
|
const res = await article.uploadPhoto(articleData.sku, file);
|
|
requireObject(res, 'POST /api/article/:sku/photos');
|
|
requireObject(res.article, 'article');
|
|
onArticleUpdated?.(res.article);
|
|
} finally {
|
|
setBusy(false);
|
|
}
|
|
};
|
|
|
|
const handlePasteClick = () => {
|
|
if (busy) return;
|
|
void pasteImageOrFallback(() => {
|
|
fileInputRef.current?.click();
|
|
}).then((image) => {
|
|
if (image) void uploadRawImage(image);
|
|
});
|
|
};
|
|
|
|
const handleFileChange = (event) => {
|
|
const file = event.target.files?.[0];
|
|
event.target.value = '';
|
|
if (!file) return;
|
|
void uploadRawImage(file);
|
|
};
|
|
|
|
return (
|
|
<>
|
|
<PanelTile
|
|
wide={wide}
|
|
minHeight={minHeight}
|
|
sx={sx}
|
|
tileKey={tileKey}
|
|
action={
|
|
imageUrl
|
|
? undefined
|
|
: {
|
|
label: 'Bild einfügen',
|
|
icon: ContentPasteIcon,
|
|
onClick: handlePasteClick,
|
|
busy,
|
|
}
|
|
}
|
|
>
|
|
<ArticlePhoto imageUrl={imageUrl} />
|
|
</PanelTile>
|
|
<input
|
|
ref={fileInputRef}
|
|
type="file"
|
|
accept="image/*"
|
|
hidden
|
|
onChange={handleFileChange}
|
|
/>
|
|
</>
|
|
);
|
|
}
|