File tree Expand file tree Collapse file tree 3 files changed +67
-2
lines changed
test/unit/modules/vdom/patch Expand file tree Collapse file tree 3 files changed +67
-2
lines changed Original file line number Diff line number Diff line change @@ -116,6 +116,10 @@ export function lifecycleMixin (Vue: Class<Component>) {
116116 const vm : Component = this
117117 const hasChildren = ! ! ( vm . $options . _renderChildren || renderChildren )
118118 vm . $options . _parentVnode = parentVnode
119+ vm . $vnode = parentVnode // update vm's placeholder node without re-render
120+ if ( vm . _vnode ) { // update child tree's parent
121+ vm . _vnode . parent = parentVnode
122+ }
119123 vm . $options . _renderChildren = renderChildren
120124 // update props
121125 if ( propsData && vm . $options . props ) {
Original file line number Diff line number Diff line change @@ -505,9 +505,13 @@ export function createPatchFunction (backend) {
505505 createElm ( vnode , insertedVnodeQueue )
506506
507507 // component root element replaced.
508- // update parent placeholder node element.
508+ // update parent placeholder node element, recursively
509509 if ( vnode . parent ) {
510- vnode . parent . elm = vnode . elm
510+ let ancestor = vnode . parent
511+ while ( ancestor ) {
512+ ancestor . elm = vnode . elm
513+ ancestor = ancestor . parent
514+ }
511515 if ( isPatchable ( vnode ) ) {
512516 for ( let i = 0 ; i < cbs . create . length ; ++ i ) {
513517 cbs . create [ i ] ( emptyNode , vnode . parent )
Original file line number Diff line number Diff line change @@ -57,4 +57,61 @@ describe('vdom patch: edge cases', () => {
5757 expect ( vm . $el . querySelector ( '.d' ) . textContent ) . toBe ( '2' )
5858 } ) . then ( done )
5959 } )
60+
61+ it ( 'should synchronize vm\' vnode' , done => {
62+ const comp = {
63+ data : ( ) => ( { swap : true } ) ,
64+ render ( h ) {
65+ return this . swap
66+ ? h ( 'a' , 'atag' )
67+ : h ( 'span' , 'span' )
68+ }
69+ }
70+
71+ const wrapper = {
72+ render : h => h ( 'comp' ) ,
73+ components : { comp }
74+ }
75+
76+ const vm = new Vue ( {
77+ render ( h ) {
78+ const children = [
79+ h ( 'wrapper' ) ,
80+ h ( 'div' , 'row' )
81+ ]
82+ if ( this . swap ) {
83+ children . reverse ( )
84+ }
85+ return h ( 'div' , children )
86+ } ,
87+ data : ( ) => ( { swap : false } ) ,
88+ components : { wrapper }
89+ } ) . $mount ( )
90+
91+ expect ( vm . $el . innerHTML ) . toBe ( '<a>atag</a><div>row</div>' )
92+ const wrapperVm = vm . $children [ 0 ]
93+ const compVm = wrapperVm . $children [ 0 ]
94+ vm . swap = true
95+ waitForUpdate ( ( ) => {
96+ expect ( compVm . $vnode . parent ) . toBe ( wrapperVm . $vnode )
97+ expect ( vm . $el . innerHTML ) . toBe ( '<div>row</div><a>atag</a>' )
98+ vm . swap = false
99+ } )
100+ . then ( ( ) => {
101+ expect ( compVm . $vnode . parent ) . toBe ( wrapperVm . $vnode )
102+ expect ( vm . $el . innerHTML ) . toBe ( '<a>atag</a><div>row</div>' )
103+ compVm . swap = false
104+ } )
105+ . then ( ( ) => {
106+ expect ( vm . $el . innerHTML ) . toBe ( '<span>span</span><div>row</div>' )
107+ expect ( compVm . $vnode . parent ) . toBe ( wrapperVm . $vnode )
108+ vm . swap = true
109+ } )
110+ . then ( ( ) => {
111+ expect ( vm . $el . innerHTML ) . toBe ( '<div>row</div><span>span</span>' )
112+ expect ( compVm . $vnode . parent ) . toBe ( wrapperVm . $vnode )
113+ vm . swap = true
114+ } )
115+ . then ( done )
116+ } )
60117} )
You can’t perform that action at this time.
0 commit comments