xinnian999 / vue-form-craft

基于vue3的一款开箱即用表单方案
283 stars 21 forks source link

能否支持移动端布局 #12

Closed kscale closed 4 months ago

kscale commented 7 months ago

能否支持移动端布局,感谢。 自定义组件中引入vant 组件,经测试,部分可行。Checkbox,Radio 怎么去对应options? 图片

import {Field, RadioGroup, Radio,CheckboxGroup,Checkbox} from 'vant';

app.use(VueFormCraft, {
    customElements: {
        Checkbox: {
            component: Checkbox,
            modelName: 'modelValue',
        },
        Radio: {
            component: Radio,
            modelName: 'modelValue',
        }
    }
})
{
      "label": "多选框组",
      "component": "Checkbox",
      "props": {
        "placeholder": "请选择...",
        "mode": "static",
        "options": [
          {
            "label": "选项1",
            "value": "value1"
          },
          {
            "label": "选项2",
            "value": "value2"
          }
        ],
        "labelKey": "label",
        "valueKey": "value",
        "optionType": "circle"
      },
      "designKey": "design-M6j0",
      "name": "form-uFWC"
    },
xinnian999 commented 7 months ago

设计器原Radio等组件都被二次封装过,然后通过接受options在内部循环渲染的选项。如果你需要定制Radio等选择类的组件,就也需要二次封装后,再传给设计器

<template>
  <div v-if="!currentOptions.length && !loading" style="font-size: 12px">暂无选项</div>
  <el-radio-group v-model="selectVal" @change="selectChange" v-loading="loading" v-bind="$attrs">
    <el-space wrap :direction="direction" :size="[space, space]" alignment="normal">
      <template v-if="optionType === 'circle' || optionType === 'border'">
        <el-radio
          v-for="item in currentOptions"
          :key="item[valueKey]"
          :label="item[valueKey]"
          :border="optionType === 'border'"
          >{{ item[labelKey] }}</el-radio
        >
      </template>

      <template v-else>
        <el-radio-button
          v-for="item in currentOptions"
          :key="item[valueKey]"
          :label="item[valueKey]"
          :size="$attrs.size"
          >{{ item[labelKey] }}
        </el-radio-button>
      </template>
    </el-space>
  </el-radio-group>
</template>

<script setup>
import { defineProps, defineEmits } from 'vue'
import { ElRadioGroup, ElRadio, ElRadioButton, ElSpace } from 'element-plus'
import useSelect from '@/hooks/useSelect'

const props = defineProps({
  modelValue: {},
  options: {
    type: Array,
    default: () => []
  },
  mode: {
    type: String,
    default: 'static'
  },
  labelKey: {
    type: String,
    default: 'label'
  },
  valueKey: {
    type: String,
    default: 'value'
  },
  autoSelectedFirst: {
    type: Boolean,
    default: false
  },
  api: Object,
  name: String,
  optionType: {
    type: String,
    default: 'circle'
  },

  direction: {
    type: String,
    default: 'horizontal'
  },
  space: {
    type: Number,
    default: 20
  }
})

const emits = defineEmits(['update:modelValue', 'onChangeSelect'])

const { selectVal, currentOptions, selectChange, loading } = useSelect(props, emits)
</script>