dengrui 2 месяцев назад
Родитель
Сommit
fe26df0c69

+ 132 - 32
src/views/plan/requisition/print.vue

@@ -12,20 +12,66 @@
               v-for="obj of item.printNum"
               :key="index + item + obj"
             >
-              <div>
-                <div class="lable">物料名称:</div>
-                <div class="value">{{ item.materialName }}</div>
-                <div class="lable">物料型号:</div>
-                <div class="value">{{ item.materialModel }}</div>
-                <div class="lable">物料编码:</div>
-                <div class="value">{{ item.materialCode }}</div>
-              </div>
+              <div class="leftItem">
+                <div>
+                  <div class="lable">物料编码:</div>
+                  <div class="value">
+                    <div class="value">{{ item.materialCode }}</div>
+                  </div>
+                </div>
+                <div>
+                  <div class="lable">物料名称:</div>
 
-              <div>
+                  <template v-if="item.materialName.length > 15">
+                    <div class="value">
+                      {{ item.materialName.slice(0, 13) }}
+                    </div>
+                    <div class="value">
+                      {{
+                        item.materialName.length > 30
+                          ? item.materialName.slice(14, 24) + "..."
+                          : item.materialName.slice(14)
+                      }}
+                    </div>
+                  </template>
+                  <template v-else>
+                    <div class="value">
+                      <div class="value">{{ item.materialName }}</div>
+                    </div>
+                  </template>
+                </div>
+                <div>
+                  <div class="lable">物料批次:</div>
+
+                  <template v-if="item.applyCode.length > 15">
+                    <div class="value">
+                      {{ item.applyCode.slice(0, 13) }}
+                    </div>
+                    <div class="value">
+                      {{
+                        item.applyCode.length > 30
+                          ? item.applyCode.slice(14, 24) + "..."
+                          : item.applyCode.slice(14)
+                      }}
+                    </div>
+                  </template>
+                  <template v-else>
+                    <div class="value">
+                      <div class="value">{{ item.applyCode }}</div>
+                    </div>
+                  </template>
+                </div>
+                <div>
+                  <div class="lable">物料数量:</div>
+                  <div class="value">{{ item.receiveNum }}</div>
+                </div>
+              </div>
+              <div class="rightItem">
                 <vue-qrcode
                   :value="item.code"
-                  size="30"
+                  size="40"
                   error-level="H"
+                  :margin="0"
                 ></vue-qrcode>
               </div>
             </div>
@@ -41,20 +87,43 @@
             v-for="obj of item.printNum"
             :key="index + item + obj"
           >
-            <div>
-              <div class="lable">物料名称:</div>
-              <div class="value">{{ item.materialName }}</div>
-              <div class="lable">物料型号:</div>
-              <div class="value">{{ item.materialModel }}</div>
-              <div class="lable">物料编码:</div>
-              <div class="value">{{ item.materialCode }}</div>
+            <div class="leftItem">
+              <div>
+                <div class="lable">物料编码:</div>
+
+                <template v-if="item.materialCode.length > 15">
+                  <div class="value">
+                    {{ item.materialCode.slice(0, 13) }}
+                  </div>
+                  <div class="value">
+                    {{
+                      item.materialCode.length > 30
+                        ? item.materialCode.slice(14, 24) + "..."
+                        : item.materialCode.slice(14)
+                    }}
+                  </div>
+                </template>
+              </div>
+              <div>
+                <div class="lable">物料名称:</div>
+                <div class="value">{{ item.materialName }}</div>
+              </div>
+              <div>
+                <div class="lable">物料批次:</div>
+                <div class="value">{{ item.applyCode }}</div>
+              </div>
+              <div>
+                <div class="lable">物料数量:</div>
+                <div class="value">{{ item.receiveNum }}</div>
+              </div>
             </div>
 
-            <div>
+            <div class="rightItem">
               <vue-qrcode
                 :value="item.code"
-                size="30"
+                size="40"
                 error-level="H"
+                :margin="0"
               ></vue-qrcode>
             </div>
           </div>
@@ -104,13 +173,32 @@ const printPage = () => {
     justify-content: space-between;
     margin-bottom: 10px;
     border-radius: 16px;
-    .lable {
-      font-weight: 500;
-      color: black;
+    .leftItem {
+      width: 30mm;
+      display: flex;
+      flex-direction: column;
+      justify-content: space-evenly;
+      .lable {
+        font-weight: 500;
+        color: black;
+      }
+      .value {
+        font-weight: 500;
+        color: black;
+        display: -webkit-box;
+        -webkit-box-orient: vertical;
+        -webkit-line-clamp: 2; /* 设置你想显示的行数 */
+        overflow: hidden;
+        text-overflow: ellipsis;
+        white-space: normal;
+        word-wrap: break-word;
+      }
     }
-    .value {
-      font-weight: 500;
-      color: black;
+    .rightItem {
+      width: 45mm;
+      display: flex;
+      justify-content: center;
+      align-items: center;
     }
   }
 }
@@ -125,16 +213,28 @@ const printPage = () => {
   .printItem {
     width: 80mm !important;
     height: 60mm !important;
-    padding: 2mm;
     display: flex;
     justify-content: space-between;
-    .lable {
-      font-weight: 500;
-      color: black;
+    .leftItem {
+      width: 30mm;
+      height: 60mm !important;
+      display: flex;
+      flex-direction: column;
+      justify-content: space-evenly;
+      .lable {
+        font-weight: 500;
+        color: black;
+      }
+      .value {
+        font-weight: 500;
+        color: black;
+      }
     }
-    .value {
-      font-weight: 500;
-      color: black;
+    .rightItem {
+      width: 45mm;
+      display: flex;
+      justify-content: center;
+      align-items: center;
     }
   }
 }

+ 595 - 14
src/views/report/statistics/screens/line3D/index.vue

@@ -1,7 +1,7 @@
 <template>
   <div>
-    <Middle3D />
-    <!-- <div class="screen-container">
+    <Middle3D ref="modelRef" />
+    <div class="screen-container">
       <common-headerB title="装调一体式智能生产线仿真大屏" />
       <div class="body">
         <div class="left block">
@@ -9,12 +9,62 @@
             <div class="text">工位状态</div>
             <div class="english">Station status</div>
           </div>
-          <div class="block-body"></div>
+          <div class="block-body">
+            <div class="left-header">
+              <div class="num-item">
+                <div class="item-title">总数</div>
+                <div class="item-num">20</div>
+              </div>
+              <div class="num-item">
+                <div class="item-title">在线</div>
+                <div class="item-num">12</div>
+              </div>
+              <div class="num-item">
+                <div class="item-title">离线</div>
+                <div class="item-num">2</div>
+              </div>
+              <div class="num-item">
+                <div class="item-title">故障</div>
+                <div class="item-num">0</div>
+              </div>
+            </div>
+            <div class="divider"></div>
+            <ShowScroll
+              ref="ShowScrollRef1"
+              :scrollRef="scrollbarRef1"
+              :innerRef="innerRef1"
+            >
+              <el-scrollbar ref="scrollbarRef1" class="left-scrollbar">
+                <div ref="innerRef1">
+                  <div
+                    class="infoItem"
+                    v-for="(item, index) in taskRateArray"
+                    :key="index"
+                  >
+                    <div class="leftItem textComent itembg">
+                      {{ item.stationName }}
+                    </div>
+                    <div class="rightItem itembg">{{ item.dayRate }}</div>
+                  </div>
+                </div>
+              </el-scrollbar>
+            </ShowScroll>
+          </div>
         </div>
         <div class="btn">
           <div class="tab">
-            <div class="tab-list tab-active" @click="autoView">自动巡航</div>
-            <div class="tab-list" @click="returnView">恢复视角</div>
+            <div
+              :class="aotuStatus ? 'tab-list tab-active' : 'tab-list'"
+              @click="autoView"
+            >
+              自动巡航
+            </div>
+            <div
+              :class="!aotuStatus ? 'tab-list tab-active' : 'tab-list'"
+              @click="returnView"
+            >
+              恢复视角
+            </div>
           </div>
         </div>
         <div class="right block">
@@ -22,19 +72,465 @@
             <div class="text">自动化设备状态</div>
             <div class="english">auto-equipment status</div>
           </div>
-          <div class="block-body"></div>
+          <div class="block-body">
+            <ShowScroll
+              ref="ShowScrollRef2"
+              :scrollRef="scrollbarRef2"
+              :innerRef="innerRef2"
+            >
+              <el-scrollbar ref="scrollbarRef2" class="right-scrollbar">
+                <div ref="innerRef2">
+                  <div
+                    class="deviceInfo"
+                    v-for="(item, index) in deviceArray"
+                    :key="index"
+                  >
+                    <div class="img">
+                      <el-image
+                        :src="`/images/${getRandomLetter()}.png`"
+                        class="img"
+                      />
+                      <div
+                        class="imgbg"
+                        :class="{
+                          outlinebg: item.state == '离线',
+                          errorbg: item.state == '故障',
+                        }"
+                      ></div>
+                    </div>
+                    <div class="info">
+                      <div class="info1">{{ item.deviceName }}</div>
+                      <div class="info2">
+                        <div class="text2">
+                          今日稼动
+                          <span class="nums">{{ item.utilizationRate }}</span>
+                        </div>
+                        |
+                        <div class="text2">
+                          总稼动
+                          <span class="nums" style="color: white">{{
+                            item.totalRate
+                          }}</span>
+                        </div>
+                      </div>
+                      <div class="info3">
+                        <div class="ip">ID:{{ item.id }}</div>
+                        <div class="ip">IP:{{ item.ip }}</div>
+                        <div
+                          class="infoState"
+                          :class="{
+                            red: item.state == '故障',
+                            white: item.state == '离线',
+                          }"
+                        >
+                          {{ item.state }}
+                        </div>
+                      </div>
+                    </div>
+                  </div>
+                </div>
+              </el-scrollbar>
+            </ShowScroll>
+          </div>
         </div>
       </div>
-    </div> -->
+    </div>
   </div>
 </template>
 
 <script setup>
 import CommonHeaderB from "@/views/report/statistics/screens/common-headerB.vue";
 import Middle3D from "./middle3D.vue";
+const aotuStatus = ref(true);
+const ShowScrollRef1 = ref(null);
+const innerRef1 = ref(null);
+const scrollbarRef1 = ref(null);
+const ShowScrollRef2 = ref(null);
+const innerRef2 = ref(null);
+const scrollbarRef2 = ref(null);
+const modelRef = ref(null);
+const autoView = () => {
+  aotuStatus.value = true;
+  modelRef.value.start();
+};
+const returnView = () => {
+  aotuStatus.value = false;
+  modelRef.value.down();
+};
+
+const deviceArray = ref([
+  {
+    deviceName: "测试设备",
+    ip: "11.22.108.4",
+    id: "12313213",
+    state: "离线",
+    stationName: "",
+    totalRate: "27%",
+    utilizationRate: "48%",
+  },
+  {
+    deviceName: "测试设备",
+    ip: "11.22.108.4",
+    id: "12313213",
+    state: "离线",
+    stationName: "",
+    totalRate: "28%",
+    utilizationRate: "12%",
+  },
+  {
+    deviceName: "测试设备",
+    ip: "11.22.108.4",
+    id: "12313213",
+    state: "离线",
+    stationName: "",
+    totalRate: "55%",
+    utilizationRate: "99%",
+  },
+  {
+    deviceName: "测试设备",
+    ip: "11.22.108.4",
+    id: "123133",
+    state: "离线",
+    stationName: "",
+    totalRate: "28%",
+    utilizationRate: "48%",
+  },
+  {
+    deviceName: "测试设备",
+    ip: "11.22.108.4",
+    id: "123133",
+    state: "离线",
+    stationName: "",
+    totalRate: "16%",
+    utilizationRate: "8%",
+  },
+  {
+    deviceName: "测试设备",
+    ip: "11.22.108.4",
+    id: "123133",
+    state: "在线",
+    stationName: "",
+    totalRate: "59%",
+    utilizationRate: "40%",
+  },
+  {
+    deviceName: "测试设备23",
+    ip: "11.22.108.4",
+    id: "123133",
+    state: "离线",
+    stationName: "",
+    totalRate: "90%",
+    utilizationRate: "45%",
+  },
+  {
+    deviceName: "测试设备22",
+    ip: "11.22.108.4",
+    id: "123133",
+    state: "在线",
+    stationName: "生产准备工位-4",
+    totalRate: "47%",
+    utilizationRate: "82%",
+  },
+  {
+    deviceName: "测试设备21",
+    ip: "http://10.88.20.155",
+    state: "离线",
+    stationName: "生产准备工位-4",
+    totalRate: "8%",
+    utilizationRate: "100%",
+  },
+  {
+    deviceName: "测试设备",
+    ip: "192.168.2.2",
+    state: "离线",
+    stationName: "生产准备工位18",
+    totalRate: "93%",
+    utilizationRate: "73%",
+  },
+  {
+    deviceName: "测试设备",
+    ip: "192.168.2.2",
+    state: "离线",
+    stationName: "生产准备工位18",
+    totalRate: "78%",
+    utilizationRate: "69%",
+  },
+  {
+    deviceName: "智能监控器",
+    ip: "http://10.88.20.153",
+    state: "离线",
+    stationName: "生产准备工位-2",
+    totalRate: "71%",
+    utilizationRate: "33%",
+  },
+  {
+    deviceName: "智能监控器",
+    ip: "http://10.88.20.154",
+    state: "离线",
+    stationName: "生产准备工位-3",
+    totalRate: "46%",
+    utilizationRate: "18%",
+  },
+  {
+    deviceName: "温湿度监控器",
+    ip: "http://10.88.20.153",
+    state: "在线",
+    stationName: "生产准备工位-2",
+    totalRate: "39%",
+    utilizationRate: "50%",
+  },
+  {
+    deviceName: "智能监控器",
+    ip: "11.22.108.4",
+    id: "123133",
+    state: "在线",
+    stationName: "整机装配工位-3",
+    totalRate: "61%",
+    utilizationRate: "81%",
+  },
+  {
+    deviceName: "智能监控器",
+    ip: "11.22.108.4",
+    id: "123133",
+    state: "在线",
+    stationName: "返修工位-4",
+    totalRate: "50%",
+    utilizationRate: "63%",
+  },
+  {
+    deviceName: "智能监控器",
+    ip: "11.22.108.4",
+    id: "123133",
+    state: "在线",
+    stationName: "整机装配工位-1",
+    totalRate: "95%",
+    utilizationRate: "89%",
+  },
+  {
+    deviceName: "智能监控器",
+    ip: "11.22.108.4",
+    id: "123133",
+    state: "离线",
+    stationName: "返修工位-2",
+    totalRate: "56%",
+    utilizationRate: "82%",
+  },
+]);
+const getRandomLetter = () => {
+  const letters = ["a", "b", "c", "d"];
+  const randomIndex = Math.floor(Math.random() * letters.length);
+  return letters[randomIndex];
+};
+const taskRateArray = ref([
+  {
+    stationName: "测试工位-1",
+    dayRate: "正常",
+  },
+  {
+    stationName: "测试工位-2",
+    dayRate: "正常",
+  },
+  {
+    stationName: "测试工位-3",
+    dayRate: "正常",
+  },
+  {
+    stationName: "测试工位-4",
+    dayRate: "正常",
+  },
+  {
+    stationName: "流转工位-1",
+    dayRate: "正常",
+  },
+  {
+    stationName: "流转工位-2",
+    dayRate: "正常",
+  },
+  {
+    stationName: "流转工位-3",
+    dayRate: "正常",
+  },
+  {
+    stationName: "流转工位-4",
+    dayRate: "正常",
+  },
+  {
+    stationName: "焊接工位-1",
+    dayRate: "正常",
+  },
+  {
+    stationName: "检验工位-1",
+    dayRate: "正常",
+  },
+  {
+    stationName: "检验工位-2",
+    dayRate: "正常",
+  },
+  {
+    stationName: "检验工位-3",
+    dayRate: "正常",
+  },
+  {
+    stationName: "检验工位-4",
+    dayRate: "正常",
+  },
+  {
+    stationName: "装配工位-1",
+    dayRate: "正常",
+  },
+  {
+    stationName: "装配工位-2",
+    dayRate: "正常",
+  },
+  {
+    stationName: "装配工位-3",
+    dayRate: "正常",
+  },
+  {
+    stationName: "装配工位-4",
+    dayRate: "正常",
+  },
+  {
+    stationName: "检验工位-4",
+    dayRate: "正常",
+  },
+  {
+    stationName: "装配工位-1",
+    dayRate: "正常",
+  },
+  {
+    stationName: "装配工位-2",
+    dayRate: "正常",
+  },
+  {
+    stationName: "装配工位-3",
+    dayRate: "正常",
+  },
+  {
+    stationName: "装配工位-4",
+    dayRate: "正常",
+  },
+  {
+    stationName: "检验工位-4",
+    dayRate: "正常",
+  },
+  {
+    stationName: "装配工位-1",
+    dayRate: "正常",
+  },
+  {
+    stationName: "装配工位-2",
+    dayRate: "正常",
+  },
+  {
+    stationName: "装配工位-3",
+    dayRate: "正常",
+  },
+  {
+    stationName: "装配工位-4",
+    dayRate: "正常",
+  },
+]);
+setTimeout(() => {
+  nextTick(() => {
+    ShowScrollRef1.value.setActive();
+    ShowScrollRef2.value.setActive();
+  });
+}, 3000);
 </script>
 
 <style lang="scss" scoped>
+.deviceInfo {
+  width: 21vw;
+  height: 10vh;
+  margin: 1vh 0;
+  display: flex;
+  background-color: rgba(255, 255, 255, 0.05);
+  // clip-path: polygon(0% 0%, 85% 0%, 100% 25%, 100% 100%, 0% 100%);
+  .img {
+    height: 10vh;
+    width: 7vw;
+    position: relative;
+    .imgbg {
+      position: absolute;
+      height: 10vh;
+      width: 7vw;
+      top: 0;
+      left: 0;
+      z-index: 2;
+      background-color: #06ffa520;
+      border: 0.4vh solid #06ffa5;
+    }
+    .outlinebg {
+      background-color: #ffffff20 !important;
+      border: 0.4vh solid #fff !important;
+    }
+    .errorbg {
+      background-color: #db484820 !important;
+      border: 0.4vh solid #db4848 !important;
+    }
+  }
+  .info {
+    height: 10vh;
+    width: 100%;
+    display: flex;
+    flex-direction: column;
+    justify-content: space-between;
+    padding-top: 1vh;
+
+    .info1 {
+      padding-left: 0.5vw;
+      height: 2vh;
+      font-size: 2vh;
+      line-height: 2vh;
+      font-weight: 600;
+      color: white;
+    }
+    .info2 {
+      height: 2vh;
+      padding-left: 0.5vw;
+      display: flex;
+      justify-content: space-between;
+      align-items: center;
+      color: white;
+      padding-right: 1vw;
+      .text2 {
+        font-size: 1.5vh;
+        .nums {
+          color: #0ae0ff;
+          font-weight: 600;
+        }
+      }
+    }
+    .info3 {
+      height: 2vh;
+      font-size: 2vh;
+      // background-color: rgba(255, 255, 255, 0.05);
+      display: flex;
+      padding-left: 0.5vw;
+      padding-right: 1vw;
+      justify-content: space-between;
+      .ip {
+        font-size: 1.6vh;
+        line-height: 2vh;
+        color: white;
+      }
+      .infoState {
+        font-size: 1.6vh;
+        line-height: 2vh;
+        color: #06ffa5;
+      }
+    }
+  }
+}
+.textComent {
+  white-space: nowrap; /* 不允许换行 */
+  overflow: hidden; /* 超出长度时隐藏 */
+  text-overflow: ellipsis; /* 超出部分显示省略号 */
+}
+.itembg {
+  background-color: #46464635;
+}
 .screen-container {
   width: 100vw;
   height: 100vh;
@@ -71,21 +567,20 @@ import Middle3D from "./middle3D.vue";
             cursor: pointer;
           }
         }
-      }
-
-      .tab-active {
-        background-image: url("@/assets/images/environmentTest/tab_active.png");
+        .tab-active {
+          background-image: url("@/assets/images/environmentTest/tab_active.png");
+        }
       }
     }
     .block {
-      padding: 2.34375vw 2.083vw;
+      padding: 2.3vw 2vw;
       height: 92vh;
       width: 22.292vw;
       .block-header {
-        padding: 0 3.28125vw 0.15625vw;
+        padding: 0 3vw 0.15vw;
         font-weight: 700;
         font-style: italic;
-        letter-spacing: 0.104vw;
+        letter-spacing: 0.1vw;
         .text {
           color: white;
           font-size: 1.146vw;
@@ -104,6 +599,44 @@ import Middle3D from "./middle3D.vue";
         background-size: 100% 100%;
       }
       .block-body {
+        display: flex;
+        flex: 1;
+        flex-direction: column;
+        .left-scrollbar {
+          height: 63vh;
+          margin: 1vh 0;
+        }
+        .right-scrollbar {
+          width: 26.292vw;
+          height: 73vh;
+          margin: 1vh 0;
+          margin-left: -2vw;
+        }
+        .left-header {
+          height: 10vh;
+          font-style: italic;
+          display: flex;
+          justify-content: space-evenly;
+          .num-item {
+            width: 3vw;
+            height: 10vh;
+            display: flex;
+            flex-direction: column;
+            justify-content: space-evenly;
+            text-align: center;
+            color: white;
+            font-size: 2.5vh;
+            .item-title {
+            }
+            .item-num {
+            }
+          }
+        }
+        .divider {
+          height: 0.104vw;
+          background-image: url("@/assets/images/environmentTest/divider.png");
+          background-size: 100% 100%;
+        }
       }
     }
     .left {
@@ -116,4 +649,52 @@ import Middle3D from "./middle3D.vue";
     }
   }
 }
+.infoItem {
+  height: 4vh;
+  margin-bottom: 0.4vh;
+  display: flex;
+  .leftItem {
+    flex: 1;
+    height: 4vh;
+    font-size: 1.8vh;
+    line-height: 4vh;
+    color: white;
+    text-align: center;
+  }
+  .rightItem {
+    width: 25%;
+    height: 4vh;
+    line-height: 4vh;
+    margin-left: 0.3vw;
+    font-size: 1.8vh;
+    color: white;
+    text-align: center;
+  }
+  .leftItem1 {
+    flex: 1;
+    height: 4vh;
+    font-size: 1.8vh;
+    line-height: 4vh;
+    color: white;
+    text-align: center;
+  }
+  .midItem1 {
+    width: 25%;
+    height: 4vh;
+    line-height: 4vh;
+    margin-left: 0.3vw;
+    font-size: 1.8vh;
+    color: white;
+    text-align: center;
+  }
+  .rightItem1 {
+    width: 20%;
+    height: 4vh;
+    line-height: 4vh;
+    margin-left: 0.3vw;
+    font-size: 1.8vh;
+    color: white;
+    text-align: center;
+  }
+}
 </style>

+ 26 - 7
src/views/report/statistics/screens/line3D/middle3D.vue

@@ -32,12 +32,22 @@ const getInfoArray = async () => {
 };
 
 const init3D = () => {
+  let internval = null;
+  //巡航函数
+  const start = () => {
+    console.log("111");
+    // animateCamera();
+    // internval = setInterval(() => {
+    //   animateCamera();
+    // }, 30000);
+  };
+  //停止巡航
+  const down = () => {
+    clearInterval(interval);
+  };
   //创建场景
   const scene = new THREE.Scene();
-  scene.background = new THREE.TextureLoader()
-    .load("logo.png")
-    .setSize(window.innerWidth, window.innerHeight);
-
+  scene.background = new THREE.TextureLoader().load("logo.png");
   //渲染函数
   const render = () => {
     renderer.render(scene, camera);
@@ -159,7 +169,7 @@ const init3D = () => {
   const controls = new OrbitControls(camera, renderer.domElement);
   controls.update();
   const loader = new GLTFLoader();
-  guiFnc();
+  // guiFnc();
   render();
   //加载模型
   loader.load("/3dmodel/XF2025.glb", (gltf) => {
@@ -254,11 +264,20 @@ const init3D = () => {
   //   sprite.position.set(0, -5, 0);
   //   scene.add(sprite);
   // }
+  return {
+    start,
+    down,
+  };
 };
-
+const startFnc = ref(null);
+const downFnc = ref(null);
+defineExpose({ startFnc, downFnc });
 onMounted(() => {
   getInfoArray();
-  init3D();
+  const { start, down } = init3D();
+  startFnc.value = start;
+  downFnc.value = down;
+  console.log(startFnc.value);
 });
 </script>