migration wip
This commit is contained in:
2
.next/cache/.tsbuildinfo
vendored
2
.next/cache/.tsbuildinfo
vendored
File diff suppressed because one or more lines are too long
BIN
.next/cache/webpack/client-production/0.pack
vendored
BIN
.next/cache/webpack/client-production/0.pack
vendored
Binary file not shown.
BIN
.next/cache/webpack/client-production/1.pack
vendored
BIN
.next/cache/webpack/client-production/1.pack
vendored
Binary file not shown.
BIN
.next/cache/webpack/client-production/2.pack
vendored
BIN
.next/cache/webpack/client-production/2.pack
vendored
Binary file not shown.
BIN
.next/cache/webpack/client-production/3.pack
vendored
BIN
.next/cache/webpack/client-production/3.pack
vendored
Binary file not shown.
BIN
.next/cache/webpack/client-production/4.pack
vendored
BIN
.next/cache/webpack/client-production/4.pack
vendored
Binary file not shown.
BIN
.next/cache/webpack/client-production/5.pack
vendored
BIN
.next/cache/webpack/client-production/5.pack
vendored
Binary file not shown.
BIN
.next/cache/webpack/client-production/6.pack
vendored
BIN
.next/cache/webpack/client-production/6.pack
vendored
Binary file not shown.
BIN
.next/cache/webpack/client-production/index.pack
vendored
BIN
.next/cache/webpack/client-production/index.pack
vendored
Binary file not shown.
BIN
.next/cache/webpack/client-production/index.pack.old
vendored
BIN
.next/cache/webpack/client-production/index.pack.old
vendored
Binary file not shown.
BIN
.next/cache/webpack/server-development/0.pack.gz
vendored
BIN
.next/cache/webpack/server-development/0.pack.gz
vendored
Binary file not shown.
BIN
.next/cache/webpack/server-development/1.pack.gz
vendored
BIN
.next/cache/webpack/server-development/1.pack.gz
vendored
Binary file not shown.
BIN
.next/cache/webpack/server-development/index.pack.gz
vendored
BIN
.next/cache/webpack/server-development/index.pack.gz
vendored
Binary file not shown.
Binary file not shown.
BIN
.next/cache/webpack/server-production/0.pack
vendored
BIN
.next/cache/webpack/server-production/0.pack
vendored
Binary file not shown.
BIN
.next/cache/webpack/server-production/1.pack
vendored
BIN
.next/cache/webpack/server-production/1.pack
vendored
Binary file not shown.
BIN
.next/cache/webpack/server-production/2.pack
vendored
BIN
.next/cache/webpack/server-production/2.pack
vendored
Binary file not shown.
BIN
.next/cache/webpack/server-production/3.pack
vendored
BIN
.next/cache/webpack/server-production/3.pack
vendored
Binary file not shown.
BIN
.next/cache/webpack/server-production/4.pack
vendored
BIN
.next/cache/webpack/server-production/4.pack
vendored
Binary file not shown.
BIN
.next/cache/webpack/server-production/index.pack
vendored
BIN
.next/cache/webpack/server-production/index.pack
vendored
Binary file not shown.
BIN
.next/cache/webpack/server-production/index.pack.old
vendored
BIN
.next/cache/webpack/server-production/index.pack.old
vendored
Binary file not shown.
File diff suppressed because one or more lines are too long
@@ -18,7 +18,7 @@
|
|||||||
"assets": [],
|
"assets": [],
|
||||||
"env": {
|
"env": {
|
||||||
"__NEXT_BUILD_ID": "development",
|
"__NEXT_BUILD_ID": "development",
|
||||||
"NEXT_SERVER_ACTIONS_ENCRYPTION_KEY": "FV9R3duv3e6hZD53ocfPgBrQwGX7rHfUyZRgkqwqFtk="
|
"NEXT_SERVER_ACTIONS_ENCRYPTION_KEY": "0R3AeKRiCnSumpEO3wgP/k8sKq7OCUs1SBp+q3dmhMw="
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|||||||
@@ -1,5 +1,5 @@
|
|||||||
{
|
{
|
||||||
"node": {},
|
"node": {},
|
||||||
"edge": {},
|
"edge": {},
|
||||||
"encryptionKey": "FV9R3duv3e6hZD53ocfPgBrQwGX7rHfUyZRgkqwqFtk="
|
"encryptionKey": "0R3AeKRiCnSumpEO3wgP/k8sKq7OCUs1SBp+q3dmhMw="
|
||||||
}
|
}
|
||||||
@@ -125,7 +125,7 @@
|
|||||||
/******/
|
/******/
|
||||||
/******/ /* webpack/runtime/getFullHash */
|
/******/ /* webpack/runtime/getFullHash */
|
||||||
/******/ (() => {
|
/******/ (() => {
|
||||||
/******/ __webpack_require__.h = () => ("f11be5ba913d1b5f")
|
/******/ __webpack_require__.h = () => ("c80591bbb933a4a4")
|
||||||
/******/ })();
|
/******/ })();
|
||||||
/******/
|
/******/
|
||||||
/******/ /* webpack/runtime/hasOwnProperty shorthand */
|
/******/ /* webpack/runtime/hasOwnProperty shorthand */
|
||||||
|
|||||||
18
.next/trace
18
.next/trace
File diff suppressed because one or more lines are too long
@@ -7,6 +7,7 @@ import { getLocalizedPath } from '@/lib/i18n';
|
|||||||
import { t } from '@/lib/i18n';
|
import { t } from '@/lib/i18n';
|
||||||
import { SEO } from '@/components/SEO';
|
import { SEO } from '@/components/SEO';
|
||||||
import { LocaleSwitcher } from '@/components/LocaleSwitcher';
|
import { LocaleSwitcher } from '@/components/LocaleSwitcher';
|
||||||
|
import { ContentRenderer } from '@/components/content/ContentRenderer';
|
||||||
|
|
||||||
interface PageProps {
|
interface PageProps {
|
||||||
params: {
|
params: {
|
||||||
@@ -211,10 +212,12 @@ export default async function BlogDetailPage({ params }: PageProps) {
|
|||||||
})()}
|
})()}
|
||||||
|
|
||||||
{/* Article Content */}
|
{/* Article Content */}
|
||||||
<div
|
<div className="mb-12">
|
||||||
className="prose prose-lg prose-blue max-w-none mb-12"
|
<ContentRenderer
|
||||||
dangerouslySetInnerHTML={{ __html: processedContent }}
|
content={post.contentHtml}
|
||||||
/>
|
className="prose prose-lg prose-blue"
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
|
|
||||||
{/* Article Footer */}
|
{/* Article Footer */}
|
||||||
<footer className="border-t border-gray-200 pt-8 mt-12">
|
<footer className="border-t border-gray-200 pt-8 mt-12">
|
||||||
|
|||||||
@@ -4,7 +4,7 @@ import { getPostsByLocale, getCategoriesByLocale, getMediaById } from '@/lib/dat
|
|||||||
import { getSiteInfo, t, getLocalizedPath } from '@/lib/i18n';
|
import { getSiteInfo, t, getLocalizedPath } from '@/lib/i18n';
|
||||||
import { SEO } from '@/components/SEO';
|
import { SEO } from '@/components/SEO';
|
||||||
import { LocaleSwitcher } from '@/components/LocaleSwitcher';
|
import { LocaleSwitcher } from '@/components/LocaleSwitcher';
|
||||||
import { processHTML } from '@/lib/html-compat';
|
import { ContentRenderer } from '@/components/content/ContentRenderer';
|
||||||
|
|
||||||
interface PageProps {
|
interface PageProps {
|
||||||
params: {
|
params: {
|
||||||
@@ -140,10 +140,12 @@ export default async function BlogPage({ params }: PageProps) {
|
|||||||
{post.title}
|
{post.title}
|
||||||
</Link>
|
</Link>
|
||||||
</h3>
|
</h3>
|
||||||
<div
|
<div className="text-gray-600 line-clamp-3 text-sm mb-4">
|
||||||
className="text-gray-600 line-clamp-3 text-sm mb-4"
|
<ContentRenderer
|
||||||
dangerouslySetInnerHTML={{ __html: processHTML(post.excerptHtml) }}
|
content={post.excerptHtml}
|
||||||
/>
|
className="text-gray-600 line-clamp-3 text-sm"
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
<Link
|
<Link
|
||||||
href={getLocalizedPath(`/blog/${post.slug}`, locale as 'en' | 'de')}
|
href={getLocalizedPath(`/blog/${post.slug}`, locale as 'en' | 'de')}
|
||||||
className="inline-flex items-center text-sm font-medium text-blue-600 hover:text-blue-700"
|
className="inline-flex items-center text-sm font-medium text-blue-600 hover:text-blue-700"
|
||||||
@@ -205,10 +207,12 @@ export default async function BlogPage({ params }: PageProps) {
|
|||||||
{post.title}
|
{post.title}
|
||||||
</Link>
|
</Link>
|
||||||
</h3>
|
</h3>
|
||||||
<div
|
<div className="text-gray-600 mb-3">
|
||||||
className="text-gray-600 mb-3"
|
<ContentRenderer
|
||||||
dangerouslySetInnerHTML={{ __html: processHTML(post.excerptHtml) }}
|
content={post.excerptHtml}
|
||||||
/>
|
className="text-gray-600 mb-3"
|
||||||
|
/>
|
||||||
|
</div>
|
||||||
<Link
|
<Link
|
||||||
href={getLocalizedPath(`/blog/${post.slug}`, locale as 'en' | 'de')}
|
href={getLocalizedPath(`/blog/${post.slug}`, locale as 'en' | 'de')}
|
||||||
className="inline-flex items-center text-sm font-medium text-blue-600 hover:text-blue-700"
|
className="inline-flex items-center text-sm font-medium text-blue-600 hover:text-blue-700"
|
||||||
|
|||||||
@@ -9,6 +9,7 @@ import { ResponsiveSection, ResponsiveWrapper, ResponsiveGrid } from '@/componen
|
|||||||
import { FeaturedImage } from '@/components/content/FeaturedImage';
|
import { FeaturedImage } from '@/components/content/FeaturedImage';
|
||||||
import { Container } from '@/components/ui/Container';
|
import { Container } from '@/components/ui/Container';
|
||||||
import { Button } from '@/components/ui/Button';
|
import { Button } from '@/components/ui/Button';
|
||||||
|
import { ContentRenderer } from '@/components/content/ContentRenderer';
|
||||||
|
|
||||||
interface PageProps {
|
interface PageProps {
|
||||||
params: {
|
params: {
|
||||||
@@ -117,9 +118,9 @@ export default async function Page({ params }: PageProps) {
|
|||||||
{page.title}
|
{page.title}
|
||||||
</h1>
|
</h1>
|
||||||
{page.excerptHtml && (
|
{page.excerptHtml && (
|
||||||
<div
|
<ContentRenderer
|
||||||
|
content={page.excerptHtml}
|
||||||
className="text-lg sm:text-xl text-gray-600 leading-relaxed"
|
className="text-lg sm:text-xl text-gray-600 leading-relaxed"
|
||||||
dangerouslySetInnerHTML={{ __html: processHTML(page.excerptHtml) }}
|
|
||||||
/>
|
/>
|
||||||
)}
|
)}
|
||||||
</ResponsiveWrapper>
|
</ResponsiveWrapper>
|
||||||
@@ -127,9 +128,9 @@ export default async function Page({ params }: PageProps) {
|
|||||||
|
|
||||||
{processedContent && (
|
{processedContent && (
|
||||||
<ResponsiveWrapper className="bg-white rounded-lg shadow-sm p-6 sm:p-8" container={true} maxWidth="full">
|
<ResponsiveWrapper className="bg-white rounded-lg shadow-sm p-6 sm:p-8" container={true} maxWidth="full">
|
||||||
<div
|
<ContentRenderer
|
||||||
|
content={contentToDisplay || ''}
|
||||||
className="prose prose-lg max-w-none"
|
className="prose prose-lg max-w-none"
|
||||||
dangerouslySetInnerHTML={{ __html: processedContent }}
|
|
||||||
/>
|
/>
|
||||||
</ResponsiveWrapper>
|
</ResponsiveWrapper>
|
||||||
)}
|
)}
|
||||||
|
|||||||
@@ -2,6 +2,7 @@ import { notFound } from 'next/navigation'
|
|||||||
import { getAllCategories, getProductsByCategory } from '@/lib/data'
|
import { getAllCategories, getProductsByCategory } from '@/lib/data'
|
||||||
import { ProductList } from '@/components/ProductList'
|
import { ProductList } from '@/components/ProductList'
|
||||||
import { Metadata } from 'next'
|
import { Metadata } from 'next'
|
||||||
|
import { ContentRenderer } from '@/components/content/ContentRenderer'
|
||||||
|
|
||||||
interface PageProps {
|
interface PageProps {
|
||||||
params: {
|
params: {
|
||||||
@@ -48,9 +49,9 @@ export default async function ProductCategoryPage({ params }: PageProps) {
|
|||||||
<div className="container mx-auto px-4 py-8">
|
<div className="container mx-auto px-4 py-8">
|
||||||
<h1 className="text-4xl font-bold mb-6">{category.name}</h1>
|
<h1 className="text-4xl font-bold mb-6">{category.name}</h1>
|
||||||
{category.description && (
|
{category.description && (
|
||||||
<div
|
<ContentRenderer
|
||||||
|
content={category.description}
|
||||||
className="mb-8 prose max-w-none"
|
className="mb-8 prose max-w-none"
|
||||||
dangerouslySetInnerHTML={{ __html: category.description }}
|
|
||||||
/>
|
/>
|
||||||
)}
|
)}
|
||||||
|
|
||||||
|
|||||||
@@ -6,6 +6,7 @@ import { getSiteInfo, t, getLocaleFromPath, getLocalizedPath } from '@/lib/i18n'
|
|||||||
import { processHTML } from '@/lib/html-compat';
|
import { processHTML } from '@/lib/html-compat';
|
||||||
import { SEO } from '@/components/SEO';
|
import { SEO } from '@/components/SEO';
|
||||||
import { LocaleSwitcher } from '@/components/LocaleSwitcher';
|
import { LocaleSwitcher } from '@/components/LocaleSwitcher';
|
||||||
|
import { ContentRenderer } from '@/components/content/ContentRenderer';
|
||||||
|
|
||||||
interface PageProps {
|
interface PageProps {
|
||||||
params: {
|
params: {
|
||||||
@@ -187,9 +188,9 @@ export default async function ProductDetailPage({ params }: PageProps) {
|
|||||||
<h3 className="text-sm font-medium text-gray-900 mb-3">
|
<h3 className="text-sm font-medium text-gray-900 mb-3">
|
||||||
{t('products.description', locale as 'en' | 'de')}
|
{t('products.description', locale as 'en' | 'de')}
|
||||||
</h3>
|
</h3>
|
||||||
<div
|
<ContentRenderer
|
||||||
|
content={product.descriptionHtml || ''}
|
||||||
className="prose prose-sm max-w-none text-gray-600"
|
className="prose prose-sm max-w-none text-gray-600"
|
||||||
dangerouslySetInnerHTML={{ __html: processedDescription }}
|
|
||||||
/>
|
/>
|
||||||
</div>
|
</div>
|
||||||
)}
|
)}
|
||||||
|
|||||||
@@ -89,8 +89,16 @@ export const ContentRenderer: React.FC<ContentRendererProps> = ({
|
|||||||
/**
|
/**
|
||||||
* Parse HTML string to React elements
|
* Parse HTML string to React elements
|
||||||
* This is a safe parser that only allows specific tags and attributes
|
* This is a safe parser that only allows specific tags and attributes
|
||||||
|
* Works in both server and client environments
|
||||||
*/
|
*/
|
||||||
function parseHTMLToReact(html: string): React.ReactNode {
|
function parseHTMLToReact(html: string): React.ReactNode {
|
||||||
|
// For server-side rendering, use a simple approach with dangerouslySetInnerHTML
|
||||||
|
// The HTML has already been sanitized by processHTML, so it's safe
|
||||||
|
if (typeof window === 'undefined') {
|
||||||
|
return <div dangerouslySetInnerHTML={{ __html: html }} />;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Client-side: use DOMParser for proper parsing
|
||||||
// Define allowed tags and their properties
|
// Define allowed tags and their properties
|
||||||
const allowedTags = {
|
const allowedTags = {
|
||||||
div: ['className', 'id', 'style'],
|
div: ['className', 'id', 'style'],
|
||||||
|
|||||||
@@ -113,8 +113,8 @@ function sanitizeHTML(html: string): string {
|
|||||||
// Remove dangerous attributes
|
// Remove dangerous attributes
|
||||||
processed = processed.replace(/\s+(href|src)\s*=\s*["']\s*javascript:/gi, '');
|
processed = processed.replace(/\s+(href|src)\s*=\s*["']\s*javascript:/gi, '');
|
||||||
|
|
||||||
// Remove any remaining WordPress shortcode-like content (e.g., [vc_row...])
|
// Note: Shortcode removal is handled in processShortcodes function
|
||||||
processed = processed.replace(/\[[^\]]*\]/g, '');
|
// Don't remove shortcodes here as they need to be processed first
|
||||||
|
|
||||||
// Allow safe HTML tags
|
// Allow safe HTML tags
|
||||||
const allowedTags = [
|
const allowedTags = [
|
||||||
@@ -170,23 +170,72 @@ function processVcRowShortcodes(html: string): string {
|
|||||||
const bgImage = extractAttribute(attrs, 'bg_image');
|
const bgImage = extractAttribute(attrs, 'bg_image');
|
||||||
const bgColor = extractAttribute(attrs, 'bg_color');
|
const bgColor = extractAttribute(attrs, 'bg_color');
|
||||||
const colorOverlay = extractAttribute(attrs, 'color_overlay');
|
const colorOverlay = extractAttribute(attrs, 'color_overlay');
|
||||||
|
const colorOverlay2 = extractAttribute(attrs, 'color_overlay_2');
|
||||||
const overlayStrength = extractAttribute(attrs, 'overlay_strength');
|
const overlayStrength = extractAttribute(attrs, 'overlay_strength');
|
||||||
const enableGradient = extractAttribute(attrs, 'enable_gradient');
|
const enableGradient = extractAttribute(attrs, 'enable_gradient');
|
||||||
const gradientDirection = extractAttribute(attrs, 'gradient_direction');
|
const gradientDirection = extractAttribute(attrs, 'gradient_direction');
|
||||||
const topPadding = extractAttribute(attrs, 'top_padding');
|
const topPadding = extractAttribute(attrs, 'top_padding');
|
||||||
const bottomPadding = extractAttribute(attrs, 'bottom_padding');
|
const bottomPadding = extractAttribute(attrs, 'bottom_padding');
|
||||||
const fullScreen = extractAttribute(attrs, 'full_screen_row_position');
|
const fullScreen = extractAttribute(attrs, 'full_screen_row_position');
|
||||||
|
const videoBg = extractAttribute(attrs, 'video_bg');
|
||||||
|
const videoMp4 = extractAttribute(attrs, 'video_mp4');
|
||||||
|
const videoWebm = extractAttribute(attrs, 'video_webm');
|
||||||
|
const textAlign = extractAttribute(attrs, 'text_align');
|
||||||
|
const textColor = extractAttribute(attrs, 'text_color');
|
||||||
|
const overflow = extractAttribute(attrs, 'overflow');
|
||||||
|
const equalHeight = extractAttribute(attrs, 'equal_height');
|
||||||
|
const contentPlacement = extractAttribute(attrs, 'content_placement');
|
||||||
|
const columnDirection = extractAttribute(attrs, 'column_direction');
|
||||||
|
const rowBorderRadius = extractAttribute(attrs, 'row_border_radius');
|
||||||
|
const rowBorderRadiusApplies = extractAttribute(attrs, 'row_border_radius_applies');
|
||||||
|
|
||||||
// Build style string
|
// Build style string
|
||||||
let style = '';
|
let style = '';
|
||||||
let wrapperClasses = [...classes];
|
let wrapperClasses = [...classes];
|
||||||
|
|
||||||
|
// Handle text alignment
|
||||||
|
if (textAlign === 'center') wrapperClasses.push('text-center');
|
||||||
|
if (textAlign === 'right') wrapperClasses.push('text-right');
|
||||||
|
if (textAlign === 'left') wrapperClasses.push('text-left');
|
||||||
|
|
||||||
|
// Handle text color
|
||||||
|
if (textColor === 'light') wrapperClasses.push('text-white');
|
||||||
|
|
||||||
|
// Handle overflow
|
||||||
|
if (overflow === 'visible') wrapperClasses.push('overflow-visible');
|
||||||
|
|
||||||
|
// Handle equal height
|
||||||
|
if (equalHeight === 'yes') {
|
||||||
|
wrapperClasses.push('items-stretch');
|
||||||
|
wrapperClasses.push('flex');
|
||||||
|
}
|
||||||
|
|
||||||
|
// Handle content placement
|
||||||
|
if (contentPlacement === 'bottom') wrapperClasses.push('justify-end');
|
||||||
|
if (contentPlacement === 'middle') wrapperClasses.push('justify-center');
|
||||||
|
|
||||||
|
// Handle column direction
|
||||||
|
if (columnDirection === 'column') wrapperClasses.push('flex-col');
|
||||||
|
|
||||||
|
// Handle border radius
|
||||||
|
if (rowBorderRadius === 'none' && rowBorderRadiusApplies === 'bg') {
|
||||||
|
wrapperClasses.push('rounded-none');
|
||||||
|
}
|
||||||
|
|
||||||
// Handle background image
|
// Handle background image
|
||||||
if (bgImage) {
|
if (bgImage) {
|
||||||
style += `background-image: url(/media/${bgImage}.webp); `;
|
// Try to get media by ID first
|
||||||
|
const mediaId = parseInt(bgImage);
|
||||||
|
if (!isNaN(mediaId)) {
|
||||||
|
// This will be handled by ContentRenderer with data attributes
|
||||||
|
wrapperClasses.push('bg-cover', 'bg-center');
|
||||||
|
style += `background-image: url(/media/${bgImage}.webp); `;
|
||||||
|
} else {
|
||||||
|
// Assume it's a direct URL
|
||||||
|
style += `background-image: url(${bgImage}); `;
|
||||||
|
}
|
||||||
style += `background-size: cover; `;
|
style += `background-size: cover; `;
|
||||||
style += `background-position: center; `;
|
style += `background-position: center; `;
|
||||||
wrapperClasses.push('bg-cover', 'bg-center');
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Handle background color
|
// Handle background color
|
||||||
@@ -194,21 +243,63 @@ function processVcRowShortcodes(html: string): string {
|
|||||||
style += `background-color: ${bgColor}; `;
|
style += `background-color: ${bgColor}; `;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Handle color overlay
|
// Handle video background
|
||||||
if (colorOverlay) {
|
if (videoBg === 'use_video' && (videoMp4 || videoWebm)) {
|
||||||
const opacity = overlayStrength ? parseFloat(overlayStrength) : 0.5;
|
// Mark for ContentRenderer to handle
|
||||||
|
wrapperClasses.push('relative', 'overflow-hidden');
|
||||||
|
style += `position: relative; `;
|
||||||
|
|
||||||
|
// Create video background structure
|
||||||
|
const videoAttrs = [];
|
||||||
|
if (videoMp4) videoAttrs.push(`data-video-mp4="${videoMp4}"`);
|
||||||
|
if (videoWebm) videoAttrs.push(`data-video-webm="${videoWebm}"`);
|
||||||
|
videoAttrs.push('data-video-bg="true"');
|
||||||
|
|
||||||
|
return `<div class="${wrapperClasses.join(' ')}" style="${style}" ${videoAttrs.join(' ')}>
|
||||||
|
<div class="relative flex flex-wrap -mx-4 w-full h-full">${content}</div>
|
||||||
|
</div>`;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Handle color overlay (single or gradient)
|
||||||
|
if (colorOverlay || colorOverlay2 || enableGradient === 'true' || enableGradient === '1') {
|
||||||
style += `position: relative; `;
|
style += `position: relative; `;
|
||||||
wrapperClasses.push('relative');
|
wrapperClasses.push('relative');
|
||||||
|
|
||||||
// Create overlay div
|
let overlayStyle = '';
|
||||||
const overlayStyle = `background-color: ${colorOverlay}; opacity: ${opacity};`;
|
if (colorOverlay2 && enableGradient === 'true') {
|
||||||
|
// Gradient overlay
|
||||||
|
const gradientDir = gradientDirection || 'left_to_right';
|
||||||
|
let gradientCSS = '';
|
||||||
|
switch(gradientDir) {
|
||||||
|
case 'left_to_right':
|
||||||
|
gradientCSS = `linear-gradient(to right, ${colorOverlay}, ${colorOverlay2})`;
|
||||||
|
break;
|
||||||
|
case 'right_to_left':
|
||||||
|
gradientCSS = `linear-gradient(to left, ${colorOverlay}, ${colorOverlay2})`;
|
||||||
|
break;
|
||||||
|
case 'top_to_bottom':
|
||||||
|
gradientCSS = `linear-gradient(to bottom, ${colorOverlay}, ${colorOverlay2})`;
|
||||||
|
break;
|
||||||
|
case 'bottom_to_top':
|
||||||
|
gradientCSS = `linear-gradient(to top, ${colorOverlay}, ${colorOverlay2})`;
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
gradientCSS = `linear-gradient(to right, ${colorOverlay}, ${colorOverlay2})`;
|
||||||
|
}
|
||||||
|
overlayStyle = `background: ${gradientCSS}; opacity: 0.32;`;
|
||||||
|
} else if (colorOverlay) {
|
||||||
|
// Solid color overlay
|
||||||
|
const opacity = overlayStrength ? parseFloat(overlayStrength) : 0.5;
|
||||||
|
overlayStyle = `background-color: ${colorOverlay}; opacity: ${opacity};`;
|
||||||
|
}
|
||||||
|
|
||||||
return `<div class="${wrapperClasses.join(' ')}" style="${style}">
|
return `<div class="${wrapperClasses.join(' ')}" style="${style}">
|
||||||
<div class="absolute inset-0" style="${overlayStyle}"></div>
|
<div class="absolute inset-0" style="${overlayStyle}"></div>
|
||||||
<div class="relative flex flex-wrap -mx-4 w-full">${content}</div>
|
<div class="relative flex flex-wrap -mx-4 w-full">${content}</div>
|
||||||
</div>`;
|
</div>`;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Handle gradient
|
// Handle gradient (without overlay)
|
||||||
if (enableGradient === 'true' || enableGradient === '1') {
|
if (enableGradient === 'true' || enableGradient === '1') {
|
||||||
const gradientClass = getGradientClass(gradientDirection);
|
const gradientClass = getGradientClass(gradientDirection);
|
||||||
wrapperClasses.push(gradientClass);
|
wrapperClasses.push(gradientClass);
|
||||||
@@ -216,9 +307,11 @@ function processVcRowShortcodes(html: string): string {
|
|||||||
|
|
||||||
// Handle padding
|
// Handle padding
|
||||||
if (topPadding || bottomPadding) {
|
if (topPadding || bottomPadding) {
|
||||||
|
// Convert percentage values to Tailwind arbitrary values
|
||||||
const pt = topPadding ? `pt-[${topPadding}]` : '';
|
const pt = topPadding ? `pt-[${topPadding}]` : '';
|
||||||
const pb = bottomPadding ? `pb-[${bottomPadding}]` : '';
|
const pb = bottomPadding ? `pb-[${bottomPadding}]` : '';
|
||||||
wrapperClasses.push(pt, pb);
|
if (pt) wrapperClasses.push(pt);
|
||||||
|
if (pb) wrapperClasses.push(pb);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Handle full screen
|
// Handle full screen
|
||||||
|
|||||||
Reference in New Issue
Block a user