@aegov/design-system-react
Version:
A design system for the Government of the United Arab Emirates. Extending the original design system released as @aegov/design-system, this is the package specefically created for the ReactJs enviornment.
111 lines (107 loc) • 5.15 kB
JavaScript
"use strict";
Object.defineProperty(exports, "__esModule", {
value: true
});
exports.default = void 0;
var _react = _interopRequireDefault(require("react"));
var _zod = require("zod");
var _react2 = require("@phosphor-icons/react");
var _tailwindMerge = require("tailwind-merge");
function _interopRequireDefault(e) { return e && e.__esModule ? e : { default: e }; }
function _extends() { return _extends = Object.assign ? Object.assign.bind() : function (n) { for (var e = 1; e < arguments.length; e++) { var t = arguments[e]; for (var r in t) ({}).hasOwnProperty.call(t, r) && (n[r] = t[r]); } return n; }, _extends.apply(null, arguments); }
// Define schemas for validation
const BannerPositionSchema = _zod.z.enum(['top', 'bottom']);
const BannerVariantSchema = _zod.z.enum(['default', 'camel', 'red', 'notice', 'dark']);
const BannerCenteredSchema = _zod.z.boolean();
// Define styles
const variantStyles = {
default: 'bg-slate-50 border-slate-500 text-slate-600',
camel: 'bg-camel-600 border-camel-500 text-camel-50',
red: 'bg-aered-50 border-aered-500 text-aered-600',
notice: 'bg-slate-50 border-slate-700',
dark: 'bg-slate-700 text-slate-50 rounded-xl m-4'
};
const actionStyles = {
default: 'text-slate-600 hover:text-slate-700 focus-visible:ring-slate-400',
camel: 'text-camel-50 hover:text-camel-100 focus-visible:ring-camel-400',
red: 'text-aered-600 hover:text-aered-700 focus-visible:ring-aered-400',
notice: 'text-slate-700 hover:text-slate-800 focus-visible:ring-slate-400',
dark: 'text-slate-50 hover:text-slate-100 focus-visible:ring-slate-400'
};
const positionStyles = {
top: 'border-b-2 fixed top-0 left-0 right-0 z-50',
bottom: 'border-t-2 fixed bottom-0 left-0 right-0 z-50'
};
// Helper function to get base classes
const getBaseClasses = (variant, position, className) => (0, _tailwindMerge.twMerge)('relative px-4 py-3 flex', variantStyles[variant], positionStyles[position], variant === 'notice' && 'flex flex-col md:flex-row justify-between gap-4', className);
// Helper function to get action classes
const getActionClasses = variant => (0, _tailwindMerge.twMerge)('inline-flex items-center gap-2 font-medium underline underline-offset-1 hover:underline focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-offset-2 rounded-sm whitespace-nowrap', actionStyles[variant]);
const Banner = ({
children,
position = 'top',
variant = 'default',
className,
onDismiss,
action,
title,
isDismissible = false,
centered = true
}) => {
// Validate props
BannerPositionSchema.parse(position);
BannerVariantSchema.parse(variant);
BannerCenteredSchema.parse(centered);
const baseClasses = getBaseClasses(variant, position, className);
const actionClasses = getActionClasses(variant);
const renderAction = () => {
if (!action?.text) return null;
const {
href = '#',
text,
onClick,
...actionProps
} = action;
return /*#__PURE__*/_react.default.createElement("a", _extends({
href: href,
className: actionClasses,
onClick: onClick
}, actionProps), text, /*#__PURE__*/_react.default.createElement(_react2.CaretRight, {
weight: "bold",
className: "w-5 h-5 rtl:-scale-x-100"
}));
};
const renderDismissButton = () => {
if (!isDismissible || !onDismiss) return null;
return /*#__PURE__*/_react.default.createElement("button", {
onClick: onDismiss,
className: "p-0.5 hover:opacity-60 focus:outline-none focus:ring-2 focus:ring-offset-2 focus:ring-slate-400 rounded",
"aria-label": "Dismiss"
}, /*#__PURE__*/_react.default.createElement(_react2.X, {
weight: "bold",
className: "w-5 h-5"
}));
};
const renderContent = () => /*#__PURE__*/_react.default.createElement(_react.default.Fragment, null, /*#__PURE__*/_react.default.createElement("div", {
className: `flex flex-col md:flex-row gap-3 ${centered ? 'justify-center' : 'justify-start'} flex-grow`
}, /*#__PURE__*/_react.default.createElement("div", {
className: `${centered ? 'text-center' : 'text-left'}`
}, children), /*#__PURE__*/_react.default.createElement("div", {
className: `flex items-center ${centered ? 'justify-center' : 'justify-start'} gap-3`
}, renderAction())), renderDismissButton() && /*#__PURE__*/_react.default.createElement("div", {
className: "flex items-center"
}, renderDismissButton()));
return /*#__PURE__*/_react.default.createElement("div", {
className: baseClasses,
role: "alert",
tabIndex: variant === 'notice' ? '-1' : undefined
}, variant === 'notice' ? /*#__PURE__*/_react.default.createElement("div", {
className: "py-4 max-w-screen-lg"
}, title && /*#__PURE__*/_react.default.createElement("h2", {
className: "mb-4 text-xl font-bold text-slate-800"
}, title), /*#__PURE__*/_react.default.createElement("p", {
className: "font-normal text-slate-800 mb-0"
}, children)) : renderContent(), variant === 'notice' && /*#__PURE__*/_react.default.createElement("div", {
className: "flex items-center gap-4"
}, renderAction(), renderDismissButton()));
};
var _default = exports.default = Banner;