/** * UiElementRenderer Component * * Unified UI Element Renderer - single source of truth for element rendering. * Used by both CanvasElement (constructor) and RuntimeElement (presentation) * to ensure WYSIWYG consistency. * * Renders any UI element with consistent styling by delegating to per-type components. */ import React from 'react'; import type { CanvasElement } from '../../types/constructor'; import { useElementWrapperStyle } from './shared/useElementWrapperStyle'; import { isNavigationElementType, isTooltipElementType, isDescriptionElementType, isGalleryElementType, isCarouselElementType, isVideoPlayerElementType, isAudioPlayerElementType, isLogoElementType, isSpotElementType, isPopupElementType, } from '../../lib/elementDefaults'; // Import per-type components import NavigationElement from './elements/NavigationElement'; import GalleryElement from './elements/GalleryElement'; import TooltipElement from './elements/TooltipElement'; import DescriptionElement from './elements/DescriptionElement'; import CarouselElement from './elements/CarouselElement'; import LogoElement from './elements/LogoElement'; import SpotElement from './elements/SpotElement'; import VideoPlayerElement from './elements/VideoPlayerElement'; import AudioPlayerElement from './elements/AudioPlayerElement'; import PopupElement from './elements/PopupElement'; export interface UiElementRendererProps { element: CanvasElement; resolveUrl?: (url: string | undefined) => string; // Constructor-specific props (optional) isSelected?: boolean; isEditMode?: boolean; isDisabled?: boolean; // Gallery carousel callback onGalleryCardClick?: (cardIndex: number) => void; } /** * Unified UI Element Renderer * * Renders any UI element with consistent styling. * Used by both CanvasElement (constructor) and RuntimeElement (presentation). */ export const UiElementRenderer: React.FC = ({ element, resolveUrl, isSelected = false, isEditMode = false, isDisabled = false, onGalleryCardClick, }) => { const { className, style } = useElementWrapperStyle({ element, isSelected, isEditMode, isDisabled, }); // Common props for all element types const commonProps = { element, resolveUrl, className, style }; // Delegate to type-specific component if (isNavigationElementType(element.type)) { return ; } if (isGalleryElementType(element.type)) { return ; } if (isTooltipElementType(element.type)) { return ; } if (isDescriptionElementType(element.type)) { return ; } if (isCarouselElementType(element.type)) { return ; } if (isVideoPlayerElementType(element.type)) { return ; } if (isAudioPlayerElementType(element.type)) { return ; } if (isLogoElementType(element.type)) { return ; } if (isSpotElementType(element.type)) { return ; } if (isPopupElementType(element.type)) { return ; } // Fallback for unknown types return (
{element.label || element.type}
); }; export default UiElementRenderer;