@mondrianai/runyourai-design-system 0.0.28 → 0.0.30

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.d.mts CHANGED
@@ -622,6 +622,8 @@ interface ModalButtonProps {
622
622
  }
623
623
  interface ModalProps {
624
624
  id?: string;
625
+ /** 패널 너비: sm 400px / md 430px / lg 480px (기본: lg) */
626
+ size?: 'sm' | 'md' | 'lg';
625
627
  /**
626
628
  * 모달을 여는 트리거 — render prop 패턴.
627
629
  * open 함수를 인자로 받아 원하는 요소에 직접 연결.
@@ -635,21 +637,32 @@ interface ModalProps {
635
637
  open?: boolean;
636
638
  /** controlled 모드에서 열림 상태 변경 콜백 */
637
639
  onOpenChange?: (open: boolean) => void;
640
+ /**
641
+ * 포커스·배경 상호작용 격리 여부 (기본: true).
642
+ * 외부 SDK가 별도 포털/iframe을 열면 false로 설정한다. 외부 포커스/클릭으로
643
+ * 원본 콘텐츠를 닫지 않으며, 딤 클릭은 closeOnOverlayClick을 따른다.
644
+ * SDK가 초기 포커스를, 소비 앱이 SDK 종료 후 포커스 복구를 담당한다.
645
+ * false에서는 배경의 키보드 상호작용도 소비 앱이 별도로 차단해야 한다.
646
+ * 열린 동안 값을 변경하면 콘텐츠가 재마운트되므로 고정해서 사용한다.
647
+ */
648
+ modal?: boolean;
638
649
  /**
639
650
  * footer 버튼 렌더 방식
640
651
  * confirm — 취소 + default(검정) 확인 버튼
641
652
  * danger — 취소 + destructive(빨강) 확인 버튼
642
- * dialog — footer 없음 (children으로 모든 콘텐츠 처리)
653
+ * dialog — 기본 버튼 없음 (필요하면 footer로 직접 제공)
643
654
  */
644
655
  variant?: 'confirm' | 'danger' | 'dialog';
645
656
  /** 모달 제목 */
646
657
  title: string;
647
- /** 제목 아래 부제목 (선택) */
658
+ /** 본문 첫 항목으로 표시하는 설명 (선택) */
648
659
  description?: string;
649
- /** 우상단 X 닫기 버튼 표시 여부 (기본: true) */
660
+ /** 우상단 X 닫기 버튼 표시 여부 (기본: false). 기본 닫기는 footer·ESC·오버레이를 사용한다. */
650
661
  showCloseButton?: boolean;
651
- /** 모달 본문 */
662
+ /** 모달 본문. 직접 자식 항목 사이에는 12px 간격이 적용된다. 중첩 그룹도 gap-3을 사용한다. */
652
663
  children?: React$1.ReactNode;
664
+ /** dialog 변형의 하단 버튼. 본문과 16px 간격을 적용한다. */
665
+ footer?: React$1.ReactNode;
653
666
  /** 취소 버튼 커스터마이즈 (label 기본: "취소") */
654
667
  cancelButtonProps?: ModalButtonProps;
655
668
  /** 확인 버튼 커스터마이즈 (label 기본: "확인") */
@@ -664,10 +677,17 @@ interface ModalProps {
664
677
  onCancel?: () => void;
665
678
  /** 오버레이 클릭 시 닫기 (기본: true) */
666
679
  closeOnOverlayClick?: boolean;
680
+ /** 모달 오버레이에 추가할 className (예: 외부 포털보다 낮은 stacking level 지정) */
681
+ overlayClassName?: string;
667
682
  /** 모달 패널에 추가할 className */
668
683
  className?: string;
669
684
  }
670
- declare function Modal({ id, trigger, open: openProp, onOpenChange, variant, title, description, showCloseButton, children, cancelButtonProps, confirmButtonProps, onConfirm, onCancel, closeOnOverlayClick, className, }: ModalProps): react_jsx_runtime.JSX.Element;
685
+ /**
686
+ * 앱의 확인/입력 다이얼로그를 렌더링한다. 기본은 모달이며, 외부 SDK 연동 시
687
+ * modal=false로 모달 격리를 해제하고 SDK를 소유한 원본 콘텐츠를 유지한다.
688
+ * 외부 포털과 stacking level을 조율할 때는 className과 overlayClassName을 함께 사용한다.
689
+ */
690
+ declare function Modal({ id, size, trigger, open: openProp, onOpenChange, modal, variant, title, description, showCloseButton, children, footer, cancelButtonProps, confirmButtonProps, onConfirm, onCancel, closeOnOverlayClick, overlayClassName, className, }: ModalProps): react_jsx_runtime.JSX.Element;
671
691
 
672
692
  declare const Menubar: React$1.ForwardRefExoticComponent<Omit<Menubar$1.MenubarProps & React$1.RefAttributes<HTMLDivElement>, "ref"> & React$1.RefAttributes<HTMLDivElement>>;
673
693
  declare const MenubarMenu: {
package/dist/index.d.ts CHANGED
@@ -622,6 +622,8 @@ interface ModalButtonProps {
622
622
  }
623
623
  interface ModalProps {
624
624
  id?: string;
625
+ /** 패널 너비: sm 400px / md 430px / lg 480px (기본: lg) */
626
+ size?: 'sm' | 'md' | 'lg';
625
627
  /**
626
628
  * 모달을 여는 트리거 — render prop 패턴.
627
629
  * open 함수를 인자로 받아 원하는 요소에 직접 연결.
@@ -635,21 +637,32 @@ interface ModalProps {
635
637
  open?: boolean;
636
638
  /** controlled 모드에서 열림 상태 변경 콜백 */
637
639
  onOpenChange?: (open: boolean) => void;
640
+ /**
641
+ * 포커스·배경 상호작용 격리 여부 (기본: true).
642
+ * 외부 SDK가 별도 포털/iframe을 열면 false로 설정한다. 외부 포커스/클릭으로
643
+ * 원본 콘텐츠를 닫지 않으며, 딤 클릭은 closeOnOverlayClick을 따른다.
644
+ * SDK가 초기 포커스를, 소비 앱이 SDK 종료 후 포커스 복구를 담당한다.
645
+ * false에서는 배경의 키보드 상호작용도 소비 앱이 별도로 차단해야 한다.
646
+ * 열린 동안 값을 변경하면 콘텐츠가 재마운트되므로 고정해서 사용한다.
647
+ */
648
+ modal?: boolean;
638
649
  /**
639
650
  * footer 버튼 렌더 방식
640
651
  * confirm — 취소 + default(검정) 확인 버튼
641
652
  * danger — 취소 + destructive(빨강) 확인 버튼
642
- * dialog — footer 없음 (children으로 모든 콘텐츠 처리)
653
+ * dialog — 기본 버튼 없음 (필요하면 footer로 직접 제공)
643
654
  */
644
655
  variant?: 'confirm' | 'danger' | 'dialog';
645
656
  /** 모달 제목 */
646
657
  title: string;
647
- /** 제목 아래 부제목 (선택) */
658
+ /** 본문 첫 항목으로 표시하는 설명 (선택) */
648
659
  description?: string;
649
- /** 우상단 X 닫기 버튼 표시 여부 (기본: true) */
660
+ /** 우상단 X 닫기 버튼 표시 여부 (기본: false). 기본 닫기는 footer·ESC·오버레이를 사용한다. */
650
661
  showCloseButton?: boolean;
651
- /** 모달 본문 */
662
+ /** 모달 본문. 직접 자식 항목 사이에는 12px 간격이 적용된다. 중첩 그룹도 gap-3을 사용한다. */
652
663
  children?: React$1.ReactNode;
664
+ /** dialog 변형의 하단 버튼. 본문과 16px 간격을 적용한다. */
665
+ footer?: React$1.ReactNode;
653
666
  /** 취소 버튼 커스터마이즈 (label 기본: "취소") */
654
667
  cancelButtonProps?: ModalButtonProps;
655
668
  /** 확인 버튼 커스터마이즈 (label 기본: "확인") */
@@ -664,10 +677,17 @@ interface ModalProps {
664
677
  onCancel?: () => void;
665
678
  /** 오버레이 클릭 시 닫기 (기본: true) */
666
679
  closeOnOverlayClick?: boolean;
680
+ /** 모달 오버레이에 추가할 className (예: 외부 포털보다 낮은 stacking level 지정) */
681
+ overlayClassName?: string;
667
682
  /** 모달 패널에 추가할 className */
668
683
  className?: string;
669
684
  }
670
- declare function Modal({ id, trigger, open: openProp, onOpenChange, variant, title, description, showCloseButton, children, cancelButtonProps, confirmButtonProps, onConfirm, onCancel, closeOnOverlayClick, className, }: ModalProps): react_jsx_runtime.JSX.Element;
685
+ /**
686
+ * 앱의 확인/입력 다이얼로그를 렌더링한다. 기본은 모달이며, 외부 SDK 연동 시
687
+ * modal=false로 모달 격리를 해제하고 SDK를 소유한 원본 콘텐츠를 유지한다.
688
+ * 외부 포털과 stacking level을 조율할 때는 className과 overlayClassName을 함께 사용한다.
689
+ */
690
+ declare function Modal({ id, size, trigger, open: openProp, onOpenChange, modal, variant, title, description, showCloseButton, children, footer, cancelButtonProps, confirmButtonProps, onConfirm, onCancel, closeOnOverlayClick, overlayClassName, className, }: ModalProps): react_jsx_runtime.JSX.Element;
671
691
 
672
692
  declare const Menubar: React$1.ForwardRefExoticComponent<Omit<Menubar$1.MenubarProps & React$1.RefAttributes<HTMLDivElement>, "ref"> & React$1.RefAttributes<HTMLDivElement>>;
673
693
  declare const MenubarMenu: {
package/dist/index.js CHANGED
@@ -4395,19 +4395,23 @@ function withIconSize(icon) {
4395
4395
  }
4396
4396
  function Modal({
4397
4397
  id,
4398
+ size = "lg",
4398
4399
  trigger,
4399
4400
  open: openProp,
4400
4401
  onOpenChange,
4402
+ modal = true,
4401
4403
  variant = "confirm",
4402
4404
  title,
4403
4405
  description,
4404
- showCloseButton = true,
4406
+ showCloseButton = false,
4405
4407
  children,
4408
+ footer,
4406
4409
  cancelButtonProps,
4407
4410
  confirmButtonProps,
4408
4411
  onConfirm,
4409
4412
  onCancel,
4410
4413
  closeOnOverlayClick = true,
4414
+ overlayClassName,
4411
4415
  className
4412
4416
  }) {
4413
4417
  const {
@@ -4430,6 +4434,7 @@ function Modal({
4430
4434
  const [openState, setOpenState] = React19.useState(false);
4431
4435
  const open = isControlled ? openProp : openState;
4432
4436
  const [loading, setLoading] = React19.useState(false);
4437
+ const Overlay = modal ? import_radix_ui12.Dialog.Overlay : "div";
4433
4438
  const setOpen = React19.useCallback(
4434
4439
  (next) => {
4435
4440
  if (!isControlled) setOpenState(next);
@@ -4472,17 +4477,25 @@ function Modal({
4472
4477
  );
4473
4478
  return /* @__PURE__ */ (0, import_jsx_runtime32.jsxs)(import_jsx_runtime32.Fragment, { children: [
4474
4479
  trigger == null ? void 0 : trigger(() => setOpen(true)),
4475
- /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(import_radix_ui12.Dialog.Root, { open, onOpenChange: handleRootOpenChange, children: /* @__PURE__ */ (0, import_jsx_runtime32.jsxs)(import_radix_ui12.Dialog.Portal, { children: [
4480
+ /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(import_radix_ui12.Dialog.Root, { open, onOpenChange: handleRootOpenChange, modal, children: /* @__PURE__ */ (0, import_jsx_runtime32.jsxs)(import_radix_ui12.Dialog.Portal, { children: [
4476
4481
  /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(
4477
- import_radix_ui12.Dialog.Overlay,
4478
- {
4482
+ Overlay,
4483
+ __spreadProps(__spreadValues({}, !modal ? {
4484
+ "data-state": open ? "open" : "closed",
4485
+ "aria-hidden": true
4486
+ } : {}), {
4487
+ onClick: !modal ? (event) => {
4488
+ event.stopPropagation();
4489
+ if (open && closeOnOverlayClick) handleClose();
4490
+ } : void 0,
4479
4491
  className: cn(
4480
4492
  "fixed inset-0 z-50 bg-black/[0.32]",
4481
4493
  "data-[state=open]:animate-in data-[state=closed]:animate-out",
4482
4494
  "data-[state=open]:fade-in-0 data-[state=closed]:fade-out-0",
4483
- "duration-200 data-[state=closed]:duration-150"
4495
+ "duration-200 data-[state=closed]:duration-150",
4496
+ overlayClassName
4484
4497
  )
4485
- }
4498
+ })
4486
4499
  ),
4487
4500
  /* @__PURE__ */ (0, import_jsx_runtime32.jsxs)(
4488
4501
  import_radix_ui12.Dialog.Content,
@@ -4493,11 +4506,16 @@ function Modal({
4493
4506
  if (loadingRef.current) e.preventDefault();
4494
4507
  },
4495
4508
  onInteractOutside: (e) => {
4509
+ if (!modal) {
4510
+ e.preventDefault();
4511
+ return;
4512
+ }
4496
4513
  if (!closeOnOverlayClick || loadingRef.current) e.preventDefault();
4497
4514
  },
4498
4515
  className: cn(
4499
4516
  "fixed left-1/2 top-1/2 z-50 -translate-x-1/2 -translate-y-1/2",
4500
- "max-h-[calc(100dvh-2rem)] w-120 overflow-y-auto",
4517
+ "max-h-[calc(100dvh-2rem)] max-w-modal-viewport overflow-y-auto",
4518
+ { sm: "w-100", md: "w-107.5", lg: "w-120" }[size],
4501
4519
  "bg-background border border-border rounded-2xl shadow-modal flex flex-col gap-4 p-6",
4502
4520
  "data-[state=open]:animate-in data-[state=closed]:animate-out",
4503
4521
  "data-[state=open]:fade-in-0 data-[state=closed]:fade-out-0",
@@ -4505,32 +4523,23 @@ function Modal({
4505
4523
  className
4506
4524
  ),
4507
4525
  children: [
4508
- /* @__PURE__ */ (0, import_jsx_runtime32.jsxs)(
4509
- "div",
4510
- {
4511
- className: cn(
4512
- "flex flex-col w-full",
4513
- description ? "gap-1" : "gap-0"
4514
- ),
4515
- children: [
4516
- /* @__PURE__ */ (0, import_jsx_runtime32.jsxs)("div", { className: "flex items-start justify-between w-full", children: [
4517
- /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(import_radix_ui12.Dialog.Title, { className: "flex-1 text-left text-lg font-semibold leading-7 tracking-tight text-foreground", children: title }),
4518
- showCloseButton && /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(
4519
- "button",
4520
- {
4521
- type: "button",
4522
- onClick: handleClose,
4523
- className: "flex size-5 items-center justify-center ml-2 shrink-0 opacity-70 hover:opacity-100 transition-opacity cursor-pointer",
4524
- children: /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(Icon, { name: "x", className: "size-4 text-foreground" })
4525
- }
4526
- )
4527
- ] }),
4528
- description && /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(import_radix_ui12.Dialog.Description, { className: "text-sm font-normal leading-5 tracking-tight text-muted-foreground", children: description })
4529
- ]
4530
- }
4531
- ),
4532
- children && /* @__PURE__ */ (0, import_jsx_runtime32.jsx)("div", { className: "w-full text-left", children }),
4533
- variant !== "dialog" && /* @__PURE__ */ (0, import_jsx_runtime32.jsxs)("div", { className: "flex gap-2 items-center justify-end w-full", children: [
4526
+ /* @__PURE__ */ (0, import_jsx_runtime32.jsx)("div", { "data-slot": "modal-header", className: "w-full", children: /* @__PURE__ */ (0, import_jsx_runtime32.jsxs)("div", { className: "flex items-start justify-between w-full", children: [
4527
+ /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(import_radix_ui12.Dialog.Title, { className: "flex-1 text-left text-lg font-semibold leading-7 tracking-tight text-foreground", children: title }),
4528
+ showCloseButton && /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(
4529
+ "button",
4530
+ {
4531
+ type: "button",
4532
+ onClick: handleClose,
4533
+ className: "flex size-5 items-center justify-center ml-2 shrink-0 opacity-70 hover:opacity-100 transition-opacity cursor-pointer",
4534
+ children: /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(Icon, { name: "x", className: "size-4 text-foreground" })
4535
+ }
4536
+ )
4537
+ ] }) }),
4538
+ (description || children) && /* @__PURE__ */ (0, import_jsx_runtime32.jsxs)("div", { "data-slot": "modal-body", className: "flex w-full flex-col gap-3 text-left", children: [
4539
+ description && /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(import_radix_ui12.Dialog.Description, { className: "text-sm font-normal leading-5 tracking-tight text-muted-foreground", children: description }),
4540
+ children
4541
+ ] }),
4542
+ variant === "dialog" ? footer && /* @__PURE__ */ (0, import_jsx_runtime32.jsx)("div", { "data-slot": "modal-footer", className: "flex gap-2 items-center justify-end w-full", children: footer }) : /* @__PURE__ */ (0, import_jsx_runtime32.jsxs)("div", { "data-slot": "modal-footer", className: "flex gap-2 items-center justify-end w-full", children: [
4534
4543
  /* @__PURE__ */ (0, import_jsx_runtime32.jsx)(
4535
4544
  Button,
4536
4545
  {