diff --git a/src/PrerenderProduct.js b/src/PrerenderProduct.js index f6baa2e..e80afdc 100644 --- a/src/PrerenderProduct.js +++ b/src/PrerenderProduct.js @@ -90,178 +90,322 @@ class PrerenderProduct extends React.Component { flexGrow: 1 } }, + // Back button (breadcrumbs section) React.createElement( Box, { sx: { + mb: 2, + position: ["-webkit-sticky", "sticky"], + top: { + xs: "80px", + sm: "80px", + md: "80px", + lg: "80px", + }, + left: 0, + width: "100%", display: "flex", - flexDirection: { xs: "column", md: "row" }, - gap: 4, - background: "#fff", - borderRadius: 2, - boxShadow: "0 2px 8px rgba(0,0,0,0.08)", + zIndex: 999, // Just below the AppBar + py: 0, + px: 2, } }, - // Product Image Section React.createElement( Box, { sx: { - width: { xs: "100%", sm: "555px" }, - maxWidth: "100%", - minHeight: "400px", - background: "#f8f8f8", - display: "flex", - flexDirection: "column", - alignItems: "center", - justifyContent: "center", + ml: { xs: 0, md: 0 }, + display: "inline-flex", + px: 0, + py: 1, + backgroundColor: "#2e7d32", // primary dark green + borderRadius: 1, } }, - React.createElement( - CardMedia, - { - component: 'img', - height: '400', - image: mainImage, - alt: product.name, - sx: { objectFit: 'contain', p: 2 } - } - ) - ), - // Product Details Section - React.createElement( - Box, - { - sx: { - flex: "1 1 60%", - p: { xs: 2, md: 4 }, - display: "flex", - flexDirection: "column", - } - }, - // Product identifiers - React.createElement( - Box, - { sx: { mb: 1 } }, - React.createElement( - Typography, - { variant: 'body2', color: 'text.secondary' }, - (this.props.t ? this.props.t('product.articleNumber') : 'Artikelnummer')+': '+product.articleNumber+' '+(product.gtin ? ` | GTIN: ${product.gtin}` : "") - ) - ), - // Product title React.createElement( Typography, - { - variant: 'h4', - component: 'h1', - gutterBottom: true, - sx: { fontWeight: 600, color: "#333" } - }, - cleanProductName(product.name) - ), - // Manufacturer if available - product.manufacturer && React.createElement( - Box, - { sx: { display: "flex", alignItems: "center", mb: 2 } }, + { variant: "body2", color: "text.secondary" }, React.createElement( - Typography, - { variant: 'body2', sx: { fontStyle: "italic" } }, - (this.props.t ? this.props.t('product.manufacturer') : 'Hersteller')+': '+product.manufacturer - ) - ), - // Product specifications (attributes) - attributes.length > 0 && React.createElement( - Box, - { sx: { mb: 2 } }, - React.createElement( - Stack, - { direction: 'row', spacing: 1, flexWrap: 'wrap', gap: 1 }, - ...attributes.map((attr, index) => - React.createElement( - Chip, - { - key: index, - label: `${attr.cName}: ${attr.cWert}`, - disabled: true, - sx: { mb: 1 } - } - ) - ) - ) - ), - // Weight - product.weight && product.weight > 0 && React.createElement( - Box, - { sx: { mb: 2 } }, - React.createElement( - Typography, - { variant: 'body2', color: 'text.secondary' }, - (this.props.t ? this.props.t('product.weight', { weight: product.weight.toFixed(1).replace(".", ",") }) : `Gewicht: ${product.weight.toFixed(1).replace(".", ",")} kg`) - ) - ), - // Price and availability section - React.createElement( - Box, - { - sx: { - mt: "auto", - p: 3, - background: "#f9f9f9", - borderRadius: 2, - } - }, - React.createElement( - Box, + 'a', { - sx: { - display: "flex", - flexDirection: { xs: "column", sm: "row" }, - justifyContent: "space-between", - alignItems: { xs: "flex-start", sm: "flex-start" }, - gap: 2, + href: "#", + onClick: (e) => { + e.preventDefault(); + if (window.history.length > 1) { + window.history.back(); + } else { + window.location.href = '/'; + } + }, + style: { + paddingLeft: 16, + paddingRight: 16, + paddingTop: 8, + paddingBottom: 8, + textDecoration: "none", + color: "#fff", + fontWeight: "bold", + cursor: "pointer" } }, - React.createElement( - Box, - null, - React.createElement( - Typography, - { - variant: "h4", - color: "primary", - sx: { fontWeight: "bold" } - }, - priceWithTax - ), - product.vat && React.createElement( - Typography, - { variant: 'body2', color: 'text.secondary' }, - (this.props.t ? this.props.t('product.inclVat', { vat: product.vat }) : `inkl. ${product.vat}% MwSt.`) - ), - product.versandklasse && - product.versandklasse != "standard" && - product.versandklasse != "kostenlos" && React.createElement( - Typography, - { variant: 'body2', color: 'text.secondary' }, - product.versandklasse - ), - React.createElement( - Typography, - { - variant: 'body1', - color: product.available ? 'success.main' : 'error.main', - fontWeight: 'medium', - sx: { mt: 1 } - }, - product.available ? '✅ Verfügbar' : '❌ Nicht verfügbar' - ) - ) + this.props.t ? this.props.t('common.back') : 'Zurück' ) ) ) ), - // Product full description + React.createElement( + Box, + { + sx: { + display: "flex", + flexDirection: { xs: "column", md: "row" }, + gap: 4, + background: "#fff", + borderRadius: 2, + boxShadow: "0 2px 8px rgba(0,0,0,0.08)", + } + }, + // Product Image Section + React.createElement( + Box, + { + sx: { + width: { xs: "100%", sm: "555px" }, + maxWidth: "100%", + minHeight: "400px", + height: "400px", // Fixed height to prevent shifts + background: "#f8f8f8", + display: "flex", + flexDirection: "column", + alignItems: "center", + justifyContent: "center", + } + }, + React.createElement( + CardMedia, + { + component: 'img', + height: '400', + image: mainImage, + alt: product.name, + sx: { + objectFit: 'contain', + p: 2, + width: '100%', + maxWidth: '100%' + } + } + ) + ), + // Product Details Section + React.createElement( + Box, + { + sx: { + flex: "1 1 60%", + p: { xs: 2, md: 4 }, + display: "flex", + flexDirection: "column", + minHeight: "400px", // Ensure consistent minimum height + } + }, + // Product identifiers - fixed height to prevent shifts + React.createElement( + Box, + { sx: { mb: 1, minHeight: "24px" } }, + React.createElement( + Typography, + { variant: 'body2', color: 'text.secondary' }, + (this.props.t ? this.props.t('product.articleNumber') : 'Artikelnummer')+': '+product.articleNumber+' '+(product.gtin ? ` | GTIN: ${product.gtin}` : "") + ) + ), + // Product title - reserve space for 2 lines + React.createElement( + Box, + { sx: { mb: 2, minHeight: "72px" } }, + React.createElement( + Typography, + { + variant: 'h4', + component: 'h1', + sx: { + fontWeight: 600, + color: "#333", + display: '-webkit-box', + WebkitLineClamp: 2, + WebkitBoxOrient: 'vertical', + overflow: 'hidden', + lineHeight: 1.2 + } + }, + cleanProductName(product.name) + ) + ), + // Manufacturer if available - fixed height placeholder + React.createElement( + Box, + { sx: { display: "flex", alignItems: "center", mb: 2, minHeight: "28px" } }, + product.manufacturer && React.createElement( + Typography, + { variant: 'body2', sx: { fontStyle: "italic" } }, + (this.props.t ? this.props.t('product.manufacturer') : 'Hersteller')+': '+product.manufacturer + ) + ), + // Product specifications (attributes) - fixed height container + React.createElement( + Box, + { sx: { mb: 2, minHeight: attributes.length > 0 ? "auto" : "0px" } }, + attributes.length > 0 && React.createElement( + Stack, + { direction: 'row', spacing: 1, flexWrap: 'wrap', gap: 1 }, + ...attributes.map((attr, index) => + React.createElement( + Chip, + { + key: index, + label: `${attr.cName}: ${attr.cWert}`, + disabled: true, + size: "small", + sx: { mb: 1 } + } + ) + ) + ) + ), + // Weight - fixed height placeholder + React.createElement( + Box, + { sx: { mb: 2, minHeight: "28px" } }, + product.weight && product.weight > 0 && React.createElement( + Typography, + { variant: 'body2', color: 'text.secondary' }, + (this.props.t ? this.props.t('product.weight', { weight: product.weight.toFixed(1).replace(".", ",") }) : `Gewicht: ${product.weight.toFixed(1).replace(".", ",")} kg`) + ) + ), + // Price and availability section - positioned at bottom + React.createElement( + Box, + { + sx: { + mt: "auto", + p: 3, + background: "#f9f9f9", + borderRadius: 2, + minHeight: "120px", // Fixed minimum height for price section + } + }, + React.createElement( + Box, + { + sx: { + display: "flex", + flexDirection: { xs: "column", sm: "row" }, + justifyContent: "space-between", + alignItems: { xs: "flex-start", sm: "flex-start" }, + gap: 2, + } + }, + // Left side - Price information + React.createElement( + Box, + { sx: { flex: 1 } }, + React.createElement( + Typography, + { + variant: "h4", + color: "primary", + sx: { fontWeight: "bold", mb: 1 } + }, + priceWithTax + ), + // VAT info with fixed height + React.createElement( + Box, + { sx: { minHeight: "20px", mb: 1 } }, + product.vat && React.createElement( + Typography, + { variant: 'body2', color: 'text.secondary' }, + (this.props.t ? this.props.t('product.inclVat', { vat: product.vat }) : `inkl. ${product.vat}% MwSt.`) + ) + ), + // Shipping class with fixed height + React.createElement( + Box, + { sx: { minHeight: "20px", mb: 1 } }, + product.versandklasse && + product.versandklasse != "standard" && + product.versandklasse != "kostenlos" && React.createElement( + Typography, + { variant: 'body2', color: 'text.secondary' }, + product.versandklasse + ) + ) + ), + // Right side - Cart button area with availability info + React.createElement( + Box, + { + sx: { + display: "flex", + flexDirection: "column", + minWidth: { xs: "100%", sm: "200px" } + } + }, + // Placeholder for AddToCartButton area + React.createElement( + Box, + { + sx: { + minHeight: "48px", + mb: 1, + display: "flex", + alignItems: "center", + justifyContent: "center", + backgroundColor: "#f0f0f0", + borderRadius: 2, + border: "1px dashed #ccc" + } + }, + React.createElement( + Typography, + { + variant: 'body2', + color: 'text.secondary', + sx: { fontStyle: 'italic' } + }, + 'Add to Cart Button' + ) + ), + // Availability and delivery time info (matching ProductDetailPage) + React.createElement( + Typography, + { + variant: 'caption', + sx: { + fontStyle: "italic", + color: "text.secondary", + textAlign: "center", + minHeight: "28px", + display: "flex", + alignItems: "center", + justifyContent: "center" + } + }, + product.id && product.id.toString().endsWith("steckling") ? + (this.props.t ? this.props.t('delivery.times.cutting14Days') : "Lieferzeit: 14 Tage") : + product.available == 1 ? + (this.props.t ? this.props.t('delivery.times.standard2to3Days') : "Lieferzeit: 2-3 Tage") : + product.availableSupplier == 1 ? + (this.props.t ? this.props.t('delivery.times.supplier7to9Days') : "Lieferzeit: 7-9 Tage") : + (product.available ? '✅ Verfügbar' : '❌ Nicht verfügbar') + ) + ) + ) + ) + ) + ), + // Product full description - separate card product.description && React.createElement( Box, { @@ -271,6 +415,7 @@ class PrerenderProduct extends React.Component { background: "#fff", borderRadius: 2, boxShadow: "0 2px 8px rgba(0,0,0,0.08)", + minHeight: "100px" // Minimum height to prevent shifts } }, React.createElement(