jiuyiUniapp/jiuyi/TUIKit/tui-customer-service-plugin/components/message-rating/message-rating-number.vue

249 lines
5.4 KiB
Vue
Raw Normal View History

2024-12-18 15:46:27 +08:00
<template>
<div class="message-rating-star">
<p class="rating-head">
{{ props.ratingTemplate.head }}
</p>
<div class="rating-card">
<span class="card-title">请对本次服务进行评价</span>
<div class="card-wrapper">
<div style="max-width: 250px">
<div
v-for="(item, index) in numberList"
:key="index"
:class="{
'active': !(index !== selectValue && index !== hoverValue),
'de-active': index !== selectValue && index !== hoverValue,
}"
:style="{
marginLeft: index === 0 ? 0 + 'px' : 20 + 'px',
margin: 5 + 'px',
}"
@click="setValue(index)"
@mouseenter="setHoverValue(index)"
@mouseleave="setHoverValue(-1)"
>
{{ item + 1 }}
</div>
</div>
</div>
<div :style="{ marginTop: 10 + 'px', marginBottom: 10 + 'px' }">
{{
hoverValue === -1
? selectValue === -1
? "如果满意请给好评哦~"
: desc[selectValue]
: desc[hoverValue]
}}
</div>
<button
class="submit-button"
:disabled="hasReply || hasExpire"
@click="submitRatingStar"
>
提交评价
</button>
</div>
<p
v-if="hasReply"
class="rating-tail"
:style="{
marginTop: 20 + 'px',
}"
>
{{ props.ratingTemplate.tail }}
</p>
</div>
</template>
<script lang="ts">
import vue from '../../adapter-vue';
import { CUSTOM_MESSAGE_SRC } from '../../constant';
import { ratingTemplateType } from '../../interface';
const { computed, ref, watchEffect } = vue;
interface Props {
ratingTemplate: ratingTemplateType;
}
export default {
props: {
ratingTemplate: {
type: Object as () => ratingTemplateType,
default: () => ({}),
},
},
emits: ['sendMessage'],
setup(props: Props, { emit }) {
const hasReply = ref<boolean>(false);
const sessionId = ref<string>('');
const selectValue = ref<number>(-1);
const hoverValue = ref<number>(-1);
const hasExpire = ref<boolean>(false);
const desc = computed(() => {
return props.ratingTemplate?.menu.map(item => item.content);
});
const numberList = computed(() => {
return props.ratingTemplate?.menu.map((item, index) => index);
});
watchEffect(() => {
sessionId.value = props.ratingTemplate.sessionId || '';
if (props.ratingTemplate.selected != undefined) {
for (let i = 0; i < props.ratingTemplate.menu.length; i++) {
if (props.ratingTemplate.menu[i].id == props.ratingTemplate.selected.id) {
hasReply.value = true;
selectValue.value = i;
break;
}
}
}
const timestamp = Math.floor(new Date().getTime() / 1000);
if (timestamp > props.ratingTemplate.expireTime) {
hasExpire.value = true;
}
});
const setValue = (val: number) => {
if (!hasReply.value) {
selectValue.value = val;
}
};
const setHoverValue = (value: number) => {
if (!hasReply.value) {
hoverValue.value = value;
}
};
const submitRatingStar = () => {
if (selectValue.value >= 0) {
const submitData = {
data: JSON.stringify({
src: CUSTOM_MESSAGE_SRC.MENU_SELECTED,
menuSelected: {
id: props.ratingTemplate.menu[selectValue.value].id,
content: props.ratingTemplate.menu[selectValue.value].content,
sessionId: sessionId.value,
},
customerServicePlugin: 0,
}),
};
hasReply.value = true;
emit('sendMessage', submitData);
}
};
return {
props,
hasReply,
sessionId,
selectValue,
hoverValue,
hasExpire,
desc,
numberList,
setValue,
setHoverValue,
submitRatingStar,
};
},
};
</script>
<style lang="scss" scoped>
.rating-head {
font-size: 14px;
font-weight: 400;
color: #999;
}
.rating-tail {
font-size: 14px;
font-weight: 400;
color: #999;
}
.card-title {
font-size: 14px;
font-weight: 500;
}
.rating-card {
min-width: 270px;
width: 50%;
background: #fbfbfb;
border-radius: 20px;
border: 0;
margin-top: 10px;
padding-top: 20px;
padding-bottom: 20px;
button:disabled {
background: #d8d8d8;
}
}
.message-rating-star {
text-align: center;
display: flex;
flex-flow: column wrap;
justify-content: center;
padding-bottom: 30px;
align-items: center;
}
.card-wrapper {
display: flex;
flex-wrap: wrap;
justify-content: center;
padding-top: 10px;
}
.submit-button {
width: 50%;
height: 50px;
background-color: #0365f9;
font-size: 18px;
font-weight: 400;
color: white;
border: 0;
border-radius: 8px;
cursor: pointer;
}
.de-active {
height: 34px;
width: 34px;
display: inline-block;
border: 0 solid #006eff0d;
border-radius: 5px;
color: #006eff;
font-weight: 400;
font-size: 16px;
text-align: center;
line-height: 34px;
background: #006eff0d;
}
.active {
width: 34px;
height: 34px;
display: inline-block;
background: linear-gradient(
136.96deg,
rgba(10, 124, 255, 0.3) -39.64%,
#0a7cff 131.39%
);
border-radius: 5px;
color: white;
font-weight: 400;
font-size: 16px;
border: 0 solid #0a7cff;
text-align: center;
line-height: 34px;
}
</style>