Reputation: 2022
With Vue 2, we could use this.$children
to get all the children components in the component slot. But with Vue 3 this is not possible anymore. And I couldn't find anything about an alternative or a workaround!
So, can anyone help with that? :)
What I want to achieve is:
To have a component with let's say name TabsView
And I want to use it like this:
<tabs-view>
<tabs-title target="tab1">Title1</tabs-title>
<tab-content name="tab1">...</tab-content>
<tabs-title target="tab2">Title2</tabs-title>
<tab-content name="tab2">...</tab-content>
<tabs-view>
And I want all the logic inside the TabsView component. So that is why I want to get the $children within it. So I can build the tabs using the values of the children components.
Because I will use the same to build tabs in different many places. And I don't want to copy the logic with refs. unless there is a way to do that with refs without moving the same logic to every place I use the component
Upvotes: 4
Views: 2045
Reputation: 35694
You can either use this.$el.parentElement.children
to get the DOM elements, but that won't give you the components. this: this.$.subTree.children
will give you the children, which will include DOM elements and the components.
But this functionality is likely kept hidden for a reason, so if @Guillaume F wants you to consider an alternate solution, I'd heed his advice.
example:
const app = Vue.createApp({
data() {
return {
color: null
}
},
mounted() {
const children = this.$.subTree.children
console.log(children.map(c => c.type))
}
})
app.component('tabs-title', {
template: '<h1>TITLE: <slot></slot></h1>'
})
app.component('tab-content', {
template: '<p>TAB: <slot></slot></p>'
})
app.mount('#app')
<script src="https://unpkg.com/[email protected]/dist/vue.global.prod.js"></script>
<div id="app">
<tabs-title target="tab1">Title1</tabs-title>
<tab-content name="tab1">...</tab-content>
<hr/> <!-- will return string as type -->
<tabs-title target="tab2">Title2</tabs-title>
<tab-content name="tab2">...</tab-content>
</div>
Upvotes: 2