Description
This is a follow up of #7740 (comment)
Rational
Problems with current scoped slot usage:
- Verbose if using
<template slot-scope>
- Limited to one element/component is using
slot-scope
directly on the slot element.
Proposal
Introduce a new v-scope
directive, that can only be used on components:
<comp v-scope="scope">
{{ scope.msg }}
</comp>
It would work the same as slot-scope
for the default scoped slot for <comp>
(with <comp>
providing the scope value). So it also works with deconstructing:
<comp v-scope="{ msg }">
{{ msg }}
</comp>
Why a New Directive
I believe the team briefly discussed what I proposed in #7740 (comment) on Slack some time back, but I could no longer find the chat record. Here's the reasoning behind a new directive:
-
slot-scope
was introduced as a special attribute instead of a directive (attributes that start withv-
prefix) becauseslot
is an attribute, and we wanted to keep slot-related attributes consistent.slot
was in turn introduced as a non-directive attribute because we want the usage to mirror the actual slot usage in the Shadow DOM standard. We figured it would be best to avoid having our own parallelv-slot
when there's something that is conceptually the same in the standard. -
Originally,
slot-scope
was designed to be only usable on<template>
elements that act as abstract containers. But that was verbose - so we introduced the ability to use it directly on a slot element without the wrapping<template>
. However, this also makes it impossible to allow usingslot-scope
directly on the component itself, because it would lead to ambiguity as illustrated here. -
I thought about adding modifiers or special prefixes to
slot-scope
so that that we can use it on a component directly to indicate its slot content should be treated as the default scoped slot, but neither a modifier or a prefix like$
seem to be the right fit. The modifier by design should only be applied to directives, while new special syntax for a single use case is inconsistent with the whole syntax design. -
For a very long time we've shied away from adding more directives, part of it being template syntax is something we want to keep as stable as possible, part of it being that we want to keep core directives to a minimum and only do things that users cannot easily do in userland. However, in this case scoped slot usage is important enough, and I think a new directive can be justified for making its usage significantly less noisy.
Concerns
-
The expression accepted by
v-scope
is different from most other directives: it expects a temporary variable name (which can also be a deconstruction), but not without a precedence: it acts just like the alias part ofv-for
. So conceptuallyv-scope
falls into the same camp withv-for
as a structural directive that creates temporary variables for its inner scope. -
This would break the users code if the user has a custom directive named
v-scope
and is used on a component.-
Since custom directives in v2 are primarily focused on direct DOM manipulations, it's relatively rare to see custom directives used on components, even more so for something that happens to be called
v-scope
, so the impact should be minimal. -
Even in the case of it actually happening, it is straightforward to deal with by simply renaming the custom directive.
-