Files
site-builder/craft/src/components/layout/Container.tsx
T
shadowdao 65a10a1ef9 refactor(builder): remove dead component settings UI
Each component defined a .craft.related.settings panel that was never
rendered -- the right panel renders only GuidedStyles (per-type
*StylePanel components), never .related.settings. Removed all dead
settings components across every component, their settings-only helpers
(including the dead uploadToWhp/showBrowser/handleBrowse asset-browse
blocks in Logo/Navbar/VideoBlock/FeaturesGrid, and CtasEditor in
_cta-helpers), and dropped the now-empty related keys. Render output,
.craft props/rules, and toHtml statics are unchanged.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
2026-07-12 13:16:53 -07:00

114 lines
3.5 KiB
TypeScript

import React, { CSSProperties } from 'react';
import { useNode, UserComponent } from '@craftjs/core';
import { cssPropsToString } from '../../utils/style-helpers';
import { escapeAttr } from '../../utils/escape';
interface ContainerProps {
style?: CSSProperties;
tag?: 'div' | 'section' | 'article' | 'header' | 'footer' | 'main';
children?: React.ReactNode;
cssId?: string;
cssClass?: string;
anchorId?: string;
hideOnDesktop?: boolean;
hideOnTablet?: boolean;
hideOnMobile?: boolean;
animation?: string;
animationDelay?: string;
fullWidth?: boolean;
contentWidth?: 'boxed' | 'full';
}
// Map textAlign to a flex alignItems value so block-level children (images,
// columns, sections) align horizontally — textAlign alone only affects inline
// content. Returns undefined when no alignment is set so we leave layout as
// normal block flow.
const flexAlignFromTextAlign = (textAlign: CSSProperties['textAlign']): CSSProperties => {
if (textAlign === 'center') return { display: 'flex', flexDirection: 'column', alignItems: 'center' };
if (textAlign === 'right') return { display: 'flex', flexDirection: 'column', alignItems: 'flex-end' };
if (textAlign === 'left') return { display: 'flex', flexDirection: 'column', alignItems: 'flex-start' };
return {};
};
export const Container: UserComponent<ContainerProps> = ({
style = {},
tag = 'div',
children,
fullWidth = false,
contentWidth = 'full',
anchorId,
}) => {
const { connectors: { connect, drag } } = useNode();
const needsBoxedWrapper = contentWidth === 'boxed';
const flexStyles = flexAlignFromTextAlign(style.textAlign);
const outerStyle: CSSProperties = {
minHeight: '40px',
...style,
...(fullWidth ? { width: '100vw', marginLeft: 'calc(-50vw + 50%)' } : {}),
...(needsBoxedWrapper ? {} : flexStyles),
};
const el = React.createElement(
tag,
{
ref: (ref: HTMLElement | null): void => { if (ref) connect(drag(ref)); },
style: outerStyle,
'data-craft-container': 'true',
id: anchorId || undefined,
},
needsBoxedWrapper
? React.createElement('div', { style: { maxWidth: '1200px', margin: '0 auto', ...flexStyles } }, children)
: children,
);
return el;
};
/* ---------- Craft config ---------- */
Container.craft = {
displayName: 'Container',
props: {
style: { padding: '20px', minHeight: '100px' },
tag: 'div',
fullWidth: false,
contentWidth: 'full',
anchorId: '',
},
rules: {
canDrag: () => true,
canMoveIn: () => true,
canMoveOut: () => true,
},
};
/* ---------- HTML export ---------- */
(Container as any).toHtml = (props: ContainerProps, childrenHtml: string) => {
const tag = props.tag || 'div';
const isBoxed = props.contentWidth === 'boxed';
const flexStyles = flexAlignFromTextAlign(props.style?.textAlign);
const outerCss: CSSProperties = {
...props.style,
...(isBoxed ? {} : flexStyles),
};
if (props.fullWidth) {
outerCss.width = '100vw';
outerCss.marginLeft = 'calc(-50vw + 50%)';
}
const styleStr = cssPropsToString(outerCss);
const idAttr = props.anchorId ? ` id="${escapeAttr(props.anchorId)}"` : '';
if (isBoxed) {
const innerStyle = cssPropsToString({ maxWidth: '1200px', margin: '0 auto', ...flexStyles });
return { html: `<${tag}${idAttr}${styleStr ? ` style="${styleStr}"` : ''}><div${innerStyle ? ` style="${innerStyle}"` : ''}>${childrenHtml}</div></${tag}>` };
}
return { html: `<${tag}${idAttr}${styleStr ? ` style="${styleStr}"` : ''}>${childrenHtml}</${tag}>` };
};