凉纪 1 жил өмнө
parent
commit
638c09ef47

+ 16 - 0
src/assets/css/index.scss

@@ -119,3 +119,19 @@ pre{
 .van-info--dot{
   background-color:#ee0a24;
 }
+.legend{
+  height:80px;
+  display: flex;
+  justify-content: space-around;
+  li{
+    display: flex;
+    align-items: center;
+    >span{
+      display: inline-block;
+      width: 25px;
+      height: 25px;
+      margin-right: 10px;
+      border-radius: 50%;
+    }
+  }
+}

+ 2 - 2
src/components/waterCom.vue

@@ -41,9 +41,9 @@ export default {
     //   设置文字大小
       ctx.fillStyle = 'rgba(0,0,0,.1)' //设置文字颜色及透明度
       ctx.rotate(-0.4) //设置文字旋转角度
-      ctx.fillText(`${userName||''}${orgName||''}${this.date}`, -10, 120) //设置显示文字内容
+      ctx.fillText(`${userName||''}${orgName||''}${this.date}`, -30, 120) //设置显示文字内容
       const img = canvas.toDataURL('image/png') //参数默认为 image/png,可以是其他image/jpeg等,该方法返回值是一个url,是base64组成的图片的源数据、可以直接赋值给图片的src属性
-      const style = `background-image:url(${img});width:1200px;z-index:111;display:${type==1? 'block':'none'};` //定义样式
+      const style = `background-image:url(${img});width:100%;z-index:111;display:${type==1? 'block':'none'};` //定义样式
       water.setAttribute('style', style) //给要添加水印的元素设置样式
     }
   }

+ 12 - 6
src/router/router.config.js

@@ -339,12 +339,18 @@ export let routers = [
         component: () => import('@/views/menu/iot/videoQuality/index.vue'),
         meta: { title: '录像质量',  keepAlive: true ,hideTabBar:false,deep: 1}
       },
-      // {
-      //   path: '/videoDay',
-      //   name: 'videoDay',
-      //   component: () => import('@/views/menu/iot/videoDay/index.vue'),
-      //   meta: { title: '录像完整性',  keepAlive: true ,hideTabBar:false,deep: 1}
-      // },
+      {
+        path: '/videoDay',
+        name: 'videoDay',
+        component: () => import('@/views/menu/iot/videoDay/index.vue'),
+        meta: { title: '录像天数',  keepAlive: true ,hideTabBar:false,deep: 1}
+      },
+      {
+        path: '/videoDayDetail',
+        name: 'videoDayDetail',
+        component: () => import('@/views/menu/iot/videoDay/detail.vue'),
+        meta: { title: '录像天数详情',  keepAlive: false ,hideTabBar:true,deep: 2}
+      },
     ],
   },
 ]

+ 44 - 0
src/views/menu/iot/videoDay/api.js

@@ -0,0 +1,44 @@
+import request from "@/utils/request";
+//获取列表
+export function dataList(data) {
+  return request({
+    url: "/core/outinrecord/list",
+    method: "get",
+    params: data,
+  });
+}
+
+//用户列表
+export function userList(params) {
+  return request({
+    url: "/core/letter/approved/person",
+    method: "get",
+    params
+  });
+}
+
+//获取详情
+export function userDetails(id){
+  return request({
+    url: "/core/outinrecord/"+id,
+    method: "get",
+  });
+}
+
+//人员登记
+export function userRegister(data){
+  return request({
+    url: "/core/outinrecord",
+    method: "post",
+    data
+  });
+}
+
+//登记离开
+export function userDepart(data){
+  return request({
+    url: "/core/outinrecord",
+    method: "put",
+    data
+  });
+}

+ 417 - 0
src/views/menu/iot/videoDay/detail.vue

@@ -0,0 +1,417 @@
+<template>
+  <div class="record-detail">
+    <nav-bar></nav-bar>
+    <div class="page-container">
+      <div class="card">
+        <van-panel title="XXX区域">
+          <div class="tag-box">
+            <div v-for="(v,i) in tagList"
+             class="tag-item"
+             :style="{backgroundColor:getColor(v.state),borderColor:getColor(v.state)}"
+             @click="clickTag" :key="i">
+              {{v.name+i}}
+              <div class="top-dot">34</div>
+            </div>
+          </div>
+          <ul class="legend">
+            <li v-for="v in legend" :key="v.type">
+              <span :style="{background:v.color}"></span>
+              {{v.type}}
+            </li>
+          </ul>
+        </van-panel>
+      </div>
+      <!--   基本信息   -->
+      <div class="card">
+        <van-panel >
+            <template #header>
+              <span></span>
+            </template>
+          <div class="panel-box">
+            <van-cell title="组织机构" :value="selectedUser.userName"></van-cell>
+            <van-cell title="监控主机" :value="getDictLabel(selectedUser.type,'out_in_type')"></van-cell>
+            <van-cell title="通道号" :value="selectedUser.reasons"></van-cell>
+            <van-cell title="计划存储天数" :value="selectedUser.companyName"></van-cell>
+            <van-cell title="上报日期" :value="getDictLabel(selectedUser.idType,'letter_id_type')"></van-cell>
+            <van-cell title="最早录像日期" :value="selectedUser.idCard"></van-cell>
+            <van-cell title="计划存储天数" :value="selectedUser.idCard"></van-cell>
+            <van-cell title="实际存储天数" :value="selectedUser.idCard"></van-cell>
+            <van-cell title="计划存储日期" :value="selectedUser.idCard"></van-cell>
+            <van-cell title="计划缺失时间" >
+              <template #label>
+                <van-cell title="1" :value="dayjs(selectedUser.arrivalTime).format('YYYY-DD-MM HH:mm')"></van-cell>
+                <van-cell title="2" :value="dayjs(selectedUser.arrivalTime).format('YYYY-DD-MM HH:mm')"></van-cell>
+                <van-cell title="3" :value="dayjs(selectedUser.arrivalTime).format('YYYY-DD-MM HH:mm')"></van-cell>
+              </template>
+            </van-cell>
+          </div>
+          <div class="big-btn-box" >
+            <van-button  type="info" size="large" @click="onSubmit">生成运维单</van-button>
+          </div>
+        </van-panel>
+      </div>
+
+    </div>
+  </div>
+</template>
+
+<script>
+
+import DateCell from "@/components/dateCell/index.vue";
+import Uploader from "@/components/upload/gxuploader.vue";
+import {formatDate} from "@/filters/filter";
+import {mapGetters} from "vuex";
+import {imgUrl} from "@/utils";
+import { ImagePreview } from 'vant'
+import {userDetails, userDepart} from './api'
+import dayjs from 'dayjs'
+export default {
+  components: {Uploader, DateCell},
+  data(){
+    return {
+      legend:[
+        {
+          type:'正常',
+          color:'#009240',
+        },
+        {
+          type:'运维',
+          color:'#FFA500',
+        },
+        {
+          type:'异常',
+          color:'#D7000F',
+        },
+        {
+          type:'未上报',
+          color:'#aaaaaa',
+        }
+      ],
+      tagList:[
+        {
+          name:'通道',
+          state:1,
+        },
+        {
+          name:'通道',
+          state:3,
+        },
+        {
+          name:'通道',
+          state:2,
+        },
+        {
+          name:'通道',
+          state:1,
+        },
+        {
+          name:'通道',
+          state:3,
+        },
+        {
+          name:'通道',
+          state:2,
+        },
+        {
+          name:'通道',
+          state:1,
+        },
+        {
+          name:'通道',
+          state:3,
+        },
+        {
+          name:'通道',
+          state:2,
+        },
+        {
+          name:'通道',
+          state:1,
+        },
+        {
+          name:'通道',
+          state:3,
+        },
+        {
+          name:'通道',
+          state:2,
+        },
+        {
+          name:'通道',
+          state:1,
+        },
+        {
+          name:'通道',
+          state:3,
+        },
+        {
+          name:'通道',
+          state:2,
+        },
+      ],
+      maxData:new Date(),
+      minDate:null,
+      visitId:null,
+      userList:[],
+      selectedUser:{},
+      prop:{
+        label:'userName',
+        value:'id'
+      },
+      formData:{
+        arrivalTime:null,
+        departureTime:null,
+      },
+      dicts:['out_in_approve_status','out_in_type','letter_id_type']
+    }
+  },
+  computed:{
+    ...mapGetters(['orgId','id','dictionary']),
+  },
+  created(){
+    this.visitId = this.$route.query.id;
+    this.getUserInfo();
+  },
+  methods:{
+    imgUrl,formatDate,
+    getColor(s){
+      if(s ===1){
+        return '#009240';
+      }
+      if(s ===2){
+        return '#D7000F';
+      }
+      if(s===3){
+        return '#FFA500';
+      }
+    },
+    clickTag(){
+
+    },
+    onSubmit(){
+      this.$router.replace({
+        name:'addOrder',
+        path:'/addOrder',
+      });
+    },
+    getUserInfo(){
+      userDetails(this.visitId).then(res=>{
+        let checkImage = res.data.checkImage.split(',');
+        let imgFile = res.data.imgFile.split(',');
+        let letterFile = [];
+        if(res.data.letterFile && res.data.letterFile.length > 0){
+            letterFile = res.data.letterFile.map(v=>{
+            return JSON.parse(v)
+          })
+        }
+        this.selectedUser = res.data;
+        this.selectedUser.checkImage = checkImage;
+        this.selectedUser.imgFile = imgFile;
+        this.selectedUser.letterFile = letterFile;
+        //设置最小时间
+        let minDate = this.selectedUser.arrivalTime;
+        this.minDate = new Date(minDate);
+      })
+    },
+    previewFile(file){
+      this.openFilePreview(file);
+    },
+    preView(val) {
+      if(Array.isArray(val)){
+        let arr = val.map(v=>{
+          return imgUrl(v);
+        })
+        ImagePreview(arr);
+      }else {
+        ImagePreview([imgUrl(val)]);
+      }
+    },
+  }
+}
+</script>
+<style lang="scss">
+.record-detail{
+  .van-card{
+    padding: 20px;
+  }
+  .card-cell-box{
+    width: 70%;
+    .van-cell{
+      padding: 10px;
+      &::after{
+        left:10px;
+        right:10px;
+      }
+    }
+    .van-cell__title{
+      flex:.25;
+    }
+    .van-cell__value{
+      flex:.75;
+    }
+  }
+}
+</style>
+<style scoped lang="scss">
+.record-detail{
+  height: 100%;
+  overflow: hidden;
+}
+.page-container{
+  height: calc(100vh - 94px);
+  overflow: auto;
+  padding: 20px;
+
+}
+.tag-box{
+   padding: 20px;
+   display:  grid;
+   grid-template-columns: repeat(4, 1fr);
+  .tag-item{
+    position: relative;
+    width: 130px;
+    height: 70px;
+    display: flex;
+    justify-content: center;
+    align-items: center;
+    margin: 10px 18px;
+    font-size: 26px;
+    background-color: #009dff;
+    border:1px solid #009dff;
+    color:#fff;
+    padding:10px;
+    border-radius: 10px;
+    white-space: nowrap;
+    &:hover{
+      color: #009dff;
+      background-color:#fff!important;
+    }
+    .top-dot{
+      position: absolute;
+      right: -24px;
+      top:-18px;
+      min-width: 36px;
+      color:#fff;
+      padding: 4px;
+      display: flex;
+      justify-content: center;
+      align-items: center;
+      font-size: 24px;
+      -border: 1px solid #eaeaea;
+      border-radius: 10px;
+      background-color: rgba(0,0,0,.3);
+    }
+  }
+}
+.flex-box{
+  display: flex;
+  justify-content: space-between;
+  align-items: center;
+  >span{
+    margin: 0 20px;
+  }
+}
+.card{
+  margin-bottom: 20px;
+  box-shadow: 0 10px 10px #eaeaea;
+}
+.card:last-child{
+  margin-bottom: 0;
+}
+.panel-box{
+  -padding:0 20px;
+}
+.panel-box-item{
+  height: 36px;
+  line-height: 36px;
+}
+.item-label{
+  width: 100%;
+  display: flex;
+  justify-content: right;
+  align-items: center;
+}
+.item-value{
+  width: 100%;
+  display: flex;
+  justify-content: left;
+  align-items: center;
+}
+.upload-box{
+  padding: 20px 30px;
+  display: flex;
+  >span{
+    display: inline-block;
+    height: 160px;
+    width: 200px;
+    line-height: 160px;
+    font-size: 28px;
+    color:#999;
+    >i{
+      font-style: normal;
+      color: #ee0a24;
+    }
+  }
+  .required::before{
+    content: '*';
+    color: #ee0a24;
+    position: absolute;
+    left: 14px;
+  }
+}
+.goods-card{
+  width: 100%;
+  display: flex;
+  align-items: center;
+  padding: 10px;
+  background-color: #fff;
+  .card-img-box{
+    width: 200px;
+    height: 200px;
+    margin-right: 10px;
+    >img{
+      width: 100%;
+      height: 100%;
+      object-fit: cover;
+      border-radius: 10px;
+    }
+  }
+}
+.big-btn-box{
+  padding: 20px;
+}
+.file-box{
+  width: 70%;
+  display: flex;
+  justify-content: flex-end;
+  color:#008cd6;
+}
+.nfc-img {
+  display: inline-block;
+  width: 140px;
+  height: 140px;
+  margin: 0 10px;
+  position: relative;
+  > img {
+    width: 100%;
+    height: 100%;
+    border: none;
+  }
+  > span {
+    position: absolute;
+    padding: 0 10px;
+    bottom: 0;
+    left: 0;
+    display: block;
+    width: 100%;
+    background-color: rgba(0, 0, 0, 0.2);
+    color: #eaeaea;
+    font-size: 20px;
+    overflow: hidden;
+    text-overflow: ellipsis;
+    white-space: nowrap;
+    line-height: 30px;
+    height: 30px;
+  }
+}
+</style>

+ 31 - 28
src/views/menu/iot/videoDay/index.vue

@@ -2,17 +2,19 @@
   <div class="visitRecord">
     <NavBar/>
     <div class="page-container">
-      <van-search v-model="query.userName" class="van-hairline--bottom" placeholder="请输入人员姓名" @clear="refreshData"  @change="refreshData"/>
+      <div class="org-line van-hairline--bottom">
+        <org-tree clearable v-model="query.beCheckedOrgId" placeholder="选择机构" @change="refreshData"></org-tree>
+      </div>
       <div class="search-flex">
         <select-cell
           style="border-right: 1px solid #f5f5f5;"
-          title="介绍信类型"
+          title="状态"
           is-all
+          is-row
           :border="false"
           v-model="query.type"
           :data-list="getDictItem('out_in_type')"
           @change="refreshData"/>
-        <date-cell title="日期" is-all v-model="query.arrivalTime" date-type="date" @change="refreshData"/>
       </div>
       <div class="card-list">
         <Scroll
@@ -24,36 +26,24 @@
           <card v-else v-for="(v,i) in dataList" :key="v.id">
             <van-cell
               :border="false"
-              class="item-title"
-              :title-style="{color:'#008cd6'}"
-              :title="`介绍信类型: ${getDictLabel(v.type,'out_in_type')}`"
-              @click="clickItem(v.id)">
-              <template #right-icon>
-                <van-button v-if="!v.departureTime" type="info" size="mini">登记离开时间</van-button>
-              </template>
-            </van-cell>
-            <van-cell
-              :border="false"
               class="item-value"
               @click="clickItem(v.id)">
               <template #default>
+                <div class="info-item">
+                  <div class="item-label item-device">XXX区域</div>
+                  <i  class="point-icon" :class="{'active':!v.isRead}" />
+                </div>
                 <div class="info-box">
                   <div class="info-item">
-                    <div class="item-label">人员姓名</div>
+                    <div class="item-label">品牌</div>
                     <div class="item-value"> {{v.userName}}</div>
                   </div>
                   <div class="info-item">
-                    <div class="item-label">到达时间</div>
+                    <div class="item-label">机构</div>
                     <div class="item-value">
                       {{ dayjs(v.arrivalTime).format('YYYY-MM-DD HH:mm')}}
                     </div>
                   </div>
-                  <div class="info-item">
-                    <div class="item-label">离开时间</div>
-                    <div class="item-value">
-                      {{v.departureTime? dayjs(v.departureTime).format('YYYY-MM-DD HH:mm') : '暂无'}}
-                    </div>
-                  </div>
                 </div>
               </template>
             </van-cell>
@@ -104,7 +94,6 @@
         </Scroll>
       </div>
     </div>
-    <drag-button @btnClick="clickAdd"></drag-button>
   </div>
 </template>
 <script>
@@ -116,15 +105,12 @@ import dateCell from '@/components/dateCell/index.vue'
 import selectCell from '@/components/selectCell/index.vue'
 import {dataList} from './api'
 import {mapGetters} from "vuex";
-import {formatDate} from "@/filters/filter";
-import DragButton from "@/components/DragButton/index.vue";
 import dayjs from "dayjs";
 import Item from "@/views/menu/protection/components/item.vue";
 export default {
   name: 'visitRecord',
   components: {
     Item,
-    DragButton,
     NavBar,
     OrgTree,
     Scroll,
@@ -204,7 +190,7 @@ export default {
     },
     clickItem(id){
       this.$router.push({
-        path:'/visitRecordDetail',
+        path:'/videoDayDetail',
         query:{id}
       });
     }
@@ -241,8 +227,9 @@ export default {
 }
 .card-list{
   padding:0 20px 20px 20px;
-  height: calc(100vh - 426px);
+  height: calc(100vh - 372px);
   overflow:  auto;
+  -border: 1px solid red;
 }
 .item-title{
   border-bottom: 1px solid #f5f5f5;
@@ -260,7 +247,7 @@ export default {
   justify-content: space-between;
   border-bottom: 1px solid #f5f5f5;
   >div{
-    width: 50%;
+    width: 100%;
   }
 }
 .btn-box{
@@ -311,5 +298,21 @@ export default {
     overflow: hidden;
     text-overflow: ellipsis;
   }
+  .item-device{
+    font-size: 32px;
+    color:#008cd6;
+  }
+  .point-icon{
+    width: 20px;
+    height: 20px;
+    background-color:#ccc;
+    border-radius: 50%;
+    margin-top: 10px;
+    display: none;
+    &.active{
+      display: block;
+      background-color: #ee0a24;
+    }
+  }
 }
 </style>

+ 26 - 9
src/views/menu/iot/videoIntegrity/detail.vue

@@ -3,10 +3,7 @@
     <nav-bar></nav-bar>
     <div class="page-container">
       <div class="card">
-        <van-panel>
-          <template #header>
-            <span></span>
-          </template>
+        <van-panel title="XXX区域">
           <div class="tag-box">
             <div v-for="(v,i) in tagList"
              class="tag-item"
@@ -15,6 +12,12 @@
               {{v.name+i}}
             </div>
           </div>
+          <ul class="legend">
+            <li v-for="v in legend" :key="v.type">
+              <span :style="{background:v.color}"></span>
+              {{v.type}}
+            </li>
+          </ul>
         </van-panel>
       </div>
       <!--   基本信息   -->
@@ -73,6 +76,20 @@ export default {
   components: {Uploader, DateCell},
   data(){
     return {
+      legend:[
+        {
+          type:'正常',
+          color:'#009240',
+        },
+        {
+          type:'运维',
+          color:'#FFA500',
+        },
+        {
+          type:'异常',
+          color:'#D7000F',
+        }
+      ],
       tagList:[
         {
           name:'通道',
@@ -256,6 +273,7 @@ export default {
   .tag-item{
     width: 130px;
     height: 70px;
+    font-size: 26px;
     display: flex;
     justify-content: center;
     align-items: center;
@@ -265,11 +283,10 @@ export default {
     color:#fff;
     padding:10px;
     border-radius: 10px;
-    //&:hover{
-    //  color: #009dff;
-    //  background-color:#fff;
-    //  border:1px solid #009dff;
-    //}
+    &:hover{
+      color: #009dff;
+      background-color:#fff!important;
+    }
   }
 }
 .flex-box{

+ 1 - 1
src/views/menu/iot/videoIntegrity/index.vue

@@ -30,7 +30,7 @@
               @click="clickItem(v.id)">
               <template #default>
                 <div class="info-item">
-                  <div class="item-label item-device">XXX设备</div>
+                  <div class="item-label item-device">XXX区域</div>
                   <i  class="point-icon" :class="{'active':!v.isRead}" />
                 </div>
                 <div class="info-box">