diff options
Diffstat (limited to 'src/components/user_card/user_card.vue')
| -rw-r--r-- | src/components/user_card/user_card.vue | 436 |
1 files changed, 65 insertions, 371 deletions
diff --git a/src/components/user_card/user_card.vue b/src/components/user_card/user_card.vue index 528b92fb..897d89f9 100644 --- a/src/components/user_card/user_card.vue +++ b/src/components/user_card/user_card.vue @@ -8,25 +8,32 @@ :style="style" class="background-image" /> - <div class="panel-heading"> + <div :class="onClose ? '' : panel-heading -flexible-height"> <div class="user-info"> <div class="container"> <a - v-if="allowZoomingAvatar" - class="user-info-avatar-link" + v-if="avatarAction === 'zoom'" + class="user-info-avatar -link" @click="zoomAvatar" > <UserAvatar :better-shadow="betterShadow" :user="user" /> - <div class="user-info-avatar-link-overlay"> + <div class="user-info-avatar -link -overlay"> <FAIcon class="fa-scale-110 fa-old-padding" icon="search-plus" /> </div> </a> + <UserAvatar + v-else-if="typeof avatarAction === 'function'" + class="user-info-avatar" + :better-shadow="betterShadow" + :user="user" + @click="avatarAction" + /> <router-link v-else :to="userProfileLink(user)" @@ -38,21 +45,16 @@ </router-link> <div class="user-summary"> <div class="top-line"> - <!-- eslint-disable vue/no-v-html --> - <div - v-if="user.name_html" - :title="user.name" - class="user-name" - v-html="user.name_html" - /> - <!-- eslint-enable vue/no-v-html --> - <div - v-else - :title="user.name" + <router-link + :to="userProfileLink(user)" class="user-name" > - {{ user.name }} - </div> + <RichContent + :title="user.name" + :html="user.name" + :emoji="user.emoji" + /> + </router-link> <button v-if="!isOtherUser && user.is_local" class="button-unstyled edit-profile-button" @@ -65,7 +67,7 @@ :title="$t('user_card.edit_profile')" /> </button> - <button + <a v-if="isOtherUser && !user.is_local" :href="user.statusnet_profile_url" target="_blank" @@ -75,23 +77,47 @@ class="icon" icon="external-link-alt" /> - </button> + </a> <AccountActions v-if="isOtherUser && loggedIn" :user="user" :relationship="relationship" /> - </div> - <div class="bottom-line"> <router-link - class="user-screen-name" - :title="user.screen_name_ui" + v-if="onClose" :to="userProfileLink(user)" + class="button-unstyled external-link-button" + @click="onClose" > - @{{ user.screen_name_ui }} + <FAIcon + class="icon" + icon="expand-alt" + /> </router-link> + <button + v-if="onClose" + class="button-unstyled external-link-button" + @click="onClose" + > + <FAIcon + class="icon" + icon="times" + /> + </button> + </div> + <div class="bottom-line"> + <user-link + class="user-screen-name" + :user="user" + /> <template v-if="!hideBio"> <span + v-if="user.deactivated" + class="alert user-role" + > + {{ $t('user_card.deactivated') }} + </span> + <span v-if="!!visibleRole" class="alert user-role" > @@ -144,6 +170,7 @@ class="userHighlightCl" type="color" > + {{ ' ' }} <Select :id="'userHighlightSel'+user.id" v-model="userHighlightType" @@ -169,7 +196,10 @@ class="user-interactions" > <div class="btn-group"> - <FollowButton :relationship="relationship" /> + <FollowButton + :relationship="relationship" + :user="user" + /> <template v-if="relationship.following"> <ProgressButton v-if="!relationship.subscribing" @@ -204,6 +234,7 @@ <button v-if="relationship.muting" class="btn button-default btn-block toggled" + :disabled="user.deactivated" @click="unmuteUser" > {{ $t('user_card.muted') }} @@ -211,6 +242,7 @@ <button v-else class="btn button-default btn-block" + :disabled="user.deactivated" @click="muteUser" > {{ $t('user_card.mute') }} @@ -219,13 +251,14 @@ <div> <button class="btn button-default btn-block" + :disabled="user.deactivated" @click="mentionUser" > {{ $t('user_card.mention') }} </button> </div> <ModerationTools - v-if="loggedIn.role === "admin"" + v-if="showModerationMenu" :user="user" /> </div> @@ -267,356 +300,17 @@ <span>{{ hideFollowersCount ? $t('user_card.hidden') : user.followers_count }}</span> </div> </div> - <!-- eslint-disable vue/no-v-html --> - <p - v-if="!hideBio && user.description_html" + <RichContent + v-if="!hideBio" class="user-card-bio" - @click.prevent="linkClicked" - v-html="user.description_html" + :html="user.description_html" + :emoji="user.emoji" + :handle-links="true" /> - <!-- eslint-enable vue/no-v-html --> - <p - v-else-if="!hideBio" - class="user-card-bio" - > - {{ user.description }} - </p> </div> </div> </template> <script src="./user_card.js"></script> -<style lang="scss"> -@import '../../_variables.scss'; - -.user-card { - position: relative; - - &:hover .Avatar { - --_still-image-img-visibility: visible; - --_still-image-canvas-visibility: hidden; - } - - .panel-heading { - padding: .5em 0; - text-align: center; - box-shadow: none; - background: transparent; - flex-direction: column; - align-items: stretch; - // create new stacking context - position: relative; - } - - .panel-body { - word-wrap: break-word; - border-bottom-right-radius: inherit; - border-bottom-left-radius: inherit; - // create new stacking context - position: relative; - } - - .background-image { - position: absolute; - top: 0; - left: 0; - right: 0; - bottom: 0; - mask: linear-gradient(to top, white, transparent) bottom no-repeat, - linear-gradient(to top, white, white); - // Autoprefixed seem to ignore this one, and also syntax is different - -webkit-mask-composite: xor; - mask-composite: exclude; - background-size: cover; - mask-size: 100% 60%; - border-top-left-radius: calc(var(--panelRadius) - 1px); - border-top-right-radius: calc(var(--panelRadius) - 1px); - background-color: var(--profileBg); - - &.hide-bio { - mask-size: 100% 40px; - } - } - - p { - margin-bottom: 0; - } - - &-bio { - text-align: center; - - a { - color: $fallback--link; - color: var(--postLink, $fallback--link); - } - - img { - object-fit: contain; - vertical-align: middle; - max-width: 100%; - max-height: 400px; - - &.emoji { - width: 32px; - height: 32px; - } - } - } - - // Modifiers - - &-rounded-t { - border-top-left-radius: $fallback--panelRadius; - border-top-left-radius: var(--panelRadius, $fallback--panelRadius); - border-top-right-radius: $fallback--panelRadius; - border-top-right-radius: var(--panelRadius, $fallback--panelRadius); - } - - &-rounded { - border-radius: $fallback--panelRadius; - border-radius: var(--panelRadius, $fallback--panelRadius); - } - - &-bordered { - border-width: 1px; - border-style: solid; - border-color: $fallback--border; - border-color: var(--border, $fallback--border); - } -} - -.user-info { - color: $fallback--lightText; - color: var(--lightText, $fallback--lightText); - padding: 0 26px; - - .container { - padding: 16px 0 6px; - display: flex; - align-items: flex-start; - max-height: 56px; - - .Avatar { - --_avatarShadowBox: var(--avatarShadow); - --_avatarShadowFilter: var(--avatarShadowFilter); - --_avatarShadowInset: var(--avatarShadowInset); - - flex: 1 0 100%; - width: 56px; - height: 56px; - object-fit: cover; - } - } - - &-avatar-link { - position: relative; - cursor: pointer; - - &-overlay { - position: absolute; - left: 0; - top: 0; - right: 0; - bottom: 0; - background-color: rgba(0, 0, 0, 0.3); - display: flex; - justify-content: center; - align-items: center; - border-radius: $fallback--avatarRadius; - border-radius: var(--avatarRadius, $fallback--avatarRadius); - opacity: 0; - transition: opacity .2s ease; - - svg { - color: #FFF; - } - } - - &:hover &-overlay { - opacity: 1; - } - } - - .external-link-button, .edit-profile-button { - cursor: pointer; - width: 2.5em; - text-align: center; - margin: -0.5em 0; - padding: 0.5em 0; - - &:not(:hover) .icon { - color: $fallback--lightText; - color: var(--lightText, $fallback--lightText); - } - } - - .user-summary { - display: block; - margin-left: 0.6em; - text-align: left; - text-overflow: ellipsis; - white-space: nowrap; - flex: 1 1 0; - // This is so that text doesn't get overlapped by avatar's shadow if it has - // big one - z-index: 1; - - img { - width: 26px; - height: 26px; - vertical-align: middle; - object-fit: contain - } - - .top-line { - display: flex; - } - } - - .user-name { - text-overflow: ellipsis; - overflow: hidden; - flex: 1 1 auto; - margin-right: 1em; - font-size: 15px; - - img { - object-fit: contain; - height: 16px; - width: 16px; - vertical-align: middle; - } - } - - .bottom-line { - display: flex; - font-weight: light; - font-size: 15px; - - .lock-icon { - margin-left: 0.5em; - } - - .user-screen-name { - min-width: 1px; - flex: 0 1 auto; - text-overflow: ellipsis; - overflow: hidden; - color: $fallback--lightText; - color: var(--lightText, $fallback--lightText); - } - - .dailyAvg { - min-width: 1px; - flex: 0 0 auto; - margin-left: 1em; - font-size: 0.7em; - color: $fallback--text; - color: var(--text, $fallback--text); - } - - .user-role { - flex: none; - color: $fallback--text; - color: var(--alertNeutralText, $fallback--text); - background-color: $fallback--fg; - background-color: var(--alertNeutral, $fallback--fg); - } - } - - .user-meta { - margin-bottom: .15em; - display: flex; - align-items: baseline; - font-size: 14px; - line-height: 22px; - flex-wrap: wrap; - - .following { - flex: 1 0 auto; - margin: 0; - margin-bottom: .25em; - text-align: left; - } - - .highlighter { - flex: 0 1 auto; - display: flex; - flex-wrap: wrap; - margin-right: -.5em; - align-self: start; - - .userHighlightCl { - padding: 2px 10px; - flex: 1 0 auto; - } - - .userHighlightSel { - padding-top: 0; - padding-bottom: 0; - flex: 1 0 auto; - } - - .userHighlightText { - width: 70px; - flex: 1 0 auto; - } - - .userHighlightCl, - .userHighlightText, - .userHighlightSel { - vertical-align: top; - margin-right: .5em; - margin-bottom: .25em; - } - } - } - .user-interactions { - position: relative; - display: flex; - flex-flow: row wrap; - margin-right: -.75em; - - > * { - margin: 0 .75em .6em 0; - white-space: nowrap; - min-width: 95px; - } - - button { - margin: 0; - } - } -} - -.sidebar .edit-profile-button { - display: none; -} - -.user-counts { - display: flex; - line-height:16px; - padding: .5em 1.5em 0em 1.5em; - text-align: center; - justify-content: space-between; - color: $fallback--lightText; - color: var(--lightText, $fallback--lightText); - flex-wrap: wrap; -} - -.user-count { - flex: 1 0 auto; - padding: .5em 0 .5em 0; - margin: 0 .5em; - - h5 { - font-size:1em; - font-weight: bolder; - margin: 0 0 0.25em; - } - a { - text-decoration: none; - } -} -</style> +<style lang="scss" src="./user_card.scss" /> |
