vue3+tsx 组件如何传递泛型

2024-03-31阅读(99)评论(0)牵着狗狗看MM

苏州实时公交查询

组件传递泛型(vue3.3+)

官方提供了函数签名,但实际使用非常不方便,仍然需要手动声明运行时的 props(虽然官方计划提供一个 Babel 插件,自动推断并注入运行时 props ,以便省略运行时 props 的声明,截至目前还没有提供),不如直接用defineComponent定义组件

const Comp = defineComponent(
  <T extends string | number>(props: { msg: T; list: T[] }) => {
    // 就像在 <script setup> 中一样使用组合式 API
    const count = ref(0)

    return () => {
      // 渲染函数或 JSX
      return <div>{count.value}</div>
    }
  },
  // 目前仍然需要手动声明运行时的 props
  {
    props: ['msg', 'list']
  }
)

但是直接用defineComponent定义组件的话,组件之间如何传递泛型就是一个非常头疼的问题,总不能在父组件在子组件emits的方法中再声明一次返回体类型,这样很繁琐,我们希望的是,使用子组件时,只需声明一次需要支持的泛型类型即可,这里可以使用函数封装一下

export default function defineGenericComponent<T>() {
    return defineComponent(...) //defineComponent是实际子组件内容
}

下面用一个实际的例子来说明

// Parent.tsx
import { defineComponent, ref, Ref, onMounted } from 'vue'
import Child from './Child'

interface DataItem {
    name: string
}

const ChildCom = Child<DataItem>()

export default defineComponent({
    setup() {
        onMounted(() => {
            console.log('onMounted') //生命周期
        })

        return () => (
            <ChildCom
                onSelectionChange={(res) => {
                    console.log(res)
                }}
            />
        )
    },
})


// Child.tsx
import { defineComponent, onMounted } from 'vue'

export default function defineGenericComponent<T>() {
    //defineComponent是实际子组件内容
    return defineComponent({
        props: {
            data: {
                type: Array as PropType<T[]>,
                default: () => [],
            },
        },
        emits: {
            selectionChange: (val: T[]) => true,
        },
        setup(props, { emit }) {
            onMounted(() => {
                console.log('onMounted') //生命周期
            })

            return () => (
                <div
                    onClick={() => {
                        emit('selectionChange', props.data)
                    }}
                >
                    child
                </div>
            )
        },
    })
}

通过如上方式引用子组件后,父组件在使用Child组件时,就有emit方法的提示,且能正常显示onSelectionChange的返回体类型声明

赞(1)
转载请注明来源:Web前端(W3Cways.com) - Web前端学习之路 » vue3+tsx 组件如何传递泛型
分享到: 更多 (0)