Add lead and subtitle menu (#181)

* Add lead and subtitle menu

* resolve conversation
This commit is contained in:
Ilya Y 2023-08-17 07:31:03 +03:00 committed by GitHub
parent 542f669a94
commit e958f5c41d
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
6 changed files with 91 additions and 21 deletions

View File

@ -9,8 +9,10 @@
"Add cover": "Add cover", "Add cover": "Add cover",
"Add image": "Add image", "Add image": "Add image",
"Add images": "Add images", "Add images": "Add images",
"Add intro": "Add intro",
"Add link": "Add link", "Add link": "Add link",
"Add signature": "Add signature", "Add signature": "Add signature",
"Add subtitle": "Add subtitle",
"Add url": "Add url", "Add url": "Add url",
"Address on Discourse": "Address on Discourse", "Address on Discourse": "Address on Discourse",
"Album name": "Название aльбома", "Album name": "Название aльбома",
@ -70,8 +72,8 @@
"Create Group": "Create a group", "Create Group": "Create a group",
"Create account": "Create an account", "Create account": "Create an account",
"Create an account to add to your bookmarks": "Create an account to add to your bookmarks", "Create an account to add to your bookmarks": "Create an account to add to your bookmarks",
"Create an account to publish articles": "Create an account to publish articles",
"Create an account to participate in discussions": "Create an account to participate in discussions", "Create an account to participate in discussions": "Create an account to participate in discussions",
"Create an account to publish articles": "Create an account to publish articles",
"Create an account to subscribe": "Create an account to subscribe", "Create an account to subscribe": "Create an account to subscribe",
"Create an account to subscribe to new publications": "Create an account to subscribe to new publications", "Create an account to subscribe to new publications": "Create an account to subscribe to new publications",
"Create an account to vote": "Create an account to vote", "Create an account to vote": "Create an account to vote",
@ -103,8 +105,8 @@
"Enter text": "Enter text", "Enter text": "Enter text",
"Enter the Discours": "Enter the Discours", "Enter the Discours": "Enter the Discours",
"Enter the Discours to add to your bookmarks": "Enter the Discours to add to your bookmarks", "Enter the Discours to add to your bookmarks": "Enter the Discours to add to your bookmarks",
"Enter the Discours to publish articles": "Enter the Discours to publish articles",
"Enter the Discours to participate in discussions": "Enter the Discours to participate in discussions", "Enter the Discours to participate in discussions": "Enter the Discours to participate in discussions",
"Enter the Discours to publish articles": "Enter the Discours to publish articles",
"Enter the Discours to subscribe": "Enter the Discours to subscribe", "Enter the Discours to subscribe": "Enter the Discours to subscribe",
"Enter the Discours to subscribe to new publications": "Enter the Discours to subscribe to new publications", "Enter the Discours to subscribe to new publications": "Enter the Discours to subscribe to new publications",
"Enter the Discours to vote": "Enter the Discours to vote", "Enter the Discours to vote": "Enter the Discours to vote",
@ -283,6 +285,8 @@
"Terms of use": "Site rules", "Terms of use": "Site rules",
"Text checking": "Text checking", "Text checking": "Text checking",
"Thank you": "Thank you", "Thank you": "Thank you",
"There are unsaved changes in your profile settings. Are you sure you want to leave the page without saving?": "There are unsaved changes in your profile settings. Are you sure you want to leave the page without saving?",
"There are unsaved changes in your publishing settings. Are you sure you want to leave the page without saving?": "There are unsaved changes in your publishing settings. Are you sure you want to leave the page without saving?",
"This comment has not yet been rated": "This comment has not yet been rated", "This comment has not yet been rated": "This comment has not yet been rated",
"This email is already taken. If it's you": "This email is already taken. If it's you", "This email is already taken. If it's you": "This email is already taken. If it's you",
"This functionality is currently not available, we would like to work on this issue. Use the download link.": "This functionality is currently not available, we would like to work on this issue. Use the download link.", "This functionality is currently not available, we would like to work on this issue. Use the download link.": "This functionality is currently not available, we would like to work on this issue. Use the download link.",
@ -302,8 +306,6 @@
"Topic is supported by": "Topic is supported by", "Topic is supported by": "Topic is supported by",
"Topics": "Topics", "Topics": "Topics",
"Topics which supported by author": "Topics which supported by author", "Topics which supported by author": "Topics which supported by author",
"There are unsaved changes in your publishing settings. Are you sure you want to leave the page without saving?": "There are unsaved changes in your publishing settings. Are you sure you want to leave the page without saving?",
"There are unsaved changes in your profile settings. Are you sure you want to leave the page without saving?": "There are unsaved changes in your profile settings. Are you sure you want to leave the page without saving?",
"Try to find another way": "Try to find another way", "Try to find another way": "Try to find another way",
"Unfollow": "Unfollow", "Unfollow": "Unfollow",
"Unfollow the topic": "Unfollow the topic", "Unfollow the topic": "Unfollow the topic",

View File

@ -11,8 +11,10 @@
"Add cover": "Добавить обложку", "Add cover": "Добавить обложку",
"Add image": "Добавить изображение", "Add image": "Добавить изображение",
"Add images": "Добавить изображения", "Add images": "Добавить изображения",
"Add intro": "Добавить вступление",
"Add link": "Добавить ссылку", "Add link": "Добавить ссылку",
"Add signature": "Добавить подпись", "Add signature": "Добавить подпись",
"Add subtitle": "Добавить подзаголовок",
"Add to bookmarks": "Добавить в закладки", "Add to bookmarks": "Добавить в закладки",
"Add url": "Добавить ссылку", "Add url": "Добавить ссылку",
"Address on Discourse": "Адрес на Дискурсе", "Address on Discourse": "Адрес на Дискурсе",
@ -74,8 +76,8 @@
"Create Group": "Создать группу", "Create Group": "Создать группу",
"Create account": "Создать аккаунт", "Create account": "Создать аккаунт",
"Create an account to add to your bookmarks": "Создайте аккаунт, чтобы добавить в закладки", "Create an account to add to your bookmarks": "Создайте аккаунт, чтобы добавить в закладки",
"Create an account to publish articles": "Создайте аккаунт, чтобы публиковать статьи",
"Create an account to participate in discussions": "Создайте аккаунт для участия в дискуссиях", "Create an account to participate in discussions": "Создайте аккаунт для участия в дискуссиях",
"Create an account to publish articles": "Создайте аккаунт, чтобы публиковать статьи",
"Create an account to subscribe": "Создайте аккаунт, чтобы подписаться", "Create an account to subscribe": "Создайте аккаунт, чтобы подписаться",
"Create an account to subscribe to new publications": "Создайте аккаунт для подписки на новые публикации", "Create an account to subscribe to new publications": "Создайте аккаунт для подписки на новые публикации",
"Create an account to vote": "Создайте аккаунт, чтобы голосовать", "Create an account to vote": "Создайте аккаунт, чтобы голосовать",
@ -107,9 +109,9 @@
"Enter image title": "Введите название изображения", "Enter image title": "Введите название изображения",
"Enter text": "Введите текст", "Enter text": "Введите текст",
"Enter the Discours": "Войти в Дискурс", "Enter the Discours": "Войти в Дискурс",
"Enter the Discours to publish articles": "Войдите в Дискурс, чтобы публиковать статьи",
"Enter the Discours to add to your bookmarks": "Войдите в Дискурс, чтобы добавить в закладки", "Enter the Discours to add to your bookmarks": "Войдите в Дискурс, чтобы добавить в закладки",
"Enter the Discours to participate in discussions": "Войдите в Дискурс для участия в дискуссиях", "Enter the Discours to participate in discussions": "Войдите в Дискурс для участия в дискуссиях",
"Enter the Discours to publish articles": "Войдите в Дискурс, чтобы публиковать статьи",
"Enter the Discours to subscribe": "Войдите в Дискурс для подписки на новые публикации", "Enter the Discours to subscribe": "Войдите в Дискурс для подписки на новые публикации",
"Enter the Discours to subscribe to new publications": "Войдите в Дискурс, чтобы подписаться", "Enter the Discours to subscribe to new publications": "Войдите в Дискурс, чтобы подписаться",
"Enter the Discours to vote": "Войдите в Дискурс, чтобы голосовать", "Enter the Discours to vote": "Войдите в Дискурс, чтобы голосовать",
@ -300,6 +302,8 @@
"Terms of use": "Правила сайта", "Terms of use": "Правила сайта",
"Text checking": "Проверка текста", "Text checking": "Проверка текста",
"Thank you": "Благодарности", "Thank you": "Благодарности",
"There are unsaved changes in your profile settings. Are you sure you want to leave the page without saving?": "В настройках вашего профиля есть несохраненные изменения. Уверены, что хотите покинуть страницу без сохранения?",
"There are unsaved changes in your publishing settings. Are you sure you want to leave the page without saving?": "В настройках публикации есть несохраненные изменения. Уверены, что хотите покинуть страницу без сохранения?",
"This comment has not yet been rated": "Этот комментарий еще пока никто не оценил", "This comment has not yet been rated": "Этот комментарий еще пока никто не оценил",
"This email is already taken. If it's you": "Такой email уже зарегистрирован. Если это вы", "This email is already taken. If it's you": "Такой email уже зарегистрирован. Если это вы",
"This functionality is currently not available, we would like to work on this issue. Use the download link.": "В данный момент этот функционал не доступен, бы работаем над этой проблемой. Воспользуйтесь загрузкой по ссылке.", "This functionality is currently not available, we would like to work on this issue. Use the download link.": "В данный момент этот функционал не доступен, бы работаем над этой проблемой. Воспользуйтесь загрузкой по ссылке.",
@ -319,8 +323,6 @@
"Topic is supported by": "Тему поддерживают", "Topic is supported by": "Тему поддерживают",
"Topics": "Темы", "Topics": "Темы",
"Topics which supported by author": "Автор поддерживает темы", "Topics which supported by author": "Автор поддерживает темы",
"There are unsaved changes in your publishing settings. Are you sure you want to leave the page without saving?": "В настройках публикации есть несохраненные изменения. Уверены, что хотите покинуть страницу без сохранения?",
"There are unsaved changes in your profile settings. Are you sure you want to leave the page without saving?": "В настройках вашего профиля есть несохраненные изменения. Уверены, что хотите покинуть страницу без сохранения?",
"Try to find another way": "Попробуйте найти по-другому", "Try to find another way": "Попробуйте найти по-другому",
"Unfollow": "Отписаться", "Unfollow": "Отписаться",
"Unfollow the topic": "Отписаться от темы", "Unfollow the topic": "Отписаться от темы",

View File

@ -9,8 +9,23 @@
.container { .container {
position: relative; position: relative;
.headingActions {
@include font-size(1.2rem);
margin-bottom: 0.5rem;
display: flex;
flex-direction: row;
gap: 1rem;
color: var(--blue-link);
.action {
cursor: pointer;
}
}
.titleInput, .titleInput,
.subtitleInput { .subtitleInput,
.leadInput {
font-size: 36px; font-size: 36px;
line-height: 1.1; line-height: 1.1;
margin-bottom: 1.2rem; margin-bottom: 1.2rem;
@ -21,9 +36,14 @@
} }
} }
.leadInput {
font-size: unset;
}
.titleInput { .titleInput {
font-weight: 700; font-weight: 700;
} }
.additional { .additional {
margin-top: auto; margin-top: auto;

View File

@ -26,6 +26,8 @@ type Props = {
shout: Shout shout: Shout
} }
export const MAX_HEADER_LIMIT = 100
export const MAX_LEAD_LIMIT = 400
export const EMPTY_TOPIC: Topic = { export const EMPTY_TOPIC: Topic = {
id: -1, id: -1,
slug: '' slug: ''
@ -72,8 +74,13 @@ export const EditView = (props: Props) => {
}) })
} }
const subtitleInput: { current: HTMLTextAreaElement } = { current: null }
const leadInput: { current: HTMLTextAreaElement } = { current: null }
const [prevForm, setPrevForm] = createStore<ShoutForm>(clone(form)) const [prevForm, setPrevForm] = createStore<ShoutForm>(clone(form))
const [saving, setSaving] = createSignal(false) const [saving, setSaving] = createSignal(false)
const [isSubtitleVisible, setIsSubtitleVisible] = createSignal(Boolean(form.subtitle))
const [isLeadVisible, setIsLeadVisible] = createSignal(Boolean(form.lead))
const mediaItems: Accessor<MediaItem[]> = createMemo(() => { const mediaItems: Accessor<MediaItem[]> = createMemo(() => {
return JSON.parse(form.media || '[]') return JSON.parse(form.media || '[]')
@ -213,6 +220,15 @@ export const EditView = (props: Props) => {
stopAutoSave() stopAutoSave()
}) })
const showSubtitleInput = () => {
setIsSubtitleVisible(true)
subtitleInput.current.focus()
}
const showLeadInput = () => {
setIsLeadVisible(true)
leadInput.current.focus()
}
return ( return (
<> <>
<div class={styles.container}> <div class={styles.container}>
@ -233,6 +249,18 @@ export const EditView = (props: Props) => {
<div class="row"> <div class="row">
<div class="col-md-19 col-lg-18 col-xl-16 offset-md-5"> <div class="col-md-19 col-lg-18 col-xl-16 offset-md-5">
<Show when={page().route === 'edit'}> <Show when={page().route === 'edit'}>
<div class={styles.headingActions}>
<Show when={!isSubtitleVisible()}>
<div class={styles.action} onClick={showSubtitleInput}>
{t('Add subtitle')}
</div>
</Show>
<Show when={!isLeadVisible()}>
<div class={styles.action} onClick={showLeadInput}>
{t('Add intro')}
</div>
</Show>
</div>
<> <>
<div class={clsx({ [styles.audioHeader]: props.shout.layout === 'audio' })}> <div class={clsx({ [styles.audioHeader]: props.shout.layout === 'audio' })}>
<div class={styles.inputContainer}> <div class={styles.inputContainer}>
@ -242,7 +270,7 @@ export const EditView = (props: Props) => {
class={styles.titleInput} class={styles.titleInput}
placeholder={articleTitle()} placeholder={articleTitle()}
initialValue={form.title} initialValue={form.title}
maxLength={100} maxLength={MAX_HEADER_LIMIT}
/> />
<Show when={formErrors.title}> <Show when={formErrors.title}>
@ -277,17 +305,34 @@ export const EditView = (props: Props) => {
/> />
</div> </div>
</Show> </Show>
<Show when={props.shout.layout !== 'audio'}> <Show when={props.shout.layout !== 'audio'}>
<Show when={isSubtitleVisible()}>
<GrowingTextarea <GrowingTextarea
textAreaRef={(el) => {
subtitleInput.current = el
}}
allowEnterKey={false} allowEnterKey={false}
value={(value) => setForm('subtitle', value)} value={(value) => setForm('subtitle', value)}
class={styles.subtitleInput} class={styles.subtitleInput}
placeholder={t('Subheader')} placeholder={t('Subheader')}
initialValue={form.subtitle} initialValue={form.subtitle}
maxLength={100} maxLength={MAX_HEADER_LIMIT}
/> />
</Show> </Show>
<Show when={isLeadVisible()}>
<GrowingTextarea
textAreaRef={(el) => {
leadInput.current = el
}}
allowEnterKey={true}
value={(value) => setForm('lead', value)}
class={styles.leadInput}
placeholder={t('Description')}
initialValue={form.subtitle}
maxLength={MAX_LEAD_LIMIT}
/>
</Show>
</Show>
</div> </div>
<Show when={props.shout.layout === 'audio'}> <Show when={props.shout.layout === 'audio'}>
<Show <Show

View File

@ -10,7 +10,7 @@ import { useLocalize } from '../../../context/localize'
import { Modal } from '../../Nav/Modal' import { Modal } from '../../Nav/Modal'
import { Topic } from '../../../graphql/types.gen' import { Topic } from '../../../graphql/types.gen'
import { apiClient } from '../../../utils/apiClient' import { apiClient } from '../../../utils/apiClient'
import { EMPTY_TOPIC } from '../Edit' import { EMPTY_TOPIC, MAX_LEAD_LIMIT } from '../Edit'
import { useSession } from '../../../context/session' import { useSession } from '../../../context/session'
import { Icon } from '../../_shared/Icon' import { Icon } from '../../_shared/Icon'
import stylesBeside from '../../Feed/Beside.module.scss' import stylesBeside from '../../Feed/Beside.module.scss'
@ -25,7 +25,6 @@ type Props = {
form: ShoutForm form: ShoutForm
} }
const MAX_LEAD_LIMIT = 400
const shorten = (str: string, maxLen: number) => { const shorten = (str: string, maxLen: number) => {
if (str.length <= maxLen) return str if (str.length <= maxLen) return str
const result = str.slice(0, Math.max(0, str.lastIndexOf(' ', maxLen))).trim() const result = str.slice(0, Math.max(0, str.lastIndexOf(' ', maxLen))).trim()

View File

@ -11,6 +11,7 @@ type Props = {
allowEnterKey: boolean allowEnterKey: boolean
variant?: 'bordered' variant?: 'bordered'
fieldName?: string fieldName?: string
textAreaRef?: (el: HTMLTextAreaElement) => void
} }
export const GrowingTextarea = (props: Props) => { export const GrowingTextarea = (props: Props) => {
@ -42,6 +43,7 @@ export const GrowingTextarea = (props: Props) => {
</Show> </Show>
<div class={clsx(styles.growWrap, props.class)} data-replicated-value={value()}> <div class={clsx(styles.growWrap, props.class)} data-replicated-value={value()}>
<textarea <textarea
ref={props.textAreaRef}
rows={1} rows={1}
maxlength={props.maxLength} maxlength={props.maxLength}
autocomplete="off" autocomplete="off"