优化UI,修复群BUG

This commit is contained in:
cbb
2026-01-24 16:49:47 +08:00
parent c508b1fcb4
commit a55a1593bb
11 changed files with 555 additions and 445 deletions

View File

@@ -12,7 +12,7 @@
:class="['tui-chat', !isPC && 'tui-chat-h5']"
>
<ChatHeader
:isGroup="isGroup"
:isGroup="!isNotInGroup ? isGroup : null"
:headerExtensionList="headerExtensionList"
:serviceID="serviceID"
@closeChat="closeChat"
@@ -287,7 +287,6 @@
}
function onCurrentConversationUpdate(conversation: IConversationModel) {
updateUIUserNotInGroup(conversation)
// return when currentConversation is null
if (!conversation) {

View File

@@ -56,7 +56,7 @@
item.type === TYPES.MSG_GRP_TIP ||
isCreateGroupCustomMessage(item)
"
:content="item.getMessageContent()"
:content="item"
/>
<div
v-else-if="!item.isRevoked && !isPluginMessage(item)"

View File

@@ -12,7 +12,7 @@ const props = defineProps({
default: () => ({}),
},
});
const tipContent = computed(() => props.content?.text || props.content?.custom || '');
const tipContent = computed(() => `${props.content.nick || props.content.from} 创建群聊`);
</script>
<style lang="scss" scoped>
@import "../../../../assets/styles/common";

View File

@@ -128,7 +128,10 @@
{{ conversation.getGroupAtInfo() }}
</span>
<view class="middle-box-content">
{{ conversation.getLastMessage('text') }}
{{
isFirstCreateGroup(conversation) ||
conversation.getLastMessage('text')
}}
</view>
</view>
</view>
@@ -366,7 +369,7 @@
const redEnvelopeText = (item: IConversationModel) => {
const payload = JSON.parse(item.lastMessage?.payload?.data)
const text = item.getLastMessage('text')?.split(':')
console.log(text)
if (text && text.length > 1) {
return `${text[0]}:[积分红包] ${payload.title}`
} else {
@@ -374,6 +377,17 @@
}
}
/** 是否最开始创建群聊 */
const isFirstCreateGroup = (item: IConversationModel) => {
if (item.type === 'GROUP' && item?.lastMessage?.payload?.data) {
const data = JSON.parse(item?.lastMessage?.payload?.data)
return data.content === 'Create Group'
? `${item.getLastMessage('text')?.split(':')[0]}:创建群聊`
: ''
}
return ''
}
function onConversationListUpdated(list: IConversationModel[]) {
conversationList.value = list
}

View File

@@ -1,8 +1,8 @@
<template>
<div class="group" :class="[!isPC ? 'group-h5' : '']">
<view class="group" :class="[!isPC ? 'group-h5' : '']">
<div class="group-box">
<ul v-if="!groupInfo.isEdit" class="group-list">
<li class="group-list-item">
<li style="border-bottom: none" class="group-list-item">
<label class="group-list-item-label">
{{ TUITranslateService.t('TUIGroup.群头像') }}
</label>
@@ -12,23 +12,23 @@
<li
v-for="(item, index) in createInfo"
:key="index"
class="group-list-item"
class="group-list-item item-input_box"
>
<label class="group-list-item-label">{{ item.name }}</label>
<input
v-if="isPC"
v-model="groupInfo.profile[item.key]"
type="text"
:placeholder="item.placeholder"
class="btn-input"
/>
<span
<!-- <span
v-else
class="group-h5-list-item-content"
@click="edit(item.key)"
>
<p class="content">{{ groupInfo.profile[item.key] }}</p>
<Icon :file="rightIcon" />
</span>
</span> -->
</li>
<!-- <li class="group-list-item" @click="cbPopupShow.open('bottom')">
<label class="group-list-item-label">申请加群方式</label>
@@ -89,7 +89,8 @@
@selectType="selected"
/>
</div>
<footer class="group-profile-footer">
<!-- 原版确认按钮 -->
<!-- <footer class="group-profile-footer">
<button
v-if="isPC && !groupInfo.isEdit"
class="btn-default"
@@ -104,7 +105,12 @@
>
{{ TUITranslateService.t('TUIGroup.确认') }}
</button>
</footer>
</footer> -->
<bottom-view>
<cb-button :disabled="submitDisabledStatus" @click="submit">
确认添加
</cb-button>
</bottom-view>
</div>
<uni-popup ref="cbPopupShow" backgroundColor="#fff">
@@ -125,7 +131,7 @@
<text @click="cbPopupShow.close()">取消</text>
</view>
</uni-popup>
</div>
</view>
</template>
<script lang="ts" setup>
import TUIChatEngine, {
@@ -370,12 +376,45 @@
</script>
<style lang="scss" scoped src="./style/index.scss"></style>
<style lang="scss" scoped>
.group {
background: #f4f4f4;
}
.group-h5 {
padding: 32rpx 24rpx;
}
.group-box {
border-radius: 16rpx;
}
.group-h5-list-item-content {
.content {
padding: 0 !important;
font-size: 32rpx;
color: #333333;
}
}
.group-list {
margin: 0 !important;
.group-list-item {
padding: 24rpx 32rpx !important;
display: flex;
align-items: center;
border-bottom: 2rpx solid #e5e5e5;
box-sizing: border-box;
}
.item-input_box {
.btn-input {
padding: 0;
height: 44rpx;
font-size: 32rpx;
color: #333333;
border: none !important;
// background: rgb(238, 128, 128);
text-align: right;
}
}
}
.popup-content {

View File

@@ -48,6 +48,7 @@
TUIStore.watch(StoreName.GRP, {
isShowCreateComponent: (data: any) => {
console.log(data, '=============1111')
if (data) {
isShowCreateGroup.value = true
title.value = TUITranslateService.t('TUIConversation.发起群聊')
@@ -56,6 +57,7 @@
}
},
isShowManageComponent: (data: any) => {
console.log(data, '=============2222')
if (data) {
isShowManageGroup.value = true
title.value = TUITranslateService.t('TUIGroup.群管理')
@@ -87,6 +89,9 @@
}
</script>
<style lang="scss" scoped>
page {
background: #f4f4f4;
}
.tui-group {
width: 100%;
height: 100%;

View File

@@ -14,16 +14,23 @@
@getMore="getMember('more')"
/>
<main
v-else-if="!currentTab || (isUniFrameWork && currentTab != 'admin')"
v-else-if="
currentGroup?.groupID &&
(!currentTab || (isUniFrameWork && currentTab != 'admin'))
"
class="main"
>
<view class="main-box">
<ManageName
:isAuthor="isOwner || isAdmin || isWorkGroup"
:data="currentGroup"
@update="updateProfile"
/>
<div class="user-info space-top">
<header class="user-info-header" @click="setCurrentTab('member')">
<header
class="user-info-header"
@click="setCurrentTab('member')"
>
<label class="user-info-header-left">
{{ TUITranslateService.t(`TUIGroup.群成员`) }}
</label>
@@ -37,7 +44,10 @@
</header>
<ol class="user-info-list">
<dl
v-for="(item, index) in groupMemberList.slice(0, showUserNum)"
v-for="(item, index) in groupMemberList.slice(
0,
showUserNum
)"
:key="index"
class="user-info-list-item"
>
@@ -58,7 +68,7 @@
{{ item.nick || item.userID }}
</dd>
</dl>
<dl v-if="isShowAddMember" class="user-info-list-item">
<!-- <dl v-if="isShowAddMember" class="user-info-list-item">
<dt class="avatar" @click="toggleMask('add')">+</dt>
</dl>
<dl
@@ -66,7 +76,7 @@
class="user-info-list-item"
>
<dt class="avatar" @click="toggleMask('remove')">-</dt>
</dl>
</dl> -->
</ol>
<div
v-if="groupMemberList.length > showUserNum"
@@ -147,6 +157,7 @@
{{ TUITranslateService.t(`TUIGroup.退出群组`) }}
</li>
</ul>
</view>
</main>
<ManageMember
v-if="currentTab === 'member'"
@@ -238,12 +249,15 @@
import Server from '../server'
import { enableSampleTaskStatus } from '../../../utils/enableSampleTaskStatus'
import { IFriendProfile, IGroupMember } from '../../../interface'
import { useUI } from '../../../../utils/use-ui'
import {
createImGroup,
deleteImGroup,
quitImGroup
} from '../../../../api/tui-kit'
const { showLoading, hideLoading, showDialog } = useUI()
const TUIGroupServer = Server.getInstance()
const TUIConstants = TUIGroupServer.constants
@@ -676,14 +690,25 @@
}
const dismissGroup = async (group: any) => {
const show = await showDialog('提示', '确定要解散群组吗?')
if (!show) {
return
}
// await deleteImGroup(group.groupID)
await TUIGroupService.dismissGroup(group.groupID)
showLoading()
TUIGroupService.dismissGroup(group.groupID)
.then(() => {
enableSampleTaskStatus('dismissGroup')
hideLoading()
Toast({
message: TUITranslateService.t('TUIGroup.群组解散成功'),
type: TOAST_TYPE.SUCCESS
})
clearGroupInfo()
})
.catch(() => {
hideLoading()
})
}
const clearGroupInfo = () => {
@@ -724,9 +749,8 @@
switch (transferType.value) {
case 'add':
try {
imMemberResponse = await TUIGroupService.getGroupMemberProfile(
options
)
imMemberResponse =
await TUIGroupService.getGroupMemberProfile(options)
transferList.value = transferList.value.filter(
(item: any) => item.userID !== imResponse.data[0]?.userID
)
@@ -752,9 +776,8 @@
break
case 'remove':
try {
imResponse = await TUIGroupService.getGroupMemberProfile(
options
)
imResponse =
await TUIGroupService.getGroupMemberProfile(options)
if (imResponse.data.memberList.length === 0) {
const message = TUITranslateService.t(
'TUIGroup.该用户不在群组内'
@@ -894,9 +917,24 @@
}
const quitGroup = async (group: any) => {
const show = await showDialog('提示', '确定要退出群组吗?')
if (!show) {
return
}
showLoading()
// await quitImGroup(group.groupID)
await TUIGroupService.quitGroup(group.groupID)
TUIGroupService.quitGroup(group.groupID)
.then(() => {
hideLoading()
Toast({
message: '退出群组成功',
type: TOAST_TYPE.SUCCESS
})
clearGroupInfo()
})
.catch(() => {
hideLoading()
})
}
const back = () => {

View File

@@ -1,5 +1,6 @@
<template>
<div class="admin-main">
<view class="admin-box">
<div class="admin-manage">
<div class="admin-manage-header">
{{ TUITranslateService.t(`TUIGroup.群管理员`) }}
@@ -17,23 +18,20 @@
item.avatar ||
'https://web.sdk.qcloud.com/component/TUIKit/assets/avatar_21.png'
"
onerror="this.onerror=null;this.src='https://web.sdk.qcloud.com/component/TUIKit/assets/avatar_21.png'"
>
onerror="
this.onerror = null
this.src =
'https://web.sdk.qcloud.com/component/TUIKit/assets/avatar_21.png'
"
/>
</div>
<div class="item-name">
{{ item.nick || item.userID }}
</div>
</li>
<li class="admin-manage-list-item">
<div
class="item-main"
@click="addAdmin"
>
<Icon
:file="plusSVG"
width="16px"
height="16px"
/>
<div class="item-main" @click="addAdmin">
<Icon :file="plusSVG" width="16px" height="16px" />
</div>
</li>
<li class="admin-manage-list-item">
@@ -42,19 +40,12 @@
class="item-main"
@click="removeAdmin"
>
<Icon
:file="minusSVG"
width="16px"
height="16px"
/>
<Icon :file="minusSVG" width="16px" height="16px" />
</div>
</li>
</ul>
</div>
<div
v-if="isAdminSetMuteTime"
class="admin-mute-all"
>
<div v-if="isAdminSetMuteTime" class="admin-mute-all">
<div>
<div class="admin-mute-all-title">
{{ TUITranslateService.t(`TUIGroup.全员禁言`) }}
@@ -72,10 +63,7 @@
@change="setAllMuteTime"
/>
</div>
<div
v-if="isAdminSetMuteTime"
class="admin-mute"
>
<div v-if="isAdminSetMuteTime" class="admin-mute">
<div class="admin-mute-header">
{{ TUITranslateService.t(`TUIGroup.单独禁言人员`) }}
</div>
@@ -92,23 +80,20 @@
item.avatar ||
'https://web.sdk.qcloud.com/component/TUIKit/assets/avatar_21.png'
"
onerror="this.onerror=null;this.src='https://web.sdk.qcloud.com/component/TUIKit/assets/avatar_21.png'"
>
onerror="
this.onerror = null
this.src =
'https://web.sdk.qcloud.com/component/TUIKit/assets/avatar_21.png'
"
/>
</div>
<div class="item-name">
{{ item.nick || item.userID }}
</div>
</li>
<li class="admin-mute-list-item">
<div
class="item-main"
@click="addMute"
>
<Icon
:file="plusSVG"
width="16px"
height="16px"
/>
<div class="item-main" @click="addMute">
<Icon :file="plusSVG" width="16px" height="16px" />
</div>
</li>
<li class="admin-mute-list-item">
@@ -117,62 +102,59 @@
class="item-main"
@click="removeMute"
>
<Icon
:file="minusSVG"
width="16px"
height="16px"
/>
<Icon :file="minusSVG" width="16px" height="16px" />
</div>
</li>
</ul>
</div>
</view>
</div>
</template>
<script lang="ts" setup>
import {
TUITranslateService,
IGroupModel,
} from '@tencentcloud/chat-uikit-engine-lite';
import { watchEffect, ref } from '../../../adapter-vue';
import Slider from '../../common/Slider/index.vue';
import Icon from '../../common/Icon.vue';
import plusSVG from '../../../assets/icon/plus.svg';
import minusSVG from '../../../assets/icon/minus.svg';
import { IGroupMember } from '../../../interface';
IGroupModel
} from '@tencentcloud/chat-uikit-engine-lite'
import { watchEffect, ref } from '../../../adapter-vue'
import Slider from '../../common/Slider/index.vue'
import Icon from '../../common/Icon.vue'
import plusSVG from '../../../assets/icon/plus.svg'
import minusSVG from '../../../assets/icon/minus.svg'
import { IGroupMember } from '../../../interface'
const props = defineProps({
member: {
type: Object,
default: () => {},
default: () => {}
},
isSetMuteTime: {
type: Boolean,
default: () => false,
default: () => false
},
currentGroup: {
type: Object,
default: () => {},
},
});
default: () => {}
}
})
const isAdminSetMuteTime = ref(false);
const isAdminSetMuteTime = ref(false)
const memberAdmin = ref({
admin: [] as Array<IGroupMember>,
member: [] as Array<IGroupMember>,
muteMember: [] as Array<IGroupMember>,
});
const currentGroupAdmin = ref<IGroupModel>();
muteMember: [] as Array<IGroupMember>
})
const currentGroupAdmin = ref<IGroupModel>()
watchEffect(() => {
memberAdmin.value = props.member as {
admin: Array<IGroupMember>;
member: Array<IGroupMember>;
muteMember: Array<IGroupMember>;
};
isAdminSetMuteTime.value = props.isSetMuteTime;
currentGroupAdmin.value = props.currentGroup;
});
admin: Array<IGroupMember>
member: Array<IGroupMember>
muteMember: Array<IGroupMember>
}
isAdminSetMuteTime.value = props.isSetMuteTime
currentGroupAdmin.value = props.currentGroup
})
const emits = defineEmits([
'addAdmin',
@@ -180,32 +162,32 @@ const emits = defineEmits([
'setAllMuteTime',
'addMute',
'removeMute',
'close',
]);
'close'
])
const addAdmin = () => {
emits('addAdmin');
};
emits('addAdmin')
}
const removeAdmin = () => {
emits('removeAdmin');
};
emits('removeAdmin')
}
const setAllMuteTime = (value: boolean) => {
emits('setAllMuteTime', value);
};
emits('setAllMuteTime', value)
}
const addMute = () => {
emits('addMute');
};
emits('addMute')
}
const removeMute = () => {
emits('removeMute');
};
emits('removeMute')
}
</script>
<style lang="scss" scoped>
@import "../../../assets/styles/common";
@import '../../../assets/styles/common';
.admin {
width: 100%;
@@ -218,7 +200,7 @@ const removeMute = () => {
padding: 10px;
&-left {
font-family: "PingFang SC", sans-serif;
font-family: 'PingFang SC', sans-serif;
font-size: 18px;
font-weight: 500;
line-height: 50px;
@@ -227,7 +209,7 @@ const removeMute = () => {
}
&-close {
font-family: "PingFang SC", sans-serif;
font-family: 'PingFang SC', sans-serif;
font-size: 16px;
font-weight: 400;
line-height: 48px;
@@ -253,7 +235,7 @@ const removeMute = () => {
&-header {
padding-left: 10px;
font-family: "PingFang SC", sans-serif;
font-family: 'PingFang SC', sans-serif;
font-size: 14px;
font-weight: 400;
line-height: 20px;
@@ -314,7 +296,7 @@ const removeMute = () => {
&-title {
padding-left: 10px;
font-family: "PingFang SC", sans-serif;
font-family: 'PingFang SC', sans-serif;
font-size: 14px;
font-weight: 400;
line-height: 20px;
@@ -325,7 +307,7 @@ const removeMute = () => {
&-content {
color: #999;
padding-left: 10px;
font-family: "PingFang SC", sans-serif;
font-family: 'PingFang SC', sans-serif;
font-size: 12px;
font-weight: 400;
line-height: 17px;
@@ -335,4 +317,22 @@ const removeMute = () => {
}
}
}
.admin-main {
background: #f4f4f4;
.admin-box {
padding: 32rpx 24rpx;
.admin-manage,
.admin-mute-all,
.admin-mute {
background: #ffffff;
border-bottom: 0;
border-radius: 16rpx;
}
.admin-mute-all {
margin: 20rpx 0;
}
}
}
</style>

View File

@@ -143,6 +143,8 @@
@import '../../../assets/styles/common';
.group-name {
background: #ffffff;
border-radius: 16rpx;
padding: 14px 20px;
font-weight: 400;
font-size: 14px;

View File

@@ -3,7 +3,6 @@
@import './web';
@import './h5';
.icon-close {
display: inline-block;
width: 24px;
@@ -14,9 +13,9 @@
.icon-close::before,
.icon-close::after {
content: "";
content: '';
position: absolute;
background-color: #8F959E;
background-color: #8f959e;
height: 16px;
width: 2px;
top: 50%;
@@ -37,3 +36,17 @@
position: absolute;
left: 20px;
}
.main {
background: #f4f4f4;
.main-box {
padding: 32rpx 24rpx;
.space-top {
border-top: 0 !important;
background: #ffffff;
border-radius: 16rpx !important;
margin-top: 20rpx;
overflow: hidden;
}
}
}

View File

@@ -1,8 +1,8 @@
import { TUIStore, StoreName } from "@tencentcloud/chat-uikit-engine-lite";
import { TUIStore, StoreName } from '@tencentcloud/chat-uikit-engine-lite'
export function enableSampleTaskStatus(taskKey: string) {
const tasks = TUIStore.getData(StoreName.APP, "tasks");
const tasks = TUIStore.getData(StoreName.APP, 'tasks')
if (taskKey in tasks && !tasks[taskKey]) {
tasks[taskKey] = true;
TUIStore.update(StoreName.APP, "tasks", tasks);
tasks[taskKey] = true
TUIStore.update(StoreName.APP, 'tasks', tasks)
}
}