import { memo, useCallback } from 'react' import PropTypes from 'prop-types' import { Dropdown, MenuItem } from 'react-bootstrap' import { Trans, useTranslation } from 'react-i18next' import Tooltip from '../../../shared/components/tooltip' import Icon from '../../../shared/components/icon' import IconChecked from '../../../shared/components/icon-checked' import ControlledDropdown from '../../../shared/components/controlled-dropdown' import { useLayoutContext } from '../../../shared/context/layout-context' import * as eventTracking from '../../../infrastructure/event-tracking' import useEventListener from '../../../shared/hooks/use-event-listener' function IconPlaceholder() { return } function IconRefresh() { return } function IconLayout() { return } function IconSplit() { return } function IconDetach() { return } function IconEditorOnly() { return } function IconPdfOnly() { return } function IconCheckmark({ iconFor, pdfLayout, view, detachRole }) { if (detachRole === 'detacher' || view === 'history') { return } if ( iconFor === 'editorOnly' && pdfLayout === 'flat' && (view === 'editor' || view === 'file') ) { return } else if (iconFor === 'pdfOnly' && pdfLayout === 'flat' && view === 'pdf') { return } else if (iconFor === 'sideBySide' && pdfLayout === 'sideBySide') { return } // return empty icon for placeholder return } function LayoutMenuItem({ checkmark, icon, text, ...props }) { return (
{checkmark}
{icon}
{text}
) } LayoutMenuItem.propTypes = { checkmark: PropTypes.node.isRequired, icon: PropTypes.node.isRequired, text: PropTypes.oneOfType([PropTypes.string, PropTypes.node]).isRequired, onSelect: PropTypes.func, } function DetachDisabled() { const { t } = useTranslation() return ( } icon={} text={t('pdf_in_separate_tab')} /> ) } function LayoutDropdownButton() { const { t } = useTranslation() const { reattach, detach, detachIsLinked, detachRole, changeLayout, view, pdfLayout, } = useLayoutContext(layoutContextPropTypes) const handleDetach = useCallback(() => { detach() eventTracking.sendMB('project-layout-detach') }, [detach]) const handleReattach = useCallback(() => { if (detachRole !== 'detacher') { return } reattach() eventTracking.sendMB('project-layout-reattach') }, [detachRole, reattach]) // reattach when the PDF pane opens useEventListener('ui:pdf-open', handleReattach) const handleChangeLayout = useCallback( (newLayout, newView) => { handleReattach() changeLayout(newLayout, newView) eventTracking.sendMB('project-layout-change', { layout: newLayout, view: newView, }) }, [changeLayout, handleReattach] ) const processing = !detachIsLinked && detachRole === 'detacher' // bsStyle is required for Dropdown.Toggle, but we will override style return ( <> {processing && (
{t('layout_processing')}
)} {processing ? : } {t('layout')} handleChangeLayout('sideBySide')} checkmark={ } icon={} text={&} /> handleChangeLayout('flat', 'editor')} checkmark={ } icon={} text={ , ]} /> } /> handleChangeLayout('flat', 'pdf')} checkmark={ } icon={} text={ , ]} /> } /> {'BroadcastChannel' in window ? ( handleDetach()} checkmark={ detachRole === 'detacher' ? ( detachIsLinked ? ( ) : ( ) ) : ( ) } icon={} text={t('pdf_in_separate_tab')} /> ) : ( )} ) } export default memo(LayoutDropdownButton) IconCheckmark.propTypes = { iconFor: PropTypes.string.isRequired, pdfLayout: PropTypes.string.isRequired, view: PropTypes.string, detachRole: PropTypes.string, } const layoutContextPropTypes = { reattach: PropTypes.func.isRequired, detach: PropTypes.func.isRequired, changeLayout: PropTypes.func.isRequired, detachIsLinked: PropTypes.bool, detachRole: PropTypes.string, pdfLayout: PropTypes.string.isRequired, view: PropTypes.string, }