系統監控: 點擊card時zoom in 且 Sprite 放大

This commit is contained in:
koko 2024-11-21 09:27:30 +08:00
parent 2693ad5713
commit 258f28e056
3 changed files with 56 additions and 37 deletions

View File

@ -7,11 +7,11 @@ import useForgeFloor from "./useForgeFloor";
export default function useForgeSprite() { export default function useForgeSprite() {
const { subscribeData } = inject("system_deviceList"); const { subscribeData } = inject("system_deviceList");
const { getCurrentInfoModalData, clearSelectedDeviceInfo } = inject( const { getCurrentInfoModalData, clearSelectedDeviceInfo, selected_dbid } =
"system_selectedDevice" inject("system_selectedDevice");
);
const forgeViewer = ref(null); const forgeViewer = ref(null);
const dataVizExtn = ref(null); const dataVizExtn = ref(null);
let lastClickedDbId = null;
const { createHeatMap, updateViewExtension } = useForgeHeatmap(); const { createHeatMap, updateViewExtension } = useForgeHeatmap();
const { updateViewerFloor } = useForgeFloor(); const { updateViewerFloor } = useForgeFloor();
@ -109,6 +109,19 @@ export default function useForgeSprite() {
} }
); );
watch(
() => selected_dbid,
() => {
if (forgeViewer.value?.isLoadDone()) {
cardfitToView(selected_dbid.value);
}
},
{
immediate: true,
deep: true,
}
);
const forgeClickListener = () => { const forgeClickListener = () => {
console.log("監聽forge"); console.log("監聽forge");
@ -122,25 +135,42 @@ export default function useForgeSprite() {
); );
}; };
const fitToView = () => { const cardfitToView = async ([forge_dbid,spriteDbId]) => {
const { x, y, z } = JSON.parse(searchParams.value.camera_position); try {
const newPosition = new THREE.Vector3(x, y, z); //!<<< 相机的新位置 // 相機調整
const nav = forgeViewer.value.navigation;
const camera = nav.getCamera();
forgeViewer.value.fitToView([forge_dbid], null, true);
const direction = new THREE.Vector3();
camera.getWorldDirection(direction);
const distanceBack = 30;
camera.position.add(direction.multiplyScalar(-distanceBack));
const target = nav.getTarget();
const fov = nav.getVerticalFov();
nav.setRequestTransition(true, camera.position, target, fov);
const {
x: x1, if (lastClickedDbId !== null && lastClickedDbId !== spriteDbId) {
y: y1, dataVizExtn.value.invalidateViewables([lastClickedDbId], (viewable) => {
z: z1, return {
} = JSON.parse(searchParams.value.target_position); //!<<< 计算新焦点位置 scale: 1.0, // 恢復為 scale 1
const newTarget = new THREE.Vector3(x1, y1, z1); //!<<< 焦點的新位置 };
});
}
dataVizExtn.value.invalidateViewables([spriteDbId], (viewable) => {
return {
scale: 2.0, // 設置為 scale 2
};
});
NOP_VIEWER.navigation.getCamera().setView({ lastClickedDbId = spriteDbId;
position: newPosition.clone(),
target: newTarget.clone(), } catch (error) {
}); console.error("Error in cardfitToView:", error);
setTimeout(() => { }
updateDbidPosition(NOP_VIEWER, subscribeData.value);
}, 700);
}; };
const hideAllObjects = () => { const hideAllObjects = () => {
const tree = forgeViewer.value.model.getInstanceTree(); const tree = forgeViewer.value.model.getInstanceTree();
@ -179,5 +209,6 @@ export default function useForgeSprite() {
showSubSystemObjects, showSubSystemObjects,
forgeClickListener, forgeClickListener,
clear, clear,
cardfitToView,
}; };
} }

View File

@ -38,6 +38,7 @@ const data = ref([]); // filter data
const route = useRoute(); const route = useRoute();
const floors = ref([]); const floors = ref([]);
const companyOptions = ref([]); const companyOptions = ref([]);
const selected_dbid = ref([]);
const getFloors = async () => { const getFloors = async () => {
const res = await getAssetFloorList(); const res = await getAssetFloorList();
@ -218,7 +219,7 @@ const clearSelectedDeviceInfo = () => {
selectedDevice.value.value = null; selectedDevice.value.value = null;
} }
provide("system_selectedDevice", { selectedDeviceRealtime, selectedDevice, getCurrentInfoModalData, clearSelectedDeviceInfo, selectedDeviceCog, }) provide("system_selectedDevice", { selectedDeviceRealtime, selectedDevice, getCurrentInfoModalData, clearSelectedDeviceInfo, selectedDeviceCog, selected_dbid })
onBeforeUnmount(() => { onBeforeUnmount(() => {
clearInterval(timeId.value); clearInterval(timeId.value);

View File

@ -2,26 +2,13 @@
import { computed, inject, watch } from "vue" import { computed, inject, watch } from "vue"
import useSystemShowData from "@/hooks/useSystemShowData" import useSystemShowData from "@/hooks/useSystemShowData"
const { getCurrentInfoModalData } = inject("system_selectedDevice") const { getCurrentInfoModalData, selected_dbid } = inject("system_selectedDevice")
const { showData } = useSystemShowData() const { showData } = useSystemShowData()
const FILE_BASEURL = import.meta.env.VITE_FILE_API_BASEURL; const FILE_BASEURL = import.meta.env.VITE_FILE_API_BASEURL;
const fitToView = (forge_dbid) => { const fitToView = (forge_dbid,spriteDbId) => {
const viewer = window.NOP_VIEWER; selected_dbid.value=[forge_dbid,spriteDbId];
if (!viewer) return;
const nav = viewer.navigation;
const camera = nav.getCamera();
viewer.fitToView([forge_dbid], null, true);
const direction = new THREE.Vector3();
camera.getWorldDirection(direction);
// 退
const distanceBack = 30; // 退
camera.position.add(direction.multiplyScalar(-distanceBack));
const target = nav.getTarget();
const fov = nav.getVerticalFov();
nav.setRequestTransition(true, camera.position, target, fov);
}; };
</script> </script>
@ -35,7 +22,7 @@ const fitToView = (forge_dbid) => {
<p class="title">{{ d.full_name }}</p> <p class="title">{{ d.full_name }}</p>
<div class="grid grid-cols-1 lg:grid-cols-2 gap-5"> <div class="grid grid-cols-1 lg:grid-cols-2 gap-5">
<div class="col-auto relative" v-for="device in d.device_list" :key="device.device_guid"> <div class="col-auto relative" v-for="device in d.device_list" :key="device.device_guid">
<div class="item h-full cursor-pointer" @click="() => fitToView(device.forge_dbid)"> <div class="item h-full cursor-pointer" @click="() => fitToView(device.forge_dbid, device.spriteDbId)">
<div class="left h-full flex flex-wrap justify-center"> <div class="left h-full flex flex-wrap justify-center">
<div class="sec02 w-full"> <div class="sec02 w-full">
<img v-if="device.device_image_url" :src="`${FILE_BASEURL}/upload/device_icon/${device.device_image}`" :alt="device.device_image" > <img v-if="device.device_image_url" :src="`${FILE_BASEURL}/upload/device_icon/${device.device_image}`" :alt="device.device_image" >