<template>
  <div class="task-detail-panel">
    <el-card shadow="never" v-if="displayTask">
      <div slot="header" class="detail-header">
        <div class="header-left">
          <div class="title-row">
            <span class="task-title">{{ displayTask.name || displayTask.taskName || '未命名任务' }}</span>
            <el-tag :type="getStatusMeta(displayTask).tag" size="small">
              {{ getStatusMeta(displayTask).label }}
            </el-tag>
          </div>
          <div class="subtitle">
            任务编号：{{ displayTask.taskNo || '-' }} · 事件：{{ getEventName(displayTask) || '-' }}
          </div>
        </div>
        <div class="header-actions">
          <el-button size="mini" icon="el-icon-refresh" @click="refreshDetail" :loading="loadingDetail">
            刷新
          </el-button>
          <el-button 
            size="mini" 
            type="text" 
            :icon="isMobile ? 'el-icon-arrow-left' : 'el-icon-close'" 
            @click="handleClose"
          >
            {{ isMobile ? '返回' : '关闭' }}
          </el-button>
        </div>
      </div>

      <div v-if="loadingDetail" class="detail-loading">
        <i class="el-icon-loading" />
        <span>加载任务详情...</span>
      </div>
      <div v-else>
        <el-descriptions :column="isMobile ? 1 : 2" border class="detail-info">
          <el-descriptions-item label="事件级别">
            <el-tag
              :type="getEventLevelTag(displayTask)"
              size="mini"
            >
              {{ getEventLevel(displayTask) || '-' }}
            </el-tag>
          </el-descriptions-item>
          <el-descriptions-item label="发布时间">
            {{ formatDate(displayTask.createTime) }}
          </el-descriptions-item>
          <el-descriptions-item label="最新更新">
            {{ formatDate(displayTask.updateTime) }}
          </el-descriptions-item>
          <el-descriptions-item label="任务状态">
            {{ getStatusMeta(displayTask).label }}
          </el-descriptions-item>
          <el-descriptions-item label="事件地点" :span="isMobile ? 1 : 2">
            {{ getEventLocation(displayTask) || '未填写' }}
          </el-descriptions-item>
          <el-descriptions-item label="任务描述" :span="isMobile ? 1 : 2">
            {{ displayTask.description || '未填写' }}
          </el-descriptions-item>
        </el-descriptions>

        <el-card shadow="never" class="map-card">
          <div slot="header" class="section-header">
            <span>事件位置</span>
          </div>
          <div v-if="hasEventCoordinates" class="map-wrapper">
            <Amap
              :container-id="mapContainerId"
              height="240px"
              :center="mapCenter"
              :zoom="13"
              :markers="mapMarkers"
            />
            <div class="map-meta">
              <div>{{ getEventLocation(displayTask) || '位置描述缺失' }}</div>
              <div class="coord">
                经度：{{ eventLongitude }} · 纬度：{{ eventLatitude }}
              </div>
            </div>
          </div>
          <el-empty v-else description="暂无位置信息" />
        </el-card>

        <!-- Participants Section -->
        <el-card shadow="never" class="participants-card">
          <div slot="header" class="section-header">
            <span>参与方</span>
          </div>
          <div v-if="participantsLoading" class="section-loading">
            <i class="el-icon-loading" />
            <span>加载中...</span>
          </div>
          <div v-else-if="participants && participants.length > 0" class="participants-section">
            <el-table :data="participants" border size="small" :show-header="true">
              <el-table-column prop="personName" label="姓名" width="120">
                <template slot-scope="scope">
                  {{ getPersonName(scope.row) }}
                </template>
              </el-table-column>
              <el-table-column prop="teamName" label="所属队伍" width="150">
                <template slot-scope="scope">
                  {{ getTeamName(scope.row) || '-' }}
                </template>
              </el-table-column>
              <el-table-column prop="role" label="角色" width="100">
                <template slot-scope="scope">
                  {{ getPersonRole(scope.row) || '-' }}
                </template>
              </el-table-column>
              <el-table-column prop="distance" label="距离" width="100" v-if="hasEventCoordinates">
                <template slot-scope="scope">
                  {{ getParticipantDistance(scope.row) }}
                </template>
              </el-table-column>
              <el-table-column prop="contact" label="联系方式" min-width="120">
                <template slot-scope="scope">
                  {{ getPersonContact(scope.row) || '-' }}
                </template>
              </el-table-column>
              <el-table-column label="操作" width="100" fixed="right">
                <template slot-scope="scope">
                  <el-dropdown trigger="click" @command="(cmd) => handleParticipantAction(cmd, scope.row)">
                    <el-button size="mini" type="text">
                      更多操作<i class="el-icon-arrow-down el-icon--right"></i>
                    </el-button>
                    <el-dropdown-menu slot="dropdown">
                      <el-dropdown-item command="voice">
                        <i class="el-icon-phone"></i> 语音通话
                      </el-dropdown-item>
                      <el-dropdown-item command="sms">
                        <i class="el-icon-message"></i> 短信
                      </el-dropdown-item>
                      <el-dropdown-item command="video">
                        <i class="el-icon-video-camera"></i> 视频
                      </el-dropdown-item>
                      <el-dropdown-item command="internal">
                        <i class="el-icon-chat-line-round"></i> 站内通信
                      </el-dropdown-item>
                    </el-dropdown-menu>
                  </el-dropdown>
                </template>
              </el-table-column>
            </el-table>
          </div>
          <div v-else class="section-empty">
            <el-empty description="暂无参与方" :image-size="80" />
          </div>
        </el-card>

        <TaskStepsCard
          :task-id="effectiveTaskId"
          :task="displayTask"
          :steps="detailSteps"
          :loading="stepsLoading"
          @refresh="handleStepsRefresh"
          @view-step="handleViewStep"
          @step-action="handleStepAction"
          @task-status-changed="handleTaskStatusChanged"
        />

      </div>
    </el-card>
    <div v-else class="empty-detail">
      <i class="el-icon-document"></i>
      <p>请选择任务查看详情</p>
    </div>
  </div>
</template>

<script>
import { getDispatchTask, listDispatchParticipants, listDispatchSteps, listDispatchStepResources } from '@/api/emergency/dispatchTask'
import { getEvent } from '@/api/emergency/event'
import { getLevelLabel, getLevelTagType } from '@/views/duty/alert/utils/alertFormatters'
import { getUser } from '@/api/system/user'
import Amap from '@/components/Amap'
import TaskStepsCard from './TaskStepsCard.vue'

export default {
  name: 'TaskDetailPanel',
  components: {
    Amap,
    TaskStepsCard
  },
  props: {
    task: {
      type: Object,
      default: null
    },
    taskId: {
      type: [Number, String],
      default: null
    },
    isMobile: {
      type: Boolean,
      default: false
    }
  },
  data() {
    return {
      loadingDetail: false,
      detail: null,
      eventInfo: null,
      assigneeName: null,
      assigneeInfo: null,
      participants: [],
      participantsLoading: false,
      rawSteps: [],
      steps: [],
      stepsLoading: false
    }
  },
  computed: {
    effectiveTaskId() {
      // 优先使用 taskId prop，其次使用 task.id，最后使用 detail.id
      if (this.taskId) {
        return this.taskId
      }
      if (this.task && this.task.id) {
        return this.task.id
      }
      if (this.detail && this.detail.id) {
        return this.detail.id
      }
      return null
    },
    displayTask() {
      const base = this.detail || this.task
      if (!base) return null
      return {
        ...base,
        event: this.eventInfo || base.event,
        assigneeName: this.assigneeName || base.assigneeName,
        participants: this.participants.length ? this.participants : (base.participants || [])
      }
    },
    detailSteps() {
      return this.steps
    },
    eventLongitude() {
      return this.displayTask?.event?.longitude || this.displayTask?.eventLongitude || null
    },
    eventLatitude() {
      return this.displayTask?.event?.latitude || this.displayTask?.eventLatitude || null
    },
    hasEventCoordinates() {
      return Boolean(this.eventLongitude && this.eventLatitude)
    },
    mapCenter() {
      if (!this.hasEventCoordinates) {
        return [120.1551, 30.2741]
      }
      return [
        Number(this.eventLongitude) || 120.1551,
        Number(this.eventLatitude) || 30.2741
      ]
    },
    mapMarkers() {
      if (!this.hasEventCoordinates) return []
      return [
        {
          lng: Number(this.eventLongitude),
          lat: Number(this.eventLatitude),
          title: this.getEventName(this.displayTask) || '事件',
          content: this.getEventLocation(this.displayTask) || ''
        }
      ]
    },
    mapContainerId() {
      return `task-detail-event-map-${this.displayTask?.id || 'main'}`
    }
  },
  watch: {
    task: {
      immediate: true,
      handler(val) {
        if (val && val.id) {
          this.participants = []
          this.rawSteps = []
          this.steps = []
          this.fetchDetail(val.id)
        } else {
          this.detail = null
          this.participants = []
          this.rawSteps = []
          this.steps = []
        }
      }
    },
    taskId: {
      immediate: true,
      handler(val) {
        if (val && !this.task) {
          this.participants = []
          this.rawSteps = []
          this.steps = []
          this.fetchDetail(val)
        }
      }
    },
    participants: {
      deep: true,
      handler() {
        this.refreshStepsView()
      }
    }
  },
  methods: {
    fetchDetail(id) {
      this.loadingDetail = true
      getDispatchTask(id)
        .then(res => {
          if (res && res.code === 200) {
            const taskData = res.data || null
            this.detail = taskData
            if (taskData?.eventId) {
              this.fetchEvent(taskData.eventId)
            } else {
              this.eventInfo = taskData?.event || null
            }
            this.assigneeName = taskData?.assigneeName || taskData?.assignee
            if (taskData?.assigneeId) {
              this.fetchAssignee(taskData.assigneeId)
            } else {
              this.assigneeInfo = null
            }
            this.fetchParticipants(id)
            this.fetchSteps(id)
          } else {
            this.detail = null
            this.participants = []
            this.steps = []
          }
        })
        .finally(() => {
          this.loadingDetail = false
        })
    },
    fetchEvent(eventId) {
      getEvent(eventId)
        .then(res => {
          if (res && res.code === 200) {
            this.eventInfo = res.data || null
          }
        })
    },
    fetchAssignee(userId) {
      getUser(userId)
        .then(res => {
          if (res && res.code === 200) {
            this.assigneeInfo = res.data || null
          }
        })
        .catch(() => {
          this.assigneeInfo = null
        })
    },
    refreshDetail() {
      const id = this.effectiveTaskId
      if (id) {
        this.fetchDetail(id)
        this.$emit('refresh')
      }
    },
    handleStepsRefresh() {
      const id = this.effectiveTaskId
      if (id) {
        this.fetchSteps(id, { silent: false })
      }
    },
    handleTaskStatusChanged() {
      // 当任务状态变更时，刷新任务详情
      this.refreshDetail()
    },
    handleViewStep(step) {
      this.$emit('view-step', step)
    },
    handleStepAction({ command, step }) {
      this.$emit('step-action', { command, step })
    },
    fetchParticipants(taskId) {
      if (!taskId) {
        this.participants = []
        return
      }
      this.participantsLoading = true
      listDispatchParticipants(taskId)
        .then(res => {
          if (res && res.code === 200) {
            const list = (res.data || []).map(item => this.transformParticipant(item))
            this.participants = list
            if (this.detail) {
              this.$set(this.detail, 'participants', list)
            }
            this.refreshStepsView()
          } else {
            this.participants = []
          }
        })
        .catch(() => {
          this.participants = []
        })
        .finally(() => {
          this.participantsLoading = false
        })
    },
    fetchSteps(taskId, options = { silent: true }) {
      if (!taskId) {
        this.setSteps([])
        return
      }
      if (!options.silent) {
        this.stepsLoading = true
      }
      listDispatchSteps(taskId)
        .then(res => {
          if (res && res.code === 200) {
            this.setSteps(res.data || [])
            this.loadStepResources(taskId)
          }
        })
        .finally(() => {
          this.stepsLoading = false
        })
    },
    setSteps(rawSteps) {
      this.rawSteps = Array.isArray(rawSteps) ? rawSteps : []
      this.refreshStepsView()
    },
    refreshStepsView() {
      this.steps = (this.rawSteps || []).map((step, index) => ({
        id: step.id,
        order: step.stepOrder || index + 1,
        name: step.name || step.title || '-',
        executor: this.resolveExecutorDisplay(step),
        status: step.status || 'pending',
        planTime: this.formatDate(step.planTime || step.planStartTime),
        description: step.description || '-',
        resources: step.resources || []
      }))
    },
    resolveExecutorDisplay(step) {
      const executorId = step?.executorId
      const fallback = step?.executorName || step?.executor || (executorId ? `ID:${executorId}` : '-')
      if (!executorId || !this.participants.length) {
        return fallback
      }
      // executorId 现在表示 dispatch_task_participant.id
      const matched = this.participants.find(p =>
        String(p.id) === String(executorId)
      )
      if (matched) {
        return matched.displayName || this.getParticipantName(matched)
      }
      return fallback
    },
    attachStepResources(resourceMap = {}) {
      if (!this.rawSteps.length) return
      this.rawSteps = this.rawSteps.map(step => ({
        ...step,
        resources: resourceMap[step.id] || step.resources || []
      }))
      this.refreshStepsView()
    },
    loadStepResources(taskId) {
      if (!taskId || !this.rawSteps.length) return
      const resourceMap = {}
      const promises = this.rawSteps.map(step => {
        if (!step.id) return Promise.resolve()
        return listDispatchStepResources(taskId, step.id)
          .then(res => {
            if (res && res.code === 200) {
              resourceMap[step.id] = res.data || []
            } else {
              resourceMap[step.id] = []
            }
          })
          .catch(() => {
            resourceMap[step.id] = []
          })
      })
      Promise.all(promises).then(() => {
        this.attachStepResources(resourceMap)
      })
    },
    getAssigneeDisplay() {
      if (this.assigneeInfo) {
        return this.assigneeInfo.nickName
          || this.assigneeInfo.userName
          || this.assigneeInfo.phonenumber
          || '-'
      }
      return this.assigneeName || '-'
    },
    formatDate(value) {
      if (!value) return '-'
      const date = new Date(value)
      if (Number.isNaN(date.getTime())) return value
      const pad = num => (num < 10 ? `0${num}` : num)
      return `${date.getFullYear()}-${pad(date.getMonth() + 1)}-${pad(date.getDate())} ${pad(date.getHours())}:${pad(date.getMinutes())}`
    },
    getStatusMeta(task) {
      const status = task?.status
      const meta = {
        draft: { label: '草稿', tag: 'info' },
        published: { label: '已下达', tag: 'warning' },
        in_progress: { label: '执行中', tag: 'primary' },
        closed: { label: '已完成', tag: 'success' },
        cancelled: { label: '已取消', tag: 'info' }
      }
      return meta[status] || { label: status || '未知', tag: 'info' }
    },
    isParticipantConfirmed(task) {
      if (!task) return false
      if (typeof task.participantConfirmed === 'boolean') {
        return task.participantConfirmed
      }
      if (task.status === 'in_progress' || task.status === 'closed') {
        return true
      }
      const participantList = this.participants.length
        ? this.participants
        : Array.isArray(task.participants) ? task.participants : []
      if (Array.isArray(participantList)) {
        return participantList.some(p => Number(p.confirmedFlag) === 1)
      }
      return false
    },
    getEventName(task) {
      return task?.eventName
        || task?.event?.eventName
        || task?.event?.title
        || task?.event?.name
        || ''
    },
    getEventLevel(task) {
      const level = task?.eventLevel
        || task?.event?.eventLevel
        || task?.event?.level
        || ''
      if (!level) return '-'
      if (['I', 'II', 'III', 'IV'].includes(level)) {
        return `${level}级`
      }
      if (level.startsWith('level')) {
        return getLevelLabel(level)?.replace(/[（(].*/, '') || level
      }
      return level
    },
    getEventLevelTag(task) {
      const level = task?.eventLevel
        || task?.event?.eventLevel
        || task?.event?.level
        || ''
      if (!level) return 'info'
      if (['I', 'II', 'III', 'IV'].includes(level)) {
        const tagMap = {
          I: 'danger',
          II: 'warning',
          III: 'info',
          IV: 'success'
        }
        return tagMap[level] || 'info'
      }
      if (level.startsWith('level')) {
        return getLevelTagType(level) || 'info'
      }
      return 'info'
    },
    getEventLocation(task) {
      return task?.eventLocation
        || task?.event?.location
        || task?.location
        || ''
    },
    transformParticipant(participant = {}) {
      const snapshot = this.parseParticipantSnapshot(participant.personSnapshot)
      const displayName = participant.personName
        || participant.memberName
        || snapshot?.name
        || snapshot?.personName
        || snapshot?.memberName
        || '-'
      const teamName = participant.teamName
        || snapshot?.teamName
        || snapshot?.unit
        || snapshot?.orgName
        || ''
      const role = participant.role
        || snapshot?.role
        || snapshot?.position
        || snapshot?.duty
        || ''
      const contact = participant.phone
        || snapshot?.phone
        || snapshot?.contact
        || snapshot?.mobile
        || ''
      const confirmedFlag = participant.confirmedFlag != null
        ? Number(participant.confirmedFlag)
        : snapshot?.confirmedFlag != null
          ? Number(snapshot.confirmedFlag)
          : 0
      return {
        ...participant,
        snapshot,
        displayName,
        teamName,
        role,
        contact,
        confirmedFlag
      }
    },
    parseParticipantSnapshot(rawSnapshot) {
      if (!rawSnapshot) return null
      if (typeof rawSnapshot === 'object') return rawSnapshot
      try {
        return JSON.parse(rawSnapshot)
      } catch (error) {
        return null
      }
    },
    getParticipantName(participant) {
      return participant?.displayName || '-'
    },
    getParticipantMeta(participant) {
      if (!participant) return ''
      const segments = []
      if (participant.teamName) {
        segments.push(participant.teamName)
      }
      if (participant.role) {
        segments.push(participant.role)
      }
      if (participant.contact) {
        segments.push(participant.contact)
      }
      return segments.join(' · ')
    },
    getPersonName(participant) {
      if (participant.personSnapshot) {
        try {
          const snapshot = typeof participant.personSnapshot === 'string' 
            ? JSON.parse(participant.personSnapshot) 
            : participant.personSnapshot
          return snapshot.name || snapshot.personName || participant.displayName || '-'
        } catch (e) {
          return participant.displayName || '-'
        }
      }
      return participant.displayName || '-'
    },
    getTeamName(participant) {
      if (participant.teamId) {
        return `队伍 ${participant.teamId}`
      }
      if (participant.personSnapshot) {
        try {
          const snapshot = typeof participant.personSnapshot === 'string' 
            ? JSON.parse(participant.personSnapshot) 
            : participant.personSnapshot
          return snapshot.teamName || snapshot.unit || participant.teamName || '-'
        } catch (e) {
          return participant.teamName || '-'
        }
      }
      return participant.teamName || '-'
    },
    getPersonRole(participant) {
      if (participant.personSnapshot) {
        try {
          const snapshot = typeof participant.personSnapshot === 'string' 
            ? JSON.parse(participant.personSnapshot) 
            : participant.personSnapshot
          return snapshot.role || snapshot.position || participant.role || '-'
        } catch (e) {
          return participant.role || '-'
        }
      }
      return participant.role || '-'
    },
    getPersonContact(participant) {
      if (participant.personSnapshot) {
        try {
          const snapshot = typeof participant.personSnapshot === 'string' 
            ? JSON.parse(participant.personSnapshot) 
            : participant.personSnapshot
          return snapshot.phone || snapshot.contact || snapshot.telephone || participant.contact || '-'
        } catch (e) {
          return participant.contact || '-'
        }
      }
      return participant.contact || '-'
    },
    calculateDistance(lat1, lon1, lat2, lon2) {
      if (!lat1 || !lon1 || !lat2 || !lon2) return null
      
      const R = 6371 // Earth's radius in km
      const dLat = (lat2 - lat1) * Math.PI / 180
      const dLon = (lon2 - lon1) * Math.PI / 180
      const a = Math.sin(dLat / 2) * Math.sin(dLat / 2) +
                Math.cos(lat1 * Math.PI / 180) * Math.cos(lat2 * Math.PI / 180) *
                Math.sin(dLon / 2) * Math.sin(dLon / 2)
      const c = 2 * Math.atan2(Math.sqrt(a), Math.sqrt(1 - a))
      return R * c
    },
    getParticipantDistance(participant) {
      if (!this.hasEventCoordinates || !participant.personSnapshot) return '-'
      try {
        const snapshot = typeof participant.personSnapshot === 'string' 
          ? JSON.parse(participant.personSnapshot) 
          : participant.personSnapshot
        
        // Check for team member coordinates (teamLatitude/teamLongitude)
        if (snapshot.teamLatitude && snapshot.teamLongitude) {
          const distance = this.calculateDistance(
            snapshot.teamLatitude,
            snapshot.teamLongitude,
            parseFloat(this.eventLatitude),
            parseFloat(this.eventLongitude)
          )
          if (distance === null) return '-'
          if (distance < 1) {
            return `${(distance * 1000).toFixed(0)}m`
          } else {
            return `${distance.toFixed(1)}km`
          }
        }
        
        // Check for individual coordinates (latitude/longitude)
        if (snapshot.latitude && snapshot.longitude) {
          const distance = this.calculateDistance(
            snapshot.latitude,
            snapshot.longitude,
            parseFloat(this.eventLatitude),
            parseFloat(this.eventLongitude)
          )
          if (distance === null) return '-'
          if (distance < 1) {
            return `${(distance * 1000).toFixed(0)}m`
          } else {
            return `${distance.toFixed(1)}km`
          }
        }
      } catch (e) {
        return '-'
      }
      return '-'
    },
    // 检查参与方是否有联系方式
    hasContact(participant) {
      const contact = this.getPersonContact(participant)
      return contact && contact !== '-'
    },
    // 处理参与方操作
    handleParticipantAction(command, participant) {
      switch (command) {
        case 'voice':
          this.handleVoiceCall(participant)
          break
        case 'sms':
          this.handleSms(participant)
          break
        case 'video':
          this.handleVideoCall(participant)
          break
        case 'internal':
          this.handleInternalMessage(participant)
          break
        default:
          break
      }
    },
    // 处理语音通话
    handleVoiceCall(participant) {
      if (this.hasContact(participant)) {
        this.$message.info('功能集成中')
      } else {
        this.$message.warning('请先维护联系方式')
      }
    },
    // 处理短信
    handleSms(participant) {
      if (this.hasContact(participant)) {
        this.$message.info('功能集成中')
      } else {
        this.$message.warning('请先维护联系方式')
      }
    },
    // 处理视频通话
    handleVideoCall(participant) {
      this.$message.info('功能集成中')
    },
    // 处理站内通信
    handleInternalMessage(participant) {
      this.$message.info('功能集成中')
    },
    handleClose() {
      this.$emit('close')
    }
  }
}
</script>

<style lang="scss" scoped>
.task-detail-panel {
  height: 100%;
  display: flex;
  flex-direction: column;
  background: #fff;
}

.task-detail-panel ::v-deep .el-card {
  flex: 1;
  display: flex;
  flex-direction: column;
  border-radius: 0;
  border: none;
  box-shadow: none;
}

.task-detail-panel ::v-deep .el-card__body {
  flex: 1;
  overflow-y: auto;
  padding-bottom: 16px;
}

.detail-header {
  display: flex;
  justify-content: space-between;
  align-items: center;
  flex-wrap: wrap;
}

.header-left {
  display: flex;
  flex-direction: column;
  gap: 4px;
}

.title-row {
  display: flex;
  align-items: center;
  gap: 8px;
}

.task-title {
  font-size: 18px;
  font-weight: 600;
  color: #303133;
}

.subtitle {
  font-size: 12px;
  color: #909399;
}

.header-actions {
  display: flex;
  gap: 8px;
  align-items: center;
}

.detail-loading {
  display: flex;
  align-items: center;
  gap: 8px;
  padding: 40px 0;
  color: #909399;
  justify-content: center;
}

.detail-info {
  margin-bottom: 16px;
}

.section-header {
  display: flex;
  align-items: center;
  justify-content: space-between;
}

.map-card,
.participants-card,
.steps-card,
.disposal-card {
  margin-bottom: 16px;
}

.map-wrapper {
  display: flex;
  flex-direction: column;
  gap: 8px;
}

.map-meta {
  font-size: 13px;
  color: #606266;
  display: flex;
  flex-direction: column;
  gap: 4px;
}

.map-meta .coord {
  font-size: 12px;
  color: #909399;
}

.participant-section {
  display: flex;
  flex-direction: column;
  gap: 4px;
}

.participant-loading {
  display: flex;
  align-items: center;
  gap: 6px;
  color: #909399;
  font-size: 12px;
}

.section-loading {
  display: flex;
  align-items: center;
  justify-content: center;
  gap: 8px;
  padding: 40px 20px;
  color: #909399;
}

.section-empty {
  padding: 20px;
}

.participants-section {
  margin-bottom: 0;
}

.participant-tags {
  display: flex;
  flex-wrap: wrap;
  gap: 8px;
}

.participant-chip {
  display: flex;
  align-items: center;
  gap: 4px;
}

.participant-meta {
  font-size: 12px;
  color: #909399;
}

.muted-text {
  color: #c0c4cc;
  font-size: 12px;
}

.empty-detail {
  display: flex;
  flex-direction: column;
  align-items: center;
  justify-content: center;
  height: 100%;
  color: #909399;

  i {
    font-size: 64px;
    margin-bottom: 16px;
  }
}
</style>