ldc-ovoteam/resources/ts/front/Components/Theme/ActionSection.tsx

119 lines
3.6 KiB
TypeScript

/** SHADCN */
import { ButtonProps } from "@/components/ui/button";
/** THEME */
import Button from "$/uwil/Button";
import SafeHtml from "@/components/safe-html";
import {
BgColorName,
bgColors,
VerticalPlacementName,
verticalPlacements,
} from "@/front/lib/constants";
import { cn } from "@/lib/utils";
import { CustomButtonVariant, TextProps } from "@/types/front";
type Props = {
/** Button configuration */
button: {
/** Button label */
label: string;
/** Link URL */
href: string;
/** Button vertical placement (top or bottom). Default: bottom */
placement?: VerticalPlacementName;
/** Custom button variant (optional) */
variant?: ButtonProps["variant"] | CustomButtonVariant;
};
/** Background color variant. Default: PRIMARY */
variant?: BgColorName;
/** Text content configuration */
text: TextProps;
};
/**
* ActionSection
*
* A reusable section component displaying a call-to-action with text and a button.
* The button can be positioned either above or below the text.
*
* This component is designed to be flexible and theme-aware through background variants
* and button styles.
*
* @component
*
* @param {Object} props - Component props
* @param {Object} props.button - Button configuration
* @param {string} props.button.label - Text displayed inside the button
* @param {string} props.button.href - URL the button links to
* @param {VerticalPlacementName} [props.button.placement="bottom"] - Vertical position of the button relative to the text ("top" or "bottom")
* @param {ButtonProps["variant"] | CustomButtonVariant} [props.button.variant] - Optional custom button variant (overrides default behavior)
*
* @param {BgColorName} [props.variant=bgColors.PRIMARY] - Background color variant of the section
*
* @param {TextProps} props.text - Text content configuration
* @param {string} props.text.text - HTML string displayed as the main text (rendered using dangerouslySetInnerHTML)
* @param {string} props.text.font - CSS class applied to the text for font styling
*
* @return {JSX.Element} A styled section with text and a call-to-action button
*
* @example
* <ActionSection
* variant={bgColors.SECONDARY}
* text={{
* text: "<strong>Start now</strong> and boost your productivity",
* font: "font-semibold"
* }}
* button={{
* label: "Get Started",
* href: "/signup",
* placement: verticalPlacements.BOTTOM
* }}
* />
*/
export default function ActionSection(props: Readonly<Props>) {
const { button, variant = bgColors.PRIMARY, text } = props;
const placement = button.placement ?? verticalPlacements.BOTTOM;
const btnVariant = variant === bgColors.PRIMARY ? "inverted" : "default";
return (
<div className={cn("text-center py-20", variant)}>
<div className="max-w-7xl mx-auto px-4 md:px-0 space-y-6">
{placement === verticalPlacements.TOP && (
<Button
variant={button.variant ?? btnVariant}
icon={{
icon: "chevron-right",
placement: "right",
}}
link={{
label: button.label,
href: button.href,
}}
/>
)}
<SafeHtml
as="p"
className={cn("text-2xl", text.font)}
html={text.text}
/>
{placement === verticalPlacements.BOTTOM && (
<Button
variant={button.variant ?? btnVariant}
icon={{
icon: "chevron-right",
placement: "right",
}}
link={{
label: button.label,
href: button.href,
}}
/>
)}
</div>
</div>
);
}