EditPage.tsx 1.8 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374
  1. import { useCallback, useEffect, useRef } from 'react';
  2. import { useTranslation } from 'next-i18next';
  3. import { useStartEditing } from '~/client/services/use-start-editing';
  4. import { toastError } from '~/client/util/toastr';
  5. import { useCurrentPathname } from '~/states/global';
  6. import { useIsEditable, useCurrentPagePath } from '~/states/page';
  7. type Props = {
  8. onDeleteRender: () => void,
  9. }
  10. /**
  11. * Custom hook for edit page logic
  12. */
  13. const useEditPage = (
  14. onCompleted: () => void,
  15. onError?: (path: string) => void,
  16. ): void => {
  17. const isEditable = useIsEditable();
  18. const startEditing = useStartEditing();
  19. const currentPagePath = useCurrentPagePath();
  20. const currentPathname = useCurrentPathname();
  21. const path = currentPagePath ?? currentPathname;
  22. const isExecutedRef = useRef(false);
  23. useEffect(() => {
  24. (async() => {
  25. // Prevent multiple executions
  26. if (isExecutedRef.current) return;
  27. isExecutedRef.current = true;
  28. if (!isEditable) {
  29. return;
  30. }
  31. // ignore when dom that has 'modal in' classes exists
  32. if (document.getElementsByClassName('modal in').length > 0) {
  33. return;
  34. }
  35. try {
  36. await startEditing(path);
  37. }
  38. catch (err) {
  39. onError?.(path);
  40. }
  41. onCompleted();
  42. })();
  43. }, [startEditing, isEditable, path, onCompleted, onError]);
  44. };
  45. /**
  46. * EditPage component - handles hotkey 'e' for editing
  47. */
  48. const EditPage = (props: Props): null => {
  49. const { t } = useTranslation('commons');
  50. const handleError = useCallback((path: string) => {
  51. toastError(t('toaster.create_failed', { target: path }));
  52. }, [t]);
  53. useEditPage(props.onDeleteRender, handleError);
  54. return null;
  55. };
  56. EditPage.getHotkeyStrokes = () => {
  57. return [['e']];
  58. };
  59. export default EditPage;