新增pdf预览
This commit is contained in:
@@ -0,0 +1,108 @@
|
||||
<template>
|
||||
<view class="popup-view" v-if="modelValue">
|
||||
<view class="close-preview" @click="emit('update:modelValue', false)" >X</view>
|
||||
<view class="popup-view-preview" v-if="showView">
|
||||
<web-view :src="showUrl" :fullscreen="true" class="web-view-class" :webview-styles="{
|
||||
width: '100%',
|
||||
height: '100%'
|
||||
}"></web-view>
|
||||
</view>
|
||||
</view>
|
||||
<view v-else></view>
|
||||
</template>
|
||||
|
||||
<script setup>
|
||||
import {
|
||||
ref,
|
||||
onMounted,
|
||||
computed,
|
||||
defineProps,
|
||||
watch
|
||||
} from 'vue'
|
||||
import {
|
||||
getToken
|
||||
} from "@/common/common.js"
|
||||
import {
|
||||
downloadFile
|
||||
} from "@/api/common.js"
|
||||
import {
|
||||
get_base_url
|
||||
} from '@/api/request.js'
|
||||
const emit = defineEmits(['update:modelValue'])
|
||||
const props = defineProps({
|
||||
modelValue: {
|
||||
type: Boolean,
|
||||
default: false
|
||||
},
|
||||
fileId: {
|
||||
default: '',
|
||||
type: String
|
||||
},
|
||||
fileName: {
|
||||
default: '',
|
||||
type: String
|
||||
}
|
||||
})
|
||||
watch(()=>props.modelValue,(val)=>{
|
||||
if(val){
|
||||
openPdfFn()
|
||||
}else{
|
||||
showView.value = false
|
||||
}
|
||||
})
|
||||
const base_url = get_base_url('/traask/traFilePreview/')
|
||||
const showUrl = ref('')
|
||||
const viewerUrl = ref('/static/pdf-view/web/viewer.html')
|
||||
const showView = ref(false)
|
||||
const openPdfFn = (data) => {
|
||||
const token = getToken();
|
||||
const header = {};
|
||||
let _id = data?.fileId || props.fileId
|
||||
let fileUrl = base_url + '/traask/traFilePreview/' + _id
|
||||
if (token)
|
||||
header['summary'] = token
|
||||
uni.downloadFile({
|
||||
//需要预览的文件地址
|
||||
url: fileUrl,
|
||||
header: header,
|
||||
success: (res) => {
|
||||
//下载成功,得到文件临时地址
|
||||
console.log('下载成功', res.tempFilePath);
|
||||
|
||||
//条件编译,若为h5端则直接赋值文件地址
|
||||
// #ifdef H5
|
||||
let newUrl = res.tempFilePath
|
||||
// #endif
|
||||
|
||||
//条件编译,若为App端,则需要将本地文件系统URL转换为平台绝对路径
|
||||
// #ifdef APP-PLUS
|
||||
let newUrl = plus.io.convertLocalFileSystemURL(res.tempFilePath)
|
||||
// #endif
|
||||
showUrl.value = viewerUrl.value + '?file=' + newUrl
|
||||
showView.value = true
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
</script>
|
||||
|
||||
<style lang="scss">
|
||||
.popup-view{
|
||||
width: 100vw;
|
||||
height: 100vh;
|
||||
}
|
||||
.popup-view-preview{
|
||||
height: 100vh;
|
||||
width: 100%;
|
||||
z-index: 100;
|
||||
position: relative;
|
||||
}
|
||||
.close-preview{
|
||||
position: fixed;
|
||||
right: 20rpx;
|
||||
top: calc(var(--status-bar-height) + 20rpx);
|
||||
color: #000;
|
||||
z-index: 1000;
|
||||
font-size: 30rpx;
|
||||
}
|
||||
</style>
|
||||
@@ -10,6 +10,7 @@
|
||||
"usingComponents" : true,
|
||||
"nvueStyleCompiler" : "uni-app",
|
||||
"compilerVersion" : 3,
|
||||
"renderer": "auto",
|
||||
"splashscreen" : {
|
||||
"alwaysShowBeforeRender" : true,
|
||||
"waiting" : false,
|
||||
|
||||
@@ -270,6 +270,15 @@
|
||||
"titleNView": false
|
||||
}
|
||||
}
|
||||
},
|
||||
{
|
||||
"path": "pages/index/preview",
|
||||
"style": {
|
||||
"navigationBarTitleText": "",
|
||||
"app-plus": {
|
||||
"titleNView": false
|
||||
}
|
||||
}
|
||||
}
|
||||
],
|
||||
"tabBar": {
|
||||
|
||||
@@ -18,7 +18,7 @@
|
||||
<image class="total-score-icon" src="@/static/images/course/score.png" alt=""></image>
|
||||
</view>
|
||||
<view v-for="(item,index) in dataList" :class="['score-item', 'score-item'+(index+1)]">
|
||||
<view class="score-item-name">{{ item.gradeDimensName }}</view>
|
||||
<view class="score-item-name">{{ item.gradeDimens || item.gradeDimensName }}</view>
|
||||
<view class="score-item-score">{{ item.anlyGrade }}</view>
|
||||
</view>
|
||||
</view>
|
||||
|
||||
@@ -8,9 +8,10 @@
|
||||
6 发送loading状态
|
||||
7 教师反馈文本不翻译
|
||||
8 问题反馈信息
|
||||
9 已学完当前知识点反馈信息
|
||||
-->
|
||||
<template>
|
||||
<view :class="['ai-answer', props.class]" :id="props.id" v-if="[3,4,5,8].indexOf(type) >= 0">
|
||||
<view :class="['ai-answer', props.class]" :id="props.id" v-if="[3,4,5,8,9].indexOf(type) >= 0">
|
||||
<!-- 头像信息 -->
|
||||
<view class="user-info">
|
||||
<view class="avatar-box">
|
||||
@@ -24,14 +25,14 @@
|
||||
<!-- 对话信息 -->
|
||||
<view :class="['talking-info', [4].indexOf(type) >= 0 ? 'talking-info-less':''] ">
|
||||
<!-- 语音加载状态 -->
|
||||
<view :class="['talking-gif', !voiceLoading && (activeVoiceId === dataInfo.id)?'is-play':'']" v-if="!([5, 8].indexOf(type) >= 0)">
|
||||
<view :class="['talking-gif', !voiceLoading && (activeVoiceId === dataInfo.id)?'is-play':'']" v-if="!([5, 8, 9].indexOf(type) >= 0)">
|
||||
<CommonLoading color="#06f" v-show="voiceLoading"/>
|
||||
</view>
|
||||
<view class="talking-cont">
|
||||
<!-- 加载状态 -->
|
||||
<CommonLoading color="#06f" v-show="dataInfo.isLoading"/>
|
||||
<!-- 题干/段落内容 -->
|
||||
<text class="talking-text" v-if="[3, 5, 6].indexOf(type) >= 0 && !dataInfo.isLoading">
|
||||
<text class="talking-text" v-if="[3, 5, 6, 9].indexOf(type) >= 0 && !dataInfo.isLoading">
|
||||
{{ showContent }}
|
||||
</text>
|
||||
<text class="talking-text" v-if="[4].indexOf(type) >= 0 && dataInfo.qnsTyp === 'ES'">
|
||||
@@ -58,18 +59,22 @@
|
||||
<ChartThree v-if="dataInfo.evalDimens.length === 3" :dataList="dataInfo.evalDimens" :score="dataInfo.intrctGrade"/>
|
||||
<ChartFive v-if="dataInfo.evalDimens.length === 5" :dataList="dataInfo.evalDimens" :score="dataInfo.intrctGrade"/>
|
||||
</view>
|
||||
<!-- 参考答案 -->
|
||||
<view class="talking-text" v-if="type === 5 && !dataInfo.isLoading" style="overflow: hidden;">
|
||||
参考答案:{{ dataInfo.itemAnswer }}
|
||||
</view>
|
||||
<!-- 举例预览 -->
|
||||
<view class="talking-text" v-if="type === 3 && dataInfo.knoExampie " style="overflow: hidden;">
|
||||
举例:{{ dataInfo.knoExampie }}
|
||||
</view>
|
||||
</view>
|
||||
<view class="btns-cont" v-show="!dataInfo.isLoading">
|
||||
<!-- 重新回答 -->
|
||||
<view class="replay-btn" @click.stop="restartPlay" v-if="!([5, 8].indexOf(type) >= 0)">
|
||||
<!-- 重新播放 -->
|
||||
<view class="replay-btn" @click.stop="restartPlay" v-if="!([5, 8, 9].indexOf(type) >= 0)">
|
||||
<image class="icon" src="@/static/images/course/replay.png" style="width: 100%;height: 100%;"></image>
|
||||
</view>
|
||||
<!-- 停止回答 -->
|
||||
<view class="play-btn" v-if="!([5,8].indexOf(type) >= 0)">
|
||||
<!-- 播放/暂停 -->
|
||||
<view class="play-btn" v-if="!([5, 8, 9].indexOf(type) >= 0)">
|
||||
<image
|
||||
class="icon"
|
||||
src="@/static/images/course/play.png"
|
||||
@@ -86,7 +91,7 @@
|
||||
></image>
|
||||
</view>
|
||||
<view class="next-learn-btn"
|
||||
v-if="showNextBtn && [5,8].indexOf(type) >= 0 && isLast"
|
||||
v-if="showNextBtn && [5,8,9].indexOf(type) >= 0 && isLast"
|
||||
@click.stop="goOnRestartPrgh"
|
||||
>
|
||||
重新学
|
||||
@@ -102,7 +107,7 @@
|
||||
</view>
|
||||
<view
|
||||
class="replay-study-btn next-learn-btn"
|
||||
v-if="showNextBtn && [5,8].indexOf(type) >= 0 && isLast && (dataInfo.passStat === 'PS' || !!dataInfo.traQnsInfoVo?.judgeResult)"
|
||||
v-if="showGoOnStudyBtn"
|
||||
@click.stop="goOnGetQues"
|
||||
>
|
||||
继续学
|
||||
@@ -111,7 +116,7 @@
|
||||
<view class="next-btn" @click.stop="goOnGetQues" v-if="showGoonBtn">继续
|
||||
<image class="icon icon-iamge" src="@/static/images/course/goon.png" ></image></view>
|
||||
</view>
|
||||
<!-- 解析信息 -->
|
||||
<!-- 简答鼓励信息 -->
|
||||
<view class="talking-cont last-cont" v-if=" [5].indexOf(type) >= 0 && !dataInfo.isLoading">
|
||||
<view class="talking-text">
|
||||
{{ changeBr(dataInfo.suggestContent || '--') }}
|
||||
@@ -335,7 +340,21 @@ const audioCacheObj = computed(() => storageStore.audioObj)
|
||||
deep: true,
|
||||
immediate: true
|
||||
})
|
||||
|
||||
const showGoOnStudyBtn = computed(()=> {
|
||||
if(!(showNextBtn.value && isLast.value)){
|
||||
return false
|
||||
}
|
||||
if(type.value === 5){
|
||||
return true
|
||||
}
|
||||
if(type.value === 8){
|
||||
return !!dataInfo.value.traQnsInfoVo?.judgeResult
|
||||
}
|
||||
if(type.value === 9){
|
||||
return dataInfo.value.stdyStat === 'Y'
|
||||
}
|
||||
return false
|
||||
})
|
||||
const transformContent = ref('')
|
||||
const showContentBase = computed(() => {
|
||||
if(props.isTransform){
|
||||
@@ -345,7 +364,8 @@ const audioCacheObj = computed(() => storageStore.audioObj)
|
||||
else if(props.type === 2) return unref(dataInfo)?.chatContent || unref(dataInfo)?.talkingContent
|
||||
else if(props.type === 3) return unref(dataInfo)?.chatContent || unref(dataInfo)?.pgrphContent
|
||||
else if(props.type === 4) return unref(dataInfo)?.chatContent || unref(dataInfo)?.qnsContent
|
||||
else if(props.type === 5) return unref(dataInfo)?.chatContent || unref(dataInfo)?.evalContent
|
||||
else if(props.type === 5) return unref(dataInfo)?.chatContent || unref(dataInfo)?.analyContent
|
||||
else if(props.type === 9) return unref(dataInfo)?.chatContent || unref(dataInfo)?.analyContent
|
||||
else if(props.type === 0) return unref(dataInfo)?.chatContent || unref(dataInfo)?.talkingContent
|
||||
else return unref(dataInfo)?.chatContent || unref(dataInfo)?.talkingContent
|
||||
}
|
||||
@@ -527,9 +547,12 @@ const audioCacheObj = computed(() => storageStore.audioObj)
|
||||
if([5,8].indexOf(props.type) >= 0){
|
||||
// 完成问题
|
||||
emit('nextQuestion', unref(dataInfo))
|
||||
}else if(props.type === 3){
|
||||
}else if([3].indexOf(props.type) >= 0){
|
||||
// 完成段落
|
||||
emit('nextQuestion', unref(dataInfo), 'overGraph')
|
||||
}else if([9].indexOf(props.type) >= 0){
|
||||
// 下一段落
|
||||
emit('nextQuestion', unref(dataInfo), 'nextGraph')
|
||||
}
|
||||
}
|
||||
const clickNow = () => {
|
||||
|
||||
+51
-33
@@ -446,23 +446,8 @@
|
||||
.then(res => {
|
||||
let _id = new Date().getTime() + 'id'
|
||||
let _body = res.body || {}
|
||||
if (Number(_body.bodyTyp) === 7) {
|
||||
common.show('恭喜你已学完全部知识点', '有什么心得跟我们分享吗?', true, '取消', '去评论').then((res) => {
|
||||
if (res) {
|
||||
// 去评论
|
||||
common.redirectTo(
|
||||
`/pages/courseDetail/submit?crsId=${crsId.value}&crsNum=${crsNum.value}&from=study&imgId=${imageId.value}`
|
||||
)
|
||||
} else {
|
||||
// 取消
|
||||
common.redirectTo(
|
||||
`/pages/courseDetail/index?crsId=${crsId.value}&crsNum=${crsNum.value}&from=study`)
|
||||
}
|
||||
}).finally(() => {})
|
||||
return
|
||||
}
|
||||
if (_body.chatBody && _body.chatBody?.stdyStat !== 'N') {
|
||||
let _id = new Date().getTime() + 'id'
|
||||
console.log(_body)
|
||||
if (_body.bodyTyp === '4') {
|
||||
lastTalkingInfo.value = {
|
||||
crsId: crsId.value,
|
||||
stdyId: unref(stdyId),
|
||||
@@ -470,9 +455,6 @@
|
||||
logId: unref(logId),
|
||||
pgrphId,
|
||||
chatContent: _body.chatContent || '',
|
||||
userInfo: {
|
||||
...choiceTeacherInfo.value
|
||||
},
|
||||
...(_body.chatBody || {}),
|
||||
type: 4,
|
||||
userInfo: {
|
||||
@@ -487,7 +469,22 @@
|
||||
qstLogId.value = _body.chatBody?.qstLogId
|
||||
scrollToBottomNow(800)
|
||||
} else {
|
||||
getGraphInfoUnStudy()
|
||||
// getGraphInfoUnStudy()
|
||||
lastTalkingInfo.value = {
|
||||
crsId: crsId.value,
|
||||
stdyId: unref(stdyId),
|
||||
stdyBatch: unref(stdyBatch),
|
||||
logId: unref(logId),
|
||||
chatContent: _body.chatContent || '',
|
||||
stdyStat: _body.chatBody.stdyStat,
|
||||
type: 9,
|
||||
pgrphId,
|
||||
userInfo: {
|
||||
...choiceTeacherInfo.value
|
||||
},
|
||||
id: _id,
|
||||
}
|
||||
talkingList.value.push(JSON.parse(JSON.stringify(lastTalkingInfo.value)))
|
||||
}
|
||||
})
|
||||
}
|
||||
@@ -524,6 +521,16 @@
|
||||
scrollToBottomNow()
|
||||
getQuestionInfoUnStudy(info.pgrphId)
|
||||
})
|
||||
} else if (type === 'nextGraph') {
|
||||
talkingList.value.push({
|
||||
crsId: info.crsId,
|
||||
pgrphId: info.pgrphId,
|
||||
talkingContent: '继续学',
|
||||
type: 0,
|
||||
id: _id
|
||||
})
|
||||
// 下个段落
|
||||
getGraphInfoUnStudy()
|
||||
} else if (type === 'reStart') {
|
||||
talkingList.value.push({
|
||||
crsId: info.crsId,
|
||||
@@ -569,10 +576,11 @@
|
||||
type: 0,
|
||||
id: _id
|
||||
})
|
||||
console.log(unref(logId))
|
||||
textChartApi({
|
||||
processType: 'NEW-KNOW',
|
||||
requestBody: JSON.stringify({
|
||||
logId: info.logId,
|
||||
logId: unref(logId),
|
||||
pgrphId: info.pgrphId
|
||||
})
|
||||
}).then(res => {
|
||||
@@ -732,6 +740,7 @@
|
||||
crsId: crsId.value, // 课程ID 必输项:true 类型:String
|
||||
stdyBatch: stdyBatch.value, // 学习批次 必输项:true 类型:String
|
||||
ansterContent: '', // 回答文本内容 必输项:false 类型:String
|
||||
asrStartTm: unref(lastTalkingInfo).asrStartTm
|
||||
}
|
||||
let _id = new Date().getTime() + 'id'
|
||||
//#ifndef APP-PLUS
|
||||
@@ -829,7 +838,8 @@
|
||||
qstLogId: unref(qstLogId), // 段落ID 必输项:true 类型:String
|
||||
crsId: crsId.value, // 课程ID 必输项:true 类型:String
|
||||
stdyBatch: stdyBatch.value, // 学习批次 必输项:true 类型:String
|
||||
ansterContent: val // 回答文本内容 必输项:false 类型:String
|
||||
ansterContent: val, // 回答文本内容 必输项:false 类型:String
|
||||
asrStartTm: unref(lastTalkingInfo).asrStartTm
|
||||
}
|
||||
textChartApi({
|
||||
processType: 'ANSER-TEXT',
|
||||
@@ -876,14 +886,15 @@
|
||||
talkingList.value = talkingList.value.filter(t => t.recordId !== data.recordId)
|
||||
})
|
||||
}
|
||||
const loadingQstLogId = ref('')
|
||||
const loadingExecLogId = ref('')
|
||||
const answerQuestionNow = (data) => {
|
||||
let _data = {
|
||||
qnsId: data.qnsId, // 问题ID 必输项:true 类型:String
|
||||
pgrphId: data.pgrphId, // 段落ID 必输项:true 类型:String
|
||||
crsId: crsId.value, // 课程ID 必输项:true 类型:String
|
||||
stdyBatch: stdyBatch.value, // 学习批次 必输项:true 类型:String
|
||||
ansterContent: data.answer.join(',') // 回答文本内容 必输项:false 类型:String
|
||||
ansterContent: data.answer.join(','), // 回答文本内容 必输项:false 类型:String
|
||||
asrStartTm: data.asrStartTm
|
||||
}
|
||||
// 发出答案
|
||||
let _answer = data.answerItems.map(t => t.itemNo).join(',')
|
||||
@@ -931,13 +942,14 @@
|
||||
processType: 'ANSER-OVER',
|
||||
requestBody: JSON.stringify({
|
||||
qnsId: data.qnsId,
|
||||
stdyPgrphId: data.stdyPgrphId
|
||||
stdyPgrphId: data.stdyPgrphId,
|
||||
asrStartTm: data.asrStartTm
|
||||
})
|
||||
})
|
||||
.then(res => {
|
||||
// common.msg('完成成功,开始获取评分维度数据!')
|
||||
let _state = res.body.chatBody.processStat
|
||||
if (_state === 'ER') {
|
||||
let _state = res.body.chatBody.isWait
|
||||
if (_state !== 'Y') {
|
||||
common.msg('提交答案失败!')
|
||||
return
|
||||
}
|
||||
@@ -950,8 +962,8 @@
|
||||
},
|
||||
type: 0
|
||||
})
|
||||
loadingQstLogId.value = res.body.chatBody.qstLogId
|
||||
qstLogId.value = loadingQstLogId.value
|
||||
loadingExecLogId.value = res.body.chatBody.execLogId
|
||||
qstLogId.value = loadingExecLogId.value
|
||||
let _id = new Date().getTime() + 'id'
|
||||
lastTalkingInfo.value = {
|
||||
isLoading: true,
|
||||
@@ -964,15 +976,17 @@
|
||||
talkingList.value.push(JSON.parse(JSON.stringify(lastTalkingInfo.value)))
|
||||
scrollToBottomNow(0)
|
||||
getQuestionEvalateRequest(_id, data, 1)
|
||||
}).catch(err=> {
|
||||
console.log(err)
|
||||
})
|
||||
}
|
||||
// 查询问题回答评分
|
||||
const getQuestionEvalateRequest = (id, data, num) => {
|
||||
if (loadingQstLogId.value) {
|
||||
if (loadingExecLogId.value) {
|
||||
textChartApi({
|
||||
processType: 'ANSER-RESULT',
|
||||
requestBody: JSON.stringify({
|
||||
qstLogId: loadingQstLogId.value
|
||||
execLogId: loadingExecLogId.value
|
||||
})
|
||||
})
|
||||
.then(res => {
|
||||
@@ -986,11 +1000,15 @@
|
||||
lastTalkingInfo.value = {
|
||||
..._body.chatBody,
|
||||
pgrphId: data.pgrphId,
|
||||
qstLogId: loadingQstLogId.value,
|
||||
qstLogId: loadingExecLogId.value,
|
||||
id,
|
||||
userInfo: {
|
||||
...choiceTeacherInfo.value
|
||||
},
|
||||
evalDimens: (_body.chatBody.essayEvalVo||[]).map(t=>({
|
||||
...t,
|
||||
gradeDimensName: t.gradeDimens
|
||||
})),
|
||||
type: 5
|
||||
}
|
||||
return lastTalkingInfo.value
|
||||
|
||||
@@ -7,14 +7,14 @@
|
||||
</view>
|
||||
<view class="answer-content" v-else>
|
||||
<view class="talking-link">
|
||||
<view :class="['link-cont', activeNames.indexOf(1) >= 0 ? 'is-active' : '']" @click="changeActive(1)">
|
||||
<view class="link-info">
|
||||
<view :class="['link-cont', activeNames.indexOf(1) >= 0 ? 'is-active' : '']">
|
||||
<view class="link-info" @click="changeActive(1)">
|
||||
<view class="info-text">
|
||||
引用知识库{{3}}篇相关资料
|
||||
引用知识库{{fileList.length}}篇相关资料
|
||||
</view>
|
||||
</view>
|
||||
<view class="link-items">
|
||||
<view class="link-item" v-for="(item, index) in 3">{{index+1}}. {{item}}</view>
|
||||
<view class="link-item" v-for="(item, index) in fileList" @click.stop="previewFile(item)">{{index+1}}. {{item.docName}}</view>
|
||||
</view>
|
||||
</view>
|
||||
<view :class="['link-cont', activeNames.indexOf(2) >= 0 ? 'is-active' : '']">
|
||||
@@ -84,6 +84,7 @@
|
||||
immediate: true
|
||||
})
|
||||
const mdText = computed(() => props.dataInfo?.talkingText)
|
||||
const fileList = computed(() => props.dataInfo?.talkingFiles || [])
|
||||
const activeNames = ref([1, 2])
|
||||
|
||||
const changeActive = (val) => {
|
||||
@@ -105,6 +106,9 @@
|
||||
const feedbackAnswer = ()=>{
|
||||
emit('handleEvents', 'feedback')
|
||||
}
|
||||
const previewFile = (item) => {
|
||||
emit('handleEvents', 'preview', item)
|
||||
}
|
||||
</script>
|
||||
|
||||
<style scoped lang="scss">
|
||||
|
||||
@@ -1,39 +1,34 @@
|
||||
<template>
|
||||
<view class="talking-item">
|
||||
<questionVue
|
||||
v-if="talkingType === 'question'"
|
||||
@changePlay="changePlay"
|
||||
:dataInfo="talkingInfo"
|
||||
:activeVoiceId="activeVoiceId"
|
||||
></questionVue>
|
||||
<answerVue
|
||||
v-else-if="talkingType === 'answer'"
|
||||
:dataInfo="props.talkingInfo"
|
||||
:isLoading="!!props.talkingInfo.isLoading"
|
||||
:isAnswering="props.isAnswering"
|
||||
@handleEvents="handleEvents"
|
||||
></answerVue>
|
||||
<questionVue v-if="talkingType === 'question'" @changePlay="changePlay" :dataInfo="talkingInfo"
|
||||
:activeVoiceId="activeVoiceId"></questionVue>
|
||||
<answerVue v-else-if="talkingType === 'answer'" :dataInfo="props.talkingInfo"
|
||||
:isLoading="!!props.talkingInfo.isLoading" :isAnswering="props.isAnswering" @handleEvents="handleEvents">
|
||||
</answerVue>
|
||||
<view v-else></view>
|
||||
</view>
|
||||
</template>
|
||||
|
||||
<script setup>
|
||||
import { toRefs, watch } from 'vue'
|
||||
import {
|
||||
toRefs,
|
||||
watch
|
||||
} from 'vue'
|
||||
import questionVue from './question.vue';
|
||||
import answerVue from './answer.vue';
|
||||
|
||||
|
||||
const emit = defineEmits(['handleEvents'])
|
||||
const props = defineProps({
|
||||
talkingType:{
|
||||
default:'question',
|
||||
talkingType: {
|
||||
default: 'question',
|
||||
type: String
|
||||
},
|
||||
talkingInfo:{
|
||||
talkingInfo: {
|
||||
default: () => ({}),
|
||||
type: Object
|
||||
},
|
||||
activeVoiceId:{
|
||||
default:'',
|
||||
activeVoiceId: {
|
||||
default: '',
|
||||
type: String
|
||||
},
|
||||
isAnswering: {
|
||||
@@ -41,22 +36,42 @@
|
||||
type: Boolean
|
||||
}
|
||||
})
|
||||
watch(() => props.activeVoiceId, () => {},{deep: true,immediate: true})
|
||||
watch(() => props.talkingInfo, () => {},{deep: true,immediate: true})
|
||||
const { talkingType } = toRefs(props)
|
||||
const handleEvents = (type) => {
|
||||
emit('handleEvents',{ type, data: props.talkingInfo, id:""})
|
||||
watch(() => props.activeVoiceId, () => {}, {
|
||||
deep: true,
|
||||
immediate: true
|
||||
})
|
||||
watch(() => props.talkingInfo, () => {}, {
|
||||
deep: true,
|
||||
immediate: true
|
||||
})
|
||||
const {
|
||||
talkingType
|
||||
} = toRefs(props)
|
||||
const handleEvents = (type, info) => {
|
||||
console.log(info)
|
||||
emit('handleEvents', {
|
||||
type,
|
||||
data: props.talkingInfo,
|
||||
id: "",
|
||||
info
|
||||
})
|
||||
}
|
||||
const changePlay = (id) => {
|
||||
emit('handleEvents', {type: 'changePlay', data: props.talkingInfo, id})
|
||||
emit('handleEvents', {
|
||||
type: 'changePlay',
|
||||
data: props.talkingInfo,
|
||||
id,
|
||||
info: {}
|
||||
})
|
||||
}
|
||||
</script>
|
||||
|
||||
<style scoped lang="scss">
|
||||
.talking-item{
|
||||
.talking-item {
|
||||
overflow: hidden;
|
||||
margin-top: 0rpx;
|
||||
&+.talking-item{
|
||||
|
||||
&+.talking-item {
|
||||
margin-top: 30rpx;
|
||||
}
|
||||
}
|
||||
|
||||
+44
-20
@@ -1,20 +1,20 @@
|
||||
<template>
|
||||
<view class="index-dialog-page">
|
||||
<view class="index-dialog-page" v-show="!showPreview">
|
||||
<!-- <MarkdownPreview/> -->
|
||||
<view class="top-bg"></view>
|
||||
<view class="bot-bg"></view>
|
||||
<scroll-view class="index-dialog-body" :scroll-y="true" upper-threshold="0" refresher-enabled="true"
|
||||
refresher-default-style="none" @refresherrefresh="scrolltolower">
|
||||
|
||||
<view class="body-title">
|
||||
<!-- <uv-icon class="arrow-icon" name="arrow-left" @click="common.navigateBack()"/> -->
|
||||
AI问答
|
||||
<view class="seek-setting">
|
||||
<image src="@/static/images/dialog/new-dialog.png" alt="" class="image-icon-new" @click="createNewDialog"></image>
|
||||
<image src="@/static/images/dialog/new-dialog.png" alt="" class="image-icon-new" @click="createNewDialog">
|
||||
</image>
|
||||
<image src="@/static/images/dialog/history.png" alt="" class="image-icon" @click="showHistory"></image>
|
||||
</view>
|
||||
</view>
|
||||
|
||||
|
||||
<view class="ai-info">
|
||||
<!-- <image src="@/static/images/dialog/pet-3.png" alt="" class="image-pet-bg"></image> -->
|
||||
<image src="@/static/images/dialog/pet-bg-base.png" alt="" class="image-pet-bg"></image>
|
||||
@@ -33,8 +33,7 @@
|
||||
</view>
|
||||
</view>
|
||||
<view class="question-row">
|
||||
<view class="question-item"
|
||||
v-for="item in questionList.length - Math.ceil(questionList.length/2)"
|
||||
<view class="question-item" v-for="item in questionList.length - Math.ceil(questionList.length/2)"
|
||||
@click="sendText(questionList[item + Math.ceil(questionList.length/2)-1].hotContent)">
|
||||
{{questionList[item + Math.ceil(questionList.length/2)-1].hotContent}}
|
||||
</view>
|
||||
@@ -42,10 +41,10 @@
|
||||
</scroll-view>
|
||||
</view>
|
||||
<view class="talking-list">
|
||||
<scroll-view class="talking-scroll-list" :scroll-y="true" :scroll-top="scrollTop"
|
||||
:show-scrollbar="false" :scroll-with-animation="false">
|
||||
<TalkingItem v-for="item in talkingList" :talkingType="item.type" :talkingInfo="item" :isAnswering="!answerIsOver"
|
||||
:activeVoiceId="activeVoiceTalkingItemId" @handleEvents="talkItemEvents">
|
||||
<scroll-view class="talking-scroll-list" :scroll-y="true" :scroll-top="scrollTop" :show-scrollbar="false"
|
||||
:scroll-with-animation="false">
|
||||
<TalkingItem v-for="item in talkingList" :talkingType="item.type" :talkingInfo="item"
|
||||
:isAnswering="!answerIsOver" :activeVoiceId="activeVoiceTalkingItemId" @handleEvents="talkItemEvents">
|
||||
</TalkingItem>
|
||||
</scroll-view>
|
||||
</view>
|
||||
@@ -87,9 +86,10 @@
|
||||
<!-- 反馈组件 -->
|
||||
<Feedback ref="feedbackRef"></Feedback>
|
||||
<History ref="historyRef"></History>
|
||||
<PreviewVue ref="previewRef"/>
|
||||
<PreviewVue ref="previewRef" />
|
||||
</scroll-view>
|
||||
</view>
|
||||
<file-preview ref="previewFileRef" :file-id="'603058d8-88e0-43d2-8242-3132b85bc91c'" v-model="showPreview" />
|
||||
</template>
|
||||
|
||||
<script setup>
|
||||
@@ -138,7 +138,7 @@
|
||||
} from "@/api/dialog.js"
|
||||
import Feedback from './components/feedback.vue'
|
||||
import History from './components/history.vue'
|
||||
|
||||
|
||||
const {
|
||||
statusBarHeight
|
||||
} = uni.getWindowInfo()
|
||||
@@ -149,7 +149,7 @@
|
||||
const {
|
||||
SocketObj
|
||||
} = storeToRefs(socketStore)
|
||||
|
||||
|
||||
const feedbackRef = ref()
|
||||
const userInfo = ref(getUserInfo())
|
||||
const questionList = ref([
|
||||
@@ -184,6 +184,7 @@
|
||||
return unref(userInfo)?.mascotInfo?.mascotId || 'Tst00001'
|
||||
})
|
||||
const answerText = ref('')
|
||||
const answerFileList = ref('')
|
||||
const answerIsOver = ref(true)
|
||||
const talkingList = ref([])
|
||||
|
||||
@@ -267,7 +268,6 @@
|
||||
seqNo.value = body.seqNo
|
||||
touchBtnCallBack.value && touchBtnCallBack.value()
|
||||
touchBtnCallBack.value = null
|
||||
console.log('嘻嘻嘻嘻嘻嘻嘻嘻嘻嘻嘻嘻嘻', body);
|
||||
talkingList.value.push({
|
||||
type: 'question',
|
||||
talkingText: body.intrctContent,
|
||||
@@ -304,7 +304,10 @@
|
||||
isLoading: false,
|
||||
id: _id,
|
||||
...body,
|
||||
askData: {...askData.value}
|
||||
askData: {
|
||||
...askData.value
|
||||
},
|
||||
talkingFiles: []
|
||||
})
|
||||
} else if (body.event === 'token') {
|
||||
answerIsOver.value = false
|
||||
@@ -312,6 +315,10 @@
|
||||
} else if (body.event === 'end') {
|
||||
console.log('完成回答!')
|
||||
answerIsOver.value = true
|
||||
} else if (body.event === 'sourceDocuments') {
|
||||
console.log('回答返回文件列表!')
|
||||
if (talkingList.value.length === 0) return
|
||||
talkingList.value[talkingList.value.length - 1].talkingFiles = JSON.parse(body.data) || []
|
||||
}
|
||||
return
|
||||
}
|
||||
@@ -364,7 +371,12 @@
|
||||
}
|
||||
|
||||
const stopAnswerCallBack = ref(null)
|
||||
const talkItemEvents = ({type, data, id}) => {
|
||||
const talkItemEvents = ({
|
||||
type,
|
||||
data,
|
||||
id,
|
||||
info = {}
|
||||
}) => {
|
||||
switch (type) {
|
||||
case 'reAnswer':
|
||||
console.log('重新提问回答')
|
||||
@@ -407,6 +419,14 @@
|
||||
case 'feedback':
|
||||
feedbackRef.value.open(data)
|
||||
break;
|
||||
case 'preview':
|
||||
console.log(type, data, id)
|
||||
// showPreview.value = true
|
||||
common.navigateTo('/pages/index/preview?fileId=' + info.docId)
|
||||
break;
|
||||
case 'toCourse':
|
||||
console.log(type, data, id)
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
@@ -558,24 +578,28 @@
|
||||
return
|
||||
}
|
||||
// 判断下如果没有设置吉祥物就跳转到吉祥物页面
|
||||
if(userInfo.value?.mascotInfo.mascotId === null) { //说明这人在上次选吉祥物的时候退出了,没有选到吉祥物
|
||||
if (userInfo.value?.mascotInfo.mascotId === null) { //说明这人在上次选吉祥物的时候退出了,没有选到吉祥物
|
||||
common.redirectTo('/pages/mascot/mascot_select_list');
|
||||
return
|
||||
}
|
||||
})
|
||||
const previewRef = ref()
|
||||
const previewFileRef = ref()
|
||||
const showPreview = ref(false)
|
||||
onMounted(() => {
|
||||
loadData()
|
||||
// previewRef.value.open()
|
||||
// previewFileRef.value.open({
|
||||
// fileId: '0006e7f7-a332-4c81-9802-ac4e2d971c71'
|
||||
// })
|
||||
})
|
||||
|
||||
const refreshData = () => {
|
||||
loadData();
|
||||
};
|
||||
|
||||
|
||||
const keyboardHeight = ref('0px')
|
||||
const setHeight = (res) => {
|
||||
keyboardHeight.value = res.height +'px'
|
||||
keyboardHeight.value = res.height + 'px'
|
||||
}
|
||||
//#ifdef APP-PLUS
|
||||
onHide(() => {
|
||||
|
||||
@@ -0,0 +1,127 @@
|
||||
<template>
|
||||
<view class="popup-view">
|
||||
<view class="body-title">
|
||||
<uv-icon class="arrow-icon" name="arrow-left" @click="backRouter()" />
|
||||
文件预览
|
||||
</view>
|
||||
<view class="popup-view-preview" v-if="showView">
|
||||
<web-view :src="showUrl" :fullscreen="true" :webview-styles="{
|
||||
width: '100%',
|
||||
height: '100%'
|
||||
}"></web-view>
|
||||
</view>
|
||||
</view>
|
||||
</template>
|
||||
|
||||
<script >
|
||||
import {
|
||||
getToken
|
||||
} from "@/common/common.js"
|
||||
import common from '@/common/common';
|
||||
import {
|
||||
downloadFile
|
||||
} from "@/api/common.js"
|
||||
import {
|
||||
get_base_url
|
||||
} from '@/api/request.js'
|
||||
var wv
|
||||
export default{
|
||||
data(){
|
||||
return {
|
||||
fileId:'',
|
||||
showUrl:'',
|
||||
viewerUrl: '/static/pdf-view/web/viewer.html',
|
||||
showView: false,
|
||||
wv: null
|
||||
}
|
||||
},
|
||||
onLoad(params){
|
||||
this.fileId = params.fileId || '';
|
||||
},
|
||||
onShow(){
|
||||
this.openPdfFn({
|
||||
fileId: this.fileId
|
||||
})
|
||||
},
|
||||
onReady(){
|
||||
//#ifdef APP-PLUS
|
||||
var currentWebview = this.$scope.$getAppWebview()
|
||||
setTimeout(()=>{
|
||||
wv = currentWebview.children()[0]
|
||||
wv.setStyle({
|
||||
top: 80
|
||||
})
|
||||
uni.onKeyboardHeightChange(setHeight)
|
||||
},1000)
|
||||
// #endif
|
||||
},
|
||||
methods:{
|
||||
// setHeight(res){
|
||||
// wv.setStyle({
|
||||
// top: res.height + 20
|
||||
// })
|
||||
// },
|
||||
backRouter(){
|
||||
common.navigateBack()
|
||||
},
|
||||
openPdfFn(data){
|
||||
const base_url = get_base_url('/traask/traFilePreview/')
|
||||
const token = getToken();
|
||||
const header = {};
|
||||
let _id = data?.fileId
|
||||
let fileUrl = base_url + '/traask/traFilePreview/' + _id
|
||||
if (token)
|
||||
header['summary'] = token
|
||||
uni.downloadFile({
|
||||
//需要预览的文件地址
|
||||
url: fileUrl,
|
||||
header: header,
|
||||
success: (res) => {
|
||||
//下载成功,得到文件临时地址
|
||||
//条件编译,若为h5端则直接赋值文件地址
|
||||
// #ifdef H5
|
||||
let newUrl = res.tempFilePath
|
||||
// #endif
|
||||
//条件编译,若为App端,则需要将本地文件系统URL转换为平台绝对路径
|
||||
// #ifdef APP-PLUS
|
||||
let newUrl = plus.io.convertLocalFileSystemURL(res.tempFilePath)
|
||||
// #endif
|
||||
this.showUrl = this.viewerUrl + '?file=' + newUrl
|
||||
this.showView = true
|
||||
}
|
||||
})
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<style lang="scss" scoped>
|
||||
.popup-view{
|
||||
width: 100vw;
|
||||
height: 100vh;
|
||||
}
|
||||
.body-title {
|
||||
height: 90rpx;
|
||||
text-align: center;
|
||||
font-size: 33rpx;
|
||||
padding-top: 10rpx;
|
||||
line-height: 46rpx;
|
||||
box-sizing: border-box;
|
||||
font-weight: 500;
|
||||
color: #000;
|
||||
position: fixed;
|
||||
top: var(--status-bar-height);
|
||||
left: 0;
|
||||
width: 100vw;
|
||||
z-index: 10000;
|
||||
// margin-bottom: 23rpx;
|
||||
.arrow-icon {
|
||||
position: absolute;
|
||||
left: 21rpx;
|
||||
top: 5rpx;
|
||||
color: #000;
|
||||
padding: 15rpx;
|
||||
// background-color: red;
|
||||
}
|
||||
}
|
||||
</style>
|
||||
+10
-2
@@ -1,6 +1,5 @@
|
||||
{
|
||||
"pages": [
|
||||
{
|
||||
"pages": [{
|
||||
"path": "pages/course/index",
|
||||
"style": {
|
||||
"navigationBarTitleText": "课程中心",
|
||||
@@ -27,5 +26,14 @@
|
||||
}
|
||||
}
|
||||
},
|
||||
{
|
||||
"path": "pages/index/preview",
|
||||
"style": {
|
||||
"navigationBarTitleText": "",
|
||||
"app-plus": {
|
||||
"titleNView": false
|
||||
}
|
||||
}
|
||||
}
|
||||
]
|
||||
}
|
||||
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
@@ -0,0 +1,3 @@
|
||||
àRCopyright 1990-2009 Adobe Systems Incorporated.
|
||||
All rights reserved.
|
||||
See ./LICENSEáCNS2-H
|
||||
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
@@ -0,0 +1,3 @@
|
||||
àRCopyright 1990-2009 Adobe Systems Incorporated.
|
||||
All rights reserved.
|
||||
See ./LICENSEá ETen-B5-H` ^
|
||||
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
@@ -0,0 +1,4 @@
|
||||
àRCopyright 1990-2009 Adobe Systems Incorporated.
|
||||
All rights reserved.
|
||||
See ./LICENSE!!�º]aX!!]`�21�> �p�z�$]‚�"R‚d�-Uƒ7�*„␍4„%�+ „Z „{�/…%…<�9K…b�1]†.�"‡‰`]‡,�"]ˆ
|
||||
�"]ˆh�"]‰F�"]Š$�"]‹�"]‹`�"]Œ>�"]��"]�z�"]ŽX�"]�6�"]��"]�r�"]‘P�"]’.�"]“�"]“j�"]”H�"]•&�"]–�"]–b�"]—@�"]˜�"]˜|�"]™Z�"]š8�"]›�"]›t�"]œR�"]�0�"]ž�"]žl�"]ŸJ�"] (�"]¡�"]¡d�"]¢B�"]£ �"X£~�']¤W�"]¥5�"]¦�"]¦q�"]§O�"]¨-�"]©�"]©i�"]ªG�"]«%�"]¬�"]¬a�"]?�"]®�"]®{�"]¯Y�"]°7�"]±�"]±s�"]²Q�"]³/�"]´␍�"]´k�"]µI�"]¶'�"]·�"]·c�"]¸A�"]¹�"]¹}�"]º[�"]»9
|
||||
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user