Replies: 7 comments 2 replies
-
<Page>
<PageHeader>
header content goes here
</PageHeader>
<PageBody>
body goes here
</PageBody>
</Page> The above code means the same as the following code in terms of the current semantics: <Page>
<template v-slot:default>
<PageHeader>
header content goes here
</PageHeader>
<PageBody>
body goes here
</PageBody>
</template>
</Page> So I think it's probably the biggest obstacle to supporting this feature. |
Beta Was this translation helpful? Give feedback.
-
Yes, I realise this. However, since a component in itself is a template, it feels like we have nested tags now. I very much know it might be a breaking change, but it still feels like one I would enjoy ;-) |
Beta Was this translation helpful? Give feedback.
-
This is not even a breaking change, strictly speaking, but it inverts responsibilities and opens up a lot of questions both technically and from a DX perspective.
<!-- fine -->
<Page>
<PageHeader>
header content goes here
</PageHeader>
<PageBody>
body goes here
</PageBody>
</Page>
<! --- lets add a wrapper div for some positioning -->
<Page>
<PageHeader>
header content goes here
</PageHeader>
<div> <!-- oh no, that div now ends up in the default slot! -->
<PageBody>
body goes here
</PageBody>
<div>
</Page>
<!-- sso we refactor to: -->
<Page>
<PageHeader>
header content goes here
</PageHeader>
<template v-slot:body>
<div>
<PageBody>
body goes here
</PageBody>
<div>
</template>
</Page> I'm sure a lot more questions would pop up. I would therefore like to move this to the discussions area. If a proper proposal would come of this, an RFC could be written and officially proposed in the |
Beta Was this translation helpful? Give feedback.
-
Hi @LinusBorg, Thanks for the reply, and yes: I totally agree with your remarks / views.
|
Beta Was this translation helpful? Give feedback.
-
slot content is compiled into a function which is passed down to the child component. This function has a closure over the parent template, but is run in the child, so the child collects the reactive dependencies (so that the child re-rendered when they change, not the parent. So the compiler has to know - while processing the parent component - which part of the slot content has to be wrapped in a function, and into which slot it has to be passed. h(Parent, {}, {
header: () => h(PageHeader)
default: () => h(PageBody)
})
So far, the compiler can process each SFC completely on its own. it's not important what other SFCs contain in order for the compiler to do its work. Your proposal would require a re-work of the compiler to process the child components of an SFC as well, in order to understand which slot they belong in. Further: Vue allows for components to be globally registered. Now the compiler would have to somehow know which components from the template are registered globally, and where to find their code, in order to check which slot they belong in, and so forth. Also, components could be imported from a precomiled package in Just a giant complexity increase.
I find this to be a limited use case that so far, doesn't warrant the complexity and work is would bring with it.
I personally am not a fan of the implicit context-dependent behavior this proposal would introduce, just for saving keystrokes. An RFC is a lot of work and needs someone who believes in the proposal and is willing to work for it. I am not that person. You either need to be that yourself or find someone willing to be. PSA: I'll move this to discussions. |
Beta Was this translation helpful? Give feedback.
-
How about adding <ComponentWithSlot>
<Foo v-slot:bar>whatever</Foo>
</ComponentWithSlot> would still be <ComponentWithSlot>
<Foo>
<template v-slot:bar>whatever</template>
</Foo>
</ComponentWithSlot> but <ComponentWithSlot>
<Foo v-slot:bar.self>whatever</Foo>
</ComponentWithSlot> would be <ComponentWithSlot>
<template v-slot:bar>
<Foo>whatever</Foo>
</template>
</ComponentWithSlot> That sounds quite simple, but the drawback is that slot name can contain a dot, so |
Beta Was this translation helpful? Give feedback.
-
I've been contemplating ways to address the issue of code verbosity when working with named slots. The template can get quite ugly with all these I wonder if it's possible to create a directive that could improve this. something like this:
Okay, I understand that this might not be feasible, but how challenging could it be to define slot names in components where I want to assign slots, like in the following example?
|
Beta Was this translation helpful? Give feedback.
-
What problem does this feature solve?
We were currently working on a new UI component library where we want to try and keep the work for devs using it as minimal as possible. Let's consider we have a Page component that comes with a Header and a Body. The Header consists of a Title, and an Icon, and we can have some action buttons.
Keeping our devs in mind, we want to allow them to be able to do the following:
Now obviously we don't want the devs to alwahs have to think about how to structure the child components or in what order to pass them in. Our UX designer might like the icon to the left and the buttons to the right of the screen, but he might change his mind later down the road... So: enter named slots.
Just looking at the PageHeader, we would create a component like this:
PageHeader.vue
Now this all works brilliantly, but now to pass down the content to the right scope, a developer would have to do the following:
This gets a bit verbose to me, so I was looking at the short hands that are supported
When there is only one slot passed down, we can get rid of the
template
tags becauseis a shorthand for
But I can't get around the idea that this shorthand is a little useless. Most of the times, you would be naming your slots exactly because you have more than one in a parent component, so those are the use cases where the shorthand doesn't work.
in an ideal world, I want my devs to not having to worry about this, and just be able to nest the components and have the components do their work
What does the proposed API look like?
So building on the example above, we would really like it if we could build our components as follows:
Page.vue
PageHeader.vue
PageBody.vue
then when we are creating a page, we could just do this:
and vue would know that the pageheader and pagebody components would need to go into the slots named header and body respectively as defined in the Page component.
I've been trying to bend my mind as to why the shorthand doesn't work like this to begin with, but I'm sure I'm missing some info there, so feel free to let me know.
But when creating UI components like this, I believe somehing like this would really make things easier, and clean up a lot of the code we sometimes have.
Beta Was this translation helpful? Give feedback.
All reactions