From 27cd042df9aca0383a49f3514bc21958dd890912 Mon Sep 17 00:00:00 2001
From: gaoluyang <2820782392@qq.com>
Date: 星期一, 29 六月 2026 15:42:23 +0800
Subject: [PATCH] 银川 1.联调产品维护页面 2.添加IM即时通讯模块
---
src/views/im/home/pages/conversation/components/input/message-multi-select-bar.vue | 153 +++++++++++++++++++++++++++++++++++++++++++++++++++
1 files changed, 153 insertions(+), 0 deletions(-)
diff --git a/src/views/im/home/pages/conversation/components/input/message-multi-select-bar.vue b/src/views/im/home/pages/conversation/components/input/message-multi-select-bar.vue
new file mode 100644
index 0000000..fa30729
--- /dev/null
+++ b/src/views/im/home/pages/conversation/components/input/message-multi-select-bar.vue
@@ -0,0 +1,153 @@
+<script lang="ts" setup>
+import type { Message } from '#/views/im/home/types'
+
+import { computed, inject } from 'vue'
+
+import { confirm } from '#/packages/effects/common-ui/src'
+import { IconifyIcon as Icon } from '#/packages/icons/src'
+
+import { useMessageMultiSelect } from '#/views/im/home/composables/useMessageMultiSelect'
+import { useConversationStore } from '#/views/im/home/store/conversationStore'
+import { useMessageStore } from '#/views/im/home/store/messageStore'
+import { ImForwardMode, isNormalMessage } from '#/views/im/utils/constants'
+import { getClientConversationId } from '#/views/im/utils/db'
+
+import { IM_FORWARD_DIALOG_KEY } from '../message/forward/keys'
+
+defineOptions({ name: 'ImMessageMultiSelectBar' })
+
+const conversationStore = useConversationStore()
+const messageStore = useMessageStore()
+const openForwardDialog = inject(IM_FORWARD_DIALOG_KEY)
+const multiSelect = useMessageMultiSelect()
+
+/** 閫変腑鏉℃暟 */
+const selectedCount = computed(() => multiSelect.state.selectedClientMessageIds.length)
+
+/** 褰撳墠浼氳瘽鍐呭凡閫夋秷鎭� */
+function getSelectedMessages(): Message[] {
+ const conversation = conversationStore.activeConversation
+ if (!conversation) {
+ return []
+ }
+ const ids = multiSelect.selectedIdSet.value
+ return messageStore
+ .getMessages(getClientConversationId(conversation.type, conversation.targetId))
+ .filter((message) => ids.has(message.clientMessageId) && isNormalMessage(message.type))
+}
+
+/** 閫愭潯杞彂锛氬紑 ForwardDialog 鍗曟潯妯″紡 */
+function handleForwardOneByOne() {
+ const conversation = conversationStore.activeConversation
+ if (!conversation) {
+ return
+ }
+ const messages = getSelectedMessages()
+ if (messages.length === 0) {
+ return
+ }
+ openForwardDialog?.({
+ mode: ImForwardMode.SINGLE,
+ messages,
+ sourceConversation: conversation
+ })
+}
+
+/** 鍚堝苟杞彂锛氬紑 ForwardDialog 鍚堝苟妯″紡 */
+function handleForwardMerged() {
+ const conversation = conversationStore.activeConversation
+ if (!conversation) {
+ return
+ }
+ const messages = getSelectedMessages()
+ if (messages.length === 0) {
+ return
+ }
+ openForwardDialog?.({
+ mode: ImForwardMode.MERGE,
+ messages,
+ sourceConversation: conversation
+ })
+}
+
+/** 鍒犻櫎锛氬脊纭妗� 鈫� 鏈湴鎵归噺绉婚櫎锛堜笉鍚屾鍚庣锛屽榻愬井淇°�屽垹闄ゃ�嶈涔夛級 */
+async function handleDelete() {
+ const conversation = conversationStore.activeConversation
+ if (!conversation) {
+ return
+ }
+ const messages = getSelectedMessages()
+ if (messages.length === 0) {
+ return
+ }
+ try {
+ await confirm(`纭鍒犻櫎閫変腑鐨� ${messages.length} 鏉℃秷鎭紵`, {
+ cancelText: '鍙栨秷',
+ confirmText: '纭畾',
+ icon: 'warning',
+ title: '鍒犻櫎纭'
+ })
+ } catch {
+ return
+ }
+ for (const m of messages) {
+ messageStore.removeMessage(conversation.type, conversation.targetId, {
+ id: m.id,
+ clientMessageId: m.clientMessageId
+ })
+ }
+ multiSelect.exit()
+}
+
+/** 鍙栨秷澶氶�� */
+function handleCancel() {
+ multiSelect.exit()
+}
+</script>
+
+<template>
+ <div
+ v-if="multiSelect.state.active"
+ class="flex items-center justify-center gap-12 px-5 w-full h-full border-t border-t-solid bg-[var(--ant-color-bg-container)] border-[var(--im-border-color-lighter)]"
+ >
+ <span
+ class="absolute left-5 top-1/2 -translate-y-1/2 text-12px text-[var(--ant-color-text-secondary)]"
+ >
+ 宸查�� {{ selectedCount }} 鏉�
+ </span>
+
+ <button
+ class="inline-flex flex-col items-center gap-1 px-3 py-1 text-12px rounded-md border-0 bg-transparent cursor-pointer transition-colors text-[var(--ant-color-text)] hover:text-[var(--ant-color-primary)] hover:bg-[var(--ant-color-fill)] disabled:text-[var(--ant-color-text-disabled)] disabled:cursor-not-allowed disabled:bg-transparent"
+ :disabled="selectedCount === 0"
+ @click="handleForwardOneByOne"
+ >
+ <Icon icon="ant-design:share-alt-outlined" :size="22" />
+ <span>閫愭潯杞彂</span>
+ </button>
+
+ <button
+ class="inline-flex flex-col items-center gap-1 px-3 py-1 text-12px rounded-md border-0 bg-transparent cursor-pointer transition-colors text-[var(--ant-color-text)] hover:text-[var(--ant-color-primary)] hover:bg-[var(--ant-color-fill)] disabled:text-[var(--ant-color-text-disabled)] disabled:cursor-not-allowed disabled:bg-transparent"
+ :disabled="selectedCount === 0"
+ @click="handleForwardMerged"
+ >
+ <Icon icon="tabler:arrow-merge" :size="22" />
+ <span>鍚堝苟杞彂</span>
+ </button>
+
+ <button
+ class="inline-flex flex-col items-center gap-1 px-3 py-1 text-12px rounded-md border-0 bg-transparent cursor-pointer transition-colors text-[var(--ant-color-text)] hover:bg-[var(--ant-color-fill)] hover:text-[var(--ant-color-error)] disabled:text-[var(--ant-color-text-disabled)] disabled:cursor-not-allowed disabled:bg-transparent"
+ :disabled="selectedCount === 0"
+ @click="handleDelete"
+ >
+ <Icon icon="ant-design:delete-outlined" :size="22" />
+ <span>鍒犻櫎</span>
+ </button>
+
+ <button
+ class="absolute right-5 top-1/2 -translate-y-1/2 inline-flex items-center justify-center w-7 h-7 rounded-full border-0 bg-transparent cursor-pointer transition-colors text-[var(--ant-color-text-secondary)] hover:text-[var(--ant-color-text)] hover:bg-[var(--ant-color-fill)]"
+ @click="handleCancel"
+ >
+ <Icon icon="ant-design:close-outlined" :size="20" />
+ </button>
+ </div>
+</template>
--
Gitblit v1.9.3