<template>
  <div class="app-container tsb-home">
    <div class="tsb-home-header">
      <h2 class="tsb-home-title">调试宝设备</h2>
    </div>

    <div v-loading="loading">
      <div v-if="onlineDevices.length" class="section-block">
        <div class="section-title">
          <span>已登录设备</span>
          <el-tag size="mini" type="success">{{ onlineDevices.length }}</el-tag>
        </div>
        <el-row :gutter="16">
          <el-col v-for="item in onlineDevices" :key="'on-' + item.deviceId" :xs="24" :sm="12" :md="8" :lg="6">
            <device-card :device="item" :active="isActive(item)" @operate="handleOperate" />
          </el-col>
        </el-row>
      </div>

      <el-collapse v-if="offlineDevices.length" v-model="offlineCollapse" class="offline-collapse">
        <el-collapse-item name="offline">
          <template slot="title">
            <span class="section-title inline">
              <span>未登录设备</span>
              <el-tag size="mini" type="info">{{ offlineDevices.length }}</el-tag>
              <span class="collapse-hint">点击标题可展开/收起</span>
            </span>
          </template>
          <el-row :gutter="16">
            <el-col v-for="item in offlineDevices" :key="'off-' + item.deviceId" :xs="24" :sm="12" :md="8" :lg="6">
              <device-card :device="item" offline />
            </el-col>
          </el-row>
        </el-collapse-item>
      </el-collapse>

      <el-empty v-if="!loading && !deviceList.length" description="暂无调试宝设备" />
    </div>
  </div>
</template>

<script>
import { listTsbDeviceHome } from '@/api/tsb/device'
import tsbWebSocket from '@/utils/tsbWebSocket'
import { navigateToWorkspace } from '@/utils/tsbWorkspaceNav'
import DeviceCard from './dashboard/DeviceCard'

export default {
  name: 'Index',
  components: { DeviceCard },
  data() {
    return {
      loading: false,
      deviceList: [],
      offlineCollapse: [],
      refreshTimer: null,
      connectingDeviceSn: null
    }
  },
  computed: {
    onlineDevices() {
      return this.deviceList.filter(d => Number(d.lineStatus) === 1)
    },
    offlineDevices() {
      return this.deviceList.filter(d => Number(d.lineStatus) !== 1)
    },
    openedDevices() {
      return this.$store.getters.tsbOpenedDevices || []
    }
  },
  created() {
    this.loadDevices()
    this.refreshTimer = setInterval(() => this.loadDevices(true), 30000)
  },
  beforeDestroy() {
    if (this.refreshTimer) {
      clearInterval(this.refreshTimer)
    }
  },
  methods: {
    loadDevices(silent) {
      if (!silent) {
        this.loading = true
      }
      listTsbDeviceHome().then(res => {
        const data = res.data
        this.deviceList = Array.isArray(data) ? data : []
      }).catch(() => {
        this.deviceList = []
      }).finally(() => {
        this.loading = false
      })
    },
    isActive(device) {
      return this.openedDevices.some(d => d.deviceSn === device.deviceSn)
    },
    handleOperate(device) {
      if (this.connectingDeviceSn === device.deviceSn) {
        return
      }
      this.connectingDeviceSn = device.deviceSn
      tsbWebSocket.connectWithDevice(device).then(() => {
        navigateToWorkspace().catch(() => {})
      }).catch((err) => {
        const msg = typeof err === 'string' ? err : (err && (err.message || err.msg)) || '设备连接失败'
        this.$message.error(msg)
      }).finally(() => {
        this.connectingDeviceSn = null
      })
    }
  }
}
</script>

<style scoped lang="scss">
.tsb-home-header {
  margin-bottom: 16px;
}
.tsb-home-title {
  margin: 0;
  font-size: 20px;
  font-weight: 600;
}
.section-block {
  margin-bottom: 20px;
}
.section-title {
  display: flex;
  align-items: center;
  gap: 8px;
  margin-bottom: 12px;
  font-size: 15px;
  font-weight: 500;
  &.inline {
    margin-bottom: 0;
  }
}
.collapse-hint {
  margin-left: 4px;
  font-size: 12px;
  font-weight: normal;
  color: #909399;
}
.offline-collapse {
  border: none;
  ::v-deep .el-collapse-item__header {
    border-bottom: none;
    font-size: 15px;
  }
  ::v-deep .el-collapse-item__wrap {
    border-bottom: none;
  }
}
</style>
