editor-properties-context.tsx 3.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114
  1. import {
  2. createContext,
  3. Dispatch,
  4. FC,
  5. PropsWithChildren,
  6. SetStateAction,
  7. useCallback,
  8. useContext,
  9. useState,
  10. } from 'react'
  11. import customLocalStorage from '@/infrastructure/local-storage'
  12. import usePersistedState from '@/shared/hooks/use-persisted-state'
  13. import getMeta from '@/utils/meta'
  14. import { useUnstableStoreSync } from '@/shared/hooks/use-unstable-store-sync'
  15. import { sendMB } from '@/infrastructure/event-tracking'
  16. // Context value type
  17. export type EditorPropertiesContextValue = {
  18. showVisual: boolean
  19. setShowVisual: Dispatch<SetStateAction<boolean>>
  20. showSymbolPalette: boolean
  21. setShowSymbolPalette: Dispatch<SetStateAction<boolean>>
  22. toggleSymbolPalette: () => void
  23. opening: boolean
  24. setOpening: Dispatch<SetStateAction<boolean>>
  25. trackChanges: boolean
  26. setTrackChanges: Dispatch<SetStateAction<boolean>>
  27. wantTrackChanges: boolean
  28. setWantTrackChanges: Dispatch<SetStateAction<boolean>>
  29. errorState: boolean
  30. setErrorState: Dispatch<SetStateAction<boolean>>
  31. }
  32. export const EditorPropertiesContext = createContext<
  33. EditorPropertiesContextValue | undefined
  34. >(undefined)
  35. function showVisualFallbackValue() {
  36. const projectId = getMeta('ol-project_id')
  37. const editorModeKey = `editor.mode.${projectId}`
  38. const editorModeVal = customLocalStorage.getItem(editorModeKey)
  39. if (editorModeVal) {
  40. // clean up the old key
  41. customLocalStorage.removeItem(editorModeKey)
  42. }
  43. return editorModeVal === 'rich-text'
  44. }
  45. export const EditorPropertiesProvider: FC<PropsWithChildren> = ({
  46. children,
  47. }) => {
  48. const [showVisual, setShowVisual] = usePersistedState(
  49. `editor.lastUsedMode`,
  50. showVisualFallbackValue(),
  51. {
  52. converter: {
  53. toPersisted: showVisual => (showVisual ? 'visual' : 'code'),
  54. fromPersisted: mode => mode === 'visual',
  55. },
  56. }
  57. )
  58. // Sync the showVisual state with the exposed store
  59. useUnstableStoreSync('editor.showVisual', showVisual)
  60. const [showSymbolPalette, setShowSymbolPalette] = useState(false)
  61. const toggleSymbolPalette = useCallback(() => {
  62. setShowSymbolPalette(show => {
  63. const newValue = !show
  64. sendMB(newValue ? 'symbol-palette-show' : 'symbol-palette-hide')
  65. return newValue
  66. })
  67. }, [setShowSymbolPalette])
  68. const [opening, setOpening] = useState(true)
  69. const [trackChanges, setTrackChanges] = useState(false)
  70. const [wantTrackChanges, setWantTrackChanges] = useState(false)
  71. const [errorState, setErrorState] = useState(false)
  72. const value = {
  73. showVisual,
  74. setShowVisual,
  75. showSymbolPalette,
  76. setShowSymbolPalette,
  77. toggleSymbolPalette,
  78. opening,
  79. setOpening,
  80. trackChanges,
  81. setTrackChanges,
  82. wantTrackChanges,
  83. setWantTrackChanges,
  84. errorState,
  85. setErrorState,
  86. }
  87. return (
  88. <EditorPropertiesContext.Provider value={value}>
  89. {children}
  90. </EditorPropertiesContext.Provider>
  91. )
  92. }
  93. export const useEditorPropertiesContext = (): EditorPropertiesContextValue => {
  94. const context = useContext(EditorPropertiesContext)
  95. if (!context) {
  96. throw new Error(
  97. 'useEditorPropertiesContext is only available inside EditorPropertiesContext.Provider'
  98. )
  99. }
  100. return context
  101. }