You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
1120 lines
32 KiB
1120 lines
32 KiB
<template> |
|
<view class="detail"> |
|
<scroll-view @scroll="handleScroll" scroll-y="true" :scroll-top="scrollTop" :style="{ |
|
height: isExpanded ? 'calc(100% - 1rpx)' : 'calc(100% - 1rpx)', |
|
}" class="chatlist" :class="{ 'chatlist-wrapper-expanded': isExpanded }" id="scrollView" ref="scrollView" |
|
@click="clickContent"> |
|
<view v-if="!msgList.length" class="helloContent"> |
|
<image :src="$.imgSrc + '/left_user.png'" class="imgLeft" /> |
|
<view class="titleBox"> |
|
<view class="titleOne"> 您好,我是海信通途大模型 </view> |
|
<view class="titleTwo"> |
|
作为你的智能伙伴,我可以为你提供交通领域知识的答疑解惑。 |
|
</view> |
|
<view class="text"> 你可以这样问我: </view> |
|
<view class="tipQuestions"> |
|
<view class="" v-for="(item, index) in tipQuestions" :key="index"> |
|
<view class="tipItem" @click="handleBtn(item.text)"> |
|
<view class="title"> |
|
{{ item.title }} |
|
</view> |
|
<view class="text"> |
|
{{ item.text }} |
|
</view> |
|
</view> |
|
</view> |
|
</view> |
|
</view> |
|
</view> |
|
<view :class="['bar', item.answerId == '0' ? 'currAnswer' : '']" v-for="item in msgList" :key="item.id"> |
|
<!--<image :src="item.answerId == '0' ? $.imgSrc + '/self.png' : $.imgSrc + '/left_user.png'" class="img" />--> |
|
<image :src=" |
|
item.answerId == '0' |
|
? 'data:image/jpeg;base64,iVBORw0KGgoAAAANSUhEUgAAACYAAAAmCAYAAACoPemuAAAAGXRFWHRTb2Z0d2FyZQBBZG9iZSBJbWFnZVJlYWR5ccllPAAAAyZpVFh0WE1MOmNvbS5hZG9iZS54bXAAAAAAADw/eHBhY2tldCBiZWdpbj0i77u/IiBpZD0iVzVNME1wQ2VoaUh6cmVTek5UY3prYzlkIj8+IDx4OnhtcG1ldGEgeG1sbnM6eD0iYWRvYmU6bnM6bWV0YS8iIHg6eG1wdGs9IkFkb2JlIFhNUCBDb3JlIDUuNi1jMDY3IDc5LjE1Nzc0NywgMjAxNS8wMy8zMC0yMzo0MDo0MiAgICAgICAgIj4gPHJkZjpSREYgeG1sbnM6cmRmPSJodHRwOi8vd3d3LnczLm9yZy8xOTk5LzAyLzIyLXJkZi1zeW50YXgtbnMjIj4gPHJkZjpEZXNjcmlwdGlvbiByZGY6YWJvdXQ9IiIgeG1sbnM6eG1wPSJodHRwOi8vbnMuYWRvYmUuY29tL3hhcC8xLjAvIiB4bWxuczp4bXBNTT0iaHR0cDovL25zLmFkb2JlLmNvbS94YXAvMS4wL21tLyIgeG1sbnM6c3RSZWY9Imh0dHA6Ly9ucy5hZG9iZS5jb20veGFwLzEuMC9zVHlwZS9SZXNvdXJjZVJlZiMiIHhtcDpDcmVhdG9yVG9vbD0iQWRvYmUgUGhvdG9zaG9wIENDIDIwMTUgKFdpbmRvd3MpIiB4bXBNTTpJbnN0YW5jZUlEPSJ4bXAuaWlkOkYwQjdBNUI1OTNGMzExRTk5OEMyRUJEREM0NTA0NzFEIiB4bXBNTTpEb2N1bWVudElEPSJ4bXAuZGlkOkYwQjdBNUI2OTNGMzExRTk5OEMyRUJEREM0NTA0NzFEIj4gPHhtcE1NOkRlcml2ZWRGcm9tIHN0UmVmOmluc3RhbmNlSUQ9InhtcC5paWQ6RjBCN0E1QjM5M0YzMTFFOTk4QzJFQkREQzQ1MDQ3MUQiIHN0UmVmOmRvY3VtZW50SUQ9InhtcC5kaWQ6RjBCN0E1QjQ5M0YzMTFFOTk4QzJFQkREQzQ1MDQ3MUQiLz4gPC9yZGY6RGVzY3JpcHRpb24+IDwvcmRmOlJERj4gPC94OnhtcG1ldGE+IDw/eHBhY2tldCBlbmQ9InIiPz6ceP8WAAAFRUlEQVR42sxYa0xbVRzvvb29bS9taQvtYBQ63kxhsBlw6mbwQZyabE4H6geTZfOR+MFPiyZO4jRxiYl+UOOXOdTERxyLcxs+trkFxbGxwZgb22CAPDoKpQ8ofVFa7q3/g7ekK33ce9st/pNfbnLPOf/zyzn/839hoVBIJEBKAHWAdYACQA5Azo7NAywAE+Aq4CJgmO8GGA9iFGA7YBugiOc+I4BjgJ8AvnQREwOaAC8DMkWpyRzgIKAVQKdCDF3TB4C1ovRKP2Ave90xBU+weDPgmztASsTq/JbdgxexJwEfATJEd04odo+nuF7lw+wCXHR3hAHsAXQkImZkr4/iorHvHxv13cl+fdf1KbXPHxSH/5OEmKkqznY3PV5urV9f4MKwpKrQS30JMB6LGFL8dTKbYpiQ6LeuUfWP7YP6ayN25ZI9YFho59OV5qK8TL911idpaevL884HCTSWp1P4n60vs+54pMwhlxJMkgexM/xaI6+riYuh/3B6IPu9lnPFYVLLRvlA4WzXtSnV5mqDi4ogYLZ5ZJ8d7i34+PvuPA4P4vlo46dYP5VU6u7JdeMx7iZHmxEkJWIGkZKRxAofdV9FjpuD+t1hMwoT287VeZYY1AsNdUbbbdcbCmG79p8oz9crF97/6rzxltUtjxwvK9B4tmwsdHJQn8lyWbaxVj5hxulZEL/24akytBQdXiBIwyH+d4oSAmdoOoRRMoImxHgI4fXnasw1pXofR/UofDUhAy3lG/vUCikNRi4FAxcnm4sehlYlW+ShHnEpRcRqhTifrZuKrRaHj7wxZlcgktHuEMgHy41ar05NBQpWqQI81dciYpVCiP15eUJjc/rI0nyNt7Io24PjWAg9CoZl6JjzS64M2ZRZmbKgAPVViFihEGKrwT9N2j2yG6MOJSDuvNxshVuA+jXoVeqFENt4b64rnfOiRI9zDT/RAt7ckSGXJMypYHwRzRMS4AUHaoVcwry6rXoi0RwYN6N5QvTjXFPdWPJiQ4UdQpEtZt4E/9G4QNU+RMyaSs7y7q4HTcg1RLsK9D8FtVZEbCwVYl5Id7Co2IlcBgpTKagdQ+6iD9DAZ5VnPoh3XjWregYsio7LE9rP9zw2+PeQjfqk9ZIR2d0T969xvtD889oN5XoXBG/PQ+vyXDxtrQ8R6+Y62zbrIz493Lu6vfdWFoqP4f+nLoyraTihhQCNO91+4gTka6ZplxzhaMfwKikpZurX5zveaNwwqdNQXMJTN1I+xAbOhHK6ezyz8Z22ypMXxnSRpJYMwumT7KgvtZcYNN5N1YY564yPjBxHhNG6pua2yjM948myGMRlKLzB8UQz4dqUzQfOFkemz5HSUGt0nr8+pRyemM34/eKYZvfWKgsKUSvsEYJ+84HO4nN9k4oE2x2PzMeOsMVoTIHrM9BMfGM+9tdwloJ1tih9bj1zM5uJM3+RZjDIaA1xVLlYLsvEkC9ribexFDLTRCd69opZq5CTS8SMOSr/L50juoR1Q/wXezDsV4mIn4fYenJF3v/l3i2DR/4Y0rZfMmkGTDMZ4UIj8hR6+i1KJUUuznkWCMuMVxqtA9JtBrJf7+Yag7Px0fJYjvcmy0F4+TZl90igyCCnoSKanvGSyLgpmYSGrJVBX5PFJSMIPAS5WDBHSwUgEwkYdMoA2J2g8u1/VfDG2hxN2McuuBuk9kWTStS7+BXwZioBnkugBrzF7iWoDbUfUJFmUgOAtxO1ofg07l4BqFIkhPzUF+lo3N2WGwKeYVudfOuEUbbVeRTlAOnuwSZrDlMRtpNyc/hfAQYAFFwdv9Iba+4AAAAASUVORK5CYII=' |
|
: $.imgSrc + '/left_user.png' |
|
" class="img" /> |
|
<view class="content"> |
|
<zeroMarkdownView :markdown="item.data" /> |
|
<!-- <ua-markdown :source="mdvalue" /> --> |
|
<view class="icon" v-show="item.answerId != '0' && item.isOver && item.isSuccess"> |
|
<uni-icons |
|
:type="item.iconsType == '' ? 'hand-up' : (item.iconsType == 'handUp' ? 'hand-up-filled' : 'hand-up')" |
|
:color="item.iconsType == 'handUp' ? '#FFD131' : ''" |
|
size="22" |
|
@click="clickIcon('handUp', item.qaId)"> |
|
</uni-icons> |
|
<uni-icons |
|
:type="item.iconsType == '' ? 'hand-down' : (item.iconsType == 'handDown' ? 'hand-down-filled' : 'hand-down')" |
|
size="22" |
|
@click="clickIcon('handDown', item.qaId)"> |
|
</uni-icons> |
|
</view> |
|
</view> |
|
</view> |
|
<view class="loading-animation" v-if="loading"> |
|
<view class="bounce-dot"></view> |
|
<view class="bounce-dot"></view> |
|
<view class="bounce-dot"></view> |
|
</view> |
|
</scroll-view> |
|
<view class="con" :class="{ 'con-wrapper-expanded': isExpanded }"></view> |
|
<view class="input-wrapper" :class="{ 'input-wrapper-expanded': isExpanded }"> |
|
<view class="topContent"> |
|
<input class="uni-input" placeholder="请输入内容" :value="inputValue" @confirm="handleSend" |
|
@input="onKeyInput" /> |
|
|
|
<uni-icons class="uni-icon" type="plus" size="30" @click="handlePlus" color='#cccccc'></uni-icons> |
|
</view> |
|
<view v-if="isExpanded" class="expanded"> |
|
<view @click="chooseImage" class="expandedItem"> |
|
<uni-icons class="camera-icon" type="image" size="28"></uni-icons> |
|
<view>照片</view> |
|
</view> |
|
<view class="expandedItem" style="margin-top:6px"> |
|
<image src="../../static/video.png" class="video"></image> |
|
<view style="top:-10rpx;position: relative;">视频</view> |
|
</view> |
|
</view> |
|
|
|
</view> |
|
<!-- <view class="downward" v-if="isToBottom" @click="toBottom"> |
|
<u-icon name="arrow-downward"></u-icon> |
|
</view> --> |
|
</view> |
|
</template> |
|
|
|
<script> |
|
// import AbortController from "abort-controller/dist/abort-controller"; |
|
import TopTitle from "../../components/top-title.vue"; |
|
// import headerNavBar from '../../components/headerNavBar/headerNavBar.vue' |
|
import zeroMarkdownView from "../../components/zeroMarkdownView/zeroMarkdownView.vue"; |
|
// import { |
|
// EventSourcePolyfill |
|
// } from 'event-source-polyfill'; |
|
import $ from "../../common/globalJs/globalJs.js"; |
|
import { |
|
fetchEventSource |
|
} from "@microsoft/fetch-event-source"; |
|
// import { |
|
// baseUrl |
|
// } from '../../utils/config.js'; |
|
let baseUrl = ""; |
|
export default { |
|
components: { |
|
zeroMarkdownView |
|
}, |
|
data() { |
|
return { |
|
$: this.$, |
|
active: 0, |
|
inputValue: "", |
|
es: null, |
|
msgList: [], |
|
loading: false, |
|
streamLoading: true, |
|
scrollTop: 0, |
|
title: "", |
|
isExpanded: false, |
|
sessionId: "", |
|
id: "", |
|
tipQuestions: [{ |
|
title: "标准法规", |
|
text: "一级公路停车视距标准是什么?", |
|
}, |
|
{ |
|
title: "工作指南", |
|
text: "如何开展道路安全隐患排查工作?", |
|
}, |
|
{ |
|
title: "参考案例", |
|
text: "请给我一个典型的视距不良路口案例。", |
|
}, |
|
], |
|
timer: null, |
|
isHandleScroll: true, |
|
startX: 0, // 触摸开始时的X坐标 |
|
startY: 0, // 触摸开始时的Y坐标 |
|
isScrolling: false, // 是否正在滑动 |
|
isToBottom: false, |
|
lastScrollTop: 0, // 记录上一次滚动位置 |
|
temp: 0, |
|
iconsType: '', |
|
}; |
|
}, |
|
onLoad() { |
|
let params = uni.getStorageSync("itemMessage"); |
|
// params = JSON.parse(decodeURIComponent(this.$route.query.params)) |
|
// this.sessionId = params.sessionId |
|
// this.id = '37020017407' |
|
this.sessionId = "37020017407"; |
|
this.id = "37020017407"; |
|
// console.log(params.roadName,"5555"); |
|
let str = ""; |
|
if (params.roadName) { |
|
str += "路段名:" + params.roadName; |
|
this.title = params.roadName + "智能排查"; |
|
} |
|
if (params.id) { |
|
str += ",id:" + params.id; |
|
} |
|
// this.queryChat("开始隐患排查," + str, ); |
|
}, |
|
onUnload() { |
|
if (this.es) { |
|
this.es.close(); |
|
this.es = null; |
|
} |
|
}, |
|
methods: { |
|
async clickIcon(type, qaId) { |
|
console.log(this.msgList) |
|
this.msgList.forEach(item => { |
|
if(item.qaId == qaId) { |
|
if(item.iconsType == '' || !item.hasOwnProperty('iconsType')) { |
|
this.iconsType = type |
|
this.$set(item, 'iconsType', type) |
|
} else { |
|
if(item.iconsType == 'handUp') { |
|
if(type == 'handUp') { |
|
this.iconsType = '' |
|
this.$set(item, 'iconsType', '') |
|
} else { |
|
this.iconsType = 'handDown' |
|
this.$set(item, 'iconsType', 'handDown') |
|
} |
|
} else { |
|
if(type == 'handUp') { |
|
this.iconsType = 'handUp' |
|
this.$set(item, 'iconsType', 'handUp') |
|
} else { |
|
this.iconsType = '' |
|
this.$set(item, 'iconsType', '') |
|
} |
|
} |
|
} |
|
} |
|
}) |
|
|
|
const params = { |
|
qaId, |
|
feedbackStatus : this.iconsType == '' ? 0 : (this.iconsType == 'handUp' ? 1 : 2), |
|
feedbackInfo: '' |
|
} |
|
// this.$request.globalRequest('/hitap/feadBack', params, 'POST').then(res => { |
|
|
|
// }) |
|
const [err, res] = await uni.request({ |
|
url: this.$.chatUrl + "/feadBack", |
|
dataType: "json", |
|
method: "POST", |
|
headers: { |
|
"content-type": "application/json", |
|
}, |
|
data: params |
|
}) |
|
this.$.toast(res.data.result); |
|
// uni.showToast({ |
|
// title: res.data.result, |
|
// // icon: 'success', |
|
// duration: 2000 |
|
// }); |
|
}, |
|
handleTouchStart(e) { |
|
// 获取触摸开始时的坐标 |
|
this.startX = e.touches[0].clientX; |
|
this.startY = e.touches[0].clientY; |
|
// this.isScrolling = false; // 重置滑动状态 |
|
}, |
|
handleTouchMove(e) { |
|
// 获取触摸移动时的坐标 |
|
let moveX = e.touches[0].clientX; |
|
let moveY = e.touches[0].clientY; |
|
|
|
// 计算坐标变化量 |
|
let deltaX = moveX - this.startX; |
|
let deltaY = moveY - this.startY; |
|
|
|
// 判断是否发生了足够的滑动(这里以5px为例) |
|
if (Math.abs(deltaX) > 5 || Math.abs(deltaY) > 5) { |
|
// this.isScrolling = true; // 标记为正在滑动 |
|
this.isHandleScroll = false |
|
// 根据deltaY的正负判断滑动方向 |
|
if (deltaY > 0) { |
|
console.log('用户正在向下滑动'); |
|
} else if (deltaY < 0) { |
|
|
|
console.log('用户正在向上滑动'); |
|
} |
|
|
|
// 如果需要,可以在这里更新startX和startY为moveX和moveY,以继续追踪滑动 |
|
// 但在这个简单的示例中,我们不需要这样做 |
|
} |
|
|
|
// 注意:这里不更新startX和startY,因为我们只关心触摸开始到当前位置的相对变化 |
|
}, |
|
handleTouchEnd(e) { |
|
// 触摸结束时的处理 |
|
// 例如,可以重置startX和startY,或者执行其他清理工作 |
|
// 但在这个示例中,我们不做额外处理 |
|
}, |
|
handleScroll(event) { |
|
// event.detail 包含了滚动事件的详细信息 |
|
const scrollTop = event.detail.scrollTop; |
|
if (scrollTop > this.lastScrollTop) { |
|
console.log('向下滑动'); |
|
} else { |
|
this.temp++ |
|
if (this.temp == 2) { |
|
this.isHandleScroll = false |
|
} |
|
|
|
console.log('向上滑动'); |
|
} |
|
this.lastScrollTop = scrollTop; |
|
}, |
|
toBottom() { |
|
this.isToBottom = false |
|
this.scrollTop = Number(this.scrollTop) + 100; |
|
this.isHandleScroll = true |
|
|
|
}, |
|
async queryChat(voiceText) { |
|
// console.log(voiceText,"voiceText"); |
|
clearInterval(this.timer) |
|
this.loading = true; |
|
const [err, res] = await uni.request({ |
|
// url: 'http://10.16.3.159:8777/api/local_doc_qa/local_doc_chat', |
|
url: this.$.chatUrl + "/chat", |
|
dataType: "json", |
|
method: "POST", |
|
// responseType: 'arraybuffer', |
|
headers: { |
|
// 'Accept': 'text/event-stream', |
|
"content-type": "application/json", |
|
}, |
|
data: { |
|
voiceText, |
|
deptId: "3702000000", |
|
id: "37020017407", |
|
multiType: "", |
|
sceneFlag: "", |
|
stream: false, |
|
type: "0", |
|
userId: "admin1", |
|
// "user_id": "zzp", |
|
// "kb_ids": ["KBa80ea15e786241eca70a20f136f4e34c"], |
|
// "question": "隐患排查流程是什么", |
|
// "streaming": true, |
|
// "history": [] |
|
}, |
|
}); |
|
console.log(res); |
|
if (res && res.data && res.data.code == 200) { |
|
// console.log('request success', res.data) |
|
// const { result = {} } = res.data; |
|
// const { data = {} } = result; |
|
// if (data.tabkey - 1 != this.active) { |
|
// this.active = data.tabkey - 1 > 0 ? data.tabkey - 1 : 0; |
|
// } |
|
if (res.data.result) { |
|
this.changeMsgList("1", res.data.result, res.data.qaId); |
|
} |
|
this.loading = false; |
|
} else { |
|
if (err) { |
|
console.log("request fail", err.errMsg); |
|
} |
|
this.loading = false |
|
this.changeMsgList("1", "查询失败,请联系管理员或稍后重试!"); |
|
uni.showToast({ |
|
title: "查询失败", |
|
icon: "error", |
|
duration: 12000, |
|
}); |
|
} |
|
}, |
|
// 快捷回复 |
|
handleBtn(text) { |
|
this.handleSend(text); |
|
}, |
|
// 输入框 |
|
onKeyInput(event) { |
|
this.inputValue = event.detail.value; |
|
}, |
|
// 发送 |
|
handleSend(text) { |
|
if (!this.inputValue & !text) { |
|
uni.showToast({ |
|
title: "请输入内容", |
|
icon: "closeempty", |
|
duration: 2000, |
|
}); |
|
} |
|
this.temp = 0 |
|
this.isHandleScroll = true |
|
this.changeMsgList("0", this.inputValue || text); |
|
this.queryChat(this.inputValue || text); |
|
this.inputValue = ""; |
|
}, |
|
// 更新列表信息 |
|
changeMsgList(answerId, data, qaId) { |
|
data = data.replace("undefined", '') |
|
data = data.replace("null", '') |
|
let id = 1; |
|
if (this.msgList.length > 0) { |
|
id = this.msgList[this.msgList.length - 1].id + 1; |
|
} |
|
if (answerId == "1") { |
|
// 后台返回来的消息 |
|
let newdata = ""; |
|
let index = 0; |
|
this.timer = setInterval(() => { |
|
newdata = newdata += data[index]; |
|
if (this.msgList?.filter((item) => item.id == id).length == 0) { |
|
this.msgList = [ |
|
...this.msgList, |
|
{ |
|
id, |
|
answerId, |
|
qaId, |
|
data: newdata, |
|
isSuccess: true, |
|
}, |
|
]; |
|
} else { |
|
this.msgList[this.msgList.length - 1].data = newdata; |
|
} |
|
index += 1; |
|
this.$nextTick(() => { |
|
// const height = |
|
// this.$refs.scrollView && |
|
// this.$refs.scrollView.$refs && |
|
// this.$refs.scrollView.$refs.content |
|
// ? this.$refs.scrollView.$refs.content.scrollHeight |
|
// : 0; |
|
if (this.isHandleScroll) { |
|
this.scrollTop = Number(this.scrollTop) + 100; |
|
} |
|
|
|
}); |
|
if (newdata == data) { |
|
clearInterval(this.timer); |
|
this.msgList[this.msgList.length - 1].isOver = true |
|
} |
|
}, 50); |
|
} else { |
|
this.msgList = [ |
|
...this.msgList, |
|
{ |
|
id, |
|
answerId, |
|
data, |
|
}, |
|
]; |
|
this.$nextTick(() => { |
|
// const height = |
|
// this.$refs.scrollView && |
|
// this.$refs.scrollView.$refs && |
|
// this.$refs.scrollView.$refs.content |
|
// ? this.$refs.scrollView.$refs.content.scrollHeight |
|
// : 0; |
|
if (this.isHandleScroll) { |
|
this.scrollTop = Number(this.scrollTop) + 100; |
|
} |
|
}); |
|
} |
|
|
|
}, |
|
handlePlus() { |
|
this.$.toast("此功能暂不开放"); |
|
|
|
// this.isExpanded = !this.isExpanded; |
|
}, |
|
clickContent() { |
|
if (this.isExpanded) { |
|
this.isExpanded = !this.isExpanded; |
|
} |
|
}, |
|
goToKnowledge() { |
|
uni.navigateTo({ |
|
url: `/pages/home/detail?params=${encodeURIComponent( |
|
JSON.stringify(item) |
|
)}`, |
|
}); |
|
}, |
|
|
|
// 选择图片 |
|
chooseImage() { |
|
uni.chooseImage({ |
|
count: 6, //默认9 |
|
sizeType: ["original", "compressed"], //可以指定是原图还是压缩图,默认二者都有 |
|
sourceType: ["album"], //从相册选择 |
|
success: async (res) => { |
|
console.log(res); |
|
if (res.tempFilePaths && res.tempFilePaths.length) { |
|
let str = ""; |
|
let jsonArr = []; |
|
for (let i = 0; i < res.tempFilePaths.length; i++) { |
|
const result = await this.uploadFilePromise(res.tempFilePaths[i]); |
|
let json = JSON.parse(result); |
|
str += ``; |
|
jsonArr.push(json.result); |
|
} |
|
|
|
console.log(str); |
|
if (this.id == 12121212) { |
|
this.changeMsgList("0", str); |
|
this.queryChat(jsonArr); |
|
} else { |
|
// this.addQuestion(str, "0"); |
|
// this.SSE(jsonArr, "0"); |
|
this.changeMsgList("0", str); |
|
let j = jsonArr.join(',') |
|
this.queryChat(j); |
|
} |
|
} |
|
}, |
|
}); |
|
}, |
|
uploadFilePromise(url) { |
|
return new Promise((resolve, reject) => { |
|
let a = uni.uploadFile({ |
|
url: this.$.baseUrl + "/hiddenDanger/ftp/uploadFileToFtp", // 仅为示例,非真实的接口地址 |
|
filePath: url, |
|
name: "file", |
|
success: (res) => { |
|
resolve(res.data); |
|
}, |
|
}); |
|
}); |
|
}, |
|
}, |
|
// methods: { |
|
// // 建立SSE长连接 |
|
// SSE(voiceText, answerId) { |
|
// const ctrl = new AbortController(); |
|
// console.log(ctrl.signal); |
|
// fetchEventSource($.chatUrl + "/chat", { |
|
// method: "POST", |
|
// headers: { |
|
// "Content-Type": "application/json", |
|
// Accept: ["text/event-stream", "application/json"], |
|
// }, |
|
// body: JSON.stringify({ |
|
// voiceText, |
|
// deptId: "3702000000", |
|
// id: "37020017407", |
|
// multiType: "", |
|
// sceneFlag: "", |
|
// stream: true, |
|
// type: "0", |
|
// userId: "admin1", |
|
// }), |
|
// signal: ctrl.signal, |
|
// openWhenHidden: true, |
|
// onopen: () => {}, |
|
// onmessage: (ev) => { |
|
// console.log(ev); |
|
// this.loading = true; |
|
// const res = JSON.parse(ev.data); |
|
// if (res?.code == 200 && res.result) { |
|
// console.log(res.result.data.tabkey); |
|
// console.log(res.result.data); |
|
// this.tabkey = res.result.data.tabkey; |
|
// if (this.tabkey - 1 != this.active) { |
|
// this.active = this.tabkey - 1 > 0 ? this.tabkey - 1 : 0; |
|
// } |
|
// if (this.msgList.length == 0) { |
|
// this.msgList = [ |
|
// { |
|
// answerId, |
|
// data: res.result.data.content, |
|
// }, |
|
// ]; |
|
// } else { |
|
// // debugger |
|
// //回答 |
|
// if (this.msgList[this.msgList.length - 1].answerId == "1") { |
|
// //最后一个是回答 |
|
// this.msgList[this.msgList.length - 1].data += |
|
// res.result.data.content; |
|
// } else { |
|
// //最后一个是问题 |
|
// this.msgList = [ |
|
// ...this.msgList, |
|
// { |
|
// answerId: "1", |
|
// data: res.result.data.content, |
|
// }, |
|
// ]; |
|
// } |
|
// } |
|
|
|
// // debugger |
|
|
|
// this.scrollBottom(); |
|
// } |
|
// }, |
|
// onclose: () => { |
|
// console.log(1111); |
|
// this.loading = false; |
|
|
|
// if (this.isExpanded) { |
|
// this.isExpanded = !this.isExpanded; |
|
// } |
|
// }, |
|
// onerror(error) { |
|
// console.log("error", error); |
|
// throw error; |
|
// }, |
|
// }); |
|
// }, |
|
|
|
// async queryChat(voiceText) { |
|
|
|
// // console.log(voiceText,"voiceText"); |
|
// this.loading = true; |
|
// const [err, res] = await uni.request({ |
|
// // url: 'http://10.16.3.159:8777/api/local_doc_qa/local_doc_chat', |
|
// url: $.chatUrl + "/chat", |
|
// dataType: "json", |
|
// method: "POST", |
|
// // responseType: 'arraybuffer', |
|
// headers: { |
|
// // 'Accept': 'text/event-stream', |
|
// "content-type": "application/json", |
|
// }, |
|
// data: { |
|
// voiceText, |
|
// sceneFlag: "", |
|
// sessionId: this.sessionId, |
|
// id: this.id, |
|
// multiType: "", |
|
// userId: "admin1", |
|
// deptId: "3702000000", |
|
// type: '0', |
|
// stream: false, |
|
// // "user_id": "zzp", |
|
// // "kb_ids": ["KBa80ea15e786241eca70a20f136f4e34c"], |
|
// // "question": "隐患排查流程是什么", |
|
// // "streaming": true, |
|
// // "history": [] |
|
// }, |
|
// }); |
|
// if (res && res.data && res.data.code == 200) { |
|
// // console.log('request success', res.data) |
|
// const { result = {} } = res.data; |
|
// const { data = {} } = result; |
|
// if (data.tabkey - 1 != this.active) { |
|
// this.active = data.tabkey - 1 > 0 ? data.tabkey - 1 : 0; |
|
// } |
|
// if (data.content) { |
|
// this.changeMsgList( |
|
// data.answerId || "1", |
|
// data.content, |
|
// data.answerOptions |
|
// ); |
|
// } |
|
// this.loading = false; |
|
// if (this.isExpanded) { |
|
// this.isExpanded = !this.isExpanded; |
|
// } |
|
// } else { |
|
// if (err) { |
|
// console.log("request fail", err.errMsg); |
|
// } |
|
// uni.showToast({ |
|
// title: "查询失败", |
|
// icon: "error", |
|
// duration: 2000, |
|
// }); |
|
// } |
|
// }, |
|
// // 输入框 |
|
// onKeyInput(event) { |
|
// this.inputValue = event.detail.value; |
|
// }, |
|
// addQuestion(q, answerId) { |
|
// const newQuestion = { |
|
// answerId, |
|
// data: q, |
|
// }; |
|
// this.msgList.push(newQuestion); // 将问题添加到消息列表 |
|
// // this.$store.commit('setMSg_List', this.msgList); |
|
// this.scrollBottom(); |
|
// }, |
|
// scrollBottom() { |
|
// this.$nextTick(() => { |
|
// // const height = |
|
// // this.$refs.scrollView && |
|
// // this.$refs.scrollView.$refs && |
|
// // this.$refs.scrollView.$refs.content |
|
// // ? this.$refs.scrollView.$refs.content.scrollHeight |
|
// // : 0; |
|
// this.scrollTop = this.scrollTop + 1; |
|
// }); |
|
// }, |
|
// // 发送 |
|
// handleSend(text) { |
|
// if (!this.inputValue & !text) { |
|
// uni.showToast({ |
|
// title: "请输入内容", |
|
// icon: "closeempty", |
|
// duration: 2000, |
|
// }); |
|
// } |
|
// if (text || this.inputValue) { |
|
// // if (this.params.id == 12121212) { |
|
// this.changeMsgList("0", this.inputValue || text); |
|
// this.queryChat(this.inputValue || text); |
|
// this.scrollBottom(); |
|
// // } else { |
|
// // this.addQuestion(this.inputValue || text, "0"); |
|
// // this.SSE(this.inputValue || text, "0"); |
|
// // } |
|
// this.inputValue = ""; |
|
// } |
|
// }, |
|
// // 更新列表信息 |
|
// changeMsgList(answerId, data, answerOptions) { |
|
// let id = 1; |
|
// if (this.msgList.length > 0) { |
|
// id = this.msgList[this.msgList.length - 1].id + 1; |
|
// } |
|
// if (answerId == "1") { |
|
// // 后台返回来的消息 |
|
// let newdata = ""; |
|
// let index = 0; |
|
// const timer = setInterval(() => { |
|
// newdata = newdata += data[index]; |
|
// if (this.msgList?.filter((item) => item.id == id).length == 0) { |
|
// this.msgList = [ |
|
// ...this.msgList, |
|
// { |
|
// id, |
|
// answerId, |
|
// data: newdata, |
|
// // options: answerOptions // ['东南西北','东北','东南北','东南西北'] answerOptions |
|
// }, |
|
// ]; |
|
// } else { |
|
// this.msgList[this.msgList.length - 1].data = newdata; |
|
// } |
|
// index += 1; |
|
// this.scrollBottom(); |
|
// if (newdata == data) { |
|
// this.msgList[this.msgList.length - 1].options = answerOptions; |
|
// clearInterval(timer); |
|
// } |
|
// }, 50); |
|
// } else { |
|
// this.msgList = [ |
|
// ...this.msgList, |
|
// { |
|
// id, |
|
// answerId, |
|
// data, |
|
// }, |
|
// ]; |
|
// this.scrollBottom(); |
|
// } |
|
// }, |
|
|
|
// handlePlus() { |
|
// this.isExpanded = !this.isExpanded; |
|
// }, |
|
// // 快捷回复 |
|
// handleBtn(text) { |
|
// this.handleSend(text); |
|
// }, |
|
// clickContent() { |
|
// if (this.isExpanded) { |
|
// this.isExpanded = !this.isExpanded; |
|
// } |
|
// }, |
|
// goToKnowledge() { |
|
// uni.navigateTo({ |
|
// url: "/pages/home/knowledge", |
|
// // url: `/pages/home/knowledge?params=${encodeURIComponent(JSON.stringify(this.$route.query.params))}` |
|
// }); |
|
// }, |
|
// // 选择图片 |
|
// chooseImage() { |
|
// uni.chooseImage({ |
|
// count: 6, //默认9 |
|
// sizeType: ["original", "compressed"], //可以指定是原图还是压缩图,默认二者都有 |
|
// sourceType: ["album"], //从相册选择 |
|
// success: async (res) => { |
|
// console.log(res) |
|
// if (res.tempFilePaths && res.tempFilePaths.length) { |
|
// let str = ""; |
|
// let jsonArr = [] |
|
// for (let i = 0; i < res.tempFilePaths.length; i++) { |
|
// const result = await this.uploadFilePromise(res.tempFilePaths[i]); |
|
// let json = JSON.parse(result) |
|
// str += ``; |
|
// jsonArr.push(json.result) |
|
// } |
|
|
|
// console.log(str) |
|
// if (this.id == 12121212) { |
|
// this.changeMsgList("0", str); |
|
// this.queryChat(jsonArr); |
|
// } else { |
|
// // this.addQuestion(str, "0"); |
|
// // this.SSE(jsonArr, "0"); |
|
// this.changeMsgList("0", str); |
|
// this.queryChat(jsonArr); |
|
// } |
|
// } |
|
// }, |
|
// }); |
|
// }, |
|
// uploadFilePromise(url) { |
|
// return new Promise((resolve, reject) => { |
|
// let a = uni.uploadFile({ |
|
// url: this.$.baseUrl + '/hiddenDanger/ftp/uploadFileToFtp', // 仅为示例,非真实的接口地址 |
|
// filePath: url, |
|
// name: 'file', |
|
// success: (res) => { |
|
// resolve(res.data) |
|
// } |
|
// }); |
|
// }) |
|
// }, |
|
// }, |
|
}; |
|
</script> |
|
|
|
<style scoped lang="scss"> |
|
.detail { |
|
width: 100%; |
|
margin: auto; |
|
// height: 100vh; |
|
// height: calc(100vh - 12px); |
|
overflow: hidden; |
|
|
|
.knowledge { |
|
width: 40rpx; |
|
height: 40rpx; |
|
} |
|
|
|
.helloContent { |
|
display: flex; |
|
|
|
.imgLeft { |
|
width: 80rpx; |
|
height: 80rpx; |
|
margin-top: 15rpx; |
|
} |
|
|
|
.titleBox { |
|
display: inline-block; |
|
max-width: 80%; |
|
border: 1px solid #ddd; |
|
border-radius: 5px; |
|
padding: 0; |
|
margin: 15rpx 0rpx 0 20rpx; |
|
// flex: 1; |
|
overflow: hidden; |
|
background-color: #ffffff; |
|
padding: 15rpx; |
|
|
|
.titleOne { |
|
font-weight: 700; |
|
font-size: 32rpx; |
|
} |
|
|
|
.titleTwo { |
|
margin: 15rpx 0; |
|
font-size: 28rpx; |
|
} |
|
|
|
.tipItem { |
|
background-color: #e1f8f8; |
|
margin: 15rpx; |
|
padding: 15rpx; |
|
|
|
.title { |
|
font-size: 32rpx; |
|
font-weight: 700; |
|
} |
|
|
|
.text { |
|
font-size: 28rpx; |
|
} |
|
} |
|
} |
|
|
|
.text { |
|
font-size: 32rpx; |
|
} |
|
} |
|
|
|
.stepBox { |
|
width: 100%; |
|
height: 150rpx; |
|
display: flex; |
|
justify-content: center; |
|
align-items: center; |
|
background-color: #ffffff; |
|
|
|
.step { |
|
display: flex; |
|
|
|
.stepItem { |
|
display: flex; |
|
flex-direction: column; |
|
align-items: center; |
|
} |
|
|
|
.circles { |
|
display: flex; |
|
// justify-content: space-between; |
|
padding: 22px 0; |
|
|
|
.circle { |
|
width: 4rpx; |
|
height: 4rpx; |
|
border-radius: 50%; |
|
background-color: #e9edf5; |
|
margin: 0 1px; |
|
} |
|
|
|
.circleActive { |
|
width: 4rpx; |
|
height: 4rpx; |
|
border-radius: 50%; |
|
background-color: #ccc; |
|
margin: 0 1px; |
|
} |
|
} |
|
|
|
.stepCircle { |
|
width: 60rpx; |
|
height: 60rpx; |
|
line-height: 60rpx; |
|
border-radius: 50%; |
|
background-color: #e9edf5; |
|
color: #a0abbd; |
|
text-align: center; |
|
margin-bottom: 10rpx; |
|
} |
|
|
|
.stepCircleActive { |
|
width: 50rpx; |
|
height: 50rpx; |
|
line-height: 50rpx; |
|
border-radius: 50%; |
|
background-color: #295cbc; |
|
color: #ffffff; |
|
text-align: center; |
|
margin-bottom: 4rpx; |
|
border: 5px solid #c6d8fc; |
|
} |
|
|
|
.stepText { |
|
font-size: 16px; |
|
color: #bcc3cd; |
|
} |
|
} |
|
} |
|
|
|
.chatlist { |
|
width: 96%; |
|
margin: auto; |
|
height: calc(100vh - 1px) !important; |
|
/* #ifdef H5 */ |
|
height: calc(100vh - 100px) !important; |
|
/*#endif*/ |
|
// background-color: #f0f2f7; |
|
// padding-bottom: 110rpx; |
|
|
|
.bar { |
|
width: 100%; |
|
display: flex; |
|
margin-bottom: 40rpx; |
|
overflow: hidden; |
|
|
|
.img { |
|
width: 80rpx; |
|
height: 80rpx; |
|
margin-top: 15rpx; |
|
} |
|
|
|
.content { |
|
display: inline-block; |
|
max-width: 80%; |
|
border: 1px solid #ddd; |
|
border-radius: 5px; |
|
padding: 0; |
|
margin: 15rpx 20rpx 0 20rpx; |
|
// flex: 1; |
|
overflow: hidden; |
|
background-color: #ffffff; |
|
|
|
._img { |
|
max-width: 80%; |
|
} |
|
} |
|
|
|
&.currAnswer { |
|
flex-direction: row-reverse; |
|
|
|
.content { |
|
background-color: #cce0ff; |
|
} |
|
} |
|
} |
|
} |
|
|
|
.chatlist-wrapper-expanded { |
|
// padding-bottom: 230rpx; |
|
} |
|
|
|
.input-wrapper { |
|
display: flex; |
|
position: fixed; |
|
bottom: 0; |
|
z-index: 10; |
|
width: 100%; |
|
margin: 20rpx auto 0 auto; |
|
// height: 80rpx; |
|
flex-direction: column; |
|
background-color: #ffffff; |
|
box-sizing: border-box; |
|
border-top: 1px solid #e2e4e9; |
|
bottom: 1px solid #e2e4e9; |
|
padding: 20rpx 20rpx 20rpx 20rpx; |
|
|
|
.topContent { |
|
display: flex; |
|
width: 100%; |
|
} |
|
|
|
.expanded { |
|
background-color: #f5f7fa; |
|
display: flex; |
|
margin-top: 10rpx; |
|
|
|
.expandedItem { |
|
width: 106rpx; |
|
height: 106rpx; |
|
display: flex; |
|
flex-direction: column; |
|
align-items: center; |
|
justify-content: space-between; |
|
|
|
.camera-icon { |
|
margin-top: 5px; |
|
} |
|
} |
|
|
|
.video { |
|
width: 56rpx; |
|
height: 56rpx; |
|
} |
|
} |
|
} |
|
|
|
.input-wrapper-expanded { |
|
// height: 200rpx; |
|
} |
|
|
|
.uni-input { |
|
height: 56rpx; |
|
line-height: 56rpx; |
|
font-size: 30rpx; |
|
padding: 0rpx 10rpx; |
|
flex: 1; |
|
background-color: #fff; |
|
} |
|
|
|
.uni-icon { |
|
font-family: uniicons; |
|
font-size: 48rpx; |
|
font-weight: normal; |
|
font-style: normal; |
|
width: 48rpx; |
|
height: 48rpx; |
|
line-height: 48rpx; |
|
color: #999999; |
|
margin: 0 10rpx; |
|
} |
|
|
|
.loading-animation { |
|
display: flex; |
|
justify-content: center; |
|
margin-top: 0; |
|
|
|
.bounce-dot { |
|
width: 20rpx; |
|
height: 20rpx; |
|
margin: 10rpx; |
|
background-color: #666; |
|
border-radius: 50%; |
|
animation: bounce 1.4s infinite both; |
|
|
|
&:nth-child(2) { |
|
animation-delay: 0.2s; |
|
} |
|
|
|
&:nth-child(3) { |
|
animation-delay: 0.4s; |
|
} |
|
} |
|
} |
|
} |
|
|
|
|
|
.con { |
|
width: 600rpx; |
|
height: 100rpx; |
|
} |
|
|
|
.con-wrapper-expanded { |
|
width: 600rpx; |
|
height: 230rpx; |
|
} |
|
|
|
@keyframes bounce { |
|
|
|
0%, |
|
80%, |
|
100% { |
|
transform: scale(0); |
|
} |
|
|
|
40% { |
|
transform: scale(1); |
|
} |
|
} |
|
|
|
.downward { |
|
position: fixed; |
|
z-index: 100rpx; |
|
right: 20rpx; |
|
bottom: 150rpx; |
|
background: #ffffff; |
|
border: #cccccc solid 1px; |
|
width: 60rpx; |
|
height: 60rpx; |
|
border-radius: 50%; |
|
display: flex; |
|
justify-content: center; |
|
align-items: center; |
|
|
|
/deep/ .u-icon__icon { |
|
font-size: 30rpx !important; |
|
color: #999999 !important; |
|
} |
|
} |
|
.icon{ |
|
display: flex; |
|
justify-content: flex-end; |
|
margin: 0 15rpx 15rpx 12rpx; |
|
.uni-icons{ |
|
margin-left: 15rpx; |
|
} |
|
} |
|
</style>
|
|
|