@sqrzro/ui 4.0.0-alpha.17 → 4.0.0-alpha.18
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/components/utility/Action/index.d.ts +1 -1
- package/dist/components/utility/Confirmable/index.js +1 -0
- package/dist/components/utility/MenuItem/index.d.ts +1 -1
- package/dist/components/utility/MenuItem/index.js +5 -1
- package/dist/hooks/useConfirmable.d.ts +4 -1
- package/dist/hooks/useConfirmable.js +9 -3
- package/dist/hooks/usePopover.d.ts +11 -0
- package/dist/hooks/usePopover.js +17 -0
- package/dist/navigation/components/AppNavigation/index.d.ts +1 -0
- package/dist/navigation/components/AppNavigation/index.js +3 -3
- package/dist/navigation/components/AppNavigationItem/index.d.ts +4 -2
- package/dist/navigation/components/AppNavigationItem/index.js +11 -3
- package/dist/navigation/components/Tabs/index.js +1 -4
- package/dist/utility/interfaces.d.ts +4 -1
- package/package.json +1 -1
|
@@ -4,7 +4,7 @@ export interface ActionProps<Data extends object | null = null> extends Omit<Act
|
|
|
4
4
|
readonly label?: React.ReactNode;
|
|
5
5
|
readonly render: (props: ActionComponentProps<Data>) => React.ReactElement;
|
|
6
6
|
}
|
|
7
|
-
export interface ActionComponentProps<Data extends object | null = null> extends Pick<ActionProps<Data>, 'href' | 'icon' | 'isDisabled' | 'isLoading' | 'isSubmittable' | 'onClick' | 'variant'> {
|
|
7
|
+
export interface ActionComponentProps<Data extends object | null = null> extends Pick<ActionProps<Data>, 'href' | 'icon' | 'isDisabled' | 'isLoading' | 'isSubmittable' | 'onClick' | 'searchParams' | 'variant'> {
|
|
8
8
|
children: React.ReactNode;
|
|
9
9
|
}
|
|
10
10
|
declare function Action<Data extends object | null = null>(props: ActionProps<Data>): React.ReactElement;
|
|
@@ -7,6 +7,7 @@ function Confirmable({ confirmable, renderProps, render, }) {
|
|
|
7
7
|
const { handle, isOpen, modalProps } = useConfirmable({
|
|
8
8
|
isLoading: renderProps.isLoading,
|
|
9
9
|
onConfirm: (event) => renderProps.onClick?.(event),
|
|
10
|
+
refreshOnSuccess: true,
|
|
10
11
|
});
|
|
11
12
|
return (_jsxs(Fragment, { children: [render({ ...renderProps, isLoading: renderProps.isLoading, onClick: handle }), isOpen ? _jsx(ConfirmModal, { confirmable: confirmable, ...modalProps }) : null] }));
|
|
12
13
|
}
|
|
@@ -1,4 +1,4 @@
|
|
|
1
1
|
import type { ActionComponentProps } from '../Action';
|
|
2
2
|
type MenuItemProps<Data extends object | null = null> = ActionComponentProps<Data>;
|
|
3
|
-
declare function MenuItem<Data extends object | null = null>({ children, onClick, }: MenuItemProps<Data>): React.ReactElement;
|
|
3
|
+
declare function MenuItem<Data extends object | null = null>({ children, href, onClick, }: MenuItemProps<Data>): React.ReactElement;
|
|
4
4
|
export default MenuItem;
|
|
@@ -1,5 +1,9 @@
|
|
|
1
1
|
import { jsx as _jsx } from "react/jsx-runtime";
|
|
2
|
-
|
|
2
|
+
import Link from '../Link';
|
|
3
|
+
function MenuItem({ children, href, onClick, }) {
|
|
4
|
+
if (href) {
|
|
5
|
+
return (_jsx(Link, { href: href, onClick: onClick, children: children }));
|
|
6
|
+
}
|
|
3
7
|
return (_jsx("button", { onClick: onClick, type: "button", children: children }));
|
|
4
8
|
}
|
|
5
9
|
export default MenuItem;
|
|
@@ -3,6 +3,9 @@ interface UseConfirmableArgs {
|
|
|
3
3
|
isLoading?: boolean;
|
|
4
4
|
onBeforeConfirm?: () => void;
|
|
5
5
|
onConfirm: (event: ActionEvent, currentRef: HTMLButtonElement | null) => void;
|
|
6
|
+
onSuccess?: () => Promise<void> | void;
|
|
7
|
+
redirectOnSuccess?: string | false | ((response: Response) => string | false);
|
|
8
|
+
refreshOnSuccess?: boolean;
|
|
6
9
|
}
|
|
7
10
|
interface UseConfirmableReturn {
|
|
8
11
|
handle: (event?: ActionEvent) => void;
|
|
@@ -14,5 +17,5 @@ interface UseConfirmableReturn {
|
|
|
14
17
|
};
|
|
15
18
|
ref: React.RefObject<HTMLButtonElement | null>;
|
|
16
19
|
}
|
|
17
|
-
declare function useConfirmable({ isLoading, onBeforeConfirm, onConfirm, }: Readonly<UseConfirmableArgs>): UseConfirmableReturn;
|
|
20
|
+
declare function useConfirmable({ isLoading, onBeforeConfirm, onConfirm, onSuccess, redirectOnSuccess, refreshOnSuccess, }: Readonly<UseConfirmableArgs>): UseConfirmableReturn;
|
|
18
21
|
export default useConfirmable;
|
|
@@ -1,7 +1,9 @@
|
|
|
1
1
|
'use client';
|
|
2
2
|
import { useEffect, useRef, useState } from 'react';
|
|
3
|
-
|
|
3
|
+
import { useRouter } from 'next/navigation';
|
|
4
|
+
function useConfirmable({ isLoading, onBeforeConfirm, onConfirm, onSuccess, redirectOnSuccess, refreshOnSuccess, }) {
|
|
4
5
|
const ref = useRef(null);
|
|
6
|
+
const router = useRouter();
|
|
5
7
|
const [isModalOpen, setIsModalOpen] = useState(false);
|
|
6
8
|
const [isConfirmed, setIsConfirmed] = useState(false);
|
|
7
9
|
const [refEvent, setRefEvent] = useState();
|
|
@@ -32,10 +34,14 @@ function useConfirmable({ isLoading, onBeforeConfirm, onConfirm, }) {
|
|
|
32
34
|
function handleCancel() {
|
|
33
35
|
setIsModalOpen(false);
|
|
34
36
|
}
|
|
37
|
+
function handleSuccess() {
|
|
38
|
+
setIsConfirmed(false);
|
|
39
|
+
setIsModalOpen(false);
|
|
40
|
+
router.refresh();
|
|
41
|
+
}
|
|
35
42
|
useEffect(() => {
|
|
36
43
|
if (!isLoading && isConfirmed) {
|
|
37
|
-
|
|
38
|
-
setIsModalOpen(false);
|
|
44
|
+
handleSuccess();
|
|
39
45
|
}
|
|
40
46
|
}, [isLoading]);
|
|
41
47
|
return {
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
interface UsePopoverReturn<T extends HTMLElement = HTMLElement> {
|
|
2
|
+
controlProps: {
|
|
3
|
+
onClick: () => void;
|
|
4
|
+
};
|
|
5
|
+
ref: React.RefObject<T | null>;
|
|
6
|
+
targetProps: {
|
|
7
|
+
isOpen: boolean;
|
|
8
|
+
};
|
|
9
|
+
}
|
|
10
|
+
declare function usePopover<T extends HTMLElement = HTMLElement>(): UsePopoverReturn<T>;
|
|
11
|
+
export default usePopover;
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
import useClickOutside from './useClickOutside';
|
|
2
|
+
function usePopover() {
|
|
3
|
+
const [isOpen, setIsOpen, ref] = useClickOutside();
|
|
4
|
+
function toggleIsOpen() {
|
|
5
|
+
setIsOpen(!isOpen);
|
|
6
|
+
}
|
|
7
|
+
return {
|
|
8
|
+
controlProps: {
|
|
9
|
+
onClick: toggleIsOpen,
|
|
10
|
+
},
|
|
11
|
+
ref,
|
|
12
|
+
targetProps: {
|
|
13
|
+
isOpen,
|
|
14
|
+
},
|
|
15
|
+
};
|
|
16
|
+
}
|
|
17
|
+
export default usePopover;
|
|
@@ -7,6 +7,7 @@ export interface AppNavigationClassNames {
|
|
|
7
7
|
link: HighlightableClassName;
|
|
8
8
|
}
|
|
9
9
|
export interface AppNavigationProps extends ClassNameProps<AppNavigationClassNames> {
|
|
10
|
+
classNameKey?: 'appNavigation' | 'tabs';
|
|
10
11
|
data: NavigationObject[];
|
|
11
12
|
}
|
|
12
13
|
declare function AppNavigation(props: Readonly<AppNavigationProps>): React.ReactElement;
|
|
@@ -4,10 +4,10 @@ import { Suspense } from 'react';
|
|
|
4
4
|
import { getClassNames } from '../../../styles/classnames';
|
|
5
5
|
import useNavigation from '../../hooks/useNavigation';
|
|
6
6
|
import AppNavigationItem from '../AppNavigationItem';
|
|
7
|
-
function AppNavigationComponent({ classNameProps, classNames, data, }) {
|
|
8
|
-
const componentClassNames = getClassNames('appNavigation', { props: classNameProps }, classNames);
|
|
7
|
+
function AppNavigationComponent({ classNameKey, classNameProps, classNames, data, }) {
|
|
8
|
+
const componentClassNames = getClassNames(classNameKey ?? 'appNavigation', { props: classNameProps }, classNames);
|
|
9
9
|
const navigation = useNavigation(data);
|
|
10
|
-
return (_jsx("nav", { className: componentClassNames?.root, children: _jsx("ul", { className: componentClassNames?.list, children: navigation.map((item, index) => (_jsx(AppNavigationItem, { classNames: classNames, ...item }, index))) }) }));
|
|
10
|
+
return (_jsx("nav", { className: componentClassNames?.root, children: _jsx("ul", { className: componentClassNames?.list, children: navigation.map((item, index) => (_jsx(AppNavigationItem, { classNameKey: classNameKey, classNames: classNames, ...item }, index))) }) }));
|
|
11
11
|
}
|
|
12
12
|
function AppNavigation(props) {
|
|
13
13
|
return (_jsx(Suspense, { children: _jsx(AppNavigationComponent, { ...props }) }));
|
|
@@ -1,6 +1,8 @@
|
|
|
1
1
|
import type { NavigationObject } from '../../../navigation/interfaces';
|
|
2
2
|
import type { ClassNameProps } from '../../../styles/classnames/interfaces';
|
|
3
3
|
import type { AppNavigationClassNames } from '../AppNavigation';
|
|
4
|
-
export
|
|
5
|
-
|
|
4
|
+
export interface AppNavigationItemProps extends NavigationObject, ClassNameProps<AppNavigationClassNames> {
|
|
5
|
+
classNameKey?: 'appNavigation' | 'tabs';
|
|
6
|
+
}
|
|
7
|
+
declare function AppNavigationItem({ children, classNameKey, classNameProps, classNames, href, isActive, label, }: Readonly<AppNavigationItemProps>): React.ReactElement;
|
|
6
8
|
export default AppNavigationItem;
|
|
@@ -1,8 +1,16 @@
|
|
|
1
|
-
import { jsx as _jsx } from "react/jsx-runtime";
|
|
1
|
+
import { jsx as _jsx, jsxs as _jsxs } from "react/jsx-runtime";
|
|
2
|
+
import Action from '../../../components/utility/Action';
|
|
2
3
|
import Link from '../../../components/utility/Link';
|
|
4
|
+
import MenuItem from '../../../components/utility/MenuItem';
|
|
5
|
+
import Popover from '../../../components/utility/Popover';
|
|
6
|
+
import usePopover from '../../../hooks/usePopover';
|
|
3
7
|
import { getClassNames } from '../../../styles/classnames';
|
|
4
|
-
function AppNavigationItem({ classNameProps, classNames, href, isActive, label, }) {
|
|
5
|
-
const componentClassNames = getClassNames('appNavigation', { props: classNameProps, states: { isHighlighted: isActive ?? false } }, classNames);
|
|
8
|
+
function AppNavigationItem({ children, classNameKey, classNameProps, classNames, href, isActive, label, }) {
|
|
9
|
+
const componentClassNames = getClassNames(classNameKey ?? 'appNavigation', { props: classNameProps, states: { isHighlighted: isActive ?? false } }, classNames);
|
|
10
|
+
const { controlProps, ref, targetProps } = usePopover();
|
|
11
|
+
if (children?.length) {
|
|
12
|
+
return (_jsxs("li", { className: componentClassNames?.item, ref: ref, children: [_jsx("button", { className: componentClassNames?.link, type: "button", ...controlProps, children: label }), _jsx(Popover, { align: "left", vAlign: "bottom", ...targetProps, children: _jsx("ul", { children: children.map((item, index) => (_jsx("li", { children: _jsx(Action, { ...item, render: MenuItem }) }, index))) }) })] }));
|
|
13
|
+
}
|
|
6
14
|
return (_jsx("li", { className: componentClassNames?.item, children: _jsx(Link, { className: componentClassNames?.link, href: href, children: label }) }));
|
|
7
15
|
}
|
|
8
16
|
export default AppNavigationItem;
|
|
@@ -1,9 +1,6 @@
|
|
|
1
|
-
'use client';
|
|
2
1
|
import { jsx as _jsx } from "react/jsx-runtime";
|
|
3
|
-
import { getClassNames } from '../../../styles/classnames';
|
|
4
2
|
import AppNavigation from '../AppNavigation';
|
|
5
3
|
function Tabs({ classNameProps, classNames, ...props }) {
|
|
6
|
-
|
|
7
|
-
return _jsx(AppNavigation, { classNames: componentClassNames ?? {}, ...props });
|
|
4
|
+
return _jsx(AppNavigation, { classNameKey: "tabs", ...props });
|
|
8
5
|
}
|
|
9
6
|
export default Tabs;
|
|
@@ -7,12 +7,15 @@ export interface ConfirmableObject {
|
|
|
7
7
|
modalIcon?: React.ReactNode;
|
|
8
8
|
onBeforeConfirm?: () => void;
|
|
9
9
|
onConfirm?: () => void;
|
|
10
|
+
onSuccess?: () => Promise<void> | void;
|
|
11
|
+
redirectOnSuccess?: string | false | ((response: Response) => string | false);
|
|
12
|
+
refreshOnSuccess?: boolean;
|
|
10
13
|
submitLabel?: string;
|
|
11
14
|
title?: React.ReactNode;
|
|
12
15
|
}
|
|
13
16
|
export type ActionEvent = React.MouseEvent<HTMLAnchorElement> | React.MouseEvent<HTMLButtonElement>;
|
|
14
17
|
export interface ActionObject<Data extends object | null = null> {
|
|
15
|
-
action?: (data
|
|
18
|
+
action?: (data: Data) => Promise<void>;
|
|
16
19
|
confirmable?: ConfirmableObject;
|
|
17
20
|
data?: Data;
|
|
18
21
|
details?: React.ReactNode;
|