Explorar el Código

[FE]首页人脸识别 视频监控布局

chenxr3 %!s(int64=4) %!d(string=hace) años
padre
commit
4b37da7ef4

+ 1 - 1
ebc-middle-platform/src/assets/locals/zh-CN.json

@ -81,7 +81,7 @@
81 81
      "hello": "您好",
82 82
      "welcome": "欢迎登录",
83 83
      "system": "系统",
84
      "demo": "系统名称",
84
      "demo": "人员定位与搜救",
85 85
      "username": "用户名",
86 86
      "account": "账户名",
87 87
      "password": "密码",

+ 15 - 3
ebc-middle-platform/src/components/loginer.vue

@ -158,11 +158,23 @@ export default {
158 158
            this.$test
159 159
              .post(services.login.FIND_MENUS, {userCode: data.RESULT.CODE})
160 160
              .then((data) => {
161
162
                localStorage.setItem('menus',  JSON.stringify(data))
161
                var map = new Map()
162
                data.RESULT.forEach(e => {
163
                  if (e.ROOT_MENU){
164
                    map.set(e.ROOT_MENU[0].NAME,e.ROOT_MENU[0].ID)
165
                  }
166
                  map.set(e.NAME,e.ID)
167
                  if (e.menu_list) {
168
                    e.menu_list.forEach( m => {
169
                      map.set(m.NAME,m.ID)
170
                    })
171
                  }
172
                })
173
                debugger
174
                localStorage.setItem('menus',  JSON.stringify(map))
163 175
                store.dispatch(`permission/${GENERATE_ROUTES}`, roles)
176
                this.$router.push({ name: this.homeName })
164 177
              })
165
            this.$router.push({ name: this.homeName })
166 178
          }).catch((e) => {
167 179
            this.loging = false
168 180
            this.$Message.danger(e)

+ 4 - 0
security-protection-platform/src/api/dashboard/index.js

@ -20,6 +20,10 @@ const api = {
20 20
    return $default.get('/sp/homePage/queryAlarmAnalysisTopList', {}).then(resp => {
21 21
      return resp.data
22 22
    })
23
  },
24
  // 进出识别
25
  queryHomeLastInAndOutRecord (data) {
26
    return $default.get('/sp/inAndOutRecord/queryHomeLastInAndOutRecord?monitorSceneId=3', data)
23 27
  }
24 28
  // 直播流
25 29
  // queryMonitorSceneTerminalRel () {

+ 64 - 13
security-protection-platform/src/modules/dashboard/index.vue

@ -70,17 +70,16 @@
70 70
          <span class="title-span">人员进出识别</span>
71 71
        </div>
72 72
        <div v-for="(item,index) in distinguishData" :style="`background-image: url(${border})`" class="distinguish">
73
          <div class="distinguish-title"> {{ item.name }} </div>
73
          <div class="distinguish-title"> {{ item.monitorSceneName }} </div>
74 74
          <div class="distinguish-row">
75 75
            <div class="similarity">
76
              <p style="opacity: 1;font-size: 12px">70%</p>
76
              <p class="p">{{ item.simi }}</p>
77 77
            </div>
78
            <img src="@/assets/images/indexT1.png" class="distinguish-col">
79
            <img src="@/assets/images/indexT1.png" class="distinguish-col">
78
            <img :src="item.newImg" alt="" class="distinguish-col">
79
            <img :src="item.headerImage" class="distinguish-col">
80 80
            <div style="width: 40%;margin-top: 4%;height: 79%;">
81
              <div class="distinguish-col-row">王小明(00220)</div>
82
              <div class="distinguish-col-row">已佩戴口罩</div>
83
              <div class="distinguish-col-row">2021.01.05 12:11:00</div>
81
              <div class="distinguish-col-row">{{ item.employeeName }}({{ item.employeeCode }})</div>
82
              <div class="distinguish-col-row">{{ item.taskExecuteTime }}</div>
84 83
            </div>
85 84
          </div>
86 85
        </div>
@ -92,6 +91,7 @@
92 91
93 92
<script>
94 93
import imgBg from '@/assets/images/indexTop.png'
94
import avatar from '@/assets/images/avatar.png'
95 95
import titleImgBg from '@/assets/images/indexTitle.png'
96 96
import polygon from '@/assets/images/polygon.png'
97 97
import border from '@/assets/images/border.png'
@ -159,7 +159,7 @@ export default {
159 159
        sources: [{
160 160
          withCredentials: false,
161 161
          type: 'application/x-mpegURL', // 这里的种类支持很多种:基本视频格式、直播、流媒体等,具体可以参看git网址项目
162
          src: 'http://10.19.90.34:1080/live/1.m3u8' // url地址
162
          src: 'http://10.19.90.34:1080/live/01.m3u8' // url地址
163 163
        }],
164 164
        flash: { hls: { withCredentials: false } },
165 165
        html5: { hls: { withCredentials: false } },
@ -174,6 +174,7 @@ export default {
174 174
      videoOptionsList: [],
175 175
      imgBg: imgBg,
176 176
      titleImgBg: titleImgBg,
177
      avatar: avatar,
177 178
      polygon: polygon,
178 179
      border: border,
179 180
      attendanceData: [],
@ -182,10 +183,7 @@ export default {
182 183
      alarmDataY: [],
183 184
      topData: [],
184 185
      topData1: [],
185
      distinguishData: [{name: '1风场', url: '@/assets/images/indexT1.png', url2: '@/assets/images/indexT1.png'},
186
        {name: '2风场', url: '@/assets/images/indexT1.png', url2: '@/assets/images/indexT1.png'},
187
        {name: '3风场', url: '@/assets/images/indexT1.png', url2: '@/assets/images/indexT1.png'},
188
        {name: '2风场', url: '@/assets/images/indexT1.png', url2: '@/assets/images/indexT1.png'}]
186
      distinguishData: []
189 187
    }
190 188
  },
191 189
  computed: {
@ -195,9 +193,13 @@ export default {
195 193
    setInterval(() => { // 当前时间
196 194
      this.nowDate = new Date()
197 195
    }, 1000)
196
    this.initRecognition()
198 197
    this.initAttendance()
199 198
    this.initAlarm()
200 199
    this.init24Top()
200
    setInterval(() => { // 识别记录
201
      this.initRecognition()
202
    }, 10000)
201 203
  },
202 204
  methods: {
203 205
    initVideo() {
@ -292,6 +294,46 @@ export default {
292 294
        }
293 295
      })
294 296
    },
297
    initRecognition() {
298
      dasapi.queryHomeLastInAndOutRecord({monitorSceneId: 3}).then(res => {
299
        var data = res.data.data
300
        if (data.length > 4){
301
          data = data.slice(0,4)
302
        }
303
        data.forEach(e => {
304
          e.simi = e.simi.split('.')[0] + '%'
305
          e.newImg = e.idenPictureUrl
306
          var loadTimer;
307
          var imgObject = new Image();
308
          imgObject.setAttribute('crossOrigin', 'anonymous');
309
          imgObject.src = e.idenPictureUrl;
310
          imgObject.onLoad = onImgLoaded();
311
          function onImgLoaded() {
312
            if (loadTimer != null) clearTimeout(loadTimer);
313
            if (!imgObject.complete) {
314
              loadTimer = setTimeout(function() {
315
                onImgLoaded();
316
              }, 3);
317
            } else {
318
              e.newImg = getImagePortion(imgObject, e.face_box[2] - e.face_box[0], e.face_box[3] - e.face_box[1], e.face_box[0], e.face_box[1]);
319
            }
320
          }
321
          function getImagePortion(imgObj, newWidth, newHeight, startX, startY){
322
            var tnCanvas = document.createElement('canvas');
323
            var tnCanvasContext = tnCanvas.getContext('2d');
324
            tnCanvas.width = newWidth; tnCanvas.height = newHeight;
325
            var bufferCanvas = document.createElement('canvas');
326
            var bufferContext = bufferCanvas.getContext('2d');
327
            bufferCanvas.width = imgObj.width;
328
            bufferCanvas.height = imgObj.height;
329
            bufferContext.drawImage(imgObj, 0, 0);
330
            tnCanvasContext.drawImage(bufferCanvas, startX,startY,newWidth, newHeight,0,0,newWidth,newHeight);
331
            return tnCanvas.toDataURL();
332
          }
333
        })
334
        this.distinguishData = data
335
      })
336
    },
295 337
    initAttendanceData() {
296 338
      var dom = document.getElementById('doughnut')
297 339
      var myChart = echarts.init(dom)
@ -602,6 +644,14 @@ export default {
602 644
            opacity: 0.5;
603 645
            border-radius: 50%;
604 646
            padding-top: 1%;
647
            filter:alpha(opacity=50); /*支持IE */
648
            -moz-opacity:0.5; /*支持FF */
649
            //opacity:0.5;
650
            .p{
651
              position:relative;
652
              color: #00d8f3;
653
              font-size: 10px
654
            }
605 655
          }
606 656
          .distinguish-col{
607 657
            width: 27%;
@ -610,7 +660,8 @@ export default {
610 660
          }
611 661
          .distinguish-col-row{
612 662
            padding-left: 5%;
613
            height: 30%;
663
            padding-top: 5%;
664
            height: 40%;
614 665
            width: 130%;
615 666
            color: white;
616 667
            font-size: 14px;

+ 25 - 10
security-protection-platform/src/modules/videoSurveillance/index.vue

@ -11,20 +11,21 @@
11 11
        <t-option v-for="(item,index) in organizationList" :key="index" :value="item.id">{{ item.name }}</t-option>
12 12
      </t-select>
13 13
    </div>
14
    <div class="page-bottom">
15
      <div v-for="(item,index) in videoList" :key="index" :value="item.resourceToolId" style="width:400px;margin:24px 0px 0 24px;">
14
15
    <div class="page-bottom grid-demo">
16
      <t-col v-for="(item,index) in videoList" :span="viewLayoutSpan" :key="index" :value="item.resourceToolId" style="margin-top:24px">
16 17
        <video-player
17
          :ref="'video'+index"
18
          :options="videoOptions[index]"
19
          :playsinline="false"
20
          :events="events"
21
          class="vjs-custom-skin videoPlayer"
22
          @dblclick="handlefullscreenchange"
18
            :ref="'video'+index"
19
            :options="videoOptions[index]"
20
            :playsinline="false"
21
            :events="events"
22
            class="vjs-custom-skin videoPlayer"
23
            @dblclick="handlefullscreenchange"
23 24
        ></video-player>
25
      </t-col>
24 26
      <!-- <rtmp-video :list="getVideoPlayList(item)" @goDistinguishRecord="goDistinguishRecord(item.resourceToolId)" @videoReplay="handleReview"></rtmp-video> -->
25
      </div>
26 27
    </div>
27
    <t-pager :page-size="videoPageSize" :current="videoCurrent" :total="videoTotal" :sizer-range="[ 5, 10, 20, 30 ]" class="pager" show-elevator @on-change="onChangeGate"></t-pager>
28
    <t-pager :page-size="videoPageSize" :current="videoCurrent" :total="videoTotal" :sizer-range="[ 1, 4, 9, 16 ]" class="pager" show-elevator @on-change="onChangeGate"></t-pager>
28 29
    <replay-dialog :list="replayList" :visibled.sync="showReplayDialog" @get-list="queryMonitorVideoLog" />
29 30
  </div>
30 31
</template>
@ -52,6 +53,7 @@ export default {
52 53
  },
53 54
  data () {
54 55
    return {
56
      viewLayoutSpan: 3,
55 57
      events: ['fullscreenchange'],
56 58
      videoOptions: [],
57 59
      videoCurrent: 1, // 大门分页数据
@ -140,6 +142,19 @@ export default {
140 142
        if (element.id === this.gateFieldData) {
141 143
          sysapi.getMonitorScene(this.organizationList[index].id).then((resp) => {
142 144
            this.sceneList = resp.data.data || []
145
            if (resp.data.data[0].monitorViewLayout === '1X1') {
146
              this.viewLayoutSpan = 10
147
              this.videoPageSize = 1
148
            } else if (resp.data.data[0].monitorViewLayout === '2X2') {
149
              this.viewLayoutSpan = 6
150
              this.videoPageSize = 4
151
            } else if (resp.data.data[0].monitorViewLayout === '3X3') {
152
              this.viewLayoutSpan = 4
153
              this.videoPageSize = 9
154
            } else if (resp.data.data[0].monitorViewLayout === '4X4') {
155
              this.viewLayoutSpan = 3
156
              this.videoPageSize = 16
157
            }
143 158
            this.tabClick(this.sceneList[0].monitorSceneId)
144 159
          })
145 160
        }