aboutsummaryrefslogtreecommitdiff
path: root/src/components
diff options
context:
space:
mode:
Diffstat (limited to 'src/components')
-rw-r--r--src/components/basic_user_card/basic_user_card.vue2
-rw-r--r--src/components/chat/chat.js2
-rw-r--r--src/components/chat/chat.scss6
-rw-r--r--src/components/chat_panel/chat_panel.js12
-rw-r--r--src/components/chat_panel/chat_panel.vue15
-rw-r--r--src/components/chat_title/chat_title.js2
-rw-r--r--src/components/conversation/conversation.vue1
-rw-r--r--src/components/emoji_input/emoji_input.js8
-rw-r--r--src/components/emoji_input/emoji_input.vue2
-rw-r--r--src/components/emoji_input/suggestor.js4
-rw-r--r--src/components/mfa_form/recovery_form.vue4
-rw-r--r--src/components/mfa_form/totp_form.vue4
-rw-r--r--src/components/moderation_tools/moderation_tools.vue33
-rw-r--r--src/components/notification/notification.vue10
-rw-r--r--src/components/popover/popover.js14
-rw-r--r--src/components/popover/popover.vue37
-rw-r--r--src/components/post_status_form/post_status_form.js4
-rw-r--r--src/components/react_button/react_button.js6
-rw-r--r--src/components/react_button/react_button.vue1
-rw-r--r--src/components/scope_selector/scope_selector.vue8
-rw-r--r--src/components/search/search.vue2
-rw-r--r--src/components/search_bar/search_bar.vue6
-rw-r--r--src/components/settings_modal/helpers/boolean_setting.vue12
-rw-r--r--src/components/settings_modal/helpers/modified_indicator.vue20
-rw-r--r--src/components/settings_modal/tabs/filtering_tab.vue2
-rw-r--r--src/components/settings_modal/tabs/general_tab.vue7
-rw-r--r--src/components/status/status.js4
-rw-r--r--src/components/status/status.vue6
-rw-r--r--src/components/timeline/timeline.js9
-rw-r--r--src/components/timeline/timeline.vue4
-rw-r--r--src/components/timeline/timeline_quick_settings.js63
-rw-r--r--src/components/timeline/timeline_quick_settings.vue107
-rw-r--r--src/components/user_avatar/user_avatar.vue4
-rw-r--r--src/components/user_card/user_card.vue12
-rw-r--r--src/components/user_list_popover/user_list_popover.vue2
-rw-r--r--src/components/user_reporting_modal/user_reporting_modal.vue2
36 files changed, 333 insertions, 104 deletions
diff --git a/src/components/basic_user_card/basic_user_card.vue b/src/components/basic_user_card/basic_user_card.vue
index 9e410610..c53f6a9c 100644
--- a/src/components/basic_user_card/basic_user_card.vue
+++ b/src/components/basic_user_card/basic_user_card.vue
@@ -42,7 +42,7 @@
class="basic-user-card-screen-name"
:to="userProfileLink(user)"
>
- @{{ user.screen_name }}
+ @{{ user.screen_name_ui }}
</router-link>
</div>
<slot />
diff --git a/src/components/chat/chat.js b/src/components/chat/chat.js
index 2780be75..b54f5fb2 100644
--- a/src/components/chat/chat.js
+++ b/src/components/chat/chat.js
@@ -73,7 +73,7 @@ const Chat = {
},
formPlaceholder () {
if (this.recipient) {
- return this.$t('chats.message_user', { nickname: this.recipient.screen_name })
+ return this.$t('chats.message_user', { nickname: this.recipient.screen_name_ui })
} else {
return ''
}
diff --git a/src/components/chat/chat.scss b/src/components/chat/chat.scss
index aef58495..3a26686c 100644
--- a/src/components/chat/chat.scss
+++ b/src/components/chat/chat.scss
@@ -98,10 +98,10 @@
.unread-message-count {
font-size: 0.8em;
left: 50%;
- transform: translate(-50%, 0);
- border-radius: 100%;
margin-top: -1rem;
- padding: 0;
+ padding: 0.1em;
+ border-radius: 50px;
+ position: absolute;
}
.chat-loading-error {
diff --git a/src/components/chat_panel/chat_panel.js b/src/components/chat_panel/chat_panel.js
index c3887098..556694ae 100644
--- a/src/components/chat_panel/chat_panel.js
+++ b/src/components/chat_panel/chat_panel.js
@@ -35,6 +35,18 @@ const chatPanel = {
userProfileLink (user) {
return generateProfileLink(user.id, user.username, this.$store.state.instance.restrictedNicknames)
}
+ },
+ watch: {
+ messages (newVal) {
+ const scrollEl = this.$el.querySelector('.chat-window')
+ if (!scrollEl) return
+ if (scrollEl.scrollTop + scrollEl.offsetHeight + 20 > scrollEl.scrollHeight) {
+ this.$nextTick(() => {
+ if (!scrollEl) return
+ scrollEl.scrollTop = scrollEl.scrollHeight - scrollEl.offsetHeight
+ })
+ }
+ }
}
}
diff --git a/src/components/chat_panel/chat_panel.vue b/src/components/chat_panel/chat_panel.vue
index 7993c94d..8a829115 100644
--- a/src/components/chat_panel/chat_panel.vue
+++ b/src/components/chat_panel/chat_panel.vue
@@ -10,17 +10,15 @@
@click.stop.prevent="togglePanel"
>
<div class="title">
- <span>{{ $t('shoutbox.title') }}</span>
+ {{ $t('shoutbox.title') }}
<FAIcon
v-if="floating"
icon="times"
+ class="close-icon"
/>
</div>
</div>
- <div
- v-chat-scroll
- class="chat-window"
- >
+ <div class="chat-window">
<div
v-for="message in messages"
:key="message.id"
@@ -94,6 +92,13 @@
.icon {
color: $fallback--text;
color: var(--text, $fallback--text);
+ margin-right: 0.5em;
+ }
+
+ .title {
+ display: flex;
+ justify-content: space-between;
+ align-items: center;
}
}
diff --git a/src/components/chat_title/chat_title.js b/src/components/chat_title/chat_title.js
index e424bb1f..edfbe7a4 100644
--- a/src/components/chat_title/chat_title.js
+++ b/src/components/chat_title/chat_title.js
@@ -12,7 +12,7 @@ export default Vue.component('chat-title', {
],
computed: {
title () {
- return this.user ? this.user.screen_name : ''
+ return this.user ? this.user.screen_name_ui : ''
},
htmlTitle () {
return this.user ? this.user.name_html : ''
diff --git a/src/components/conversation/conversation.vue b/src/components/conversation/conversation.vue
index 353859b8..3fb26d92 100644
--- a/src/components/conversation/conversation.vue
+++ b/src/components/conversation/conversation.vue
@@ -50,7 +50,6 @@
.Conversation {
.conversation-status {
- border-left: none;
border-bottom-width: 1px;
border-bottom-style: solid;
border-bottom-color: var(--border, $fallback--border);
diff --git a/src/components/emoji_input/emoji_input.js b/src/components/emoji_input/emoji_input.js
index 2068a598..dc03bc9f 100644
--- a/src/components/emoji_input/emoji_input.js
+++ b/src/components/emoji_input/emoji_input.js
@@ -194,11 +194,18 @@ const EmojiInput = {
}
},
methods: {
+ focusPickerInput () {
+ const pickerEl = this.$refs.picker.$el
+ if (!pickerEl) return
+ const pickerInput = pickerEl.querySelector('input')
+ if (pickerInput) pickerInput.focus()
+ },
triggerShowPicker () {
this.showPicker = true
this.$refs.picker.startEmojiLoad()
this.$nextTick(() => {
this.scrollIntoView()
+ this.focusPickerInput()
})
// This temporarily disables "click outside" handler
// since external trigger also means click originates
@@ -214,6 +221,7 @@ const EmojiInput = {
if (this.showPicker) {
this.scrollIntoView()
this.$refs.picker.startEmojiLoad()
+ this.$nextTick(this.focusPickerInput)
}
},
replace (replacement) {
diff --git a/src/components/emoji_input/emoji_input.vue b/src/components/emoji_input/emoji_input.vue
index 1d6c760e..ad62484d 100644
--- a/src/components/emoji_input/emoji_input.vue
+++ b/src/components/emoji_input/emoji_input.vue
@@ -9,8 +9,8 @@
<button
v-if="!hideEmojiButton"
class="button-unstyled emoji-picker-icon"
- @click.prevent="togglePicker"
type="button"
+ @click.prevent="togglePicker"
>
<FAIcon :icon="['far', 'smile-beam']" />
</button>
diff --git a/src/components/emoji_input/suggestor.js b/src/components/emoji_input/suggestor.js
index 14a2b41e..e8efbd1e 100644
--- a/src/components/emoji_input/suggestor.js
+++ b/src/components/emoji_input/suggestor.js
@@ -116,8 +116,8 @@ export const suggestUsers = ({ dispatch, state }) => {
return diff + nameAlphabetically + screenNameAlphabetically
/* eslint-disable camelcase */
- }).map(({ screen_name, name, profile_image_url_original }) => ({
- displayText: screen_name,
+ }).map(({ screen_name, screen_name_ui, name, profile_image_url_original }) => ({
+ displayText: screen_name_ui,
detailText: name,
imageUrl: profile_image_url_original,
replacement: '@' + screen_name + ' '
diff --git a/src/components/mfa_form/recovery_form.vue b/src/components/mfa_form/recovery_form.vue
index 8457ec5d..7c594228 100644
--- a/src/components/mfa_form/recovery_form.vue
+++ b/src/components/mfa_form/recovery_form.vue
@@ -25,16 +25,16 @@
<div>
<button
class="button-unstyled -link"
- @click.prevent="requireTOTP"
type="button"
+ @click.prevent="requireTOTP"
>
{{ $t('login.enter_two_factor_code') }}
</button>
<br>
<button
class="button-unstyled -link"
- @click.prevent="abortMFA"
type="button"
+ @click.prevent="abortMFA"
>
{{ $t('general.cancel') }}
</button>
diff --git a/src/components/mfa_form/totp_form.vue b/src/components/mfa_form/totp_form.vue
index 5d80e185..4ee13992 100644
--- a/src/components/mfa_form/totp_form.vue
+++ b/src/components/mfa_form/totp_form.vue
@@ -27,16 +27,16 @@
<div>
<button
class="button-unstyled -link"
- @click.prevent="requireRecovery"
type="button"
+ @click.prevent="requireRecovery"
>
{{ $t('login.enter_recovery_code') }}
</button>
<br>
<button
class="button-unstyled -link"
- @click.prevent="abortMFA"
type="button"
+ @click.prevent="abortMFA"
>
{{ $t('general.cancel') }}
</button>
diff --git a/src/components/moderation_tools/moderation_tools.vue b/src/components/moderation_tools/moderation_tools.vue
index 5c7b82ec..bf25adc5 100644
--- a/src/components/moderation_tools/moderation_tools.vue
+++ b/src/components/moderation_tools/moderation_tools.vue
@@ -50,74 +50,74 @@
class="button-default dropdown-item"
@click="toggleTag(tags.FORCE_NSFW)"
>
- {{ $t('user_card.admin_menu.force_nsfw') }}
<span
class="menu-checkbox"
:class="{ 'menu-checkbox-checked': hasTag(tags.FORCE_NSFW) }"
/>
+ {{ $t('user_card.admin_menu.force_nsfw') }}
</button>
<button
class="button-default dropdown-item"
@click="toggleTag(tags.STRIP_MEDIA)"
>
- {{ $t('user_card.admin_menu.strip_media') }}
<span
class="menu-checkbox"
:class="{ 'menu-checkbox-checked': hasTag(tags.STRIP_MEDIA) }"
/>
+ {{ $t('user_card.admin_menu.strip_media') }}
</button>
<button
class="button-default dropdown-item"
@click="toggleTag(tags.FORCE_UNLISTED)"
>
- {{ $t('user_card.admin_menu.force_unlisted') }}
<span
class="menu-checkbox"
:class="{ 'menu-checkbox-checked': hasTag(tags.FORCE_UNLISTED) }"
/>
+ {{ $t('user_card.admin_menu.force_unlisted') }}
</button>
<button
class="button-default dropdown-item"
@click="toggleTag(tags.SANDBOX)"
>
- {{ $t('user_card.admin_menu.sandbox') }}
<span
class="menu-checkbox"
:class="{ 'menu-checkbox-checked': hasTag(tags.SANDBOX) }"
/>
+ {{ $t('user_card.admin_menu.sandbox') }}
</button>
<button
v-if="user.is_local"
class="button-default dropdown-item"
@click="toggleTag(tags.DISABLE_REMOTE_SUBSCRIPTION)"
>
- {{ $t('user_card.admin_menu.disable_remote_subscription') }}
<span
class="menu-checkbox"
:class="{ 'menu-checkbox-checked': hasTag(tags.DISABLE_REMOTE_SUBSCRIPTION) }"
/>
+ {{ $t('user_card.admin_menu.disable_remote_subscription') }}
</button>
<button
v-if="user.is_local"
class="button-default dropdown-item"
@click="toggleTag(tags.DISABLE_ANY_SUBSCRIPTION)"
>
- {{ $t('user_card.admin_menu.disable_any_subscription') }}
<span
class="menu-checkbox"
:class="{ 'menu-checkbox-checked': hasTag(tags.DISABLE_ANY_SUBSCRIPTION) }"
/>
+ {{ $t('user_card.admin_menu.disable_any_subscription') }}
</button>
<button
v-if="user.is_local"
class="button-default dropdown-item"
@click="toggleTag(tags.QUARANTINE)"
>
- {{ $t('user_card.admin_menu.quarantine') }}
<span
class="menu-checkbox"
:class="{ 'menu-checkbox-checked': hasTag(tags.QUARANTINE) }"
/>
+ {{ $t('user_card.admin_menu.quarantine') }}
</button>
</span>
</div>
@@ -163,25 +163,6 @@
<style lang="scss">
@import '../../_variables.scss';
-.menu-checkbox {
- float: right;
- min-width: 22px;
- max-width: 22px;
- min-height: 22px;
- max-height: 22px;
- line-height: 22px;
- text-align: center;
- border-radius: 0px;
- background-color: $fallback--fg;
- background-color: var(--input, $fallback--fg);
- box-shadow: 0px 0px 2px black inset;
- box-shadow: var(--inputShadow);
-
- &.menu-checkbox-checked::after {
- content: '✓';
- }
-}
-
.moderation-tools-popover {
height: 100%;
.trigger {
diff --git a/src/components/notification/notification.vue b/src/components/notification/notification.vue
index f56aa977..0081dee4 100644
--- a/src/components/notification/notification.vue
+++ b/src/components/notification/notification.vue
@@ -11,7 +11,7 @@
>
<small>
<router-link :to="userProfileLink">
- {{ notification.from_profile.screen_name }}
+ {{ notification.from_profile.screen_name_ui }}
</router-link>
</small>
<button
@@ -54,14 +54,14 @@
<bdi
v-if="!!notification.from_profile.name_html"
class="username"
- :title="'@'+notification.from_profile.screen_name"
+ :title="'@'+notification.from_profile.screen_name_ui"
v-html="notification.from_profile.name_html"
/>
<!-- eslint-enable vue/no-v-html -->
<span
v-else
class="username"
- :title="'@'+notification.from_profile.screen_name"
+ :title="'@'+notification.from_profile.screen_name_ui"
>{{ notification.from_profile.name }}</span>
<span v-if="notification.type === 'like'">
<FAIcon
@@ -152,7 +152,7 @@
:to="userProfileLink"
class="follow-name"
>
- @{{ notification.from_profile.screen_name }}
+ @{{ notification.from_profile.screen_name_ui }}
</router-link>
<div
v-if="notification.type === 'follow_request'"
@@ -177,7 +177,7 @@
class="move-text"
>
<router-link :to="targetUserProfileLink">
- @{{ notification.target.screen_name }}
+ @{{ notification.target.screen_name_ui }}
</router-link>
</div>
<template v-else>
diff --git a/src/components/popover/popover.js b/src/components/popover/popover.js
index 5e417fa0..391d6422 100644
--- a/src/components/popover/popover.js
+++ b/src/components/popover/popover.js
@@ -3,25 +3,32 @@ const Popover = {
props: {
// Action to trigger popover: either 'hover' or 'click'
trigger: String,
+
// Either 'top' or 'bottom'
placement: String,
+
// Takes object with properties 'x' and 'y', values of these can be
// 'container' for using offsetParent as boundaries for either axis
// or 'viewport'
boundTo: Object,
+
// Takes a selector to use as a replacement for the parent container
// for getting boundaries for x an y axis
boundToSelector: String,
+
// Takes a top/bottom/left/right object, how much space to leave
// between boundary and popover element
margin: Object,
+
// Takes a x/y object and tells how many pixels to offset from
// anchor point on either axis
offset: Object,
+
// Replaces the classes you may want for the popover container.
// Use 'popover-default' in addition to get the default popover
// styles with your custom class.
popoverClass: String,
+
// If true, subtract padding when calculating position for the popover,
// use it when popover offset looks to be different on top vs bottom.
removePadding: Boolean
@@ -121,9 +128,12 @@ const Popover = {
}
},
showPopover () {
- if (this.hidden) this.$emit('show')
+ const wasHidden = this.hidden
this.hidden = false
- this.$nextTick(this.updateStyles)
+ this.$nextTick(() => {
+ if (wasHidden) this.$emit('show')
+ this.updateStyles()
+ })
},
hidePopover () {
if (!this.hidden) this.$emit('close')
diff --git a/src/components/popover/popover.vue b/src/components/popover/popover.vue
index 876dd61d..2e78a09e 100644
--- a/src/components/popover/popover.vue
+++ b/src/components/popover/popover.vue
@@ -6,8 +6,8 @@
<button
ref="trigger"
class="button-unstyled -fullwidth popover-trigger-button"
- @click="onClick"
type="button"
+ @click="onClick"
>
<slot name="trigger" />
</button>
@@ -82,10 +82,9 @@
.dropdown-item {
line-height: 21px;
- margin-right: 5px;
overflow: auto;
display: block;
- padding: .25rem 1.0rem .25rem 1.5rem;
+ padding: .5em 0.75em;
clear: both;
font-weight: 400;
text-align: inherit;
@@ -101,10 +100,9 @@
--btnText: var(--popoverText, $fallback--text);
&-icon {
- padding-left: 0.5rem;
-
svg {
- margin-right: 0.25rem;
+ width: 22px;
+ margin-right: 0.75rem;
color: var(--menuPopoverIcon, $fallback--icon)
}
}
@@ -123,6 +121,33 @@
}
}
+ .menu-checkbox {
+ display: inline-block;
+ vertical-align: middle;
+ min-width: 22px;
+ max-width: 22px;
+ min-height: 22px;
+ max-height: 22px;
+ line-height: 22px;
+ text-align: center;
+ border-radius: 0px;
+ background-color: $fallback--fg;
+ background-color: var(--input, $fallback--fg);
+ box-shadow: 0px 0px 2px black inset;
+ box-shadow: var(--inputShadow);
+ margin-right: 0.75em;
+
+ &.menu-checkbox-checked::after {
+ font-size: 1.25em;
+ content: '✓';
+ }
+
+ &.menu-checkbox-radio::after {
+ font-size: 2em;
+ content: '•';
+ }
+ }
+
}
}
</style>
diff --git a/src/components/post_status_form/post_status_form.js b/src/components/post_status_form/post_status_form.js
index 4148381c..e540654b 100644
--- a/src/components/post_status_form/post_status_form.js
+++ b/src/components/post_status_form/post_status_form.js
@@ -115,7 +115,7 @@ const PostStatusForm = {
? this.copyMessageScope
: this.$store.state.users.currentUser.default_scope
- const { postContentType: contentType } = this.$store.getters.mergedConfig
+ const { postContentType: contentType, sensitiveByDefault } = this.$store.getters.mergedConfig
return {
dropFiles: [],
@@ -126,7 +126,7 @@ const PostStatusForm = {
newStatus: {
spoilerText: this.subject || '',
status: statusText,
- nsfw: false,
+ nsfw: !!sensitiveByDefault,
files: [],
poll: {},
mediaDescriptions: {},
diff --git a/src/components/react_button/react_button.js b/src/components/react_button/react_button.js
index 5e7b7580..ce82c90d 100644
--- a/src/components/react_button/react_button.js
+++ b/src/components/react_button/react_button.js
@@ -23,6 +23,12 @@ const ReactButton = {
this.$store.dispatch('reactWithEmoji', { id: this.status.id, emoji })
}
close()
+ },
+ focusInput () {
+ this.$nextTick(() => {
+ const input = this.$el.querySelector('input')
+ if (input) input.focus()
+ })
}
},
computed: {
diff --git a/src/components/react_button/react_button.vue b/src/components/react_button/react_button.vue
index 04734674..4839024c 100644
--- a/src/components/react_button/react_button.vue
+++ b/src/components/react_button/react_button.vue
@@ -6,6 +6,7 @@
:offset="{ y: 5 }"
:bound-to="{ x: 'container' }"
remove-padding
+ @show="focusInput"
>
<div
slot="content"
diff --git a/src/components/scope_selector/scope_selector.vue b/src/components/scope_selector/scope_selector.vue
index 60e8c3ba..a01242fc 100644
--- a/src/components/scope_selector/scope_selector.vue
+++ b/src/components/scope_selector/scope_selector.vue
@@ -8,8 +8,8 @@
class="button-unstyled scope"
:class="css.direct"
:title="$t('post_status.scope.direct')"
- @click="changeVis('direct')"
type="button"
+ @click="changeVis('direct')"
>
<FAIcon
icon="envelope"
@@ -21,8 +21,8 @@
class="button-unstyled scope"
:class="css.private"
:title="$t('post_status.scope.private')"
- @click="changeVis('private')"
type="button"
+ @click="changeVis('private')"
>
<FAIcon
icon="lock"
@@ -34,8 +34,8 @@
class="button-unstyled scope"
:class="css.unlisted"
:title="$t('post_status.scope.unlisted')"
- @click="changeVis('unlisted')"
type="button"
+ @click="changeVis('unlisted')"
>
<FAIcon
icon="lock-open"
@@ -47,8 +47,8 @@
class="button-unstyled scope"
:class="css.public"
:title="$t('post_status.scope.public')"
- @click="changeVis('public')"
type="button"
+ @click="changeVis('public')"
>
<FAIcon
icon="globe"
diff --git a/src/components/search/search.vue b/src/components/search/search.vue
index fa648365..b7bfc1f3 100644
--- a/src/components/search/search.vue
+++ b/src/components/search/search.vue
@@ -15,8 +15,8 @@
>
<button
class="btn button-default search-button"
- @click="newQuery(searchTerm)"
type="submit"
+ @click="newQuery(searchTerm)"
>
<FAIcon icon="search" />
</button>
diff --git a/src/components/search_bar/search_bar.vue b/src/components/search_bar/search_bar.vue
index a7432dcb..222f57ba 100644
--- a/src/components/search_bar/search_bar.vue
+++ b/src/components/search_bar/search_bar.vue
@@ -7,8 +7,8 @@
v-if="hidden"
class="button-unstyled nav-icon"
:title="$t('nav.search')"
- @click.prevent.stop="toggleHidden"
type="button"
+ @click.prevent.stop="toggleHidden"
>
<FAIcon
fixed-width
@@ -28,8 +28,8 @@
>
<button
class="button-default search-button"
- @click="find(searchTerm)"
type="submit"
+ @click="find(searchTerm)"
>
<FAIcon
fixed-width
@@ -38,8 +38,8 @@
</button>
<button
class="button-unstyled cancel-search"
- @click.prevent.stop="toggleHidden"
type="button"
+ @click.prevent.stop="toggleHidden"
>
<FAIcon
fixed-width
diff --git a/src/components/settings_modal/helpers/boolean_setting.vue b/src/components/settings_modal/helpers/boolean_setting.vue
index b600b63b..146ad6c1 100644
--- a/src/components/settings_modal/helpers/boolean_setting.vue
+++ b/src/components/settings_modal/helpers/boolean_setting.vue
@@ -4,13 +4,13 @@
>
<Checkbox
:checked="state"
- @change="update"
:disabled="disabled"
+ @change="update"
>
<span
v-if="!!$slots.default"
class="label"
- >
+ >
<slot />
</span>
<ModifiedIndicator :changed="isChanged" />
@@ -23,14 +23,14 @@ import { get, set } from 'lodash'
import Checkbox from 'src/components/checkbox/checkbox.vue'
import ModifiedIndicator from './modified_indicator.vue'
export default {
- props: [
- 'path',
- 'disabled'
- ],
components: {
Checkbox,
ModifiedIndicator
},
+ props: [
+ 'path',
+ 'disabled'
+ ],
computed: {
pathDefault () {
const [firstSegment, ...rest] = this.path.split('.')
diff --git a/src/components/settings_modal/helpers/modified_indicator.vue b/src/components/settings_modal/helpers/modified_indicator.vue
index b75a2811..9f4e81fe 100644
--- a/src/components/settings_modal/helpers/modified_indicator.vue
+++ b/src/components/settings_modal/helpers/modified_indicator.vue
@@ -2,21 +2,21 @@
<span
v-if="changed"
class="ModifiedIndicator"
- >
+ >
<Popover
trigger="hover"
- >
+ >
<span slot="trigger">
&nbsp;
- <FAIcon
- icon="wrench"
- />
+ <FAIcon
+ icon="wrench"
+ />
</span>
<div
- class="modified-tooltip"
slot="content"
- >
- {{ $t('settings.setting_changed') }}
+ class="modified-tooltip"
+ >
+ {{ $t('settings.setting_changed') }}
</div>
</Popover>
</span>
@@ -32,8 +32,8 @@ library.add(
)
export default {
- props: ['changed'],
- components: { Popover }
+ components: { Popover },
+ props: ['changed']
}
</script>
diff --git a/src/components/settings_modal/tabs/filtering_tab.vue b/src/components/settings_modal/tabs/filtering_tab.vue
index 18dd4be9..402c2a4a 100644
--- a/src/components/settings_modal/tabs/filtering_tab.vue
+++ b/src/components/settings_modal/tabs/filtering_tab.vue
@@ -75,8 +75,8 @@
<p>{{ $t('settings.filtering_explanation') }}</p>
<textarea
id="muteWords"
- class="resize-height"
v-model="muteWordsString"
+ class="resize-height"
/>
</div>
<div>
diff --git a/src/components/settings_modal/tabs/general_tab.vue b/src/components/settings_modal/tabs/general_tab.vue
index f93f4ea0..9228c78e 100644
--- a/src/components/settings_modal/tabs/general_tab.vue
+++ b/src/components/settings_modal/tabs/general_tab.vue
@@ -144,7 +144,12 @@
</li>
<li>
<BooleanSetting path="minimalScopesMode">
- {{ $t('settings.minimal_scopes_mode') }} {{ minimalScopesModeDefaultValue }}
+ {{ $t('settings.minimal_scopes_mode') }}
+ </BooleanSetting>
+ </li>
+ <li>
+ <BooleanSetting path="sensitiveByDefault">
+ {{ $t('settings.sensitive_by_default') }}
</BooleanSetting>
</li>
<li>
diff --git a/src/components/status/status.js b/src/components/status/status.js
index 2bf93a9e..470c01f1 100644
--- a/src/components/status/status.js
+++ b/src/components/status/status.js
@@ -136,7 +136,7 @@ const Status = {
}
},
retweet () { return !!this.statusoid.retweeted_status },
- retweeter () { return this.statusoid.user.name || this.statusoid.user.screen_name },
+ retweeter () { return this.statusoid.user.name || this.statusoid.user.screen_name_ui },
retweeterHtml () { return this.statusoid.user.name_html },
retweeterProfileLink () { return this.generateUserProfileLink(this.statusoid.user.id, this.statusoid.user.screen_name) },
status () {
@@ -216,7 +216,7 @@ const Status = {
return this.status.in_reply_to_screen_name
} else {
const user = this.$store.getters.findUser(this.status.in_reply_to_user_id)
- return user && user.screen_name
+ return user && user.screen_name_ui
}
},
replySubject () {
diff --git a/src/components/status/status.vue b/src/components/status/status.vue
index 6ee8117f..00e962f3 100644
--- a/src/components/status/status.vue
+++ b/src/components/status/status.vue
@@ -26,7 +26,7 @@
icon="retweet"
/>
<router-link :to="userProfileLink">
- {{ status.user.screen_name }}
+ {{ status.user.screen_name_ui }}
</router-link>
</small>
<small
@@ -156,10 +156,10 @@
</h4>
<router-link
class="account-name"
- :title="status.user.screen_name"
+ :title="status.user.screen_name_ui"
:to="userProfileLink"
>
- {{ status.user.screen_name }}
+ {{ status.user.screen_name_ui }}
</router-link>
<img
v-if="!!(status.user && status.user.favicon)"
diff --git a/src/components/timeline/timeline.js b/src/components/timeline/timeline.js
index 665d195e..44f749c3 100644
--- a/src/components/timeline/timeline.js
+++ b/src/components/timeline/timeline.js
@@ -2,12 +2,14 @@ import Status from '../status/status.vue'
import timelineFetcher from '../../services/timeline_fetcher/timeline_fetcher.service.js'
import Conversation from '../conversation/conversation.vue'
import TimelineMenu from '../timeline_menu/timeline_menu.vue'
+import TimelineQuickSettings from './timeline_quick_settings.vue'
import { debounce, throttle, keyBy } from 'lodash'
import { library } from '@fortawesome/fontawesome-svg-core'
-import { faCircleNotch } from '@fortawesome/free-solid-svg-icons'
+import { faCircleNotch, faCog } from '@fortawesome/free-solid-svg-icons'
library.add(
- faCircleNotch
+ faCircleNotch,
+ faCog
)
export const getExcludedStatusIdsByPinning = (statuses, pinnedStatusIds) => {
@@ -47,7 +49,8 @@ const Timeline = {
components: {
Status,
Conversation,
- TimelineMenu
+ TimelineMenu,
+ TimelineQuickSettings
},
computed: {
newStatusCount () {
diff --git a/src/components/timeline/timeline.vue b/src/components/timeline/timeline.vue
index 4c43fe5c..286477c2 100644
--- a/src/components/timeline/timeline.vue
+++ b/src/components/timeline/timeline.vue
@@ -16,6 +16,7 @@
>
{{ $t('timeline.up_to_date') }}
</div>
+ <TimelineQuickSettings v-if="!embedded" />
</div>
<div :class="classes.body">
<div
@@ -103,9 +104,12 @@
max-width: 100%;
flex-wrap: nowrap;
align-items: center;
+ position: relative;
+
.loadmore-button {
flex-shrink: 0;
}
+
.loadmore-text {
flex-shrink: 0;
line-height: 1em;
diff --git a/src/components/timeline/timeline_quick_settings.js b/src/components/timeline/timeline_quick_settings.js
new file mode 100644
index 00000000..9ec1a007
--- /dev/null
+++ b/src/components/timeline/timeline_quick_settings.js
@@ -0,0 +1,63 @@
+import Popover from '../popover/popover.vue'
+import BooleanSetting from '../settings_modal/helpers/boolean_setting.vue'
+import { mapGetters } from 'vuex'
+import { library } from '@fortawesome/fontawesome-svg-core'
+import { faFilter, faFont, faWrench } from '@fortawesome/free-solid-svg-icons'
+
+library.add(
+ faFilter,
+ faFont,
+ faWrench
+)
+
+const TimelineQuickSettings = {
+ components: {
+ Popover,
+ BooleanSetting
+ },
+ methods: {
+ setReplyVisibility (visibility) {
+ this.$store.dispatch('setOption', { name: 'replyVisibility', value: visibility })
+ this.$store.dispatch('queueFlushAll')
+ },
+ openTab (tab) {
+ this.$store.dispatch('openSettingsModalTab', tab)
+ }
+ },
+ computed: {
+ ...mapGetters(['mergedConfig']),
+ loggedIn () {
+ return !!this.$store.state.users.currentUser
+ },
+ replyVisibilitySelf: {
+ get () { return this.mergedConfig.replyVisibility === 'self' },
+ set () { this.setReplyVisibility('self') }
+ },
+ replyVisibilityFollowing: {
+ get () { return this.mergedConfig.replyVisibility === 'following' },
+ set () { this.setReplyVisibility('following') }
+ },
+ replyVisibilityAll: {
+ get () { return this.mergedConfig.replyVisibility === 'all' },
+ set () { this.setReplyVisibility('all') }
+ },
+ hideMedia: {
+ get () { return this.mergedConfig.hideAttachments || this.mergedConfig.hideAttachmentsInConv },
+ set () {
+ const value = !this.hideMedia
+ this.$store.dispatch('setOption', { name: 'hideAttachments', value })
+ this.$store.dispatch('setOption', { name: 'hideAttachmentsInConv', value })
+ }
+ },
+ hideMutedPosts: {
+ get () { return this.mergedConfig.hideMutedPosts || this.mergedConfig.hideFilteredStatuses },
+ set () {
+ const value = !this.hideMutedPosts
+ this.$store.dispatch('setOption', { name: 'hideMutedPosts', value })
+ this.$store.dispatch('setOption', { name: 'hideFilteredStatuses', value })
+ }
+ }
+ }
+}
+
+export default TimelineQuickSettings
diff --git a/src/components/timeline/timeline_quick_settings.vue b/src/components/timeline/timeline_quick_settings.vue
new file mode 100644
index 00000000..4ad2842b
--- /dev/null
+++ b/src/components/timeline/timeline_quick_settings.vue
@@ -0,0 +1,107 @@
+<template>
+ <Popover
+ trigger="click"
+ class="TimelineQuickSettings"
+ :bound-to="{ x: 'container' }"
+ >
+ <div
+ slot="content"
+ class="timeline-settings-menu dropdown-menu"
+ >
+ <div v-if="loggedIn">
+ <button
+ class="button-default dropdown-item"
+ @click="replyVisibilityAll = true"
+ >
+ <span
+ class="menu-checkbox"
+ :class="{ 'menu-checkbox-radio': replyVisibilityAll }"
+ />{{ $t('settings.reply_visibility_all') }}
+ </button>
+ <button
+ class="button-default dropdown-item"
+ @click="replyVisibilityFollowing = true"
+ >
+ <span
+ class="menu-checkbox"
+ :class="{ 'menu-checkbox-radio': replyVisibilityFollowing }"
+ />{{ $t('settings.reply_visibility_following_short') }}
+ </button>
+ <button
+ class="button-default dropdown-item"
+ @click="replyVisibilitySelf = true"
+ >
+ <span
+ class="menu-checkbox"
+ :class="{ 'menu-checkbox-radio': replyVisibilitySelf }"
+ />{{ $t('settings.reply_visibility_self_short') }}
+ </button>
+ <div
+ role="separator"
+ class="dropdown-divider"
+ />
+ </div>
+ <button
+ class="button-default dropdown-item"
+ @click="hideMedia = !hideMedia"
+ >
+ <span
+ class="menu-checkbox"
+ :class="{ 'menu-checkbox-checked': hideMedia }"
+ />{{ $t('settings.hide_media_previews') }}
+ </button>
+ <button
+ class="button-default dropdown-item"
+ @click="hideMutedPosts = !hideMutedPosts"
+ >
+ <span
+ class="menu-checkbox"
+ :class="{ 'menu-checkbox-checked': hideMutedPosts }"
+ />{{ $t('settings.hide_all_muted_posts') }}
+ </button>
+ <button
+ class="button-default dropdown-item dropdown-item-icon"
+ @click="openTab('filtering')"
+ >
+ <FAIcon icon="font" />{{ $t('settings.word_filter') }}
+ </button>
+ <button
+ class="button-default dropdown-item dropdown-item-icon"
+ @click="openTab('general')"
+ >
+ <FAIcon icon="wrench" />{{ $t('settings.more_settings') }}
+ </button>
+ </div>
+ <div slot="trigger">
+ <FAIcon icon="filter" />
+ </div>
+ </Popover>
+</template>
+
+<script src="./timeline_quick_settings.js"></script>
+
+<style lang="scss">
+
+.TimelineQuickSettings {
+ align-self: stretch;
+
+ > button {
+ font-size: 1.2em;
+ padding-left: 0.7em;
+ padding-right: 0.2em;
+ line-height: 100%;
+ height: 100%;
+ }
+
+ .dropdown-item {
+ margin: 0;
+ }
+
+ .timeline-settings-menu {
+ display: flex;
+ min-width: 12em;
+ flex-direction: column;
+ }
+}
+
+</style>
diff --git a/src/components/user_avatar/user_avatar.vue b/src/components/user_avatar/user_avatar.vue
index 0f7c584b..4040e263 100644
--- a/src/components/user_avatar/user_avatar.vue
+++ b/src/components/user_avatar/user_avatar.vue
@@ -2,8 +2,8 @@
<StillImage
v-if="user"
class="Avatar"
- :alt="user.screen_name"
- :title="user.screen_name"
+ :alt="user.screen_name_ui"
+ :title="user.screen_name_ui"
:src="imgSrc(user.profile_image_url_original)"
:class="{ 'avatar-compact': compact, 'better-shadow': betterShadow }"
:image-load-error="imageLoadError"
diff --git a/src/components/user_card/user_card.vue b/src/components/user_card/user_card.vue
index 572943b5..4b7ee7d5 100644
--- a/src/components/user_card/user_card.vue
+++ b/src/components/user_card/user_card.vue
@@ -73,10 +73,10 @@
<div class="bottom-line">
<router-link
class="user-screen-name"
- :title="user.screen_name"
+ :title="user.screen_name_ui"
:to="userProfileLink(user)"
>
- @{{ user.screen_name }}
+ @{{ user.screen_name_ui }}
</router-link>
<template v-if="!hideBio">
<span
@@ -141,10 +141,10 @@
v-model="userHighlightType"
class="userHighlightSel"
>
- <option value="disabled">No highlight</option>
- <option value="solid">Solid bg</option>
- <option value="striped">Striped bg</option>
- <option value="side">Side stripe</option>
+ <option value="disabled">{{ $t('user_card.highlight.disabled') }}</option>
+ <option value="solid">{{ $t('user_card.highlight.solid') }}</option>
+ <option value="striped">{{ $t('user_card.highlight.striped') }}</option>
+ <option value="side">{{ $t('user_card.highlight.side') }}</option>
</select>
<FAIcon
class="select-down-icon"
diff --git a/src/components/user_list_popover/user_list_popover.vue b/src/components/user_list_popover/user_list_popover.vue
index 95673733..d0aa315e 100644
--- a/src/components/user_list_popover/user_list_popover.vue
+++ b/src/components/user_list_popover/user_list_popover.vue
@@ -26,7 +26,7 @@
<!-- eslint-disable vue/no-v-html -->
<span v-html="user.name_html" />
<!-- eslint-enable vue/no-v-html -->
- <span class="user-list-screen-name">{{ user.screen_name }}</span>
+ <span class="user-list-screen-name">{{ user.screen_name_ui }}</span>
</div>
</div>
</div>
diff --git a/src/components/user_reporting_modal/user_reporting_modal.vue b/src/components/user_reporting_modal/user_reporting_modal.vue
index fb43094f..a71c02c1 100644
--- a/src/components/user_reporting_modal/user_reporting_modal.vue
+++ b/src/components/user_reporting_modal/user_reporting_modal.vue
@@ -6,7 +6,7 @@
<div class="user-reporting-panel panel">
<div class="panel-heading">
<div class="title">
- {{ $t('user_reporting.title', [user.screen_name]) }}
+ {{ $t('user_reporting.title', [user.screen_name_ui]) }}
</div>
</div>
<div class="panel-body">