import type { Author, Shout, Topic } from '../../../graphql/schema/core.gen' import { getPagePath, openPage } from '@nanostores/router' import { clsx } from 'clsx' import { createMemo, createSignal, For, Show } from 'solid-js' import { useLocalize } from '../../../context/localize' import { useSession } from '../../../context/session' import { router, useRouter } from '../../../stores/router' import { capitalize } from '../../../utils/capitalize' import { getDescription } from '../../../utils/meta' import { Icon } from '../../_shared/Icon' import { Image } from '../../_shared/Image' import { Popover } from '../../_shared/Popover' import { CoverImage } from '../../Article/CoverImage' import { getShareUrl, SharePopup } from '../../Article/SharePopup' import { ShoutRatingControl } from '../../Article/ShoutRatingControl' import { AuthorLink } from '../../Author/AhtorLink' import { CardTopic } from '../CardTopic' import { FeedArticlePopup } from '../FeedArticlePopup' import styles from './ArticleCard.module.scss' import stylesHeader from '../../Nav/Header/Header.module.scss' export type ArticleCardProps = { // TODO: refactor this, please settings?: { noicon?: boolean noimage?: boolean nosubtitle?: boolean noauthor?: boolean nodate?: boolean isGroup?: boolean photoBottom?: boolean additionalClass?: string isFeedMode?: boolean isFloorImportant?: boolean isWithCover?: boolean isBigTitle?: boolean isVertical?: boolean isShort?: boolean withBorder?: boolean isCompact?: boolean isSingle?: boolean isBeside?: boolean withViewed?: boolean noAuthorLink?: boolean } desktopCoverSize: 'XS' | 'S' | 'M' | 'L' article: Shout } const desktopCoverImageWidths: Record = { XS: 300, S: 400, M: 600, L: 800, } const getTitleAndSubtitle = ( article: Shout, ): { title: string subtitle: string } => { let title = article.title let subtitle = article.subtitle if (!subtitle) { let tt = article.title?.split('. ') || [] if (tt?.length === 1) { tt = article.title?.split(/{!|\?|:|;}\s/) || [] } if (tt && tt.length > 1) { const sep = article.title?.replace(tt[0], '').split(' ', 1)[0] title = tt[0] + (sep === '.' || sep === ':' ? '' : sep) subtitle = capitalize(article.title?.replace(tt[0] + sep, ''), true) } } return { title, subtitle } } export const ArticleCard = (props: ArticleCardProps) => { const { t, lang, formatDate } = useLocalize() const { author } = useSession() const mainTopicSlug = props.article.main_topic const mainTopic = props.article.topics.find((tpc: Topic) => tpc.slug === mainTopicSlug) const mainTopicTitle = lang() === 'ru' && mainTopic?.title ? mainTopic.title : mainTopicSlug.replace('-', ' ') const formattedDate = createMemo(() => { return formatDate(new Date(props.article.created_at * 1000)) }) const { title, subtitle } = getTitleAndSubtitle(props.article) const canEdit = () => props.article.authors?.some((a) => a.slug === author()?.slug) || props.article.created_by?.id === author()?.id const { changeSearchParam } = useRouter() const scrollToComments = (event) => { event.preventDefault() openPage(router, 'article', { slug: props.article.slug }) changeSearchParam({ scrollTo: 'comments', }) } const [isActionPopupActive, setIsActionPopupActive] = createSignal(false) const [isCoverImageLoadError, setIsCoverImageLoadError] = createSignal(false) const [isCoverImageLoading, setIsCoverImageLoading] = createSignal(true) return (
} > {title} { setIsCoverImageLoadError(true) setIsCoverImageLoading(false) }} onLoad={() => setIsCoverImageLoading(false)} />
{(a: Author) => { return ( ) }}
{(triggerRef: (el) => void) => ( )} {(triggerRef: (el) => void) => (
)}
{(triggerRef: (el) => void) => (
setIsActionPopupActive(value)} trigger={ } />
)}
setIsActionPopupActive(value)} trigger={ } />
) }