editor-switch.tsx 2.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107
  1. import { ChangeEvent, FC, memo, useCallback } from 'react'
  2. import useScopeValue from '@/shared/hooks/use-scope-value'
  3. import OLTooltip from '@/features/ui/components/ol/ol-tooltip'
  4. import { sendMB } from '../../../infrastructure/event-tracking'
  5. import { isValidTeXFile } from '../../../main/is-valid-tex-file'
  6. import { useTranslation } from 'react-i18next'
  7. import { useEditorManagerContext } from '@/features/ide-react/context/editor-manager-context'
  8. function EditorSwitch() {
  9. const { t } = useTranslation()
  10. const [visual, setVisual] = useScopeValue('editor.showVisual')
  11. const { openDocName } = useEditorManagerContext()
  12. const richTextAvailable = openDocName ? isValidTeXFile(openDocName) : false
  13. const handleChange = useCallback(
  14. (event: ChangeEvent<HTMLInputElement>) => {
  15. const editorType = event.target.value
  16. switch (editorType) {
  17. case 'cm6':
  18. setVisual(false)
  19. break
  20. case 'rich-text':
  21. setVisual(true)
  22. break
  23. }
  24. sendMB('editor-switch-change', { editorType })
  25. },
  26. [setVisual]
  27. )
  28. return (
  29. <div
  30. className="editor-toggle-switch"
  31. aria-label={t('toolbar_code_visual_editor_switch')}
  32. >
  33. <fieldset className="toggle-switch">
  34. <legend className="sr-only">Editor mode.</legend>
  35. <input
  36. type="radio"
  37. name="editor"
  38. value="cm6"
  39. id="editor-switch-cm6"
  40. className="toggle-switch-input"
  41. checked={!richTextAvailable || !visual}
  42. onChange={handleChange}
  43. />
  44. <label htmlFor="editor-switch-cm6" className="toggle-switch-label">
  45. <span>{t('code_editor')}</span>
  46. </label>
  47. <RichTextToggle
  48. checked={richTextAvailable && visual}
  49. disabled={!richTextAvailable}
  50. handleChange={handleChange}
  51. />
  52. </fieldset>
  53. </div>
  54. )
  55. }
  56. const RichTextToggle: FC<{
  57. checked: boolean
  58. disabled: boolean
  59. handleChange: (event: ChangeEvent<HTMLInputElement>) => void
  60. }> = ({ checked, disabled, handleChange }) => {
  61. const { t } = useTranslation()
  62. const toggle = (
  63. <span>
  64. <input
  65. type="radio"
  66. name="editor"
  67. value="rich-text"
  68. id="editor-switch-rich-text"
  69. className="toggle-switch-input"
  70. checked={checked}
  71. onChange={handleChange}
  72. disabled={disabled}
  73. />
  74. <label htmlFor="editor-switch-rich-text" className="toggle-switch-label">
  75. <span>{t('visual_editor')}</span>
  76. </label>
  77. </span>
  78. )
  79. if (disabled) {
  80. return (
  81. <OLTooltip
  82. description={t('visual_editor_is_only_available_for_tex_files')}
  83. id="rich-text-toggle-tooltip"
  84. overlayProps={{ placement: 'bottom' }}
  85. tooltipProps={{ className: 'tooltip-wide' }}
  86. >
  87. {toggle}
  88. </OLTooltip>
  89. )
  90. }
  91. return toggle
  92. }
  93. export default memo(EditorSwitch)