<script setup lang="ts">
import { Modal, message } from 'ant-design-vue';
import { ref } from 'vue';
import doubleSelect from './doubleSelect.vue';
import MapDialog from './mapDialog.vue';
import morejc from './morejc.vue';
import photolist from './photolist.vue';
import morenum from './morenum.vue';
import mxend from './mxend.vue';
import photomodal from './photomodal.vue';
import nameModal from './nameModal.vue';
import { getFullModelFileURL } from '@/utils/common';
// const props = withDefaults(defineProps<{
// searchobj: any
// }>(), {
// searchobj: () => { },
// });
const name = ref();
const confirmData = ref([]);
const treeData: any = ref([
]);
// 航线信息
const doubleSelectList = ref([
{
label: '三维建模测试航线A',
children: [
{
label: '三维建模测试航线A-航线1',
value: '1',
},
{
label: '三维建模测试航线A-航线2',
value: '2',
},
{
label: '三维建模测试航线A-航线3',
value: '3',
},
{
label: '三维建模测试航线A-航线4',
value: '4',
},
{
label: '三维建模测试航线A-航线5',
value: '5',
},
],
value: '12',
},
{
label: '三维建模测试航线B',
children: [
{
label: '三维建模测试航线B-航线1',
value: '11',
},
{
label: '三维建模测试航线B-航线2',
value: '22',
},
{
label: '三维建模测试航线B-航线3',
value: '33',
},
{
label: '三维建模测试航线B-航线4',
value: '44',
},
{
label: '三维建模测试航线B-航线5',
value: '55',
},
],
value: '21',
},
]);
// const 0-未开始, 1-未完成, 2-正常
const STATE = {
'0': '未开始',
'1': '未完成',
'2': '已完成',
'-1': '建模失败',
};
const mapDialogRef = ref();
// 左侧模型列表
let currentPage = 1;
const leftItem = ref();
const total = ref<number>(0);
const photolistqsRef = ref(); // 期数图片组件
const makeTypeshow = ref(1);// 模型样式
const numObj = ref();// 期数对象
const timer = ref<any>(); // 定时器
function _getApiModelMakePageQuery(isNew?: boolean, paramsObj?: any) {
if (isNew) {
currentPage = 1;
}
else {
currentPage++;
}
const params: any = {
currentPage,
pageSize: 10,
name: name.value,
};
if (paramsObj && paramsObj !== null) {
params.createStartTime = paramsObj.createStartTime;
params.createEndTime = paramsObj.createEndTime;
params.finishStartTime = paramsObj.finishStartTime;
params.finishEndTime = paramsObj.finishEndTime;
params.state = paramsObj.state;
}
getApiModelMakePageQuery(params).then((res) => {
if (res.success) {
if (res.data && res.data !== null) {
const _list: any = res.data?.records;
total.value = res?.data?.total ?? 0;
if (_list && _list.length) {
if (isNew) {
treeData.value = _list;
}
else {
treeData.value = [...treeData.value, ..._list];
}
listClick(0, treeData.value[0]);
leftItem.value = treeData.value[0]; // 默认第一条
timer.value = setInterval(() => {
// 获取进度
treeData.value.forEach((element: any, index: any) => {
// 0-未开始, 1-未完成, 2-正常 -1建模失败 */
if (element.state === 1) {
_getApiMediaModelLibraryGetOdmTaskInfoByModelMakePeriodId(element.latestModelMakePeriodId, index);
}
else if (element.state === 2) {
treeData.value[index].modelState = 99;
treeData.value[index].progress = 100;
}
else if (element.state === -1) {
treeData.value[index].modelState = -2;
treeData.value[index].progress = 0;
}
else {
treeData.value[index].modelState = -1;
treeData.value[index].progress = 0;
}
});
}, 1000);
}
}
else {
treeData.value = [];
}
}
});
}
// 停止定时请求
function stop() {
if (timer.value) {
clearInterval(timer.value);
timer.value = null;
}
}
/**
* 筛选确认事件
* @param val
*/
function onConfirm(val: any) {
confirmData.value = val;
const d = val.map((item: any) => {
return {
flyRecordId: item.id,
taskName: item.taskName,
};
});
// 追加架次
_postApiModelMakePeriodAppend(d);
}
/**
* 删除已选数据事件
* @param val
*/
function onDelete(val: any) {
Modal.confirm({
title: '提示',
content: '是否确认删除?',
okText: '确认',
cancelText: '取消',
async onOk() {
_postApiModelMakePeriodClear(val.modelMakePeriodId, [val]);
},
});
}
// 已选任务删除
function _postApiModelMakePeriodClear(id: any, list: any) {
postApiModelMakePeriodClear({
id,
flyRecordList: list,
}).then((res) => {
if (res.success) {
message.success(res.msg);
_getApiModelMakePeriodFlyRecordList(numObj.value.id);// 已选任务
photolistqsRef.value?._getApiModelMakePeriodImagePageQuery(); // 更新图片
}
else {
message.error(res.msg);
}
});
}
function search() {
_getApiModelMakePageQuery(true);
}
function add() {
mapDialogRef.value.open();
}
const listIndex = ref(0);
const numList: any = ref([
]);
const titIndex = ref(0);
// 左侧点击
function listClick(index: any, item: any) {
leftItem.value = item;
listIndex.value = index;
// 获取期数
numObj.value = null;
titIndex.value = 0;
confirmData.value = [];
makeTypeshow.value = 1;
numList.value = [];
_getApiModelMakePeriodList();
}
function _getApiModelMakePeriodList() {
getApiModelMakePeriodList({
modelMakeId: leftItem.value.id,
}).then((res) => {
if (res.success) {
if (res.data && res.data !== null) {
numList.value = res?.data;
if (numList.value && numList.value.length) {
numObj.value = numList.value[0]; // 默认第一期
// 当前期数下已选任务
_getApiModelMakePeriodFlyRecordList(numObj.value.id);
// 如若是已完成 显示模型
showModal(numObj.value);
}
}
}
});
}
// 更新期数列表
function getNumList() {
_getApiModelMakePeriodList();
_getApiModelMakePageQuery(true);// 左侧列表也更新
}
// 期数点击
const newNumIndex = ref();
const newNumItem = ref();
function titClick(index: any, item: any) {
titIndex.value = index;
numObj.value = item; // 当前期数
newNumIndex.value = index;
newNumItem.value = item;
// console.log(item, 22222222222);
// 已选任务
_getApiModelMakePeriodFlyRecordList(item.id);
// 如若是已完成 显示模型
showModal(item);
}
// 追加架次
const morejcRef = ref();
function addmorejc() {
if (!numObj.value) {
message.warning('请先新建期数');
return;
}
morejcRef.value.open();
}
// 重新添加
function addreset() {
Modal.confirm({
title: '提示',
content: '重新添加架次将清空所有已选数据,是否确定重新添加?',
okText: '确认',
cancelText: '取消',
async onOk() {
_postApiModelMakePeriodClear(numObj.value.id, []);
},
});
}
// 三维制作
function doing() {
Modal.confirm({
title: '三维建模',
content: '确认是否开始建模?',
okText: '确认',
cancelText: '取消',
async onOk() {
postApiModelMakePeriodStart({
id: numObj.value.id,
}).then((res) => {
if (res.success) {
message.success(res.msg);
_getApiModelMakePageQuery(true);// 左侧列表刷新
}
else {
message.error(res.msg);
}
});
},
});
}
// 新增期数
const morenumRef = ref();
function addnum() {
// 左侧点击的值传过去
morenumRef.value.open(leftItem.value);
}
const switchv = ref(1);
// 右侧是否点击
const rightIsclick = ref(0);
function makeClick() {
rightIsclick.value++;
}
// 获取追加架次
function getjiaciconfirm(data: any) {
const dd = data.map((item: any) => {
return {
flyRecordId: item.value,
taskName: item.label,
};
});
_postApiModelMakePeriodAppend(dd);
}
// 追加架次
function _postApiModelMakePeriodAppend(dataArr: any) {
postApiModelMakePeriodAppend({
id: numObj.value.id, // 期数id
flyRecordList: dataArr,
}).then((res) => {
if (res.success) {
message.success(res.msg);
_getApiModelMakePeriodFlyRecordList(numObj.value.id);// 已选任务
photolistqsRef.value?._getApiModelMakePeriodImagePageQuery();// 期数图片
}
else {
message.error(res.msg);
}
});
}
// 查看原始数据
const photomodalRef = ref();
function lookPhoto() {
photomodalRef.value.open();
}
// 若是已完成,显示模型
function showModal(item: any) {
if (item.state === 2) {
makeTypeshow.value = 2;
nextTick(() => {
(window as any).viewer.tifModel.addModel(getFullModelFileURL(item.geoJsonPath), true, leftItem.value.altitude, 16);
});
}
else {
makeTypeshow.value = 1;
}
}
// 获取任务列表
function _getApiModelMakePeriodFlyRecordList(id: any) {
getApiModelMakePeriodFlyRecordList({
id,
}).then((res) => {
if (res.success) {
if (res.data && res.data.length) {
confirmData.value = res.data;
}
else {
confirmData.value = [];
}
// console.log('confirmData.value ', confirmData.value);
}
});
}
// 名称修改
const nameModalRef = ref();
function edit() {
nameModalRef.value?.open(leftItem.value);
}
function getname(data: any) {
// postApiModelMakeUpdate
// postApiModelMakePeriodUpdate
postApiModelMakeUpdate({
id: leftItem.value.id,
name: data.name,
}).then((res) => {
if (res.success) {
message.success(res.msg);
_getApiModelMakePageQuery(true);
// nextTick(()=>{
// listClick(listIndex.value, leftItem.value);
// setTimeout(() => {
// titClick(newNumIndex.value, newNumItem.value);
// }, 1000);
// })
}
else {
message.error(res.msg);
}
});
}
// 期数模型进度
function _getApiMediaModelLibraryGetOdmTaskInfoByModelMakePeriodId(modelMakePeriodIdv: any, index: any) {
if (modelMakePeriodIdv && modelMakePeriodIdv !== null) {
getApiMediaModelLibraryGetOdmTaskInfoByModelMakePeriodId({
modelMakePeriodId: modelMakePeriodIdv,
}).then((res) => {
if (res.success) {
if (res.data && res.data !== null) {
treeData.value[index].modelState = res.data.state;
treeData.value[index].progress = (res.data.progress)?.toFixed(2);
// console.log('treeData.value111', treeData.value);
// 如果有正常的重新刷新列表
if (res.data.state === 99) {
stop();
_getApiModelMakePageQuery(true);
}
}
}
});
}
}
function switchChange() {
(window as any).viewer.tifModel.showModel(switchv.value);
}
// watch(
// () => props.searchobj,
// () => {
// console.log('props.searchobj1111',props.searchobj)
// },
// {
// deep: true,
// immediate: true,
// },
// );
_getApiModelMakePageQuery(true);
onUnmounted(() => {
rightIsclick.value = 0;
stop();
});
defineExpose({
_getApiModelMakePageQuery,
});
</script>
<template>
<div class="h-full flex wrap-box" @click="makeClick">
<div class="flex-none w-350px py-4 px-3 left-box">
<div class="flex justify-between">
<a-input v-model:value="name" placeholder="请输入" class="flex-none w-70%" allow-clear @change="search">
<template #prefix>
<SearchOutlined />
</template>
</a-input>
<a-button v-auth="'board.achievement.add'" type="primary" @click="add">
新建模型
</a-button>
</div>
<ScrollLoad
v-if="treeData?.length" class="list-box flex-auto overflow-auto min-h-0 pb-10"
@load-more="_getApiModelMakePageQuery(false)"
>
<div
v-for="(item, index) in treeData" :key="index" class="list-box-sub"
:class="listIndex === index ? 'active' : ''" @click="listClick(index, item)"
>
<div>
<span>
{{ item.name }}
</span> <span :class="`state-${item.state}`">{{ STATE[item.state] }}</span>
</div>
<div>
{{ item.address }}
</div>
<!-- 进度新增 -->
<div class="external-wrap">
<div class="chart-rising-external">
<div
:style="{ width: `${item.progress}%` }" class="chart-rising-inside"
:class="`state${item.modelState}`"
/>
</div>
<div class="chart-rising-text">
{{ item.progress ? item.progress : 0 }}%
</div>
</div>
</div>
</ScrollLoad>
<div v-else class="no-data pt-4 pl-2">
暂无数据
</div>
</div>
<div class="flex-auto make_box">
<div class="right-top">
三维照片:
<div v-if="numList?.length" class="top-tit">
<span
v-for="(item, index) in numList" :key="index" :class="titIndex === index ? 'active' : ''"
@click="titClick(index, item)"
>第
{{ item.periods }}
期</span>
</div>
<div v-else class="no-data">
暂无期数
</div>
<a-button
v-if="treeData?.length" v-auth="'board.achievement.numadd'" type="primary" class="ml-2"
@click="addnum"
>
新增
</a-button>
</div>
<!-- 展示内容-制作添加 -->
<div v-if="makeTypeshow === 1" class="cont-box">
<div class="flex items-center">
<doubleSelect
title="选择飞行数据:" :tree-data="doubleSelectList" :right-isclick="rightIsclick" :num-obj="numObj"
@confirm="onConfirm"
/>
<div class="flex justify-between" style="flex-grow: 1;">
<div>
<a-button v-auth="'board.achievement.addzj'" type="primary" class="mr-3" @click="addmorejc">
追加架次
</a-button>
<a-button
v-if="confirmData && confirmData.length" v-auth="'board.achievement.resetadd'"
@click="addreset"
>
重新添加
</a-button>
</div>
<div>
<span class="mr-3">创建时间:{{ numObj ? numObj.createTime ? numObj.createTime : '--' : '--' }}</span>
<!-- 未完成才可以制作 -->
<a-button
v-if="numObj && numObj.state === 0 && confirmData.length" v-auth="'board.achievement.adddoing'"
type="primary" class="mr-3" @click="doing"
>
三维制作
</a-button>
</div>
</div>
</div>
<div v-if="confirmData && confirmData.length" class="flex yixuan-box">
<div class="tit">
已选数据:
</div>
<div class="flex w-full flex-wrap">
<div v-for="item, index in confirmData" :key="index" class="select-item">
<a-tooltip placement="top" :title="item?.taskName">
<div class="select-item-text">
{{ item?.taskName }}
</div>
</a-tooltip>
<div v-auth="'board.achievement.numdel'" class="img" @click="onDelete(item)">
<img src="@/assets/images/delete.png" alt="">
</div>
</div>
</div>
</div>
<div v-else class="no-data yixuan-box">
已选数据:请先选择
</div>
<!-- 图片墙 -->
<photolist ref="photolistqsRef" :model-make-period-id="numObj ? numObj.id : ''" />
</div>
<!-- 展示内容-制作完成显示 -->
<div v-if="makeTypeshow === 2" class="cont-box cont-box2">
<div class="tit-box flex">
<div class="tit-box-left">
<img src="@/assets/images/achieveDisplay/cont-right-icon.png" alt="" class="img1">
<span>
{{ leftItem ? leftItem.name ? leftItem.name : '' : '' }}
</span>
<img
v-auth="'board.achievement.edit'" src="@/assets/images/achieveDisplay/cont-right-edit.png" alt=""
class="img2" @click="edit"
>
<span class="mr-4">|</span>
<span class="detail-cls" @click="lookPhoto">
查看原始建模数据
</span>
<img src="@/assets/images/achieveDisplay/cont-right-arrow.png" alt="" class="img3">
</div>
<div class="tit-box-right">
<span class="mr-8">
制作完成时间:{{ numObj.finishTime ? numObj.finishTime : '--' }}
</span>
<span class="mr-8">
在地图上显示
<a-switch v-model:checked="switchv" :checked-value="1" :un-checked-value="0" class="ml-2" @change="switchChange" />
</span>
<span>
默认展示
<a-switch v-model:checked="switchv" :checked-value="1" :un-checked-value="0" class="ml-2" @change="switchChange" />
</span>
</div>
</div>
<!-- 完整模型 -->
<mxend />
</div>
</div>
<MapDialog ref="mapDialogRef" @confirm="_getApiModelMakePageQuery(true)" />
<!-- 追加架次 -->
<morejc ref="morejcRef" @confirm="getjiaciconfirm" />
<!-- 期数添加 -->
<morenum ref="morenumRef" @confirm="getNumList" />
<!-- 原始建模数据 -->
<photomodal ref="photomodalRef" :model-make-period-id="numObj ? numObj.id : ''" :rewn-list="confirmData" />
<!-- 修改名称 -->
<nameModal ref="nameModalRef" @confirmname="getname" />
</div>
</template>
<style lang="less" scoped>
.wrap-box {
border: 1px solid #456b9f;
.left-box {
border-right: 1px solid #456b9f;
.list-box {
// overflow-y: auto;
// height: calc(100% - 50px);
height: 670px;
margin-top: 12px;
.list-box-sub {
padding: 8px;
margin-bottom: 10px;
font-family: PingFangSC-Regular;
font-size: 15px;
font-weight: 400;
color: #f7f7f7;
cursor: pointer;
&:hover {
background: #0c2e52;
}
&.active {
background: #0c2e52;
}
div:nth-of-type(1) {
display: flex;
line-height: 21px;
span:nth-of-type(1) {
display: inline-block;
width: 260px;
}
span:nth-of-type(2) {
display: inline-block;
width: 55px;
// height: 16px;
margin-top: 2px;
margin-left: 8px;
font-size: 12px;
line-height: 16px;
color: #ffffff;
text-align: center;
text-align: center;
// background: #007f4f59;
border-radius: 3px;
// box-shadow: inset -3px -3px 12px 0 #03865cc7;
}
.state--1 {
background: red;
box-shadow: inset -3px -3px 12px 0 red;
}
.state-0 {
background: #d86605;
box-shadow: inset -3px -3px 12px 0 #d86605;
}
.state-1 {
background: #fff70459;
box-shadow: inset -3px -3px 12px 0 #f1e90659;
}
.state-2 {
background: #007f4f59;
box-shadow: inset -3px -3px 12px 0 #007f4f59;
}
}
div:nth-of-type(2) {
margin-top: 5px;
font-size: 13px;
color: #ffffffb3;
}
// .chart-rising-title {
// width: 62px;
// text-align: right;
// }
// .chart-rising-title,
// .chart-rising-text {
// margin: 0 5px;
// font-size: 8px;
// font-weight: 400;
// color: rgba(255, 255, 255, 0.7);
// }
.external-wrap {
display: flex;
align-items: center;
margin-top: 5px;
.chart-rising-external {
display: flex;
align-items: center;
width: 272px;
height: 4px;
background: #096fff4d;
border-radius: 11px;
.chart-rising-inside {
height: 4px;
background: #1790ff;
border-radius: 11px;
&.state99 {
background: #59c06c;
}
&.state-1 {
background: red;
}
&.state-2 {
background: red;
}
&.state-3 {
background: red;
}
}
}
.chart-rising-text {
margin-top: 0;
margin-left: 8px;
font-family: PingFangSC-Regular;
font-size: 12px;
font-weight: 400;
color: #ffffff80;
text-align: right;
}
}
}
}
}
.make_box {
.right-top {
display: flex;
align-items: center;
height: 48px;
padding: 0 16px;
font-family: PingFangSC-Medium;
font-size: 15px;
font-weight: 500;
color: #ffffff;
border-bottom: 1px solid #456b9f;
.top-tit {
display: flex;
align-items: center;
height: 100%;
margin-left: 26px;
span {
display: flex;
align-items: center;
height: 100%;
margin-right: 43px;
font-family: PingFangSC-Regular;
font-size: 15px;
font-weight: 400;
color: #ffffffb3;
text-align: center;
cursor: pointer;
// &:hover {
// color: #fff;
// border-bottom: 2px solid #2f6bff;
// }
&.active {
color: #fff;
border-bottom: 2px solid #2f6bff;
}
}
}
}
.cont-box {
.yixuan-box {
display: flex;
// flex-wrap: wrap;
// align-items: center;
// height: 32px;
padding: 0 16px;
.tit {
width: 80px;
}
.select-item {
display: flex;
align-items: center;
width: 218px;
height: 28px;
margin-right: 12px;
margin-bottom: 10px;
line-height: 32px;
cursor: pointer;
background: #173d66;
border: 1px solid #446d9e00;
border-radius: 4px;
.select-item-text {
width: 185px;
padding: 3px 8px;
overflow: hidden;
text-overflow: ellipsis;
white-space: nowrap;
cursor: pointer;
}
.img {
// padding-left: 15px;
padding: 0 6px;
margin-top: 4px;
cursor: pointer;
img {
width: 15px;
height: 15px;
}
}
}
}
&.cont-box2 {
align-items: center;
padding: 16px;
.tit-box {
display: flex;
align-items: center;
justify-content: space-between;
height: 32px;
line-height: 32px;
.tit-box-left {
display: flex;
align-items: center;
.img1 {
width: 33px;
height: 33px;
margin-right: 8px;
}
.img2 {
width: 16px;
height: 16px;
margin-right: 16px;
margin-left: 4px;
cursor: pointer;
}
.img3 {
width: 16px;
height: 16px;
margin-left: 4px;
}
.detail-cls {
font-family: PingFangSC-Regular;
font-size: 15px;
font-weight: 400;
color: #1790ff;
cursor: pointer;
}
}
.tit-box-right {
display: flex;
align-items: center;
span {
display: flex;
align-items: center;
}
}
}
}
}
}
}
</style>