element ui form 表单 二次封装 (行内表单和基础表单)

新建一个form文件,封装支持输入框,时间,日期选择器,单选框。

<template>
  <div :class="inline == true ? 'the-form' : ''">
    <el-form
      :model="tempFormData"
      :label-width="labelWidth"
      :width="formWidth"
      :inline="inline"
      :loading="loading"
      ref="form"
      :size="size"
    >
      <el-form-item
        v-for="item in tempFormItems"
        :label="item.label ? item.label + ':' : ''"
        :key="item.prop"
        :prop="item.prop"
        :rules="item.rules"
      >
        <!-- 输入框 -->
        <el-input
          v-if="item.type === 'Input' && !view"
          v-model="tempFormData[item.prop]"
          :style="{ width: item.width }"
          :disabled="item.disable"
          :placeholder="item.placeholder ? item.placeholder : '请输入' + item.label"
        >
        </el-input>
        <template v-if="view">
          <span v-text="tempFormData[item.prop]"></span>
        </template>
        <!-- 数字输入框 -->
        <el-input
          type="number"
          :min="1"
          v-if="item.type === 'inputNumber' && !view"
          v-model.number="tempFormData[item.prop]"
          :style="{ width: item.width }"
          :disabled="item.disable"
          :placeholder="item.placeholder ? item.placeholder : '请输入' + item.label"
        >
        </el-input>
        <template v-if="view">
          <span v-text="tempFormData[item.prop]"></span>
        </template>
        <!-- 下拉框 filterable 是否可搜索 默认是false  multiple 是否多选 默认false-->
        <el-select
          v-if="item.type === 'Select'"
          :multiple="item.multiple"
          :filterable="item.filterable"
          v-model="tempFormData[item.prop]"
          :style="{ width: item.width }"
          :disabled="item.disable"
          :placeholder="item.placeholder ? item.placeholder : '请选择' + item.label"
          :remote="item.remote"
          :remote-method="
            (query) => {
              remoteMethod(query, item.prop);
            }
          "
          clearable
        >
          <el-option
            v-for="op in item.options.data"
            :label="op[item.options.value] || op.value"
            :value="op[item.options.key] || op.key"
            :key="op[item.options.key] || op.key"
          >
          </el-option>
        </el-select>

        <!-- 日期 -->
        <el-date-picker
          v-if="item.type === 'Date'"
          v-model="tempFormData[item.prop]"
          :disabled="item.disable"
          :placeholder="item.placeholder ? item.placeholder : '请选择日期'"
          clearable
        >
        </el-date-picker>

        <!-- 时间 -->
        <el-time-select
          v-if="item.type === 'Time'"
          v-model="tempFormData[item.prop]"
          :disabled="item.disable"
          :placeholder="item.placeholder ? item.placeholder : '请选择时间'"
          clearable
        >
        </el-time-select>

        <!-- 日期时间 -->
        <el-date-picker
          v-if="item.type === 'DateTime'"
          type="datetime"
          v-model="tempFormData[item.prop]"
          :disabled="item.disable"
          :placeholder="item.placeholder ? item.placeholder : '请选择日期'"
          clearable
        >
        </el-date-picker>

        <!-- 日期范围 -->
        <el-date-picker
          v-if="item.type === 'datetimerange'"
          type="datetimerange"
          v-model="tempFormData[item.prop]"
          :disabled="item.disable"
          range-separator="至"
          start-placeholder="开始日期"
          end-placeholder="结束日期"
          clearable
        >
        </el-date-picker>

        <!-- 单选框 普通的样式 Radio 的尺寸,仅在 border 为真时有效-->
        <template v-if="item.type === 'radio'">
          <el-radio
            v-model="tempFormData[item.prop]"
            v-for="op in item.options.data"
            :disabled="item.disable"
            :border="tempFormData[item.border]"
            :size="tempFormData[item.size]"
            :label="op[item.options.value] || op.value"
            :value="op[item.options.key] || op.key"
            :key="op[item.options.key] || op.key"
          ></el-radio>
        </template>

        <!-- 单选框 按钮样式 -->
        <el-radio-group
          v-if="item.type === 'radioButtom'"
          v-model="tempFormData[item.prop]"
          :size="tempFormData[item.size]"
          :disabled="item.disable"
        >
          <el-radio-button
            v-for="op in item.options.data"
            :label="op[item.options.value] || op.value"
            :value="op[item.options.key] || op.key"
            :key="op[item.options.key] || op.key"
          ></el-radio-button>
        </el-radio-group>

        <!-- 文本框 -->
        <el-input
          v-if="item.type === 'textarea' && !view"
          v-model="tempFormData[item.prop]"
          type="textarea"
          :style="{ width: item.width }"
          :disabled="item.disable"
          :rows="item.row"
          :autosize="item.autosize"
          :placeholder="item.placeholder ? item.placeholder : '请输入' + item.label"
        >
        </el-input>
      </el-form-item>
      <!-- 查询按钮 de-->
      <span v-if="inline">
        <el-form-item v-show="show">
          <el-button type="primary" @click="handleSearch" :btnLoading="btnLoading">
            {{ formBtn }}
          </el-button>
        </el-form-item>
      </span>
    </el-form>
  </div>
</template>

<script>
import { deepClone } from "@/utils";
export default {
  props: {
    view: {
      type: Boolean,
      default: false,
    },
    formBtn: {
      type: String,
      default: "查询",
    },
    btnLoading: {
      type: Boolean,
      default: false,
    },
    loading: {
      //加载
      type: Boolean,
      default: false,
    },
    isBtnSave: {
      type: Boolean,
      default: false,
    },
    // 由inline属性决定form表单是普通表单,还是行内表单
    inline: {
      //排列方式
      type: Boolean,
      default: true,
    },
    isSearch: {
      //是否展示搜索按钮
      type: Boolean,
      default: true,
    },
    labelWidth: {
      type: String,
      default: "120px",
    },
    formWidth: {
      //form表单宽度
      type: String,
      default: "200px",
    },
    formItems: {
      type: Array,
      default: [],
    },
    formData: {
      type: Object,
      default: function () {
        return {};
      },
    },
    // 用于控制该表单内组件的尺寸 medium / small / mini
    size: {
      type: String,
      default: "medium",
    },
  },
  computed: {},
  watch: {
    formData: {
      handler(val) {
        this.tempFormData = val;
      },
      deep: true,
      immediate: true,
    },
    formItems: {
      handler(val) {
        this.tempFormItems = deepClone(val);
      },
      deep: true,
      immediate: true,
    },
  },
  data() {
    return {
      show: true,
      tempFormData: {},
      tempFormItems: [],
    };
  },
  methods: {
    // 远程搜索
    remoteMethod(value, type) {
      this.$emit("remoteMethod", value, type);
    },
    // 行内表单搜索事件
    handleSearch() {
      this.$emit("handleSearch");
    },
    // 清空form表单事件
    resetFields() {
      this.$refs.form.resetFields();
    },
  },
};
</script>

如何在父组件中使用封装好的form表单,这里我在全局注册了一个<j-el-dialog>组件,下面是行内表单的用法

<template>
  <div class="page">
    <j-el-form
      :formData="formData"
      :formItems="formItems"
      :btnLoading="btnLoading"
      @handleSearch="handleSearch"
    />
  </div>
</template>
<script>
export default {
  data() {
    return {
      formItems: [],
      formData: {},
      btnLoading: false,
    };
  },
  created() {
    this.initFormItems();
  },
  methods: {
    initFormItems() {
      this.formItems = [
        {
          type: "Input",
          name: "keywords",
          prop: "keywords",
          placeholder: "请输入用户名",
        },
        {
          type: "Select",
          name: "keywods",
          prop: "keywods",
          placeholder: "请选择角色",
          options:{
            data:[],
            key:""  //传给后台的value
            value:"" //要展示的数据
          }
        },
      ];
    },
    handleSearch() {},
  },
};
</script>

  • 1
    点赞
  • 8
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值