webapp/src/components/Editor/Panel/Panel.tsx

267 lines
7.9 KiB
TypeScript
Raw Normal View History

import { clsx } from 'clsx'
2024-02-04 11:25:21 +00:00
import { Show, createSignal } from 'solid-js'
import { useEditorHTML } from 'solid-tiptap'
import Typograf from 'typograf'
2024-06-24 17:50:27 +00:00
import { useUI } from '~/context/ui'
import { useEditorContext } from '../../../context/editor'
import { useLocalize } from '../../../context/localize'
import { useEscKeyDownHandler } from '../../../utils/useEscKeyDownHandler'
import { useOutsideClickHandler } from '../../../utils/useOutsideClickHandler'
import { Button } from '../../_shared/Button'
import { DarkModeToggle } from '../../_shared/DarkModeToggle'
import { Icon } from '../../_shared/Icon'
2024-06-24 17:50:27 +00:00
import { A } from '@solidjs/router'
import styles from './Panel.module.scss'
const typograf = new Typograf({ locale: ['ru', 'en-US'] })
type Props = {
2023-05-08 17:21:06 +00:00
shoutId: number
2023-05-03 16:13:48 +00:00
}
export const Panel = (props: Props) => {
const { t } = useLocalize()
2024-06-24 17:50:27 +00:00
const { showModal } = useUI()
2024-05-03 08:36:15 +00:00
const {
isEditorPanelVisible,
wordCounter,
2024-06-24 17:50:27 +00:00
editor,
2024-05-03 08:36:15 +00:00
form,
toggleEditorPanel,
saveShout,
saveDraft,
publishShout,
} = useEditorContext()
2023-05-03 16:13:48 +00:00
2024-06-24 17:50:27 +00:00
let containerRef: HTMLElement | undefined
const [isShortcutsVisible, setIsShortcutsVisible] = createSignal(false)
const [isTypographyFixed, setIsTypographyFixed] = createSignal(false)
2023-05-03 16:13:48 +00:00
useOutsideClickHandler({
containerRef,
predicate: () => isEditorPanelVisible(),
handler: () => toggleEditorPanel(),
2023-05-03 16:13:48 +00:00
})
useEscKeyDownHandler(() => {
if (isEditorPanelVisible()) {
toggleEditorPanel()
}
})
const handleSaveClick = () => {
2024-05-03 08:36:15 +00:00
const hasTopics = form.selectedTopics?.length > 0
if (hasTopics) {
saveShout(form)
} else {
saveDraft(form)
}
2023-05-08 17:21:06 +00:00
}
2024-06-24 17:50:27 +00:00
const html = useEditorHTML(() => editor()) // FIXME: lost current() call
2024-02-05 15:49:08 +00:00
const handleFixTypographyClick = () => {
2024-06-24 17:50:27 +00:00
editor()?.commands.setContent(typograf.execute(html() || '')) // here too
setIsTypographyFixed(true)
}
return (
2023-05-03 16:13:48 +00:00
<aside
2024-06-24 17:50:27 +00:00
ref={(el) => (containerRef = el)}
2023-05-03 16:13:48 +00:00
class={clsx('col-md-6', styles.Panel, { [styles.hidden]: !isEditorPanelVisible() })}
>
<Button
value={<Icon name="close" />}
variant={'inline'}
class={styles.close}
onClick={() => toggleEditorPanel()}
/>
<div class={clsx(styles.actionsHolder, styles.scrolled, { hidden: isShortcutsVisible() })}>
<section>
2023-05-03 16:13:48 +00:00
<p>
2024-02-12 08:12:23 +00:00
<span class={styles.link} onClick={() => publishShout(form)}>
2023-05-08 17:21:06 +00:00
{t('Publish')}
</span>
2023-05-03 16:13:48 +00:00
</p>
<p>
<span class={styles.link} onClick={handleSaveClick}>
2023-05-08 17:21:06 +00:00
{t('Save draft')}
</span>
2023-05-03 16:13:48 +00:00
</p>
</section>
<section>
2023-05-03 16:13:48 +00:00
<p>
<span class={styles.link} onClick={() => showModal('inviteMembers')}>
{t('Invite co-authors')}
</span>
2023-05-03 16:13:48 +00:00
</p>
<p>
2024-06-24 17:50:27 +00:00
<A
class={styles.link}
onClick={() => toggleEditorPanel()}
2024-06-24 17:50:27 +00:00
href={`/edit/${props.shoutId}/settings`}
>
2023-05-03 16:13:48 +00:00
{t('Publication settings')}
2024-06-24 17:50:27 +00:00
</A>
2023-05-03 16:13:48 +00:00
</p>
<p>
<span class={styles.link}>{t('Corrections history')}</span>
2023-05-03 16:13:48 +00:00
</p>
</section>
<section>
<div class={styles.typograph}>
<div>
<span class={styles.link} onClick={handleFixTypographyClick}>
{t('Autotypograph')}
</span>
</div>
<Show when={isTypographyFixed()}>
<div class={clsx(styles.typographStatus, styles.typographStatusSuccess)}>{t('Fixed')}</div>
</Show>
</div>
<p>{t('Text checking')}</p>
</section>
<section>
<DarkModeToggle />
</section>
<section>
<p>
<a class={styles.link} href="/how-to-write-a-good-article">
{t('How to write a good article')}
</a>
</p>
<p>
<button class={styles.link} onClick={() => setIsShortcutsVisible(true)}>
{t('Hotkeys')}
</button>
</p>
<p>
<a class={styles.link} href="#">
{t('Help')}
</a>
</p>
</section>
<div class={styles.stats}>
<div>
{t('Characters')}: <em>{wordCounter().characters}</em>
</div>
<div>
{t('Words')}: <em>{wordCounter().words}</em>
</div>
2023-05-03 16:13:48 +00:00
{/*<div>*/}
{/* {t('Last rev.')}: <em>22.03.22 в 18:20</em>*/}
{/*</div>*/}
</div>
</div>
<div class={clsx(styles.actionsHolder, styles.scrolled, { hidden: !isShortcutsVisible() })}>
<p>
<button class={styles.backToMenuControl} onClick={() => setIsShortcutsVisible(false)}>
{t('back to menu"')}
</button>
</p>
<section class={styles.shortcutList}>
<p>
{t('bold')}
<span class={styles.shortcut}>
<span class={styles.shortcutButton}>Ctrl</span>
<span class={styles.shortcutButton}>B</span>
</span>
</p>
<p>
{t('italic')}
<span class={styles.shortcut}>
<span class={styles.shortcutButton}>Ctrl</span>
<span class={styles.shortcutButton}>I</span>
</span>
</p>
<p>
{t('add link')}
<span class={styles.shortcut}>
<span class={styles.shortcutButton}>Ctrl</span>
<span class={styles.shortcutButton}>K</span>
</span>
</p>
</section>
<section class={styles.shortcutList}>
<p>
{t('header 1')}
<span class={styles.shortcut}>
<span class={styles.shortcutButton}>Ctrl</span>
<span class={styles.shortcutButton}>Alt</span>
<span class={styles.shortcutButton}>1</span>
</span>
</p>
<p>
{t('header 2')}
<span class={styles.shortcut}>
<span class={styles.shortcutButton}>Ctrl</span>
<span class={styles.shortcutButton}>Alt</span>
<span class={styles.shortcutButton}>2</span>
</span>
</p>
<p>
{t('header 3')}
<span class={styles.shortcut}>
<span class={styles.shortcutButton}>Ctrl</span>
<span class={styles.shortcutButton}>Alt</span>
<span class={styles.shortcutButton}>3</span>
</span>
</p>
</section>
<section class={styles.shortcutList}>
<p>
{t('marker list')}
<span class={styles.shortcut}>
<span class={styles.shortcutButton}>*</span>
<span class={styles.shortcutButton}>Space</span>
</span>
</p>
<p>
{t('number list')}
<span class={styles.shortcut}>
<span class={styles.shortcutButton}>1</span>
<span class={styles.shortcutButton}>Space</span>
</span>
</p>
<p>
{t('delimiter')}
<span class={styles.shortcut}>
<span class={styles.shortcutButton}>***</span>
<span class={styles.shortcutButton}>Enter</span>
</span>
</p>
</section>
<section class={styles.shortcutList}>
<p>
{t('cancel')}
<span class={styles.shortcut}>
<span class={styles.shortcutButton}>Ctrl</span>
<span class={styles.shortcutButton}>Z</span>
</span>
</p>
<p>
{t('repeat')}
<span class={styles.shortcut}>
<span class={styles.shortcutButton}>Ctrl</span>
<span class={styles.shortcutButton}>Shift</span>
<span class={styles.shortcutButton}>Z</span>
</span>
</p>
</section>
</div>
</aside>
)
}