commit: 5222da77483c89b93441b7bbe6b38ca7a6005be5
parent 17917932a032e1feb2798738b69a846069dcf826
Author: Henry Jameson <me@hjkos.com>
Date: Sun, 12 Jan 2025 18:49:44 +0200
inner dropdowns work
Diffstat:
10 files changed, 225 insertions(+), 157 deletions(-)
diff --git a/src/components/extra_buttons/extra_buttons.vue b/src/components/extra_buttons/extra_buttons.vue
@@ -18,7 +18,7 @@
>
<button
v-if="canMute && !status.thread_muted"
- class="menu-item dropdown-item dropdown-item-icon"
+ class="menu-item dropdown-item -icon"
role="menuitem"
@click.prevent="muteConversation"
>
@@ -29,7 +29,7 @@
</button>
<button
v-if="canMute && status.thread_muted"
- class="menu-item dropdown-item dropdown-item-icon"
+ class="menu-item dropdown-item -icon"
role="menuitem"
@click.prevent="unmuteConversation"
>
@@ -40,7 +40,7 @@
</button>
<button
v-if="!status.pinned && canPin"
- class="menu-item dropdown-item dropdown-item-icon"
+ class="menu-item dropdown-item -icon"
role="menuitem"
@click.prevent="pinStatus"
@click="close"
@@ -52,7 +52,7 @@
</button>
<button
v-if="status.pinned && canPin"
- class="menu-item dropdown-item dropdown-item-icon"
+ class="menu-item dropdown-item -icon"
role="menuitem"
@click.prevent="unpinStatus"
@click="close"
@@ -65,7 +65,7 @@
<template v-if="canBookmark">
<button
v-if="!status.bookmarked"
- class="menu-item dropdown-item dropdown-item-icon"
+ class="menu-item dropdown-item -icon"
role="menuitem"
@click.prevent="bookmarkStatus"
@click="close"
@@ -77,7 +77,7 @@
</button>
<button
v-if="status.bookmarked"
- class="menu-item dropdown-item dropdown-item-icon"
+ class="menu-item dropdown-item -icon"
role="menuitem"
@click.prevent="unbookmarkStatus"
@click="close"
@@ -94,7 +94,7 @@
</template>
<button
v-if="ownStatus && editingAvailable"
- class="menu-item dropdown-item dropdown-item-icon"
+ class="menu-item dropdown-item -icon"
role="menuitem"
@click.prevent="editStatus"
@click="close"
@@ -106,7 +106,7 @@
</button>
<button
v-if="isEdited && editingAvailable"
- class="menu-item dropdown-item dropdown-item-icon"
+ class="menu-item dropdown-item -icon"
role="menuitem"
@click.prevent="showStatusHistory"
@click="close"
@@ -118,7 +118,7 @@
</button>
<button
v-if="canDelete"
- class="menu-item dropdown-item dropdown-item-icon"
+ class="menu-item dropdown-item -icon"
role="menuitem"
@click.prevent="deleteStatus"
@click="close"
@@ -129,7 +129,7 @@
/><span>{{ $t("status.delete") }}</span>
</button>
<button
- class="menu-item dropdown-item dropdown-item-icon"
+ class="menu-item dropdown-item -icon"
role="menuitem"
@click.prevent="copyLink"
@click="close"
@@ -141,7 +141,7 @@
</button>
<a
v-if="!status.is_local"
- class="menu-item dropdown-item dropdown-item-icon"
+ class="menu-item dropdown-item -icon"
role="menuitem"
title="Source"
:href="status.external_url"
@@ -153,7 +153,7 @@
/><span>{{ $t("status.external_source") }}</span>
</a>
<button
- class="menu-item dropdown-item dropdown-item-icon"
+ class="menu-item dropdown-item -icon"
role="menuitem"
@click.prevent="reportStatus"
@click="close"
diff --git a/src/components/popover/popover.scss b/src/components/popover/popover.scss
@@ -54,65 +54,59 @@
a.dropdown-item,
button.dropdown-item,
- .dropdown-item:not(button, a) > button:first-child,
- .dropdown-item:not(button, a) > a:first-child {
- box-sizing: border-box;
- padding: var(--__horizontal-gap) var(--__horizontal-gap);
- grid-gap: var(--__horizontal-gap);
- display: grid;
- border: none;
- align-items: center;
- grid-template-columns: 1fr var(--__line-height);
- grid-auto-flow: column;
- grid-auto-columns: auto;
+ .dropdown-item:not(button, a) {
+ &.disabled {
+ cursor: not-allowed;
+ }
- .menu-checkbox {
- display: inline-block;
- vertical-align: middle;
- min-width: calc(var(--__line-height) + 1px);
- max-width: calc(var(--__line-height) + 1px);
- min-height: calc(var(--__line-height) + 1px);
- max-height: calc(var(--__line-height) + 1px);
- line-height: var(--__line-height);
- text-align: center;
- border-radius: 0;
- box-shadow: var(--shadow);
- margin-right: var(--__horizontal-gap);
+ &:not(.disabled) {
+ cursor: pointer;
+ }
- &.menu-checkbox-checked::after {
- font-size: 1.25em;
- content: "✓";
- }
+ .main-button {
+ box-sizing: border-box;
+ padding: var(--__horizontal-gap) var(--__horizontal-gap);
+ grid-gap: var(--__horizontal-gap);
+ display: grid;
+ border: none;
+ align-items: center;
+ grid-template-columns: 1fr var(--__line-height);
+ grid-auto-flow: column;
+ grid-auto-columns: auto;
- &.-radio {
- border-radius: 9999px;
+ .menu-checkbox {
+ display: inline-block;
+ vertical-align: middle;
+ min-width: calc(var(--__line-height) + 1px);
+ max-width: calc(var(--__line-height) + 1px);
+ min-height: calc(var(--__line-height) + 1px);
+ max-height: calc(var(--__line-height) + 1px);
+ line-height: var(--__line-height);
+ text-align: center;
+ border-radius: 0;
+ box-shadow: var(--shadow);
+ margin-right: var(--__horizontal-gap);
&.menu-checkbox-checked::after {
- font-size: 2em;
- content: "•";
+ font-size: 1.25em;
+ content: "✓";
}
- }
- }
- }
- a.dropdown-item-icon,
- button.dropdown-item-icon,
- .dropdown-item-icon:not(button, a) > button:first-child,
- .dropdown-item-icon:not(button, a) > a:first-child {
- grid-template-columns: var(--__line-height) 1fr;
- }
+ &.-radio {
+ border-radius: 9999px;
- a.dropdown-item:not(.disabled),
- button.dropdown:not(.disabled),
- .dropdown-item:not(.disabled, button, a) > button:first-child,
- .dropdown-item:not(.disabled, button, a) > a:first-child {
- cursor: pointer;
- }
+ &.menu-checkbox-checked::after {
+ font-size: 2em;
+ content: "•";
+ }
+ }
+ }
+ }
- a.dropdown-item.disabled,
- button.dropdown.disabled,
- .dropdown-item.disabled:not(button, a) > button:first-child,
- .dropdown-item.disabled:not(button, a) > a:first-child {
- cursor: not-allowed;
+ &.-icon {
+ .main-button {
+ grid-template-columns: var(--__line-height) 1fr;
+ }
+ }
}
}
diff --git a/src/components/quick_filter_settings/quick_filter_settings.vue b/src/components/quick_filter_settings/quick_filter_settings.vue
@@ -108,7 +108,7 @@
/>{{ $t('settings.hide_all_muted_posts') }}
</button>
<button
- class="menu-item dropdown-item dropdown-item-icon"
+ class="menu-item dropdown-item -icon"
role="menuitem"
@click="openTab('filtering')"
>
diff --git a/src/components/quick_view_settings/quick_view_settings.vue b/src/components/quick_view_settings/quick_view_settings.vue
@@ -85,7 +85,7 @@
/>{{ $t('settings.collapse_subject') }}
</button>
<button
- class="menu-item dropdown-item dropdown-item-icon"
+ class="menu-item dropdown-item -icon"
role="menuitem"
@click="openTab('general')"
>
diff --git a/src/components/settings_modal/settings_modal.vue b/src/components/settings_modal/settings_modal.vue
@@ -70,7 +70,7 @@
<template #content="{close}">
<div class="dropdown-menu">
<button
- class="menu-item dropdown-item dropdown-item-icon"
+ class="menu-item dropdown-item -icon"
@click.prevent="backup"
@click="close"
>
@@ -80,7 +80,7 @@
/><span>{{ $t("settings.file_export_import.backup_settings") }}</span>
</button>
<button
- class="menu-item dropdown-item dropdown-item-icon"
+ class="menu-item dropdown-item -icon"
@click.prevent="backupWithTheme"
@click="close"
>
@@ -90,7 +90,7 @@
/><span>{{ $t("settings.file_export_import.backup_settings_theme") }}</span>
</button>
<button
- class="menu-item dropdown-item dropdown-item-icon"
+ class="menu-item dropdown-item -icon"
@click.prevent="restore"
@click="close"
>
diff --git a/src/components/status_action_buttons/action_button.vue b/src/components/status_action_buttons/action_button.vue
@@ -0,0 +1,112 @@
+<template>
+ <div>
+ <component
+ :is="getComponent(button)"
+ class="main-button"
+ role="menuitem"
+ :tabindex="0"
+ :disabled="getClass(button).disabled"
+ :href="getComponent(button) == 'a' ? button.link?.(funcArg) || getRemoteInteractionLink : undefined"
+ @click.stop="getComponent(button) === 'button' && doAction(button)"
+ @click="close"
+ >
+ <FALayers>
+ <FAIcon
+ class="fa-scale-110"
+ :icon="button.icon(funcArg)"
+ :spin="!extra && button.animated?.() && animationState[button.name]"
+ :fixed-width="extra"
+ />
+ <template v-if="!getClass(button).disabled && button.toggleable?.(funcArg) && button.active">
+ <FAIcon
+ v-if="button.active(funcArg)"
+ class="active-marker"
+ transform="shrink-6 up-9 right-12"
+ :icon="button.activeIndicator?.(funcArg) || 'check'"
+ />
+ <FAIcon
+ v-if="!button.active(funcArg)"
+ class="focus-marker"
+ transform="shrink-6 up-9 right-12"
+ :icon="button.openIndicator?.(funcArg) || 'plus'"
+ />
+ <FAIcon
+ v-else
+ class="focus-marker"
+ transform="shrink-6 up-9 right-12"
+ :icon="button.closeIndicator?.(funcArg) || 'minus'"
+ />
+ </template>
+ </FALayers><span>{{ $t(button.label(funcArg)) }}</span>
+ <FAIcon
+ v-if="button.name === 'bookmark'"
+ class="chevron-icon"
+ size="lg"
+ icon="chevron-right"
+ />
+ </component>
+ </div>
+</template>
+
+<script>
+import { library } from '@fortawesome/fontawesome-svg-core'
+import {
+ faPlus,
+ faMinus,
+ faCheck,
+ faTimes,
+ faWrench,
+
+ faReply,
+ faRetweet,
+ faStar,
+ faSmileBeam,
+
+ faEllipsisH,
+ faBookmark,
+ faEyeSlash,
+ faThumbtack,
+ faShareAlt,
+ faExternalLinkAlt,
+ faHistory
+} from '@fortawesome/free-solid-svg-icons'
+import {
+ faStar as faStarRegular
+} from '@fortawesome/free-regular-svg-icons'
+
+library.add(
+ faPlus,
+ faMinus,
+ faCheck,
+ faTimes,
+ faWrench,
+
+ faReply,
+ faRetweet,
+ faStar,
+ faStarRegular,
+ faSmileBeam,
+
+ faEllipsisH,
+ faBookmark,
+ faEyeSlash,
+ faThumbtack,
+ faShareAlt,
+ faExternalLinkAlt,
+ faHistory
+)
+
+export default {
+ props: [
+ 'button',
+ 'extra',
+ 'status',
+ 'funcArg',
+ 'animationState',
+ 'getClass',
+ 'getComponent',
+ 'doAction',
+ 'close'
+ ]
+}
+</script>
diff --git a/src/components/status_action_buttons/status_action_buttons.js b/src/components/status_action_buttons/status_action_buttons.js
@@ -1,6 +1,8 @@
import { mapState } from 'vuex'
import ConfirmModal from 'src/components/confirm_modal/confirm_modal.vue'
+import ActionButton from './action_button.vue'
+import StatusBookmarkFolderMenu from 'src/components/status_bookmark_folder_menu/status_bookmark_folder_menu.vue'
import Popover from 'src/components/popover/popover.vue'
import genRandomSeed from 'src/services/random_seed/random_seed.service.js'
@@ -187,8 +189,7 @@ const BUTTONS = [{
} else {
return dispatch('bookmark', { id: status.id })
}
- },
- popover: 'bookmark-folders'
+ }
}, {
// =========
// EDIT
@@ -299,7 +300,9 @@ const StatusActionButtons = {
},
components: {
Popover,
- ConfirmModal
+ ConfirmModal,
+ ActionButton,
+ StatusBookmarkFolderMenu
},
computed: {
...mapState({
@@ -333,7 +336,6 @@ const StatusActionButtons = {
triggerAttrs () {
return {
title: this.$t('status.more_actions'),
- id: `popup-trigger-${this.randomSeed}`,
'aria-controls': `popup-menu-${this.randomSeed}`,
'aria-expanded': this.expanded,
'aria-haspopup': 'menu'
@@ -375,7 +377,7 @@ const StatusActionButtons = {
this.$store.commit('addCollectionPreference', { path: 'collections.pinnedStatusActions', value: button.name })
this.$store.dispatch('pushServerSideStorage')
},
- component (button) {
+ getComponent (button) {
if (!this.$store.state.users.currentUser && button.anonLink) {
return 'a'
} else if (button.action == null && button.link != null) {
diff --git a/src/components/status_action_buttons/status_action_buttons.vue b/src/components/status_action_buttons/status_action_buttons.vue
@@ -8,15 +8,15 @@
:key="button.name"
>
<component
- :is="component(button)"
+ :is="getComponent(button)"
class="button-unstyled action-button"
:class="getClass(button)"
:disabled="getClass(button).disabled"
role="button"
:tabindex="0"
:title="$t(button.label(funcArg))"
- @click.stop="component(button) === 'button' && doAction(button)"
- :href="component(button) == 'a' ? button.link?.(funcArg) || getRemoteInteractionLink : undefined"
+ @click.stop="getComponent(button) === 'button' && doAction(button)"
+ :href="getComponent(button) == 'a' ? button.link?.(funcArg) || getRemoteInteractionLink : undefined"
>
<FALayers>
<FAIcon
@@ -90,7 +90,7 @@
class="dropdown-menu extra-action-buttons"
role="menu"
>
- <div class="menu-item dropdown-item extra-action dropdown-item-icon">
+ <div class="menu-item dropdown-item extra-action -icon">
<button
class="main-button"
role="menuitem"
@@ -107,50 +107,32 @@
<div
v-for="button in extraButtons"
:key="button.name"
- class="menu-item dropdown-item extra-action dropdown-item-icon"
+ class="menu-item dropdown-item extra-action -icon"
:disabled="getClass(button).disabled"
:class="{ disabled: getClass(button).disabled }"
>
- <component
- :is="component(button)"
- class="main-button"
- role="menuitem"
- :class="getClass(button)"
- :tabindex="0"
- :disabled="getClass(button).disabled"
- @click.stop="component(button) === 'button' && doAction(button)"
- @click="close"
- :href="component(button) == 'a' ? button.link?.(funcArg) || getRemoteInteractionLink : undefined"
+ <Popover
+ v-if="getComponent(button) === 'button'"
+ trigger="hover"
+ placement="right"
>
- <FALayers>
- <FAIcon
- class="fa-scale-110"
- :icon="button.icon(funcArg)"
- :spin="button.animated?.() && animationState[button.name]"
- fixed-width
+ <template #trigger>
+ <ActionButton
+ :button="button"
+ :status="status"
+ :extra="true"
+ :funcArg="funcArg"
+ :get-class="getClass"
+ :get-component="getComponent"
+ :animation-state="animationState"
+ :close="close"
+ :do-action="doAction"
/>
- <template v-if="!getClass(button).disabled && button.toggleable?.(funcArg) && button.active">
- <FAIcon
- v-if="button.active(funcArg)"
- class="active-marker"
- transform="shrink-6 up-9 right-12"
- :icon="button.activeIndicator?.(funcArg) || 'check'"
- />
- <FAIcon
- v-if="!button.active(funcArg)"
- class="focus-marker"
- transform="shrink-6 up-9 right-12"
- :icon="button.openIndicator?.(funcArg) || 'plus'"
- />
- <FAIcon
- v-else
- class="focus-marker"
- transform="shrink-6 up-9 right-12"
- :icon="button.closeIndicator?.(funcArg) || 'minus'"
- />
- </template>
- </FALayers><span>{{ $t(button.label(funcArg)) }}</span>
- </component>
+ </template>
+ <template #content>
+ <StatusBookmarkFolderMenu v-if="button.name === 'bookmark'" :status="funcArg.status" />
+ </template>
+ </Popover>
<button
v-if="showPin && currentUser"
type="button"
diff --git a/src/components/status_bookmark_folder_menu/status_bookmark_folder_menu.vue b/src/components/status_bookmark_folder_menu/status_bookmark_folder_menu.vue
@@ -1,39 +1,17 @@
<template>
- <div class="StatusBookmarkFolderMenu">
- <Popover
- trigger="hover"
- placement="left"
- remove-padding
+ <div class="dropdown-menu">
+ <button
+ v-for="folder in folders"
+ :key="folder.id"
+ class="menu-item dropdown-item -icon"
+ @click="toggleFolder(folder.id)"
>
- <template #content>
- <div class="dropdown-menu">
- <button
- v-for="folder in folders"
- :key="folder.id"
- class="menu-item dropdown-item"
- @click="toggleFolder(folder.id)"
- >
- <span
- class="input menu-checkbox -radio"
- :class="{ 'menu-checkbox-checked': status.bookmark_folder_id == folder.id }"
- />
- {{ folder.name }}
- </button>
- </div>
- </template>
- <template #trigger>
- <button class="menu-item dropdown-item dropdown-item-icon -has-submenu">
- <FAIcon
- fixed-width
- icon="folder"
- />{{ $t('bookmark_folders.select_folder') }}<FAIcon
- class="chevron-icon"
- size="lg"
- icon="chevron-right"
- />
- </button>
- </template>
- </Popover>
+ <span
+ class="input menu-checkbox -radio"
+ :class="{ 'menu-checkbox-checked': status.bookmark_folder_id == folder.id }"
+ />
+ {{ folder.name }}
+ </button>
</div>
</template>
diff --git a/src/components/user_list_menu/user_list_menu.vue b/src/components/user_list_menu/user_list_menu.vue
@@ -11,7 +11,7 @@
<button
v-for="list in lists"
:key="list.id"
- class="menu-item dropdown-item dropdown-item-icon"
+ class="menu-item dropdown-item -icon"
@click="toggleList(list.id)"
>
<span
@@ -23,14 +23,14 @@
</div>
</template>
<template #trigger>
- <span>
+ <span class="main-button">
{{ $t('lists.manage_lists') }}
+ <FAIcon
+ class="chevron-icon"
+ size="lg"
+ icon="chevron-right"
+ />
</span>
- <FAIcon
- class="chevron-icon"
- size="lg"
- icon="chevron-right"
- />
</template>
</Popover>
</div>