lvkun 2 жил өмнө
parent
commit
48310e484a

+ 103 - 60
src/pages/Iot/device/topology.vue

@@ -2,68 +2,77 @@
   <a-card>
     <a-row>
       <a-col>
-        <a-select
-          placeholder="请选择产品"
-          v-model:value="state.modelId"
-        >
-          <a-select-option
-            v-for="model in state.modelList"
-            :key="model.id"
-            :value="model.id"
+        <a-space>
+          <a-select
+            placeholder="请选择产品"
+            v-model:value="state.modelId"
+            style="width: 170px"
           >
-            {{model.modelLabel}}
-          </a-select-option>
-        </a-select>
-        <a-button @click="exportDomToImage" >导出</a-button>
+            <a-select-option
+              v-for="model in state.modelList"
+              :key="model.id"
+              :value="model.id"
+            >
+              {{model.modelLabel}}
+            </a-select-option>
+          </a-select>
+          <a-button @click="exportDomToImage" >导出</a-button>
+        </a-space>
       </a-col>
     </a-row>
 
-    <div class="topology-preview" >
-      <a-row class="zoom-navbar" >
-        <a-col>
-          <a-tooltip>
-            <template #title>放大</template>
-            <zoom-in-outlined  :style="{fontSize: '34px'}" />
-          </a-tooltip>
-          <a-tooltip>
-            <template #title>缩小</template>
-            <zoom-out-outlined :style="{fontSize: '34px'}" />
-          </a-tooltip>
-        </a-col>
-      </a-row>
-      <vue-tree
-        style="width: 1000px; height: 600px; border: 1px solid gray;"
-        :dataset="treeData.richMediaData"
-        :config="treeData.treeConfig"
-        id="vueTreeRef"
-        ref="vueTreeRef"
-      >
-        <template v-slot:node="{ node, collapsed }">
-          <a-row
-            class="rich-media-node"
-          >
-            <a-col :span="24"  >
-              <a-space>
-                📦
-                  <div>
-                  {{node.value}}
-                  {{node.modelLabel}}
-                  {{node.deviceLabel}}
+    <a-spin style="width: 1000px;" :spinning="state.loading" >
+      <div class="topology-preview" >
+        <a-row class="zoom-navbar" justify="center" >
+          <a-col  >
+            <a-space>
+              <a-tooltip>
+                <template #title>放大</template>
+                <zoom-in-outlined  @click="zoomIn" :style="{fontSize: '20px', cursor: 'pointer'}" />
+              </a-tooltip>
+              <span>{{zoomCount}}%</span>
+              <a-tooltip>
+                <template #title>缩小</template>
+                <zoom-out-outlined  @click="zoomOut" :style="{fontSize: '20px', cursor: 'pointer'}" />
+              </a-tooltip>
+              <a-button @click="resetZoom" >重置</a-button>
+            </a-space>
+          </a-col>
+        </a-row>
+        <vue-tree
+          style="width: 1000px; height: 600px; border: 1px solid gray;"
+          :dataset="treeData.richMediaData"
+          :config="treeData.treeConfig"
+          id="vueTreeRef"
+          ref="vueTreeRef"
+        >
+          <template v-slot:node="{ node, collapsed }">
+            <a-row
+              class="rich-media-node"
+            >
+              <a-col :span="24"  >
+                <a-space>
+                  📦
+                    <div>
+                    {{node.value}}
+                    {{node.modelLabel}}
+                    {{node.deviceLabel}}
+                  </div>
+                </a-space>
+              </a-col>
+              <a-col>
+                <div>
+                  {{node.transportType}}
+                {{node.payloadType}}
                 </div>
-              </a-space>
-            </a-col>
-            <a-col>
-              <div>
-                {{node.transportType}}
-              {{node.payloadType}}
-              </div>
-
-            </a-col>
-            <!-- {{node.deviceLabel}} -->
-          </a-row>
-        </template>
-      </vue-tree>
-    </div>
+
+              </a-col>
+              <!-- {{node.deviceLabel}} -->
+            </a-row>
+          </template>
+        </vue-tree>
+      </div>
+    </a-spin>
 
   </a-card>
 </template>
@@ -83,9 +92,11 @@ const state = reactive<{
     gatewayDevice: any[]
     model: IOT.API.MODEL.Model[]
     subDevice: IOT.API.DEVICE.Device[]
-  }
+  },
+  loading: false
 }>({
   modelId: '',
+  loading: false,
   modelList: [],
   dataSource: {
     gatewayDevice: [],
@@ -96,18 +107,34 @@ const state = reactive<{
 
 const vueTreeRef = ref('')
 
+const zoomCount = ref(100)
+
 const treeData = reactive({
   richMediaData: {},
   treeConfig: { nodeWidth: 120, nodeHeight: 80, levelHeight: 200 }
 }
 )
 
+const zoomIn = () => {
+  zoomCount.value += 10
+  vueTreeRef.value.zoomIn()
+}
+
+const zoomOut = () => {
+  zoomCount.value -= 10
+  vueTreeRef.value.zoomOut()
+}
+
+const resetZoom = () => {
+  zoomCount.value = 100
+}
+
 window.addEventListener('wheel', function (event) {
   console.log(event.deltaY)
   if (event.deltaY > 0) {
-    vueTreeRef.value.zoomOut()
+    zoomOut()
   } else {
-    vueTreeRef.value.zoomIn()
+    zoomIn()
   }
 })
 
@@ -127,6 +154,7 @@ function exportDomToImage () {
 }
 
 const getDeviceTopology = async () => {
+  state.loading = true
   const { data } = await DeviceContriller.getDeviceTopology(state.modelId)
   const { gatewayDevice, model, subDevice } = data
 
@@ -152,6 +180,7 @@ const getDeviceTopology = async () => {
   })
 
   treeData.richMediaData = obj
+  state.loading = false
   console.log('obj:', obj)
 }
 
@@ -185,12 +214,26 @@ onMounted(() => {
   }
 }
 
+#vueTreeRef {
+  position: relative;
+  z-index: 1;
+}
+
 .topology-preview {
   position: relative;
+  width: 1000px;
+  margin-top: 20px;
   .zoom-navbar {
     position: absolute;
     top: 0;
     left: 0;
+    width: 100%;
+    height: 50px;
+    background-color: #f6f6f6;
+    display: flex;
+    justify-content: center;
+    align-items: center;
+    z-index: 2;
   }
 }