DescendantsPageListModal.tsx 3.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111
  1. import React, { useState, useMemo, useEffect } from 'react';
  2. import { useTranslation } from 'next-i18next';
  3. import dynamic from 'next/dynamic';
  4. import { useRouter } from 'next/router';
  5. import {
  6. Modal, ModalHeader, ModalBody,
  7. } from 'reactstrap';
  8. import { useIsSharedUser } from '~/stores/context';
  9. import { useDescendantsPageListModal } from '~/stores/modal';
  10. import { CustomNavTab } from './CustomNavigation/CustomNav';
  11. import CustomTabContent from './CustomNavigation/CustomTabContent';
  12. import type { DescendantsPageListProps } from './DescendantsPageList';
  13. import ExpandOrContractButton from './ExpandOrContractButton';
  14. import styles from './DescendantsPageListModal.module.scss';
  15. const DescendantsPageList = dynamic<DescendantsPageListProps>(() => import('./DescendantsPageList').then(mod => mod.DescendantsPageList), { ssr: false });
  16. const PageTimeline = dynamic(() => import('./PageTimeline').then(mod => mod.PageTimeline), { ssr: false });
  17. export const DescendantsPageListModal = (): JSX.Element => {
  18. const { t } = useTranslation();
  19. const [activeTab, setActiveTab] = useState('pagelist');
  20. const [isWindowExpanded, setIsWindowExpanded] = useState(false);
  21. const { data: isSharedUser } = useIsSharedUser();
  22. const { data: status, close } = useDescendantsPageListModal();
  23. const { events } = useRouter();
  24. useEffect(() => {
  25. events.on('routeChangeStart', close);
  26. return () => {
  27. events.off('routeChangeStart', close);
  28. };
  29. }, [close, events]);
  30. const navTabMapping = useMemo(() => {
  31. return {
  32. pagelist: {
  33. Icon: () => <span className="material-symbols-outlined">subject</span>,
  34. Content: () => {
  35. if (status == null || status.path == null || !status.isOpened) {
  36. return <></>;
  37. }
  38. return <DescendantsPageList path={status.path} />;
  39. },
  40. i18n: t('page_list'),
  41. isLinkEnabled: () => !isSharedUser,
  42. },
  43. timeline: {
  44. Icon: () => <span className="material-symbols-outlined">timeline</span>,
  45. Content: () => {
  46. if (status == null || !status.isOpened) {
  47. return <></>;
  48. }
  49. return <PageTimeline />;
  50. },
  51. i18n: t('Timeline View'),
  52. isLinkEnabled: () => !isSharedUser,
  53. },
  54. };
  55. }, [isSharedUser, status, t]);
  56. const buttons = useMemo(() => (
  57. <span className="me-3">
  58. <ExpandOrContractButton
  59. isWindowExpanded={isWindowExpanded}
  60. expandWindow={() => setIsWindowExpanded(true)}
  61. contractWindow={() => setIsWindowExpanded(false)}
  62. />
  63. <button type="button" className="btn btn-close ms-2" onClick={close} aria-label="Close"></button>
  64. </span>
  65. ), [close, isWindowExpanded]);
  66. if (status == null) {
  67. return <></>;
  68. }
  69. const { isOpened } = status;
  70. return (
  71. <Modal
  72. size="xl"
  73. isOpen={isOpened}
  74. toggle={close}
  75. data-testid="descendants-page-list-modal"
  76. className={`grw-descendants-page-list-modal ${styles['grw-descendants-page-list-modal']} ${isWindowExpanded ? 'grw-modal-expanded' : ''} `}
  77. >
  78. <ModalHeader className="p-0" toggle={close} close={buttons}>
  79. <CustomNavTab
  80. activeTab={activeTab}
  81. navTabMapping={navTabMapping}
  82. breakpointToHideInactiveTabsDown="md"
  83. onNavSelected={v => setActiveTab(v)}
  84. hideBorderBottom
  85. />
  86. </ModalHeader>
  87. <ModalBody>
  88. <CustomTabContent activeTab={activeTab} navTabMapping={navTabMapping} />
  89. </ModalBody>
  90. </Modal>
  91. );
  92. };