LsxPage.tsx 2.7 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495
  1. import React, { useMemo } from 'react';
  2. import { pathUtils } from '@growi/core';
  3. import { PagePathLabel, PageListMeta } from '@growi/ui';
  4. import { PageNode } from '../PageNode';
  5. import { LsxContext } from '../lsx-context';
  6. type Props = {
  7. pageNode: PageNode,
  8. lsxContext: LsxContext,
  9. depth: number,
  10. basisViewersCount?: number,
  11. };
  12. export const LsxPage = React.memo((props: Props): JSX.Element => {
  13. const {
  14. pageNode, lsxContext, depth, basisViewersCount,
  15. } = props;
  16. const isExists = pageNode.page !== undefined;
  17. const isLinkable = (() => {
  18. // process depth option
  19. const optDepth = lsxContext.getOptDepth();
  20. if (optDepth == null) {
  21. return true;
  22. }
  23. // debug
  24. // console.log(pageNode.pagePath, {depth, decGens, 'optDepth.start': optDepth.start, 'optDepth.end': optDepth.end});
  25. return optDepth.start <= depth;
  26. })();
  27. const hasChildren = pageNode.children.length > 0;
  28. const childrenElements: JSX.Element = useMemo(() => {
  29. let element = <></>;
  30. // create child pages elements
  31. if (hasChildren) {
  32. const pages = pageNode.children.map((pageNode) => {
  33. return (
  34. <LsxPage
  35. key={pageNode.pagePath}
  36. depth={depth + 1}
  37. pageNode={pageNode}
  38. lsxContext={lsxContext}
  39. basisViewersCount={basisViewersCount}
  40. />
  41. );
  42. });
  43. element = <ul className="page-list-ul">{pages}</ul>;
  44. }
  45. return element;
  46. }, [basisViewersCount, depth, hasChildren, lsxContext, pageNode.children]);
  47. const iconElement: JSX.Element = useMemo(() => {
  48. return (isExists)
  49. ? <i className="ti ti-agenda" aria-hidden="true"></i>
  50. : <i className="ti ti-file lsx-page-not-exist" aria-hidden="true"></i>;
  51. }, [isExists]);
  52. const pagePathElement: JSX.Element = useMemo(() => {
  53. const classNames: string[] = [];
  54. if (!isExists) {
  55. classNames.push('lsx-page-not-exist');
  56. }
  57. // create PagePath element
  58. let pagePathNode = <PagePathLabel path={pageNode.pagePath} isLatterOnly additionalClassNames={classNames} />;
  59. if (isLinkable) {
  60. pagePathNode = <a className="page-list-link" href={encodeURI(pathUtils.removeTrailingSlash(pageNode.pagePath))}>{pagePathNode}</a>;
  61. }
  62. return pagePathNode;
  63. }, [isExists, isLinkable, pageNode.pagePath]);
  64. const pageListMetaElement: JSX.Element = useMemo(() => {
  65. if (!isExists) {
  66. return <></>;
  67. }
  68. return <PageListMeta page={pageNode.page} basisViewersCount={basisViewersCount} />;
  69. }, [basisViewersCount, isExists, pageNode.page]);
  70. return (
  71. <li className="page-list-li">
  72. <small>{iconElement}</small> {pagePathElement}
  73. <span className="ml-2">{pageListMetaElement}</span>
  74. {childrenElements}
  75. </li>
  76. );
  77. });