use slotted() in component is not working when use transition element
Version
3.0.4
Reproduction link
https://github.com/pgy108103/vue3_vite_issue_sample
Steps to reproduce
Change hasTransition flage in todo.vue, you will see that.
What is expected?
I want transition elements to be used with components that use slotted()
What is actually happening?
As title.
const setScopeId = (
el: RendererElement,
scopeId: string | false | null,
vnode: VNode,
parentComponent: ComponentInternalInstance | null
) => {
if (scopeId) {
hostSetScopeId(el, scopeId)
}
if (parentComponent) {
const treeOwnerId = parentComponent.type.__scopeId
// vnode's own scopeId and the current patched component's scopeId is
// different - this is a slot content node.
if (treeOwnerId && treeOwnerId !== scopeId) {
hostSetScopeId(el, treeOwnerId + '-s')
}
//.....
}
}
caused by: scopeId
is incorrectly set, causing css
to not take effect.
if slot's parentComponent
is Transition
or KeepAlive
.parentComponent.type.__scopeId
is null
,but parentComponent.subTree.scopeId
has the correct value.
@edison1105 Your fix does not solve the real cause. And there are problems according to your changes, let's say if the Transition
has an out-in
mode, then the subtree
may be undefined
. I made another PR, see https://github.com/vuejs/vue-next/pull/3150
@edison1105 Your fix does not solve the real cause. And there are problems according to your changes, let's say if the
Transition
has anout-in
mode, then thesubtree
may beundefined
. I made another PR, see #3150
Nice to know this and I will close my PR.
Update: the root cause of this is flawed implementation of :slotted
scoped id logic. Currently, the following fails:
<Comp>
<slot/>
</Comp>
<style scoped>
:slotted(*) { color: red }
</style>
#3150 only special cases internal components like Transition, but the ideal behavior is for :slotted
to be able to affect elements inside <slot/>
regardless of whether it's passed to another component's slot.
I'm working on a fix for this but it requires a pretty substantial refactor and may take a while.