forked from AkkomaGang/akkoma-fe
Merge branch '599' into 'develop'
Fix "Posts get cut off when there is not enough space to display them at the bottom" Closes #599 See merge request pleroma/pleroma-fe!863
This commit is contained in:
commit
c79da5c456
10 changed files with 185 additions and 143 deletions
|
@ -39,10 +39,13 @@ h4 {
|
|||
text-align: center;
|
||||
}
|
||||
|
||||
html {
|
||||
font-size: 14px;
|
||||
}
|
||||
|
||||
body {
|
||||
font-family: sans-serif;
|
||||
font-family: var(--interfaceFont, sans-serif);
|
||||
font-size: 14px;
|
||||
margin: 0;
|
||||
color: $fallback--text;
|
||||
color: var(--text, $fallback--text);
|
||||
|
|
|
@ -4,8 +4,6 @@
|
|||
trigger="click"
|
||||
placement="top"
|
||||
class="extra-button-popover"
|
||||
:offset="5"
|
||||
:container="false"
|
||||
>
|
||||
<div slot="popover">
|
||||
<div class="dropdown-menu">
|
||||
|
|
|
@ -3,9 +3,7 @@
|
|||
<v-popover
|
||||
trigger="click"
|
||||
class="moderation-tools-popover"
|
||||
:container="false"
|
||||
placement="bottom-end"
|
||||
:offset="5"
|
||||
@show="showDropDown = true"
|
||||
@hide="showDropDown = false"
|
||||
>
|
||||
|
|
|
@ -20,7 +20,6 @@
|
|||
margin: 5px;
|
||||
border-color: $fallback--bg;
|
||||
border-color: var(--bg, $fallback--bg);
|
||||
z-index: 1;
|
||||
}
|
||||
|
||||
&[x-placement^="top"] {
|
||||
|
@ -31,7 +30,7 @@
|
|||
border-left-color: transparent !important;
|
||||
border-right-color: transparent !important;
|
||||
border-bottom-color: transparent !important;
|
||||
bottom: -5px;
|
||||
bottom: -4px;
|
||||
left: calc(50% - 5px);
|
||||
margin-top: 0;
|
||||
margin-bottom: 0;
|
||||
|
@ -46,7 +45,7 @@
|
|||
border-left-color: transparent !important;
|
||||
border-right-color: transparent !important;
|
||||
border-top-color: transparent !important;
|
||||
top: -5px;
|
||||
top: -4px;
|
||||
left: calc(50% - 5px);
|
||||
margin-top: 0;
|
||||
margin-bottom: 0;
|
||||
|
@ -61,7 +60,7 @@
|
|||
border-left-color: transparent !important;
|
||||
border-top-color: transparent !important;
|
||||
border-bottom-color: transparent !important;
|
||||
left: -5px;
|
||||
left: -4px;
|
||||
top: calc(50% - 5px);
|
||||
margin-left: 0;
|
||||
margin-right: 0;
|
||||
|
@ -76,7 +75,7 @@
|
|||
border-top-color: transparent !important;
|
||||
border-right-color: transparent !important;
|
||||
border-bottom-color: transparent !important;
|
||||
right: -5px;
|
||||
right: -4px;
|
||||
top: calc(50% - 5px);
|
||||
margin-left: 0;
|
||||
margin-right: 0;
|
||||
|
|
|
@ -10,11 +10,12 @@ import Gallery from '../gallery/gallery.vue'
|
|||
import LinkPreview from '../link-preview/link-preview.vue'
|
||||
import AvatarList from '../avatar_list/avatar_list.vue'
|
||||
import Timeago from '../timeago/timeago.vue'
|
||||
import StatusPopover from '../status_popover/status_popover.vue'
|
||||
import generateProfileLink from 'src/services/user_profile_link_generator/user_profile_link_generator'
|
||||
import fileType from 'src/services/file_type/file_type.service'
|
||||
import { highlightClass, highlightStyle } from '../../services/user_highlighter/user_highlighter.js'
|
||||
import { mentionMatchesUrl, extractTagFromUrl } from 'src/services/matcher/matcher.service.js'
|
||||
import { filter, find, unescape, uniqBy } from 'lodash'
|
||||
import { filter, unescape, uniqBy } from 'lodash'
|
||||
|
||||
const Status = {
|
||||
name: 'Status',
|
||||
|
@ -37,8 +38,6 @@ const Status = {
|
|||
replying: false,
|
||||
unmuted: false,
|
||||
userExpanded: false,
|
||||
preview: null,
|
||||
showPreview: false,
|
||||
showingTall: this.inConversation && this.focused,
|
||||
showingLongSubject: false,
|
||||
error: null,
|
||||
|
@ -301,7 +300,8 @@ const Status = {
|
|||
Gallery,
|
||||
LinkPreview,
|
||||
AvatarList,
|
||||
Timeago
|
||||
Timeago,
|
||||
StatusPopover
|
||||
},
|
||||
methods: {
|
||||
visibilityIcon (visibility) {
|
||||
|
@ -376,27 +376,6 @@ const Status = {
|
|||
this.expandingSubject = true
|
||||
}
|
||||
},
|
||||
replyEnter (id, event) {
|
||||
this.showPreview = true
|
||||
const targetId = id
|
||||
const statuses = this.$store.state.statuses.allStatuses
|
||||
|
||||
if (!this.preview) {
|
||||
// if we have the status somewhere already
|
||||
this.preview = find(statuses, { 'id': targetId })
|
||||
// or if we have to fetch it
|
||||
if (!this.preview) {
|
||||
this.$store.state.api.backendInteractor.fetchStatus({ id }).then((status) => {
|
||||
this.preview = status
|
||||
})
|
||||
}
|
||||
} else if (this.preview.id !== targetId) {
|
||||
this.preview = find(statuses, { 'id': targetId })
|
||||
}
|
||||
},
|
||||
replyLeave () {
|
||||
this.showPreview = false
|
||||
},
|
||||
generateUserProfileLink (id, name) {
|
||||
return generateProfileLink(id, name, this.$store.state.instance.restrictedNicknames)
|
||||
},
|
||||
|
|
|
@ -173,21 +173,27 @@
|
|||
<div
|
||||
v-if="isReply"
|
||||
class="reply-to-and-accountname"
|
||||
>
|
||||
<StatusPopover
|
||||
v-if="!isPreview"
|
||||
:status-id="status.in_reply_to_status_id"
|
||||
>
|
||||
<a
|
||||
class="reply-to"
|
||||
href="#"
|
||||
:aria-label="$t('tool_tip.reply')"
|
||||
@click.prevent="gotoOriginal(status.in_reply_to_status_id)"
|
||||
@mouseenter.prevent.stop="replyEnter(status.in_reply_to_status_id, $event)"
|
||||
@mouseleave.prevent.stop="replyLeave()"
|
||||
>
|
||||
<i
|
||||
v-if="!isPreview"
|
||||
class="button-icon icon-reply"
|
||||
/>
|
||||
<i class="button-icon icon-reply" />
|
||||
<span class="faint-link reply-to-text">{{ $t('status.reply_to') }}</span>
|
||||
</a>
|
||||
</StatusPopover>
|
||||
<span
|
||||
v-else
|
||||
class="reply-to"
|
||||
>
|
||||
<span class="reply-to-text">{{ $t('status.reply_to') }}</span>
|
||||
</span>
|
||||
<router-link :to="replyProfileLink">
|
||||
{{ replyToName }}
|
||||
</router-link>
|
||||
|
@ -199,50 +205,25 @@
|
|||
</span>
|
||||
</div>
|
||||
<div
|
||||
v-if="inConversation && !isPreview"
|
||||
v-if="inConversation && !isPreview && replies && replies.length"
|
||||
class="replies"
|
||||
>
|
||||
<span
|
||||
v-if="replies && replies.length"
|
||||
class="faint"
|
||||
>{{ $t('status.replies_list') }}</span>
|
||||
<template v-if="replies">
|
||||
<span
|
||||
<span class="faint">{{ $t('status.replies_list') }}</span>
|
||||
<StatusPopover
|
||||
v-for="reply in replies"
|
||||
:key="reply.id"
|
||||
class="reply-link faint"
|
||||
:status-id="reply.id"
|
||||
>
|
||||
<a
|
||||
href="#"
|
||||
class="reply-link"
|
||||
@click.prevent="gotoOriginal(reply.id)"
|
||||
@mouseenter="replyEnter(reply.id, $event)"
|
||||
@mouseout="replyLeave()"
|
||||
>{{ reply.name }}</a>
|
||||
</span>
|
||||
</template>
|
||||
</StatusPopover>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div
|
||||
v-if="showPreview"
|
||||
class="status-preview-container"
|
||||
>
|
||||
<status
|
||||
v-if="preview"
|
||||
class="status-preview"
|
||||
:is-preview="true"
|
||||
:statusoid="preview"
|
||||
:compact="true"
|
||||
/>
|
||||
<div
|
||||
v-else
|
||||
class="status-preview status-preview-loading"
|
||||
>
|
||||
<i class="icon-spin4 animate-spin" />
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div
|
||||
v-if="longSubject"
|
||||
class="status-content-wrapper"
|
||||
|
@ -439,18 +420,6 @@ $status-margin: 0.75em;
|
|||
min-width: 0;
|
||||
}
|
||||
|
||||
.status-preview.status-el {
|
||||
border-style: solid;
|
||||
border-width: 1px;
|
||||
border-color: $fallback--border;
|
||||
border-color: var(--border, $fallback--border);
|
||||
}
|
||||
|
||||
.status-preview-container {
|
||||
position: relative;
|
||||
max-width: 100%;
|
||||
}
|
||||
|
||||
.status-pin {
|
||||
padding: $status-margin $status-margin 0;
|
||||
display: flex;
|
||||
|
@ -458,44 +427,6 @@ $status-margin: 0.75em;
|
|||
justify-content: flex-end;
|
||||
}
|
||||
|
||||
.status-preview {
|
||||
position: absolute;
|
||||
max-width: 95%;
|
||||
display: flex;
|
||||
background-color: $fallback--bg;
|
||||
background-color: var(--bg, $fallback--bg);
|
||||
border-color: $fallback--border;
|
||||
border-color: var(--border, $fallback--border);
|
||||
border-style: solid;
|
||||
border-width: 1px;
|
||||
border-radius: $fallback--tooltipRadius;
|
||||
border-radius: var(--tooltipRadius, $fallback--tooltipRadius);
|
||||
box-shadow: 2px 2px 3px rgba(0, 0, 0, 0.5);
|
||||
box-shadow: var(--popupShadow);
|
||||
margin-top: 0.25em;
|
||||
margin-left: 0.5em;
|
||||
z-index: 50;
|
||||
|
||||
.status {
|
||||
flex: 1;
|
||||
border: 0;
|
||||
min-width: 15em;
|
||||
}
|
||||
}
|
||||
|
||||
.status-preview-loading {
|
||||
display: block;
|
||||
min-width: 15em;
|
||||
padding: 1em;
|
||||
text-align: center;
|
||||
border-width: 1px;
|
||||
border-style: solid;
|
||||
|
||||
i {
|
||||
font-size: 2em;
|
||||
}
|
||||
}
|
||||
|
||||
.media-left {
|
||||
margin-right: $status-margin;
|
||||
}
|
||||
|
@ -553,11 +484,6 @@ $status-margin: 0.75em;
|
|||
flex-basis: 100%;
|
||||
margin-bottom: 0.5em;
|
||||
|
||||
a {
|
||||
display: inline-block;
|
||||
word-break: break-all;
|
||||
}
|
||||
|
||||
small {
|
||||
font-weight: lighter;
|
||||
}
|
||||
|
@ -568,6 +494,11 @@ $status-margin: 0.75em;
|
|||
justify-content: space-between;
|
||||
line-height: 18px;
|
||||
|
||||
a {
|
||||
display: inline-block;
|
||||
word-break: break-all;
|
||||
}
|
||||
|
||||
.name-and-account-name {
|
||||
display: flex;
|
||||
min-width: 0;
|
||||
|
@ -600,6 +531,7 @@ $status-margin: 0.75em;
|
|||
}
|
||||
|
||||
.heading-reply-row {
|
||||
position: relative;
|
||||
align-content: baseline;
|
||||
font-size: 12px;
|
||||
line-height: 18px;
|
||||
|
@ -608,11 +540,13 @@ $status-margin: 0.75em;
|
|||
flex-wrap: wrap;
|
||||
align-items: stretch;
|
||||
|
||||
a {
|
||||
> .reply-to-and-accountname > a {
|
||||
max-width: 100%;
|
||||
text-overflow: ellipsis;
|
||||
overflow: hidden;
|
||||
white-space: nowrap;
|
||||
display: inline-block;
|
||||
word-break: break-all;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -639,6 +573,8 @@ $status-margin: 0.75em;
|
|||
overflow: hidden;
|
||||
text-overflow: ellipsis;
|
||||
margin: 0 0.4em 0 0.2em;
|
||||
color: $fallback--faint;
|
||||
color: var(--faint, $fallback--faint);
|
||||
}
|
||||
|
||||
.replies-separator {
|
||||
|
|
34
src/components/status_popover/status_popover.js
Normal file
34
src/components/status_popover/status_popover.js
Normal file
|
@ -0,0 +1,34 @@
|
|||
import { find } from 'lodash'
|
||||
|
||||
const StatusPopover = {
|
||||
name: 'StatusPopover',
|
||||
props: [
|
||||
'statusId'
|
||||
],
|
||||
data () {
|
||||
return {
|
||||
popperOptions: {
|
||||
modifiers: {
|
||||
preventOverflow: { padding: { top: 50 }, boundariesElement: 'viewport' }
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
computed: {
|
||||
status () {
|
||||
return find(this.$store.state.statuses.allStatuses, { id: this.statusId })
|
||||
}
|
||||
},
|
||||
components: {
|
||||
Status: () => import('../status/status.vue')
|
||||
},
|
||||
methods: {
|
||||
enter () {
|
||||
if (!this.status) {
|
||||
this.$store.dispatch('fetchStatus', this.statusId)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
export default StatusPopover
|
85
src/components/status_popover/status_popover.vue
Normal file
85
src/components/status_popover/status_popover.vue
Normal file
|
@ -0,0 +1,85 @@
|
|||
<template>
|
||||
<v-popover
|
||||
popover-class="status-popover"
|
||||
placement="top-start"
|
||||
:popper-options="popperOptions"
|
||||
@show="enter()"
|
||||
>
|
||||
<template slot="popover">
|
||||
<Status
|
||||
v-if="status"
|
||||
:is-preview="true"
|
||||
:statusoid="status"
|
||||
:compact="true"
|
||||
/>
|
||||
<div
|
||||
v-else
|
||||
class="status-preview-loading"
|
||||
>
|
||||
<i class="icon-spin4 animate-spin" />
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<slot />
|
||||
</v-popover>
|
||||
</template>
|
||||
|
||||
<script src="./status_popover.js" ></script>
|
||||
|
||||
<style lang="scss">
|
||||
@import '../../_variables.scss';
|
||||
|
||||
.tooltip.popover.status-popover {
|
||||
font-size: 1rem;
|
||||
min-width: 15em;
|
||||
max-width: 95%;
|
||||
margin-left: 0.5em;
|
||||
|
||||
.popover-inner {
|
||||
border-color: $fallback--border;
|
||||
border-color: var(--border, $fallback--border);
|
||||
border-style: solid;
|
||||
border-width: 1px;
|
||||
border-radius: $fallback--tooltipRadius;
|
||||
border-radius: var(--tooltipRadius, $fallback--tooltipRadius);
|
||||
box-shadow: 2px 2px 3px rgba(0, 0, 0, 0.5);
|
||||
box-shadow: var(--popupShadow);
|
||||
}
|
||||
|
||||
.popover-arrow::before {
|
||||
position: absolute;
|
||||
content: '';
|
||||
left: -7px;
|
||||
border: solid 7px transparent;
|
||||
z-index: -1;
|
||||
}
|
||||
|
||||
&[x-placement^="bottom-start"] .popover-arrow::before {
|
||||
top: -2px;
|
||||
border-top-width: 0;
|
||||
border-bottom-color: $fallback--border;
|
||||
border-bottom-color: var(--border, $fallback--border);
|
||||
}
|
||||
|
||||
&[x-placement^="top-start"] .popover-arrow::before {
|
||||
bottom: -2px;
|
||||
border-bottom-width: 0;
|
||||
border-top-color: $fallback--border;
|
||||
border-top-color: var(--border, $fallback--border);
|
||||
}
|
||||
|
||||
.status-el.status-el {
|
||||
border: none;
|
||||
}
|
||||
|
||||
.status-preview-loading {
|
||||
padding: 1em;
|
||||
text-align: center;
|
||||
|
||||
i {
|
||||
font-size: 2em;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
</style>
|
|
@ -41,7 +41,13 @@ Vue.use(VueChatScroll)
|
|||
Vue.use(VueClickOutside)
|
||||
Vue.use(PortalVue)
|
||||
Vue.use(VBodyScrollLock)
|
||||
Vue.use(VTooltip)
|
||||
Vue.use(VTooltip, {
|
||||
popover: {
|
||||
defaultTrigger: 'hover click',
|
||||
defaultContainer: false,
|
||||
defaultOffset: 5
|
||||
}
|
||||
})
|
||||
|
||||
const i18n = new VueI18n({
|
||||
// By default, use the browser locale, we will update it if neccessary
|
||||
|
|
|
@ -537,6 +537,10 @@ const statuses = {
|
|||
setNotificationsSilence ({ rootState, commit }, { value }) {
|
||||
commit('setNotificationsSilence', { value })
|
||||
},
|
||||
fetchStatus ({ rootState, dispatch }, id) {
|
||||
rootState.api.backendInteractor.fetchStatus({ id })
|
||||
.then((status) => dispatch('addNewStatuses', { statuses: [status] }))
|
||||
},
|
||||
deleteStatus ({ rootState, commit }, status) {
|
||||
commit('setDeleted', { status })
|
||||
apiService.deleteStatus({ id: status.id, credentials: rootState.users.currentUser.credentials })
|
||||
|
|
Loading…
Reference in a new issue