diff --git a/src/components/post_status_form/post_status_form.js b/src/components/post_status_form/post_status_form.js index b75fee69..4e3f327e 100644 --- a/src/components/post_status_form/post_status_form.js +++ b/src/components/post_status_form/post_status_form.js @@ -54,6 +54,16 @@ const pxStringToNumber = (str) => { return Number(str.substring(0, str.length - 2)) } +const typeAndRefId = ({ replyTo, statusId }) => { + if (replyTo) { + return ['reply', replyTo] + } else if (statusId) { + return ['edit', statusId] + } else { + return ['new', ''] + } +} + const PostStatusForm = { props: [ 'statusId', @@ -86,7 +96,8 @@ const PostStatusForm = { 'fileLimit', 'submitOnEnter', 'emojiPickerPlacement', - 'optimisticPosting' + 'optimisticPosting', + 'draftId' ], emits: [ 'posted', @@ -124,7 +135,9 @@ const PostStatusForm = { const { scopeCopy } = this.$store.getters.mergedConfig - if (this.replyTo) { + const [statusType, refId] = typeAndRefId({ replyTo: this.replyTo, statusId: this.statusId }) + + if (statusType === 'reply') { const currentUser = this.$store.state.users.currentUser statusText = buildMentionsString({ user: this.repliedUser, attentions: this.attentions }, currentUser) } @@ -136,6 +149,8 @@ const PostStatusForm = { const { postContentType: contentType, sensitiveByDefault } = this.$store.getters.mergedConfig let statusParams = { + type: statusType, + refId, spoilerText: this.subject || '', status: statusText, nsfw: !!sensitiveByDefault, @@ -146,9 +161,11 @@ const PostStatusForm = { contentType } - if (this.statusId) { + if (statusType === 'edit') { const statusContentType = this.statusContentType || contentType statusParams = { + type: statusType, + refId, spoilerText: this.subject || '', status: this.statusText || '', nsfw: this.statusIsSensitive || !!sensitiveByDefault, @@ -160,6 +177,21 @@ const PostStatusForm = { } } + console.debug('type and ref:', [statusType, refId]) + + const maybeDraft = this.$store.state.drafts.drafts[this.draftId] + if (this.draftId && maybeDraft) { + console.debug('current draft:', maybeDraft) + statusParams = maybeDraft + } else { + const existingDrafts = this.$store.getters.draftsByTypeAndRefId(statusType, refId) + + console.debug('existing drafts:', existingDrafts) + if (existingDrafts.length) { + statusParams = existingDrafts[0] + } + } + return { dropFiles: [], uploadingFiles: false, @@ -265,6 +297,19 @@ const PostStatusForm = { isEdit () { return typeof this.statusId !== 'undefined' && this.statusId.trim() !== '' }, + saveDraft () { + return debounce(() => { + if (this.newStatus.status) { + console.debug('Saving status', this.newStatus) + this.$store.dispatch('addOrSaveDraft', { draft: this.newStatus }) + .then(id => { + if (this.newStatus.id !== id) { + this.newStatus.id = id + } + }) + } + }, 3000) + }, ...mapGetters(['mergedConfig']), ...mapState({ mobileLayout: state => state.interface.mobileLayout @@ -282,6 +327,7 @@ const PostStatusForm = { statusChanged () { this.autoPreview() this.updateIdempotencyKey() + this.saveDraft() }, clearStatus () { const newStatus = this.newStatus diff --git a/src/main.js b/src/main.js index 9ca7eb91..2c82c93c 100644 --- a/src/main.js +++ b/src/main.js @@ -22,6 +22,7 @@ import pollsModule from './modules/polls.js' import postStatusModule from './modules/postStatus.js' import editStatusModule from './modules/editStatus.js' import statusHistoryModule from './modules/statusHistory.js' +import draftsModule from './modules/drafts.js' import chatsModule from './modules/chats.js' import announcementsModule from './modules/announcements.js' @@ -92,6 +93,7 @@ const persistedStateOptions = { postStatus: postStatusModule, editStatus: editStatusModule, statusHistory: statusHistoryModule, + drafts: draftsModule, chats: chatsModule, announcements: announcementsModule }, diff --git a/src/modules/drafts.js b/src/modules/drafts.js new file mode 100644 index 00000000..465c9aad --- /dev/null +++ b/src/modules/drafts.js @@ -0,0 +1,35 @@ + +export const defaultState = { + drafts: {} +} + +export const mutations = { + addOrSaveDraft (state, { draft }) { + state.drafts[draft.id] = draft + } +} + +export const actions = { + addOrSaveDraft (store, { draft }) { + const id = draft.id || (new Date().getTime()).toString() + store.commit('addOrSaveDraft', { draft: { ...draft, id } }) + return id + } +} + +export const getters = { + draftsByTypeAndRefId (state) { + return (type, refId) => { + return Object.values(state.drafts).filter(draft => draft.type === type && draft.refId === refId) + } + } +} + +const drafts = { + state: defaultState, + mutations, + getters, + actions +} + +export default drafts