Skip to content

DynamicCascadeInput

级联动态录入

基本使用

效果

:
:
:

结果

{
  "a": {
    "b": {
      "c": {
        "d": {
          "e": "hello world"
        }
      }
    }
  },
  "aa": [
    5,
    2,
    0
  ],
  "aaa": 1314
}
vue

<script setup lang="ts">
  import {ref} from 'vue'
  import {DynamicCascadeInput, type dynamicCascadeInputRef} from 'dynamicformdjx'

  const test = ref({
    a: {
      b: {
        c: {
          d: {
            e: "hello world"
          }
        }
      }
    },
    aa: [5, 2, 0],
    aaa: 1314
  })

  const dyRef = ref<dynamicCascadeInputRef | null>(null)

  const setData = () => {
    dyRef.value?.onSet({test: 'helloWorld'})
  }
</script>

<template>
  <p>Base</p>
  <DynamicCascadeInput v-model="test" ref="dyRef" is-controller/>
  <pre>{{ test }}</pre>
  <div>
    <button @click="setData">setData</button>
  </div>
</template>
vue

<script setup>
  import {ref} from 'vue'
  import {DynamicCascadeInput} from 'dynamicformdjx'

  const test = ref({
    a: {
      b: {
        c: {
          d: {
            e: "hello world"
          }
        }
      }
    },
    aa: [5, 2, 0],
    aaa: 1314
  })

  const dyRef = ref(null)

  const setData = () => {
    dyRef.value?.onSet({test: 'helloWorld'})
  }
</script>

<template>
  <p>Base</p>
  <DynamicCascadeInput v-model="test" ref="dyRef" is-controller/>
  <pre>{{ test }}</pre>
  <div>
    <button @click="setData">setData</button>
  </div>
</template>

插槽使用

Cascade dynamicInput

:
 
:
 
:
 
{
  "a": {
    "b": 111
  },
  "aa": [
    5,
    2,
    0
  ],
  "aaa": 1314
}
vue

<script setup>
  import {ref} from 'vue'
  import {DynamicInput} from 'dynamicformdjx'

  const test = ref({
    a: 'Hello world',
    b: 1314,
    c: [5, 2, 0]
  })
</script>

<template>
  <DynamicInput v-model="test" ref="dyRef" is-controller>
    <template #newBtn="{newItem}">
      <button @click="newItem">新</button>
    </template>
    <template #resetBtn="{reset}">
      <button @click="reset">重置</button>
    </template>
    <template #mergeBtn="{merge}">
      <button @click="merge">合并</button>
    </template>
    <template #typeTools="{row,toggleArray,toggleNumber}">
      <button @click="toggleArray" :class="row.isArray?'act':''">Array</button>&nbsp;
      <button @click="toggleNumber" :class="row.isNumber?'act':''">Number</button>
    </template>
    <template #rowActions="{isLast,addItem,removeItem}">
      <button @click="addItem" :disabled="!isLast">+</button>
      <button @click="removeItem">-</button>
    </template>
    <template #newChild="{addChild,row}">
      <button @click="addChild">+{{ row.key }}+</button>
    </template>
  </DynamicInput>
</template>
<style scoped>
  .act {
    background: skyblue;
  }
</style>

API

Props

属性名说明类型默认值必填
depth子层深度number3
isController受控属性boolean
dyCls动态表单容器的自定义 CSS 类名string
randomFun生成每个动态表单项唯一 ID 的函数Function(i?: number) => \${Date.now()}_${i ?? 0}``
newChildTxt新增child函数Function(it: DyCasFormItem) => \`添加 '${it.key}' 子项```
btnConfigs按钮文案配置(重置 / 新增 / 合并)object{ resetTxt: "重置", newTxt: "添加项", mergeTxt: "合并" }
configs表单行为配置,如最大高度、是否允许筛选等object{ hideReset: false, maxHeight: "600px", allowFilter: true,showBorder: true,showPad: true,retractLen: 0,borderColors: [], }
dyListConfigs动态列表项配置,例如数组分隔符等object{ arraySplitSymbol: "," }
modelValue绑定到表单的模型值,父组件传入并与表单同步(支持 v-model / model-valueobject

Emits

事件名说明回调参数
update:modelValue当表单值变化时触发,返回新的模型值(value: object)
onReset当用户点击重置时触发
onMerge当表单数据合并时触发,返回合并后的数据和原始数据(merged: object, origin: object[])

Expose

方法名参数说明返回值描述
onSet(o?: object)o = object → 设置新表单数据
o = undefined → 重置表单
void设置或重置表单数据
getResult(t = 'res')t = 'res' → 获取当前最终结果
t = 'ori' → 获取渲染时数组
object / array获取表单内部数据结构

Slots

  • 所有插槽均为 具名插槽,在 TSX 中通过 v-slots 传入。
  • 插槽函数返回 VNode[]

类型

ts
type CasScopeType = {
    row: {
        rId: string
        key: string
        value: string
        isArray?: boolean
        isNumber?: boolean
    }
    index: number
    isLast: boolean
    addItem: () => void
    removeItem: () => void
    toggleArray: () => boolean
    toggleNumber: () => boolean
    addChild: () => void
}

插槽列表

插槽名参数参数类型描述
newBtn{ newItem }{ newItem: () => void }自定义「新增按钮」区域。调用 newItem() 触发新增一行。
resetBtn{ reset }{ reset: () => void }自定义「重置按钮」区域。调用 reset() 重置数据。
mergeBtn{ merge }{ merge: () => void }自定义「合并按钮」区域。调用 merge() 执行合并逻辑。
typeToolsscopeCasScopeType自定义每一行的类型工具区(如 Array/Number 切换)。可使用 toggleArray() / toggleNumber() 等。
rowActionsscopeCasScopeType自定义每一行的操作区(如 + / -)。可使用 addItem() / removeItem(),并通过 isLast 控制最后一行才能新增等。
newChildscopeCasScopeType自定义每一行子层的新增区。可使用 addChild(),次插槽优先级高于propsnewChildTxt

Extra Use

如果你项目使用了Naive UiElement Plus,可使用下方导入

vue

<script setup lang="ts">
  // 依赖于naive-ui
  import {NaiDynamicCascadeInput} from "dynamicformdjx/naiveUi";
  // 依赖于element-plus
  import {EleDynamicCascadeInput} from "dynamicformdjx/elementPlus";

  const test2 = ref<{ d: number[] }>({
    d: [6, 6, 6]
  })
  const test3 = ref<{ e: string }>({
    e: "victory"
  })
</script>

<template>
  <div>
    <p>Base on NaiveUi</p>
    <nai-dynamic-cascade-input v-model="test2"
                               is-controller
    />
    <pre>{{ test2 }}</pre>
    <p>Base on element plus</p>
    <ele-dynamic-cascade-input v-model="test3"
                               :dy-list-configs="{arraySplitSymbol:'-'}"
    />
    <pre>{{ test3 }}</pre>
  </div>
</template>