封装form表单

目录

[1. 源码](#1. 源码)

[2. 其他页面引用](#2. 其他页面引用)


ps:请看完看明白再复用

1. 源码

html 复制代码
<template>
  <div style="width: 100%; height: 100%" class="form-condition">
    <!-- 普通表单 -->
    <el-card shadow="hover" class="cardheight">
      <div class="form-content">
        <el-form ref="FormRef" label-width="auto" :model="FormRef">
          <el-row
            v-for="(formType, indexs) in formTypeArray"
            :key="indexs"
            :gutter="20"
          >
            <!-- <el-button @click="Text(formTypeArray[indexs])"></el-button> -->
            <el-col
              :span="formTypeArray[indexs].length < 2 ? 24 : span"
              v-for="(data, index) in formTypeArray[indexs]"
              :key="index"
            >
              <!-- 关于Id相关的均不显示,此处需要后台进行配合完成 -->
              <!-- &&
                  (data.label
                    ? data.label.includes('ID')
                      ? false
                      : true
                    : false) -->
              <el-form-item
                v-if="
                  data.type !== 'allCheckBox' &&
                  data.type !== 'checkbox' &&
                  (data.label
                    ? data.label.includes('ID')
                      ? false
                      : true
                    : false)
                "
                :label="data.label"
                :prop="data.prop"
                :rules="rules(data)"
              >
                <!-- :label="data.label.includes('ID') ? '序号' : data.label" -->

                <!-- active-text="打开" -->
                <!-- inactive-text="关闭" -->
                <el-switch
                  v-if="data.type == 'switch'"
                  v-model="FormRef[data.prop]"
                  class="mb-2"
                  style="
                    --el-switch-on-color: #13ce66;
                    --el-switch-off-color: #ff4949;
                  "
                  :active-value="1"
                  :inactive-value="0"
                  :disabled="data.disabled"
                  @change="
                    SwitchChang(
                      $event,
                      formTypeArray[indexs][index],
                      indexs,
                      index
                    )
                  "
                />
                <!-- 输入框类型 -->
                <!-- 修改点  去除 v-model.number="FormRef[data.prop]"  202302002-->
                <el-input
                  v-if="data.type == 'input'"
                  v-model="FormRef[data.prop]"
                  :placeholder="data.placeholder"
                  :disabled="data.disabled"
                  suffix-icon="xxxx"
                ></el-input>
                <!-- 时间类型 -->
                <el-date-picker
                  popper-class="date-style"
                  v-if="data.type == 'date'"
                  type="datetime"
                  :placeholder="data.placeholder"
                  v-model="FormRef[data.prop]"
                  format="YYYY/MM/DD HH:mm:ss"
                  value-format="YYYY-MM-DD HH:mm:ss"
                  style="width: 100%"
                  :disabled="data.disabled"
                ></el-date-picker>
                <!-- 下拉框类型 -->
                <el-select
                  :popper-append-to-body="false"
                  v-if="data.type == 'select'"
                  :multiple="data.multiple"
                  :clearable="data.clearable"
                  v-model="FormRef[data.prop]"
                  :placeholder="data.placeholder"
                  :change="SelectChange(FormRef[data.prop], data.label)"
                  style="width: 100%"
                  :disabled="data.disabled"
                >
                  <el-option
                    v-for="(item, i) in data.option"
                    :key="item.value"
                    :label="item.label"
                    :value="item.value"
                  ></el-option>
                </el-select>

                <!-- lu 文本域-->
                <!-- 输入框类型 -->
                <el-input
                  v-if="data.type == 'inputText'"
                  type="textarea"
                  v-model="FormRef[data.prop]"
                  :placeholder="data.placeholder"
                  :disabled="data.disabled"
                  suffix-icon="xxxx"
                ></el-input>

                <el-checkbox
                  v-if="data.type == 'Radio'"
                  :true-label="1"
                  :false-label="0"
                  v-model="FormRef[data.prop]"
                  :label="'点击激活此项为' + data.label + '产品售后信息'"
                  border
                />

                <!-- 显示带有"check-on-click-node"的复选框:树形下拉框 -->
                <el-tree-select
                  v-if="data.type == 'treeSelect'"
                  v-model="FormRef[data.prop]"
                  :data="data.option"
                  check-strictly
                  :render-after-expand="false"
                  show-checkbox
                  check-on-click-node
                  style="width: 100%"
                  :disabled="data.disabled"
                  :multiple="data.multiple"
                />
                <!-- 上传控件 -->
                <el-upload
                  v-if="data.type == 'upload'"
                  action="#"
                  multiple
                  :auto-upload="true"
                  accept="jpg,jpeg,png,PNG"
                  list-type="picture-card"
                  :file-list="files"
                  :http-request="uploadFile"
                  :before-upload="beforeUpload"
                  :on-preview="handlePictureCardPreview"
                  :on-change="ChangeImage"
                  :on-remove="handleRemove"
                >
                  <el-icon><Plus /></el-icon>
                </el-upload>
                <!-- <el-button @click="SubPicForm">提交上传</el-button> -->
                <el-dialog v-model="dialogVisible">
                  <img style="width: 100%" :src="dialogImageUrl" alt="" />
                </el-dialog>
              </el-form-item>
              <el-row
                v-if="
                  data.type == 'allCheckBox' &&
                  JSON.stringify(data.childList) !== '{}'
                "
                class="allcheckBoxOther"
              >
                <el-form-item label-width="auto" label="随带资料">
                  <div v-for="(checkBoxData, key) in data.childList" :key="key">
                    <el-form-item label-width="auto">
                      <el-checkbox
                        border
                        :true-label="1"
                        :false-label="0"
                        :label="checkBoxData.label"
                        v-model="FormRef[checkBoxData.prop]"
                      >
                      </el-checkbox>
                    </el-form-item>
                  </div>
                </el-form-item>
              </el-row>
            </el-col>
          </el-row>
          <el-row style="width: 100%; height: 32px; padding-top: 10px">
            <el-col :span="span" style="width: 100%; margin: 0 auto">
              <el-form-item style="width: 100%">
                <div class="content-btn" style="margin: auto">
                  <el-button
                    plain
                    type="danger"
                    style="float: left; margin-right: 15px"
                    @click="cleanFormValue"
                    ><el-icon><FolderRemove /></el-icon>&ensp; 清 空</el-button
                  >

                  <el-button
                    plain
                    type="primary"
                    style="float: left"
                    @click="getCondition()"
                    ><el-icon><Search /></el-icon>&ensp;{{
                      isOpenSonDataTable || isOpenSonTransfer ? "保存" : "提 交"
                    }}</el-button
                  >
                </div>
              </el-form-item>
            </el-col>
          </el-row>
        </el-form>
      </div>
    </el-card>

    <!-- 是否存在明细附表 -->
    <div v-if="isOpenSonDataTable">
      <!-- 表单 -->
      <el-card shadow="hover">
        <!-- 表单按钮组件 -->
        <div style="margin-bottom: 10px">
          <ButtonView ref="ButtonRef" @ButtonMessage="GetBtnClick"></ButtonView>
        </div>
        <!-- 数据表格组件 -->
        <div class="aa">
          <TableDialog
            ref="tableSonDataRef"
            @getPage="GetDataFenYeWath"
            @tableMessage="GetTableMessage"
          ></TableDialog>
        </div>
      </el-card>
    </div>
    <!-- 抽屉,明细表编辑处 :before-close="drawerCloseSonForm"-->
    <el-drawer
      :key="itemKey"
      :title="dialogTitle"
      v-model="dialog"
      direction="ltr"
      :size="drawerSize"
      custom-class="demo-drawer"
      ref="drawer"
      destroy-on-close
    >
      <div class="demo-drawer__content">
        <!-- 表单组件 -->
        <FromView
          ref="SonfromView"
          @conditionParams="GetCondition"
          @conditionFormData="GetConditionFormData"
          @SonSelectChange="GetSonSelectChange"
        ></FromView>
      </div>
    </el-drawer>
    <!-- 是否存在其他组件 -->
    <div v-if="isOpenSonTransfer">
      <el-card shadow="hover" style="height: 439px">
        <p style="text-align: center; margin: 0 0 20px">
          请选择左侧的数据项,点击中间">"按钮添加数据项
        </p>
        <div style="text-align: center">
          <div>
            <el-transfer
              style="text-align: left; display: inline-block"
              v-model="transferValue"
              :data="transferDatas"
              :props="{
                label: 'title',
              }"
              filterable
              :titles="['待选数据', '已选数据']"
              :button-texts="['取消', '选择']"
            ></el-transfer>
          </div>
          <el-button plain class="squan" type="success" @click="Authorization()"
            >绑 定</el-button
          >
        </div>
      </el-card>
    </div>
  </div>
</template>

<script>
import { computed, provide, inject, ref } from "@vue/runtime-core";
import { watchEffect, getCurrentInstance, reactive } from "vue";
import { ElMessage, ElMessageBox } from "element-plus";

export default {
  name: "FromView",
  emits: ["conditionParams"],
  setup(props, context) {
    let FormRefTest = reactive({});
    let span = ref(6); //6
    let formTypeArray = ref(new Array());
    //用于接收父组件传递的Form表单配置
    const formTypeConfig = inject("formTypeConfig");
    //行数
    let formRowsCount = inject("formRowsCount");
    let checkBoxList = [
      {
        type: "allCheckBox",
        label: "allCheckBox",
        childList: {},
      },
    ];

    //移位,将特定的元素移到最后
    function moveArray(arr, sourceIndex, targetIndex) {
      // splice 将目标元素替换并将原结果扔回来赋值给它
      arr[sourceIndex] = arr.splice(targetIndex, 1, arr[sourceIndex])[0];
    }
    /**
     * 设置表单类型
     * @param array 表单配置
     * @param col 每行表单项个数
     */
    const setFormType = (oldArray, col) => {
      formTypeArray = ref(new Array());
      //console.log("进入FormView组件中的方法", formTypeArray);
      //console.log(oldArray, col);
      let array = [];
      oldArray.map((item) => {
        if (item.type == "checkbox") {
          checkBoxList[0].childList[item.prop] = item;
          array.push(item);
        } else {
          array.push(item);
        }
      });

      //console.log("checkBoxList====", checkBoxList);
      //console.log("array====", array);
      //#region 移动 checkbox 参数位置
      //移动
      var sourceIndexes = [];
      array.forEach((item, index) => {
        if (item.type && item.type == "checkbox") {
          sourceIndexes.push(index);
        }
      });
      // 遍历索引数组,移动元素
      sourceIndexes.forEach((sourceIndex) => {
        moveArray(array, sourceIndex, array.length);
      });
      //过滤undefined
      array = array.filter((item) => {
        return item !== undefined || !!item;
      });
      //#endregion
      if (col == null || col == "" || array == null || array == "") {
        col = 4; // 默认分4列
      }
      span.value = 24 / col;
      if (array != null) {
        array.map((item) => {
          FormRefTest[item.prop] = item.value;
        });

        //console.log("==========FormRef=====", FormRefTest);
        // 只有一行
        if (col >= array.length) {
          formTypeArray.value.push(array);
        } else {
          // 超过一行
          let deb = col;
          let i = 0;
          while (i < array.length) {
            let item = []; //null
            var isFlag = false; //当它为True时,下方将不再Push
            while (i < deb) {
              if (array[i].label.indexOf("后台自增ID") !== -1) {
                item.push(array[i]);
                i++;
                break;
              } else if (
                array[i].label.indexOf("备注") !== -1 ||
                array[i].label.indexOf("概述") !== -1 ||
                array[i].label.indexOf("附件") !== -1 ||
                array[i].type.indexOf("inputText") !== -1
              ) {
                //说明在此之前已有数据
                if (item.length > 0) {
                  isFlag = true;
                  formTypeArray.value.push(item);
                  item = [];
                }
                item.push(array[i]);
                i++;
                break;
              } else {
                item.push(array[i]);
                //console.log(deb);
                i++;
              }
            }
            if (!isFlag) {
              formTypeArray.value.push(item);
            }
            if (array.length - i < col) {
              deb = array.length;
            } else {
              deb = i + col;
            }
          }
          formTypeArray.value.push(checkBoxList);
        }
      }

      //console.log("---------表单配置数据 SUCCESS----------");
    };

    //#region 明细表配置
    //用于监听子表表单数据
    let FatherisOk = ref(false);
    //用于父表单保存后的Id
    let FatherIds = ref(0);
    //用于监听子表单中的数据
    let SonConfigCondition = ref([]);
    //用于监听子表一行几个
    let SonformRowsCount = ref(1);
    //明细表单配置
    const ConfigurationCondition = () => {
      provide("formTypeConfig", SonConfigCondition);
      provide("formRowsCount", SonformRowsCount);
    };
    //#endregion

    //#region 穿梭框配置

    //#endregion

    // 监听表单配置数据 数据变化时, 更新配置
    watchEffect(() => {
      //console.log("-------监听formTypeConfig--------");
      //console.log("=formTypeConfig==========", formTypeConfig);
      //console.log(formRowsCount);

      var rowlCount = formRowsCount == undefined ? 1 : formRowsCount.value;

      setFormType(formTypeConfig.value, rowlCount);
    });

    return {
      formTypeArray,
      span,
      //cleanFormValue,
      setFormType,
      ConfigurationCondition, //明细表单配置
      SonConfigCondition,
      FatherisOk, //用于子表判断附表是否已经保存
      FatherIds, //若主表已经保存,此字段不为0且同时可以获取主表新增数据后的Id
      formRowsCount, //行数
      //#region 穿梭框配置
      FormRefTest,
      //#endregion
    };
  },
  data() {
    return {
      FormRef: {},
      checkBoxList: {},
      isOpenSonDataTable: false, //是否存在明细表格
      isOpenSonTransfer: false, //是否存在其他组件
      listData: [], //此处我子表单中选择的数据,用于对其修改、删除使用
      GetDataFenYe: null, //分页查询数据
      GetDataHanderAndFrom: null, //明细表表头查询数据
      dialog: false,
      dialogTitle: "",
      itemKey: "",
      transferValue: [], //穿梭框选中的
      transferDatas: [], //穿梭框数据源
      //上传如下:
      files: [],
      dialogVisible: false,
      dialogImageUrl: "",
      deleteFiles: [],
      //抽屉大小
      drawerSize: "22%",
    };
  },
  created() {
    //默认初始化明细表单配置
    this.ConfigurationCondition();
    this.FormRef = this.FormRefTest;
    //console.log("this.FormRef====", this.FormRef);
    //console.log("this.FormRefTest====", this.FormRefTest);
  },
  methods: {
    Text(val) {},
    rules(data) {
      //#region 自定义验证校验
      if (data.isRules) {
        //校验数值类型
        if (data.propTypes == "INT") {
          var validatorTel = (rule, value, callback) => {
            if (!value) {
              return callback(new Error(data.label + "不能为空"));
            }
            var numReg = /^[0-9]+$/;
            var numRe = new RegExp(numReg);
            if (!numRe.test(value)) {
              callback(new Error("请输入数字值"));
            } else {
              callback();
            }
          };
          return [
            {
              required: true,
              validator: validatorTel,
              trigger: "blur",
            },
          ];
        }
      }
      //#endregion

      //校验手机号 regMobile
      //暂时屏蔽校验手机号,此处不完善,目前只打开校验是否为空
      //20230202留
      // const regMobile =
      //   /^((\(\d{3,4}\)|\d{3,4}-|\s)?\d{7,14})|([1][3,4,5,6,7,8,9][0-9]{9})$/;
      // if (data.prop.includes("Tel")) {
      //   var validatorTel = (rule, value, callback) => {
      //     if (!value) {
      //       return callback(new Error(data.label + "不能为空"));
      //     }
      //     var numReg = /^[0-9]+$/;
      //     var numRe = new RegExp(numReg);
      //     if (!numRe.test(value)) {
      //       callback(new Error("请输入数字值"));
      //     } else {
      //       if (!regMobile.test(value)) {
      //         callback(new Error("请输入正确的号码"));
      //       } else {
      //         callback();
      //       }
      //     }
      //   };
      //   return [
      //     {
      //       required: true,
      //       validator: validatorTel,
      //       trigger: "blur",
      //     },
      //   ];
      // } else
      if (
        data.prop == "LoginAccount" ||
        data.prop == "Password" ||
        data.prop.includes("Eqipment") ||
        data.prop == "ProductID" ||
        data.prop == "PartID" ||
        data.prop == "WorkNo" ||
        data.prop == "QualityCode"
      ) {
        if (data.type === "select") {
          return [
            { required: true, message: "此处为必填项", trigger: "change" },
          ];
        }
        if (data.type === "input") {
          return [{ required: true, message: "此处为必填项", trigger: "blur" }];
        }
      }
    },
    SwitchChang(data, formData, indexs, index) {
      // this.FormRef[data.prop] = data ? 1 : 0;
      //
    },
    //实时监听子组件发送的信息
    GetDataFenYeWath(Msg) {
       
      //重新赋值,避免新增、修改、删除操作
      this.pageSize = Msg.pageSize;
      this.pageNum = Msg.pageNum;
      let param = {
        params: Msg,
      };

      if (this.GetDataFenYe != null) {
        this.GetDataFenYe(param);
      }
       this.$emit("SongetPage", { pageSize: this.pageSize, pageNum: this.pageNum });
    },
    //获取表格组件传递的信息
    GetTableMessage(msg) {
      //获取listDatas值
      this.listData =
        msg.type === "列表选择"
          ? msg.listData
          : msg.type === "页码切换"
          ? null
          : null;
      //console.log("组件:表格发送信息:" + this.listData);
    },
    //选择框事件
    SelectChange(data, labels) {
      console.log(labels);
      var linsDatas = { value: data, label: labels };

      //匹配新格式
      var datas = {
        data: linsDatas,
        type: "选择",
      };
      //选择框事件,回传给父组件
      this.$emit("SonSelectChange", datas);
    },
    /**
     * 获取父组件传递过来的数据信息链,这里指isOpenSonTransfer 穿梭框的数据
     */
    SetDataSonTransfer(SonDataTransFer) {
      this.isOpenSonTransfer = SonDataTransFer.isOpenSonTransfer; //是否开启穿梭框
      var tData = SonDataTransFer.SonTransfer; //穿梭框左侧数据
      //为True的情况下,进行渲染明细
      if (this.isOpenSonTransfer) {
        //每次选择后清空,重新触发
        this.transferDatas = [];
        this.transferDatas = tData;
      }
    },
    /**
     * 获取父组件传递过来的数据信息链,这里指isOpenSonTransfer 穿梭框的数据
     */
    SetDataSonTransferDatas(SonDataTransFer) {
      this.isOpenSonTransfer = SonDataTransFer.isOpenSonTransfer; //是否开启穿梭框
      var SonTransferValue = SonDataTransFer.SonTransferValue; //穿梭框右侧数据
      //为True的情况下,进行渲染明细
      if (this.isOpenSonTransfer) {
        //每次选择后清空,重新触发
        this.transferValue = [];
        var ChangeLst = [];
        SonTransferValue.forEach((element) => {
          ChangeLst.push(element.PartID.toString());
        });
        this.transferValue = ChangeLst;
      }
    },
    //绑定按钮
    Authorization() {
      // 优先判断在新增的情况下,主表是否已经完成了保存 多用于子表进行新增操作
      if (!this.FatherisOk) {
        //警告
        this.$message({
          message:
            "在新建明细信息的情况下,请优先添加主表信息,再对其明细表进行新增编辑操作",
          type: "warning",
        });
        return;
      }
      this.formTypeArray;
      this.transferValue;
      var datas = {
        form: this.formTypeArray,
        transDatas: this.transferDatas,
        trans: this.transferValue,
        FatherIds: this.FatherIds,
        type: "绑定",
      };
      this.$emit("SonSelectChange", datas);
    },
    /**
     * 获取父组件传递过来的数据信息链,不包含明细表数据
     * @param {} GetDataLists
     */
    SetData(SonDataTableDatas) {
      this.isOpenSonDataTable = SonDataTableDatas.isOpenSonDataTable;
      //为True的情况下,进行渲染明细
      if (this.isOpenSonDataTable) {
        //渲染 ------ 延迟加载
        this.$nextTick(() => {
          this.$nextTick(() => {
            //自动高度
            this.$refs.tableSonDataRef.heights = "auto";
          });
          //普通表格
          this.$refs.tableSonDataRef.SetTableType(true);
          //组件渲染表头表单
          this.$refs.tableSonDataRef.SetDataTableHeader(
            SonDataTableDatas.GetDataHanderAndFrom
          );
          //添加子表表单数据
          this.SonConfigCondition =
            SonDataTableDatas.GetDataHanderAndFrom.lstSubset[0].Froms;
          //渲染明细按钮
          this.$refs.ButtonRef.SetButtonConfigDatas(
            SonDataTableDatas.PartButtonList
          );
        });
      }
    },
    //接收父组件传递的明细表数据,通过此方法作为媒介进行对孙组件传值
    SetDataSonTable(GetDataFenYe) {
      this.$nextTick(() => {
        //若编辑一条装备主表数据时,存在部件表,此处需要赋值
        this.$refs.tableSonDataRef.SetDataTable(GetDataFenYe);
        // this.dialog = false;
      });
    },
    //获取按钮组件消息------------------------用于明细表单
    GetBtnClick(val) {
      //拿到组件信息后,新增、修改弹出Dalod
      if (val.search("新增") != -1) {
        // 优先判断在新增的情况下,主表是否已经完成了保存 多用于子表进行新增操作
        if (!this.FatherisOk) {
          //警告
          this.$message({
            message:
              "在新建明细信息的情况下,请优先添加主表信息,再对其明细表进行新增编辑操作",
            type: "warning",
          });
          return;
        }
        // 优先添加
        this.dialog = true;
        this.dialogTitle = val;
        // //优先清空
        // this.$refs.SonfromView.CloseSonForm();
        var parm = { type: "新增" };
        this.$emit("GrandsonFormArr", parm);
      }
      if (val.search("编辑") != -1) {
        //仅支持单条编辑
        if (JSON.parse(JSON.stringify(this.listData)).length != 1) {
          //警告
          this.$message({
            message: "请选择一条数据进行编辑操作!",
            type: "warning",
          });
          return;
        }
        //结构剖析
        var newListData = JSON.parse(JSON.stringify(this.listData));

        //循环表单
        this.SonConfigCondition.forEach((item) => {
          newListData.forEach((dataitem) => {
            //循环找Key
            for (let key in dataitem) {
              if (item.prop == key) {
                item.value = dataitem[key];
              }
            }
          });
        });
        //先打开
        this.dialog = true;
        this.dialogTitle = val;
        if (
          newListData[0].Files !== undefined &&
          newListData[0].Files !== null
        ) {
          //剔除特殊字符
          var newFilesString = newListData[0].Files.replace(/"/g, "");
          //分割数组
          var newFilesArr = newFilesString.replace(/"/g, "").split("|");
          //删除最后一位,总是多出的空 ''
          newFilesArr.pop();

          //此处延迟加载会帮你解决一切
          this.$nextTick(() => {
            var newFiles = [];
            //构建回显所需要的参数值
            newFilesArr.forEach((element) => {
              var file = { url: this.$FWurl + element };
              newFiles.push(file);
            });
            //组件渲染
            this.$refs.SonfromView.SetFilesData(newFiles);
          });
        }

        var parm = { type: "编辑", Ids: newListData[0].ID };
        this.$emit("GrandsonFormArr", parm);
      }
      if (val.search("删除") != -1) {
        this.$nextTick(() => {
          var _this = this;
          //仅支持单条编辑
          if (JSON.parse(JSON.stringify(this.listData)).length != 1) {
            //警告
            this.$message({
              message: "请选择一条数据进行删除操作!",
              type: "warning",
            });
            return;
          }
          //结构剖析
          var newListData = JSON.parse(JSON.stringify(this.listData));
          //此参数在删除时无需传递
          delete newListData[0].id;
          ElMessageBox.confirm("确认删除这条信息吗?", "警告", {
            confirmButtonText: "确定",
            cancelButtonText: "取消",
            type: "warning",
          })
            .then(() => {
              let dataParam = { data: newListData[0], type: "删除" };
              this.$emit("SonFormArr", dataParam);
            })
            .catch(() => {});
        });
      }
    },
    //给孙组件的抽屉添加宽度
    SetDrawerSize(value) {
      //渲染 ------ 延迟加载
      this.$nextTick(() => {
        //重新渲染,itemKey用于处理Table不渲染的问题
        this.drawerSize = value;
      });
    },
    //孙组件获取父组件传递的File信息
    GetConditionFormData(datas) {
      // Ids虽然是从父级得来,但是此处可能会丢失Ids,所以需要将孙级位面中Ids获取,也就是明细Id
      //先删后加,垃圾FormData特性

      datas.delete("Ids");
      datas.append("Ids", this.FatherIds); //属于哪条明细表数据
      this.$emit("conditionFormData", datas);
    },
    //获取表单组件传递的信息,此处接收的表单乃是数据表格对应的表单------------------------用于明细表单
    GetCondition(datas) {
      //console.log("组件:表单组件发送信息:" + datas);
      var formDatas = {};
      formDatas = datas;

      // datas.forEach((e, index) => {
      //   for (let i = 0; i < e.length; i++) {
      //     var keys = datas[index][i].prop;
      //     var values = datas[index][i].value;
      //     formDatas[keys] = values;
      //   }
      // });
      const param = formDatas;
      //获取表单组件后,判断是新增/修改
      if (this.dialogTitle.search("新增") != -1) {
        //将新增后的主表Id拿到后进行新增操作,此处需要回传到最外层的组件中
        param.FatherIds = this.FatherIds;
        let dataParam = { data: param, type: "新增" };
        this.$emit("SonFormArr", dataParam);
      }
      if (this.dialogTitle.search("编辑") != -1) {
        param.FatherIds = this.FatherIds;
        let dataParam = { data: param, type: "编辑" };
        this.$emit("SonFormArr", dataParam);
      }
    },

    //清空子表表单数据
    CloseSonForm() {
      //清空选择
      this.cleanFormValue();
    },

    //抽屉回调,关闭前清空表单数据
    drawerCloseSonForm(done) {
      //清空选择
      this.$refs.SonfromView.CloseSonForm();
      done();
    },

    /**
     * 清空表单内容
     */
    cleanFormValue() {
      for (let key in this.FormRef) {
        this.FormRef[key] = "";
      }
    },
    //#region 关于图片组上传
    uploadFile(file) {
      //console.log(file);
    },
    //删除事件
    handleRemove(file, fileList) {
      var obj = file.url.split("upLoad/").slice(-1)[0];
      //添加 需要删除的附件
      this.deleteFiles.push(obj);
      //console.log(file, fileList);
    },
    //预览事件
    handlePictureCardPreview(file) {
      this.dialogImageUrl = file.url;
      this.dialogVisible = true;
    },
    //添加图片
    ChangeImage(file, filelist) {
      this.files = filelist;
      //console.log("-----------" + JSON.stringify(file));
    },
    /**
     * 给父组件返回表单输入的内容
     */

    /// lu
    getCondition() {
      this.$refs.FormRef.validate((valid) => {
        //console.log("valid===", valid);
        if (valid) {
          var formData = new FormData();
          this.files.forEach((item) => {
            if (!(!item.raw && item.url.indexOf("blob") === -1)) {
              formData.append("file", item.raw);
            }
          });

          formData.append("Ids", this.FatherIds); //属于哪条主表数据
          this.deleteFiles.forEach((item) => {
            formData.append("fileByDelete", item); //删除的集合
          });
          // //console.log(333333, this.formTypeArray);
          this.$emit("conditionParams", this.FormRef);
          this.$emit("conditionFormData", formData);
        } else {
          // this.$message("请输入内容");
          return false;
        }
      });
    },
    /**
     * 回显
     */
    SetFilesData(FilesList) {
      //渲染 ------ 延迟加载
      this.$nextTick(() => {
        this.files = [];
        this.files = FilesList;
      });
    },
    //#endregion
    //子组件中选择框事件
    GetSonSelectChange(datas) {
      if (datas.type == "选择") {
        this.$emit("GrandsonSelectChange", datas);
      }
      if (datas.type == "绑定") {
        this.$emit("GrandsonSelectChange", datas);
      }
    },
  },
};
</script>
<style lang="scss" scoped>
.allcheckBoxOther div:not(:first-child) {
  margin-left: 1% !important;
  :deep(.el-form-item__label-wrap) {
    margin-bottom: 20% !important;
    margin-left: 1% !important;
  }
}
.aa ::v-deep .el-scrollbar {
  height: 100px;
}
//卡片与"新增"字样之间的距离,卡片的padding-top 为0
.el-dialog--center .el-dialog__body {
  text-align: initial;
  padding: 0px calc(var(--el-dialog-padding-primary) + 5px) 30px !important;
}
</style>

2. 其他页面引用

html 复制代码
<template>
  <el-row :gutter="20">
    <el-col :span="4">
      <div>
        <!-- 树形列表组件 -->
        <el-collapse v-model="activeNames" @change="handleChange">
          <el-collapse-item style="text-align: center" title="字典项" name="1">
            <TreeView
              ref="TreeRef"
              @TreeViewMessage="GetTreeMessage"
              :defaultSelected="defaultSelected"
              nodeKey="DictID"
            ></TreeView>
          </el-collapse-item>
        </el-collapse>
      </div>
    </el-col>

    <el-divider direction="vertical">分割线</el-divider>

    <el-col :span="19">
      <div>
        <!-- 表单按钮组件 -->
        <div style="margin-bottom: 10px">
          <ButtonView @ButtonMessage="GetBtnClick"></ButtonView>
        </div>
        <!-- 数据表格组件 -->
        <div style="width: 103%">
          <TableDialog
            ref="tableRef"
            @getPage="GetDataFenYeWath"
            @tableMessage="GetTableMessage"
            @treeMessage="GetTreeMessage1"
          ></TableDialog>
        </div></div
    ></el-col>
  </el-row>
  <!-- 弹出框,用于新增、修改 -->
  <el-dialog
    v-model="dialogVisible"
    :title="dialogTitle"
    width="30%"
    center
    draggable
    destroy-on-close
  >
    <!-- 表单组件 -->
    <FromView
      style="margin-top: -25px"
      ref="fromViewRef"
      @conditionParams="GetCondition"
    ></FromView>
  </el-dialog>
  <!-- <el-backtop target=".page-component__scroll .el-scrollbar__wrap"></el-backtop> -->
</template>

<script>
import { provide, reactive, ref } from "@vue/runtime-core";
import { ElMessage, ElMessageBox } from "element-plus";

export default {
  name: "Sys_DictTable",
  data() {
    return {
      activeNames: ["1"], //左侧的折叠用户,默认展开
      dialogVisible: false, //用于控制新增、编辑
      dialogTitle: "", //用于控制新增、编辑标题
      listData: [], //已选择的数据
      Dictid: "",
      defaultSelected: "",
      selectedDictIDs: "", //左侧树勾选的id(多选)
    };
  },
  setup() {
    //默认页大小
    let pageSize = 20;
    let pageNum = 1;
    let total = 0;

    //用于监听选中的数据列表
    let ConfigCondition = ref([]);
    //表单配置
    const ConfigurationCondition = () => {
      provide("formTypeConfig", ConfigCondition);
    };
    //表格配置
    const ConfigurationTable = () => {
      var tableHeader = []; // 设置表头 [fieldName字段名, label列名, width列宽, sortable排序]
      var tableDatas = []; // 表格数据
      // 设置表头 [fieldName字段名, label列名, width列宽, sortable排序]

      // 配置表头数据
      provide("tableHeaderConfig", tableHeader);
      // 配置单元格数据及属性/ 分页配置默认值
      provide("tableDataConfig", {
        tableData: tableDatas,
      });
    };
    //树形列表配置
    const ConfigurationTree = () => {
      provide("TreeConfig", { isTreeSeleteOrBtn: 1 });
    };
    //按钮配置
    const ConfigurationButton = () => {
      let CfgButtonDatas = [];
      CfgButtonDatas = [
        {
          btnName: "新增",
          btnType: "success",
          plain: true, //简约按钮类型,与UI相关
          SvgIconName: "Insert",
        },
        {
          btnName: "编辑",
          btnType: "primary",
          plain: true,
          SvgIconName: "Update",
        },
        {
          btnName: "删除",
          btnType: "danger",
          plain: true,
          SvgIconName: "Delete",
        },
      ];
      provide("ButtonTypes", { type: 1 }); // 通常使用默认 1 按钮
      provide("ButtonConfig", { CfgButtonDatas: CfgButtonDatas });
    };

    //注册高级筛选查询配置、表单配置
    return {
      pageSize,
      pageNum,
      total,
      ConfigCondition, //表单数据,实时传递回
      ConfigurationCondition,
      ConfigurationTable,
      ConfigurationTree,
      ConfigurationButton,
    };
  },
  created() {
    //初始化配置
    this.ConfigurationCondition();
    this.ConfigurationTable();
    this.ConfigurationTree();
    this.ConfigurationButton();
    //加载表单、表格列头
    this.GetColDataList();
    // Get请求下,必须要在对象内添加params 参数,再嵌套一层,否则无法识别
    const param = {
      params: {
        pageSize: this.pageSize,
        pageNum: this.pageNum,
      },
    };
    // this.GetDataFenYe(param);
    //获取部门树形列表
    this.GetDepartMentGetDataTree();
  },
  mounted() {},
  methods: {
    //实时监听子组件发送的信息
    GetDataFenYeWath(Msg) {
      //重新赋值,避免新增、修改、删除操作
      this.pageSize = Msg.pageSize;
      this.pageNum = Msg.pageNum;

      let param = {
        params: Msg,
      };
      this.GetDataFenYe(param);
    },

    //获取用户数据,用户数据绑定在某个模块节点下,默认查询所有
    GetDepartMentGetDataTree() {
      //Get请求下,必须要在对象内添加params 参数,再嵌套一层,否则无法识别
      const param = {
        params: {},
      };
      this.$API
        .DicGetDataTree(param)
        .then((res) => {
          //组件渲染
          // console.log("树", res.data.Data.lstSubset[0].DictID);
          this.defaultSelected = [res.data.Data.lstSubset[0].DictID];
          this.selectedDictIDs = [res.data.Data.lstSubset[0]];

          this.$refs.TreeRef.SetTreeDatas(res.data.Data.lstSubset);
          const param = {
            params: {
              pageSize: this.pageSize,
              pageNum: this.pageNum,
              DictIDs: res.data.Data.lstSubset[0].DictID,
            },
          };
          this.GetDataFenYe(param);
        })
        .catch((err) => {
          // this.$notify.error({
          //   title: "消息提示",
          //   message: err,
          // });
        });
    },

    //获取用户数据,用户数据绑定在某个模块节点下,默认查询所有
    GetColDataList() {
      //Get请求下,必须要在对象内添加params 参数,再嵌套一层,否则无法识别
      const param = {
        params: { param: "1" },
      };
      this.$API
        .DicGetColDataList(param)
        .then((res) => {
          //组件渲染

          this.$refs.tableRef.SetDataTableHeader(res.data.Data);
          //直接将此数据类型贯通至组件中
          this.ConfigCondition = res.data.Data.lstSubset[0].Froms;
        })
        .catch((err) => {
          // this.$notify.error({
          //   title: "消息提示",
          //   message: err,
          // });
        });
    },
    //查询分页数据
    GetDataFenYe(param) {
      this.$API
        .DicGetDataFenYe(param)
        .then((res) => {
          //组件渲染
          console.log("数据", res.data.Data);
          this.$refs.tableRef.SetDataTable(res.data.Data);
        })
        .catch((err) => {
          // this.$notify.error({
          //   title: "消息提示",
          //   message: err,
          // });
        });
    },
    /**
     * 新增
     * @param {*} data
     */
    InsertFormDatas(data) {
      this.$API
        .DicInsertData(data)
        .then((res) => {
          ElMessage({
            type: "success",
            message: res.data.Msg,
          });

          this.CloseForm();
          this.dialogVisible = false;
          const param = {
            params: {
              pageSize: this.pageSize,
              pageNum: this.pageNum,
              DictIDs: data.DictID,
            },
          };
          this.GetDataFenYe(param);
        })
        .catch((err) => {
          this.$notify.error({
            title: "消息提示",
            message: err,
          });
        });
    },
    /**
     * 修改
     * @param {} data
     */
    UpdateFormDatas(data) {
      this.$API
        .DicUpdateData(data)

        .then((res) => {
          ElMessage({
            type: "success",
            message: res.data.Msg,
          });
          this.CloseForm();
          this.dialogVisible = false;
          const param = {
            params: {
              pageSize: this.pageSize,
              pageNum: this.pageNum,
              DictIDs: data.DictID,
            },
          };
          this.GetDataFenYe(param);
        })
        .catch((err) => {
          this.$notify.error({
            title: "消息提示",
            message: err,
          });
        });
    },
    /**
     * 删除
     * @param {*} data
     */
    DeleteFormDatas(data) {
      this.$API
        .DicDeletData(data)
        .then((res) => {
          ElMessage({
            type: "success",
            message: res.data.Msg,
          });
          this.CloseForm();
          this.dialogVisible = false;
          const param = {
            params: {
              pageSize: this.pageSize,
              pageNum: this.pageNum,
              DictIDs: data.DictID,
            },
          };
          this.GetDataFenYe(param);
        })
        .catch((err) => {
          this.$notify.error({
            title: "消息提示",
            message: err,
          });
        });
    },

    //获取表单组件传递的信息,此处接收的表单乃是数据表格对应的表单
    GetCondition(datas) {
      console.log("组件:表单组件发送信息:" + datas);
      var formDatas = {};
      // datas.forEach((e, index) => {
      //   for (let i = 0; i < e.length; i++) {
      //     var keys = datas[index][i].prop;
      //     var values = datas[index][i].value;
      //     formDatas[keys] = values;
      //   }
      // });
      const param = datas;
      //获取表单组件后,判断是新增/修改
      if (this.dialogTitle.search("新增") != -1) {
        this.InsertFormDatas(param);
      }
      if (this.dialogTitle.search("编辑") != -1) {
        console.log("param===========", param);
        this.UpdateFormDatas(param);
      }
    },
    //获取表格组件传递的信息
    GetTableMessage(msg) {
      //获取listDatas值
      this.listData =
        msg.type === "列表选择"
          ? msg.listData
          : msg.type === "页码切换"
          ? null
          : null;
      console.log("组件:表格发送信息:" + this.listData);
    },
    //获取树形组件传递的信息
    GetTreeMessage(val) {
      console.log("valaaa", val.data);
      let NodeList = JSON.parse(JSON.stringify(val.data));
      this.selectedDictIDs = val.data;
      let newParam = "";
      NodeList.forEach((element) => {
        newParam = newParam + element.DictID + ",";
      });
      //去掉最后一个逗号(如果不需要去掉,就不用写)
      if (newParam.length > 0) {
        newParam = newParam.substr(0, newParam.length - 1);
      }
      console.log("--------组件:树形列表解析后:" + newParam);
      const param = {
        params: {
          pageSize: this.pageSize,
          pageNum: this.pageNum,
          DictIDs: newParam,
        },
      };
      this.GetDataFenYe(param);
    },
    //折叠面板用户
    handleChange(val) {},
    //获取按钮组件消息
    GetBtnClick(val) {
      //拿到组件信息后,新增、修改弹出Dalod
      if (val.search("新增") != -1) {
        // this.CloseForm();
        this.$nextTick(() => {
          this.$refs.tableRef.ClearSelect();
        });
        //lu
        if (JSON.parse(JSON.stringify(this.selectedDictIDs)).length != 1) {
          //警告
          this.$message({
            message: "请选择一条字典项进行新增操作!",
            type: "warning",
          });
          return;
        }
        //循环表单
        var newSelectData = JSON.parse(JSON.stringify(this.selectedDictIDs));
        this.ConfigCondition.forEach((item) => {
          newSelectData.forEach((dataitem) => {
            //循环找Key
            for (let key in dataitem) {
              if (item.prop == key && key == "DictID") {
                item.value = dataitem[key];
              }
            }
            // item[0].value = defaultSelected;
          });
        });
        console.log("ConfigCondition===", this.ConfigCondition);

        this.dialogVisible = true;
        this.dialogTitle = val + "字典项";
      }
      if (val.search("编辑") != -1) {
        //仅支持单条编辑
        if (JSON.parse(JSON.stringify(this.listData)).length != 1) {
          //警告
          this.$message({
            message: "请选择一条数据进行编辑操作!",
            type: "warning",
          });
          return;
        }

        //结构剖析
        var newListData = JSON.parse(JSON.stringify(this.listData));

        //循环表单
        this.ConfigCondition.forEach((item) => {
          newListData.forEach((dataitem) => {
            //循环找Key
            for (let key in dataitem) {
              if (item.prop == key) {
                item.value = dataitem[key];
              }
            }
          });
        });

        this.dialogVisible = true;
        this.dialogTitle = val + "字典项";
      }

      if (val.search("删除") != -1) {
        this.$nextTick(() => {
          var _this = this;
          //仅支持单条编辑
          if (JSON.parse(JSON.stringify(this.listData)).length != 1) {
            //警告
            this.$message({
              message: "请选择一条数据进行删除操作!",
              type: "warning",
            });
            return;
          }
          //结构剖析
          var newListData = JSON.parse(JSON.stringify(this.listData));

          ElMessageBox.confirm("确认删除这条信息吗?", "警告", {
            confirmButtonText: "确定",
            cancelButtonText: "取消",
            type: "warning",
          })
            .then(() => {
              _this.DeleteFormDatas(newListData[0]);
            })
            .catch(() => {});
        });
      }
    },
    //清空表单数据,解决选中某行时,点击新增按钮,响应ConfigCondition参数的清空以及取消选择
    CloseForm() {
      this.$nextTick(() => {
        //循环表单清空
        this.ConfigCondition.forEach((item) => {
          item.value = "";
        });
        //清空选择
        this.$refs.tableRef.ClearSelect();
      });
    },
  },
};
</script>

<style lang="scss" scoped>
.el-divider--vertical {
  display: inline-block;
  width: 1px;
  height: 53em;
  margin: 0 8px;
  vertical-align: middle;
  position: relative;
  border-left: 1px var(--el-border-color) var(--el-border-style);
}
</style>
相关推荐
天天进步20156 分钟前
Vue+Springboot用Websocket实现协同编辑
vue.js·spring boot·websocket
虾球xz17 分钟前
游戏引擎学习第20天
前端·学习·游戏引擎
我爱李星璇22 分钟前
HTML常用表格与标签
前端·html
疯狂的沙粒26 分钟前
如何在Vue项目中应用TypeScript?应该注意那些点?
前端·vue.js·typescript
小镇程序员42 分钟前
vue2 src_Todolist全局总线事件版本
前端·javascript·vue.js
野槐44 分钟前
前端图像处理(一)
前端
程序猿阿伟1 小时前
《智能指针频繁创建销毁:程序性能的“隐形杀手”》
java·开发语言·前端
疯狂的沙粒1 小时前
对 TypeScript 中函数如何更好的理解及使用?与 JavaScript 函数有哪些区别?
前端·javascript·typescript
瑞雨溪1 小时前
AJAX的基本使用
前端·javascript·ajax
力透键背1 小时前
display: none和visibility: hidden的区别
开发语言·前端·javascript