index.vue 11 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412
  1. <template>
  2. <div class="c-monitor-dashboard">
  3. <audio
  4. v-show="false"
  5. ref="alarmNormal"
  6. muted
  7. src="@/assets/v1/alarmNormal.mp3"
  8. />
  9. <audio
  10. v-show="false"
  11. ref="alarmUrgent"
  12. muted
  13. src="@/assets/v1/alarmUrgent.mp3"
  14. />
  15. <div
  16. class="c-monitor-dashboard__main"
  17. :style="style"
  18. >
  19. <department-drawer
  20. ref="departmentDrawer"
  21. @change="onGroupChanged"
  22. />
  23. <Header ref="Header">
  24. <template #content>
  25. <div
  26. class="c-monitor-dashboard__mode has-active"
  27. @click="onClickBusiness"
  28. >
  29. 切换为运营大数据
  30. </div>
  31. </template>
  32. </Header>
  33. <NewNotice
  34. class="new-notice"
  35. :class="{ active: showNotice }"
  36. :notice="curNotice"
  37. :count="noticeCount"
  38. />
  39. <div class="l-flex--col center">
  40. <div class="l-flex--row">
  41. <div class="l-flex--col l-flex__none">
  42. <div
  43. class="l-flex__none dashboard-block"
  44. style="width: 1040px; height: 450px"
  45. >
  46. <MessageNotice
  47. ref="MessageNotice"
  48. @new-alarm="onNewAlarm"
  49. />
  50. </div>
  51. <div class="l-flex__none dashboard-block l-flex--row">
  52. <div
  53. class="l-flex__none l-flex--col block-item"
  54. style="width: 510px; height: 450px"
  55. >
  56. <AssetStatistic />
  57. </div>
  58. <div
  59. class="l-flex__none l-flex--col block-item"
  60. style="width: 510px; height: 450px"
  61. >
  62. <ProgramStatistic />
  63. </div>
  64. </div>
  65. <div class="l-flex__none dashboard-block l-flex--row">
  66. <div
  67. class="l-flex__none l-flex--col block-item"
  68. style="width: 510px; height: 450px"
  69. >
  70. <ProgramRate />
  71. </div>
  72. <div
  73. class="l-flex__none l-flex--col block-item"
  74. style="width: 510px; height: 450px"
  75. >
  76. <ProgramTop />
  77. </div>
  78. </div>
  79. </div>
  80. <div class="l-flex--col l-flex__none">
  81. <div
  82. class="l-flex__none dashboard-block"
  83. style="width: 1480px; height: 1390px"
  84. >
  85. <Map
  86. ref="map"
  87. :status-data="statusData"
  88. :device-list="deviceList"
  89. @closeAlarm="onCloseAlarm"
  90. >
  91. <template #default>
  92. <div
  93. class="c-department-button has-active"
  94. @click="onShowDepatment"
  95. >
  96. 概况
  97. </div>
  98. </template>
  99. </Map>
  100. </div>
  101. </div>
  102. <div class="l-flex--col l-flex__none">
  103. <div
  104. class="l-flex__none dashboard-block"
  105. style="width: 1040px; height: 685px"
  106. >
  107. <Record ref="record" />
  108. </div>
  109. <div
  110. class="l-flex__none dashboard-block"
  111. style="width: 1040px; height: 685px"
  112. >
  113. <CameraScreen />
  114. </div>
  115. </div>
  116. </div>
  117. <div class="l-flex--row">
  118. <div class="l-flex--col l-flex__none">
  119. <div
  120. v-if="false"
  121. class="l-flex__none dashboard-block"
  122. style="width: 1040px; height: 450px"
  123. >
  124. <DeviceCalender :device-list="deviceList" />
  125. </div>
  126. <div
  127. v-else
  128. class="l-flex__none dashboard-block l-flex--row"
  129. >
  130. <div
  131. class="l-flex__none l-flex--col block-item"
  132. style="width: 510px; height: 450px"
  133. >
  134. <ProgramTop type="getTopOnlineSeconds" />
  135. </div>
  136. <div
  137. class="l-flex__none l-flex--col block-item"
  138. style="width: 510px; height: 450px"
  139. >
  140. <ProgramTop
  141. :type="topMap[topIndex]"
  142. @click.native="topIndex=(topIndex+1)%topMap.length"
  143. />
  144. </div>
  145. </div>
  146. </div>
  147. <div
  148. class="l-flex__none l-flex--col"
  149. style="width: 730px; height: 450px"
  150. >
  151. <AlarmLevel />
  152. </div>
  153. <div
  154. class="l-flex__none l-flex--col"
  155. style="width: 730px; height: 450px"
  156. >
  157. <AlarmRate />
  158. </div>
  159. <div class="l-flex--col l-flex__none">
  160. <div
  161. class="l-flex__none dashboard-block"
  162. style="width: 1040px; height: 450px"
  163. >
  164. <AlarmType />
  165. </div>
  166. </div>
  167. </div>
  168. </div>
  169. </div>
  170. </div>
  171. </template>
  172. <script>
  173. import { Index } from './config'
  174. import {
  175. getDevicesByQuery,
  176. getDeviceStatisticsByPath
  177. } from '@/api/device'
  178. import DeviceCalender from './DeviceCalender'
  179. import Map from './Map'
  180. import AlarmType from './AlarmType'
  181. import AlarmRate from './AlarmRate'
  182. import AlarmLevel from './AlarmLevel'
  183. import MessageNotice from './MessageNotice'
  184. import Record from './Record'
  185. // import SystemLoad from './SystemLoad'
  186. import Header from './Header'
  187. import ProgramRate from './ProgramRate'
  188. import ProgramTop from './ProgramTop'
  189. import AssetStatistic from './AssetStatistic'
  190. import ProgramStatistic from './ProgramStatistic'
  191. import CameraScreen from './CameraScreen'
  192. import NewNotice from './NewNotice'
  193. export default {
  194. components: {
  195. AssetStatistic,
  196. ProgramStatistic,
  197. Map,
  198. AlarmType,
  199. AlarmRate,
  200. MessageNotice,
  201. Record,
  202. DeviceCalender,
  203. AlarmLevel,
  204. Header,
  205. ProgramRate,
  206. ProgramTop,
  207. // SystemLoad,
  208. CameraScreen,
  209. NewNotice
  210. },
  211. data () {
  212. this.topMap = ['getPagePriceRank', 'getPageDurationRank', 'getPageCountRank']
  213. return {
  214. topIndex: 0,
  215. style: null,
  216. statusData: [
  217. { label: '设备总数', value: '-' },
  218. { label: '设备在线数', value: '-' },
  219. { label: '设备离线数', value: '-' },
  220. { label: '设备未启用数', value: '-' }
  221. ],
  222. deviceList: [],
  223. showNotice: false,
  224. curNotice: {},
  225. noticeCount: Index.noticeTimer,
  226. group: { path: this.$store.getters.org }
  227. }
  228. },
  229. computed: {
  230. mapDeviceList () {
  231. return this.deviceList.filter(i => i.longitude && i.latitude)
  232. }
  233. },
  234. created () {
  235. this.getDeviceStatistics()
  236. this.$timer = setInterval(this.getDeviceStatistics, Index.deviceTimer)
  237. },
  238. mounted () {
  239. this.checkScale()
  240. window.addEventListener('resize', this.checkScale)
  241. document.querySelector('body').setAttribute('version', '')
  242. },
  243. beforeDestroy () {
  244. clearInterval(this.$timer)
  245. clearInterval(this.$newAlarmTimer)
  246. window.removeEventListener('resize', this.checkScale)
  247. document.querySelector('body').setAttribute('version', __VERSION__)
  248. },
  249. methods: {
  250. onGroupChanged ({ path, name }) {
  251. if (!this.group || this.group.path !== path) {
  252. this.group = { path, name }
  253. this.getDeviceStatistics()
  254. }
  255. },
  256. onShowDepatment () {
  257. this.$refs.departmentDrawer.show()
  258. },
  259. checkScale () {
  260. this.style = {
  261. transform: `scale(${window.innerWidth / 3840}, ${
  262. window.innerHeight / 2160
  263. })`
  264. }
  265. },
  266. playAlarm (type) {
  267. const audio = this.$refs[type]
  268. if (!audio) { return }
  269. if (!audio.paused) {
  270. audio.currentTime = 0
  271. }
  272. audio.play()
  273. },
  274. onCloseAlarm (alarm) {
  275. this.$refs.MessageNotice.closeNewAlarm(alarm)
  276. },
  277. onNewAlarm (alarm) {
  278. const onlineMap = [32, 9]
  279. const offlineMap = [1, 15, 16, 17]
  280. if (onlineMap.includes(alarm.deviceErrorId)) {
  281. this.getDeviceStatistics()
  282. this.$refs.map?.closeOfflineAlarm(alarm, offlineMap)
  283. }
  284. if (offlineMap.includes(alarm.deviceErrorId)) {
  285. this.getDeviceStatistics()
  286. }
  287. if (alarm.level > 1) {
  288. this.$refs.map?.setNewAlarm(alarm)
  289. this.playAlarm('alarmUrgent')
  290. } else {
  291. this.playAlarm('alarmNormal')
  292. this.showNotice = true
  293. this.curNotice = alarm
  294. clearInterval(this.$newAlarmTimer)
  295. this.noticeCount = Index.noticeTimer / 1000
  296. this.$newAlarmTimer = setInterval(() => {
  297. this.noticeCount--
  298. if (this.noticeCount <= 0) {
  299. this.showNotice = false
  300. this.noticeCount = 0
  301. clearInterval(this.$newAlarmTimer)
  302. }
  303. }, 1000)
  304. }
  305. },
  306. getDeviceStatistics () {
  307. getDeviceStatisticsByPath(this.group.path).then(({ data }) => {
  308. const {
  309. deactivatedTotal,
  310. notConnectedTotal,
  311. offLineTotal,
  312. onLineTotal,
  313. total
  314. } = data
  315. this.statusData = [
  316. { label: '设备总数', value: total },
  317. { label: '设备在线数', value: onLineTotal },
  318. { label: '设备离线数', value: offLineTotal + notConnectedTotal },
  319. { label: '设备未启用数', value: deactivatedTotal }
  320. ]
  321. this.getDevices(total - deactivatedTotal)
  322. })
  323. },
  324. getDevices (total) {
  325. getDevicesByQuery(
  326. {
  327. pageNum: 1,
  328. pageSize: total,
  329. activate: 1,
  330. org: this.group.path
  331. },
  332. { custom: true }
  333. ).then(({ data }) => {
  334. this.deviceList = data
  335. })
  336. },
  337. onClickBusiness () {
  338. this.$router.push({
  339. name: 'v-business',
  340. params: { isFullScreen: this.$refs.Header.getFullScreen() ? '1' : '' }
  341. })
  342. }
  343. }
  344. }
  345. </script>
  346. <style lang="scss" scoped>
  347. .c-monitor-dashboard {
  348. height: 100%;
  349. overflow: hidden;
  350. &__main {
  351. width: 3840px;
  352. height: 2160px;
  353. background: url("~@/assets/v1/monitor_bg.png");
  354. transform-origin: left top;
  355. }
  356. &__mode {
  357. position: absolute;
  358. left: 135px;
  359. bottom: 10px;
  360. font-size: 32px;
  361. z-index: 999;
  362. }
  363. }
  364. .dashboard-block {
  365. & ~ & {
  366. margin-top: 20px;
  367. }
  368. }
  369. .l-flex--row {
  370. & ~ & {
  371. margin-top: 20px;
  372. }
  373. }
  374. .l-flex--col {
  375. & ~ & {
  376. margin-left: 20px;
  377. }
  378. }
  379. .new-notice {
  380. position: fixed;
  381. bottom: 0;
  382. right: 0;
  383. width: 640px;
  384. min-height: 360px;
  385. transition: all 1s;
  386. z-index: 999;
  387. transform: translateY(100%);
  388. &.active {
  389. transform: translateY(0);
  390. }
  391. }
  392. .c-department-button {
  393. position: absolute;
  394. top: 0;
  395. left: 0;
  396. font-size: 32px;
  397. line-height: 64px;
  398. z-index: 1;
  399. }
  400. </style>