Form.vue 9.74 KB
<template>
  <el-dialog
    :title="dialogTitle"
    :visible.sync="visible"
    width="720px"
    :close-on-click-modal="false"
    class="gold-triangle-form-dialog"
    append-to-body
    @close="handleClose"
  >
    <el-form ref="basicForm" :model="dataForm" size="small" label-width="90px" :rules="rules" :disabled="!!isDetail">
      <el-row :gutter="16">
        <el-col :span="12">
          <el-form-item label="月份" prop="yf">
            <el-date-picker
              v-model="monthValue"
              type="month"
              placeholder="请选择月份"
              format="yyyyMM"
              value-format="yyyyMM"
              style="width: 100%"
              @change="onMonthChange"
            />
          </el-form-item>
        </el-col>
        <el-col :span="12">
          <el-form-item label="门店">
            <el-input :value="currentStoreName" disabled />
          </el-form-item>
        </el-col>
        <el-col :span="24">
          <el-form-item label="金三角" prop="jsj">
            <el-input v-model="dataForm.jsj" placeholder="请输入金三角名称" clearable maxlength="50" />
          </el-form-item>
        </el-col>
      </el-row>
    </el-form>

    <!-- 成员管理 -->
    <div class="member-section" v-if="!isDetail || members.length">
      <div class="section-title">
        <span>{{ isDetail ? '成员信息' : '成员管理' }}</span>
        <div class="member-actions" v-if="!isDetail">
          <el-button type="primary" icon="el-icon-plus" @click="addMember" size="small">添加成员</el-button>
          <el-button type="warning" icon="el-icon-refresh" @click="refreshMembers" size="small">刷新</el-button>
          <span class="member-count">共 {{ members.length }} 人</span>
        </div>
        <span class="member-count" v-else>共 {{ members.length }} 人</span>
      </div>

      <el-table :data="members" border size="small" style="width: 100%; margin-top: 10px;">
        <el-table-column type="index" label="序号" width="60" align="center" />
        <el-table-column prop="userName" label="姓名" min-width="100">
          <template slot-scope="scope">
            <el-input v-if="!isDetail" v-model="scope.row.userName" size="small" placeholder="姓名" />
            <span v-else>{{ scope.row.userName }}</span>
          </template>
        </el-table-column>
        <el-table-column prop="userId" label="用户" min-width="160">
          <template slot-scope="scope">
            <el-select
              v-if="!isDetail"
              v-model="scope.row.userId"
              placeholder="选择用户"
              size="small"
              filterable
              style="width: 100%"
              @change="onUserChange(scope.$index, $event)"
            >
              <el-option v-for="u in availableUsers" :key="u.id" :label="u.name" :value="u.id" />
            </el-select>
            <span v-else>{{ scope.row.userName || scope.row.userId }}</span>
          </template>
        </el-table-column>
        <el-table-column label="是否顾问" width="100" align="center">
          <template slot-scope="scope">
            <el-radio-group v-if="!isDetail" v-model="scope.row.isLeader" size="small">
              <el-radio :label="1">是</el-radio>
              <el-radio :label="0">否</el-radio>
            </el-radio-group>
            <el-tag v-else :type="scope.row.isLeader === 1 ? 'success' : 'info'" size="small">
              {{ scope.row.isLeader === 1 ? '是' : '否' }}
            </el-tag>
          </template>
        </el-table-column>
        <el-table-column label="排序" width="80" align="center">
          <template slot-scope="scope">
            <el-input-number v-if="!isDetail" v-model="scope.row.sortOrder" :min="1" :max="999" size="small" style="width: 100%" />
            <span v-else>{{ scope.row.sortOrder }}</span>
          </template>
        </el-table-column>
        <el-table-column label="操作" width="80" align="center" v-if="!isDetail">
          <template slot-scope="scope">
            <el-button type="danger" icon="el-icon-delete" size="mini" plain @click="removeMember(scope.$index)">删除</el-button>
          </template>
        </el-table-column>
      </el-table>
    </div>

    <span slot="footer" class="dialog-footer">
      <el-button @click="handleClose">取 消</el-button>
      <el-button type="primary" @click="dataFormSubmit" v-if="!isDetail">确 定</el-button>
    </span>
  </el-dialog>
</template>

<script>
import request from '@/utils/request'

export default {
  name: 'GoldTriangleForm',
  props: {
    currentStoreId: { type: String, default: '' },
    currentStoreName: { type: String, default: '' }
  },
  data() {
    return {
      visible: true,
      isDetail: false,
      dataForm: { id: '', yf: '', md: '', jsj: '' },
      members: [],
      availableUsers: [],
      monthValue: null,
      rules: {
        yf: [
          { required: true, message: '请选择月份', trigger: 'change' },
          { pattern: /^\d{6}$/, message: '月份格式为yyyyMM', trigger: 'blur' }
        ],
        jsj: [{ required: true, message: '请输入金三角名称', trigger: 'blur' }]
      }
    }
  },
  computed: {
    dialogTitle() {
      if (this.isDetail) return '金三角详情'
      return this.dataForm.id ? '编辑金三角' : '新建金三角'
    }
  },
  methods: {
    init(id, isDetail) {
      this.dataForm.id = id || ''
      this.isDetail = !!isDetail
      this.members = []
      this.dataForm.md = this.currentStoreId

      this.$nextTick(() => {
        this.$refs.basicForm && this.$refs.basicForm.resetFields()
        if (this.dataForm.id) {
          this.loadData()
        } else {
          const now = new Date()
          this.monthValue = `${now.getFullYear()}${String(now.getMonth() + 1).padStart(2, '0')}`
          this.dataForm.yf = this.monthValue
          this.dataForm.md = this.currentStoreId
          this.loadUsersByStore()
        }
      })
    },
    loadData() {
      request({ url: `/Extend/LqYcsdJsj/${this.dataForm.id}`, method: 'get' }).then(res => {
        const d = res.data || res
        this.dataForm = { ...this.dataForm, ...d }
        this.monthValue = this.dataForm.yf
        if (this.dataForm.md) this.loadUsersByStore()
      })

      request({ url: `/Extend/LqYcsdJsj/${this.dataForm.id}/detail`, method: 'get' }).then(res => {
        const d = res.data || res
        this.members = (d.members || []).map(m => ({ ...m, isLeader: m.isLeader ?? 0 }))
      })
    },
    loadUsersByStore() {
      if (!this.currentStoreId) {
        this.availableUsers = []
        return
      }
      // 仅获取当前门店内的健康师(gw=健康师 筛选岗位)
      request({
        url: '/Extend/User/Selector',
        method: 'get',
        params: { mdid: this.currentStoreId, gw: '健康师' }
      }).then(res => {
        const list = res.data || res
        this.availableUsers = Array.isArray(list) ? list.map(x => ({ id: x.id, name: x.realName || x.name })) : []
        if (this.availableUsers.length === 0 && !this.dataForm.id) {
          this.$message.warning('当前门店暂无健康师,请先在系统中配置')
        }
      }).catch(() => {
        this.availableUsers = []
      })
    },
    onMonthChange(val) {
      this.dataForm.yf = val
    },
    onUserChange(index, userId) {
      const u = this.availableUsers.find(x => x.id === userId)
      if (u) this.$set(this.members[index], 'userName', u.name)
    },
    addMember() {
      if (!this.currentStoreId) {
        this.$message.warning('门店信息异常')
        return
      }
      if (this.availableUsers.length === 0) {
        this.$message.warning('请先选择月份,暂无可用用户')
        return
      }
      this.members.push({ userId: '', userName: '', isLeader: 0, sortOrder: this.members.length + 1 })
    },
    removeMember(index) {
      this.$confirm('确定删除该成员?', '提示', { type: 'warning' }).then(() => {
        this.members.splice(index, 1)
        this.members.forEach((m, i) => { m.sortOrder = i + 1 })
      }).catch(() => {})
    },
    refreshMembers() {
      if (this.dataForm.id) this.loadData()
    },
    dataFormSubmit() {
      this.$refs.basicForm.validate(valid => {
        if (!valid) return
        if (this.members.length >= 2) {
          const hasLeader = this.members.some(m => m.isLeader === 1)
          if (!hasLeader) {
            this.$message.error('两人及以上战队必须有一个顾问')
            return
          }
        }

        const submitData = { ...this.dataForm, members: this.members, md: this.currentStoreId }

        if (this.dataForm.id) {
          request({ url: `/Extend/LqYcsdJsj/${this.dataForm.id}`, method: 'put', data: submitData }).then(res => {
            this.$message.success(res.msg || '保存成功')
            this.handleClose()
            this.$emit('refresh', true)
          })
        } else {
          request({ url: '/Extend/LqYcsdJsj', method: 'post', data: submitData }).then(res => {
            this.$message.success(res.msg || '创建成功')
            this.handleClose()
            this.$emit('refresh', true)
          })
        }
      })
    },
    handleClose() {
      this.visible = false
      this.$emit('refresh')
    }
  }
}
</script>

<style lang="scss" scoped>
.member-section {
  margin-top: 20px;
  padding: 16px;
  border: 1px solid #e2e8f0;
  border-radius: 8px;
  background: #f8fafc;
}

.section-title {
  display: flex;
  align-items: center;
  justify-content: space-between;
  margin-bottom: 12px;
  font-size: 15px;
  font-weight: 600;
  color: #334155;
}

.member-actions {
  display: flex;
  align-items: center;
  gap: 10px;
}

.member-count {
  font-size: 12px;
  color: #64748b;
  background: #e2e8f0;
  padding: 4px 10px;
  border-radius: 6px;
}

::v-deep .gold-triangle-form-dialog .el-dialog__body {
  padding: 20px 24px;
}
</style>