217 lines
5.7 KiB
Vue
217 lines
5.7 KiB
Vue
<template>
|
||
<view>
|
||
<navbar-back title="任务单预览"></navbar-back>
|
||
<!-- #ifdef H5 -->
|
||
<web-view :src="pdfUrlH5"></web-view>
|
||
<u-button v-if="showConfirmBtn" class="confirm-btn" type="success" @click="handleConfirm()">数据确认</u-button>
|
||
<!-- #endif -->
|
||
</view>
|
||
</template>
|
||
|
||
<script setup>
|
||
import { ref, onMounted } from 'vue'
|
||
import { onLoad, onHide, onUnload } from '@dcloudio/uni-app'
|
||
import { getBaseUrl } from '@/defaultBaseUrl'
|
||
import nx from '@/nx'
|
||
|
||
// 响应式数据
|
||
const businessAssayTaskId = ref('')
|
||
const localFilePath = ref('')
|
||
const reportKey = ref('')
|
||
const hideResultFlag = ref('')
|
||
const viewerUrl = '/hybrid/html/web/viewer.html?file='
|
||
const pdfUrlH5 = ref('')
|
||
const showConfirmBtn = ref(false)
|
||
let confirmButtonRef = null // 用于保存按钮实
|
||
|
||
let wv = null // 计划创建的 webview
|
||
|
||
function handleConfirm() {
|
||
const params = {
|
||
businessAssayTaskId: businessAssayTaskId.value
|
||
}
|
||
nx.$api.assayTask.submitTask(params).then(res => {
|
||
uni.redirectTo({
|
||
url: '/pages/analysis/sample/sample-work-list'
|
||
})
|
||
})
|
||
}
|
||
// 方法:下载 PDF
|
||
const downloadPdf = (pdfUrl, retryCount = 0) => {
|
||
const MAX_RETRY = 3 // 最多重试 3 次
|
||
return new Promise(resolve => {
|
||
if (retryCount >= MAX_RETRY) {
|
||
console.error('PDF 下载失败:超过最大重试次数')
|
||
return resolve(null)
|
||
}
|
||
|
||
uni.downloadFile({
|
||
url: pdfUrl,
|
||
success: res => {
|
||
if (res.statusCode !== 200) {
|
||
console.warn(`下载失败,状态码: ${res.statusCode},重试第 ${retryCount + 1} 次`)
|
||
return resolve(downloadPdf(pdfUrl, retryCount + 1))
|
||
}
|
||
|
||
const tempFilePath = res.tempFilePath
|
||
uni.getFileInfo({
|
||
filePath: tempFilePath,
|
||
success: fileInfo => {
|
||
if (fileInfo.size > 0) {
|
||
resolve(tempFilePath)
|
||
} else {
|
||
console.warn('文件为空,重试中...')
|
||
resolve(downloadPdf(pdfUrl, retryCount + 1))
|
||
}
|
||
},
|
||
fail: () => {
|
||
console.warn('获取文件信息失败,重试中...')
|
||
resolve(downloadPdf(pdfUrl, retryCount + 1))
|
||
}
|
||
})
|
||
},
|
||
fail: () => {
|
||
console.warn('网络请求失败,重试中...')
|
||
resolve(downloadPdf(pdfUrl, retryCount + 1))
|
||
}
|
||
})
|
||
})
|
||
}
|
||
|
||
// 方法:Android 加载 PDF
|
||
const loadPdfOnAndroid = async pdfUrl => {
|
||
const tempFilePath = await downloadPdf(pdfUrl)
|
||
if (!tempFilePath) return
|
||
const localPath = plus.io.convertLocalFileSystemURL(tempFilePath)
|
||
localFilePath.value = localPath
|
||
const allUrl = viewerUrl + encodeURIComponent(localPath)
|
||
// 创建并加载 webview
|
||
wv = plus.webview.create('', 'custom-webview', {
|
||
top: uni.getSystemInfoSync().statusBarHeight + 44,
|
||
bottom: 0
|
||
})
|
||
wv.loadURL(allUrl)
|
||
|
||
confirmButtonRef = createConfirmButton()
|
||
const currentWebview = getCurrentPages().pop().$getAppWebview()
|
||
currentWebview.append(wv)
|
||
currentWebview.append(confirmButtonRef)
|
||
|
||
if (!showConfirmBtn.value) {
|
||
hideNativeButton()
|
||
}
|
||
}
|
||
const createConfirmButton = () => {
|
||
const sysInfo = uni.getSystemInfoSync()
|
||
const btnWidth = 100
|
||
const btnHeight = 40
|
||
const margin = 10
|
||
const left = sysInfo.windowWidth - btnWidth - margin
|
||
const top = sysInfo.windowHeight - btnHeight - margin
|
||
|
||
const buttonView = new plus.nativeObj.View('confirm-btn-native', {
|
||
left: left,
|
||
top: top,
|
||
width: btnWidth,
|
||
height: btnHeight
|
||
})
|
||
|
||
buttonView.drawRect({ color: '#5ac725', radius: '4px' }, { top: 0, left: 0, width: btnWidth, height: btnHeight })
|
||
|
||
buttonView.drawText(
|
||
'确认上报',
|
||
{ top: 11, left: 0, width: btnWidth, height: 18 },
|
||
{ size: '14px', color: '#ffffff', align: 'center' }
|
||
)
|
||
|
||
buttonView.interceptTouchEvent(true)
|
||
buttonView.addEventListener('click', () => {
|
||
handleConfirm()
|
||
})
|
||
|
||
return buttonView
|
||
}
|
||
|
||
// 隐藏按钮
|
||
function hideNativeButton() {
|
||
if (confirmButtonRef) {
|
||
confirmButtonRef.hide()
|
||
}
|
||
}
|
||
function destroyNativeButton() {
|
||
if (confirmButtonRef) {
|
||
confirmButtonRef.close() // 或 remove()
|
||
confirmButtonRef = null
|
||
}
|
||
}
|
||
// 获取 PDF 预览 URL
|
||
const getPdf = async () => {
|
||
const printBaseUrl = getBaseUrl()
|
||
const baseUrl = getBaseUrl()
|
||
let dataUrl = `${baseUrl}/qms/bus/sample/reporting-data-query/crossAuditByTaskId?businessAssayTaskId=${businessAssayTaskId.value}`
|
||
dataUrl += `&hideResultFlag=${hideResultFlag.value}`
|
||
const token = nx.$store('user').token
|
||
let url = `${printBaseUrl}/qms/config-report-template/preview`
|
||
url += `?token=${token}`
|
||
url += `&type=PDF`
|
||
url += `&reportKey=${reportKey.value}`
|
||
url += `&dataUrl=${encodeURIComponent(dataUrl)}`
|
||
|
||
// #ifdef H5
|
||
pdfUrlH5.value = viewerUrl + encodeURIComponent(url)
|
||
// #endif
|
||
|
||
// #ifndef H5
|
||
await loadPdfOnAndroid(url)
|
||
// #endif
|
||
}
|
||
|
||
// 删除临时文件
|
||
const deleteTmpFile = () => {
|
||
if (!localFilePath.value) return
|
||
const dir = localFilePath.value.substring(0, localFilePath.value.lastIndexOf('/'))
|
||
plus.io.resolveLocalFileSystemURL(
|
||
dir,
|
||
entry => {
|
||
entry.removeRecursively(
|
||
() => console.log('删除成功'),
|
||
e => console.log('删除失败:' + e.message)
|
||
)
|
||
},
|
||
e => console.log('目录不存在:' + e.message)
|
||
)
|
||
}
|
||
|
||
// 生命周期
|
||
onLoad(param => {
|
||
if (param.businessAssayTaskId) {
|
||
businessAssayTaskId.value = param.businessAssayTaskId
|
||
reportKey.value = param.reportKey
|
||
hideResultFlag.value = param.hideResultFlag
|
||
}
|
||
if (param.showConfirmBtn && param.showConfirmBtn === 'true') {
|
||
showConfirmBtn.value = true
|
||
}
|
||
getPdf()
|
||
})
|
||
|
||
onHide(() => {
|
||
deleteTmpFile()
|
||
})
|
||
|
||
onUnload(() => {
|
||
deleteTmpFile()
|
||
destroyNativeButton()
|
||
})
|
||
</script>
|
||
|
||
<style scoped>
|
||
.confirm-btn {
|
||
position: fixed;
|
||
bottom: 10px;
|
||
right: 10px;
|
||
width: 10%;
|
||
z-index: 9999;
|
||
}
|
||
</style>
|