Merge branch 'main' of http://yhm.blue:9080/ddtj/ts
@ -11,6 +11,8 @@
|
||||
"lint": "eslint . --ext .vue,.js,.jsx,.cjs,.mjs,.ts,.tsx,.cts,.mts --fix --ignore-path .gitignore"
|
||||
},
|
||||
"dependencies": {
|
||||
"@antv/x6": "^2.18.1",
|
||||
"@antv/x6-vue-shape": "^2.1.2",
|
||||
"@turf/turf": "^7.1.0",
|
||||
"@visactor/vtable": "^1.13.2",
|
||||
"@visactor/vtable-gantt": "^1.13.2",
|
||||
@ -24,6 +26,7 @@
|
||||
"chroma-js": "^3.1.2",
|
||||
"dayjs": "^1.11.13",
|
||||
"echarts": "^5.5.1",
|
||||
"elkjs": "^0.10.0",
|
||||
"es-toolkit": "^1.32.0",
|
||||
"lodash": "^4.17.21",
|
||||
"maplibre-gl": "^5.0.1",
|
||||
|
BIN
public/images/topology/a.png
Normal file
After Width: | Height: | Size: 2.7 KiB |
BIN
public/images/topology/arrow-bottom.png
Normal file
After Width: | Height: | Size: 512 B |
BIN
public/images/topology/arrow-left.png
Normal file
After Width: | Height: | Size: 553 B |
BIN
public/images/topology/com.png
Normal file
After Width: | Height: | Size: 3.0 KiB |
BIN
public/images/topology/cpu.png
Normal file
After Width: | Height: | Size: 4.9 KiB |
BIN
public/images/topology/duankai.png
Normal file
After Width: | Height: | Size: 918 B |
BIN
public/images/topology/fwq.png
Normal file
After Width: | Height: | Size: 3.1 KiB |
BIN
public/images/topology/hezi.png
Normal file
After Width: | Height: | Size: 5.9 KiB |
BIN
public/images/topology/xinhao.png
Normal file
After Width: | Height: | Size: 1.7 KiB |
BIN
public/images/topology/yp.png
Normal file
After Width: | Height: | Size: 4.0 KiB |
BIN
public/images/topology/zhuji.png
Normal file
After Width: | Height: | Size: 6.6 KiB |
BIN
public/images/影像1.jpg
Normal file
After Width: | Height: | Size: 558 KiB |
1512
public/json/topology.json
Normal file
@ -5,6 +5,8 @@ import { themeOverrides } from '@/styles/naiveConfig'
|
||||
import { darkTheme, NMessageProvider, zhCN, dateZhCN } from 'naive-ui'
|
||||
import Message from '@/components/Message/index.vue'
|
||||
import Notification from '@/components/Notification/index.vue'
|
||||
import Dialog from '@/components/Dialog/index.vue'
|
||||
|
||||
|
||||
import { useEntity } from '@/hooks/entity'
|
||||
|
||||
@ -44,7 +46,7 @@ const { baseMap, mubiaoMap, satelliteMap } = useEntity()
|
||||
<n-notification-provider placement="bottom-left" :max="10">
|
||||
<notification />
|
||||
</n-notification-provider>
|
||||
<n-dialog-provider> <router-view /></n-dialog-provider>
|
||||
<n-dialog-provider> <Dialog /> <router-view /></n-dialog-provider>
|
||||
<!-- </n-message-provider> -->
|
||||
<!-- </n-theme-editor> -->
|
||||
</n-config-provider>
|
||||
|
BIN
src/assets/image/topology/cpuicon.png
Normal file
After Width: | Height: | Size: 4.3 KiB |
BIN
src/assets/image/topology/neicun.png
Normal file
After Width: | Height: | Size: 3.6 KiB |
BIN
src/assets/image/topology/topology_bg.png
Normal file
After Width: | Height: | Size: 4.8 KiB |
BIN
src/assets/image/topology/ypkj.png
Normal file
After Width: | Height: | Size: 4.7 KiB |
@ -88,7 +88,7 @@ function distanceMeasure() {
|
||||
polyline: {
|
||||
show: true,
|
||||
positions: [],
|
||||
material: Cesium.Color.GOLD,
|
||||
material: Cesium.Color.RED,
|
||||
width: 2,
|
||||
clampToGround: true,
|
||||
},
|
||||
@ -174,15 +174,15 @@ function distanceMeasure() {
|
||||
position: positions[positions.length - 1],
|
||||
point: {
|
||||
pixelSize: 5,
|
||||
color: Cesium.Color.RED,
|
||||
color: Cesium.Color.WHITE,
|
||||
outlineColor: Cesium.Color.WHITE,
|
||||
outlineWidth: 2,
|
||||
// disableDepthTestDistance: Number.POSITIVE_INFINITY
|
||||
},
|
||||
label: {
|
||||
text: textDistance,
|
||||
font: '14px sans-serif',
|
||||
fillColor: Cesium.Color.GOLD,
|
||||
font: '16px sans-serif',
|
||||
fillColor: Cesium.Color.RED,
|
||||
style: Cesium.LabelStyle.FILL_AND_OUTLINE,
|
||||
outlineWidth: 2,
|
||||
verticalOrigin: Cesium.VerticalOrigin.BOTTOM,
|
||||
@ -237,7 +237,7 @@ function angleMeasure() {
|
||||
position: cartesian,
|
||||
point: {
|
||||
pixelSize: 3,
|
||||
color: Cesium.Color.RED,
|
||||
color: Cesium.Color.WHITE,
|
||||
outlineColor: Cesium.Color.WHITE,
|
||||
outlineWidth: 2,
|
||||
heightReference: Cesium.HeightReference.CLAMP_TO_GROUND,
|
||||
@ -353,7 +353,7 @@ function angleMeasure() {
|
||||
// scaleByDistance: new Cesium.NearFarScalar(7000000, 1.0, 18000000, 0.4),
|
||||
// translucencyByDistance: new Cesium.NearFarScalar(1.5e2, 2.0, 1.5e5, 0),
|
||||
font: '14px sans-serif',
|
||||
fillColor: Cesium.Color.GOLD,
|
||||
fillColor: Cesium.Color.RED,
|
||||
style: Cesium.LabelStyle.FILL_AND_OUTLINE,
|
||||
outlineWidth: 2,
|
||||
pixelOffset: new Cesium.Cartesian2(0, -20),
|
||||
|
@ -46,6 +46,11 @@ const router = createRouter({
|
||||
name: 'Test',
|
||||
component: () => import('@/views/Test/index.vue'),
|
||||
},
|
||||
{
|
||||
path: '/TopologyMap',
|
||||
name: 'TopologyMap',
|
||||
component: () => import('@/views/TopologyMap/index.vue'),
|
||||
},
|
||||
],
|
||||
})
|
||||
|
||||
|
71
src/views/BaseMB/components/HisImages/components/JImage.jsx
Normal file
@ -0,0 +1,71 @@
|
||||
import { NImage } from 'naive-ui'
|
||||
import WZoom from 'vanilla-js-wheel-zoom/dist/wheel-zoom.min.js'
|
||||
|
||||
export default defineComponent({
|
||||
props: {
|
||||
imageList: {
|
||||
type: Array,
|
||||
default: () => [],
|
||||
},
|
||||
},
|
||||
setup(props) {
|
||||
// const { images, activeIndex } = toRefs(props)
|
||||
|
||||
watch(
|
||||
() => props.imageList,
|
||||
() => {
|
||||
console.log('-------',props.imageList)
|
||||
if (props.imageList.length > 1) {
|
||||
nextTick(() => {
|
||||
props.imageList.map(image => {
|
||||
const imageElement = document
|
||||
.getElementById(`image-${image.id}`)
|
||||
.querySelector('img')
|
||||
|
||||
const wz = WZoom.create(`#image-${image.id}`, {
|
||||
type: 'html',
|
||||
maxScale: 3,
|
||||
minScale: 1,
|
||||
// zoomOnDoubleClick: true,
|
||||
width: imageElement.naturalWidth,
|
||||
height: imageElement.naturalHeight,
|
||||
})
|
||||
})
|
||||
})
|
||||
}
|
||||
}
|
||||
)
|
||||
return () => (
|
||||
<div class="l-image-container flex h-full w-full gap-4">
|
||||
{props.imageList.map(image => (
|
||||
<div class="flex h-full flex-1 flex-col gap-2">
|
||||
<div>{image.createTime}</div>
|
||||
<div class="h-0 flex-1 overflow-hidden">
|
||||
{props.imageList.length > 1 ? (
|
||||
<div
|
||||
id={`image-${image.id}`}
|
||||
class="flex h-full w-full cursor-grab items-center justify-center"
|
||||
>
|
||||
<img
|
||||
class="w-full"
|
||||
src={image.imgPath}
|
||||
draggable="false"
|
||||
// alt="image"
|
||||
/>
|
||||
</div>
|
||||
) : (
|
||||
<NImage
|
||||
class="flex justify-center object-contain w-h-full"
|
||||
object-fit="contain"
|
||||
src={image.imgPath}
|
||||
/>
|
||||
)}
|
||||
</div>
|
||||
|
||||
<div class="line-clamp-3 pb-4">{image.detailContent}</div>
|
||||
</div>
|
||||
))}
|
||||
</div>
|
||||
)
|
||||
},
|
||||
})
|
@ -14,6 +14,7 @@ export default defineComponent({
|
||||
watch(
|
||||
() => props.imageList,
|
||||
() => {
|
||||
console.log(props.imageList,'---imageList--')
|
||||
if (props.imageList.length > 1) {
|
||||
nextTick(() => {
|
||||
props.imageList.map(image => {
|
||||
@ -53,11 +54,14 @@ export default defineComponent({
|
||||
/>
|
||||
</div>
|
||||
) : (
|
||||
<NImage
|
||||
class="flex justify-center object-contain w-h-full"
|
||||
<div class="flex object-contain w-h-full">
|
||||
<NImage
|
||||
object-fit="contain"
|
||||
src={image.imgPath}
|
||||
/>
|
||||
<h2>雨辰接口数据1233</h2>
|
||||
</div>
|
||||
|
||||
)}
|
||||
</div>
|
||||
|
||||
|
209
src/views/BaseMB/components/HisImages/components/imageRoller.vue
Normal file
@ -0,0 +1,209 @@
|
||||
<template>
|
||||
<div
|
||||
class="picBox"
|
||||
@mouseenter="isHover = true"
|
||||
@mouseleave="isHover = false"
|
||||
>
|
||||
<div id="mousemoveBox">
|
||||
<div id="line">
|
||||
<!-- <img
|
||||
v-show="isHover"
|
||||
id="move"
|
||||
src="../../assets/img/area.png"
|
||||
alt=""
|
||||
/> -->
|
||||
</div>
|
||||
</div>
|
||||
<div id="before">
|
||||
<img id="beforeImg" :src="path + imgList[0]" alt="" />
|
||||
</div>
|
||||
<div id="after">
|
||||
<img id="afterImg" :src="path + imgList[1]" alt="" />
|
||||
</div>
|
||||
<div id="text">
|
||||
<h2 id="h2">12312312雨辰接口数据</h2>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script lang="ts">
|
||||
// @ts-nocheck
|
||||
import {
|
||||
defineComponent,
|
||||
reactive,
|
||||
toRefs,
|
||||
onMounted,
|
||||
onUnmounted,
|
||||
ref,
|
||||
} from "vue";
|
||||
import { useRoute, useRouter } from "vue-router";
|
||||
|
||||
export default defineComponent({
|
||||
props: {
|
||||
imgList: {
|
||||
type: Object || Array,
|
||||
},
|
||||
path: {
|
||||
type: String,
|
||||
default: "",
|
||||
},
|
||||
},
|
||||
setup(props, { emit }) {
|
||||
const route = useRoute();
|
||||
const router = useRouter();
|
||||
const contentWidth = ref("");
|
||||
const contentHeight = ref("");
|
||||
const imgWidth = ref(0);
|
||||
const isHover = ref(true);
|
||||
|
||||
const state = reactive({});
|
||||
|
||||
onMounted(() => {
|
||||
const picBox = document.querySelector(".picBox");
|
||||
contentWidth.value = picBox.offsetWidth + "px";
|
||||
contentHeight.value = picBox.offsetHeight + "px";
|
||||
contrastImg(props.imgIdList);
|
||||
});
|
||||
let line = null; //domLine
|
||||
let move = null; //domMove
|
||||
let after = null; //domAfter
|
||||
let before = null; //domBefore
|
||||
let picBox = null; //domPicBox
|
||||
let afterImg = null; //domAfterImg
|
||||
let beforeImg = null; //domBeforeImg
|
||||
let x = 0; //鼠标在页面中的位置
|
||||
let afterX = 0; //after在页面中的位置
|
||||
let picBoxWidth = 0; //picBox的宽度
|
||||
let beforeWidth = 0; //before的宽度
|
||||
let afterWidth = 0; //after的宽度
|
||||
let moveFlag = false; //鼠标是否抬起
|
||||
let lineLeft = 0; //line在页面中的位置
|
||||
let picBoxX = 0; //picBox在页面中的位置
|
||||
|
||||
const beforeMove = (beforeWidth) => {
|
||||
before.style.width = beforeWidth + "px";
|
||||
};
|
||||
const afterMove = (mousemoveDistance) => {
|
||||
after.style.width = afterWidth - mousemoveDistance + "px";
|
||||
after.style.left = afterX + mousemoveDistance + "px";
|
||||
afterImg.style.left = -(afterX + mousemoveDistance) + "px";
|
||||
};
|
||||
const mousedown = (e) => {
|
||||
picBoxX = picBox.getBoundingClientRect().left;
|
||||
moveFlag = false;
|
||||
x = e.pageX;
|
||||
beforeWidth = before.offsetWidth;
|
||||
afterWidth = after.offsetWidth;
|
||||
picBoxWidth = picBox.offsetWidth;
|
||||
afterX = after.offsetLeft;
|
||||
lineLeft = line.offsetLeft;
|
||||
line.addEventListener("mousemove", mousemove);
|
||||
};
|
||||
const mousemove = (e) => {
|
||||
if (moveFlag) return;
|
||||
if (e.pageX <= picBoxX || e.pageX >= picBoxX + picBoxWidth) return;
|
||||
const mousemoveDistance = e.pageX - x;
|
||||
line.style.left = mousemoveDistance + lineLeft + "px";
|
||||
// move.style.left = mousemoveDistance + lineLeft + 34 + "px";
|
||||
const beforeMoveWidth = beforeWidth + mousemoveDistance;
|
||||
beforeMove(beforeMoveWidth);
|
||||
afterMove(mousemoveDistance);
|
||||
};
|
||||
const mouseup = () => {
|
||||
moveFlag = true;
|
||||
};
|
||||
const contrastImg = (e) => {
|
||||
line = document.getElementById("line");
|
||||
// move = document.getElementById("move");
|
||||
after = document.getElementById("after");
|
||||
before = document.getElementById("before");
|
||||
picBox = document.querySelector(".picBox");
|
||||
afterImg = document.getElementById("afterImg");
|
||||
beforeImg = document.getElementById("beforeImg");
|
||||
line.addEventListener("mousedown", mousedown);
|
||||
document.addEventListener("mouseup", mouseup);
|
||||
};
|
||||
|
||||
onUnmounted(() => {
|
||||
line.removeEventListener("mousemove", mousemove);
|
||||
line.removeEventListener("mousedown", mousedown);
|
||||
document.addEventListener("mouseup", mouseup);
|
||||
});
|
||||
|
||||
return {
|
||||
...toRefs(state),
|
||||
isHover,
|
||||
};
|
||||
},
|
||||
});
|
||||
</script>
|
||||
|
||||
<style lang="scss" scoped>
|
||||
.picBox {
|
||||
position: relative;
|
||||
font-size: 0;
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
#mousemoveBox {
|
||||
position: absolute;
|
||||
width: 100px;
|
||||
height: 100%;
|
||||
left: calc(50% - 30px);
|
||||
z-index: 4;
|
||||
#line {
|
||||
position: absolute;
|
||||
width: 60px;
|
||||
height: 30px;
|
||||
top: calc(50% - 15px);
|
||||
z-index: 5;
|
||||
background: rgba(255, 255, 255, 0.4);
|
||||
}
|
||||
#move {
|
||||
position: absolute;
|
||||
left: 34px;
|
||||
width: 32px;
|
||||
top: calc(50% - 15px);
|
||||
z-index: 5;
|
||||
}
|
||||
}
|
||||
#before {
|
||||
position: absolute;
|
||||
width: 50%;
|
||||
height: 100%;
|
||||
overflow: hidden;
|
||||
#beforeImg {
|
||||
position: absolute;
|
||||
width: v-bind(contentWidth);
|
||||
height: 100%;
|
||||
}
|
||||
}
|
||||
#after {
|
||||
position: absolute;
|
||||
left: 50%;
|
||||
width: 50%;
|
||||
height: 100%;
|
||||
overflow: hidden;
|
||||
#afterImg {
|
||||
position: absolute;
|
||||
left: -100%;
|
||||
width: v-bind(contentWidth);
|
||||
height: 100%;
|
||||
}
|
||||
}
|
||||
#text {
|
||||
position: absolute;
|
||||
left: 50%;
|
||||
width: 50%;
|
||||
height: 100%;
|
||||
overflow: hidden;
|
||||
#h2 {
|
||||
position: absolute;
|
||||
// left: -100%;
|
||||
width: 50%;
|
||||
height: 100%;
|
||||
font-size: 16px;
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
</style>
|
@ -0,0 +1,51 @@
|
||||
<template>
|
||||
<div>
|
||||
<n-split
|
||||
direction="horizontal"
|
||||
style="height: 500px;width: 50%;"
|
||||
@drag-start="handleOnDragStart"
|
||||
@drag-move="handleOnDragMove"
|
||||
@drag-end="handleOnDragEnd"
|
||||
>
|
||||
<template #1>
|
||||
<img id="beforeImg" :src="'/images/影像.jpg'" alt="" style="width: 100%; height: 100%; object-fit: cover;"/>
|
||||
</template>
|
||||
<template #2>
|
||||
<img id="beforeImg" :src="'/images/影像.jpg'" alt="" style="width: 100%; height: 100%; object-fit: cover;" />
|
||||
</template>
|
||||
</n-split>
|
||||
</div>
|
||||
|
||||
</template>
|
||||
|
||||
<script lang="ts">
|
||||
// @ts-nocheck
|
||||
import {
|
||||
defineComponent,
|
||||
reactive,
|
||||
toRefs,
|
||||
onMounted,
|
||||
onUnmounted,
|
||||
ref,
|
||||
} from "vue";
|
||||
import type { Nsplit } from 'naive-ui'
|
||||
|
||||
import { useRoute, useRouter } from "vue-router";
|
||||
|
||||
export default defineComponent({
|
||||
setup() {
|
||||
|
||||
return {
|
||||
handleOnDragStart: () => {
|
||||
console.log("开始滚动");
|
||||
},
|
||||
handleOnDragMove: () => {
|
||||
console.log("滚动中");
|
||||
},
|
||||
handleOnDragEnd: () => {
|
||||
console.log("滚动结束");
|
||||
}
|
||||
};
|
||||
}
|
||||
});
|
||||
</script>
|
@ -5,6 +5,10 @@ import { ImageOutline } from '@vicons/ionicons5'
|
||||
import { useHisImage } from './hooks/hisImage'
|
||||
import Panel from '@/components/Panel/index.vue'
|
||||
import LImage from './components/LImage'
|
||||
import JImage from './components/JImage'
|
||||
import imageRoller from './components/imageRoller.vue'
|
||||
|
||||
|
||||
|
||||
const { sheshiData, showOrHideHisImage, getHisImages } = useHisImage()
|
||||
|
||||
@ -31,7 +35,7 @@ const rangeShortcuts = {
|
||||
return [cur - 365 * 24 * 60 * 60 * 1000, cur]
|
||||
},
|
||||
}
|
||||
const showPreview = ref(false)
|
||||
const showPreview = ref(true)
|
||||
const previewIndex = ref(0)
|
||||
const selectImg = (index: number) => {
|
||||
// show()
|
||||
@ -47,6 +51,7 @@ const selectImg = (index: number) => {
|
||||
}
|
||||
|
||||
const imageList = ref([])
|
||||
const isJ=ref(false);
|
||||
|
||||
const scrollRef = ref<HTMLElement | null>(null)
|
||||
|
||||
@ -69,6 +74,13 @@ const getImage = async () => {
|
||||
})
|
||||
// console.log(imageList.value, 'imageList')
|
||||
}
|
||||
const btnText=ref('卷帘对比');
|
||||
const changeShow= ()=>{
|
||||
btnText.value=isJ.value ? '卷帘对比' : '取消卷帘对比';
|
||||
isJ.value= !isJ.value;
|
||||
console.log('-------isJ',isJ.value)
|
||||
|
||||
}
|
||||
|
||||
const checkedImage = ref<null | string[]>(null)
|
||||
|
||||
@ -118,10 +130,15 @@ const largeImageList = computed(() => {
|
||||
:closeClick="showOrHideHisImage"
|
||||
>
|
||||
<div class="flex flex-col w-h-full">
|
||||
<div>
|
||||
<n-button type="primary" @click="changeShow" v-if="isCompare">{{ btnText }}</n-button>
|
||||
</div>
|
||||
<div class="large-container">
|
||||
<l-image :imageList="largeImageList" />
|
||||
|
||||
<!-- </vue-viewer> -->
|
||||
<!-- <h1 v-if="isJ" >12345</h1> -->
|
||||
<imageRoller :imgList="['/images/影像.jpg','/images/影像.jpg']" v-if="isJ"></imageRoller>
|
||||
<l-image :imageList="largeImageList" v-else key="l-image" />
|
||||
<!-- <j-image :imageList="largeImageList" v-else key="j-image" /> -->
|
||||
|
||||
</div>
|
||||
<div ref="scrollRef" class="flex h-[178px] flex-col">
|
||||
<div class="flex gap-2">
|
||||
|
@ -74,12 +74,23 @@ function adjustTime(targetValue) {
|
||||
}
|
||||
function getAdjustedTime(targetValue) {
|
||||
const date = adjustTime(targetValue);
|
||||
|
||||
|
||||
// 手动提取年月日时分秒
|
||||
const year = date.getFullYear();
|
||||
const month = date.getMonth() + 1; // 月份从0开始
|
||||
const day = date.getDate();
|
||||
const hours = date.getHours().toString().padStart(2, '0');
|
||||
const minutes = date.getMinutes().toString().padStart(2, '0');
|
||||
const seconds = date.getSeconds().toString().padStart(2, '0');
|
||||
|
||||
// 拼接为带大间隔的格式
|
||||
return `${year} / ${month} / ${day} ${hours}:${minutes}:${seconds}`;
|
||||
// 格式化为本地时间字符串
|
||||
return date.toLocaleString('zh-CN', {
|
||||
timeZone: 'Asia/Shanghai', // 强制使用中文时区显示
|
||||
hour12: false
|
||||
});
|
||||
// return date.toLocaleString('zh-CN', {
|
||||
// timeZone: 'Asia/Shanghai', // 强制使用中文时区显示
|
||||
// hour12: false
|
||||
// });
|
||||
}
|
||||
|
||||
// 使用示例
|
||||
|
@ -63,7 +63,7 @@ export default defineComponent({
|
||||
})
|
||||
return () => (
|
||||
<div class="relative">
|
||||
<NPopover
|
||||
{/* <NPopover
|
||||
trigger="hover"
|
||||
placement="bottom"
|
||||
v-slots={{
|
||||
@ -121,7 +121,7 @@ export default defineComponent({
|
||||
</div>
|
||||
))}
|
||||
</div>
|
||||
) : null}
|
||||
) : null} */}
|
||||
</div>
|
||||
)
|
||||
},
|
||||
|
@ -174,8 +174,8 @@ export default defineComponent({
|
||||
>
|
||||
<span>地图样式选择</span>
|
||||
</NPopover> */}
|
||||
<BaseMap />
|
||||
<HomeView />
|
||||
<BaseMap />
|
||||
</div>
|
||||
)
|
||||
},
|
||||
|
@ -6,10 +6,13 @@ import {
|
||||
NDatePicker,
|
||||
NUpload,
|
||||
NSwitch,
|
||||
NSelect,
|
||||
} from 'naive-ui'
|
||||
import ModalCom from '@/components/Modal/index.vue'
|
||||
import { useEvent } from '../hooks'
|
||||
import { addSimp, updateSimp, uploadImage } from '@/api/Gantt'
|
||||
import { addSimp, updateSimp, uploadImage, getSimpList } from '@/api/Gantt'
|
||||
import { onBeforeMount, nextTick } from 'vue'
|
||||
|
||||
export default defineComponent({
|
||||
// props: {
|
||||
// show: {
|
||||
@ -42,6 +45,7 @@ export default defineComponent({
|
||||
const formRef = ref(null)
|
||||
async function sure(e) {
|
||||
e.preventDefault()
|
||||
mainEventData.value.status = mainEventData.value.status ? 2 : 1
|
||||
const data = {
|
||||
...mainEventData.value,
|
||||
targetId: targetId.value,
|
||||
@ -78,9 +82,9 @@ export default defineComponent({
|
||||
}
|
||||
}
|
||||
watch(
|
||||
() => mainEventData.value.eventType,
|
||||
() => mainEventData.value.status,
|
||||
val => {
|
||||
console.log(val, '------eventType')
|
||||
console.log(val, '------status')
|
||||
},
|
||||
{
|
||||
immediate: true,
|
||||
@ -109,10 +113,41 @@ export default defineComponent({
|
||||
}
|
||||
)
|
||||
|
||||
async function getSimpListData() {
|
||||
const res = await getSimpList()
|
||||
ddList.value = res.data.list
|
||||
targetId.value = res.data.list[0].id
|
||||
}
|
||||
onBeforeMount(() => {
|
||||
nextTick(async () => {
|
||||
await getSimpListData()
|
||||
})
|
||||
})
|
||||
|
||||
// const ddList = Array.from({ length: 8 }, (_, i) => ({
|
||||
// label: `DD-${i + 1}`,
|
||||
// value: `DD-${i + 1}`,
|
||||
// }))
|
||||
const ddList = ref([])
|
||||
|
||||
const timeRange = ref(null)
|
||||
const uploadImg = ref([])
|
||||
// const desc = ref ()
|
||||
|
||||
const railStyle = ({ focused, checked }) => {
|
||||
const style = {}
|
||||
if (checked) {
|
||||
style.background = '#008000'
|
||||
if (focused) {
|
||||
style.boxShadow = '0 0 0 2px #00800040'
|
||||
}
|
||||
} else {
|
||||
style.background = '#2080f0'
|
||||
if (focused) {
|
||||
style.boxShadow = '0 0 0 2px #2080f040'
|
||||
}
|
||||
}
|
||||
return style
|
||||
}
|
||||
return () => (
|
||||
<ModalCom
|
||||
v-model:show={showMainEvent.value}
|
||||
@ -126,6 +161,15 @@ export default defineComponent({
|
||||
label-width="auto"
|
||||
rules={mainEventRules}
|
||||
>
|
||||
<NFormItem label="类型" path="type">
|
||||
<NSelect
|
||||
class="w-[200px]"
|
||||
v-model:value={targetId.value}
|
||||
options={ddList.value}
|
||||
label-field="name"
|
||||
value-field="id"
|
||||
></NSelect>
|
||||
</NFormItem>
|
||||
<NFormItem label="事件名称" path="name">
|
||||
<NInput v-model:value={mainEventData.value.name} />
|
||||
</NFormItem>
|
||||
@ -142,24 +186,30 @@ export default defineComponent({
|
||||
type="textarea"
|
||||
/>
|
||||
</NFormItem>
|
||||
<NFormItem label="事件类型" path="eventType">
|
||||
<NFormItem label="事件类型" path="status">
|
||||
<NSwitch
|
||||
v-model:value={mainEventData.value.eventType}
|
||||
railStyle={railStyle}
|
||||
v-model:value={mainEventData.value.status}
|
||||
checked-value={true}
|
||||
unchecked-value={false}
|
||||
default-value={true}
|
||||
default-value={false}
|
||||
v-slots={{
|
||||
checked: () => '已发生',
|
||||
unchecked: () => '未发生',
|
||||
checked: () => '未发生',
|
||||
unchecked: () => '已发生',
|
||||
}}
|
||||
></NSwitch>
|
||||
</NFormItem>
|
||||
{!mainEventData.value.eventType ? (
|
||||
<NFormItem label="导弹种类" path="category">
|
||||
<NInput
|
||||
v-model:value={mainEventData.value.category}
|
||||
type="text"
|
||||
/>
|
||||
{mainEventData.value.status ? (
|
||||
<NFormItem label="数据来源" path="source">
|
||||
<NInput v-model:value={mainEventData.value.source} type="text" />
|
||||
</NFormItem>
|
||||
) : null}
|
||||
{mainEventData.value.status ? (
|
||||
<NFormItem label="数据发布" path="publishTime">
|
||||
<NDatePicker
|
||||
v-model:value={mainEventData.value.publishTime}
|
||||
type="date"
|
||||
></NDatePicker>
|
||||
</NFormItem>
|
||||
) : null}
|
||||
|
||||
|
@ -44,22 +44,27 @@ export default defineComponent({
|
||||
const formRef = ref(null)
|
||||
async function sure(e) {
|
||||
e.preventDefault()
|
||||
|
||||
delete eventData.value.eventType
|
||||
delete eventData.value.source
|
||||
delete eventData.value.publishTime
|
||||
delete eventData.value.twoType
|
||||
console.log('eventData.value-------', eventData.value)
|
||||
const data = {
|
||||
// id: eventData.value.id ?? null,
|
||||
// activityId: oneClassData.value.activityId ?? null,
|
||||
// name: eventData.value.name,
|
||||
activityId: oneClassData.value?.pid ?? null,
|
||||
activityId: oneClassData.value?.id ?? null,
|
||||
oneType: oneClassData.value?.id,
|
||||
...eventData.value,
|
||||
// twoType: twoTypeId.value,
|
||||
fileUrl: imageValue.value,
|
||||
startTime: eventData.value.timeRange
|
||||
? eventData.value.timeRange[0]
|
||||
: null,
|
||||
endTime: eventData.value.timeRange
|
||||
? eventData.value.timeRange[1]
|
||||
: null,
|
||||
startTime: eventData.value.timeRange,
|
||||
endTime: eventData.value.timeRange,
|
||||
// ? eventData.value.timeRange[0]
|
||||
// : null,
|
||||
// endTime: eventData.value.timeRange
|
||||
// ? eventData.value.timeRange[1]
|
||||
// : null,
|
||||
}
|
||||
|
||||
// eventData.value.startTime = data.startTime
|
||||
@ -67,11 +72,7 @@ export default defineComponent({
|
||||
// console.log(erros, eventData, '')
|
||||
|
||||
// if (!erros) {
|
||||
if (
|
||||
eventData.value.name &&
|
||||
eventData.value.timeRange &&
|
||||
eventData.value.twoType
|
||||
) {
|
||||
if (eventData.value.name && eventData.value.timeRange) {
|
||||
const res = eventData.value.id
|
||||
? await updateSon(data)
|
||||
: await addSon(data)
|
||||
@ -133,14 +134,14 @@ export default defineComponent({
|
||||
label-width="auto"
|
||||
rules={subEventRules}
|
||||
>
|
||||
<NFormItem label="二级分类" path="twoType">
|
||||
{/* <NFormItem label="二级分类" path="twoType">
|
||||
<NSelect
|
||||
v-model:value={eventData.value.twoType}
|
||||
options={sonOptions.value}
|
||||
label-field="name"
|
||||
value-field="id"
|
||||
></NSelect>
|
||||
</NFormItem>
|
||||
</NFormItem> */}
|
||||
{/* <NFormItem label="步骤">
|
||||
<NSelect v-model:value={value2.value}></NSelect>
|
||||
</NFormItem>
|
||||
@ -150,13 +151,21 @@ export default defineComponent({
|
||||
<NFormItem label="事件名称" path="name">
|
||||
<NInput v-model:value={eventData.value.name} />
|
||||
</NFormItem>
|
||||
<NFormItem label="事件时间" path="timeRange">
|
||||
{/* <NFormItem label="事件时间" path="timeRange">
|
||||
<NDatePicker
|
||||
// v-model:value={timeRange.value}
|
||||
v-model:value={eventData.value.timeRange}
|
||||
type="datetimerange"
|
||||
clearable
|
||||
/>
|
||||
</NFormItem> */}
|
||||
<NFormItem label="事件时间" path="timeRange">
|
||||
<NDatePicker
|
||||
// v-model:value={timeRange.value}
|
||||
v-model:value={eventData.value.timeRange}
|
||||
type="datetime"
|
||||
clearable
|
||||
/>
|
||||
</NFormItem>
|
||||
<NFormItem label="装备型号" path="equipModel">
|
||||
<NInput v-model:value={eventData.value.equipModel} />
|
||||
|
@ -2,16 +2,26 @@ import { getSimpTreeList, getTwoClass } from '@/api/Gantt'
|
||||
|
||||
const subEventRules = {
|
||||
name: { required: true, message: '请输入名称', trigger: ['blur', 'input'] },
|
||||
// timeRange: {
|
||||
// required: true,
|
||||
// message: '请选择时间',
|
||||
// trigger: ['blur', 'input'],
|
||||
// },
|
||||
timeRange: {
|
||||
required: true,
|
||||
message: '请选择时间',
|
||||
trigger: ['blur', 'input'],
|
||||
},
|
||||
twoType: {
|
||||
required: true,
|
||||
message: '请选择二级分类',
|
||||
trigger: ['blur', 'change'],
|
||||
validator(rule, value) {
|
||||
if (!value) {
|
||||
return new Error('请选择时间范围')
|
||||
}
|
||||
return true
|
||||
},
|
||||
trigger: ['change'],
|
||||
},
|
||||
// twoType: {
|
||||
// required: true,
|
||||
// message: '请选择二级分类',
|
||||
// trigger: ['blur', 'change'],
|
||||
// },
|
||||
}
|
||||
// const mainEventRules = {
|
||||
// name: { required: true, message: '请输入名称', trigger: ['blur', 'input'] },
|
||||
@ -51,8 +61,9 @@ const mainEventData = ref({
|
||||
// type: 'mainEvent',
|
||||
describe: '',
|
||||
fileUrl: '',
|
||||
eventType: true,
|
||||
category: '123333',
|
||||
status: false,
|
||||
source: '', //数据来源
|
||||
publishTime: null,
|
||||
})
|
||||
|
||||
function resetMainEventData() {
|
||||
@ -60,7 +71,9 @@ function resetMainEventData() {
|
||||
name: '',
|
||||
timeRange: null,
|
||||
describe: '',
|
||||
eventType: true,
|
||||
status: false,
|
||||
source: '',
|
||||
publishTime: null,
|
||||
fileUrl: '',
|
||||
}
|
||||
}
|
||||
@ -71,6 +84,7 @@ const range = ref(null)
|
||||
const showNewEvent = ref(false)
|
||||
|
||||
watch(showNewEvent, show => {
|
||||
console.log('----------show',show)
|
||||
if (!show) {
|
||||
oneClassData.value = null
|
||||
resetEventData()
|
||||
@ -82,7 +96,9 @@ const eventData = ref({
|
||||
timeRange: null,
|
||||
fileUrl: '',
|
||||
describe: '',
|
||||
eventType: true,
|
||||
status: false,
|
||||
source: '',
|
||||
publishTime: null,
|
||||
equipModel: '',
|
||||
reportSite: '',
|
||||
twoType: '',
|
||||
@ -95,7 +111,9 @@ function resetEventData() {
|
||||
timeRange: null,
|
||||
fileUrl: '',
|
||||
describe: '',
|
||||
eventType: true,
|
||||
status: false,
|
||||
source: '',
|
||||
publishTime: null,
|
||||
equipModel: '',
|
||||
reportSite: '',
|
||||
twoType: '',
|
||||
|
@ -52,6 +52,7 @@ export default defineComponent({
|
||||
key: 'name',
|
||||
// width: 'auto',
|
||||
render: row => {
|
||||
console.log(row, '-row----------------------')
|
||||
return (
|
||||
<div class="inline-flex items-center gap-2">
|
||||
{/* <NIcon>
|
||||
@ -119,9 +120,35 @@ export default defineComponent({
|
||||
key: 'action',
|
||||
width: '240',
|
||||
render(row, rowIndex) {
|
||||
// console.log(row, rowIndex)
|
||||
console.log(row, rowIndex)
|
||||
return (
|
||||
<div class="flex justify-end">
|
||||
{row.level === 1 ? (
|
||||
<NButton
|
||||
type="success"
|
||||
size="small"
|
||||
quaternary
|
||||
onClick={() => addSubEvent(row)}
|
||||
>
|
||||
<NIcon>
|
||||
<AddCircleOutline />
|
||||
</NIcon>
|
||||
添加子事件
|
||||
</NButton>
|
||||
) : null}
|
||||
{/* {row.level === 1 && (
|
||||
<NButton
|
||||
type="success"
|
||||
size="small"
|
||||
quaternary
|
||||
onClick={() => addSubEvent(row)}
|
||||
>
|
||||
<NIcon>
|
||||
<AddCircleOutline />
|
||||
</NIcon>
|
||||
添加子事件
|
||||
</NButton>
|
||||
)} */}
|
||||
{row.level === 1 && (
|
||||
<NButton
|
||||
type="primary"
|
||||
@ -135,20 +162,8 @@ export default defineComponent({
|
||||
编辑事件
|
||||
</NButton>
|
||||
)}
|
||||
{row.level === 2 ? (
|
||||
<NButton
|
||||
type="success"
|
||||
size="small"
|
||||
quaternary
|
||||
onClick={() => addSubEvent(row)}
|
||||
>
|
||||
<NIcon>
|
||||
<AddCircleOutline />
|
||||
</NIcon>
|
||||
添加子事件
|
||||
</NButton>
|
||||
) : null}
|
||||
{row.level === 4 && (
|
||||
|
||||
{row.level === 3 && (
|
||||
<NButton
|
||||
type="primary"
|
||||
size="small"
|
||||
@ -161,6 +176,19 @@ export default defineComponent({
|
||||
编辑子事件
|
||||
</NButton>
|
||||
)}
|
||||
{/* {row.level === 3 && (
|
||||
<NButton
|
||||
type="error"
|
||||
size="small"
|
||||
quaternary
|
||||
onClick={() => delSubEvent(row)}
|
||||
>
|
||||
<NIcon>
|
||||
<CreateOutline />
|
||||
</NIcon>
|
||||
删除子事件
|
||||
</NButton>
|
||||
)} */}
|
||||
{Reflect.has(row, 'trajData') && (
|
||||
<NButton
|
||||
type="primary"
|
||||
@ -187,7 +215,7 @@ export default defineComponent({
|
||||
编辑子事件
|
||||
</NButton>
|
||||
)} */}
|
||||
{![2, 3].includes(row.level) ? (
|
||||
{![2].includes(row.level) ? (
|
||||
<NButton
|
||||
type="error"
|
||||
size="small"
|
||||
@ -209,11 +237,18 @@ export default defineComponent({
|
||||
|
||||
function editMainEvent(row) {
|
||||
showMainEvent.value = true
|
||||
console.log('---row', row)
|
||||
mainEventData.value = cloneDeep(row)
|
||||
mainEventData.value.status =
|
||||
mainEventData.value.status == 2 ? true : false
|
||||
mainEventData.value.timeRange = [
|
||||
mainEventData.value.startTime,
|
||||
mainEventData.value.endTime,
|
||||
]
|
||||
}
|
||||
|
||||
const addSubEvent = async row => {
|
||||
console.log(row, 'row')
|
||||
console.log('rowadd------------SubEvent', row)
|
||||
oneClassData.value = row
|
||||
showNewEvent.value = true
|
||||
// eventData.value = {}
|
||||
@ -221,13 +256,17 @@ export default defineComponent({
|
||||
}
|
||||
|
||||
function editSubEvent(row) {
|
||||
console.log('---editSubEvent----', row)
|
||||
showNewEvent.value = true
|
||||
eventData.value = cloneDeep({
|
||||
...row,
|
||||
timeRange: [row.startTime, row.endTime],
|
||||
timeRange: row.startTime,
|
||||
})
|
||||
getTwoClassList(row.oneType)
|
||||
console.log('子事件编辑:', row, 'onClassData', oneClassData)
|
||||
console.log('子事件编辑--------------:', row)
|
||||
}
|
||||
function delSubEvent(row) {
|
||||
console.log('-----------delSubEvent', row)
|
||||
}
|
||||
|
||||
const dialog = useDialog()
|
||||
@ -242,7 +281,7 @@ export default defineComponent({
|
||||
//await deleteEventById(row.id)
|
||||
if (row.level == 1) {
|
||||
await deleteSimp({ id: row.id })
|
||||
} else if (row.level == 4) {
|
||||
} else if (row.level == 3) {
|
||||
await deleteSon({ id: row.id })
|
||||
}
|
||||
searchTreeList()
|
||||
@ -292,7 +331,7 @@ export default defineComponent({
|
||||
/>
|
||||
<MainEventEdit v-model:show={showMainEvent.value} />
|
||||
|
||||
<SubEventEdit v-model:show={showNewEvent.value} />
|
||||
{/* <SubEventEdit v-model:show={showNewEvent.value} /> */}
|
||||
</>
|
||||
)
|
||||
},
|
||||
|
@ -13,6 +13,9 @@ import { getSon } from '@/api/Gantt'
|
||||
import { useTree } from '@/utils/tree'
|
||||
import { useInfoBox } from './infoBox.jsx'
|
||||
import dayjs from 'dayjs'
|
||||
import { useHappen } from '../../useHappen'
|
||||
import { useFatherData } from '../../useHappen'
|
||||
import {useEvent} from '../../EventList/hooks'
|
||||
|
||||
type GanttParams = {
|
||||
route?: any
|
||||
@ -23,9 +26,11 @@ const bgColor = '#1c202c'
|
||||
const headerBgColor = '#33566f22'
|
||||
const textColor = '#65c5e7'
|
||||
const textColorWithOp = '#75fbfd22'
|
||||
|
||||
const { getTimeRangeForTree } = useTree()
|
||||
|
||||
const currentGanttDom = ref(null)
|
||||
const currentGanttParams=ref({});
|
||||
|
||||
const useGantt = ({ router, route }: GanttParams) => {
|
||||
const currentImage = ref()
|
||||
const { subId } = route.params
|
||||
@ -33,80 +38,108 @@ const useGantt = ({ router, route }: GanttParams) => {
|
||||
|
||||
const timeRange = ref([])
|
||||
const plans = ref()
|
||||
const happen = ref()
|
||||
|
||||
// const happen = ref()
|
||||
const { happen } = useHappen()
|
||||
const { fatherData } = useFatherData()
|
||||
|
||||
// onMounted(() => {
|
||||
// getGanttData()
|
||||
// })
|
||||
|
||||
// 获取当前时间点的一个小时时间段
|
||||
function createOneHourRange(centerTime,options = {}){
|
||||
const {
|
||||
before = 0,
|
||||
after = 45*60*1000
|
||||
}=options
|
||||
|
||||
const ceterTimestamp = centerTime.getTime();
|
||||
return [
|
||||
new Date(ceterTimestamp - before),
|
||||
new Date(ceterTimestamp + after)
|
||||
]
|
||||
}
|
||||
async function getGanttData(params: Record<string, string>) {
|
||||
timeRange.value = [params.startTime, params.endTime]
|
||||
console.log('%csubId', 'color:red;font-size:20px', subId)
|
||||
const { code, data } = subId
|
||||
? await getSubGantt({ activityId: subId })
|
||||
: await getMainGantt(params)
|
||||
|
||||
if (code === 200) {
|
||||
// records.value = data.list
|
||||
if (subId) {
|
||||
records.value = data.list
|
||||
.reduce((acc, cur) => {
|
||||
if (Array.isArray(cur.children) && cur.children.length > 0) {
|
||||
acc.push(
|
||||
cur.children.map(twoType => {
|
||||
return {
|
||||
...twoType,
|
||||
children:
|
||||
twoType.children &&
|
||||
twoType.children.map(eventItem => {
|
||||
console.log(
|
||||
eventItem.startTime,
|
||||
eventItem.endTime
|
||||
// new Date(eventItem.startTime).getMonth()
|
||||
)
|
||||
return {
|
||||
...eventItem,
|
||||
start: eventItem.startTime,
|
||||
end: eventItem.endTime,
|
||||
}
|
||||
}),
|
||||
parentName: cur.name,
|
||||
childrenLengthForParent: cur.children.length,
|
||||
}
|
||||
})
|
||||
)
|
||||
}
|
||||
return acc
|
||||
}, [])
|
||||
.flat()
|
||||
// console.log(records.value)
|
||||
|
||||
records.value.length > 0 &&
|
||||
(timeRange.value = getTimeRangeForTree(records.value))
|
||||
} else {
|
||||
// console.log(data.list, '------')
|
||||
// records.value = data.list
|
||||
// .reduce((acc, cur) => {
|
||||
// if (Array.isArray(cur.children) && cur.children.length > 0) {
|
||||
// acc.push(
|
||||
// cur.children.map(twoType => {
|
||||
// return {
|
||||
// ...twoType,
|
||||
// children:
|
||||
// twoType.children &&
|
||||
// twoType.children.map(eventItem => {
|
||||
// console.log(
|
||||
// eventItem.startTime,
|
||||
// eventItem.endTime
|
||||
// // new Date(eventItem.startTime).getMonth()
|
||||
// )
|
||||
// return {
|
||||
// ...eventItem,
|
||||
// start: eventItem.startTime,
|
||||
// end: eventItem.endTime,
|
||||
// }
|
||||
// }),
|
||||
// parentName: cur.name,
|
||||
// childrenLengthForParent: cur.children.length,
|
||||
// }
|
||||
// })
|
||||
// )
|
||||
// }
|
||||
// return acc
|
||||
// }, [])
|
||||
// .flat()
|
||||
records.value = data.list.map(item => {
|
||||
return {
|
||||
...item,
|
||||
children:
|
||||
item.children &&
|
||||
item.children.map(mainEvent => {
|
||||
const date = new Date(mainEvent.startTime)
|
||||
const year = date.getFullYear()
|
||||
const month = date.getMonth()
|
||||
const startOfMonth = new Date(year, month, 1)
|
||||
// const startOfMonth = new Date(year, month, mainEvent.startTime)
|
||||
startOfMonth.setHours(0, 0, 0, 0)
|
||||
if (mainEvent.status == 2) {
|
||||
const now = new Date()
|
||||
const sortValue = parseInt(mainEvent.sort) || 0
|
||||
const daysToAdd = sortValue * 1
|
||||
const futureDate = new Date(now)
|
||||
futureDate.setDate(now.getDate() + daysToAdd)
|
||||
|
||||
const lastDayOfMonth = new Date(year, month + 1, 0)
|
||||
// const lastDayOfMonth = new Date(year, month ,mainEvent.startTime)
|
||||
const endOfMonth = new Date(
|
||||
year,
|
||||
month,
|
||||
lastDayOfMonth.getDate()
|
||||
)
|
||||
endOfMonth.setHours(23, 59, 59, 0)
|
||||
// console.log(
|
||||
// startOfMonth.toLocaleString(),
|
||||
// endOfMonth.toLocaleString()
|
||||
mainEvent.startTime = futureDate
|
||||
}
|
||||
console.log(mainEvent, 'FSLKFJSLKAFJDSL')
|
||||
const date = new Date(mainEvent.startTime)
|
||||
const startOfMonth = createOneHourRange(date)[0]
|
||||
const endOfMonth = createOneHourRange(date)[1]
|
||||
|
||||
// const year = date.getFullYear()
|
||||
// const month = date.getMonth()
|
||||
// const day = date.getDate()
|
||||
// const startOfMonth = new Date(year, month, day)
|
||||
// console.log(startOfMonth, 'startOfMonth---FSLKFJSLKAFJDSL')
|
||||
|
||||
// // const startOfMonth = new Date(year, month, mainEvent.startTime)
|
||||
// startOfMonth.setHours(1, 0, 0, 0)
|
||||
// const lastDayOfMonth = new Date(year, month + 1, day)
|
||||
// // const lastDayOfMonth = new Date(year, month ,mainEvent.startTime)
|
||||
// const endOfMonth = new Date(
|
||||
// year,
|
||||
// month,
|
||||
// lastDayOfMonth.getDate()
|
||||
// )
|
||||
// endOfMonth.setHours(2, 59, 59, 0)
|
||||
console.log(
|
||||
startOfMonth.toLocaleString(),
|
||||
endOfMonth.toLocaleString()
|
||||
)
|
||||
return {
|
||||
...mainEvent,
|
||||
start: startOfMonth,
|
||||
@ -115,33 +148,103 @@ const useGantt = ({ router, route }: GanttParams) => {
|
||||
}),
|
||||
}
|
||||
})
|
||||
records.value.length > 0 &&
|
||||
(timeRange.value = [
|
||||
getRangeTime(fatherData.value.startTime, false),
|
||||
getRangeTime(fatherData.value.endTime, true),
|
||||
])
|
||||
// records.value.length > 0 &&
|
||||
// (timeRange.value = getTimeRangeForTree(records.value))
|
||||
} else {
|
||||
// console.log(data.list, '------')
|
||||
records.value = data.list.map(item => {
|
||||
return {
|
||||
...item,
|
||||
children:
|
||||
item.children &&
|
||||
item.children.map(mainEvent => {
|
||||
console.log('mainEvent',mainEvent)
|
||||
// const date = new Date(mainEvent.startTime)
|
||||
// const year = date.getFullYear()
|
||||
// const month = date.getMonth()
|
||||
// const startOfMonth = new Date(year, month, 1)
|
||||
// // const startOfMonth = new Date(year, month, mainEvent.startTime)
|
||||
// startOfMonth.setHours(0, 0, 0, 0)
|
||||
|
||||
// const lastDayOfMonth = new Date(year, month + 1, 0)
|
||||
// // const lastDayOfMonth = new Date(year, month ,mainEvent.startTime)
|
||||
// const endOfMonth = new Date(
|
||||
// year,
|
||||
// month,
|
||||
// lastDayOfMonth.getDate()
|
||||
// )
|
||||
// endOfMonth.setHours(23, 59, 59, 0)
|
||||
|
||||
const startOfMonth = new Date(mainEvent.startTime).getTime()
|
||||
const endOfMonth =startOfMonth + 30*24*60*60*1000
|
||||
|
||||
return {
|
||||
...mainEvent,
|
||||
start: startOfMonth,
|
||||
end: happen.value === 2 ? mainEvent.endTime : endOfMonth,
|
||||
}
|
||||
}),
|
||||
}
|
||||
})
|
||||
}
|
||||
records.value.length > 0 && ganttInstance?.setRecords(records.value)
|
||||
}
|
||||
}
|
||||
|
||||
function getRangeTime(time, flag) {
|
||||
const baseDate = new Date(time)
|
||||
const type = flag ? 1 : -1
|
||||
const start = new Date(baseDate)
|
||||
start.setMonth(start.getMonth() + type)
|
||||
return start.getTime()
|
||||
}
|
||||
async function renderMainTask(
|
||||
dom: HTMLElement,
|
||||
params: Record<string, string>
|
||||
) {
|
||||
console.log(subId, 'renderMainTask')
|
||||
|
||||
currentGanttDom.value = dom
|
||||
currentGanttParams.value = params
|
||||
await getGanttData(params)
|
||||
const option = getOption()
|
||||
|
||||
// if (ganttInstance) {
|
||||
// ganttInstance.setRecords(records.value)
|
||||
// } else {
|
||||
if (records.value.length === 0) return
|
||||
if (records.value.length === 0) {
|
||||
return
|
||||
}
|
||||
ganttInstance && ganttInstance?.release()
|
||||
ganttInstance = new Gantt(dom, option)
|
||||
window['ganttInstance'] = ganttInstance
|
||||
// }
|
||||
}
|
||||
function getOption(): TYPES.GanttConstructorOptions {
|
||||
// console.log(records.value);
|
||||
let scales = 'month'
|
||||
if(subId){
|
||||
scales =plans.value ?? 'day'
|
||||
}
|
||||
const option = {
|
||||
// hierarchyType: 'tree',
|
||||
// tree: {
|
||||
// enable: true,
|
||||
// hidEmptyChildren: false,
|
||||
// defaultTreeRowHeight: 40,
|
||||
// indent: 20,
|
||||
// },
|
||||
// task: {
|
||||
// minChildren: 0,
|
||||
// },
|
||||
records: records.value,
|
||||
taskListTable: renderTaskListTable(),
|
||||
tasksShowMode: TYPES.TasksShowMode.Sub_Tasks_Arrange,
|
||||
// tasksShowMode: TYPES.TasksShowMode.All_Tasks_Arrange,
|
||||
|
||||
// groupBy: 'name',
|
||||
// groupField: 'name',
|
||||
// widthMode: 'standard',
|
||||
@ -190,7 +293,9 @@ const useGantt = ({ router, route }: GanttParams) => {
|
||||
taskBar: renderTaskBar(subId),
|
||||
timelineHeader: {
|
||||
backgroundColor: headerBgColor,
|
||||
colWidth: 150,
|
||||
// colWidth: 150,
|
||||
colWidth: 180,
|
||||
|
||||
// colWidth: 1040,
|
||||
// verticalLine: {
|
||||
// lineColor: textColorWithOp,
|
||||
@ -202,7 +307,8 @@ const useGantt = ({ router, route }: GanttParams) => {
|
||||
lineWidth: 1,
|
||||
lineDash: [4, 2],
|
||||
},
|
||||
scales: getTimeScales(subId ? 'day' : 'month'),
|
||||
// scales: getTimeScales(subId ? 'day' : 'month'),
|
||||
scales: getTimeScales(scales),
|
||||
},
|
||||
minDate: timeRange.value[0],
|
||||
maxDate: timeRange.value[1],
|
||||
@ -239,7 +345,8 @@ const useGantt = ({ router, route }: GanttParams) => {
|
||||
const columns = [
|
||||
{
|
||||
field: 'name',
|
||||
title: subId ? '目标' : '事件主体',
|
||||
// title: subId ? '目标' : '事件主体',
|
||||
title: subId ? '装备型号' : '事件主体',
|
||||
width: '120',
|
||||
mergeCell: true,
|
||||
customLayout: args => {
|
||||
@ -348,7 +455,6 @@ const useGantt = ({ router, route }: GanttParams) => {
|
||||
const { createInfoBox, updatePosition, removeInfoBox } = useInfoBox()
|
||||
|
||||
function renderTaskBar(subId: string | number) {
|
||||
// console.log(subId, '------');
|
||||
const taskBar = {
|
||||
resizable: false,
|
||||
moveable: false,
|
||||
@ -359,7 +465,7 @@ const useGantt = ({ router, route }: GanttParams) => {
|
||||
customLayout: args => {
|
||||
// console.log(args, 'args');
|
||||
const { width, height, startDate, endDate, taskRecord } = args
|
||||
// console.log(taskRecord, 'taskRecord');
|
||||
|
||||
const container = new Group({
|
||||
width,
|
||||
height,
|
||||
@ -401,6 +507,7 @@ const useGantt = ({ router, route }: GanttParams) => {
|
||||
container.addEventListener('click', async () => {
|
||||
removeInfoBox()
|
||||
if (!subId) {
|
||||
fatherData.value = taskRecord
|
||||
router.push({
|
||||
path: `/gantt/sub/${taskRecord.id}`,
|
||||
})
|
||||
@ -415,35 +522,49 @@ const useGantt = ({ router, route }: GanttParams) => {
|
||||
上报站点: data.reportSite,
|
||||
事件描述: data.describe,
|
||||
}
|
||||
window.$dialog.info({
|
||||
title: '子事件详情',
|
||||
class: '!w-[40vw]',
|
||||
content: () => {
|
||||
return h(
|
||||
'div',
|
||||
{ class: 'flex flex-col gap-4 w-full h-full' },
|
||||
[
|
||||
...Object.keys(showData).map(key => {
|
||||
return h('div', { class: 'flex w-full h-full ' }, [
|
||||
h('div', { class: 'w-[120px]' }, key),
|
||||
h(
|
||||
'div',
|
||||
{ class: 'flex-1 text-wrap' },
|
||||
showData[key]
|
||||
),
|
||||
])
|
||||
}),
|
||||
h('div', { class: 'flex w-full h-full' }, [
|
||||
h('div', { class: 'w-[120px]' }, '图片'),
|
||||
h('img', {
|
||||
src: `${window.settings.imgServer}${data.fileUrl}`,
|
||||
}),
|
||||
]),
|
||||
]
|
||||
)
|
||||
},
|
||||
positiveText: '确定',
|
||||
})
|
||||
const {showNewEvent}=useEvent();
|
||||
const {eventData} = useEvent();
|
||||
|
||||
|
||||
|
||||
eventData.value ={
|
||||
...data
|
||||
// type: 'subEvent',
|
||||
}
|
||||
showNewEvent.value=true;
|
||||
if(data.startTime){
|
||||
eventData.value.timeRange=data.startTime
|
||||
}
|
||||
|
||||
// window.$dialog.info({
|
||||
// title: '子事件详情',
|
||||
// class: '!w-[40vw]',
|
||||
// content: () => {
|
||||
// return h(
|
||||
// 'div',
|
||||
// { class: 'flex flex-col gap-4 w-full h-full' },
|
||||
// [
|
||||
// ...Object.keys(showData).map(key => {
|
||||
// return h('div', { class: 'flex w-full h-full ' }, [
|
||||
// h('div', { class: 'w-[120px]' }, key),
|
||||
// h(
|
||||
// 'div',
|
||||
// { class: 'flex-1 text-wrap' },
|
||||
// showData[key]
|
||||
// ),
|
||||
// ])
|
||||
// }),
|
||||
// h('div', { class: 'flex w-full h-full' }, [
|
||||
// h('div', { class: 'w-[120px]' }, '图片'),
|
||||
// h('img', {
|
||||
// src: `${window.settings.imgServer}${data.fileUrl}`,
|
||||
// }),
|
||||
// ]),
|
||||
// ]
|
||||
// )
|
||||
// },
|
||||
// positiveText: '确定',
|
||||
// })
|
||||
}
|
||||
}
|
||||
})
|
||||
@ -458,7 +579,7 @@ const useGantt = ({ router, route }: GanttParams) => {
|
||||
|
||||
if (subId) {
|
||||
const imgUrl = `${window.settings.imgServer}${taskRecord.fileUrl}`
|
||||
// console.log(imgUrl);
|
||||
|
||||
const image = new Image({
|
||||
image: imgUrl,
|
||||
width: 100,
|
||||
@ -470,7 +591,12 @@ const useGantt = ({ router, route }: GanttParams) => {
|
||||
// texture: 'rect',
|
||||
// textureColor: '#0006',
|
||||
// html: { dom: `<img width='200' height='200' src='${imgUrl}' />` },
|
||||
opacity: taskRecord.status === 2 ? 0.3 : 1,
|
||||
opacity: getOpacity(
|
||||
taskRecord.start,
|
||||
taskRecord.status,
|
||||
subId,
|
||||
happen.value
|
||||
),
|
||||
})
|
||||
container.add(image)
|
||||
image.addEventListener('click', e => {
|
||||
@ -522,30 +648,73 @@ const useGantt = ({ router, route }: GanttParams) => {
|
||||
fontWeight: 'bold',
|
||||
maxLineWidth: width,
|
||||
textAlign: 'center',
|
||||
opacity: taskRecord.status === 2 ? 0.3 : 1,
|
||||
// opacity: taskRecord.status === 2 ? 0.3 : 1,
|
||||
opacity: getOpacity(
|
||||
taskRecord.start,
|
||||
taskRecord.status,
|
||||
subId,
|
||||
happen.value
|
||||
),
|
||||
|
||||
// boundsPadding: [10, 0, 0, 0],
|
||||
})
|
||||
nameContainer.add(name)
|
||||
if (taskRecord.status != 2) {
|
||||
let sText=taskRecord.startTime
|
||||
if(!subId){
|
||||
sText = sText.split(' ')[0]
|
||||
}
|
||||
const start = new Text({
|
||||
text: `${sText}`,
|
||||
fontSize: 13,
|
||||
fontFamily: 'sans-serif',
|
||||
fill: textColor,
|
||||
boundsPadding: [10, 0, 0, 0],
|
||||
opacity: getOpacity(
|
||||
taskRecord.start,
|
||||
taskRecord.status,
|
||||
subId,
|
||||
happen.value
|
||||
),
|
||||
})
|
||||
container.add(start)
|
||||
}
|
||||
|
||||
const start = new Text({
|
||||
text: `${taskRecord.startTime}`,
|
||||
fontSize: 13,
|
||||
fontFamily: 'sans-serif',
|
||||
fill: textColor,
|
||||
boundsPadding: [10, 0, 0, 0],
|
||||
opacity: taskRecord.status === 2 ? 0.3 : 1,
|
||||
})
|
||||
container.add(start)
|
||||
const end = new Text({
|
||||
text: `${taskRecord.endTime}`,
|
||||
fontSize: 13,
|
||||
fontFamily: 'sans-serif',
|
||||
fill: textColor,
|
||||
boundsPadding: [10, 0, 0, 0],
|
||||
opacity: taskRecord.status === 2 ? 0.3 : 1,
|
||||
})
|
||||
container.add(end)
|
||||
if (!subId) {
|
||||
let eText=taskRecord.endTime
|
||||
if(taskRecord.status != 2){
|
||||
eText = eText.split(' ')[0]
|
||||
}
|
||||
const end = new Text({
|
||||
text: `${eText}`,
|
||||
fontSize: 13,
|
||||
fontFamily: 'sans-serif',
|
||||
fill: textColor,
|
||||
boundsPadding: [10, 0, 0, 0],
|
||||
opacity: getOpacity(
|
||||
taskRecord.start,
|
||||
taskRecord.status,
|
||||
subId,
|
||||
happen.value
|
||||
),
|
||||
})
|
||||
container.add(end)
|
||||
}
|
||||
|
||||
// const end = new Text({
|
||||
// text: `${taskRecord.endTime}`,
|
||||
// fontSize: 13,
|
||||
// fontFamily: 'sans-serif',
|
||||
// fill: textColor,
|
||||
// boundsPadding: [10, 0, 0, 0],
|
||||
// opacity: getOpacity(
|
||||
// taskRecord.start,
|
||||
// taskRecord.status,
|
||||
// subId,
|
||||
// happen.value
|
||||
// ),
|
||||
// })
|
||||
// container.add(end)
|
||||
// 事件条
|
||||
if (happen.value == 2) {
|
||||
const rect = new Rect({
|
||||
@ -570,12 +739,25 @@ const useGantt = ({ router, route }: GanttParams) => {
|
||||
],
|
||||
},
|
||||
boundsPadding: [10, 0, 0, 0],
|
||||
opacity: taskRecord.status === 2 ? 0.3 : 1,
|
||||
opacity: getOpacity(
|
||||
taskRecord.start,
|
||||
taskRecord.status,
|
||||
subId,
|
||||
happen.value
|
||||
),
|
||||
})
|
||||
container.add(rect)
|
||||
}
|
||||
|
||||
if (!subId) {
|
||||
if (!subId && happen.value == 1) {
|
||||
const dotContainer = new Group({
|
||||
display: 'flex',
|
||||
justifyContent: 'end',
|
||||
height: 10,
|
||||
width: width,
|
||||
})
|
||||
container.add(dotContainer)
|
||||
|
||||
// 添加状态圆点(直径8px)
|
||||
const dot = new Circle({
|
||||
radius: 4, // 半径4px
|
||||
@ -583,9 +765,14 @@ const useGantt = ({ router, route }: GanttParams) => {
|
||||
stroke: textColor, // 边框色
|
||||
strokeWidth: 1, // 边框粗细
|
||||
zIndex: 10, // 确保显示在最上层
|
||||
boundsPadding:[4,0,0,0]
|
||||
})
|
||||
|
||||
container.add(dot)
|
||||
dotContainer.add(dot)
|
||||
// dot.translate(
|
||||
// Math.round(width * getDaysInMontnPercent(taskRecord.startTime)),
|
||||
// 30
|
||||
// )
|
||||
}
|
||||
return {
|
||||
rootContainer: container,
|
||||
@ -605,6 +792,15 @@ const useGantt = ({ router, route }: GanttParams) => {
|
||||
return taskBar
|
||||
}
|
||||
|
||||
// 时间点
|
||||
function getDaysInMontnPercent(time) {
|
||||
const date = new Date(time)
|
||||
const year = date.getFullYear()
|
||||
const month = date.getMonth()
|
||||
const days = date.getDate()
|
||||
const allDays = new Date(year, month + 1, 0).getDate()
|
||||
return days / allDays
|
||||
}
|
||||
function updateMarkLine() {
|
||||
ganttInstance?.updateMarkLine([
|
||||
{
|
||||
@ -616,7 +812,6 @@ const useGantt = ({ router, route }: GanttParams) => {
|
||||
},
|
||||
},
|
||||
])
|
||||
console.log(ganttInstance)
|
||||
}
|
||||
function renderGroup(opt: IGroupGraphicAttribute) {
|
||||
return new Group(opt)
|
||||
@ -633,8 +828,12 @@ const useGantt = ({ router, route }: GanttParams) => {
|
||||
function changeTimeScales(scale: TYPES.ITimelineScale['unit'], val: number) {
|
||||
plans.value = scale
|
||||
happen.value = val
|
||||
const scales = getTimeScales(scale)
|
||||
ganttInstance && ganttInstance.updateScales(scales)
|
||||
|
||||
// const scales = getTimeScales(scale)
|
||||
// ganttInstance && ganttInstance.updateScales(scales)
|
||||
renderMainTask(
|
||||
currentGanttDom.value,currentGanttParams.value
|
||||
)
|
||||
}
|
||||
|
||||
function getTimeScales(
|
||||
@ -656,13 +855,16 @@ const useGantt = ({ router, route }: GanttParams) => {
|
||||
flexWrap: 'nowrap',
|
||||
})
|
||||
|
||||
// const container = new Group({
|
||||
// width:args.width,
|
||||
// height:10,
|
||||
// overflow:'hidden'
|
||||
// })
|
||||
|
||||
const day = new Text({
|
||||
text: subId
|
||||
? dayjs(startDate).format('YYYY年M月D日')
|
||||
text: subId
|
||||
? scale === 'day'?dayjs(startDate).format('YYYY年M月D日'):dayjs(startDate).format('YYYY年M月D日 HH时')
|
||||
: dayjs(startDate).format('YYYY年M月'),
|
||||
// scale === 'day'
|
||||
// ? startDate.toLocaleDateString()
|
||||
// : startDate.toLocaleTimeString(),
|
||||
fontSize: 14,
|
||||
fontWeight: 'bold',
|
||||
fontFamily: 'sans-serif',
|
||||
@ -687,12 +889,23 @@ const useGantt = ({ router, route }: GanttParams) => {
|
||||
// },
|
||||
]
|
||||
}
|
||||
|
||||
function getOpacity(time, status, subId, happen) {
|
||||
if (subId) {
|
||||
console.log(happen, 'fasfsjflksfjlaskjflkajflkfjas')
|
||||
return new Date(time).getTime() > Date.now() && happen == 2 ? 0.3 : 1
|
||||
} else {
|
||||
return status === 2 ? 0.3 : 1
|
||||
}
|
||||
}
|
||||
return {
|
||||
getGanttData,
|
||||
renderMainTask,
|
||||
changeTimeScales,
|
||||
currentImage,
|
||||
updateMarkLine,
|
||||
currentGanttDom,
|
||||
currentGanttParams
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -32,6 +32,8 @@ export default defineComponent({
|
||||
changeTimeScales,
|
||||
currentImage,
|
||||
updateMarkLine,
|
||||
currentGanttDom,
|
||||
currentGanttParams,
|
||||
} = useGantt({
|
||||
route,
|
||||
router,
|
||||
@ -57,7 +59,7 @@ export default defineComponent({
|
||||
}
|
||||
})
|
||||
function getRefresh() {
|
||||
console.log(props.happen, '------------heppen')
|
||||
console.log(props.happen, '------------heppen', props)
|
||||
renderMainTask(document.querySelector('#tableContainer'), {
|
||||
ids: props.types,
|
||||
startTime: props.dateRange ? props.dateRange[0] : null,
|
||||
@ -79,7 +81,7 @@ export default defineComponent({
|
||||
watch(
|
||||
() => props.scale,
|
||||
val => {
|
||||
changeTimeScales(val, props.happen)
|
||||
changeTimeScales(val, props.happen);
|
||||
}
|
||||
)
|
||||
watch(
|
||||
|
@ -8,13 +8,15 @@ import {
|
||||
} from 'naive-ui'
|
||||
import GanttCom from '../Gantt'
|
||||
import { getDDList } from '@/api/Gantt/gantt'
|
||||
import { onBeforeMount } from 'vue'
|
||||
import { onBeforeMount, onMounted } from 'vue'
|
||||
import { useHappen } from '../useHappen'
|
||||
|
||||
export default defineComponent({
|
||||
setup() {
|
||||
const range = ref([new Date('2000-01-01 00:00:00').getTime(), Date.now()])
|
||||
const value = ref('day')
|
||||
const happen = ref(1)
|
||||
const { happen } = useHappen()
|
||||
// const happen = ref(1)
|
||||
const types = ref([])
|
||||
|
||||
const router = useRouter()
|
||||
@ -41,8 +43,16 @@ export default defineComponent({
|
||||
ganttRef.value.refresh = true
|
||||
}
|
||||
function changeHappen() {
|
||||
range.value = [Date.now(), new Date('2027-01-01 00:00:00').getTime()]
|
||||
console.log('------console')
|
||||
if (happen.value == 1) {
|
||||
range.value = [new Date('2023-01-01 00:00:00').getTime(), Date.now()]
|
||||
} else if (happen.value == 2) {
|
||||
range.value = [Date.now(), new Date('2027-01-01 00:00:00').getTime()]
|
||||
}
|
||||
}
|
||||
onMounted(() => {
|
||||
changeHappen()
|
||||
})
|
||||
|
||||
return () => (
|
||||
<>
|
||||
@ -50,13 +60,10 @@ export default defineComponent({
|
||||
<NDatePicker
|
||||
class="w-[600px]"
|
||||
v-model:value={range.value}
|
||||
type="datetimerange"
|
||||
type="daterange"
|
||||
clearable
|
||||
/>
|
||||
{/* <NRadioGroup v-model:value={value.value} name="radiobuttongroup">
|
||||
<NRadioButton value="hour" label="日" />
|
||||
<NRadioButton value="day" label="月" />
|
||||
</NRadioGroup> */}
|
||||
|
||||
<NRadioGroup
|
||||
v-model:value={happen.value}
|
||||
name="radiobuttongroup"
|
||||
|
@ -1,11 +1,16 @@
|
||||
import { NButton } from 'naive-ui'
|
||||
import { NButton,NRadioGroup,NRadioButton } from 'naive-ui'
|
||||
import GanttCom from '../Gantt'
|
||||
import { useRouter } from 'vue-router'
|
||||
import { useEvent } from '../../components/EventList/hooks'
|
||||
const {showNewEvent}=useEvent();
|
||||
|
||||
export default defineComponent({
|
||||
setup() {
|
||||
const router = useRouter()
|
||||
|
||||
watch(showNewEvent, show => {
|
||||
console.log('----1111111------show',show)
|
||||
|
||||
})
|
||||
const value = ref('day')
|
||||
|
||||
const showView = () => {
|
||||
@ -25,8 +30,16 @@ export default defineComponent({
|
||||
>
|
||||
返回
|
||||
</NButton>
|
||||
<SubEventEdit v-model:show={showNewEvent.value} />
|
||||
|
||||
|
||||
<NRadioGroup v-model:value={value.value} name="radiobuttongroup1">
|
||||
<NRadioButton value="hour" label="小时" />
|
||||
<NRadioButton value="day" label="日" />
|
||||
</NRadioGroup>
|
||||
</div>
|
||||
<GanttCom scale={value.value} />
|
||||
|
||||
</>
|
||||
)
|
||||
},
|
||||
|
10
src/views/Gantt/components/useHappen.jsx
Normal file
@ -0,0 +1,10 @@
|
||||
const happen = ref(1)
|
||||
const fatherData = ref({})
|
||||
|
||||
export function useHappen() {
|
||||
return { happen }
|
||||
}
|
||||
|
||||
export function useFatherData() {
|
||||
return { fatherData }
|
||||
}
|
@ -15,6 +15,9 @@ import HeaderCom from '../Content/components/Header/index.vue'
|
||||
import TaskList from './components/TaskList'
|
||||
import EventList from './components/EventList'
|
||||
import NewTask from './components/TaskList/components/NewTask'
|
||||
import SubEventEdit from './components/EventList/components/SubEventEdit'
|
||||
|
||||
|
||||
|
||||
import useTask from './components/TaskList/components/NewTask/hooks'
|
||||
import { useEvent } from './components/EventList/hooks'
|
||||
@ -48,6 +51,7 @@ export default defineComponent({
|
||||
mainEventData,
|
||||
targetId,
|
||||
range,
|
||||
showNewEvent,
|
||||
searchTreeList,
|
||||
tableData,
|
||||
} = useEvent()
|
||||
@ -171,7 +175,7 @@ export default defineComponent({
|
||||
</div>
|
||||
</NDrawerContent>
|
||||
</NDrawer>
|
||||
|
||||
<SubEventEdit v-model:show={showNewEvent.value} />
|
||||
<NewTask v-model:show={showNewTask.value} />
|
||||
</div>
|
||||
)
|
||||
|
@ -137,7 +137,8 @@ function updateSatelliteLoad({ sat: sateData, detection, communication }) {
|
||||
if (!detection[0] && !communication[0]) {
|
||||
return
|
||||
}
|
||||
|
||||
console.log( detection[0] &&
|
||||
Object.values(detection[0]).some(item => isNull(item) || isUndefined(item)),'----------11')
|
||||
if (
|
||||
detection[0] &&
|
||||
Object.values(detection[0]).some(item => isNull(item) || isUndefined(item))
|
||||
@ -145,7 +146,8 @@ function updateSatelliteLoad({ sat: sateData, detection, communication }) {
|
||||
window.$message.error('探测载荷信息不完整')
|
||||
return
|
||||
}
|
||||
if (communication[0] && communication[0].target.length > 0) {
|
||||
console.log(communication[0] && communication[0].target.length > 0,'---communication[0] && communication[0].target.length > 0')
|
||||
if (!(communication[0] && communication[0].target.length > 0)) {
|
||||
window.$message.error('通信载荷信息不完整')
|
||||
return
|
||||
}
|
||||
|
@ -30,7 +30,12 @@ const textClick = item => {
|
||||
const { geom } = item
|
||||
if (geom) {
|
||||
const [lon, lat] = parseWKT(geom).coordinates
|
||||
flyTo({ lon, lat })
|
||||
// flyTo({ lon, lat })
|
||||
flyTo({
|
||||
lon: lon,
|
||||
lat: lat,
|
||||
alt: 2000000,
|
||||
});
|
||||
}
|
||||
openDetailsModal({
|
||||
contentString: item.detailContent,
|
||||
|
97
src/views/TopologyMap/components/dialogNode.vue
Normal file
@ -0,0 +1,97 @@
|
||||
<template>
|
||||
<div class="dialog" :style="{ width: width + 'px' }" v-if="id.indexOf('cpu') != -1">
|
||||
<span class="arrow-bottom" :style="{ left: (width - 17) / 2 + 'px' }"></span>
|
||||
<p>CPU:{{ cpu }}</p>
|
||||
<p>内存:{{ neicun }}</p>
|
||||
<p>硬盘:{{ yingpan }}</p>
|
||||
</div>
|
||||
<div class="dialog" :style="{ width: width + 'px' }" v-if="id.indexOf('yp2') != -1">
|
||||
<span class="arrow-left" :style="{ top: (height - 17) / 2 + 'px' }"></span>
|
||||
<p>数据:{{ shuju }}</p>
|
||||
<p>CPU:{{ cpu }}</p>
|
||||
<p>内存:{{ neicun }}</p>
|
||||
<p>硬盘:{{ yingpan }}</p>
|
||||
</div>
|
||||
<div class="dialog" :style="{ width: width + 'px' }" v-if="id.indexOf('yp1') != -1">
|
||||
<span class="arrow-bottom" :style="{ left: (width - 17) / 2 + 'px' }"></span>
|
||||
<p>数据:{{ shuju }}</p>
|
||||
<p>CPU:{{ cpu }}</p>
|
||||
<p>内存:{{ neicun }}</p>
|
||||
<p>硬盘:{{ yingpan }}</p>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script lang='ts'>
|
||||
import { defineComponent, toRefs, reactive, onMounted } from 'vue'
|
||||
// import { useRoute, useRouter } from 'vue-router';
|
||||
export default defineComponent({
|
||||
name: '',
|
||||
inject: ['getNode'],
|
||||
components: {},
|
||||
setup() {
|
||||
// const route = useRoute();
|
||||
// const router = useRouter();
|
||||
const state = reactive({
|
||||
id: "",
|
||||
"width": 70,
|
||||
"height": 55,
|
||||
"cpu": "80%",
|
||||
"neicun": "70%",
|
||||
"yingpan": "50%",
|
||||
"shuju": "128G/520G"
|
||||
})
|
||||
const getNode: Function | undefined = inject('getNode');
|
||||
onMounted(() => {
|
||||
const node = getNode();
|
||||
let info = node.getData();
|
||||
if (node) {
|
||||
console.log(info, 'info')
|
||||
state.id = info.id;
|
||||
state.width = info.width;
|
||||
state.height = info.height;
|
||||
state.shuju = info.shuju;
|
||||
state.cpu = info.cpu;
|
||||
state.neicun = info.neicun;
|
||||
state.yingpan = info.yingpan;
|
||||
}
|
||||
})
|
||||
return { ...toRefs(state) };
|
||||
}
|
||||
});
|
||||
</script>
|
||||
<style scoped lang='scss'>
|
||||
.dialog {
|
||||
background: #001232;
|
||||
border: 0.4px solid rgba(22, 238, 243, 1);
|
||||
box-shadow: inset 0px 0px 13px 0px rgba(22, 238, 243, 1);
|
||||
border-radius: 4px 4px 4px 0px 0px 0px 4px;
|
||||
border-radius: 4px;
|
||||
position: relative;
|
||||
padding: 3px 5px;
|
||||
z-index: 999;
|
||||
|
||||
.arrow-bottom {
|
||||
position: absolute;
|
||||
display: inline-block;
|
||||
width: 17px;
|
||||
height: 8px;
|
||||
bottom: -7px;
|
||||
background: url("./images/topology/arrow-bottom.png") no-repeat;
|
||||
}
|
||||
|
||||
.arrow-left {
|
||||
position: absolute;
|
||||
display: inline-block;
|
||||
width: 8px;
|
||||
height: 17px;
|
||||
left: -7px;
|
||||
background: url("./images/topology/arrow-left.png") no-repeat;
|
||||
}
|
||||
|
||||
p {
|
||||
color: #16EEF3;
|
||||
font-size: 12px;
|
||||
line-height: 16px;
|
||||
}
|
||||
}
|
||||
</style>
|
886
src/views/TopologyMap/index.vue
Normal file
@ -0,0 +1,886 @@
|
||||
<template>
|
||||
<div class="topology-map">
|
||||
<div class="top">
|
||||
<div class="left"><span>互联网</span></div>
|
||||
<div class="center"><span>办公网</span></div>
|
||||
<div class="right"><span>高密网</span></div>
|
||||
</div>
|
||||
<div class="content">
|
||||
<div id="container"></div>
|
||||
<TeleportContainer />
|
||||
</div>
|
||||
<div class="bottom">
|
||||
<div class="left">
|
||||
<i class="triangle"></i>
|
||||
<i class="rectangle"></i>
|
||||
<div class="b-con">
|
||||
<div class="b-left yingpan">
|
||||
<span>硬盘空间</span>
|
||||
</div>
|
||||
<div class="b-right">
|
||||
<div class="box">
|
||||
<p class="text">服务器1</p>
|
||||
<p class="line"><i class="jd" :style="{ 'width': 127 / 1942 * 100 + '%' }"></i></p>
|
||||
<p class="text">1942T<span class="yy">已用127T</span></p>
|
||||
</div>
|
||||
<div class="box">
|
||||
<p class="text">服务器2</p>
|
||||
<p class="line"><i class="jd" :style="{ 'width': 127 / 1942 * 100 + '%' }"></i></p>
|
||||
<p class="text">1942T<span class="yy">已用127T</span></p>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="center">
|
||||
<i class="triangle"></i>
|
||||
<i class="rectangle"></i>
|
||||
<div class="b-con">
|
||||
<div class="b-left neicun">
|
||||
<span>内存</span>
|
||||
</div>
|
||||
<div class="b-right">
|
||||
<div class="box">
|
||||
<p class="text">服务器1</p>
|
||||
<p class="line"><i class="jd" :style="{ 'width': 27 / 194 * 100 + '%' }"></i></p>
|
||||
<p class="text">194T<span class="yy">已用27T</span></p>
|
||||
</div>
|
||||
<div class="box">
|
||||
<p class="text">服务器2</p>
|
||||
<p class="line"><i class="jd" :style="{ 'width': 89 / 123 * 100 + '%' }"></i></p>
|
||||
<p class="text">123T<span class="yy">已用89T</span></p>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="right">
|
||||
<i class="triangle"></i>
|
||||
<i class="rectangle"></i>
|
||||
<div class="b-con">
|
||||
<div class="b-left cpu">
|
||||
<span>CPU</span>
|
||||
</div>
|
||||
<div class="b-right chart-box">
|
||||
<div ref="chart1Ref" class="chart"></div>
|
||||
<div ref="chart2Ref" class="chart"></div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script lang='ts'>
|
||||
import { defineComponent, toRefs, reactive, onMounted } from 'vue'
|
||||
import axios from 'axios'
|
||||
import DialogNode from './components/dialogNode.vue';
|
||||
import { Graph, Cell } from '@antv/x6'
|
||||
import { register, getTeleport } from '@antv/x6-vue-shape'
|
||||
import * as echarts from 'echarts';
|
||||
Graph.registerNode('elk-node',
|
||||
{
|
||||
inherit: 'rect',
|
||||
markup: [
|
||||
{
|
||||
tagName: 'rect',
|
||||
selector: 'body',
|
||||
},
|
||||
],
|
||||
attrs: {
|
||||
body: {
|
||||
fill: 'rgba(255,255,255,0.02)',
|
||||
stroke: 'rgba(142,255,253,0.25)',
|
||||
strokeWidth: 1,
|
||||
}
|
||||
},
|
||||
},
|
||||
true,
|
||||
)
|
||||
Graph.registerNode('rect-node',
|
||||
{
|
||||
inherit: 'rect',
|
||||
attrs: {
|
||||
body: {
|
||||
fill: 'none',
|
||||
stroke: 'none',
|
||||
strokeWidth: 1,
|
||||
},
|
||||
},
|
||||
tools: [
|
||||
{
|
||||
name: 'boundary',
|
||||
args: {
|
||||
padding: 5,
|
||||
attrs: {
|
||||
fill: 'none',
|
||||
stroke: 'rgba(142,248,255,0.25)',
|
||||
strokeWidth: 1,
|
||||
},
|
||||
},
|
||||
},
|
||||
],
|
||||
},
|
||||
true,
|
||||
)
|
||||
Graph.registerNode('node-a',
|
||||
{
|
||||
width: 48,
|
||||
height: 39,
|
||||
inherit: 'rect',
|
||||
markup: [
|
||||
{
|
||||
tagName: 'rect',
|
||||
selector: 'body',
|
||||
},
|
||||
{
|
||||
tagName: 'image',
|
||||
selector: 'img',
|
||||
},
|
||||
],
|
||||
attrs: {
|
||||
body: {
|
||||
fill: 'rgba(255,255,255,0)',
|
||||
strokeWidth: 0
|
||||
},
|
||||
img: {
|
||||
'xlink:href': "./images/topology/a.png", // 设置图片路径
|
||||
width: 48,
|
||||
height: 39,
|
||||
},
|
||||
},
|
||||
},
|
||||
true,
|
||||
)
|
||||
Graph.registerNode('node-cpu',
|
||||
{
|
||||
inherit: 'rect',
|
||||
markup: [
|
||||
{
|
||||
tagName: 'image',
|
||||
selector: 'img',
|
||||
},
|
||||
// {
|
||||
// tagName: 'rect',
|
||||
// selector: 'bg',
|
||||
// },
|
||||
// {
|
||||
// tagName: 'text',
|
||||
// selector: 'label',
|
||||
// },
|
||||
],
|
||||
attrs: {
|
||||
img: {
|
||||
'xlink:href': "./images/topology/cpu.png", // 设置图片路径
|
||||
width: 74,
|
||||
height: 86,
|
||||
},
|
||||
// bg: {
|
||||
// stroke: '#5F95FF',
|
||||
// strokeWidth: 1,
|
||||
// fill: 'rgba(0,0,0,0.5)',
|
||||
// refWidth: -10,
|
||||
// refHeight: -20,
|
||||
// rx: 5,
|
||||
// ry: 5,
|
||||
// refX: 5,
|
||||
// refY: -80,
|
||||
// },
|
||||
// label: {
|
||||
// refX: 20,
|
||||
// refY: -70,
|
||||
// fontSize: 10,
|
||||
// fill: '#fff',
|
||||
// },
|
||||
},
|
||||
},
|
||||
true,
|
||||
)
|
||||
Graph.registerNode('node-fs',
|
||||
{
|
||||
inherit: 'rect',
|
||||
markup: [
|
||||
{
|
||||
tagName: 'image',
|
||||
selector: 'img',
|
||||
},
|
||||
],
|
||||
attrs: {
|
||||
img: {
|
||||
'xlink:href': "./images/topology/fs.png", // 设置图片路径
|
||||
width: 48,
|
||||
height: 86,
|
||||
}
|
||||
},
|
||||
},
|
||||
true,
|
||||
)
|
||||
Graph.registerNode('node-fwq',
|
||||
{
|
||||
inherit: 'rect',
|
||||
markup: [
|
||||
{
|
||||
tagName: 'image',
|
||||
selector: 'img',
|
||||
},
|
||||
],
|
||||
attrs: {
|
||||
img: {
|
||||
'xlink:href': "./images/topology/fwq.png", // 设置图片路径
|
||||
width: 36,
|
||||
height: 86,
|
||||
},
|
||||
},
|
||||
},
|
||||
true,
|
||||
)
|
||||
Graph.registerNode('node-yp',
|
||||
{
|
||||
inherit: 'rect',
|
||||
markup: [
|
||||
{
|
||||
tagName: 'image',
|
||||
selector: 'img',
|
||||
},
|
||||
],
|
||||
attrs: {
|
||||
img: {
|
||||
'xlink:href': "./images/topology/yp.png", // 设置图片路径
|
||||
width: 48,
|
||||
height: 86,
|
||||
},
|
||||
},
|
||||
},
|
||||
true,
|
||||
)
|
||||
Graph.registerNode('node-com',
|
||||
{
|
||||
inherit: 'rect',
|
||||
markup: [
|
||||
{
|
||||
tagName: 'image',
|
||||
selector: 'img',
|
||||
},
|
||||
],
|
||||
attrs: {
|
||||
img: {
|
||||
'xlink:href': "./images/topology/com.png", // 设置图片路径
|
||||
width: 64,
|
||||
height: 52,
|
||||
},
|
||||
},
|
||||
},
|
||||
true,
|
||||
)
|
||||
Graph.registerNode('node-zhuji',
|
||||
{
|
||||
inherit: 'rect',
|
||||
markup: [
|
||||
{
|
||||
tagName: 'image',
|
||||
selector: 'img',
|
||||
},
|
||||
],
|
||||
attrs: {
|
||||
img: {
|
||||
'xlink:href': "./images/topology/zhuji.png", // 设置图片路径
|
||||
width: 53,
|
||||
height: 81,
|
||||
},
|
||||
},
|
||||
},
|
||||
true,
|
||||
)
|
||||
Graph.registerNode('node-xinhao',
|
||||
{
|
||||
inherit: 'rect',
|
||||
markup: [
|
||||
{
|
||||
tagName: 'rect',
|
||||
selector: 'body',
|
||||
},
|
||||
{
|
||||
tagName: 'image',
|
||||
selector: 'img',
|
||||
},
|
||||
],
|
||||
attrs: {
|
||||
body: {
|
||||
fill: 'rgba(255,255,255,0)',
|
||||
strokeWidth: 0,
|
||||
},
|
||||
img: {
|
||||
'xlink:href': "./images/topology/xinhao.png", // 设置图片路径
|
||||
width: 27,
|
||||
height: 28,
|
||||
},
|
||||
},
|
||||
},
|
||||
true,
|
||||
)
|
||||
Graph.registerNode('node-hezi',
|
||||
{
|
||||
inherit: 'rect',
|
||||
markup: [
|
||||
{
|
||||
tagName: 'rect',
|
||||
selector: 'body',
|
||||
},
|
||||
{
|
||||
tagName: 'image',
|
||||
selector: 'img',
|
||||
},
|
||||
],
|
||||
attrs: {
|
||||
body: {
|
||||
fill: 'rgba(255,255,255,0)',
|
||||
strokeWidth: 0
|
||||
},
|
||||
img: {
|
||||
'xlink:href': "./images/topology/hezi.png", // 设置图片路径
|
||||
width: 55,
|
||||
height: 56,
|
||||
},
|
||||
},
|
||||
},
|
||||
true,
|
||||
)
|
||||
|
||||
Graph.registerEdge('elk-edge',
|
||||
{
|
||||
inherit: 'edge',
|
||||
markup: [
|
||||
{
|
||||
tagName: 'path',
|
||||
selector: 'p1',
|
||||
},
|
||||
{
|
||||
tagName: 'image',
|
||||
selector: 'img',
|
||||
},
|
||||
],
|
||||
attrs: {
|
||||
p1: {
|
||||
connection: true,
|
||||
fill: 'none',
|
||||
stroke: '#16EEF3',
|
||||
strokeWidth: 1,
|
||||
targetMarker: {
|
||||
name: 'block',
|
||||
width: 6,
|
||||
height: 6,
|
||||
},
|
||||
},
|
||||
img: {
|
||||
'xlink:href': "./images/topology/duankai.png", // 设置图片路径
|
||||
width: 16,
|
||||
height: 16,
|
||||
r: 10,
|
||||
y: -8,
|
||||
atConnectionRatio: 0.2,
|
||||
},
|
||||
},
|
||||
// attrs: {
|
||||
// line: {
|
||||
// stroke: '#16EEF3',
|
||||
// strokeWidth: 1,
|
||||
// targetMarker: {
|
||||
// name: 'block',
|
||||
// width: 6,
|
||||
// height: 6,
|
||||
// },
|
||||
// },
|
||||
// },
|
||||
zIndex: 1,
|
||||
},
|
||||
true,
|
||||
)
|
||||
register({
|
||||
shape: 'node-dialog',
|
||||
component: DialogNode,
|
||||
zIndex: 15,
|
||||
})
|
||||
|
||||
interface Position {
|
||||
x: number
|
||||
y: number
|
||||
}
|
||||
|
||||
let graph: Graph;
|
||||
const TeleportContainer = getTeleport()
|
||||
|
||||
export default defineComponent({
|
||||
name: '',
|
||||
components: { TeleportContainer },
|
||||
setup() {
|
||||
// const route = useRoute();
|
||||
// const router = useRouter();
|
||||
// const elk = new ELK()
|
||||
const portIdToNodeIdMap: Record<string, string> = {}
|
||||
const cells: Cell[] = []
|
||||
const chart1Ref = ref(null);
|
||||
const chart2Ref = ref(null);
|
||||
const state = reactive({
|
||||
json: [],
|
||||
|
||||
})
|
||||
onMounted(async () => {
|
||||
graph = new Graph({
|
||||
container: document.getElementById('container'),
|
||||
width: 1795,
|
||||
height: 700,
|
||||
// background: {
|
||||
// color: 'rgba(255, 255, 255, 1)',
|
||||
// },
|
||||
router: { name: 'manhattan' },
|
||||
connector: { name: 'rounded' },
|
||||
// interacting: {
|
||||
// nodeMovable: false,
|
||||
// edgeMovable: false,
|
||||
// },
|
||||
translating: {
|
||||
restrict(view) {
|
||||
if (view) {
|
||||
const cell = view.cell
|
||||
if (cell.isNode()) {
|
||||
const parent = cell.getParent()
|
||||
if (parent) {
|
||||
return parent.getBBox()
|
||||
}
|
||||
}
|
||||
}
|
||||
return null
|
||||
},
|
||||
},
|
||||
})
|
||||
await getData().then(data => {
|
||||
addChildren(data.children || [])
|
||||
addEdges(data.edges || [])
|
||||
graph.zoomTo(1)
|
||||
// graph.centerContent()
|
||||
})
|
||||
|
||||
getCharts();
|
||||
})
|
||||
|
||||
const addChildren = (children, pos?: Position) => {
|
||||
let leftParentNode = graph.addNode({
|
||||
shape: 'elk-node',
|
||||
id: "left",
|
||||
label: "互联网",
|
||||
"x": 0,
|
||||
"y": 0,
|
||||
size: {
|
||||
"width": 347,
|
||||
"height": 666,
|
||||
},
|
||||
zIndex: 1,
|
||||
})
|
||||
let centerParentNode = graph.addNode({
|
||||
shape: 'elk-node',
|
||||
id: "center",
|
||||
label: "办公网",
|
||||
"x": 366,
|
||||
"y": 0,
|
||||
size: {
|
||||
"width": 595,
|
||||
"height": 666,
|
||||
},
|
||||
zIndex: 1,
|
||||
})
|
||||
let rightParentNode = graph.addNode({
|
||||
shape: 'elk-node',
|
||||
id: "right",
|
||||
label: "高密网",
|
||||
"x": 981,
|
||||
"y": 0,
|
||||
size: {
|
||||
"width": 814,
|
||||
"height": 666,
|
||||
},
|
||||
zIndex: 1,
|
||||
})
|
||||
children.forEach((child) => {
|
||||
const position = {
|
||||
x: (child.x || 0) + (pos ? pos.x : 0),
|
||||
y: (child.y || 0) + (pos ? pos.y : 0),
|
||||
}
|
||||
let label: string = ''
|
||||
if (typeof child.labels === 'string') {
|
||||
label = child.labels
|
||||
} else if (Array.isArray(child.labels) && child.labels[0]) {
|
||||
label = child.labels[0].text
|
||||
}
|
||||
let type = "elk-node"
|
||||
if (child.type && child.type === 'a') {
|
||||
type = 'node-a'
|
||||
} else if (child.type && child.type === 'cpu') {
|
||||
type = 'node-cpu'
|
||||
} else if (child.type && child.type === 'fwq') {
|
||||
type = 'node-fwq'
|
||||
} else if (child.type && child.type === 'yp') {
|
||||
type = 'node-yp'
|
||||
} else if (child.type && child.type === 'com') {
|
||||
type = 'node-com'
|
||||
} else if (child.type && child.type === 'rect') {
|
||||
type = 'rect-node'
|
||||
} else if (child.type && child.type === 'zhuji') {
|
||||
type = 'node-zhuji'
|
||||
} else if (child.type && child.type === 'xinhao') {
|
||||
type = 'node-xinhao'
|
||||
} else if (child.type && child.type === 'hezi') {
|
||||
type = 'node-hezi'
|
||||
}
|
||||
const node = graph.addNode({
|
||||
shape: type,
|
||||
id: child.id,
|
||||
position,
|
||||
label,
|
||||
body: {
|
||||
width: child.width || 0,
|
||||
height: child.height || 0,
|
||||
},
|
||||
size: {
|
||||
width: child.width || 0,
|
||||
height: child.height || 0,
|
||||
},
|
||||
zIndex: 2,
|
||||
})
|
||||
if (child.infos) {
|
||||
console.log(child.infos)
|
||||
const dialog = graph.createNode({
|
||||
shape: 'node-dialog',
|
||||
data: {
|
||||
id: child.id,
|
||||
...child.infos
|
||||
},
|
||||
x: child.infos.x || 0,
|
||||
y: child.infos.y || 0,
|
||||
zIndex: 3
|
||||
})
|
||||
node.addChild(dialog)
|
||||
}
|
||||
if (child.parentId === 'left') {
|
||||
leftParentNode.addChild(node)
|
||||
} else if (child.parentId === 'center') {
|
||||
centerParentNode.addChild(node)
|
||||
} else if (child.parentId === 'right') {
|
||||
rightParentNode.addChild(node)
|
||||
}
|
||||
})
|
||||
|
||||
|
||||
cells.push(leftParentNode)
|
||||
cells.push(centerParentNode)
|
||||
cells.push(rightParentNode)
|
||||
}
|
||||
const addEdges = (edges) => {
|
||||
edges.forEach((edge) => {
|
||||
let edgeline = {}
|
||||
let markup = []
|
||||
if (edge.isTrue !== undefined && edge.isTrue === false) {
|
||||
markup = [
|
||||
{
|
||||
tagName: 'path',
|
||||
selector: 'p1',
|
||||
},
|
||||
{
|
||||
tagName: 'image',
|
||||
selector: 'img',
|
||||
},
|
||||
]
|
||||
} else {
|
||||
markup = [
|
||||
{
|
||||
tagName: 'path',
|
||||
selector: 'p1',
|
||||
}
|
||||
]
|
||||
}
|
||||
if (edge.vertices) {
|
||||
edgeline = {
|
||||
shape: 'elk-edge',
|
||||
source: edge.sources,
|
||||
target: edge.targets,
|
||||
vertices: edge.vertices,
|
||||
markup: markup,
|
||||
}
|
||||
} else {
|
||||
edgeline = {
|
||||
shape: 'elk-edge',
|
||||
source: edge.sources,
|
||||
target: edge.targets,
|
||||
router: {
|
||||
name: 'er',
|
||||
args: {
|
||||
offset: 'center'
|
||||
}
|
||||
},
|
||||
markup: markup,
|
||||
}
|
||||
}
|
||||
graph.addEdge(edgeline)
|
||||
})
|
||||
}
|
||||
|
||||
const getData = () => {
|
||||
return axios.get("./json/topology.json").then(res => {
|
||||
if (res.status === 200) {
|
||||
return Promise.resolve(res.data)
|
||||
} else {
|
||||
console.log('获取TLE失败')
|
||||
return Promise.reject(res.statusText)
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
const getCharts = () => {
|
||||
const chart1 = echarts.init(chart1Ref.value);
|
||||
const chart2 = echarts.init(chart2Ref.value);
|
||||
let option1 = getOption('服务器1', 46)
|
||||
let option2 = getOption('服务器2', 23)
|
||||
|
||||
// 设置配置项并渲染图表
|
||||
chart1.setOption(option1);
|
||||
chart2.setOption(option2);
|
||||
}
|
||||
const getOption = (title, num) => {
|
||||
// 配置项
|
||||
const option = {
|
||||
title: {
|
||||
text: title,
|
||||
left: 'center',
|
||||
textStyle:
|
||||
{
|
||||
color: "#fff",
|
||||
fontSize: 14
|
||||
}
|
||||
},
|
||||
series: [
|
||||
{
|
||||
type: 'pie',
|
||||
radius: ['45%', '60%'], // 内外半径,形成环形图
|
||||
center: ['50%', '60%'],
|
||||
data: [
|
||||
{// 背景部分
|
||||
value: 100 - num, name: '未完成值',
|
||||
itemStyle: { color: 'rgba(22, 238, 243,0.3)' },
|
||||
label: {
|
||||
show: false,
|
||||
},
|
||||
},
|
||||
{ // 值部分
|
||||
value: num, name: '完成值',
|
||||
itemStyle: { color: '#16EEF3' },
|
||||
label: {
|
||||
show: true, // 不显示标签
|
||||
position: 'center',
|
||||
fontSize: 16,
|
||||
formatter: '{d}%',
|
||||
color: '#fff',
|
||||
},
|
||||
},
|
||||
],
|
||||
labelLine: {
|
||||
show: false, // 不显示标签线
|
||||
},
|
||||
emphasis: {
|
||||
scale: false, // 禁用高亮放大效果
|
||||
},
|
||||
},
|
||||
],
|
||||
};
|
||||
return option;
|
||||
}
|
||||
|
||||
return { ...toRefs(state), chart1Ref, chart2Ref };
|
||||
}
|
||||
});
|
||||
</script>
|
||||
<style scoped lang='scss'>
|
||||
.topology-map {
|
||||
height: 100%;
|
||||
background-color: #082857;
|
||||
overflow: auto;
|
||||
|
||||
.top {
|
||||
width: 1795px;
|
||||
display: flex;
|
||||
padding-top: 52px;
|
||||
margin: 0 auto 30px;
|
||||
|
||||
.left {
|
||||
width: 347px;
|
||||
}
|
||||
|
||||
.center {
|
||||
width: 595px;
|
||||
margin-left: 20px;
|
||||
}
|
||||
|
||||
.right {
|
||||
width: 814px;
|
||||
margin-left: 20px;
|
||||
}
|
||||
|
||||
.left,
|
||||
.center,
|
||||
.right {
|
||||
text-align: center;
|
||||
|
||||
span {
|
||||
display: inline-block;
|
||||
width: 262px;
|
||||
height: 32px;
|
||||
text-align: center;
|
||||
line-height: 32px;
|
||||
color: #fff;
|
||||
background: url("@/assets/image/topology/topology_bg.png") no-repeat center center;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.content {
|
||||
display: block;
|
||||
min-width: 1800px;
|
||||
// height: 666px;
|
||||
// margin: 0 auto;
|
||||
|
||||
#container {
|
||||
margin: 0 auto;
|
||||
}
|
||||
}
|
||||
|
||||
.bottom {
|
||||
display: flex;
|
||||
justify-content: space-evenly;
|
||||
|
||||
.left,
|
||||
.center,
|
||||
.right {
|
||||
width: 477px;
|
||||
height: 160px;
|
||||
// border-top: 4px solid rgba(22, 238, 243, 0.6);
|
||||
// border-bottom: 4px solid rgba(22, 238, 243, 0.3);
|
||||
position: relative;
|
||||
overflow-y: hidden;
|
||||
|
||||
.b-con {
|
||||
display: flex;
|
||||
|
||||
.b-left {
|
||||
width: 140px;
|
||||
height: 140px;
|
||||
|
||||
span {
|
||||
font-size: 16px;
|
||||
color: #16EEF3;
|
||||
text-align: center;
|
||||
display: block;
|
||||
margin-top: 35px;
|
||||
}
|
||||
|
||||
&.yingpan {
|
||||
background: url("@/assets/image/topology/ypkj.png") no-repeat center bottom;
|
||||
}
|
||||
|
||||
&.neicun {
|
||||
background: url("@/assets/image/topology/neicun.png") no-repeat center bottom;
|
||||
}
|
||||
|
||||
&.cpu {
|
||||
height: 135px;
|
||||
background: url("@/assets/image/topology/cpuicon.png") no-repeat center bottom;
|
||||
}
|
||||
}
|
||||
|
||||
.b-right {
|
||||
flex: 1;
|
||||
margin-right: 40px;
|
||||
|
||||
.box {
|
||||
margin-top: 17px;
|
||||
|
||||
.text {
|
||||
font-size: 14px;
|
||||
line-height: 22px;
|
||||
color: #fff;
|
||||
|
||||
.yy {
|
||||
color: #F5A623;
|
||||
margin-left: 10px;
|
||||
}
|
||||
}
|
||||
|
||||
.line {
|
||||
display: block;
|
||||
height: 5px;
|
||||
background: rgba(22, 238, 243, 0.5);
|
||||
border-radius: 5px;
|
||||
margin: 2px 0;
|
||||
|
||||
.jd {
|
||||
display: block;
|
||||
width: 0;
|
||||
height: 5px;
|
||||
background: #16EEF3;
|
||||
border-radius: 5px;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
&.chart-box {
|
||||
display: flex;
|
||||
margin-top: 30px;
|
||||
|
||||
.chart {
|
||||
width: 50%;
|
||||
height: 110px;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
.triangle {
|
||||
position: absolute;
|
||||
top: 0;
|
||||
right: 0;
|
||||
width: 100%;
|
||||
height: 4px;
|
||||
background: rgba(22, 238, 243, 0.6);
|
||||
}
|
||||
|
||||
.triangle::after {
|
||||
content: "";
|
||||
position: absolute;
|
||||
top: -4px;
|
||||
right: 0;
|
||||
width: 0;
|
||||
height: 0;
|
||||
border-right: 22px solid rgba(22, 238, 243, 1);
|
||||
border-bottom: 22px solid transparent;
|
||||
}
|
||||
|
||||
.rectangle {
|
||||
position: absolute;
|
||||
bottom: 0;
|
||||
left: 0;
|
||||
width: 100%;
|
||||
height: 4px;
|
||||
background-color: rgba(22, 238, 243, 1);
|
||||
}
|
||||
|
||||
.rectangle:after {
|
||||
content: "";
|
||||
position: absolute;
|
||||
right: 0;
|
||||
top: 0;
|
||||
width: 0;
|
||||
height: 0;
|
||||
border-top: 0 solid transparent;
|
||||
border-right: 50px solid #149eb5;
|
||||
border-bottom: 25px solid transparent;
|
||||
}
|
||||
|
||||
}
|
||||
}
|
||||
</style>
|