Existe-t-il un moyen de déclarer la fourniture/injection dans un composant dynamique Vue3 en dehors de la fonction de paramètres de l'hôte ?
P粉384366923
P粉384366923 2023-08-30 09:41:50
0
1
523
<p>Je crée un <code>Composant dynamique</code> dans <code>Vue3</code>. J'utilise <code>v-bind</code> pour fournir <code>props</code>. </p> <pre class="lang-js Prettyprint-override"><code><component :is='MyComponent' v-bind='myProps' /> </code></pre> <p>Je souhaite fournir/injecter</code> une fonctionnalité à l'aide de <code>. Comment puis-je mettre les propriétés que je fournis dans le composant dynamique. Mon composant dynamique appelle <code>inject</code> dans la fonction <code>setup</code> et attend une valeur </code> </p> <p>Bien que cela ne soit pas documenté sur Vue, je l'ai essayé sans succès : </p> <pre class="brush:php;toolbar:false;"><component :is='MyComponent' v-bind='myProps' :provide='myProvidedProps'/></pre> <p> J'ai même essayé de placer l'objet <code>provide</code> dans l'objet <code>props</code> </p>
P粉384366923
P粉384366923

répondre à tous(1)
P粉122932466

Après avoir parcouru le code source de Vue3, vous ne pouvez pas le 动态组件指示providespécifier directement dans le modèle. Il doit être appelé dans les paramètres de fonction ou d'options du parent hébergeant le composant dynamique, ou dans les paramètres ou options du composant dynamique.

Les deux options sont :

  1. Vous faites appel à provide sur le composant qui héberge le composant dynamique.
setup() {
  provide('message', 'hello')
}
<template>
  <component :is='myComponent' />
</template>

Cela ne fonctionne pas pour moi car ma fonction setter est appelée avant que mon composant dynamique ne soit activé ; j'ai également besoin que le type de composant soit défini avec la valeur fournie.

  1. Envoyez les éléments à fournir comme accessoires dans le composant et laissez le composant dynamique les appeler.
function setComponent(someImportedComponent, providedValues) {
  myComponent.value = someImportedComponent
  myProps.value = {
    toProvide: providedValues
  }
}
<template>
  <component :is='myComponent' v-bind='myProps' />
</template>

Mes composants

setup() {
  for(let [key,value] of Object.entries(props.toProvide) ) {
    provide(key, value)
  }
}

Maintenant, cela a ses problèmes, car chaque composant dynamique doit désormais être responsable de la compréhension et de l'appel du fournisseur entrant.

Solution 1

La solution pour que chaque composant ait besoin de connaître la valeur fournie est de créer un composant intermédiaire qui fournit la valeur.

Disponible (composants intermédiaires)

<script setup lang="ts">
import {provide} from 'vue'

const props = defineProps<{
  is: any
  provide?: Record<string, any>
  [key: string]: any
}>()

if (props.provide) {
  for (const [key, value] of Object.entries(props.provide)) {
    provide(key, value)
  }
}

const _props = Object.fromEntries(Object.entries(props).filter(it => {
  return it[0] !== 'is' && it[0] !== 'provide'
}))
</script>

<template>
  <component :is="is" v-bind="_props"/>
</template>

Utilisez-le comme ceci :

<template>
  <providable :is="myComponent" :provide='toProvide' v-bind='myProps' />
</template>

Solution 2

Une solution plus propre consiste à créer un composant wrapper, similaire au fonctionnement de keep-alive. Il suffit de mettre le composant cible 默认槽.

fourni.vue

<script setup lang="ts">
import {provide} from 'vue'

const props = defineProps<{
  value: Record<string, any>
}>()

for (const [key, value] of Object.entries(props.value)) {
  provide(key, value)
}
</script>

<template>
  <slot name="default"/>
</template>

et utilisez-le comme ceci :

<template>
  <provide value='toProvide'>
    <my-component v-bind='myProps' />
  </provide>
</template>
Derniers téléchargements
Plus>
effets Web
Code source du site Web
Matériel du site Web
Modèle frontal