WIP Comments
This commit is contained in:
parent
f6ec3558d6
commit
57f1d026da
|
@ -1,3 +1,3 @@
|
|||
<svg width="12" height="12" viewBox="0 0 12 12" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<path d="M1 1L6 6M6 6L1 11M6 6L11 1M6 6L11 11" stroke="#696969" stroke-width="2"/>
|
||||
<path d="M1 1L6 6M6 6L1 11M6 6L11 1M6 6L11 11" stroke="#000" stroke-width="2"/>
|
||||
</svg>
|
||||
|
|
Before Width: | Height: | Size: 186 B After Width: | Height: | Size: 183 B |
|
@ -1,3 +1,4 @@
|
|||
<svg width="12" height="14" viewBox="0 0 12 14" fill="none" xmlns="http://www.w3.org/2000/svg">
|
||||
<path d="M6 0C2.69432 0 0 2.6826 0 5.97389C0 9.26518 2.69432 11.9478 6 11.9478V14L7.02604 13.3453C8.5166 12.3934 11.2347 10.3384 11.8659 7.22363C11.9523 6.82188 12 6.40385 12 5.97389C12 2.6826 9.30568 0 6 0Z" fill="#696969"/>
|
||||
<path
|
||||
d="M6 0C2.69432 0 0 2.6826 0 5.97389C0 9.26518 2.69432 11.9478 6 11.9478V14L7.02604 13.3453C8.5166 12.3934 11.2347 10.3384 11.8659 7.22363C11.9523 6.82188 12 6.40385 12 5.97389C12 2.6826 9.30568 0 6 0Z" fill="#000"/>
|
||||
</svg>
|
||||
|
|
Before Width: | Height: | Size: 329 B After Width: | Height: | Size: 328 B |
204
src/components/Article/Comment.module.scss
Normal file
204
src/components/Article/Comment.module.scss
Normal file
|
@ -0,0 +1,204 @@
|
|||
.comment {
|
||||
background-color: #fff;
|
||||
margin: 0 -2.4rem 1.5em;
|
||||
padding: 0.8rem 2.4rem;
|
||||
transition: background-color 0.3s;
|
||||
|
||||
&:hover {
|
||||
background-color: #f6f6f6;
|
||||
|
||||
.commentControlShare,
|
||||
.commentControlDelete,
|
||||
.commentControlEdit,
|
||||
.commentControlComplain {
|
||||
opacity: 1;
|
||||
}
|
||||
}
|
||||
|
||||
.shout-body {
|
||||
@include font-size(1.5rem);
|
||||
|
||||
margin-bottom: 1em;
|
||||
|
||||
*:last-child {
|
||||
margin-bottom: 0;
|
||||
}
|
||||
}
|
||||
|
||||
.author {
|
||||
align-items: center;
|
||||
margin-bottom: 1.4rem;
|
||||
}
|
||||
}
|
||||
|
||||
.commentLevel1 {
|
||||
margin-left: 3.2rem;
|
||||
}
|
||||
|
||||
.commentLevel2 {
|
||||
margin-left: 6.4rem;
|
||||
}
|
||||
|
||||
.commentLevel3 {
|
||||
margin-left: 9.6rem;
|
||||
}
|
||||
|
||||
.commentLevel4 {
|
||||
margin-left: 12.8rem;
|
||||
}
|
||||
|
||||
.commentLevel5 {
|
||||
margin-left: 16rem;
|
||||
}
|
||||
|
||||
.commentControls {
|
||||
@include font-size(1.2rem);
|
||||
margin-bottom: 0.5em;
|
||||
}
|
||||
|
||||
.commentControlShare,
|
||||
.commentControlDelete,
|
||||
.commentControlEdit,
|
||||
.commentControlComplain {
|
||||
@include media-breakpoint-up(md) {
|
||||
opacity: 0;
|
||||
transition: opacity 0.3s;
|
||||
}
|
||||
}
|
||||
|
||||
.commentControlShare,
|
||||
.commentControlDelete,
|
||||
.commentControlEdit {
|
||||
.icon {
|
||||
line-height: 1.2;
|
||||
}
|
||||
}
|
||||
|
||||
.commentControlShare {
|
||||
.icon {
|
||||
height: 1.2rem;
|
||||
width: 1.2rem;
|
||||
}
|
||||
}
|
||||
|
||||
.commentControl {
|
||||
border: none;
|
||||
color: #696969;
|
||||
cursor: pointer;
|
||||
display: inline-flex;
|
||||
line-height: 1.2;
|
||||
margin-right: 0.8rem;
|
||||
padding: 0.2em 0.3em;
|
||||
transition: opacity 0.2s, color 0.3s, background-color 0.3s;
|
||||
vertical-align: top;
|
||||
|
||||
&:hover {
|
||||
background: #000;
|
||||
color: #fff;
|
||||
|
||||
.icon {
|
||||
filter: invert(1);
|
||||
opacity: 1;
|
||||
}
|
||||
}
|
||||
|
||||
.icon {
|
||||
filter: invert(0);
|
||||
margin-right: 0.3em;
|
||||
opacity: 0.6;
|
||||
transition: filter 0.3s, opacity 0.2s;
|
||||
|
||||
img {
|
||||
margin-bottom: -0.1em;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.commentControlReply {
|
||||
.icon {
|
||||
height: 1.2em;
|
||||
width: 1.2em;
|
||||
}
|
||||
}
|
||||
|
||||
.commentBody {
|
||||
@include font-size(1.5rem);
|
||||
line-height: 1.47;
|
||||
}
|
||||
|
||||
.commentAuthor,
|
||||
.commentDate,
|
||||
.commentRating {
|
||||
@include font-size(1.2rem);
|
||||
}
|
||||
|
||||
.commentDate {
|
||||
color: rgb(0 0 0 / 30%);
|
||||
flex: 1;
|
||||
|
||||
@include media-breakpoint-down(md) {
|
||||
margin-left: 1rem;
|
||||
}
|
||||
}
|
||||
|
||||
.commentDetails {
|
||||
display: flex;
|
||||
margin-bottom: 1.2rem;
|
||||
}
|
||||
|
||||
.commentRating {
|
||||
align-items: center;
|
||||
display: flex;
|
||||
font-weight: bold;
|
||||
}
|
||||
|
||||
.commentRatingValue {
|
||||
padding: 0 0.3em;
|
||||
}
|
||||
|
||||
.commentRatingPositive {
|
||||
color: #2bb452;
|
||||
}
|
||||
|
||||
.commentRatingNegative {
|
||||
color: #d00820;
|
||||
}
|
||||
|
||||
.commentRatingControl {
|
||||
border-left: 6px solid transparent;
|
||||
border-right: 6px solid transparent;
|
||||
height: 0;
|
||||
width: 0;
|
||||
}
|
||||
|
||||
.commentRatingControlUp {
|
||||
border-bottom: 8px solid rgb(0 0 0 / 40%);
|
||||
}
|
||||
|
||||
.commentRatingControlDown {
|
||||
border-top: 8px solid rgb(0 0 0 / 40%);
|
||||
}
|
||||
|
||||
.replyForm {
|
||||
background: #fff;
|
||||
border: 2px solid rgb(38 56 217 / 50%);
|
||||
border-radius: 0.8rem;
|
||||
margin-left: 2.4rem;
|
||||
position: relative;
|
||||
|
||||
textarea {
|
||||
border: none;
|
||||
border-radius: 0.8rem;
|
||||
padding-top: 1.2rem;
|
||||
}
|
||||
}
|
||||
|
||||
.replyFormControls {
|
||||
padding: 0.5rem 1.6rem 1.6rem;
|
||||
text-align: right;
|
||||
|
||||
button {
|
||||
@include font-size(1.6rem);
|
||||
margin-left: 1.2rem;
|
||||
}
|
||||
}
|
|
@ -1,119 +0,0 @@
|
|||
.comment {
|
||||
background-color: #fff;
|
||||
margin: 0 -2.4rem 1.5em;
|
||||
padding: 0.8rem 2.4rem;
|
||||
transition: background-color 0.3s;
|
||||
|
||||
&:hover {
|
||||
background-color: #f6f6f6;
|
||||
|
||||
.comment-control--share,
|
||||
.comment-control--delete,
|
||||
.comment-control--edit,
|
||||
.comment-control--complain {
|
||||
opacity: 1;
|
||||
}
|
||||
}
|
||||
|
||||
.shout-body {
|
||||
@include font-size(1.5rem);
|
||||
|
||||
margin-bottom: 1em;
|
||||
|
||||
*:last-child {
|
||||
margin-bottom: 0;
|
||||
}
|
||||
}
|
||||
|
||||
.circlewrap {
|
||||
position: absolute;
|
||||
}
|
||||
|
||||
.author {
|
||||
align-items: center;
|
||||
margin-bottom: 1.4rem;
|
||||
}
|
||||
|
||||
.author__name {
|
||||
font-weight: bold;
|
||||
@include font-size(1.2rem);
|
||||
|
||||
margin-bottom: 0;
|
||||
}
|
||||
|
||||
.author__details {
|
||||
margin-left: 4rem;
|
||||
}
|
||||
|
||||
.shout-date {
|
||||
@include font-size(1.2rem);
|
||||
|
||||
flex: 1;
|
||||
color: rgb(0 0 0 / 30%);
|
||||
}
|
||||
}
|
||||
|
||||
.comment--level-1 {
|
||||
margin-left: 2.4rem;
|
||||
}
|
||||
|
||||
.comment--level-2 {
|
||||
margin-left: 4.8rem;
|
||||
}
|
||||
|
||||
.comment--level-3 {
|
||||
margin-left: 7.2rem;
|
||||
}
|
||||
|
||||
.comment--level-4 {
|
||||
margin-left: 9.6rem;
|
||||
}
|
||||
|
||||
.comment--level-5 {
|
||||
margin-left: 12rem;
|
||||
}
|
||||
|
||||
.shout-controls {
|
||||
align-items: baseline;
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
padding-top: 0.8rem;
|
||||
}
|
||||
|
||||
.comment-controls {
|
||||
margin-bottom: 0.5em;
|
||||
}
|
||||
|
||||
.comment-control--share,
|
||||
.comment-control--delete,
|
||||
.comment-control--edit,
|
||||
.comment-control--complain {
|
||||
opacity: 0;
|
||||
transition: opacity 0.3s;
|
||||
}
|
||||
|
||||
.comment-control {
|
||||
background: rgb(0 0 0 / 5%);
|
||||
border: none;
|
||||
cursor: pointer;
|
||||
display: inline-flex;
|
||||
line-height: 1.2;
|
||||
margin-right: 0.8rem;
|
||||
padding: 0.2em 0.3em;
|
||||
vertical-align: top;
|
||||
|
||||
.icon {
|
||||
margin-right: 0.3em;
|
||||
|
||||
img {
|
||||
margin-bottom: -0.1em;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.comment-control--reply {
|
||||
.icon {
|
||||
height: 1.2em;
|
||||
width: 1.2em;
|
||||
}
|
||||
}
|
|
@ -1,13 +1,16 @@
|
|||
import './Comment.scss'
|
||||
import styles from './Comment.module.scss'
|
||||
import { Icon } from '../_shared/Icon'
|
||||
import { AuthorCard } from '../Author/Card'
|
||||
import { Show, createMemo } from 'solid-js'
|
||||
import { Show, createMemo, createSignal } from 'solid-js'
|
||||
import { clsx } from 'clsx'
|
||||
import type { Author, Reaction as Point } from '../../graphql/types.gen'
|
||||
import { t } from '../../utils/intl'
|
||||
// import { createReaction, updateReaction, deleteReaction } from '../../stores/zine/reactions'
|
||||
import MD from './MD'
|
||||
import { deleteReaction } from '../../stores/zine/reactions'
|
||||
import { formatDate } from '../../utils'
|
||||
import { SharePopup } from './SharePopup'
|
||||
import stylesHeader from '../Nav/Header.module.scss'
|
||||
|
||||
export default (props: {
|
||||
level?: number
|
||||
|
@ -15,6 +18,9 @@ export default (props: {
|
|||
canEdit?: boolean
|
||||
compact?: boolean
|
||||
}) => {
|
||||
const [isSharePopupVisible, setIsSharePopupVisible] = createSignal(false)
|
||||
const [isReplyVisible, setIsReplyVisible] = createSignal(false)
|
||||
|
||||
const comment = createMemo(() => props.comment)
|
||||
const body = createMemo(() => (comment().body || '').trim())
|
||||
const remove = () => {
|
||||
|
@ -23,19 +29,22 @@ export default (props: {
|
|||
deleteReaction(comment().id)
|
||||
}
|
||||
}
|
||||
const formattedDate = createMemo(() =>
|
||||
formatDate(new Date(comment()?.createdAt), { hour: 'numeric', minute: 'numeric' })
|
||||
)
|
||||
|
||||
return (
|
||||
<div class={clsx('comment', { [`comment--level-${props.level}`]: Boolean(props.level) })}>
|
||||
<div class={clsx(styles.comment, { [styles[`commentLevel${props.level}`]]: Boolean(props.level) })}>
|
||||
<Show when={!!body()}>
|
||||
<div class="comment__content">
|
||||
<div class={styles.commentContent}>
|
||||
<Show
|
||||
when={!props.compact}
|
||||
fallback={
|
||||
<div class="comment__details">
|
||||
<div class={styles.commentDetails}>
|
||||
<a href={`/author/${comment()?.createdBy?.slug}`}>
|
||||
@{(comment()?.createdBy || { name: 'anonymous' }).name}
|
||||
</a>
|
||||
<div class="comment__article">
|
||||
<div class={styles.commentArticle}>
|
||||
<Icon name="reply-arrow" />
|
||||
<a href={`#comment-${comment()?.id}`}>
|
||||
#{(comment()?.shout || { title: 'Lorem ipsum titled' }).title}
|
||||
|
@ -44,60 +53,100 @@ export default (props: {
|
|||
</div>
|
||||
}
|
||||
>
|
||||
<div class="comment__details">
|
||||
<div class="comment-author">
|
||||
<div class={styles.commentDetails}>
|
||||
<div class={styles.commentAuthor}>
|
||||
<AuthorCard
|
||||
author={comment()?.createdBy as Author}
|
||||
hideDescription={true}
|
||||
hideFollow={true}
|
||||
isComments={true}
|
||||
hasLink={true}
|
||||
/>
|
||||
</div>
|
||||
|
||||
<div class="comment-date">{comment()?.createdAt}</div>
|
||||
<div class="comment-rating">{comment().stat?.rating || 0}</div>
|
||||
<div class={styles.commentDate}>{formattedDate()}</div>
|
||||
<div
|
||||
class={styles.commentRating}
|
||||
classList={{
|
||||
[styles.commentRatingPositive]: comment().stat?.rating > 0,
|
||||
[styles.commentRatingNegative]: comment().stat?.rating < 0
|
||||
}}
|
||||
>
|
||||
<button class={clsx(styles.commentRatingControl, styles.commentRatingControlUp)}></button>
|
||||
<div class={styles.commentRatingValue}>{comment().stat?.rating || 0}</div>
|
||||
<button class={clsx(styles.commentRatingControl, styles.commentRatingControlDown)}></button>
|
||||
</div>
|
||||
</div>
|
||||
</Show>
|
||||
|
||||
<div class="comment-body" contenteditable={props.canEdit} id={'comment-' + (comment().id || '')}>
|
||||
<div
|
||||
class={styles.commentBody}
|
||||
contenteditable={props.canEdit}
|
||||
id={'comment-' + (comment().id || '')}
|
||||
>
|
||||
<MD body={body()} />
|
||||
</div>
|
||||
|
||||
<Show when={!props.compact}>
|
||||
<div class="comment-controls">
|
||||
<button class="comment-control comment-control--reply">
|
||||
<Icon name="reply" />
|
||||
<div class={styles.commentControls}>
|
||||
<button
|
||||
class={clsx(styles.commentControl, styles.commentControlReply)}
|
||||
onClick={() => setIsReplyVisible(!isReplyVisible())}
|
||||
>
|
||||
<Icon name="reply" class={styles.icon} />
|
||||
{t('Reply')}
|
||||
</button>
|
||||
|
||||
<Show when={props.canEdit}>
|
||||
{/*FIXME implement edit comment modal*/}
|
||||
{/*<button*/}
|
||||
{/* class="comment-control comment-control--edit"*/}
|
||||
{/* class={clsx(styles.commentControl, styles.commentControlEdit)}*/}
|
||||
{/* onClick={() => showModal('editComment')}*/}
|
||||
{/*>*/}
|
||||
{/* <Icon name="edit" />*/}
|
||||
{/* <Icon name="edit" class={styles.icon} />*/}
|
||||
{/* {t('Edit')}*/}
|
||||
{/*</button>*/}
|
||||
<button class="comment-control comment-control--delete" onClick={() => remove()}>
|
||||
<Icon name="delete" />
|
||||
<button
|
||||
class={clsx(styles.commentControl, styles.commentControlDelete)}
|
||||
onClick={() => remove()}
|
||||
>
|
||||
<Icon name="delete" class={styles.icon} />
|
||||
{t('Delete')}
|
||||
</button>
|
||||
</Show>
|
||||
|
||||
{/*FIXME implement modals */}
|
||||
<SharePopup
|
||||
onVisibilityChange={(isVisible) => {
|
||||
setIsSharePopupVisible(isVisible)
|
||||
}}
|
||||
containerCssClass={stylesHeader.control}
|
||||
trigger={
|
||||
<button class={clsx(styles.commentControl, styles.commentControlShare)}>
|
||||
<Icon name="share" class={styles.icon} />
|
||||
{t('Share')}
|
||||
</button>
|
||||
}
|
||||
/>
|
||||
|
||||
{/*<button*/}
|
||||
{/* class="comment-control comment-control--share"*/}
|
||||
{/* onClick={() => showModal('shareComment')}*/}
|
||||
{/*>*/}
|
||||
{/* {t('Share')}*/}
|
||||
{/*</button>*/}
|
||||
{/*<button*/}
|
||||
{/* class="comment-control comment-control--complain"*/}
|
||||
{/* class={clsx(styles.commentControl, styles.commentControlComplain)}*/}
|
||||
{/* onClick={() => showModal('reportComment')}*/}
|
||||
{/*>*/}
|
||||
{/* {t('Report')}*/}
|
||||
{/*</button>*/}
|
||||
</div>
|
||||
|
||||
<Show when={isReplyVisible()}>
|
||||
<form class={styles.replyForm}>
|
||||
<textarea name="reply" id="reply" rows="5"></textarea>
|
||||
<div class={styles.replyFormControls}>
|
||||
<button class="button button--light" onClick={() => setIsReplyVisible(false)}>
|
||||
Отмена
|
||||
</button>
|
||||
<button class="button">Отправить</button>
|
||||
</div>
|
||||
</form>
|
||||
</Show>
|
||||
</Show>
|
||||
</div>
|
||||
</Show>
|
||||
|
|
|
@ -7,6 +7,7 @@ import styles from '../../styles/Article.module.scss'
|
|||
import { useReactionsStore } from '../../stores/zine/reactions'
|
||||
import { createEffect, createMemo, createSignal, onMount, Suspense } from 'solid-js'
|
||||
import type { Reaction } from '../../graphql/types.gen'
|
||||
import { clsx } from 'clsx'
|
||||
|
||||
const ARTICLE_COMMENTS_PAGE_SIZE = 50
|
||||
const MAX_COMMENT_LEVEL = 6
|
||||
|
@ -44,9 +45,27 @@ export const CommentsTree = (props: { shout: string; reactions?: Reaction[] }) =
|
|||
return (
|
||||
<>
|
||||
<Show when={reactions()}>
|
||||
<h2 id="comments">
|
||||
{t('Comments')} {reactions().length.toString() || ''}
|
||||
</h2>
|
||||
<div class={styles.commentsHeaderWrapper}>
|
||||
<h2 id="comments" class={styles.commentsHeader}>
|
||||
{t('Comments')} {reactions().length.toString() || ''}
|
||||
</h2>
|
||||
|
||||
<ul class={clsx(styles.commentsViewSwitcher, 'view-switcher')}>
|
||||
<li class="selected">
|
||||
<a href="#">По порядку</a>
|
||||
</li>
|
||||
<li>
|
||||
<a href="#">По рейтингу</a>
|
||||
</li>
|
||||
</ul>
|
||||
</div>
|
||||
|
||||
<form class={styles.commentForm}>
|
||||
<div class="pretty-form__item">
|
||||
<input type="text" id="new-comment" placeholder="Коментарий" />
|
||||
<label for="new-comment">Коментарий</label>
|
||||
</div>
|
||||
</form>
|
||||
|
||||
<For each={reactions()}>
|
||||
{(reaction: Reaction) => (
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
import { capitalize } from '../../utils'
|
||||
import { capitalize, formatDate } from '../../utils'
|
||||
import './Full.scss'
|
||||
import { Icon } from '../_shared/Icon'
|
||||
import { AuthorCard } from '../Author/Card'
|
||||
|
@ -16,16 +16,6 @@ interface ArticleProps {
|
|||
article: Shout
|
||||
}
|
||||
|
||||
const formatDate = (date: Date) => {
|
||||
return date
|
||||
.toLocaleDateString('ru', {
|
||||
month: 'long',
|
||||
day: 'numeric',
|
||||
year: 'numeric'
|
||||
})
|
||||
.replace(' г.', '')
|
||||
}
|
||||
|
||||
export const FullArticle = (props: ArticleProps) => {
|
||||
const formattedDate = createMemo(() => formatDate(new Date(props.article.createdAt)))
|
||||
const [isSharePopupVisible, setIsSharePopupVisible] = createSignal(false)
|
||||
|
@ -90,7 +80,7 @@ export const FullArticle = (props: ArticleProps) => {
|
|||
<div class="col-md-8 shift-content">
|
||||
<div class={styles.shoutStats}>
|
||||
<div class={styles.shoutStatsItem}>
|
||||
<RatingControl rating={props.article.stat?.rating} />
|
||||
<RatingControl rating={props.article.stat?.rating} class={styles.ratingControl} />
|
||||
</div>
|
||||
|
||||
<div class={styles.shoutStatsItem}>
|
||||
|
@ -139,6 +129,11 @@ export const FullArticle = (props: ArticleProps) => {
|
|||
</div>
|
||||
</div>
|
||||
|
||||
<div class={styles.help}>
|
||||
<button class="button">Соучаствовать</button>
|
||||
<button class="button button--light">Пригласить к участию</button>
|
||||
</div>
|
||||
|
||||
<div class={styles.topicsList}>
|
||||
<For each={props.article.topics}>
|
||||
{(topic) => (
|
||||
|
@ -155,7 +150,7 @@ export const FullArticle = (props: ArticleProps) => {
|
|||
</Show>
|
||||
<For each={props.article?.authors}>
|
||||
{(a: Author) => (
|
||||
<div class="col-md-6">
|
||||
<div class="col-xl-6">
|
||||
<AuthorCard author={a} compact={false} hasLink={true} liteButtons={true} />
|
||||
</div>
|
||||
)}
|
||||
|
|
|
@ -49,7 +49,10 @@
|
|||
.authorSubscribe {
|
||||
align-items: center;
|
||||
display: flex;
|
||||
padding: 0 0 0 42px;
|
||||
|
||||
@include media-breakpoint-up(sm) {
|
||||
padding: 0 0 0 42px;
|
||||
}
|
||||
|
||||
a {
|
||||
background: #f7f7f7;
|
||||
|
@ -256,3 +259,14 @@
|
|||
display: block;
|
||||
}
|
||||
}
|
||||
|
||||
.authorComments {
|
||||
.authorName {
|
||||
@include font-size(1.2rem);
|
||||
margin-bottom: 0;
|
||||
}
|
||||
|
||||
.circlewrap {
|
||||
margin-top: -0.6em;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -23,6 +23,7 @@ interface AuthorCardProps {
|
|||
isAuthorsList?: boolean
|
||||
truncateBio?: boolean
|
||||
liteButtons?: boolean
|
||||
isComments?: boolean
|
||||
}
|
||||
|
||||
export const AuthorCard = (props: AuthorCardProps) => {
|
||||
|
@ -47,6 +48,7 @@ export const AuthorCard = (props: AuthorCardProps) => {
|
|||
class={clsx(styles.author)}
|
||||
classList={{
|
||||
[styles.authorPage]: props.isAuthorPage,
|
||||
[styles.authorComments]: props.isComments,
|
||||
[styles.authorsListItem]: props.isAuthorsList
|
||||
}}
|
||||
>
|
||||
|
@ -55,6 +57,7 @@ export const AuthorCard = (props: AuthorCardProps) => {
|
|||
hasLink={props.hasLink}
|
||||
isBig={props.isAuthorPage}
|
||||
isAuthorsList={props.isAuthorsList}
|
||||
class={styles.circlewrap}
|
||||
/>
|
||||
|
||||
<div class={styles.authorDetails}>
|
||||
|
|
|
@ -77,7 +77,9 @@ img {
|
|||
}
|
||||
|
||||
.shoutAuthorsList {
|
||||
margin-top: 2em;
|
||||
border-bottom: 1px solid #e8e8e8;
|
||||
margin: 2em 0;
|
||||
padding-bottom: 2em;
|
||||
|
||||
h4 {
|
||||
color: #696969;
|
||||
|
@ -118,15 +120,18 @@ img {
|
|||
}
|
||||
|
||||
.shoutStats {
|
||||
border-bottom: 1px solid #e8e8e8;
|
||||
border-top: 4px solid #000;
|
||||
display: flex;
|
||||
justify-content: flex-start;
|
||||
padding: 3.2rem 0;
|
||||
padding: 3rem 0 0;
|
||||
|
||||
@include media-breakpoint-down(sm) {
|
||||
flex-wrap: wrap;
|
||||
}
|
||||
}
|
||||
|
||||
.shoutStatsItem {
|
||||
@include font-size(1.7rem);
|
||||
@include font-size(1.5rem);
|
||||
|
||||
font-weight: 500;
|
||||
display: inline-block;
|
||||
|
@ -179,18 +184,32 @@ img {
|
|||
.icon {
|
||||
opacity: 0.4;
|
||||
}
|
||||
|
||||
@include media-breakpoint-down(sm) {
|
||||
flex: 1 100%;
|
||||
}
|
||||
}
|
||||
|
||||
.shoutStatsItemAdditionalDataItem {
|
||||
font-weight: normal;
|
||||
display: inline-block;
|
||||
margin-left: 2rem;
|
||||
margin-right: 0;
|
||||
|
||||
@include media-breakpoint-down(sm) {
|
||||
&:first-child {
|
||||
margin-left: 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.topicsList {
|
||||
@include font-size(1.2rem);
|
||||
|
||||
border-bottom: 1px solid #e8e8e8;
|
||||
letter-spacing: 0.08em;
|
||||
margin: 1.6rem 0;
|
||||
margin-top: 1.6rem;
|
||||
padding-bottom: 1.6rem;
|
||||
|
||||
.shoutTopic {
|
||||
display: inline-block;
|
||||
|
@ -210,3 +229,45 @@ img {
|
|||
}
|
||||
}
|
||||
}
|
||||
|
||||
.commentsHeaderWrapper {
|
||||
display: flex;
|
||||
justify-content: space-between;
|
||||
}
|
||||
|
||||
.commentsHeader {
|
||||
@include font-size(2.4rem);
|
||||
margin-bottom: 1em;
|
||||
}
|
||||
|
||||
.ratingControl {
|
||||
button {
|
||||
font-size: 2.225rem;
|
||||
}
|
||||
}
|
||||
|
||||
.commentForm {
|
||||
margin-bottom: 2.4rem;
|
||||
|
||||
input,
|
||||
textarea {
|
||||
border-radius: 0.8rem !important;
|
||||
}
|
||||
}
|
||||
|
||||
.commentsViewSwitcher {
|
||||
margin-top: 0;
|
||||
}
|
||||
|
||||
.help {
|
||||
border-bottom: 1px solid #e8e8e8;
|
||||
margin-bottom: 1.6rem;
|
||||
padding-bottom: 3.2rem;
|
||||
|
||||
button {
|
||||
@include font-size(1.5rem);
|
||||
border-radius: 0.8rem;
|
||||
margin-right: 1.2rem;
|
||||
padding: 1.1rem 1.2rem 0.9rem;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -67,3 +67,17 @@ export const snake2camel = (s: string) =>
|
|||
.split(/(?=[A-Z])/)
|
||||
.join('-')
|
||||
.toLowerCase()
|
||||
|
||||
export const formatDate = (date: Date, options: Intl.DateTimeFormatOptions = {}) => {
|
||||
const opts = Object.assign(
|
||||
{},
|
||||
{
|
||||
month: 'long',
|
||||
day: 'numeric',
|
||||
year: 'numeric'
|
||||
},
|
||||
options
|
||||
)
|
||||
|
||||
return date.toLocaleDateString('ru', opts).replace(' г.', '')
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue
Block a user