mirror of
https://github.com/muerwre/vault-frontend.git
synced 2025-04-25 12:56:41 +07:00
example dialog
This commit is contained in:
parent
06e72538d3
commit
80fc6523b7
5 changed files with 233 additions and 2 deletions
117
src/containers/dialogs/ScrollDialog/index.tsx
Normal file
117
src/containers/dialogs/ScrollDialog/index.tsx
Normal file
|
@ -0,0 +1,117 @@
|
|||
import React, { FC, MouseEventHandler, ReactChild, useCallback, useEffect, useState } from "react";
|
||||
// import { DialogPanel } from '~/components/panels/DialogPanel';
|
||||
import { Scroll } from "~/components/containers/Scroll";
|
||||
import * as styles from "./styles.scss";
|
||||
import classNames from "classnames";
|
||||
|
||||
interface IProps {
|
||||
children: React.ReactChild;
|
||||
title?: JSX.Element;
|
||||
buttons?: JSX.Element;
|
||||
size?: "medium" | "big";
|
||||
width?: number;
|
||||
onOverlayClick?: MouseEventHandler<HTMLDivElement>;
|
||||
onRefCapture?: (ref: any) => void;
|
||||
|
||||
top_sticky?: ReactChild;
|
||||
top_sticky_offset?: number;
|
||||
}
|
||||
|
||||
const ScrollDialog: FC<IProps> = ({
|
||||
children,
|
||||
title,
|
||||
buttons,
|
||||
size = "medium",
|
||||
width = 800,
|
||||
top_sticky,
|
||||
top_sticky_offset,
|
||||
|
||||
onOverlayClick,
|
||||
onRefCapture
|
||||
}) => {
|
||||
const [height, setHeight] = useState(window.innerHeight - 240);
|
||||
const [show_top_sticky, setShowTopSticky] = useState(false);
|
||||
const [ref, setRef] = useState(null);
|
||||
|
||||
const onResize = useCallback(() => setHeight(window.innerHeight - 240), []);
|
||||
|
||||
useEffect(() => {
|
||||
window.addEventListener("resize", onResize);
|
||||
return () => window.removeEventListener("resize", onResize);
|
||||
}, []);
|
||||
|
||||
const onScroll = useCallback(
|
||||
({ target: { scrollTop = 0 } = {} } = {}) => {
|
||||
if (!top_sticky || (!top_sticky_offset && top_sticky_offset !== 0)) return;
|
||||
|
||||
const is_shown = scrollTop >= top_sticky_offset + 20;
|
||||
|
||||
if (show_top_sticky !== is_shown) setShowTopSticky(is_shown);
|
||||
},
|
||||
[top_sticky, top_sticky_offset, show_top_sticky, setShowTopSticky]
|
||||
);
|
||||
|
||||
useEffect(() => onScroll(), []);
|
||||
useEffect(() => {
|
||||
if (ref && onRefCapture) onRefCapture(ref);
|
||||
}, [ref, onRefCapture]);
|
||||
|
||||
return (
|
||||
<div className={styles.container}>
|
||||
<div
|
||||
className={classNames(styles.content, {
|
||||
has_buttons: !!buttons,
|
||||
has_title: !!title
|
||||
})}
|
||||
style={{ flexBasis: width }}
|
||||
>
|
||||
<div
|
||||
className={styles.overlay}
|
||||
onClick={onOverlayClick}
|
||||
style={{ cursor: onOverlayClick ? "pointer" : "" }}
|
||||
/>
|
||||
|
||||
{!!title && (
|
||||
<div className={styles.top}>
|
||||
<div className={styles.wrap} style={{ flexBasis: width }}>
|
||||
<div className={styles.pan}>
|
||||
{title}
|
||||
{show_top_sticky && top_sticky && (
|
||||
<div className={styles.top_sticky}>{top_sticky}</div>
|
||||
)}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
)}
|
||||
|
||||
{!!buttons && (
|
||||
<div className={styles.bottom}>
|
||||
<div className={styles.wrap} style={{ flexBasis: width }}>
|
||||
<div className={styles.pan}>{buttons}</div>
|
||||
</div>
|
||||
</div>
|
||||
)}
|
||||
|
||||
<div
|
||||
className={styles.scroll_wrap}
|
||||
style={{ flexBasis: width + 40 }}
|
||||
// style={{ flexBasis: width }}
|
||||
>
|
||||
<Scroll
|
||||
className="dialog_scroll"
|
||||
autoHeightMax={height}
|
||||
autoHeight
|
||||
onScroll={onScroll}
|
||||
onRef={setRef}
|
||||
>
|
||||
<div className={styles.content_wrap}>
|
||||
<div className={styles.children}>{children}</div>
|
||||
</div>
|
||||
</Scroll>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
);
|
||||
};
|
||||
|
||||
export { ScrollDialog };
|
Loading…
Add table
Add a link
Reference in a new issue