add quote form

This commit is contained in:
FloatingGhost 2022-07-24 18:38:17 +01:00
parent c8b2bf96be
commit 057ec4e09f
8 changed files with 118 additions and 5 deletions

View file

@ -56,6 +56,7 @@ const pxStringToNumber = (str) => {
const PostStatusForm = {
props: [
'replyTo',
'quoteId',
'repliedUser',
'attentions',
'copyMessageScope',
@ -99,12 +100,12 @@ const PostStatusForm = {
this.updateIdempotencyKey()
this.resize(this.$refs.textarea)
if (this.replyTo) {
if (this.replyTo || this.quoteId) {
const textLength = this.$refs.textarea.value.length
this.$refs.textarea.setSelectionRange(textLength, textLength)
}
if (this.replyTo || this.autoFocus) {
if (this.replyTo || this.quoteId || this.autoFocus) {
this.$refs.textarea.focus()
}
},
@ -112,7 +113,7 @@ const PostStatusForm = {
const preset = this.$route.query.message
let statusText = preset || ''
if (this.replyTo) {
if (this.replyTo || this.quoteId) {
const currentUser = this.$store.state.users.currentUser
statusText = buildMentionsString({ user: this.repliedUser, attentions: this.attentions }, currentUser)
}
@ -314,6 +315,7 @@ const PostStatusForm = {
media: newStatus.files,
store: this.$store,
inReplyToStatusId: this.replyTo,
quoteId: this.quoteId,
contentType: newStatus.contentType,
poll,
idempotencyKey: this.idempotencyKey
@ -347,6 +349,7 @@ const PostStatusForm = {
media: [],
store: this.$store,
inReplyToStatusId: this.replyTo,
quoteId: this.quoteId,
contentType: newStatus.contentType,
poll: {},
preview: true

View file

@ -0,0 +1,16 @@
import { library } from '@fortawesome/fontawesome-svg-core'
import { faQuoteLeft } from '@fortawesome/free-solid-svg-icons'
library.add(faQuoteLeft)
const QuoteButton = {
name: 'QuoteButton',
props: ['status', 'quoting'],
computed: {
loggedIn () {
return !!this.$store.state.users.currentUser
}
}
}
export default QuoteButton

View file

@ -0,0 +1,52 @@
<template>
<div class="QuoteButton">
<button
v-if="loggedIn"
class="button-unstyled interactive"
:class="{'-active': quoting}"
:title="$t('tool_tip.quote')"
@click.prevent="$emit('toggle')"
>
<FAIcon
class="fa-scale-110 fa-old-padding"
icon="quote-left"
/>
</button>
<span v-else>
<FAIcon
icon="quot-left"
class="fa-scale-110 fa-old-padding"
:title="$t('tool_tip.quote')"
/>
</span>
</div>
</template>
<script src="./quote_button.js"></script>
<style lang="scss">
@import '../../_variables.scss';
.QuoteButton {
display: flex;
> :first-child {
padding: 10px;
margin: -10px -8px -10px -10px;
}
.action-counter {
pointer-events: none;
user-select: none;
}
.interactive {
&:hover .svg-inline--fa,
&.-active .svg-inline--fa {
color: $fallback--cBlue;
color: var(--cBlue, $fallback--cBlue);
}
}
}
</style>

View file

@ -1,4 +1,5 @@
import ReplyButton from '../reply_button/reply_button.vue'
import QuoteButton from '../quote_button/quote_button.vue'
import FavoriteButton from '../favorite_button/favorite_button.vue'
import ReactButton from '../react_button/react_button.vue'
import RetweetButton from '../retweet_button/retweet_button.vue'
@ -115,7 +116,8 @@ const Status = {
StatusContent,
RichContent,
MentionLink,
MentionsLine
MentionsLine,
QuoteButton
},
props: [
'statusoid',
@ -145,6 +147,8 @@ const Status = {
'controlledToggleShowingLongSubject',
'controlledReplying',
'controlledToggleReplying',
'controlledQuoting',
'controlledToggleQuoting',
'controlledMediaPlaying',
'controlledSetMediaPlaying',
'dive'
@ -152,6 +156,7 @@ const Status = {
data () {
return {
uncontrolledReplying: false,
uncontrolledQuoting: false,
unmuted: false,
userExpanded: false,
uncontrolledMediaPlaying: [],
@ -161,7 +166,7 @@ const Status = {
}
},
computed: {
...controlledOrUncontrolledGetters(['replying', 'mediaPlaying']),
...controlledOrUncontrolledGetters(['replying', 'quoting', 'mediaPlaying']),
muteWords () {
return this.mergedConfig.muteWords
},
@ -418,6 +423,9 @@ const Status = {
toggleReplying () {
controlledOrUncontrolledToggle(this, 'replying')
},
toggleQuoting () {
controlledOrUncontrolledToggle(this, 'quoting')
},
gotoOriginal (id) {
if (this.inConversation) {
this.$emit('goto', id)

View file

@ -355,6 +355,15 @@
flex: 1;
}
.quote-form {
padding-top: 0;
padding-bottom: 0;
}
.quote-body {
flex: 1;
}
.favs-repeated-users {
margin-top: var(--status-margin, $status-margin);
}

View file

@ -430,6 +430,11 @@
:status="status"
@toggle="toggleReplying"
/>
<quote-button
:quoting="quoting"
:status="status"
@toggle="toggleQuoting"
/>
<retweet-button
:visibility="status.visibility"
:logged-in="loggedIn"
@ -488,6 +493,20 @@
@posted="toggleReplying"
/>
</div>
<div
v-if="quoting"
class="status-container quote-form"
>
<PostStatusForm
class="quote-body"
:quote-id="status.id"
:attentions="[status.user]"
:replied-user="status.user"
:copy-message-scope="status.visibility"
:subject="replySubject"
@posted="toggleQuoting"
/>
</div>
</template>
</div>
</template>

View file

@ -763,6 +763,7 @@ const postStatus = ({
poll,
mediaIds = [],
inReplyToStatusId,
quoteId,
contentType,
preview,
idempotencyKey
@ -795,6 +796,9 @@ const postStatus = ({
if (inReplyToStatusId) {
form.append('in_reply_to_id', inReplyToStatusId)
}
if (quoteId) {
form.append('quote_id', quoteId)
}
if (preview) {
form.append('preview', 'true')
}

View file

@ -10,6 +10,7 @@ const postStatus = ({
poll,
media = [],
inReplyToStatusId = undefined,
quoteId = undefined,
contentType = 'text/plain',
preview = false,
idempotencyKey = ''
@ -24,6 +25,7 @@ const postStatus = ({
sensitive,
mediaIds,
inReplyToStatusId,
quoteId,
contentType,
poll,
preview,