123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126 |
- import { BellOutlined } from '@ant-design/icons';
- import { Badge, Spin, Tabs } from 'antd';
- import classNames from 'classnames';
- import useMergedState from 'rc-util/es/hooks/useMergedState';
- import React from 'react';
- import HeaderDropdown from '../HeaderDropdown';
- import styles from './index.less';
- import type { NoticeIconTabProps } from './NoticeList';
- import NoticeList from './NoticeList';
- const { TabPane } = Tabs;
- export type NoticeIconProps = {
- count?: number;
- bell?: React.ReactNode;
- className?: string;
- loading?: boolean;
- onClear?: (tabName: string, tabKey: string) => void;
- onItemClick?: (item: API.NoticeIconItem, tabProps: NoticeIconTabProps) => void;
- onViewMore?: (tabProps: NoticeIconTabProps, e: MouseEvent) => void;
- onTabChange?: (tabTile: string) => void;
- style?: React.CSSProperties;
- onPopupVisibleChange?: (visible: boolean) => void;
- popupVisible?: boolean;
- clearText?: string;
- viewMoreText?: string;
- clearClose?: boolean;
- emptyImage?: string;
- children?: React.ReactElement<NoticeIconTabProps>[];
- };
- const NoticeIcon: React.FC<NoticeIconProps> & {
- Tab: typeof NoticeList;
- } = (props) => {
- const getNotificationBox = (): React.ReactNode => {
- const {
- children,
- loading,
- onClear,
- onTabChange,
- onItemClick,
- onViewMore,
- clearText,
- viewMoreText,
- } = props;
- if (!children) {
- return null;
- }
- const panes: React.ReactNode[] = [];
- React.Children.forEach(children, (child: React.ReactElement<NoticeIconTabProps>): void => {
- if (!child) {
- return;
- }
- const { list, title, count, tabKey, showClear, showViewMore } = child.props;
- const len = list && list.length ? list.length : 0;
- const msgCount = count || count === 0 ? count : len;
- const tabTitle: string = msgCount > 0 ? `${title} (${msgCount})` : title;
- panes.push(
- <TabPane tab={tabTitle} key={tabKey}>
- <NoticeList
- clearText={clearText}
- viewMoreText={viewMoreText}
- list={list}
- tabKey={tabKey}
- onClear={(): void => onClear && onClear(title, tabKey)}
- onClick={(item): void => onItemClick && onItemClick(item, child.props)}
- onViewMore={(event): void => onViewMore && onViewMore(child.props, event)}
- showClear={showClear}
- showViewMore={showViewMore}
- title={title}
- />
- </TabPane>,
- );
- });
- return (
- <>
- <Spin spinning={loading} delay={300}>
- <Tabs className={styles.tabs} onChange={onTabChange}>
- {panes}
- </Tabs>
- </Spin>
- </>
- );
- };
- const { className, count, bell } = props;
- const [visible, setVisible] = useMergedState<boolean>(false, {
- value: props.popupVisible,
- onChange: props.onPopupVisibleChange,
- });
- const noticeButtonClass = classNames(className, styles.noticeButton);
- const notificationBox = getNotificationBox();
- const NoticeBellIcon = bell || <BellOutlined className={styles.icon} />;
- const trigger = (
- <span className={classNames(noticeButtonClass, { opened: visible })}>
- <Badge count={count} style={{ boxShadow: 'none' }} className={styles.badge}>
- {NoticeBellIcon}
- </Badge>
- </span>
- );
- if (!notificationBox) {
- return trigger;
- }
- return (
- <HeaderDropdown
- placement="bottomRight"
- overlay={notificationBox}
- overlayClassName={styles.popover}
- trigger={['click']}
- visible={visible}
- onVisibleChange={setVisible}
- >
- {trigger}
- </HeaderDropdown>
- );
- };
- NoticeIcon.defaultProps = {
- emptyImage: 'https://gw.alipayobjects.com/zos/rmsportal/wAhyIChODzsoKIOBHcBk.svg',
- };
- NoticeIcon.Tab = NoticeList;
- export default NoticeIcon;
|